树莓派4 Fedora IoT下无需sudo读写/dev/mem失败求助
解决BCM2835 SPI初始化失败(MAP_FAILED)的问题
核心原因分析
尽管你已加入mem、kmem组,且/dev/mem权限设为全开放,但Fedora IoT默认启用了内核级/dev/mem保护机制(CONFIG_STRICT_DEVMEM与CONFIG_IO_STRICT_DEVMEM),非特权进程无法直接映射外设寄存器所在的物理内存区域,这是mmap调用返回MAP_FAILED的根本原因。
分步解决方案
1. 临时禁用/dev/mem保护(测试验证用)
重启时在启动参数中添加devmem=1放宽限制:
- 编辑启动配置文件:
/boot/efi/extlinux/extlinux.conf - 在
append行末尾追加devmem=1,示例:append root=UUID=xxx ro quiet console=tty1 devmem=1 - 保存后重启系统,再运行代码测试。
2. 永久配置(生产环境推荐)
若临时方案有效,可通过以下步骤永久生效:
- 创建dracut配置文件:
/etc/dracut.conf.d/devmem.conf,写入:add_dracutmodules+=" kernel-modules " kernel_cmdline="devmem=1" - 重新生成initramfs:
sudo dracut -f - 重启系统完成配置。
3. 更稳妥的替代方案:使用标准SPI内核驱动
直接操作/dev/mem属于底层裸机操作,更推荐适配Linux标准SPI框架:
- 启用树莓派SPI接口:
sudo raspi-config nonint do_spi 0 - 将用户加入
spi组(若未加入):sudo usermod -aG spi pi - 修改代码,使用
/dev/spidev0.0(或对应SPI设备节点)替代BCM2835库的直接内存映射逻辑。
4. 基础验证(若坚持使用BCM2835库)
- 确认BCM2835库已适配树莓派4的外设基地址(RPi4外设基址为
0xFE000000,旧款为0x20000000),部分旧版本库可能需要手动指定。 - 检查代码中
mmap调用的参数,确保地址范围、权限位设置正确。
内容的提问来源于stack exchange,提问作者9me
相关产品推荐
相关产品推荐

