sha*_*oth 5 c# jit inline visual-studio vshost.exe
我正在尝试制作一个简短的C#片段,它将说明Assembly.GetCallingAssembly()由于MSDN中概述的JIT内联而改变行为.到目前为止,这是我的代码:
class Program
{
static void Main(string[] args)
{
Console.WriteLine( GetAssembly().FullName );
Console.ReadLine();
}
static Assembly GetAssembly()
{
return System.Reflection.Assembly.GetCallingAssembly();
}
}
Run Code Online (Sandbox Code Playgroud)
我在"Release"中构建并开始使用"Start Without Debugging" - 这个设置使得这个答案的代码产生内联.我看到的结果是
ConsoleApplication2, Version=1.0.0.0, Culture=neutral, PublicKeyToken=null
Run Code Online (Sandbox Code Playgroud)
所以显然GetAssembly()没有内联Main(),否则我会mscorlib看作是召集大会.
我已经审查了所有内联标准,我不明白为什么GetAssembly()不会内联.
是否有可能知道为什么JIT编译器决定不内联调用?
这是.NET 3.5中Assembly.GetCallingAssembly()的声明:
[MethodImpl(MethodImplOptions.NoInlining)]
public static Assembly GetCallingAssembly()
{
StackCrawlMark lookForMyCallersCaller = StackCrawlMark.LookForMyCallersCaller;
return nGetExecutingAssembly(ref lookForMyCallersCaller);
}
Run Code Online (Sandbox Code Playgroud)
StackCrawlMark枚举很有意思,"查找我的调用者调用者"在调用者内联时无法正常工作.在CSSCL的SSCLI20源代码中有一条注释,其中枚举被声明:
声明此枚举类型的局部变量并将其通过ref传递给需要执行堆栈爬行的函数将同时阻止内联调用[sic]并将ESP点传递给堆栈爬行
这与GetCallingAssembly()中发生的事情非常匹配,它是一个局部变量,确实通过ref传递.不知道机制是什么,抖动可以产生名为CORINFO_FLG_BAD_INLINEE的方法属性.这反过来又强制调用MethodDesc :: SetNotInline().这是猜测,这是非常模糊的.
| 归档时间: |
|
| 查看次数: |
2337 次 |
| 最近记录: |