FreeBSD 系统上简单汇编程序的虚假结果
我在让我在 Linux 上编写的最简单的汇编程序在我的 FreeBSD 机器上运行时遇到了问题。下面是有问题的代码(我试图使其尽可能简单):
#counts to sixty
.section .data
.section .text
.global _start
_start:
movl $1, %ecx #move $1 into ecx
movl $1, %eax
start_loop:
addl %ecx, %eax #add ecx to eax
cmpl $60, %eax #compare $60 and eax...
je end_loop #if eax = 60 go to end_loop
cmpl $60, %eax #
jle start_loop #jump if eax is < $60...
jmp start_loop #...to start_loop
end_loop:
movl %eax, %ebx #move the value of eax into ebx because ebx holds
#the return value
movb $1, %al #Move $1 into eax (int 1 is the value for the
#exit() syscall
int $0x80
Linux 机器返回预期结果,即 60,而 FreeBSD 机器始终返回 164 作为返回代码。有人知道这是为什么吗?如果是这样,您能向我解释一下发生了什么吗?另外,我应该提到它们确实都运行 x86 CPU。提前致谢 :)
I've been having problems getting even the simplest of assembly programs that I write on Linux to run on my FreeBSD machine. Here's the offending code (I'm trying to keep this as simple as possible):
#counts to sixty
.section .data
.section .text
.global _start
_start:
movl $1, %ecx #move $1 into ecx
movl $1, %eax
start_loop:
addl %ecx, %eax #add ecx to eax
cmpl $60, %eax #compare $60 and eax...
je end_loop #if eax = 60 go to end_loop
cmpl $60, %eax #
jle start_loop #jump if eax is < $60...
jmp start_loop #...to start_loop
end_loop:
movl %eax, %ebx #move the value of eax into ebx because ebx holds
#the return value
movb $1, %al #Move $1 into eax (int 1 is the value for the
#exit() syscall
int $0x80
The Linux machine returns the expected resulted which is sixty, whereas the FreeBSD machine consistently returns 164 for the return code. Does anybody know why this is? If so, can you please explain to me what is happening? Also, I should mention that they are both indeed running x86 CPUs. Thanks in advance :)
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(1)
请参阅 FreeBSD 开发人员手册,你需要这样做:
因为:
如果您想使用 Linux 约定(regs 中的某些系统调用参数,在手册中称为“替代调用约定”),则必须对可执行文件进行标记,以便系统知道您正在使用 Linux 风格的系统调用。
Refer to the FreeBSD Developer's handbook, and you need to do:
because:
%eax
, all arguments are on the stackint $0x80
but a return address where you do a syscall via acall kernel_entry
trampoline (that then can doint $0x80; ret
).If you want to use the Linux convention (some syscall args in regs, called "Alternative Calling convention" in the manual), you have to brand the executable so that the system knows you're using Linux-style syscalls.