【问题标题】:Call C/C++ function from assembly (OSX Mavericks x64)从程序集中调用 C/C++ 函数(OSX Mavericks x64)
【发布时间】:2014-04-17 14:54:28
【问题描述】:

这是一个奇怪的问题,我似乎无法找到答案。这个:

#include <iostream>
using namespace std;

void show_number(int number) {
    cout << number << endl;   // Shows '10' as expected
}

int main() {
    cout << endl; // Remove this and it fails

    __asm {
        mov rdi, 10
        call show_number
    }
}

实际上工作正常,除非您删除初始的cout &lt;&lt; endlmain 的第一行)。当您删除它时,show_number 中的 cout 似乎由于某种原因导致了段错误。

这是什么原因造成的?

(OSX Mavericks x64,但我认为也应该在 linux 中工作)

【问题讨论】:

  • 你能在这两种情况下显示调用前后寄存器的内容吗?
  • asm volatile 无法构建 (?) - Apple Clang 2.1
  • @SteveCox 我试过了,不过不太实用。
  • __asm volatile 呢?

标签: c++ c assembly posix abi


【解决方案1】:

Mac OS X ABI 在调用函数之前需要 16 字节的堆栈对齐。

如果您的代码正常工作,那么您很幸运,这就解释了为什么您在修改之前的代码部分时会遇到 e 分段错误。

因此,您需要确保堆栈在 16 字节边界上对齐。
我之前已经回答过一个类似的问题:

How to print argv[0] in NASM?

有趣的是:

; Align stack on a 16 bytes boundary
mov     ebp,                esp
and     esp,                0xFFFFFFF0

不过,请务必阅读完整答案...

【讨论】:

  • 我以前听说过,但我对如何应用它感到困惑。你能告诉我我的 asm 区域的快速编辑,以说明应该如何完成吗?
  • 查看编辑,并仔细阅读我在提到的帖子中的回答。
  • 当然感谢您的帮助,但似乎有些不对劲。事实上,我可以整天调用函数而不必担心对齐,只是cout似乎有这个问题。我调用的任何其他函数似乎都可以正常工作。
  • 有了更多经验,我现在明白你的意思了。标记为已接受,谢谢。
猜你喜欢
  • 1970-01-01
  • 2015-04-20
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2017-05-22
  • 1970-01-01
相关资源
最近更新 更多