Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/joomla/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Assembly 如何在编译时检测NASM中的体系结构,使x64和x86都有一个源代码?_Assembly_X86_Preprocessor_Nasm_X86 64 - Fatal编程技术网

Assembly 如何在编译时检测NASM中的体系结构,使x64和x86都有一个源代码?

Assembly 如何在编译时检测NASM中的体系结构,使x64和x86都有一个源代码?,assembly,x86,preprocessor,nasm,x86-64,Assembly,X86,Preprocessor,Nasm,X86 64,我正在寻找nasm中的一些预处理器功能,这些功能允许为x86和x64体系结构提供一个源代码 我的意思是,如果定义了某个常量。就像C预处理器一样,如果它想检测,比如说它是在Windows或Linux上编译的 编辑 我知道nasm旗。我使用它们。我只想拥有完全相同的源代码,并期望预处理器根据这些标志正确处理它。我会用ifdef。。。else用于堆栈操作等,两种体系结构的核心代码相同。NASM无法检测体系结构,但您可以根据需要使用输出格式(命令行选项:-felf、-felf32、-felf64、-fw

我正在寻找nasm中的一些预处理器功能,这些功能允许为x86和x64体系结构提供一个源代码

我的意思是,如果定义了某个常量。就像C预处理器一样,如果它想检测,比如说它是在Windows或Linux上编译的

编辑
我知道nasm旗。我使用它们。我只想拥有完全相同的源代码,并期望预处理器根据这些标志正确处理它。我会用ifdef。。。else用于堆栈操作等,两种体系结构的核心代码相同。

NASM无法检测体系结构,但您可以根据需要使用输出格式(命令行选项:-felf、-felf32、-felf64、-fwin32等)。阅读NASMX软件包中的.

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

\uuu输出格式\uuuu

\uuuu输出格式\uuuu
标准宏保存当前输出格式,如
-f
选项或NASM的默认值所示。键入nasm
-hf
以查看列表

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

NASM允许您随意更改代码大小(使用
bits
指令),允许您在elf64中使用16位或32位代码,或在elf32中使用64位代码。因此,检测输出格式相对错误(脆弱)

相反,您希望检测当前代码大小。为此,NASM有一个名为
\uuu BITS\uu
的标准宏。这意味着您可以在位=64时执行
%

然而,32位代码和64位代码通常使用完全不同的调用约定;64位代码有更多的寄存器、更宽的寄存器和其他差异(如果不使用额外的寄存器或额外的宽度,则意味着代码的质量极低,远远低于编译器生成的代码)。这意味着(不包括仅对几个小宏使用它)试图在同一代码中同时支持32位和64位是非常愚蠢的。您只需要为完全不同的情况编写完全不同的代码,这些代码被毫无理由地插入到同一个文件中,然后分离(使用预处理器魔术)以解决一个事实,即它从一开始就没有意义


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

对于这一点,架构是两种不同的。您将无法利用额外的寄存器,等等。坚持32位代码,或者考虑一个编译的但足够低级的语言,如C.It,由可执行格式中的标志决定,因此,您不能同时拥有这两种体系结构,因为预处理器无法通过让程序员使用ifdef x64 do_sth1 else do_sth2?@infoholic_anonymous这样的宏来利用这些标志:您可以在x64系统上构建和运行32位程序。那么架构检测有什么意义呢?但是您可以检索构建选项(
\uuuuuu输出\uuuu格式
)。你看过说明书了吗?如果通过脚本构建程序,则可以使用
uname-m
检索机器。我做了一个非常简单的项目,必须为x64和x86提供代码。在我的代码中,差异很小,主要涉及到调用约定的问题和寄存器名之类的问题。寄存器名可以由定义和调用约定替换为几行ifdef。为什么我要保留两个文件,并在更改时对其进行双重更正?我很惊讶这看起来很奇怪,在命令行程序的C源代码中,有些代码段依赖于操作系统是很常见的。我尝试了输出_格式来区分elf32和elf64,但没有结果。@Agguro感谢您的报告。您能否在NASM问题跟踪程序/邮件列表上打开一个问题并从这里链接到它?