使用GDB进行系统调用过程简析

    陈铁 + 原创作品转载请注明出处 + 《Linux内核分析》MOOC课程http://mooc.study.163.com/course/USTC-1000029000


    作业的难度在增加,实验楼的虚拟机不太稳定,经常用着用着就不能操作了。没有细致研究,于是就在VirtualBox下新建了虚拟机,还算顺利。下载了Ubuntu的mini.iso,结果界面全是Debian的,选择高级里的Xfce,虽然全部下载使安装过程有点长,不过安装完之后没有太多的问题,就达到了实验楼同样的效果。于是下载了最新的kernel,git clone了老师的最小linux的menuos。加上自己的系统程序。环境就打好了。

有图有真相。

技术分享

系统运行起来了:

技术分享

重新启动GDB,设置断点sys_getuid.

(gdb) break sys_getuid
Breakpoint 1 at 0xc1054340: file kernel/sys.c, line 857.
代码如下:


SYSCALL_DEFINE0(getuid)
{
        /* Only we change this so SMP safe */
        return from_kuid_munged(current_user_ns(), current_uid());
}
执行GDB命令finish,结果如下:

Run till exit from #0  sys_getuid () at kernel/sys.c:859
<signal handler called>
Value returned is $1 = 0
返回当前用户的ID存在变量中是0;

显示一下代码

(gdb) list
424     sysenter_do_call:
425             cmpl $(NR_syscalls), %eax
426             jae sysenter_badsys
427             call *sys_call_table(,%eax,4)
428     sysenter_after_call:
429             movl %eax,PT_EAX(%esp)
430             LOCKDEP_SYS_EXIT
431             DISABLE_INTERRUPTS(CLBR_ANY)
432             TRACE_IRQS_OFF
433             movl TI_flags(%ebp), %ecx
由于getuid命令直接调用的sys_getuid系统调用例程,所以可以直接中断到相应的函数,但是getuid-asm直接使用的中断int 0x80.所以可以使用break sysenter_do_call。

    

    总结,通过自己利用老师的代码,套用一下,就可以在最小的linux系统下编写底层的命令,虽然无法完全分析明白运行的机制,但是粗略的可以懂得系统调用的大致过程,内核将经常使用的和硬件交互的代码封装为服务例程,并且对用户提供系统调用表,只要知道相应的编号对应什么样的系统功能,就可以通过传入编号给eax寄存器,使用系统调用的中断号int0x80就可以的到想要的结果。进一步,甚至可以将自己的特定代码保存为内核例程,编译在内核中,随时供用户调用。

本文出自 “StudyPark” 博客,请务必保留此出处http://swordautumn.blog.51cto.com/1485402/1627866

郑重声明:本站内容如果来自互联网及其他传播媒体,其版权均属原媒体及文章作者所有。转载目的在于传递更多信息及用于网络分享,并不代表本站赞同其观点和对其真实性负责,也不构成任何其他建议。