第三节 构造一个简单的Linux系统MenuOS——20135203齐岳
第三节 构造一个简单的Linux系统MenuOS
By 20135203齐岳
Linux内核源代码
- arch/ 支持不同cpu的源代码
- Documentations/ 文档存储
- init/ 内核启动相关代码
- kenerl/ 进程调度相关代码
- ipc/ 进程间通信
- lib/ 公共库文件
- mm/ 内存管理相关的代码
构造一个简单的Linux系统MenuOS
使用自己的Linux系统环境搭建MenuOS的过程
下载内核源代码编译内核
cd ~/LinuxKernel/
wget https://www.kernel.org/pub/linux/kernel/v3.x/linux-3.18.6.tar.xz
xz -d linux-3.18.6.tar.xz
tar -xvf linux-3.18.6.tar
cd linux-3.18.6
make i386_defconfig
make # 一般要编译很长时间,少则20分钟多则数小时
制作根文件系统
cd ~/LinuxKernel/
mkdir rootfs
git clone https://github.com/mengning/menu.git # 如果被墙,可以使用附件menu.zip
cd menu
gcc -o init linktable.c menu.c test.c -m32 -static –lpthread
#将内核编译成一个名为init的可执行文件,系统默认第一个用户进程为init,称为1号进程
cd ../rootfs
cp ../menu/init ./#将init文件拷贝到rootfs目录下
find . | cpio -o -Hnewc |gzip -9 > ../rootfs.img
启动MenuOS系统
cd ~/LinuxKernel/
qemu -kernel linux-3.18.6/arch/x86/boot/bzImage -initrd rootfs.img
第二句代码需要重点分析:
- qemu:启动已经安装在系统中的相当于虚拟机的程序qemu,这个程序为内核的启动提供一个上下文环境
- -kernel 文件名+路径:启动内核,内核经过编译之后形成一个名为init的文件,之前我们已经将它拷贝到rootfs文件目录之下,并通过cpio的方式将rootfs下的文件打包成一个名为rootfs.img的镜像文件。
- -initrd rootfs.img:指定rootfs为为启动时的硬件驱动
经过以上代码之后,rootfs.img会找到init这个可执行文件,init又是由MenuOS这个内核源代码编译而来,由此完成使用自己的Linux系统环境搭建并启动一个内核——MenuOS的过程。

跟踪调试Linux内核的启动过程
使用gdb跟踪调试Linux内核的方法
使用gdb跟踪调试内核
qemu -kernel linux-3.18.6/arch/x86/boot/bzImage -initrd rootfs.img -s -S

关于-s和-S选项的说明:
- -S freeze CPU at startup (use ’c’ to start execution)
- -s shorthand for -gdb tcp::1234 若不想使用1234端口,则可以使用-gdb tcp:xxxx来取代-s选项
另开一个shell窗口
gdb
(gdb)file linux-3.18.6/vmlinux # 在gdb界面中targe remote之前加载符号表
(gdb)target remote:1234 # 建立gdb和gdbserver之间的连接,按c 让qemu上的Linux继续运行
(gdb)break start_kernel # 断点的设置可以在target remote之前,也可以在之后
关于符号表
内核编译的时候为什么要生成符号表?
所谓内核符号表就是在内核内部函数或变量中可供外部引用的函数和变量的符号表,如下图所示。

在内核符号表中,左边一列是符号地址,右边一列是函数和变量。在汇编语言当中函数的调用通过Jump等机器指令来完成,于是就需要函数名,变量名和内存地址的映射,这种映射关系保存在符号表中,在调试的时候也会根据这种映射关系设置断点。
如果不加载符号表或者符号表加载错误,就会出现以下报错:

符号表加载成功之后断点设置成功,可以跟踪分析调试:

简单分析start_kernel
- trap_init() 初始化一些中断向量,管理硬件中断

这里的SYSCALL_VECTOR是一个系统调用,用指令的方式来触发中断。
mm_init() 内存管理模块
sched_init() 调度模块
rest_init()
rest_init()中的kernel_init其中945行处有一个run_init_process

