2

我正在和一个朋友一起开发一个旧的 MUD 代码库,作为一个爱好项目,但是我在让代码在除 debian(特别是 x386)以外的任何操作系统中编译时遇到问题。问题是(主要)是因为我真的不了解修改的一些 asm 行。尝试在 VS 中编译时收到的错误是“错误 c2059:语法错误”第 29 行。关于如何在 x64 操作系统上编译的任何想法?

void        Execute(int nArgs, ...)
{
    if(MAX_FUNCTION_ARGS < nArgs)
        throw "Error: CFuncPtr has too many args";

    int i;
    void *fptrs[MAX_FUNCTION_ARGS], *ptrs[MAX_FUNCTION_ARGS];
    va_list ap;
    va_start(ap, nArgs);

    for(i = 0; i < nArgs; i++)
        fptrs[i] = va_arg(ap, void *);
    for(i = 0; i < nArgs; i++)
    {
        ptrs[i] = fptrs[nArgs - i - 1];
// ============== This is the part with the issue
        asm volatile("" \                         // This is line 29.
                "movl   %0, %%eax\n\t" \
                "pushl  %%eax\n\t" \
                :                       
                : "r"(ptrs[i])
                : "%eax");
// ==============
    }
    (*funcptr) ();
    va_end(ap);
}
4

1 回答 1

3

这远非微不足道,因为 x86-64 使用寄存器传递参数 [首先这是一个相当丑陋的解决方案,因为它基本上假设没有参数在寄存器中传递,并且被调用函数获取堆栈上的所有参数] .

我可能会完全避免使用汇编版本,而不是第二个 for 循环(使用汇编代码)编写如下内容:

switch(nArgs)
{
  case 0:
     (*funcptr)();
     break;
  case 1: 
     (*funcptr)(fptrs[0]);
     break;
  case 2:
     (*funcptr)(fptrs[0], fptrs[1]);
     break;
  ... Repeat until MAX_FUNCTION_ARGS is covered.
}     

除非 MAX_FUNCTION_ARGS 非常大 [在这种情况下,您可能希望首先更改调用约定funcptr],否则不太可能生成非常糟糕的代码。

于 2014-04-26T23:04:38.740 回答