默認的樹莓派鏡像Raspbian啓動的是Linux的32位4.19內核,但是筆者想將其替換成5.4.y版本的64位內核。當然也可以直接在樹莓派上編譯,不過這樣速度比較慢,所以還是選擇在Ubuntu18.04上交叉編譯。
1)首先,要安裝基本的依賴庫:
sudo apt install git bc bison flex libssl-dev make libc6-dev libncurses5-dev
2)然後,可以去官網下載最新的Raspbian內核:
git clone --depth=1 --branch rpi-5.4.y https://github.com/raspberrypi/linux
加上--depth=1參數使得只會下載最新的一次commit,能加快速度,但是後面更新代碼有點麻煩,如果網速夠快且磁盤空間夠大可以去掉。
3)由於是交叉編譯(在X86_64環境下編譯Arm64),所以需要下載Linaro編譯工具,並配置編譯環境。
可以通過wget下載:
wget https://releases.linaro.org/components/toolchain/binaries/latest-7/aarch64-linux-gnu/gcc-linaro-7.5.0-2019.12-x86_64_aarch64-linux-gnu.tar.xz
下載完成後,將文件解壓縮到制定目錄,並配置好環境變量:
tar -xvf gcc-linaro-7.5.0-2019.12-x86_64_aarch64-linux-gnu.tar.xz
mv ./gcc-linaro-7.5.0-2019.12-x86_64_aarch64-linux-gnu ~/gcc-linaro
vim ~/.bashrc
在.bashrc後面加上:
export PATH=$PATH:~/gcc-linaro/bin
然後執行:
source ~/.bashrc
4)下面就可以進入內核目錄編譯了:
cd linux
make ARCH=arm64 CROSS_COMPILE=aarch64-linux-gnu- bcm2711_defconfig
上面命令用於生成默認的內核配置文件。完成上面步驟後,使用下面命令正式啓動編譯過程:
make -j8 ARCH=arm64 CROSS_COMPILE=aarch64-linux-gnu-
整個編譯時間可能會比較長,根據編譯機器的硬件處理器數量來制定同時使用多少線程編譯(-j{n},筆者同時使用8個任務)。
編譯完成後會在arch/arm64/boot目錄下生成Image文件和所有的dts文件。當然,還有一個重要的文件System.map生成在內核源碼根目錄下。
5)一切準備就緒,可以覆蓋SD卡上的內核文件了。
將SD卡插入計算機,會出現兩個分區(如果沒出現,可以自行掛載)。一個是fat32分區,名字叫boot;另一個是ext4分區,名字叫rootfs。
boot分區是啓動分區,內核鏡像和dts編譯後的dtb文件要放到這個分區上,同時還有一個config.txt配置文件。而rootfs分區是系統文件系統根目錄的分區,模塊文件要放到這個分區上。
先拷貝內核文件:
sudo cp linux/arch/arm64/boot/Image /media/roland/boot/kernel8.img
sudo cp linux/arch/arm64/boot/dts/broadcom/*.dtb /media/roland/boot/
sudo cp linux/arch/arm64/boot/dts/overlays/*.dtb* /media/roland/boot/overlays/
sudo cp linux/arch/arm64/boot/dts/overlays/README /media/roland/boot/overlays/
將編譯好的內核鏡像文件Image拷貝到boot分區下的kernel8.img,這一步應該會覆蓋掉原始的內核鏡像,如果不放心操作之前可以備份一下。當然也可以不用這個名字,只要在下一步配置文件裏面設置好就行了。後面的命令都是用來拷貝編譯好的設備描述文件。
下面還要生成內核模塊,這一步非常重要,否則啓動的時候會報找不到設備模塊。
sudo make ARCH=arm64 CROSS_COMPILE=aarch64-linux-gnu- INSTALL_MOD_PATH=/media/roland/rootfs modules_install
爲什麼這裏還要安裝模塊呢?硬件驅動有許許多多,如果把所有的驅動都在編譯內核的時候就指定編譯到內核裏面那麼內核會非常大。所以編譯內核的時候只編譯一部分非常常用的驅動,這些驅動在Linux內核配置的時候指定爲“*”。還有一些不怎麼常用的與平臺相關的驅動被指定爲“M”編譯,它們可以放到文件系統根分區下,等真正需要的時候再加載。對於這種驅動模塊,可以用make modules編譯。不過直接make,不加任何參數,就是make all,包含make modules。雖然編譯了,但並沒有被安裝到文件系統根分區下,內核啓動的時候還是找不到這些模塊。make modules_install就是起這個作用的,把模塊放到lib/modules目錄中一個和內核名一樣的目錄下,並且運行depmod生成模塊依賴關係文件,系統啓動時加載模塊就是從dep裏面讀取信息加載模塊。由於是交叉編譯,不是要將模塊安裝到本機,所以需要使用INSTALL_MOD_PATH參數,指定安裝的根目錄是SD卡的rootfs分區。
6)最後一步是修改配置文件。
樹莓派默認是用32位內核啓動,需要修改boot分區下的config.txt文件。在文件的末尾加上下面兩行:
arm_64bit=1
kernel=kernel8.img
arm_64bit指定樹莓派4是不是要以64位的方式啓動,如果不設置這項但又指定了64位的內核鏡像文件,會沒有任何顯示輸出。
kernel指定了內核鏡像文件的名字,只需要跟上一步拷貝的名字相同就可以了。
保存後卸載分區,將修改好後的SD卡插到樹莓派4中直接啓動即可。