MicroPython v1.25
ROMFS ships after three years in development, plus a brand-new alif port and an inline RISC-V assembler.
Released April 16, 2025
ROMFS — Execute Bytecode in Place
ROMFS is a read-only, memory-mappable filesystem that lets MicroPython
execute precompiled .mpy bytecode directly from flash, without
copying it into RAM first. The result: faster imports and a lot less heap pressure.
Data resources like fonts can also be used in place. ROMFS builds on bytecode v6
(which has supported in-place execution for years).
The demo simulates a small import. In real MicroPython, bytecode v6 + ROMFS lets the VM execute opcodes directly from a memory-mapped flash region; only the per-call frame needs to live in RAM. Imports of large modules become noticeably faster.
Building & deploying ROMFS — mpremote
# 1. Build a ROMFS image from a directory tree of .py / .mpy / data files $ mpremote romfs build romfs.bin --src ./assets Built ROMFS image: 32 kB # 2. Deploy it to the /rom partition on the target device $ mpremote romfs deploy romfs.bin Deployed to /rom # 3. Imports now resolve transparently from /rom $ mpremote run app.py
Where ROMFS is enabled by default in v1.25
Other boards can opt in with manual configuration. The list will grow in subsequent releases.
alif — Multi-core ARM with ML Accelerators
A new port targeting Alif Semiconductor's Ensemble family. These MCUs
pair multiple ARM cores with Ethos-U55 machine-learning accelerators
and a generous peripheral set. v1.25 brings up the platform with TinyUSB,
OpenAMP-based dual-core support, octal-SPI flash with XIP, and the
machine classes plus cyw43 WiFi+BLE.
Alif Ensemble
Multi-core ARM
Targeted at battery-powered ML inference at the edge. v1.25 supports
Pin, UART, SPI, I2C, USB via
TinyUSB, and dual-core orchestration via OpenAMP. cyw43 WiFi and BLE work on
boards that include the radio module.
What's running where
Dual-core via OpenAMP- Cortex-M55 (HE) — high-performance core where MicroPython executes by default.
- Cortex-M0+ (LP) — low-power core; OpenAMP makes it addressable from MicroPython.
- Ethos-U55 NPU — per-core neural-network accelerator; not yet exposed at the Python layer in v1.25.
- OPENMV_AE3 targets OpenMV's upcoming AE3 camera board — the ML angle is the headline use case.
@micropython.asm_rv32 — Inline RISC-V 32-bit assembly
MicroPython's inline-assembler family gains RV32. Write small snippets of 32-bit RISC-V machine code as Python functions. Currently enabled on the rp2 port when the RP2350 is in RISC-V mode.
@micropython.viper def add_squared(a: int, b: int) -> int: return a*a + b*b
@micropython.asm_rv32 def add_squared(a0, a1) -> int: # a0 *= a0 ; a0 = a*a mul(a0, a0, a0) # a1 *= a1 ; a1 = b*b mul(a1, a1, a1) # a0 += a1 ; return a*a + b*b add(a0, a0, a1)
asm_rv32 decorator is enabled on rp2 when targeting
RP2350 in RISC-V mode (Hazard3 cores). The same release also extends the native
emitter and mpy_ld.py linker to support 32-bit RISC-V code generation
and static-library linking, so native modules can be built for RV32 targets.
DTLS — Datagram TLS
The tls module gains PROTOCOL_DTLS_CLIENT and
PROTOCOL_DTLS_SERVER modes. Wrap a UDP socket in a DTLS context
and you have an authenticated, encrypted datagram channel — useful for
CoAP-secure, low-latency telemetry, and constrained-network protocols where
TCP is the wrong tool.
import tls, socket ctx = tls.SSLContext(tls.PROTOCOL_TLS_CLIENT) ctx.load_verify_locations(cadata=ca) s = socket.socket(socket.AF_INET, socket.SOCK_STREAM) s.connect(("example.com", 443)) ss = ctx.wrap_socket(s, server_hostname="example.com") ss.send(b"GET / HTTP/1.0\r\n\r\n")
import tls, socket ctx = tls.SSLContext(tls.PROTOCOL_DTLS_CLIENT) ctx.load_verify_locations(cadata=ca) s = socket.socket(socket.AF_INET, socket.SOCK_DGRAM) s.connect(("sensor.example", 5684)) ss = ctx.wrap_socket(s, server_hostname="sensor.example") ss.send(b"telemetry payload")
DTLS Port Support
Python language tweaks
Five small core-language additions in v1.25. Pick one from the dropdown to load the example into the editor, then run it live.
marshal module with dumps() /
loads() for code objects — combined with function.__code__
that gives you function serialisation. The MicroPython release tag explicitly notes:
"This module is not enabled by default but can be used in custom build
configurations." The PyScript variant of MicroPython runs at the
FULL_FEATURES ROM level, which doesn't include marshal —
so we can't demo it here. Try it on a desktop unix build with
MICROPY_PY_MARSHAL=1.
Highlights
Other notable improvements in v1.25.
mpremote rm -r
Recursive remove on the target device. mpremote rm -rv : wipes the
current working directory.
mip install from local FS
Install a package from a local directory or relative URL via
package.json. Useful for offline / air-gapped setups.
Default I2C / SPI / UART buses
On samd, mimxrt, rp2 and others, the bus-id argument is now optional —
cross-port code can drop the explicit id.
esp32 dynamic USB devices
USB device configuration at runtime on ESP32-S2 / S3, plus IDF v5.3 / v5.4 support (sub-5.2.0 dropped). I2S enabled on all C3 boards.
RP2350 PSRAM autodetection
RP2350 boards with PSRAM auto-size on boot. rp2.bootsel_button()
and USB-during-sleep both work on RP2350.
WPA3 on cyw43 boards
Pico W, Pico 2 W and stm32 cyw43-driver boards now support WPA3 in both AP and STA modes.
stm32 deinit on soft-reset — breaking
I2C and SPI buses are now deinitialised on soft-reset. Always re-initialise instances when creating them.
littlefs corruption recovery
stm32 boots no longer hard-fault on corrupt filesystems. Falls back to default block parameters, then prints a message and continues.
zephyr Timer + WDT
The zephyr port gains machine.Timer and machine.WDT
implementations, narrowing the cross-port API gap.
mimxrt UF2 + exFAT + PPP
UF2 bootloader support for easier firmware deployment, exFAT filesystem, and PPP driver for boards with lwIP networking.
RV32 native modules
mpy_ld.py now supports 32-bit RISC-V code, plus automatic linking
of static libraries (libgcc, libm) so native modules
can use standard C functions like exp().
mboot version string
stm32 mboot embeds a version at the end of its flash slot;
fwupdate.get_mboot_version() retrieves it.
New Boards
19 new board definitions, dominated by RP2350-class rp2 boards and the brand-new alif port.
alif
mimxrt
rp2
samd
stm32
By the Numbers
v1.25 in numbers. unix and mimxrt take big code-size hits from VfsRom + exFAT; rp2 grows for DTLS + cyw43-driver 1.1.0.