有没有办法欺骗.net JIT编译器运行另一个方法?

时间:2008-10-23 16:02:01

标签: .net security clr jit dynamic-execution

好吧,说我的应用程序向内存发出(x86)指令,使页面可执行等等。有没有办法改变un-JITted方法的方法存根以指向我发出的指令流?

E.g:

假设我在内存中创建了一个x86指令流,它会执行任意操作。现在,进一步假设我有一个方法'int Target()'。我还没有打电话,所以还没有编译。有没有办法:

  1. 获取指向Target的存根
  2. 的指针
  3. 指出我发出的指令流。
  4. 我意识到.Net的几乎所有安全功能都旨在阻止这样的劫持。但是,通过托管API可以吗?

5 个答案:

答案 0 :(得分:10)

这可以通过Profiling API实现。我从未使用它,但它在TypeMock中用于类似的目的。

编辑:我认为在MSDN博客上有一个不错的帖子,会去寻找它。

编辑2:Doh,first hit

答案 1 :(得分:6)

是的,你可以做到!

mscorjit的钩子getJit方法。 每当有任何方法需要Jitting时,你都会被问到。 你可以通过你想要的任何东西。 一些.net保护器就是这样的。

答案 2 :(得分:1)

正如你所说,这并不容易,甚至可能无法实现。如果我没记错的话,代码将包含一个方法的JIT编译器的地址,但尚未编译。因此,当您尝试调用此方法时,JIT编译器将完成其工作并将地址插入到新编译的方法中。如果您可以更改此地址,则可以插入对自己代码的调用。如何做到这一点未被发现是超出我的。我当然希望CLR会发现这种篡改行为。

我不认为Profiling API会在这种情况下帮助你(正如Leppie所建议的那样),因为你并没有尝试修改MSIL。如果您认为可能会使用this article,因为它描述了您必须要执行的操作以实现TypeMock正在执行的操作。

答案 3 :(得分:0)

除了能够使用ICorProfiler并在jits之前重写您的方法之外,您还可以使用ICorDebug(MDBG具有托管接口)。设置断点,当断点命中时将下一个语句设置为拦截代码。所有这些过程都可以通过代码完成,但实际上是侵入性的,你需要一个“观察者”过程来协调这个过程。

值得关注的另一件事是PostSharp项目,如果您应用属性,它会为您提供进入和退出方法。

答案 4 :(得分:0)

我不会尝试直接弄乱内存,我不确定它是否可能而不是你可以使用探查器API - 有一些例子,但没有真正的文档。 看一下MSDN杂志的文章 - Rewrite MSIL Code on the Fly with the .NET Framework Profiling API