定製linux和linux核心編譯
自制linux系統
分割槽並建立檔案系統
- 可以用u盤或者硬碟來安裝製作一個精簡版linux
- 將要安裝linux的u盤或裝置分割槽
fdisk /dev/sdb
分兩個必要的分割槽
/dev/sdb1對應/boot /dev/sdb2對應根 /
mkfs.ext4 /dev/sdb1
掛載boot
- mkdir /mnt/boot 子目錄必須為boot
- mount /dev/sdb1 /mnt/boot
安裝grub
grub-install --root-directory=/mnt /dev/sdb
恢復核心和initramfs檔案
cp /boot/vmlinuz-2.6 .32-642.el6.x86_64 /mnt/boot/
cp /boot/initramfs-2.6.32-642.el6.x86_64.img /mnt/boot
- 裝核心檔案時可以用rpm 安裝要指定root在哪
rpm -ivh /mnt/cd1/Packages/kernel-2.6.32-696.el6.x86_64.rpm --root=/mnt
- 這樣裝不只是裝庫檔案和initramfs檔案了,還會把/lib/modules驅動模組檔案裝上所所以我們直接複製主機上的
建立grub.conf
vim /mnt/boot/grub.conf
title wanglinux
root (hd0,0 )
kernel /vmlinuz-2.6.32-642.el6.x86_64 root=/dev/sda2 selinux=0 init=/bin/bash //因為沒有init程序,所以我們指定bash程序為init
initrd /initramfs-2.6.32-642.el6.x86_64.img
- chroot /mnt/sysroot 切根進入剛剛建立的linux系統。
建立一級目錄
mkdir /mnt/sysroot mount /dev/sdb2 /mnt/sysroot mkdir –pv /mnt/sysroot/{etc,lib,lib64,bin,sbin,tmp,var,usr,sys,proc,opt,home,root,boot,dev,mnt,media}
複製bash和相關庫檔案
- 使用指令碼檔案,用此指令碼將命令複製指定目錄
#!/bin/bash
cpTopath=/app
findcmd(){
filePathe=`which $1`
fileDir=$cpTopath`dirname $filePath`
if [ ! -d "$fileDir" ];then
mkdir -p $fileDir
cp -a $filePath $fileDir
else
cp -a $filePath $fileDir
fi
}
findlib() {
libPath=`which $1`
libDir=$cpToPath/lib64
if [ ! -d "$libDir" ] ; then
mkdir -p $libDir
fi
for i in `ldd $libPath |grep -Eo "/lib64/.*\.so.[0-9]\b"`;do
cp -a $i $libDir
cp -a `ls -l $i | sed -nr 's#.* -> (.*)$#/lib64/\1#p'` $libDir &>/dev/null
done
}
testCmd() {
type $1 $>/dev/null
if [ "$?" -eq 0 ]; then
cmdType=`type $1`
if [[ "$cmdType" =~ ^.*builtin$ ]];then
echo "$cmdType,No need to copy!"
continue
fi
else
echo -e "\033[31;5m\tInput error!\033[0m" && echo_prompt
continue
fi
}
echo_prompt() {
echo -e "\t====================================================="
echo
echo -e "\t\033[31m(1)input need to copy command.(like:ls,ip)"
echo -e "\t(2)if your need to quit ,input:quit \033[0m"
echo
echo -e "\t======================================================"
}
echo_prompt
while true ;do
read -p "please input command :" cmd
if [ "$cmd" == quit ] ;then
break
else
testCmd $cmd
findcmd $cmd
findlib $cmd
fi
done
複製相關命令及相關庫檔案
- 如:ifconfig,insmod,ping,mount,ls,cat等
核心編譯
- 單核心體系設計、但充分借鑑了微核心設計體系的優點,為核心引入模組化機制
- 一般不推薦編譯安裝,除非有特種需求,因為編譯安裝無法知道核心是否穩定
- 核心組成部分:
- kernel: 核心核心,一般為bzImage,通常在/boot目錄下,名稱為vmlinuz-VERSION-RELEASE
- kernel object: 核心物件,一般放置於/lib/modules/VERSION-RELEASE/
- [ ]: N 不要此功能
- [M]: M 表示生成/lib/moudules/版本號/這個目錄裡
- [*]: Y 表示生成vmlinuz-version-release這個檔案裡
- 輔助檔案:ramdisk
- initrd
- initramfs
核心版本
uname命令:
uname - print system information
uname [OPTION]…
-n: 顯示主機名稱
-r: 顯示VERSION-RELEASE
-a:顯示所有資訊
核心模組命令
lsmod命令:
顯示由核心已經裝載的核心模組
顯示的內容來自於: /proc/modules檔案
- 模組是有依賴性的,可以被多個模組使用
modinfo命令:
顯示模組的詳細描述資訊
modinfo [ -k kernel ] [ modulename|filename… ]
-n: 只顯示模組檔案路徑
-p: 顯示模組引數
-a: author
-d: description
-l: license
lsmod |grep xfs;modinfo xfs
核心模組管理
modprobe命令: 裝載或解除安裝核心模組 rmmod 模組名
modprobe [ -C config-file ] [ modulename ] [ moduleparame-ters… ]
- 配置檔案:/etc/modprobe.conf,/etc/modprobe.d/*.conf
- modprobe [ -r ] modulename…
depmod命令
核心模組依賴關係檔案及系統資訊對映檔案的生成工具裝載或解除安裝核心模組
insmod命令:指定模組檔案,不自動解決依賴模組,這個命令要寫模組路徑
insmod [ filename ] [ module options… ]
insmodmodinfo –n exportfs
//可以用modinfo -n 模組,調出模組路徑
lnsmodmodinfo –n xfs
rmmod命令:解除安裝模組
rmmod [ modulename ]
rmmod xfs
rmmod exportfs
編譯核心
- 前提
- 準備好開發環境
- 獲取目標主機上硬體裝置的相關資訊
- 獲取目標主機系統功能的相關資訊
- 例如:需要啟用相應的檔案系統
- 獲取核心原始碼包
- www.kernel.org
開發環境準備
- 包組(CentOS 6)
Server Platform Development
Development Tools
- 目標主機硬體裝置相關資訊
CPU:
cat /proc/cpuinfo
x86info -a /預設是沒有安裝的,安裝包是x86info
lscpu
硬體裝置
- lspci
- -v 顯示詳細內容
- -vv 顯示更詳細內容
- lsusb
- -v
- -vv
- lsblk 塊裝置
瞭解全部硬體裝置資訊
hal-device:在CentOS6中可以看
- ntfs分割槽在linux系統中無法識別,也無法掛載,當然可以安裝NTFS驅動模組就可以支援
- 在boot分割槽中這個檔案存放那個些模組在核心中哪些在/lib/modules
- 這裡y整合在核心核心裡,就是boot下vmlinuz中
- m是以模組方式來存在的
- 還有一種no set 表示不啟用此功能
核心編譯安裝系統
- 安裝開發包組
- 下載原始碼檔案並解包
[[email protected] app]# tar xvf linux-4.14.12.tar.xz
[[email protected] app]# du -sh linux-4.14.12/
882M linux-4.14.12/
- 因為這裡功能模組太多,我們要實現讓linux支援ntfs檔案系統,所有把/boot/config-3.10.0.697.el7.x86_64 這個檔案複製到剛剛解壓縮的linux目錄中,並命名為.config把這個當模板,我們在這之上加上ntfs,這個檔案是編譯時選擇啟用或禁用那些功能的模板
- .config:準備文字配置檔案
- make menuconfig:配置核心選項
- make [-j #]
- make modules_install:安裝模組
- make install :安裝核心相關檔案
- 安裝bzImage為/boot/vmlinuz-VERSION-RELEASE
- 生成initramfs檔案
- 編輯grub的配置檔案
編譯安裝核心示例
- tar xf linux-3.10.67.tar.xz -C /usr/src
- cd /usr/src
- ln -sv linux-3.10.67 linux
- cd /usr/src/linux
- cp /boot/config-$(uname -r) ./.config
- make help
- make menuconfig
- make -j 2
- make modules_install
- make install
- reboot
編譯核心
- 配置核心選項
- 支援“更新”模式進行配置:make help
- make config:基於命令列以遍歷的方式去配置核心中可配置的每個選項
- make menuconfig:基於curses的文字視窗介面
- make gconfig:基於GTK (GNOME)環境視窗介面
- make xconfig:基於QT(KDE)環境的視窗介面支援“全新配置”模式進行配置
- make defconfig:基於核心為目標平臺提供的“預設”配置進行配置
- make allyesconfig: 所有選項均回答為“yes“
- make allnoconfig: 所有選項均回答為”no“
- 編譯
- 全編譯:make [-j #]
- 編譯核心的一部分功能
- 只編譯某子目錄中的相關程式碼
bash
cd /usr/src/linux //就是進入解壓縮的目錄中
make dir/
- 只編譯一個特定的模組
bash
cd /usr/src/linux
make dir/file.ko
例如:只為e1000編譯驅動:
make drivers/net/ethernet/intel/e1000/e1000.ko
- 只編譯某子目錄中的相關程式碼
如何交叉編譯核心
- 編譯的目標平臺與當前平臺不相同
- make ARCH=arch_name
- 要獲取特定目標平臺的使用幫助
- make ARCH=arch_name help
- make ARCH=arm help
在已經執行過編譯操作的核心原始碼樹做重新編譯
- 需要事先清理操作
- make clean:清理大多數編譯生成的檔案,但會保留config檔案等
- make mrproper: 清理所有編譯生成的檔案、config及某些備份檔案
- make distclean:mrproper、patches以及編輯器備份檔案
解除安裝核心
- 刪除/lib/modules/目錄下不需要的核心庫檔案
- 刪除/usr/src/linux/目錄下不需要的核心原始碼
- 刪除/boot目錄下啟動的核心和核心映像檔案
- 更改grub的配置檔案,刪除不需要的核心啟動列表
- 刪除centos7時是grub2目錄,並且grub.conf改為grub.cfg檔案要刪除
- 相當於grub.conf中從title 到initrd的內容
- 如果grub2/grub.cfg檔案刪除了,可以用grub2-make -o grub.cfg 生成此檔案
編譯核心操作
- 選擇下載linux,kernel包,在選擇核心包時最最好不要相差2個大版本
- 下載原始碼檔案並解包
[[email protected] app]# tar xvf linux-4.14.12.tar.xz
[[email protected] app]# du -sh linux-4.14.12/
882M linux-4.14.12/
- 準備.config檔案,這個檔案定義了那些功能啟用或禁用,可以參考現有的linux系統中/boot/config-3.10.0-693.el7.x86_64 這個檔案
- 由於功能很多,所有直接用現有的config-3.10.0-693.el7.x86_64檔案,並且改名為.config
[[email protected] app]# cp /boot/config-3.10.0-693.el7.x86_64 /app/linux-4.14.12/.config
- 以選單的方式來定製功能,用make menuconfig,要進入解壓包裡
- 但是可能會包這樣的錯誤缺少一些包組,我們安裝
- 安裝對應的包組,先用yum grouplist 檢視一下
- 安裝包組
[[email protected] linux-4.14.12]# yum groupinstall Development\ Tools
- 我們在次進行開啟選單發現還是缺少包,根據提示安裝對應的包,這個包是一個字元介面的視窗庫
yum install -y ncurses-devel
- 這樣就不缺少包了
- 這是選單介面,後面有—> 這種的就是由子選單可以進去,先進入總的設定,按+或-是上下功能鍵
- 這個就是我們用uname -r 命令看到的最後幾位數字的設定
- 現在我們也新增一個自己的標識,按照對應的格式來寫
- 其它的設定不想改了,可以按exit返回上一級選單
- 在繼續設定其它的,因為我們想要linux支援ntfs格式的找檔案系統這一個選項
- 找到這一個選項,進去
- 按空格鍵可以選擇是否啟用或禁用,以及生成模組檔案,這裡選擇啟用成模組
- 啟用ntfs時會出來兩個選項,這裡我們一併也啟用,支援ntfs寫,這樣就完成了,退出儲存
- 剛剛選單操作就是更改.config檔案,相當於編譯安裝成中.configrue這一步
-
- 編譯
- -j是指定用幾個核心編譯,當然是根據電腦自身配置,核心越多編譯越快
- 因為編譯時間較長我們可以設定編譯完後打出響聲來提示我們,這樣我們就可以幹其它事情
[[email protected] linux-4.14.12]# make -j 4 ; for i in {1..10};do sleep 0.3;echo -e "\a" ;done
- 這裡還缺少一些庫檔案,我們直接安裝就好,這裡只有裝其中一個就行
linux 核心編譯時出現scripts/sign-file.c:23:30: fatal error: openssl/opensslv.h錯誤的解決辦法yum install openssl-devel
編譯安裝完後執行make modules_install 安裝模組
- 安裝前
[[email protected] linux-4.14.12]# ls /lib/modules
3.10.0-693.el7.x86_64
- 安裝後
[[email protected] linux-4.14.12]# make modules_install
[[email protected] linux-4.14.12]# ls /lib/modules
3.10.0-693.el7.x86_64 4.14.12-1.0-wawa
make install :安裝核心相關檔案
- 安裝bzImage為/boot/vmlinuz-VERSION-RELEASE
- 生成initramfs檔案
- 編輯grub的配置檔案
- 檢視一下grub2目錄中grub2.cfg檔案
- 完成後重啟機器然後用新核心啟動
[[email protected]1234 ~]# uname -r
4.14.12-1.0-wawa
測試
- 將u盤插進系統看是否識別
- 但是我們發生是隻讀模式,重新掛載一下變成讀寫的
[[email protected]1234 ~]# mount -o rw,remount /run/media/root/老毛桃u盤/
mount: cannot remount /dev/sdb1 read-write, is write-protected
- 發現無法變成只讀模式,如果想寫入,要安裝ntfs-3g 這個包,視訊epel源的