为什么Console.WriteLine()使用ecx寄存器,尽管eax和ebx是免费的,但仍会发生事件?

Kam*_*l T 5 .net c# assembly

我正在对CIL优化技术进行一些研究。我创建了以下简单代码:

int Function() { return 10; }
// (...)
int Number = Function();
Console.WriteLine(Number);
Run Code Online (Sandbox Code Playgroud)

当我在反汇编窗口中观看此代码时,会看到类似以下内容的内容:

00252DB0  mov ecx,0Ah  
00252DB5  call 63A96648  
00252DBA  ret  
Run Code Online (Sandbox Code Playgroud)

我知道它将10放入ecx,然后用作 函数63A96648指针WriteLine(),但是我不确定为什么要使用ecx寄存器。

我始终认为,ecx主要用于循环计数器(当然,这就是所谓的“计数寄存器”的一个原因......),我不知道为什么它用于WriteLine()功能,即使eaxebx是免费的。即使编写更复杂的函数,最后也总是ecxWriteLine()函数之前。

我试图在Internet上找到任何有关它的东西,甚至从我的大学图书馆里找到几本书,但什么都没找到。是ecx更快还是完全没有理由使用它?

我完全意识到我不应该对此太在乎(因为只要有效,我就可以了),但是过去几天一直在困扰我,我希望有人能告诉我为什么使用该寄存器。

Han*_*ant 4

必须使用 ECX 寄存器,x86 的 __clrcall 调用约定要求它。第一个参数(在本例中为数字)通过 ECX 传递,第二个参数(如果存在)通过 EDX 传递,其他参数通过堆栈传递。

您还可以看到 Function() 方法被内联,它完全消失,优化器可以将其折叠为单个寄存器分配。这种优化使属性与字段无法区分。

这是特定于 x86 的,如果允许它在 64 位模式下运行(消除抖动强制),则最多可以通过寄存器传递 4 个参数(rcx、rdx、r8 和 r9)。项目 > 属性 > 构建选项卡,平台目标 = AnyCPU 并取消勾选“首选 32 位”。当您学习优化技术时,应该关注这种代码。64位抖动针对VS2015重写,项目名称RyuJIT。