如何在Linux虚拟机安装ARM编译器编译树莓派4B的ARM汇编代码
Linux虚拟机搭建RPi4B ARM交叉编译环境及汇编代码编译操作步骤
前置确认
先在已经跑通Raspbian的RPi4B上执行uname -m确认系统架构:
- 输出
armv7l:32位armhf架构,对应安装32位ARM交叉编译工具链 - 输出
aarch64:64位ARM64架构,对应安装64位ARM交叉编译工具链
注意:你参考的RPi3教程多基于32位系统编写,如果你当前RPi4B装的是64位Raspbian,汇编代码指令集、寄存器地址、编译参数都要对应调整,直接抄教程参数大概率编译/运行失败。
第一步:在Linux虚拟机安装对应交叉编译器
Ubuntu/Debian系虚拟机(通用桌面环境常用)
先更新软件源:
sudo apt update
- 适配32位Raspbian:
sudo apt install gcc-arm-linux-gnueabihf binutils-arm-linux-gnueabihf -y
- 适配64位Raspbian:
sudo apt install gcc-aarch64-linux-gnu binutils-aarch64-linux-gnu -y
Fedora/RHEL系虚拟机
- 适配32位Raspbian:
sudo dnf install arm-linux-gnueabihf-gcc arm-linux-gnueabihf-binutils -y
- 适配64位Raspbian:
sudo dnf install aarch64-linux-gnu-gcc aarch64-linux-gnu-binutils -y
安装完成后执行对应版本的工具命令验证,比如32位版本执行arm-linux-gnueabihf-as --version,能正常输出版本信息即为安装成功。
第二步:编译.s汇编文件
分两种使用场景对应不同编译流程,根据你的需求选即可:
场景1:编译Raspbian系统下可直接运行的用户态程序
不需要做裸机镜像,编译完把可执行文件传到RPi里就能跑:
- 汇编生成中间目标文件(以你的汇编文件名为
led_blink.s为例)- 32位工具链:
arm-linux-gnueabihf-as -o led_blink.o led_blink.s- 64位工具链:
aarch64-linux-gnu-as -o led_blink.o led_blink.s - 链接生成可执行文件
- 如果你的汇编代码调用了C库函数(比如sleep、printf),用gcc链接:
32位:arm-linux-gnueabihf-gcc -o led_blink led_blink.o
64位:aarch64-linux-gnu-gcc -o led_blink led_blink.o - 如果是纯Linux系统调用写的汇编,直接用ld链接即可:
32位:arm-linux-gnueabihf-ld -o led_blink led_blink.o
64位:aarch64-linux-gnu-ld -o led_blink led_blink.o
- 如果你的汇编代码调用了C库函数(比如sleep、printf),用gcc链接:
- 把生成的
led_blink文件通过scp/U盘/SD卡拷贝到RPi4B的Raspbian系统中,执行chmod +x led_blink加执行权限,因为操作GPIO需要root权限,执行sudo ./led_blink即可运行。
场景2:编译裸机程序(直接写入SD卡启动,不依赖Raspbian系统)
也就是你提到的全新SD卡写汇编程序直接驱动LED的场景,注意RPi4B的裸机程序加载起始地址为0x80000,和RPi3老教程常用的0x8000地址不兼容,直接抄会启动失败:
- 汇编生成目标文件的命令和场景1完全一致
- 新建链接脚本
link.ld,指定正确的加载地址:SECTIONS { . = 0x80000; .text : { *(.text) } .data : { *(.data) } .bss : { *(.bss) } } - 用链接脚本生成elf格式文件(32位为例):
arm-linux-gnueabihf-ld -T link.ld -o led_blink.elf led_blink.o - 提取可直接烧录的二进制镜像:
arm-linux-gnueabihf-objcopy -O binary led_blink.elf led_blink.img - 准备SD卡:将SD卡格式化为FAT32分区,放入RPi官方启动固件(bootcode.bin、start.elf、fixup.dat、config.txt,可从官方Raspbian镜像的boot分区直接拷贝,不要只放你自己编译的img,否则无法启动),将你生成的
led_blink.img重命名为kernel7.img(32位)/kernel8.img(64位)放入boot分区,插回RPi4B上电即可运行。
踩坑提示:RPi4B的GPIO外设寄存器基地址和RPi3不同,裸机开发时不要直接抄RPi3教程里的地址定义,否则LED不会有反应。
内容的提问来源于stack exchange,提问作者stoneww
相关产品推荐
相关产品推荐

