我在FreeBSD上学习汇编语言编程。我正在使用FreeBSD 9.0 i386发行版和nasm汇编程序。
当我编写一个简单的系统调用函数时,我发现我必须将无用的值推入堆栈才能使代码正确运行。
例如:
; File:test.asm
section .text
global _start
_start:
xor eax,eax
; Argument of exit()
push 0x0
; Syscall of exit()
mov al,1
int 0x80
我使用以下命令汇编并链接上面的代码:
%nasm -f elf test.asm -o test.o
%ld test.o -o test.bin
我用ktrace检查程序并发现:
%ktrace ./test.bin
%kdump -d -f ./ktrace.out
2059 ktrace RET ktrace 0
2059 ktrace CALL execve(-1077940941,-1077941260,-1077941252)
2059 ktrace NAMI "./test.bin"
2059 test.bin RET execve 0
2059 test.bin CALL exit(1)
因此代码没有正确运行,因为我提供了0作为exit()的唯一参数,但程序实际上运行了exit(1)。
然后我改变了我的代码。
; File:test.asm
section .text
global _start
_start:
xor eax,eax
push 0x0
; Whatever digits,0x1,0x2...0xFFFFFFFF, ect.
push 0xFFFFFFFF
mov al,1
int 0x80
然后代码正确执行。
起初,我认为这是因为“堆栈填充”或“堆栈对齐”之类的东西,如Stack allocation, padding, and alignment。所以它可能会尊重16位对齐。但我发现它不是。例如,以下代码:
; File:test.asm
section .text
global _start
_start:
xor eax,eax
push 0x0
; Actual argument of exit()
push 0x3
push 0xFFFFFFFF
; Syscall of exit()
mov al,1
int 0x80
实际执行退出(3)。它似乎没有对齐字节。我使用gdb调试上面的代码,当最后一行即将执行时,堆栈是这样的:
0xFFFFFFFF -> esp
0x00000003
0x00000000
所以这是我的问题:为什么总会有一个无用的论点,或者有一种方法可以解决?
答案 0 :(得分:7)
这是一个伪参数,可以通过阻止调用/返回指令对来略微提高性能。
请参阅以下链接中的2.1美元: