如何在编译时检测NASM中的体系结构以获得x64和x86的一个源代码?

时间:2014-06-09 16:22:33

标签: assembly x86 preprocessor nasm x86-64

我在nasm中寻找一些预处理器功能,允许为x86和x64架构提供一个源代码。

我的意思是ifdef some_constant。就像C预处理器一样,如果它想要检测它是否在Windows或Linux上编译它。

修改

我知道nasm标志。我用它们。我只想拥有完全相同的源代码,并希望预处理器能够根据这些标志正确处理它。我使用ifdef ... else进行堆栈操作,因此,两个架构的核心代码都相同。

4 个答案:

答案 0 :(得分:2)

NASM无法检测到体系结构,但您可以根据需要使用输出格式(命令行选项:-felf,-felf32,-felf64,-fwin32等)。阅读Friendly Manual

答案 1 :(得分:2)

在NASMX包中,您可以在syscalls.inc中找到%if BITS == 64行。这确定您使用的是64位还是32位。也许这就是你想知道的?

答案 2 :(得分:2)

<强> __OUTPUT_FORMAT__

http://www.nasm.us/doc/nasmdoc4.html#section-4.12.6

  

__OUTPUT_FORMAT__标准宏保存当前的输出格式,由-f选项或NASM的默认值给出。输入nasm -hf作为列表。

%ifidn __OUTPUT_FORMAT__, win32 
  %define NEWLINE 13, 10 
%elifidn __OUTPUT_FORMAT__, elf32 
 %define NEWLINE 10 
%endif

答案 3 :(得分:2)

NASM允许您随意在任意位置更改代码大小(使用bits指令),这样您就可以在elf64中使用16位或32位代码,或者在64位代码中使用64位代码。 ELF32。因此,检测输出格式相对错误(易碎)。

而是要检测当前的代码大小。为此,NASM有一个名为__BITS__的标准宏。这意味着您可以执行%if __BITS__ = 64

但是,32位代码和64位代码通常使用完全不同的调用约定; 64位代码具有更多寄存器,更宽的寄存器和其他差异(不使用额外寄存器或额外宽度意味着代码质量极差 - 远比编译器生成的代码差)。这意味着(在一些小宏中仅使用它)尝试在同一代码中同时支持32位和64位非常愚蠢。你最终会得到完全不同的代码完全不同的代码,这些代码在没有理智的情况下被打到同一个文件中然后分开(使用预处理器魔法)来解决它从一开始就没有意义的事实。

更明智的是为单独的案例(例如src/arch/x86_32目录和src/arch/x86_64目录)分别存在文件,在这种情况下,您可以让构建脚本或makefile对其进行排序(例如告诉汇编程序使用不同的“包含路径”)。