Linux 系统调用

1. 说明

系统调用(System Call)是操作系统为在用户态运行的进程与硬件设备(如CPU、磁盘、打印机等)进行交互提供的一组接口。当用户进程需要发生系统调用时,CPU 通过软中断切换到内核态开始执行内核系统调用函数。

2. 内嵌汇编

下面以获取系统当前时间为例,探讨系统调用方式。

1. glibc调用

int tt = time(NULL);

2. syscall调用

linux-2.6.32/arch/x86/kernel/syscall_table_32.S              linux-2.6.32系统调用表

linux-3.18.6/arch/x86/kernel/syscall_table_32.S         linux-2.6.32系统调用表        

linux-3.5/arch/x86/syscalls/syscall_32.tbl linux-3.5系统调用表

通过查看 syscall_table_32.S 中断调用表文件得到sys_time中断调用号为13.

int tt = syscall(13);

3. 内嵌汇编

int tt = 0;
asm("mov $0,%%ebx\n\t"
 "mov $13,%%eax\n\t"
 "int $0x80\n\t"
 "mov %%eax,%0\n\t"
 :"=m"(tt)
 );
printf( "time:%d\n", tt );

eax=13 传入系统调用号

ebx=0传入系统函数,相当于time(NULL)。如果有多个传入参数,可使用ebx,

ecx,edx,esi,edi,ebp 寄存器

eax 接收函数返回值,传出至tt

int $0x80 中断陷入,windows下采用0x2E作为系统调用入口

3. 扩展系统调用

glibc 中time()调用过程:用户态调用 time(),中断陷入内核态,调用内核函数 sys_time()。 

可通过下列四步实现自定义系统调用:

linux-2.6.32/kernel/sys.c                    

sys_xxx(),实现系统调用

linux-2.6.32/arch/x86/include/asm/unistd.h    

_NR_xxx,添加中断号宏定义

linux-2.6.32/arch/x86/kernel/syscall_table_32.S     

.long sys_xx,添加中断汇编定义

linux-2.6.32/include/linux/syscalls.h         

asmlinkage,导出该函数

参考资料:

《程序员的自我修养》

猜你喜欢

转载自tcspecial.iteye.com/blog/2361923