c# - .NET中是否有与Java的ClassFileTransformer等效的文件? (一种替换类的方法)

标签 c# .net reflection classloader instrumentation

到目前为止,我一直在寻找这个应用程序,但是没有运气。 .NET中是否有与Java的ClassFileTransformer等效的文件?基本上,我想创建一个类CustomClassFileTransformer(在Java中将实现接口ClassFileTransformer),该类在加载类时会被调用,并允许对其进行调整并将其替换为经过调整的版本。

我知道有些框架可以做类似的事情,但我一直在寻找更简单的方法,例如实现自己的ClassFileTransformer。可能吗?



编辑#1。有关为何需要此功能的更多详细信息:

基本上,我有一个C#应用程序,我需要监视它要运行的指令,以便检测对字段的读取或写入操作(操作LdfldStfld)并在发生读/写操作之前插入一些指令。

我知道如何执行此操作(除了需要调用以替换该类的那部分):对于要监视其代码的每个方法,我必须:


使用MethodBody获取方法的MethodBase.GetMethodBody()
MethodBody.GetILAsByteArray()将其转换为字节数组。它返回的byte[]包含字节码。
按照here的说明分析字节码,可能通过更改数组的内容来插入新指令或删除/修改现有指令。
使用MethodBuilder.CreateMethodBody(byte[] il, int count)创建一个新方法并使用新的字节码创建其主体,其中il是具有字节码的数组。
我将所有这些经过调整的方法放在一个新类中,并使用新类替换原来要加载的方法。


替换类的一种替代方法是在调用方法时以某种方式得到通知。然后,我将对该方法的调用替换为对自己调整后的方法的调用,该方法仅在第一次调用时进行调整,然后将其放入字典中以备将来使用,以减少开销(对于以后的调用)我只需要查找方法并调用它;就不需要再次分析字节码了。我目前正在研究执行此操作的方法,并且LinFu看起来很有趣,但是如果有类似ClassFileTransformer的内容,它将更加简单:我只需重写该类,替换它,然后让代码运行而无需监视任何内容。

附加说明:可以将类密封。我希望能够替换任何种类的类,但不能对其属性施加限制。



编辑#2。为什么我需要在运行时执行此操作。

我需要监视所有发生的事情,以便可以检测对数据的每次访问。这也适用于库类的代码。但是,我无法事先知道将要使用哪些类,即使我知道可能会加载的每个可能的类,调整所有这些类而不是等待查看它们是否真正被调用还是对它们产生巨大的性能影响。不。



可能的(但要漂亮的硬体)解决方案。如果有人感兴趣(并且我看到问题已经解决,那么我想有人问),this是我现在正在查看的内容。基本上,我将必须实现概要分析API,并且在JIT编译开始时就注册我感兴趣的事件。博客文章摘录:


在您的ICorProfilerCallback2 :: ModuleLoadFinished回调中,您调用ICorProfilerInfo2 :: GetModuleMetadata以获取指向该模块上元数据接口的指针。
所需的元数据接口的QI。在MSDN中搜索“ IMetaDataImport”,然后浏览目录以找到元数据接口上的主题。
一旦进入元数据领域,就可以访问模块中的所有类型,包括它们的字段和函数原型。您可能需要解析元数据签名,并且此签名解析器可能对您有用。
在您的ICorProfilerCallback2 :: JITCompilationStarted回调中,您可以使用ICorProfilerInfo2 :: GetILFunctionBody检查原始IL,然后使用ICorProfilerInfo2 :: GetILFunctionBodyAllocator,然后使用ICorProfilerInfo2 :: SetILFunctionBody将您的IL替换为自己的IL。


好消息:当JIT编译开始时,我会收到通知,我可以在那里替换字节码,而不必担心替换类,等等。不太好的消息:您不能从API的回调方法中调用托管代码。 ,这很有意义,但是意味着我自己在解析IL代码等,而不是能够使用Cecil,这真是轻而易举。

我认为,不使用AOP框架(例如PostSharp),没有比这更简单的方法了。如果有人有其他想法,请告诉我。我尚未将问题标记为已回答。

最佳答案

我不知道在.NET中与此直接等效。

但是,有一些方法可以实现类似的功能,例如使用Reflection.Emit按需生成程序集和类型,使用RealProxy为接口和MarshalByRefObject对象创建代理对象。但是,要建议使用什么,重要的是要了解更多有关实际用例的信息。

关于c# - .NET中是否有与Java的ClassFileTransformer等效的文件? (一种替换类的方法),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/2617235/

相关文章:

c# - 在 ASP.NET Framework 3.5 中从 url 隐藏 .aspx

c# - 媒体播放器最高效的内部数据库

c# - Dictionary <,> Size 、GetHashCode 和素数?

java - 使用反射替换 java.net.URL URLStreamHandlerFactory 是个好主意吗?

php - PHP 中的模拟 exit() 函数

java - 通过反射检查 Class<?> 是否是 other 的实例

c# - 如何在工作线程中从 UI 线程获取变量?

c# - Xamarin 表单中的动画 AbsoluteLayout 项目

c# - 如何确定 TcpClient 连接何时断开并重新连接

c# - 在 Visual Studio 中查找所有继承接口(interface)的类