大会,你好世界问题
我正在 Linux 上学习 asm (noobuntu 10.04) 我得到了以下代码:http://asm.sourceforge.net/intro/hello。 html
section .text
global _start ;must be declared for linker (ld)
_start: ;tell linker entry point
mov edx,len ;message length
mov ecx,msg ;message to write
mov ebx,1 ;file descriptor (stdout)
mov eax,4 ;system call number (sys_write)
int 0x80 ;call kernel
mov eax,1 ;system call number (sys_exit)
int 0x80 ;call kernel
section .data
msg db 'Hello, world!',0xa ;our dear string
len equ $ - msg ;length of our dear string
这是一个简单的 hello world。在 Linux 上运行 + 直接调用内核(显然)。 谁能解释一下这里到底发生了什么?我认为它读取 eax 和 eax 中的整数。 ebx 处理器寄存器和ecx、edx 数据,定义了调用内核时的系统调用。如果是这样,当调用 int 0x80 时,不同的整数组合是否定义了不同的系统调用?
我不擅长手册页,但已阅读我能找到的所有相关手册,是否有任何手册页告诉我哪些组合定义了哪些系统调用?
任何帮助表示赞赏。逐行解释将是惊人的...... -提前致谢 杰里米
I'm learning asm on Linux (noobuntu 10.04)
I got the following code off of: http://asm.sourceforge.net/intro/hello.html
section .text
global _start ;must be declared for linker (ld)
_start: ;tell linker entry point
mov edx,len ;message length
mov ecx,msg ;message to write
mov ebx,1 ;file descriptor (stdout)
mov eax,4 ;system call number (sys_write)
int 0x80 ;call kernel
mov eax,1 ;system call number (sys_exit)
int 0x80 ;call kernel
section .data
msg db 'Hello, world!',0xa ;our dear string
len equ $ - msg ;length of our dear string
It's a simple hello world. Runs on Linux + calls the kernel directly (apparently).
Can anyone please explain what is really going on here? I think it reads the integers in the eax & ebx processor registers & ecx, edx data and that defines the system call when the kernel is called. If so, do different combinations of integers define different system calls when int 0x80 is called?
I'm not good with man pages, but have read every related one I can find, does any man page tell me what combinations define what syscalls?
ANY help is appreciated. A line by line explanation would be amazing...
-Thanks in advance
Jeremy
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(3)
当您调用
int 0x80
时,内核会查看eax
寄存器的值来确定您要调用的函数(这是“系统调用号”)。根据该数字,其余寄存器被解释为特定的含义。sys_write
调用期望寄存器设置如下:eax
包含 4ebx
包含文件描述符ecx
包含要写入的数据的地址edx
包含字节数有关详细信息,请参阅 Linux 系统调用。
When you call
int 0x80
, the kernel looks at the value of theeax
register to determine the function you want to call (this is the "syscall number"). Depending on that number, the rest of the registers are interpreted to mean specific things. Thesys_write
call expects the registers to be set up as follows:eax
contains 4ebx
contains the file descriptorecx
contains the address of the data to writeedx
contains the number of bytesFor further extensive information, see Linux System Calls.
这只是标头材料,汇编程序的“文本”部分只是机器指令(而不是数据、只读数据和 BSS 部分)。
global
行类似于表示_start
函数是“公共”的。从注释中我们知道我们正在查看
sys_write
函数,因此我们可以man 2 write
来获取详细信息。 C 原型提供以下参数:fd
、*buf
和count
。从 %ebx 开始,我们看到它们匹配(%ebx = fd,%ecx = 要写入的字符串,%edx = 字符串长度)。然后,由于我们是用户进程,所以必须要求内核执行输出。这是通过 SYSCALL 接口完成的,write()
函数(显然)给出了数字 4。INT 0x80
是一个软件中断,调用 Linux 内核的 SYSCALL 例程。您可以在 Linux 头文件中找到所有系统调用的实际编号(假设您已安装它们)。在我的系统上,我检查了
/usr/include/sys/syscall.h
导致/usr/include/asm/unistd.h
,然后到/usr /include/asm-i386/unistd.h
。其中(我明白了),#define __NR_write 4
。与上一段的最后两行一样,这只是加载系统调用 ID 并执行软件中断以退出程序(删除其内存映射和清理)。
这是数据部分,它只描述我们在程序中使用的变量。
This is just header material, the "text" section of an assembly program is just the machine instructions (versus the data, read-only data, and BSS sections). The
global
line is akin to saying that the_start
function is "public."From the comments we know that we are looking at the
sys_write
function, so we canman 2 write
to get the details. The C prototype gives the following parameters:fd
,*buf
, andcount
. Starting with %ebx we see that those match (%ebx = fd, %ecx = string to write, and %edx = length of string). Then, since we are a user process, we must ask the kernel to perform the output. This is done through the SYSCALL interface, and thewrite()
function is (apparently) given the number 4.INT 0x80
is a software interrupt that calls the Linux kernel's SYSCALL routine.You can find the actual numbers of all the syscalls in the Linux header files (assuming you have them installed). On my system, I checked
/usr/include/sys/syscall.h
leading to/usr/include/asm/unistd.h
and then onto/usr/include/asm-i386/unistd.h
. Where (I see),#define __NR_write 4
.As with the last two lines of the previous segment, this just loads the syscall id and does the software interrupt to exit the program (remove it's memory mapping and cleanup).
This is the data section, it just describes variables we used in our program.
系统调用太多,无法为每个系统调用提供不同的汇编语言指令。
相反,您可以调用 TRAP 指令。 eax 的值决定将调用哪个系统调用。其他寄存器是系统调用的参数。
系统调用在内核中列出。
There are too many system calls for there to be a different assembly-language instruction for each one.
Instead, you call the TRAP instruction. The value of eax determines which system call will be invoked. The other registers are the arguments to the system call.
The system calls are listed inside the kernel.