gpt4 book ai didi

c# - 为什么我的方法调用 Assembly.GetCallingAssembly() 不是 JIT 内联的?

转载 作者:太空狗 更新时间:2023-10-29 22:19:44 27 4
gpt4 key购买 nike

我正在尝试制作一个简短的 C# 片段来说明 Assembly.GetCallingAssembly() 行为因 JIT 内联而发生的变化 outlined in MSDN .到目前为止,这是我的代码:

class Program
{
static void Main(string[] args)
{
Console.WriteLine( GetAssembly().FullName );
Console.ReadLine();
}

static Assembly GetAssembly()
{
return System.Reflection.Assembly.GetCallingAssembly();
}
}

我在“Release”中构建并开始使用“Start Without Debugging”- 此设置从 this answer 生成代码招致内联。我看到的结果是

ConsoleApplication2, Version=1.0.0.0, Culture=neutral, PublicKeyToken=null

很明显 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);
}

StackCrawlMark 枚举很有趣,当调用者将被内联时,“查找我的调用者调用者”不能很好地工作。在声明枚举的 thread.cs 的 SSCLI20 源代码中有一条注释:

declaring a local var of this enum type and passing it by ref into a function that needs to do a stack crawl will both prevent inlining of the calle [sic] and pass an ESP point to stack crawl to

这与 GetCallingAssembly() 中发生的事情非常匹配,它是一个局部变量并且确实被 ref 传递。不确定机制是什么,但是抖动可以产生一个名为 CORINFO_FLG_BAD_INLINEE 的方法属性。这反过来强制调用 MethodDesc::SetNotInline()。这是一个猜测,这是非常模糊的。

关于c# - 为什么我的方法调用 Assembly.GetCallingAssembly() 不是 JIT 内联的?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/12910167/

27 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com