
micro:bit MicroPython 构建系统揭秘yotta、Makefile 与 HEX 固件、UICR 区域原理【免费下载链接】micropythonPort of MicroPython for the BBC micro:bit项目地址: https://gitcode.com/gh_mirrors/mic/micropython本项目是MicroPython 在 BBC micro:bit 上的官方移植你可以用它把 Python 直接跑在 nRF51822 芯片上。本文带你看懂它的构建系统全貌从 yotta 拉取依赖、Makefile 编排构建流程到最终生成firmware.hex并写入神秘的 UICR 区域——一篇讲透 micro:bit MicroPython 的固件构建原理。项目是什么Python 跑上 micro:bit micro:bit 是专为教育设计的微型电脑而本项目的目标就是让它运行真正的 Python 解释器 MicroPython。克隆仓库后核心内容分布如下目录作用source/与inc/C/C 源码包含解释器核心与 micro:bit 硬件驱动examples/可直接运行的 Python 示例程序tools/构建辅助脚本版本头、UICR 写入、HEX 合并等Makefile/module.json/config.json构建入口与 yotta 模块描述其中 module.json 声明了模块名microbit-micropython、版本号以及唯一的依赖项microbit-dalmicro:bit 的底层抽象层config.json 则指向自定义配置头文件inc/microbit/MicroBitCustomConfig.h。一键构建前的准备工作依赖与 yotta 目标配置构建需要 ARM 交叉编译工具链arm-none-eabi-gcc和 yotta 构建工具。在 Ubuntu 上可一条命令装好 gcc-arm-embedded、cmake、ninja、srecord再通过 pip 安装 yotta。准备好后只需三步就能启动构建指定构建目标yotta 官方注册表已弃用目标需从社区仓库获取yotta target bbc-microbit-classic-gcc-nosdhttps://github.com/lancaster-university/yotta-target-bbc-microbit-classic-gcc-nosd拉取远程依赖模块microbit-dal、mbed-classic、nrf51-sdk 等yotta up执行构建make all构建成功后可刷写的固件会出现在仓库根目录下的build/firmware.hex。Makefile 揭秘不只是“跑一下 yotta build”根目录的 Makefile 是整个构建的总调度它比单纯的yotta build多做了几件关键的事。理解它的关键是看这条依赖链firmware.hex ← yotta 构建 ← 版本头文件生成 ↑ adduicr.py 写入 UICR各目标的分工如下all最终目标产出build/firmware.hexqstrs调用 tools/makeqstrhdr.sh预处理全部 C/C 源码并提取MP_QSTR_xxx常量重新生成字符串常量表 inc/genhdr/qstrdefs.generated.h——当你往qstrdefsport.h里加新字符串时必须执行它$(MBIT_VER_FILE)每次构建前都强制运行 tools/makeversionhdr.py从 git 信息中提取 tag、短哈希和构建日期写入inc/genhdr/microbitversion.h$(VER_ADDR_FILE)yotta 编译完成后用arm-none-eabi-objdump在二进制里定位microbit_version_string符号的链接地址供下一步写入 UICR 使用deploy把firmware.hex自动拷贝到已挂载的 micro:bit U 盘里完成刷写serial以 115200 波特率打开 REPL 串口picocom /dev/ttyACM0。版本信息最终通过 source/microbit/modos.c 中的os.uname()暴露给 Python 代码你在 REPL 里随时能查到固件是哪个版本、哪次提交构建的。HEX 固件生成套娃式的数据分层 微控制器芯片如 nRF51822 所在的 micro:bit v2的 flash 布局是有讲究的。本项目的记忆布局可以想象成俄罗斯套娃固件在外脚本在内元数据藏在最特殊的角落。按 docs/devguide/hexformat.rst 的说明标准布局为地址内容大小上限0x00000000MicroPython 固件本体248 KB0x0003e000附加的启动脚本可选已逐步被文件系统方案取代8 KB0x100010c0UICR customer 寄存器区存放 MicroPython 元数据28 字节⚠️ 文档特别提醒如果手动修改 Intel HEX 文件数据地址必须保持递增顺序一旦地址回跳DAPLink 刷写器就会直接失败。除了 yotta 产出的裸固件 HEXmake all还会自动执行 tools/adduicr.py把 UICR 数据块追加进去输出最终的build/firmware.hex。如果你想把一个 Python 脚本烧进固件还可以用 tools/makecombinedhex.py 把main.py合并进 HEX生成开机即跑的完整固件。UICR 区域原理28 字节如何被读出 UICRUser Information Configuration Registers是 nRF 芯片上一块用户可用的非易失性存储区前 128 字节被保留后 128 字节可供任意数据使用。MicroPython 从0x100010c0起按小端序写入如下 28 字节结构偏移值含义0x000x17eeb07c魔数标识这是 MicroPython 固件0x040xffffffff保留0x080x0000000aflash 页大小1024 字节的 log2 值0x0a0x0000固件起始页0x0c页数固件占用的 flash 页数由 adduicr.py 自动计算0x100xffffffff保留0x14地址版本字符串在固件中的 flash 地址0x180x00000000保留妙就妙在0x14这个字段micro:bit 的 bootloader 读取 UICR校验魔数后跳转去读版本字符串从而判断 flash 里是官方固件还是 MicroPython——这正是 MicroPython 能和官方 SDK 固件共存切换的关键机制。而版本字符串的地址正是 Makefile 里arm-none-eabi-objdump那一步探测出来的。刷写与验证deploy 一步到位固件生成后micro:bit 会把自己挂载为名为MICROBIT的 U 盘。Makefile 提供了make deploy目标挂载设备、拷入 HEX、卸载micro:bit 检测到新固件后自动刷写并重启。重启后 USB 串口即出现 REPL115200输入import microbit然后microbit.display.scroll(hello!)看到 LED 矩阵滚动出字样说明构建链路完全打通 常见问题清单 编译报undefined MP_QSTR_xxx说明改了qstrdefsport.h却没重新生成字符串表执行make qstrs即可刷写失败 / 设备无反应检查 HEX 中数据地址是否严格递增UICR 段拼接到固件末尾时尤其注意固件超过 248 KBmakecombinedhex.py会主动报 “firmware overflows into script region”需要裁剪配置config.json指向的头文件释放空间。从make all一个命令背后到 yotta 拉取依赖、版本头生成、qstr 表重建、objdump 探地址、adduicr 写 UICR 的完整流水线——现在你已经掌握了 micro:bit MicroPython 构建系统的核心原理。动手构建一次是最好的学习方式【免费下载链接】micropythonPort of MicroPython for the BBC micro:bit项目地址: https://gitcode.com/gh_mirrors/mic/micropython创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考