首页 > 开发 > 云计算 > 正文

向Linux内核增加一个系统调用

2016-07-12 21:15:23  来源:极客头条

发表于2016-3-20 20:36:34
收藏 一、实验目的
通过实验,熟悉Linux操作系统的使用,掌握构建与启动Linux内核的方法;掌握用户程序如何利用系统调用与操作系统内核实现通信的方法,加深对系统调用机制的理解;进一步掌握如何向操作系统内核增加新的系统调用的方法,以扩展操作系统的功能。
二、实验内容
1.  Linux环境下的C或C++编译和调试工具的使用。
2.  向Linux内核增加新的系统调用,系统调用名称和功能自行定义,但必须实现如下输出功能:“My Student No. is ×××,and My Name is ×××”。
3.  Linux新内核的编译、安装和配置。
4.  编写应用程序以测试新的系统调用并输出测试结果。
三、实验环境
Windows 10 x64 +VMware Workstation Pro 12 + Ubuntu10.04
四、实验步骤
1、安装VMware Workstation Pro 12 并在虚拟机上安装 ubuntu10.04。
2、安装编译源环境sudo apt-get install build-essential、sudo apt-get install gcc、sudo apt-get install g++ 编写一个c++或c程序,并使用gcc –o xxx 或 g++ -o xxx 进行编译并运行。 
3、用sudo apt-get update更新软件源,并用 apt-get install linux-source 命令下载适合自己的内核。
4、增加系统调用:
第一步:解压文件  
# cp linux-source-2.6.32.tar.bz2   /usr/src     拷贝至/usr/src目录
# tar xvf linux-source-2.6.32.tar.bz2      解压文件   
第二步:修改源程序,增加系统调用实现
#vi /usr/src/ linux-source-2.6.32 /kernel/sys.c
找一空白行,写入自己的系统调用:
asmlinkage int sys_mycall(int number)
{      
printk("My student No. is 71114236 and my name is Chen Jiahong!");     
return number;  
}
第三步:修改头文件,增加系统调用声名  
#vi /usr/src/linux-source-2.6.32/arch/x86/kernel/syscall_table_32.S  
将223行.long sys_ni_syscall改为.long sys_mycall(不要放在其他地方,否侧可能出现错误)
第四步:修改系统调用表,注册系统调用。  
#vi /usr/src/ linux-source-2.6.32/arch/x86/include/asm/unistd_32.h 增加一行,对应上面的223行:#define__NR_sys_mycall
5、编译安装内核
定位到/usr/src/linux-source-2.6.32目录
逐步执行如下指令:
第一步:make mrproper //清除内核中不稳定的目标文件,附属文件及内核配置文件
第二步:make clean //清除以前生成的目标文件和其他文件
第三步:make menuconfig  //配置内核,采用默认的内核配置即可。
第四步:make  //( 该命令等价于make bzImage编译内核 +make modules编译内核模块)
第五步:make modules_install //安装模块
安装完后,会在/lib/modules/ 目录下生成一个linux-source-2.6.32.63+drm33.26目录,下面存放该系统的内核模块。
第六步:make install  //安装内核,会自动修改启动文件。
可以看见编译后的新核心版本号:2.6.32.63+drm33.26
在终端执行以下命令:
cp /usr/src/linux-soucrce-2.6.32/arch/i386/boot/bzImage  /boot/vmlinuz-2.6.32.63+drm33.26  (拷贝内核镜像)
cp /usr/src/linux-source-2.6.32/System.map  /boot/System.map-2.6.32.63+drm33.26 (拷贝符号表)
cd /boot
mkinitramfs -o initrd.img-linux-source-2.6.32.63+drm33.26  2.6.32.63+drm33.26  (创建新核心的initrd.img文件)
6、修改启动配臵文件:
   直接使用如下指令:
   update-grub (更新grub引导文件)
   重启:reboot
7、测试系统调用
安装VIM文本编辑器,创建一个test.c文件进行编程。
#include
int main()
{         
syscall(223,1);//223是第五步中宏定义的入口参数,1为函数的参数,整型变量number        
return 0;
}


保存并退出,输入如下指令
# gcc test.c –o test
# ./test
# dmesg –c



结果如下图:

四、主要数据结构及其说明   
略 
五、程序运行时的初值和运行结果 
  初值:增加 printk("My student No.is 71114236 and my name is Chen Jiahong!"); 
  结果 如上图 
六、实验体会 
  1、首先,保证用来编译内核的系统是32位的, 这样才能够照着指导书来进行实验。64位的环境跟32的环境有很大差别且实验难度大大增加。
   2、运行update-grub就会自动生成grub.cfg而不用自己去手动更改grub.cfg文件。
  3、本实验虽不复杂,却极为耗费时间,而且出错后重新编译是一个很痛苦的过程,实验中多次遇到系统崩溃的,应该要及时做好备份工作。还有诸如64位系统的实验操作步骤不一样甚至虚拟机安装等问题,需要自己有很好的耐心与不放弃的品质,并且实验过程中要细致,理解每个步骤,否则会白白浪费时间。
七、源程序并附上注释     
//以测试新的系统调用并输出测试结果  
#include
int main()
{         
syscall(223,1);//223是第五步中宏定义的入口参数,1为函数的参数,整型变量number        
return 0;
}   
//修改源程序,增加系统调用实现  
asmlinkage int sys_mycall(int number)
{      
printk("My student No.is 71114236 and my name is Chen Jiahong!");     
return number;
} 本主题由 v 于 2016-3-24 17:38 移动本站禁止留下自己的邮箱和QQ账号,违规者一律封号处理【包括vip用户】