NASM能像8086汇编器那样工作吗?即使是在“CPU 8086”模式下,它也支持32位寻址模式
我要怎么让NASM的行为像只知道 [8086] 的1980年代汇编器那样,对后续处理器一无所知,并拒绝,或至少对任何需要更高CPU的指令发出警告?
I tried giving the following directives at the very beginning of my source file:
bits 16 ; already the default for flat-binary output
cpu 8086
但即使使用这两条指令,遇到下面这条使用 [80386] 特性的指令时,NASM仍然不会报错:(ESI是一个32位寄存器,通常也涉及32位寻址宽度)
add ax,[esi] ; 32-bit address-size instruction accepted by NASM 3.01
然后(仍然使用如上两条指令),NASM确实会对例如以下情况报错:
add eax, ecx ; 32-bit operand-size instruction rejected by NASM 3.01
我到底还缺少了什么?
背景:我对汇编完全是新手,想学习x86汇编,计划先读Steve Morse在 1982年关于8086处理器的一本书。(编辑注:他是在纸面上设计了8086的 ISA;英特尔的其他人实现了硬件和微码。他的书在他的网站上免费提供:https://stevemorse.org/8086/ 他对某些指令的预期用途给出了一些见解,例如 loop 与 rep 前缀之间的差异)
现在我显然需要一个汇编器来试手,目前我在考虑NASM。
解决方案
NASM似乎在受 CPU 8086 限制时对遇到386+内存寻址模式不会发出警告
你可以改试 €ASM 这个,它会发出警告。
用以下命令 euroasm Pollo.asm 将源文件 "Pollo.asm" 汇编
EUROASM cpu=8086
Pollo PROGRAM Format=com
add ax,[esi]
ret
ENDPROGRAM
它会给出警告
W2340 This instruction requires option "EUROASM CPU=386".
尽管它仍然会把它汇编出来并生成16位可执行文件 "Pollo.com"
备选方案
只是一个想法...
我要怎么让NASM的行为像一个只知道8086的 1980年代汇编器?
对后续处理器一无所知?
并拒绝,或至少对需要更高CPU的指令发出警告?
你可以使用NASM的单行宏 %idefine 来输出一些警告信息,提示这段代码包含32位指令。
[bits 16]
[cpu 8086]
%idefine eax eax_not_available_on_8086_cpu
%idefine ebx ebx_not_available_on_8086_cpu
%idefine ecx ecx_not_available_on_8086_cpu
%idefine edx edx_not_available_on_8086_cpu
%idefine esi esi_not_available_on_8086_cpu
%idefine edi edi_not_available_on_8086_cpu
%idefine ebp ebp_not_available_on_8086_cpu
%idefine esp esp_not_available_on_8086_cpu
%idefine fs fs_not_available_on_8086_cpu
%idefine gs gs_not_available_on_8086_cpu
section .text
mov fs, ax
mov bx, gs
mov eax,[ebx+8,ecx*4]
mov ebx,[ebp-4]
xchg ax,[2*ecx]
add ax, edx
add ax, [esi]
add dword [edi], ecx
add esp, 2