有时候为了确定代码是否编译到,我们需要在代码中添加让编译器报错的指令,对于 MASM 来说是 .ERR。在 NASM 中是”%error”【参考1】。编写例子如下:
segment code
.start:
mov ax,data
mov ds,ax
mov ax,stack
mov ss,ax
mov sp,stacktop
%error "assert error here"
mov ax,0x0600
mov bh,0x43
xor cx,cx
mov dh,24
mov dl,79
int 0x10
mov dx,hello
mov ah,9
int 0x21
mov ax,0x4c00
int 0x21
segment data
hello : db 'hello,world',13,10,'$'
segment stack stack
resb 64
stacktop:
编译时会自动报错如下:
此外,从我的实验来看,在 BIOS 代码中的 NASM 代码中随意插入字符并不能使得编译过程报错停止下来,所以如果有需要务必使用上述方法。
参考:
4.9 Reporting User-Defined Errors: %error, %warning, %fatal
The preprocessor directive %error will cause NASM to report an error if it occurs in assembled code. So if other users are going to try to assemble your source files, you can ensure that they define the right macros by means of code like this:
%ifdef F1
; do some setup
%elifdef F2
; do some different setup
%else
%error "Neither F1 nor F2 was defined."
%endif
Then any user who fails to understand the way your code is supposed to be assembled will be quickly warned of their mistake, rather than having to wait until the program crashes on being run and then not knowing what went wrong.
Similarly, %warning issues a warning, but allows assembly to continue:
%ifdef F1
; do some setup
%elifdef F2
; do some different setup
%else
%warning "Neither F1 nor F2 was defined, assuming F1."
%define F1
%endif
%error and %warning are issued only on the final assembly pass. This makes them safe to use in conjunction with tests that depend on symbol values.
%fatal terminates assembly immediately, regardless of pass. This is useful when there is no point in continuing the assembly further, and doing so is likely just going to cause a spew of confusing error messages.
It is optional for the message string after %error, %warning or %fatal to be quoted. If it is not, then single-line macros are expanded in it, which can be used to display more information to the user. For example:
%if foo > 64
%assign foo_over foo-64
%error foo is foo_over bytes too large
%endif