以下紀錄如何編譯 Raspberry Pi Kernel
查詢 RPi 上安裝的 kernel 版本號碼
$ uname -a
Linux raspberrypi 4.14.34-v7+ #1110 SMP Mon Apr 16 15:18:51 BST 2018 armv7l GNU/Linux
找一台 x86 linux 電腦,以 cross-compile 方式重新編譯 RPi kernel,雖然可以直接在 RPi 編譯,但速度會很慢,因此還是選擇用 cross-compile 方式編譯。
RPi kernel 存放在 git repository 裡面
cd
mkdir raspberry
cd raspberry
確認有安裝 git, 並更新一些套件(需要安裝nss 相關和更新curl)
yum update git
yum update nss nss-util nspr
yum update curl
下載 kernel source
git clone https://github.com/raspberrypi/linux.git
下載 cross-compilers tools
git clone https://github.com/raspberrypi/tools
使用 tools/arm-bcm2708/gcc-linaro-arm-linux-gnueabihf-raspbian
,設定環境變數 CCPREFIX
export CCPREFIX=/root/raspberry/tools/arm-bcm2708/gcc-linaro-arm-linux-gnueabihf-raspbian/bin/arm-linux-gnueabihf-
${CCPREFIX}gcc -v
在 GitHub 上面的 kernel 有許多不同的 branch,請選擇你想要使用的 branch 來使用。
cd linux
git branch -a
目前版本為
* rpi-4.14.y
remotes/origin/HEAD -> origin/rpi-4.14.y
由 RPi 取得目前的 kernel 設定,因為 RPi 上沒有 config.gz,用以下指令產生 /proc/config.gz
sudo modprobe configs
將 /proc/config.gz 複製到要編譯 kernel 的機器上的 /root/raspberry/linux 目錄中
cd /root/raspberry/linux
scp pi@192.168.1.15:/proc/config.gz .
gunzip -c config.gz > .config
用以下指令產生新的 kernel configuration,如果遇到新的功能,就會問你要不要支援
ARCH=arm CROSS_COMPILE=${CCPREFIX} make oldconfig
reset .config 裡面的 debug symbols,Enable the ‘DEBUGINFO’ option and don’t enable the DEBUGINFO_REDUCED option.
grep -v DEBUG_INFO < .config > newconfig
mv newconfig .config
ARCH=arm CROSS_COMPILE=${CCPREFIX} make oldconfig
以 menuconfig 微調設定,調整 kernel modules support。
make -j4 ARCH=arm CROSS_COMPILE=${CCPREFIX} menuconfig
編譯 kernel,如果是 multi-core cpu,可加上 -j<amount of cores>
加速編譯
ARCH=arm CROSS_COMPILE=${CCPREFIX} make
如果編譯過程中,有發生 compile error,打開錯誤的 source code,在發生錯誤的 function 前面加上
#pragma GCC optimize("-g0")
編譯完成後,必須檢查 symbols,用以下指令,查看 initutsns.name.release 的值
${CCPREFIX}gdb vmlinux
print init_uts_ns.name.release
確認 kernel 有包含 symbols 後,將 RPi 需要的 modules 放在 modules 目錄
ARCH=arm CROSS_COMPILE=${CCPREFIX} INSTALL_MOD_PATH=../modules make modules_install
建立 uncompressed kernel image,並放到 RPi 的 tmp 目錄中
cd <raspberry pi downloads>/tools/mkimage
./imagetool-uncompressed.py ../../linux/arch/arm/boot/zImage
scp kernel.img pi@raspberrypi:/tmp
將 modules 目錄,壓縮後,傳送到 RPi 的 tmp 目錄中
cd <raspberry pi downloads>/tools/modules
tar czf modules.tgz *
scp modules.tgz pi@raspberrypi:/tmp
最後 ssh 到 RPi,安裝新的 kernel 及 modules
cd /
sudo mv /tmp/kernel.img /boot/
sudo tar xzf /tmp/modules.tgz
rm /tmp/modules.tgz
reboot RPi
sudo shutdown -r now
以 uname 檢查是否使用了新版的 kernel
uname -r
如果要 debug kernel ,可參考 Preparing Raspberry PI for JTAG Debugging 的說明
References
https://sysprogs.com/VisualKernel/tutorials/raspberry/buildkernel/
https://blog.gtwang.org/iot/raspberry-pi-compile-linux-kernel/
https://www.raspberrypi.com.tw/528/compiling-kernel-for-raspberry-pi/
沒有留言:
張貼留言