Linux 内核 (Kernel) 编译与管理详解
内核(Kernel)
内核(Kernel) 计算机完成的工作们,都必须要内核支持才行。内核其实就是系统上面的一个文件。该文件包含了驱动主机各项硬件的检测程序与驱动模块。主机上可以拥有多个内核文件。启动的时候只能选择一个加载。 Linux很早就使用模块化设置(将一些不常用的类似驱动程序的东西独立出内核,编译成模块)。内核可以在系统正常运行的过程中加载模块。在不修改内核的前提下,加载编译过的适当内核模块就可以使用这个硬件。简单又方便。模块存放在/lib/modules/$(uname -r)/kernnel/中 内核文件是通过源代码编译而成。内核是直接读入到内存中。必须要编译成系统可识别的数据才行。 可以获取内核的源代码,利用Tarball安装方式完成内核编译。
更新内核的目的 需要Linux做什么?没有必要的工作就不要加入内核。系统已经将内核编译得相当适合一般用户使用了,一般用户基本上不需要编译内核
内核源代码得获取方式: Linux发行版在推出得时候已经附上内核源代码了。主要源代码在下面网站上 全部的 CentOS 原始 SRPM:http://vault.centos.org/ CentOS 7.1 的 SRPM:http://vault.centos.org/7.1.1503/ 内核官网:http://www.kernel.org/ 中国科技大学镜像站:http://centos.ustc.edu.cn/linux-kernel/ 清华大学镜像站:https://mirrors.tuna.tsinghua.edu.cn/kernel/
利用patch升级内核源代码: 内核发布时,除了完整得内核压缩文件外,也会发布[该版本与前一版本得差异性patche文件]。每个内核的patche文件仅针对前一内核版本来分析。想要由3.10.85升级到3.10.89的话,就需要下载 patch-3.10.86, patch-3.10.87, patch-3.10.88, patch-3.10.89等文件,然后依序一个一个的进行patch操作。 如果某个硬件或者非官方发布的内核功能patch文件,必须了解该patch文件适用的内核版本。
内核源代码的解压缩、安装、查看 从CentOS官网获取的SRPM或是从Linux内核官网获取的Tarball内核源代码,都会有一个tarball的内核源代码。 从Linux内核官网获取linux-3.10.89.tar.xz内核文件。地址: ftp://ftp.twaren.net/pub/Unix/Kernel/linux/kernel/v3.x/linux-3.10.89.tar.xz
内核源代码的解压缩与放置目录 假设从官网下载内核源代码文件在/root下(建议放置在/usr/src/kernels) [root@study ~]# tar -Jxvf linux-3.10.89.tar.xz -C /usr/src/kernels/ 会在/usr/src/kernels下产生一个新目录Linux-3.10.89.(内核的编译与设置必须在此目录下进行)。 内核源代码下的子目录:(内核目录下重要的数据) arch :硬件平台有关的项目,大部分指的是 CPU 的类别,如 x86, x86_64, Xen 虚拟化支持等; block :块设备较相关的设置,块数据通常指大容量存储设备! 包括是否支持类似 ext3 等文件系统。 crypto :内核支持的加密技术,例如 md5 或者是 des 等等; Documentation :内核有关的说明文件,对内核有极大的兴趣,可以看看! drivers :一些硬件的驱动程序,例如显卡、网卡、PCI 相关硬件等; firmware :一些旧硬件的固件; fs :内核支持的文件系统(filesystems) ,例如 vfat, reiserfs, nfs 等; include :可让其他程序调用的头(header)文件; init :内核初始化的功能,包括挂载与 init 程序的调用等; ipc :定义 Linux 操作系统内各程序间的通信; kernel :定义内核的程序、内核状态、线程、进程的调度 (schedule)、进程的信号 (signle) 等 lib :函式库; mm :内存单元有关的各项数据,包括 swap 与虚拟内存等; net :网络有关的协议数据,还有防火墙模块 (net/ipv4/netfilter/*) 等等; security :包括 selinux 等在内的安全性设置; sound :音效有关的各项模块; virt :虚拟化有关的信息,目前内核支持的是 KVM (Kernel base Virtual Machine)
内核编译前的预处理与内核功能选择 内核的目的是管理硬件与提供系统内核功能。所以得先找到系统硬件,并且规划主机的未来计划。 内核编译的重要工作就是【选择你想要的功能】 示例: 主机配置如下 CPU:Intel(R) Xeon(R) CPU E5-2650 主板芯片组: KVM 虚拟化的主版 (Intel 440FX 兼容) 显卡: Red Hat, Inc. QXL paravirtual graphic card 内存: 2.0GB 内存 硬盘: KVM Virtio 接口磁盘 40G (非 IDE/SATA/SAS ) 网络卡: Red Hat, Inc Virtio network device 未来需要开启防火墙,WWW服务器功能,FTP服务器功能,就是一个小型服务器的功能
保持干净的源代码:make mrproper 了解硬件后要处理一下内核源代码下面的残留文件。可以通过下面的方式处理掉编译过程的目标文件及配置文件 [root@study ~]# cd /usr/src/kernels/linux-3.10.89/ [root@study linux-3.10.89]# make mrproper 这个操作会将以前进行过的内核功能选择文件也删除掉。(建议只有第一次执行内核编译前进行这个操作)。除此之外要删除前一次编译过成的残留数据,只要执行: [root@study linux-3.10.89]# make clean make clean仅会删除类似目标文件之类的编译过程中产生的中间文件,不会删除配置文件。
开始选择内核功能:make Xxconfig /boot下有一个config-xxx文件。这个就是内核功能列表文件。下面进行的操作就是制作出该文件。后面要进行的编译操作也是通过这个文件处理的。内核功能的选择最后会在/usr/src/kernels/linux-3.10.89/下产生一个.config的隐藏文件。这个文件就是/boot/config-XXX文件。这个文件的建立方法有: make menuconfig 最常使用的命令行模式下面可以显示纯文本界面的方式,不需要启动 X Window 就能够选择内核功能选项!
make oldconfig 通过使用已存在的 ./.config 文件内容,使用该文件内的设置为默认值,只将新版本内核中的新功能选项列出让用户选择, 可以简化内核功能的选择过程! 对于作为升级内核源代码后的功能选择是非常好用的一个选项!
make xconfig 通过以 Qt 为图形界面基础功能的图形化接口显示,需要具有 X window 的支持。 例如 KDE 就是通过 Qt 来设计的 X Window,因此你如果在 KDE 画面中,可以使用此选项。
make gconfig 通过以 Gtk 为图形界面基础功能的图形化接口显示,需要具有 X window 的支持。 例如GNOME就是通过 Gtk 来设计的 X Window,因此你如果在 GNOME 画面中,可以使用此选项。
make config 最原始的功能挑选方法,每个选项都以列表方式一条一条的列出让你选择,如果设置错误只能够再次选择,很不人性化! 还有更多的方式参考内核目录下的README文件。推荐make menuconfig方式。如果是升级内核源代码并且需要重新编译,建议使用make oldconfig。
通过既有的设置来完成内核选项与功能选择
既然CentOS已经提供了它的内核设置值,只是想修改一些小细节,可以以CentOS 7的内核功能为基础,然后详细微调其他设置。
[root@study linux-3.10.89]# cp /boot/config-3.10.0-229.11.1.el7.x86_64 .config
# 上面的版本根据自己的系统环境来填写
下面开始调整,以make menuconfig(可能会要求装好多软件,自行使用yum安装。不要再使用make mrproper.因为复制了.config,使用make mrproper会将.config删除)
界面主要分为两部分,一个是大框框内的反白光条,另一个是下面的小框框, 里面有 select, exit 与 help 三个选项。 这几个组件的大致用法如下:
『左右方向键』:可以移动下面的 <Select>, <Exit>, <Help>选项;
『上下方向键』:可以移动上面大框框部分的反白白条,若该行有箭头 (—>) 则表示该行内部还有其他详细
选项需要设置;
选定选项:以【上下键】选择要设置的选项之后,以【左右键】选择 <Select> 之后, 按下【 Enter 】就可以进
入该选项做进一步的设置;
可选择的功能:在详细选项的设置中,前面有 [ ] 或 < > 符号时,该选项才可以选择, 选择使用【空白键】来选
择;
若为 [*] <*> 表示编译进内核; 若为 <M>表示编译成模块! 尽量在不知道该项目是什么时,有模块可以选,那么
就可以直接选择为模块!
选择<Exit>后,并按下【Enter】,就可以退出了!
关于内核功能的选择,建议如下: 『肯定』内核一定要的功能,直接编译进内核中; 『未来可能会用到』的功能,尽量编译成为模块; 『不知道的功能,看Helo也看不懂』的,保留默认值或将他编译成为模块;
内核功能详细选项: 内核可以选择的项目有很多,每个选项内还有不同的详细选项。看不懂的选项务必使用Help查看。 使用CentOS 7内核的配置文件进行默认的设置,许多默认的设置不需要重新调整。下面时几个比较重要的设置选项。其他更相信的内核功能查看Help
General setup 主要是针对内核与程序之间的相关性设置,保持默认值就好。 (vbird) Local version - append to kernel release [*] Automatically append version information to the version string # 希望我的内核版本为 3.10.89.vbird ,这样设置! Kernel compression mode (Bzip2) —> # 建议选择 Bzip2 即可,压缩比较好! …..(其他保留默认值)…..
<M> Kernel .config support [ ] Enable access to .config through /proc/config.gz (NEW) # 让.config 这个内核功能列表可以写入实际的内核文件中!所以就不需要保留 .config 文件! (20) Kernel log buffer size (16 => 64KB, 17 => 128KB) # CentOS 7 增加了内核的日志文件容量,占用了2的20次方。大概用了1MB容量 …..(其他保留默认值)…..
[*] Initial RAM filesystem and RAM disk (initramfs/initrd) support () Initramfs source file(s) # 这是一定要的,因為要支持启动时加载 initail RAM disk [ ] Optimize for size # 降低内核文件的大小,其实 gcc 参数使用 -Os 而不是 -O2。不是嵌入式系统,不太需要 [ ] Configure standard kernel features (expert users) —> [ ] Embedded system # 上面两个选项是决定是否支持嵌入式系统,台式机不用选择 …..(其他保留默认值)…..
loadable module + block layer 内核能够支持动态的内核模块,下面第一个设置要启动。第二个block layer默认是启动的。 [*] Enable loadable module support —> <==下面是详细选项 — Enable loadable module support [*] Forced module loading [*] Module unloading [*] Forced module unloading # 这个项目可以选择,免得常常无法卸载模块! [*] Module versioning support [*] Source checksum for all modules [*] Module signature verification [ ] Require modules to be validly signed [*] Automatically sign all modules Which hash algorithm should modules be signed with? # 可以选择 SHA256 即可!
-*- Enable the block layer —> <==默认已经选择了。下面为详细选项 -*- Block layer SG support v4 -*- Block layer SG support v4 helper lib [*] Block layer data integrity support [*] Block layer bio throttling support Partition Types —> # 下面的几个选项要选择! [*] Macintosh partition map support [*] PC BIOS (MSDOS partition tables) support [*] Windows Logical Disk Manager (Dynamic Disk) support [*] SGI partition support [*] EFI GUID Partition support …..(其他保留默认值)…..
IO Schedulers —> # 磁盘阵列的处理方式 <*> Deadline I/O scheduler # 建议将此选项设置为内核功能! <*> CFQ I/O scheduler [*] CFQ Group Scheduling support Default I/O scheduler (Deadline) —> # 建议改成Deadline
CPU的类型与功能选择 进入【Processor type and features】后,选择主机实际CPU类型。启动KVM虚拟化服务。设置如下: …..(其他保留默认值)….. [*] Linux guest support —> # 提供 Linux 虚拟化功能 [*] Enable paravirtualization code # 下面几个一定要选择 [*] Paravirtualization layer for spinlocks [*] Xen guest support [*] KVM Guest support (including kvmclock) [*] Paravirtual steal time accounting …..(其他保默认值)…..
Processor family (Generic-x86-64) —> #除非是旧系统,否则就用它! [*] Enable Maximum number of SMP Processors and NUMA Nodes [*] Multi-core scheduler support Preemption Model (No Forced Preemption (Server) —> # 调整成 server ,原本是 desktop …..(其他保留默认值)…..
Timer frequency (300 HZ) —> # server 设置成 300 ! # 这个选项是内核针对某个事件立即响应的速度有关,Server 用途可以调整到300Hz # 桌面电脑需要调整高一些。例如1000H z较好 …..(其他保留默认值)…..
电源管理功能 选择[Power management and ACPI options]进入系统的电源管理机制中.(要搭配主板及CPU的相关省电功能) …..(其他保留預設值)….. [*] ACPI (Advanced Configuration and Power Interface) Support —> #嵌入式系统可能会增加内核体积需要考虑一下,至于 desktop/server 当是选择 # 详细选项大致保持默认值即可 CPU Frequency scaling —> #决定 CPU 频率的一个重要选项,基本上的选项是 ondemand 與 performance 两者! <M> CPU frequency translation statistics [*] CPU frequency translation statistics details Default CPUFreq governor (ondemand) —> # 现在建议用这个! -*- ‘performance’ governor <*> ‘powersave’ governor <*> ‘userspace’ governor for userspace frequency scaling -*- ‘ondemand’ cpufreq policy governor <*> ‘conservative’ cpufreq governor x86 CPU frequency scaling drivers —> # 这个子选项全部是都是省电功能,能编译成模块的全部选择,要加入内核的全部加入!
总线(bus)的选项 【Bus options (PCI etc.)】与总线有关。分为最常见的PCI与PCI-express、还有笔记本电脑常见的PCMCIA卡。注意:PCI-E的接口务必要选取,不然新显卡可能无法识别。 [*] PCI support [*] Support mmconfig PCI config space access [*] PCI Express support <*> PCI Express Hotplug driver …..(其他在 PCI Express 下面的选项大多保留默认值)….. -*- Message Signaled Interrupts (MSI and MSI-X) <*> PCI Stub driver # 要玩虚拟化这两部分建议编进内核! …..(其他保留默认值)…..
编译后执行文件的格式 [Executable file formts / Emulations]里有如下选项,下面的选项必须要勾选才行。这是给Linux内核执行文件用的模块。通常与编译操作有关。 -*- Kernel support for ELF binaries [*] Write ELF core dumps with partial segments <*> Kernel support for scripts starting with #! <M> Kernel support for MISC binaries [*] IA32 Emulation <M> IA32 a.out support [*] x32 ABI for 64-bit mode # CentOS已经是纯64位的环境,建议这里要选择模拟32位的功能! # 不然有些比较旧的软件,可能会无法运行
内核的网络功能 [Networking support]是相当重要的选项。它包含了防火墙相关的选项。防火墙是在系统网络之后再设置就行。绝大部分内容建议编译成模块。有用在加载到内核 — Networking support Networking options —> # 这里的内容全部是重要的防火墙选项,尽量编译成模块! # 不了解的部分尽量保留默认值。 # 下面的内容是原本没有选择,建议选择的部分 [*] Network packet filtering framework (Netfilter) —> # 这个就是防火墙部分,里面的详细选项几乎全部选择称为模块! — Network packet filtering framework (Netfilter) Core Netfilter Configuration —> <M> Transparent proxying support
[*] QoS and/or fair queueing —> <==内容同样全为模块! Network testing —> <保留成模块默认值
#下面是一些特殊的网络设备,例如红外线、蓝牙! # 不清楚的话就使用模块。除非你真的不要该选项。 <M> Bluetooth subsystem support —> # 蓝牙支持,里面除了必选之外,其他全部成为模块 [*] Wireless —> # 这是无线网络设备,里面保留默认值,但可编成模块的就选模块 <M> WiMAX Wireless Broadband support —> # 新一代的无线网络设备,也勾选成模块 <M> NFC subsystem support —> # 和NFC(近场通信)芯片支持有关,建议编译成模块,内部选项也编译成模块为佳。
各项设备的驱动程序 [Device Drivers]所有硬件设备的驱动程序库,内容太多。建议一项一项的选择。里面很多驱动都与硬件有关。内核推出时默认值都是符合常规状态的。很多数据保留默认值已经很不错了。因为较符合一般状态。所以内核额外编译进来很多和你主机系统不符合的驱动。要考虑到扩充性。 # 大部分都保留默认值。比较重要的在下面。注意 <M> Serial ATA and Parallel ATA drivers —> # 就是 SATA/IDE 磁盘!大多选择为模块 [*] Multiple devices driver support (RAID and LVM) —> # 就是 LVM 与 RAID !要选 -*- Network device support —> # 网络方面的设备,网卡与相关设备。 -*- Network core driver support <M> Bonding driver support # 与网卡整合有关的选项,要选! <M> Ethernet team driver support —> # 与 bonding 差不多的功能,要选! <M> Virtio network driver # 虚拟网卡驱动程序,要选 -*- Ethernet driver support —> # 以太网卡,里面一堆10Gb卡,要选 <M> Chelsio 10Gb Ethernet support <M> Intel(R) PRO/10GbE support <M> PPP (point-to-point protocol) support# 与拨号有关的协议 USB Network Adapters —> # 全部编译为模块 [*] Wireless LAN —> # 无线网卡也相当重要,里面全部编译成模块
[ ] GPIO Support —> # 使用类似树莓派、香蕉派才需要 <M> Multimedia support —> # 多媒体设备,如摄像头、调频广播设备等 Graphics support —> # 显卡,作为桌面电脑使用,这里就很重要 <M> Sound card support —> # 声卡,作为桌面电脑使用,这里就很重要 [*] USB support —> # 就是USB,下面交给内部的详细选项要注意勾选 <*> xHCI HCD (USB 3.0) support <*> EHCI HCD (USB 2.0) support <*> OHCI HCD support <*> UHCI HCD (most Intel and VIA) support <M> InfiniBand support —> # 较高级的网路设备,速度通常达到40Gb以上。 <M> VFIO Non-Privileged userspace driver framework —> # 作为 VGA passthrought 用 [*] VFIO PCI support for VGA devices [*] Virtualization drivers —> # 虚拟化的驱动程序 Virtio drivers —> # 在虚拟机里面很重要的驱动程序 [*] IOMMU Hardware Support —> # 同样与虚拟化相关性较高 【Firmwaer Drivers】选项根据需求来,建议保留默认就行。
文件系统的支持 很重要的一项内核功能,如果不支持某个文件系统,Linux内核就无法识别,也无法使用。 # 下面仅列出比较重要与默认值的不同的选项!所以选项少很多! <M> Second extended fs support # 默认已经不支持 ext2/ext3,这里将它加回来! <M> Ext3 journalling file system support [*] Default to ‘data=ordered’ in ext3 (NEW) [*] Ext3 extended attributes (NEW) [*] Ext3 POSIX Access Control Lists <M> The Extended 4 (ext4) filesystem # 一定要有的支持 <M> Reiserfs support <M> XFS filesystem support # 一定要有的支持 [*] XFS Quota support [*] XFS POSIX ACL support [*] XFS Realtime subvolume support # 增加这一项 <M> Btrfs filesystem support # 最好有支持 [*] Quota support <*> Quota format vfsv0 and vfsv1 support <*> Kernel automounter version 4 support (also supports v3) <M> FUSE (Filesystem in Userspace) support DOS/FAT/NT Filesystems —> <M> MSDOS fs support <M> VFAT (Windows-95) fs support (950) Default codepage for FAT # 要改成这样,中文支持 (utf8) Default iocharset for FAT # 要改成这样,中文支持 <M> NTFS file system support # 建议加上 NTFS [*] NTFS write support # 让它可读写 Pseudo filesystems —> # 类似 /proc ,保留默认值 -*- Miscellaneous filesystems —> # 其他文件系统的支持,保留默认值 [*] Network File Systems —> # 网络文件系统,很重要。 <M> NFS client support <M> NFS server support [*] NFS server support for NFS version 4 <M> CIFS support (advanced network filesystem, SMBFS successor) [*] Extended statistics [*] Provide CIFS client caching support -*- Native language support —> # 选择默认语系。 (utf8) Default NLS Option <M> Traditional Chinese charset (Big5)
内核开发、信息安全、密码应用 【Kernel hacking】选项,是与内核开发者有关的部分,建议保留默认值。 【Security Options】选项,属于信息安全方面的设置,包括SElinux权限强化模块。编入内核,SElinux作为默 认值,且务必将NSA SElinux编进内核。其他的详细选项保留默认值。 【Cryptographic API】选项,密码API工具选项,以前的默认加密算法是MD5、近几年改用了SHA算法,默认已经将 所有的加密算法都编译进来了,也可以保留默认值。
虚拟化与函数库 计算机能力太强,时常闲置,通过虚拟化技术在一台主机上面同时启动多个操作系统来运行,就是虚拟化。Linux内核已经集成虚拟化功能。Linux认可的虚拟化机制为KVM(Kernel base Virtual Machine). 常用函数库也可以全部编为模块。 [*] Virtualization —> — Virtualization <M> Kernel-based Virtual Machine (KVM) support <M> KVM for Intel processors support <M> KVM for AMD processors support [*] Audit KVM MMU [*] KVM legacy PCI device assignment support # 虽然有了VFIO,还是建议悬起来! <M> Host kernel accelerator for virtio net
Library routines —> # 这部分全部保留默认值
然后回到主页面,在下方设置处移到[Save],点击该选项。在出现的窗口中确认文件为.config之后。按下[ok]。这样刚刚处理的选项就记录下来了。然后选择推出。准备进行编译操作
内核的编译与安装 最复杂的内核功能选择完毕后,就时进行内核模块的编译了。编译完成后就是使用,grub
编译内核与内核模块 内核与内核模块需要先编译,编译的过程非常简单。可先使用【make help】查看一下所有可用的编译参数: [root@study linux-3.10.89]# make vmlinux <==未金压缩的内核 [root@study linux-3.10.89]# make modules <==仅内核模块 [root@study linux-3.10.89]# make bzImage <==经压缩过的内核(默认) [root@study linux-3.10.89]# make all <==进行上面3个操作。 常见的/boot/下的内核文件,都是经过压缩过的。上面命令中常用的是modules与bzImage(第3个字母是大写的i)。bzImage可以制作出压缩过后的内核,就是用来进行系统启动的信息。基本操作是: [root@study linux-3.10.89]# make -j 4 clean <==先清除缓存文件 [root@study linux-3.10.89]# make -j 4 bzImage <==先编译内核 [root@study linux-3.10.89]# make -j 4 modules <==再编译模块 [root@study linux-3.10.89]# make -j 4 clean bzImage modules <==连续操作 上面操作花费的时间非常长。-j 4。4是CPU内核的意思。这几个内核可以同进行编译操作。根据自己的CPU内核加上可用的CPU数量。 制作出来的数据放置在/usr/src/kernels/linux-3.10.89/目录下。还没有放到系统的相关路径。编译过程中发生错误。可能是内核选项的设置选择不好。需要重新以make menuconfig再次检查一下相关设置。如果还是无法成功,或许将原本的内核数据内的.config文件,复制到内核原始文件目录下,然后再修改试一试。 make bzImage最终执行结果如下: Setup is 16752 bytes (padded to 16896 bytes). System is 4404 kB CRC 30310acf Kernel: arch/x86/boot/bzImage is ready (#1)
[root@study linux-3.10.89]# ll arch/x86/boot/bzImage -rw-r–r–. 1 root root 4526464 Oct 20 09:09 arch/x86/boot/bzImage 内核编译好了,放置在/usr/src/kernels/linux-3.10.89/arch/x86/boot/baImage。这个就是内核文件,(安装文件) 然后就是编译模块部分。make modules完毕后,才可以安装
实际安装模块 模块放置到/lib/modules/$(uname -r)目录,同一版本的模块反复编译,安装时会产生冲突。两个解决方法: 1、先将旧模块目录更名,然后安装内核模块到目标目录。 2、在make menuconfig时,那个General setup内的Local version修改成新的名称。 建议使用第二种方法,模块放置目录名称不同,可以避免目录同名问题。 如何安装模块到正确目录,使用make的功能就行: [root@study linux-3.10.89]# make modules_install [root@study linux-3.10.89]# ll /lib/modules/ drwxr-xr-x. 7 root root 4096 Sep 9 01:14 3.10.0-229.11.1.el7.x86_64 drwxr-xr-x. 7 root root 4096 May 4 17:56 3.10.0-229.el7.x86_64 drwxr-xr-x. 3 root root 4096 Oct 20 14:29 3.10.89vbird # 这就是刚刚安装好的内核模块! 最终在/lib/modules下建立起内核模块。 接下来就是安装内核。使用grub2
安装新内核与多重内核选项(grub) 内核文件在/usr/src/kernels/linux-3.10.89/arch/x86/boot/bzImage. 系统内核理论上都是放在/boot下,且为vmlinuz开头的文件。 一台主机可以做成多重系统引导。同时保留旧版的内核,并在主机上新增新版的内核。 grub2与grub1不一样,grub2不建议直接修改配置文件,而是让系统自动检测处理grub.cfg配置文件。 (处理内核文件的时候需要知道内核文件的命名规则) 1、移到内核到/boot且保留内核文件 保留旧内核的好处,新内核文件有问题时,可以使用旧内核启动系统。 内核文件命名规则:以vmlinuz开头,接内核版本的格式。 [root@study linux-3.10.89]# cp arch/x86/boot/bzImage /boot/vmlinuz-3.10.89vbird <==实际内核 [root@study linux-3.10.89]# cp .config /boot/config-3.10.89vbird <==建议配置文件也复制备份 [root@study linux-3.10.89]# chmod a+x /boot/vmlinuz-3.10.89vbird [root@study linux-3.10.89]# cp System.map /boot/System.map-3.10.89vbird [root@study linux-3.10.89]# gzip -c Module.symvers > /boot/symvers-3.10.89vbird.gz [root@study linux-3.10.89]# restorecon -Rv /boot 2、建立相对应的lnitial Ram Disk(initrd) 测试机使用的SATA磁盘,刚才STAT磁盘支持没有直接编译到内核,所以需要initramfs来加载。要搭配正确的内核版本 [root@study ~]# dracut -v /boot/initramfs-3.10.89vbird.img 3.10.89vbird 3、编辑启动选项(grub) 前面文件都存放妥当后,同时得根据你内核得版本处理文件名。接下来使用grub2-mkconfig处理grub2启动选项设置 [root@study ~]# grub2-mkconfig -o /boot/grub2/grub.cfg Generating grub configuration file … Found linux image: /boot/vmlinuz-3.10.89vbird # 应该要最早出现! Found initrd image: /boot/initramfs-3.10.89vbird.img …..(下面省略)….. 默认较新版本的内核会放在最前面,成为默认启动选项。 4、重新以新内核启动、测试、修改 上述操作成功后,重新启动并选择新内核启动系统,使用uname -a查看 [root@study ~]# uname -a Linux study.centos.vbird 3.10.89vbird #1 SMP Tue Oct 20 09:09:11 CST 2015 x86_64 x86_64 x86_64 GNU/Linux 内核版本与支持的硬件平台都没有问题。运行一段时间后系统很稳定的情况下,就可以将default值使用新内核来作为默认启动选项。
额外(单一)内核模块编译 内核支持的功能中,有直接编译进内核内部的,也有使用外挂模块的。外挂模块可以简单的理解成为驱动程序。根据内核模块的不同,分别放置在/lib/moduules/$(uname -r)/kernel/目录中。各个硬件驱动程序则放置在/lib/modules/$(uname -r)/kernnel/drivers中。假设自己编译的内核中,有些驱动程序忘记编译成模块了,是否需要重新进行上述的操作。或者我想要使用硬件厂商发布的新驱动程序。如何操作 1、编译前注意事项 内核原本就提供了很多内核工具给硬件开发商使用,硬件开发商也需要针对内核所提供的功能来设计他们的驱动程序模块。如果想要自行使用硬件开发商所提供的模块进行编译时,需要用到内核提供的原始文件中的头文件(header include file)来获取驱动模块需要的一些函数库或头文件的定义。 要自行编译内核模块,得有内核源代码。内核源代码可能放置在/usr/src/下。(早期内核源代码要求一定放置在/usr/src/Linux/目录下)。 在2.6版本以后,以/lib/moddules/$(uname -r)/build及/lib/moduules/$(uname -r)/source两个链接文件指向正确的内核源代码放置目录。(以刚刚由kernel 3.10.89vbird建立的内核模块举例。看看内核模块目录下有些什么) [root@study ~]# ll -h /lib/modules/3.10.89vbird/ lrwxrwxrwx. 1 root root 30 Oct 20 14:27 build -> /usr/src/kernels/linux-3.10.89 drwxr-xr-x. 11 root root 4.0K Oct 20 14:29 kernel -rw-r–r–. 1 root root 668K Oct 20 14:29 modules.alias -rw-r–r–. 1 root root 649K Oct 20 14:29 modules.alias.bin -rw-r–r–. 1 root root 5.8K Oct 20 14:27 modules.builtin -rw-r–r–. 1 root root 7.5K Oct 20 14:29 modules.builtin.bin -rw-r–r–. 1 root root 208K Oct 20 14:29 modules.dep -rw-r–r–. 1 root root 301K Oct 20 14:29 modules.dep.bin -rw-r–r–. 1 root root 316 Oct 20 14:29 modules.devname -rw-r–r–. 1 root root 81K Oct 20 14:27 modules.order -rw-r–r–. 1 root root 131 Oct 20 14:29 modules.softdep -rw-r–r–. 1 root root 269K Oct 20 14:29 modules.symbols -rw-r–r–. 1 root root 339K Oct 20 14:29 modules.symbols.bin lrwxrwxrwx. 1 root root 30 Oct 20 14:27 source -> /usr/src/kernels/linux-3.10.89 除了两个链接文件,modules.dep文件记录了内核模块依赖属性的地方。根据该文件可以使用modprobe命令加载模块。头文件则放置在/usr/src/kernels/linux-3.10.89/include/目录。就是由build/source两个链接文件来获取目录所在路径 内核模块编译和内核源代码有点关系,编译时除了make、gcc等主要编译软件工具,还需要kernel-devel软件。 要在默认的内核下新增模块,要找到内核的SRPM文件,然后安装、获取源代码后,才能进行编译。
2、单一模块编译 假设两种情况 。默认内核忘记加入某个功能,且该功能可以编译成模块。默认内核没有将该功能编译成模块,导致不能使用。 。Linux内核源代码没有某个硬件的驱动程序(module),硬件开发商提供了Linux使用的驱动源代码。 其实解决方法也很简单,就是【获取源代码后,重新编译成为系统可以加载的模块】。上面两种情况编译操作还有一点不一样。但是都需要make、gcc以及内核提供的include头文件与函数库等。
- 硬件开发商提供的额外模块 硬件开发商提供了驱动程序,直接下载源代码,重新编译,将它放置到内核模块该放置的位子旧可以使用了。
示例:使用了磁盘阵列卡(RAID),内核不支持。要针对该磁盘阵列卡来编译成模块。使用官网提供的驱动程序编译
1、下载磁盘阵列卡的驱动程序:http://www.highpoint-tech.com/USA_new/series_rr600-download.htm
可以选择【RHEL/CentOS 7 x86-64】这个已经编译的版本来处理,因为示例中的内核已经自定义了版本。会
导致该版本的自动安装脚本失效。所以重新编译。先下载【Open Source Driver】版本。假设下载的文件已经
放置在/root/raidcard目录。
# 1. 将文件解压缩并且开始编译:
[root@study ~]# cd /root/raidcard
[root@study raidcard]# ll
-rw-r–r–. 1 root root 501477 Apr 23 07:42 RR64xl_Linux_Src_v1.3.9_15_03_07.tar.gz
[root@study raidcard]# tar -zxvf RR64xl_Linux_Src_v1.3.9_15_03_07.tar.gz
[root@study raidcard]# cd rr64xl-linux-src-v1.3.9/product/rr64xl/linux/
[root@study linux]# ll
-rw-r–r–. 1 dmtsai dmtsai 1043 Mar 7 2015 config.c
-rwxr-xr-x. 1 dmtsai dmtsai 395 Dec 27 2013 Makefile # 要有这个文件才行!
[root@study linux]# make
make[1]: Entering directory `/usr/src/kernels/linux-3.10.89’
CC [M] /root/raidcard/rr64xl-linux-src-v1.3.9/product/rr64xl/linux/.build/os_linux.o
CC [M] /root/raidcard/rr64xl-linux-src-v1.3.9/product/rr64xl/linux/.build/osm_linux.o
…..(中间省略)…..
LD [M] /root/raidcard/rr64xl-linux-src-v1.3.9/product/rr64xl/linux/.build/rr640l.ko
make[1]: Leaving directory `/usr/src/kernels/linux-3.10.89’
[root@study linux]# ll
-rw-r–r–. 1 dmtsai dmtsai 1043 Mar 7 2015 config.c
-rwxr-xr-x. 1 dmtsai dmtsai 395 Dec 27 2013 Makefile
-rw-r–r–. 1 root root 1399896 Oct 21 00:59 rr640l.ko # 就是产生这个文件!
# 2. 将模块放置到正确目录!
[root@study linux]# cp rr640l.ko /lib/modules/3.10.89vbird/kernel/drivers/scsi/
[root@study linux]# depmod -a #产生模块依赖性文件!
[root@study linux]# grep rr640 /lib/modules/3.10.89vbird/modules.dep
kernel/drivers/scsi/rr640l.ko: # 确认模块在依赖性的配置文件中!
[root@study linux]# modprobe rr640l
modprobe: ERROR: could not insert ‘rr640l’: No such device
# 测试加载,实际上虚拟机没有启动 RAID card,出现错误时正常的
# 3. 启动过程就加载此模块,则需要将模块放入 initramfs 才行!
[root@study linux]# dracut –force -v –add-drivers rr640l \
> /boot/initramfs-3.10.89vbird.img 3.10.89vbird
[root@study linux]# lsinitrd /boot/initramfs-3.10.89vbird.img | grep rr640 这样操作可以将内核模块编译起来,然后直接放置到内核模块的目录,同时用depmod将模块建立相关性。未来就 可以利用modprobe来使用。(自行编译模块时,若内核有更新,必须要重新编译该模块一次。重复上面的步骤) 因为这个模块仅时针对当前的内核来编译的
- 利用旧有的内核源代码进行编译 假设忘记加入某个模块功能,仅是重新编译模块就会非常简单。首先到当前内核源代码所在目录执行make menuconfig.然后将NTFS的选项设置为模块之后之直接执行:
make fs/ntfs/
NTFS的模块(ntfs.ko)就会自动被编译出来。然后将该模块复制到/lib/modules/3.10.89vbird/kernel/ntsf/目录,再执行一次depmod -a,就可以在原来的内核下面新增某个想要的模块功能。
内核模块管理 内核与内核模块是分不开的。至于驱动模块在编译的时候,更与内核的源代码功能分不开。 必须要知道:内核、内核模块、驱动程序模块、内核源代码与头文件的相关性。 内核模块相关的命令经常使用的是modprobe。启动时读取的模块定义文件/etc/modprobe.conf
以最新的内核版本编译CentOS 7.x的内核 有时候需要最新的4.x.y的内核版本来实践某些特定的功能,只能使用最新的内核版本来编译。可以按照上面的程序一个一个处理。也可以根据ELRepo网站提供的SRPM来重新编译打包。也可以直接使用ELRepo提供的CentOS 7.x专属内核来直接安装。 示例:使用ELRepo网站提供的SRPM文件来实践内核编译。从新编译的原因是需要将VFIO的VGA支持支持的内核功能打开。整个过程类似这样: 1、先从ELRepo网站下载不含源代码的SRPM文件,并且安装该文件 2、从www.kernel.org网站下载满足ELRepo网站所需要的内核版本 3、修改内核功能 4、通过SRPM的rpmbuild重新编译打包内核。 下面测试一下:(选择ELRepo最新的SRPM文件。)
1. 先下载 ELRepo 上面的 SRPM 文件!同时安装它: [root@study ~]# wget http://elrepo.org/linux/kernel/el7/SRPMS/kernel-ml-4.2.3-1.el7.elrepo.nosrc.rpm [root@study ~]# rpm -ivh kernel-ml-4.2.3-1.el7.elrepo.nosrc.rpm
2. 根据上述的文件,下载正确的内核源代码: [root@study ~]# cd rpmbuild/SOURCES [root@study SOURCES]# wget https://cdn.kernel.org/pub/linux/kernel/v4.x/linux-4.2.3.tar.xz [root@study SOURCES]# ll -tr …..(前面省略)….. -rw-r–r–. 1 root root 85523884 Oct 3 19:58 linux-4.2.3.tar.xz # 内核源代码 -rw-rw-r–. 1 root root 294 Oct 3 22:04 cpupower.service -rw-rw-r–. 1 root root 150 Oct 3 22:04 cpupower.config -rw-rw-r–. 1 root root 162752 Oct 3 22:04 config-4.2.3-x86_64 # 主要内核功能
3. 修改内核功能设置: [root@study SOURCES]# vim config-4.2.3-x86_64 # 大约在 5623 行找到下面这一行,并在下面新增一行设置值! # CONFIG_VFIO_PCI_VGA is not set CONFIG_VFIO_PCI_VGA=y
[root@study SOURCES]# cd ../SPECS [root@study SPECS]# vim kernel-ml-4.2.spec # 大概在 145 行左右找到下面这一行: Source0: ftp://ftp.kernel.org/pub/linux/kernel/v4.x/linux-%{LKAver}.tar.xz # 将它改成如下: Source0: linux-%{LKAver}.tar.xz
4. 开始编译并打包: [root@study SPECS]# rpmbuild -bb kernel-ml-4.2.spec # 接下来会有很长的一段时间!耐心等候。 Wrote: /root/rpmbuild/RPMS/x86_64/kernel-ml-4.2.3-1.el7.centos.x86_64.rpm Wrote: /root/rpmbuild/RPMS/x86_64/kernel-ml-devel-4.2.3-1.el7.centos.x86_64.rpm Wrote: /root/rpmbuild/RPMS/x86_64/kernel-ml-headers-4.2.3-1.el7.centos.x86_64.rpm Wrote: /root/rpmbuild/RPMS/x86_64/perf-4.2.3-1.el7.centos.x86_64.rpm Wrote: /root/rpmbuild/RPMS/x86_64/python-perf-4.2.3-1.el7.centos.x86_64.rpm Wrote: /root/rpmbuild/RPMS/x86_64/kernel-ml-tools-4.2.3-1.el7.centos.x86_64.rpm Wrote: /root/rpmbuild/RPMS/x86_64/kernel-ml-tools-libs-4.2.3-1.el7.centos.x86_64.rpm Wrote: /root/rpmbuild/RPMS/x86_64/kernel-ml-tools-libs-devel-4.2.3-1.el7.centos.x86_64.rpm 最后又一个kernel-ml的软件包产生。接下来不需要像手动安装内核一样,得一个一个文件得移动到正确得目录。 只要使用yum install 新得内核版本。这样新内核就在CentOS 7.x中了 [root@study ~]# yum install /root/rpmbuild/RPMS/x86_64/kernel-ml-4.2.3-1.el7.centos.x86_64.rpm [root@study ~]# reboot
[root@study ~]# uname -a Linux study.centos.vbird 4.2.3-1.el7.centos.x86_64 #1 SMP Wed Oct 21 02:31:18 CST 2015 x86_64 x86_64 x86_64 GNU/Linux