使用库函数 API 和 C 代码中嵌入汇编代码两种方式使用同一个系统调用
张晓攀+原创作品转载请注明出处+《Linux内核分析》MOOC课程https://mooc.study.163.com/course/1000029000
实验四——使用库函数API和C代码中嵌入汇编代码两种方式使用同一个系统调用
本次实验采用4号系统调用write
一、使用库函数API
1.创建hello.c文件
vim hello.c

2.编译并运行
编译
gcc -o hello hello.c

运行
./hello

二、C代码中嵌入汇编代码
1.创建hello-asm.c文件
vim hello-asm.c

这段代码是使用内联汇编的C程序,它通过系统调用 write 向标准输出(即屏幕)打印字符串 "hello world!"。
①定义了一个 msg 字符串为 "hello world!",长度 len 为12。
②使用 asm volatile 来嵌入汇编代码,volatile 关键字告诉编译器不要优化这段汇编。
③汇编部分:
movl %2, %%edx: 将字符串长度len移入寄存器edx,作为系统调用的第三个参数。movl %1, %%ecx: 将msg的地址放入寄存器ecx,作为系统调用的第二个参数。movl $1, %%ebx: 文件描述符1(标准输出)传递给ebx,作为第一个参数。movl $4, %%eax: 系统调用号4,表示sys_write,将其放入eax。int $0x80: 执行系统调用。
④最后通过 int $0x80 触发系统调用,将消息输出到屏幕。
2.编译并运行
编译
gcc -o hello-asm hello-asm.c

运行
./hello-asm

总结
Linux 系统调用的工作机制可以包括以下几点:
- 用户态和内核态的切换:系统调用是用户程序请求操作系统内核服务的接口,调用时会从用户态切换到内核态。
- 系统调用号:每个系统调用都有一个唯一的调用号,用户程序通过
eax寄存器传递调用号给内核。 - 参数传递:系统调用的参数通过寄存器(如
ebx,ecx,edx等)传递,内核通过这些参数执行相应的操作。 - 中断触发:通过触发中断(如
int 0x80)来通知内核执行特定的系统调用。 - 返回结果:内核处理完请求后,将结果放回寄存器并返回用户态程序。

浙公网安备 33010602011771号