13得票4回答
x86_64调用约定和堆栈帧

我正在尝试理解GCC(4.4.3)为在Ubuntu Linux下运行的x86_64机器生成的可执行代码。特别是,我不明白代码如何跟踪堆栈帧。在旧的32位代码中,我习惯于在几乎所有函数中看到这个“prologue”:push %ebp movl %esp, %ebp 然后,在函数末尾,会出现一个...

13得票2回答
当经典MacOS进入程序时,68000堆栈上有什么?

我正在尝试理解一个经典的老款Mac应用程序的入口点。我已经反汇编了第一个CODE资源(不是CODE#0,这是跳转表)。该代码涉及堆栈上的一些变量:0004(A7)处的一个字,从000C(A7)开始的一组长字的数组,其长度为0004(A7)处的值,并且超出该数组的一个最终长字似乎是指向字符字符串...

13得票2回答
r10和r11的常规使用是否可接受

最近我一直在进行x64汇编程序开发(使用Linux),并将其集成到我的C/C++程序中。 由于我更关心效率,因此尽可能地减少使用不同的寄存器/内存地址,并尝试不创建任何堆栈帧或保存寄存器(每个周期都很重要)。 根据cdecl约定,r10和r11寄存器不会被保存。我想在我的函数中使用它们作为...

13得票2回答
为什么我不应该使用__fastcall而应该使用标准的__cdecl?

我听到一些人说__fastcall比__cdecl和__stdcall更快,因为它将两个参数放在寄存器中,而其他调用只有一个;但是,在另一方面,这不是C语言中使用的标准。 我想知道什么使__fastcall成为C语言标准中不理想的选项,以及何时在我的代码中使用它。

13得票3回答
如何防止将函数参数用作隐藏指针?

我尝试理解System V AMD64 - ABI的调用约定,并查看以下示例: struct Vec3{ double x, y, z; }; struct Vec3 do_something(void); void use(struct Vec3 * out){ *ou...

12得票2回答
C编译器如何在汇编中处理函数返回的结构体值

当谈到C函数的返回值时,返回值存储在EAX寄存器中。假设我们正在谈论32位寄存器,整数是可以的,但是当我们返回这些类型时会发生什么: long long,long double,大于32位的struct/union。

12得票2回答
"fastcall" 关键字在 Visual C++ 中有什么作用?

我看到许多函数前面都加了fastcall符号,它的作用是什么?

12得票2回答
无限递归而不溢出——是否可能?

栈溢出的原因是栈空间不足,但如果函数没有参数,则不必将任何数据推入栈中。这仍然需要推送“返回”地址,但在有意的无限递归的情况下,这是不必要的。 所以我想问的是......是否可能使用某种调用约定,使调用不将任何内容放入堆栈中,而只是跳转到第一条指令并执行,并提供最后一条指令将另一个调用到函数...

12得票2回答
为什么对于MEMORY类类型不执行尾调用优化?

我将尝试理解System V AMD64 - ABI对于函数返回值的影响。 对于以下数据类型: struct Vec3{ double x, y, z; }; 类型Vec3属于MEMORY类,因此ABI规定了关于“返回值”的以下内容: 如果该类型属于MEMORY类,则调用...

11得票6回答
函数调用中参数的求值顺序是什么?

我正在研究C语言中的未定义行为,发现有一条声明称: 函数参数没有特定的计算顺序 但是标准调用约定(如"_cdecl"和"_stdcall")的定义指出(书中),参数从右到左进行计算。 现在我对这两个定义感到困惑,一个根据未定义行为的规定,另一个则符合调用约定的定义。请解释这两种情...