1

例如,假设我有一个函数可以为您交换 32 位值中的字节:

uint32_t byte_swap(uint32_t in);

将那个 32 位值压入堆栈并再次弹出它似乎很愚蠢,特别是如果我们要经常调用这个函数,所以让我们通过 ECX 传递它:

#if __FASTCALL_SUPPORTED_   /* Whatever this may be */
#define FASTCALL __attribute__((fastcall))
#else
#define FASTCALL
#endif

uint32_t FASTCALL byte_swap(uint32_t in);

现在我的问题是,将该函数编译到共享库中进行分发是否安全?如果用户使用不同的编译器来编译他们的程序和链接,该函数是否仍会被正确调用?

4

1 回答 1

4

__attribute__((fastcall))是 gcc 扩展;因此,如果调用者也没有使用 gcc,它可能无法使用。此外,在您提供的示例中,如果 __FASTCALL_SUPPORTED_ 未定义,您最终会得到一个带有错误调用约定的调用 -主意。

处理此问题的一种方法可能是使用后备包装器。在您的 .c 文件中:

#include "foo.h"

uint32_t FASTCALL byte_swap(uint32_t in) {
    /* code ... */
}

uint32_t byte_swap__slowcall(uint32_t in) {
    return byte_swap(in);
}

在你的 .h 文件中:

#if __FASTCALL_SUPPORTED_   /* Whatever this may be */
#define FASTCALL __attribute__((fastcall))
#else
#define FASTCALL
#define byte_swap byte_swap__slowcall
#endif

uint32_t FASTCALL byte_swap(uint32_t in);

另外,请注意,在 Linux 上,可以在<byteswap.h>as中使用快速字节交换实现bswap_32。在 x86 机器上,它将编译为内联汇编程序,以及在足够高的-march=设置下的一条指令。

于 2009-09-27T21:42:44.380 回答