linux内核学习之二:编译内核
在linux内核学习系列的第一课中讲述了搭建学习环境的过程(http://www.cnblogs.com/xiongyuanxiong/p/3523306.html),环境搭好后,马上就进入到下一环节--编译内核。linux的内核是整个系统最核心的部分,内核的功能基本上决定了系统的能力。
linux的内核代码使用的是GPL授权,允许自由下载,修改并重新发布内核,只要求发布修改后的内核的同时提供源代码。各种各样的内核版本众多,几乎所有的linux发行版都会对内核进行或多或少的修改,debian也不例外。这些内核都有个源头,即Linus维护的官方内核,其他的内核几乎都是建立在官方内核的基础上的。我们的内核学习,也是以官方内核为准。
linux官方内核的网站是:www.kernel.org。从里面可以了解到内核开发的最新动态,现在就把该网址加入收藏夹吧。(另外有个网站:www.lwn.net里面有许多linux大牛发表的观点,也值得收藏)。从linux内核3.0开始,内核版本命名采用的策略跟以前不一样,命名格式为3.A.B,其中A为内核的版本,B为补丁的版本。即3.A.B与3.A.C的内核是相同的版本,具有相同的功能,如果C>B,只是说明3.A.C相比3.A.B修补了一些BUG而已。进入内核3.0时代后,内核的开发工作发展迅速,版本更新得很快,第一个3.0版本是在2011年7月,而现在,最新的稳定版已是3.12.8,而新的3.13版内核开发工作也已接近尾声,即将发布稳定版了。("zh.wikipedia.org/wiki/linux"内核"介绍了部分版本的特性)。
1 选择内核版本
首先我们需要从www.kernel.org选择一个版本。实际上从2.6版本开始,内核的架构没有特别大的变动,基本上是添加新的功能,添加新的驱动的支持,内核接口有一些变动。另外,除非不得已,不要再使用2.4及更低版本,因为2.6内核的整个架构经过全面重新设计,效率更高,功能更完善,也更安全。我觉得尽量选择与发行版使用的内核版本差不多的话会比较好点,内核跟其他组件相对会配合得好些,不知是不是这样。debian7.3使用的内核是3.2的,而现在该内核版本的最新版为3.2.54,使用相同内核版本的带有最新补丁的内核重编译并替换原来的内核,可以最大程度上减少与系统其他部分的兼容性问题,这样我们可以将主要精力集中在内核的学习上。下载得到的内核名为linux-3.2.54.tar.xz。下面将描述在上一课中搭建的“windows7+vmware10.0.1+debian7.3”的系统中编译内核linux-3.2.54的步骤,在真实机器上安装的debian7.3系统上编译的方法也是类似的。
2 安装vmware-tools
内核文件下载好后,需复制到vmware客户系统(即debian系统)。最好的方法是使用vmware提供的文件共享功能,这个功能由vmware-tools软件包提供,需要先安装该软件包。首先设置共享目录,在VMware菜单栏上点击"虚拟机"-->"设置",打开设置页面,点击"选项"属性页,点击"共享文件夹",在右端选择"总是启用",再点击"添加",按提示设置主机中用于共享的目录路径和共享名称(我用的是workspace)。
启动debian系统后,点击菜单栏的"虚拟机"-->"安装VMWare Tools"。稍等片刻后,虚拟机的CD光驱动应该已经有了vmware-tools的安装盘。在debian系统按以下步骤进行:
挂载光盘:sudo mount /dev/cdrom /media/cdrom
复制安装包: cp /media/cdrom/VM*.tar.gz ./
解压安装包:tar -xvf ./VM*.tar.gz
cd ./vmware-tools-distrib
安装:sudo ./vmware-install.pl(安装过程中所有选项都使用默认即可)
安装完成了,检查发现/mnt目录下多了一项hgfs目录,里面是主机共享目录,即/mnt/hgfs/workspace。
3 准备新的内核源代码
将下载的内核源代码放在上一步中设置的主机共享目录中,然后解压到默认的内核源代码目录:sudo tar -xvf /mnt/hgfs/workspace/linux-*.tar.gz -C /usr/src
/usr/src目录下是专门存放内核源代码的。放在其他目录也可以编译的,不过我们还是遵循通用的规则吧。我们的debian系统是64位版本(正式名称是x86_64),为了避免出现问题,我们的内核也将编译成x86_64版本,故修改下源代码目录名称:sudo mv /usr/src/linux-3.2.54 /usr/src/linux-3.2.54.x86_64.同时把源代码目录下的Makefile文件内容也改一下:
sudo vim /usr/src/linux-3.2.54.x86_64/Makefile
搜索字符串"EXTRAVERSION =",在"="后面加上".x86_64"。
这样,编译出来的内核镜像,模块目录等都会自动加上".x86_64"后缀。
4 配置内核
配置内核就是告诉编译器,源代码中的哪些功能要编译进内核,哪些编译成模块,哪些不需要编译。源码中包含了几千个选择,因此配置内核是个很复杂很吃力的工作,为了简化这个工作,内核开发者为各个平台编写了默认的简单配置文件。以x86平台为例,配置文件放在"arch/x86/configs"目录下,可将这些配置文件作为配置工作的起点,选择其中一个文件复制到源码目录下,并命令名为".config"(注意前面有个".",它是隐藏文件),这是内核编译时使用的配置文件,也是内核配置工具启动时加载的文件,当然内核配置修改后的配置信息也保存在这个文件里。
由于VMWare的硬件与普通的硬件不同,用内核开发者提供的配置文件编译出来的内核无法引导系统,我们先暂时忽略有关内核配置的复杂细节,走条捷径,以debian系统安装时产生的配置文件作为我们配置内核的起点。既然debian能引导,用它编译出来的内核应该不会有什么大问题,复制debian的配置文件到源代码目录,并配置:
sudo cp /boot/config-3.2.0-4-amd64 /usr/src/linux-3.2.54.x86_64/.config
cd /usr/src/linux-3.2.54.x86_64/
sudo make menuconfig
即使不修改内核的配置还是需要执行sudo make menuconfig,因为发行版的内核可能经过修改,使用的.config也可能会有差异,执行一下sudo make menuconfig,它会重新分析.config文件,设置文件中描述的配置信息,退出后再保存成新内核适用的.config文件(退出时,配置工具会询问你是否保存修改,需要选择"yes")。
5 编译,安装新内核
内核配置完成了,可以编译内核了,分别执行以下命令,进行编译并安装内核:
sudo make
sudo make modules_install
sudo make install
make命令根据配置信息进行编译,包括模块。debian系统默认加入了许多驱动模块,整个编译过程比较耗时,估计长达1.5~2个小时,在编译时可能出现各种问题,需要根据错误提示进行修改。本次编译模块时就提示“drivers/staging/rts5139”这个模块编译出错,这是一个USB读卡器的驱动,不是什么必需的驱动,直接在内核配置中去掉该模块吧。因此,重新执行sudo make menuconfig,找到该模块:“Device Drivers”-->"Staging drivers"-->"Realtek RTS5139 USB card reader support"。去掉该模块支持,退出保存,重新执行sudo make。
make modules_install命令用于安装可装载模块,这些模块会自动安装到/lib/modules/3.2.54.x86_64下。
make install命令执行三个操作:复制内核镜像到/boot目录下;生成initrd-img;更新grub。命令成功执行成功后,新的内核已可以使用,并且列在引导菜单中。
6 重启系统
重启系统,grub引导选项中多了我们新编译的内核选择,选择新内核引导。进入系统后执行命令uname -r 查看当前的内核版本,显示为“3.2.54.x86_64”,确实是我们新编译的内核。不过,在VMWare中重编译内核后,vmware-tools的文件共享功能不起作用了,这是因为vmware-tools中包含了内核模块,重编译后,这些模块不能再正常加载了。只需执行命令:sudo vmware-config-tools.pl(全部使用默认选项),重新配置vmware-tools即可让共享功能正常使用。
任务完成,可以收工!
linux内核学习之二:编译内核的更多相关文章
- Linux内核学习笔记二——进程
Linux内核学习笔记二——进程 一 进程与线程 进程就是处于执行期的程序,包含了独立地址空间,多个执行线程等资源. 线程是进程中活动的对象,每个线程都拥有独立的程序计数器.进程栈和一组进程寄存器 ...
- linux内核学习之三 跟踪分析内核的启动过程
一 前期准备工作 1 搭建环境 1.1下载内核源代码并编译内核 创建目录,并进入该目录: 下载源码: 解压缩,并进入该目录:xz -d linux-3.18.6.tar.xz tar ...
- linux驱动学习(二) Makefile高级【转】
转自:http://blog.csdn.net/ghostyu/article/details/6866863 版权声明:本文为博主原创文章,未经博主允许不得转载. 在我前一篇写的[ linux驱动学 ...
- linux内核学习之二 一个精简内核的分析(基于时间片轮转)
一 实验过程及效果 1.准备好相关的代码,分别是mymain.c,mypcb.h,myinterrupt.c ,如下图,make make成功: 在qemu创建的虚拟环境下的运行效果:(使用的命令 ...
- Linux线程学习(二)
线程基础 进程 系统中程序执行和资源分配的基本单位 每个进程有自己的数据段.代码段和堆栈段 在进行切换时需要有比较复杂的上下文切换 线程 减少处理机的空转时间,支持多处理器以及减少上下文切换开销, ...
- linux初级学习笔记二:linux操作系统及常用命令,文件的创建与删除和命名规则,命令行展开以及linux中部分目录的作用!(视频序号:02_3)
本节学习的命令:tree,mkdir,rmdir,touch,stat,rm 本节学习的技能:Linux中主要的目录作用以及特殊的目录文件: 文件的命名规则,命令行展开: 文件的创建与删除: Linu ...
- Linux服务器学习(二)
昨天简单了解了linux的基础命令,今天学习linux搭建环境(安装文件,配置文件)及权限操作. 一.搭建lnmp环境 lnmp指Linux+Nginx+Mysql+PHP Ubuntu安装文件命令为 ...
- linux shell学习笔记二---自定义函数(定义、返回值、变量作用域)介绍
linux shell 可以用户定义函数,然后在shell脚本中可以随便调用.下面说说它的定义方法,以及调用需要注意那些事项. 一.定义shell函数(define function) 语法: [ f ...
- 马哥Linux SysAdmin学习笔记(二)
Linux网络属性管理: 局域网:以太网,令牌环网 Ethernet:CSMA/CD 冲突域 广播域 MAC:media access control地址 48bit: 24bits 24bits ...
随机推荐
- HTML参考手册
New : HTML5 中的新标签. 标签 描述 <!--...--> 定义注释. <!DOCTYPE> 定义文档类型. <a> 定义锚. <abbr> ...
- Tomcat配置NIO
tomcat的运行模式有3种.修改他们的运行模式.3种模式的运行是否成功,可以看他的启动控制台,或者启动日志.或者登录他们的默认页面http://localhost:8080/查看其中的服务器状态. ...
- GitHub 的分支创建与合并
一个Git仓库可以维护很多开发分支.现在我们来创建一个新的叫"experimental"的分支: $ git branch experimental 如果你运行下面这条命令: $ ...
- TF卡格式化8G格式化时候变成128KB的解决办法
我的8GC6卡,APPS2SD后,因为不满意分区容量,所以就想删除分区重新分配容量. 删除分区方法:我的电脑---管理---磁盘管理--里删除了EXT3分区, 结果导致TF卡变成FAT格式且没有容量. ...
- 用Lighttpd做图片服务器
http://www.lsanotes.cn/install_lighttpd 用Lighttpd做图片服务器 一.安装lighttpd所需的库文件1.安装 pcrewgetftp://ftp.csx ...
- linux常用命令 http://mirrors.163.com/ubuntu-releases/12.04/
由于记忆力有限,把平时常用的Linux命令整理出来,以便随时查阅: linux 基本命令 ls (list 显示当前目录下文件和目录 ls -l 详细显示 =ll ) [root@linux ...
- Qt 学习之路:线程和事件循环
前面一章我们简单介绍了如何使用QThread实现线程.现在我们开始详细介绍如何“正确”编写多线程程序.我们这里的大部分内容来自于Qt的一篇Wiki文档,有兴趣的童鞋可以去看原文. 在介绍在以前,我们要 ...
- Linux中date命令的各种实用方法--转载
在linux环境中,不管是编程还是其他维护,时间是必不可少的,也经常会用到时间的运算,自己也曾经为时间的各种表示方法和如何修改时间而困惑,熟练运用date命令来表示自己想要表示的时间,肯定可以给自己的 ...
- ActiveNotifications
The NotificationManager can tell you how many notifications your application is currently showing. T ...
- NSIndexPath初始化
在UITableView中经常用到这个类,但一直不知道怎么初始化,网上抄录的代码如下,果然好用 NSIndexPath *index = [NSIndexPath indexPathForRow:0 ...