郵箱:pengdonglin137@163.com
概述
在嵌入式開發時,經常會通過編譯busybox來制作rootfs,然后在上面跑可執行程序。那么如何通過修改配置,讓一個rootfs同時兼容32位和64位的可執行程序呢?
我們知道,如果EL1運行在64位時,那么EL0既可以運行在64位,也可以運行在32位。具體到這里,我們讓內核運行在64位(EL1),然后在EL0運行64位或者32位的可執行程序,在加載32位的可執行程序時,會先陷入Linux內核(EL1),然后通過解析elf文件發現EL0要運行在32位模式,那么在eret異常返回到EL0時會通過SPSR將當前cpu切到32位模式運行。
正文
1、配置linux kernel
使kernel支持在EL0上運行32位可執行程序:(arch/arm64/Kconfig中)
config COMPAT bool "Kernel support for 32-bit EL0" depends on ARM64_4K_PAGES || EXPERT select COMPAT_BINFMT_ELF if BINFMT_ELF select HAVE_UID16 select OLD_SIGSUSPEND3 select COMPAT_OLD_SIGACTION help This option enables support for a 32-bit EL0 running under a 64-bit kernel at EL1. AArch32-specific components such as system calls, the user helper functions, VFP support and the ptrace interface are handled appropriately by the kernel. If you use a page size other than 4KB (i.e, 16KB or 64KB), please be aware that you will only be able to execute AArch32 binaries that were compiled with page size aligned segments. If you want to execute 32-bit userspace applications, say Y.
具體是在:Userspace binary formats --> Kernel support for 32-bit EL0
然后重新編譯內核
2、配置根文件系統
這一步需要視情況而定,如果32位的可執行程序采用的是靜態鏈接的,那么此時應該就可以直接運行。如果采用的是動態鏈接,那么就需要專門的設置了。
- 在rootfs的根目錄下創建/lib32目錄,然后將要用到的32位的動態庫拷貝到其中
- 設置LD_LIBRARY_PATH環境變量,將剛才的路徑添加到其中:export LD_LIBRARY_PATH=$LD_LIBRARY_PATH:/lib32
- 進入/lib目錄,在其中創建一個指向/lib32/ld-linux-armhf.so.3的軟連接:ld-linux-armhf.so.3
3、測試
- 運行32位可執行程序
在64位系統里運行一個32位的測試程序:
然后可以查看其虛擬內存地址分配
- 運行64位可執行程序
查看其地址分配:
完。