这也就是Linux系统中的1号进程,是第一个用户态进程,默认是根目录下的一个程序;如果根目录下没有这个进程,系统会寻找其他的默认进程作为1号进程,当系统没有进程需要执行时就调度到idle进程。
rest init()就是一个0号进程,在start_kernel内核一启动时就一直存在;然后这个0号进程就创建了1号进程kernel_init,接下来还创建了其他的一些服务类的内核线程如kthreadd。这样整个系统就启动起来了。
参考资料
【原创作品转载请注明出处】 1.《Linux内核分析》MOOC课程http://mooc.study.163.com/course/USTC-1000029000
2.《 linux内核符号表 》http://blog.chinaunix.net/uid-21633169-id-1823329.html
第三节 构造一个简单的Linux系统MenuOS——20135203齐岳的更多相关文章
- Linux内核分析— —构造一个简单的Linux系统MenuOS(20135213林涵锦)
Linux内核分析— —构造一个简单的Linux系统MenuOS 实验内容 Linux内核的启动过程,从start_kernel到init进程启动 使用实验楼的虚拟机打开shell cd LinuxK ...
- 《Linux内核分析》第三周笔记 构造一个简单的Linux系统MenuOS
构造一个简单的Linux系统MenuOS 一.linux内核源代码简介 三大法宝(存储程序计算机.函数调用堆栈.中断)和两把宝剑(中断上下文的切换:保存现场和恢复现场.进程上下文的切换) 1.在lin ...
- Linux内核分析-构造一个简单的Linux系统MenuOS
构造一个简单的Linux系统MenuOS linux内核目录结构 arch目录包括了所有和体系结构相关的核心代码.它下面的每一个子目录都代表一种Linux支持的体系结构,例如i386就是Intel C ...
- 20135220谈愈敏Blog3_构造一个简单的Linux系统MenuOS
构造一个简单的Linux系统MenuOS 谈愈敏 原创作品转载请注明出处 <Linux内核分析>MOOC课程 http://mooc.study.163.com/course/USTC-1 ...
- Linux内核分析——构造一个简单的Linux系统MenuOS
马悦+原创作品转载请注明出处+<Linux内核分析>MOOC课程http://mooc.study.163.com/course/USTC-1000029000 一.Linux内核源代码简 ...
- LINUX内核分析第三周学习总结——构造一个简单的Linux系统MenuOS
LINUX内核分析第三周学习总结——构造一个简单的Linux系统MenuOS 张忻(原创作品转载请注明出处) <Linux内核分析>MOOC课程http://mooc.study.163. ...
- 《Linux内核分析》 第三周 构造一个简单的Linux系统MenuOS
Linux内核分析 第三周 构造一个简单的Linux系统MenuOS 张嘉琪 原创作品转载请注明出处 <Linux内核分析>MOOC课程http://mooc.study.163.com/ ...
- Linux第三周学习总结——构造一个简单的Linux系统MenuOS
第三周学习总结--构造一个简单的Linux系统MenuOS 作者:刘浩晨 [原创作品转载请注明出处] <Linux内核分析>MOOC课程http://mooc.study.163.com/ ...
- 20135327郭皓--Linux内核分析第三周 构造一个简单的Linux系统MenuOS
Linux内核分析第三周 构造一个简单的Linux系统MenuOS 前提回顾 1.计算机是如何工作的三个法宝 1.存储程序计算机 2.函数调用堆栈 3.中断 2.操作系统的两把宝剑 中断上下文的切换 ...
随机推荐
- react-native 计算时间差
//计算时间var sendTime = this.props.obj.send_time; console.log(sendTime); //当前时间var nowTime = (new Date( ...
- 20145320 《Java程序设计》第6周学习总结
20145320 <Java程序设计>第6周学习总结 教材学习内容总结 第十章 输入/输出 流(Stream)是对「输入输出」的抽象,注意「输入输出」是相对程序而言的 10.1 Input ...
- c++11 auto unique_ptr 等
c++11 条款21:尽量使用std::make_unique和std::make_shared而不直接使用new c++11 条款18: 使用std::unique_ptr来进行独享所有权的资源管理 ...
- JSP知识体系大全
Jsp动态网页 Web页面之间有3种关系: 包含 请求转发 重定向 l Jsp的运行原理:(3个) Jsp页面不能直接运行 1.容器调用jsp引擎编译jsp文件 成一个java文本(Servle ...
- jsp 环境配置记录
1. jdk,下载地址1 环境变量配置: 1)新建 JAVA_HOME 变量 . 变量值填写jdk的安装目录(本人是 C:\Java\jdk1.7.0) 2) 系统变量→寻找 Path 变量→编辑 ...
- 获取访问者ip的方法
package com.mi.util; import javax.servlet.http.HttpServletRequest; import org.apache.commons.lang3.S ...
- sklearn 组合分类器
组合分类器: 组合分类器有4种方法: (1)通过处理训练数据集.如baging boosting (2)通过处理输入特征.如 Random forest (3)通过处理类标号.error_corre ...
- Python爬虫--简单爬取图片
今天晚上弄了一个简单的爬虫,可以爬取网页的图片,现在现在做一下准备工作. 需要的库:urllib 和 re urllib库可以理解为是一个url下载器,其中有三个重要的方法 urllib.urlope ...
- [ruby]Windows Ruby安装步骤
Windows Ruby 安装步骤 准备工作: 1.http://rubyinstaller.org/downloads/ 下载选择Ruby 1.9.3 2.http://rubyinstaller. ...
- sysobjects中字段的含义
--列名 数据类型 描述 name sysname --对象名. Id int --对象标识号. xtype ) --对象类型.可以是下列对象类型中的一种: C = CHECK --约束 D = -- ...