第二天 编译安装内核

注:操作步骤源自网络上,然后结合我操作时出现的现象做了修改。ubuntu 12.04+linux-2.6.34

第一步:准备工作

打开终端获得root权限:sudo su
然后安装编译内核时需要的工具:

apt-get install build-essential kernel-package libncurses5-dev libqt3-headers

 build-essential  (基本的编程库(gcc, make等)
 kernel-package   (Debian 系统里生成 kernel-image 的一些配置文件和工具)
 libncurses5-dev  (meke menuconfig要调用的)
 libqt3-headers   (make xconfig要调用的)
其他工具在升级过程中可以按提示安装

第二步:下载内核源代码linux-2.6.34.tar.gz

源码下载已经在第一节中已经说明。
假设下载在root目录,然后解压到/usr/src/linux-2.6.34目录里
cd /usr/src
tar zxvf /root/linux-2.6.34.tar.gz
解压后会在/usr/src生成新文件夹linux-2.6.34

第三步:配置

把正在使用中的内核配置文件/usr/src/linux-headers-3.11.0-15-generic/.config 拷到/usr/src/linux-2.6.34目录下

执行:sudo make mrproper   (清除以前曾经编译过的旧文件,如果你是第一次编译,可不执行)
cp /usr/src/linux-headers-3.11.0-15-generic/.config /usr/src/linux-2.6.34
执行:
cd /usr/src/linux-2.6.34
make menuconfig
终端会弹出一个配置界面
注意主菜单最后有两项:load a kernel configuration...
                  save a kernel configuration...
先选第一项load ....,意思是,利用当前的内核配置详单来设置将要编译的内核,然后选save这一项保存,最后退出配置界面。


第四步:开始编译安装新内核

注:这里的编译最好不要按照第一节的内容进行编译(make > /dev/null)
执行:sudo make     (编译,可以加-j4,如果你CPU是双核心,够牛的话,因为可以提高速度)
然后:sudo make install  
再:sudo make modules  (编译模块)
再:sudo make modules_install  (安装模块)
最后创建initrd文件:
mkinitramfs -o /boot/initrd.img-2.6.34


make过程中可能遇到的问题:

使用gcc4.6.3编译linux2.6.32.12内核出现错误如下:

         In file included from drivers/net/igbvf/ethtool.c:36:0:

         drivers/net/igbvf/igbvf.h: 在文件作用域:

         drivers/net/igbvf/igbvf.h:128:15: 错误: 重复的成员‘page’

         make[4]: *** [drivers/net/igbvf/ethtool.o] 错误 1

         make[3]: *** [drivers/net/igbvf] 错误 2

         make[2]: *** [drivers/net] 错误 2

         make[1]: *** [drivers] 错误 2

         make[1]:正在离开目录 `/usr/src/linux-2.6.32.2'

         make: *** [debian/stamp/build/kernel] 错误 2

解决方法:

1. 根据linux社区的建议,此错误是由于gcc版本与内核版本的冲突导致的。他们的建议是更换新版本的内核,但是某些特殊条件下,我们不能更换内核版本,于是我们修改内核代码适应当前的编译器。

2. 按照错误的指示,错误的代码是在drivers/net/igbvf/igbvf.h文件的第128行。

3. 打开文件,看128行,代码为:struct page *page;再往上看,第123行,也有struct page *page这行代码,这个结构定义在内部的一个结构体中。就是他的名字与128行的重复了,而4.6.3的编译器对不支持这种方式的定义,我们修改128行的代码为struct page *pagep;保存退出;

4. 重新编译,编译通过。


第五步:更新配置GRUB引导列表

注:在我的操作过程中这个步骤没有操作过,因为我执行完上面的步骤之后,打开这个文件后,这些内容已经添加进去了。内容如下,如果没有添加进去,按照你查看的这个文件内容添加相应的编译内核版本进去,修改的地方就只有把旧内核版本改成从你自己的就好。切记不要修改旧版本的内核相关内容。

menuentry 'Ubuntu,Linux 3.11.0-15-generic' --class ubuntu --class gnu-linux --class gnu --class os {

 recordfail

 gfxmode $linux_gfx_mode

 insmod gzio

 insmod part_msdos

 insmod ext2

 set root='(hd0,msdos1)'

 search --no-floppy --fs-uuid --set=root 21c02a19-5cdb-4177-9795-908a07469d04

 linux /boot/vmlinuz-3.11.0-15-generic root=UUID=21c02a19-5cdb-4177-9795-908a07469d04 ro   quiet splash $vt_handoff

 initrd /boot/initrd.img-3.11.0-15-generic

}

menuentry 'Ubuntu, with Linux 3.11.0-15-generic (recovery mode)' --class ubuntu --class gnu-linux --class gnu --class os {

 recordfail

 insmod gzio

 insmod part_msdos

 insmod ext2

 set root='(hd0,msdos1)'

 search --no-floppy --fs-uuid --set=root 21c02a19-5cdb-4177-9795-908a07469d04

 echo '载入 Linux 3.11.0-15-generic ...'

 linux /boot/vmlinuz-3.11.0-15-generic root=UUID=21c02a19-5cdb-4177-9795-908a07469d04 ro recovery nomodeset

 echo '载入初始化内存盘...'

 initrd /boot/initrd.img-3.11.0-15-generic

}

submenu "Previous Linux versions" {

menuentry 'Ubuntu,Linux 2.6.34' --class ubuntu --class gnu-linux --class gnu --class os {

 recordfail

 gfxmode $linux_gfx_mode

 insmod gzio

 insmod part_msdos

 insmod ext2

 set root='(hd0,msdos1)'

 search --no-floppy --fs-uuid --set=root 21c02a19-5cdb-4177-9795-908a07469d04

 linux /boot/vmlinuz-2.6.34 root=UUID=21c02a19-5cdb-4177-9795-908a07469d04 ro   quiet splash $vt_handoff

 initrd /boot/initrd.img-2.6.34

}

menuentry 'Ubuntu, with Linux 2.6.34 (recovery mode)' --class ubuntu --class gnu-linux --class gnu --class os {

 recordfail

 insmod gzio

 insmod part_msdos

 insmod ext2

 set root='(hd0,msdos1)'

 search --no-floppy --fs-uuid --set=root 21c02a19-5cdb-4177-9795-908a07469d04

 echo '载入 Linux 2.6.34 ...'

 linux /boot/vmlinuz-2.6.34 root=UUID=21c02a19-5cdb-4177-9795-908a07469d04 ro recovery nomodeset

 echo '载入初始化内存盘...'

 initrd /boot/initrd.img-2.6.34

}

下面是网上的步骤:
sudo gedit /boot/grub/grub.cfg
我的grub.cfg添加如下:
menuentry 'Ubuntu 14.04,Linux 2.6.34' --class ubuntu --class gnu-linux --class gnu --class os {
 recordfail
 insmod ext2
 set root='(hd1,9)'
 search --no-floppy --fs-uuid --set 501d3a42-1d52-4438-99bf-e679da605867
 linux /vmlinuz-2.6.34 root=UUID=33883099-83a5-49f3-9c12-ee6a4d90da9e ro   quiet splash
 initrd /initrd.img-2.6.34
}
#以下是原2.6.32内核启动项
menuentry 'Ubuntu,Linux 2.6.32-22-generic' --class ubuntu --class gnu-linux --class gnu --class os {
 recordfail
 insmod ext2
 set root='(hd1,9)'
 search --no-floppy --fs-uuid --set 501d3a42-1d52-4438-99bf-e679da605867
 linux /vmlinuz-2.6.32-22-generic root=UUID=33883099-83a5-49f3-9c12-ee6a4d90da9e ro   quiet splash
 initrd /initrd.img-2.6.32-22-generic
}

到此为止,整个内核的编译就全部完成啦。

第六步.启动自己编译的内核

重启系统,在出现提示按F12的时候按下ESC键,进入选择界面(本来是截图贴上的,只是不知道怎么贴图到CSDN),在一系列的选项中选择这一项:

Previous Linux Versions 进去之后选择:linux-2.6.34。

选择启动后可能会遇到如下问题:

        虽然启动菜单中增加了新内核2.6.34的启动项,但极可能会启动失败,出现以下提示:

warning:can't open directory /lib/modules/2.6.34/modules.dep,no such files or directory

        此时不应气馁,玩LINUX要有敢食螃蟹的勇气和毅力,哈哈。静下心,选择从旧内核启动登录系统,然后执行以下命令(为了避免输入错误,最好复制下面的命令)修改后就能成功启动新内核了。


######################################
sudo su  (保证获得root权限,否则会提示权限不够,不能成功完成任务哦)
cd /boot
cp initrd.img-2.6.34 initrd-2.6.34.old (先做一个备份以防万一,哈哈)
depmod -a
update-initramfs -k 2.6.34 -c
cd /tmp
gzip -dc /boot/initrd.img-2.6.34| cpio -id
touch lib/modules/2.6.34/modules.dep
find ./ | cpio -H newc -o > /boot/initrd.img-2.6.34.new
gzip /boot/initrd.img-2.6.34.new
cd /boot
mv initrd.img-2.6.34.new.gz initrd.img-2.6.34

######################################

完成上述操作后,重启系统。再按第6步骤操作。能进入系统就成功了,打开终端输入命令:uname -a 会打印你的内核版本。

到此内核编译和安装启动大功告成。


你可能感兴趣的:(linux内核设计与实现)