Skip to main content
Pre-release

This release is a pre-release and may not be stable for production use.

rp2040py

license pypi version python versions Pre-commit Test MicroPython Releases Test Pi Pico SDK coverage

Raspberry Pi Pico (RP2040) Emulator in Python — a faithful port of rp2040js. It blinks, runs native code, and even the MicroPython REPL!

See docs/PORTING.md for the file-by-file port status against upstream rp2040js.

Run the demo project

Native code

You'd need to get hello_uart.hex by building it from the pico-examples repo, then copy it to the rp2040py root directory and run:

uv run python demo/emulator_run.py

You can also specify the path to the image on the command line and/or load a UF2 image:

uv run python demo/emulator_run.py --image ./my-pico-project.uf2

A GDB server will be available on port 3333, and the data written to UART0 will be printed to the console.

MicroPython code

To run the MicroPython demo, first download RPI_PICO-20230426-v1.20.0.uf2, place it in the rp2040py root directory, then run:

uv run python demo/micropython_run.py

and enjoy the MicroPython REPL! Quit the REPL with Ctrl+X. A different MicroPython UF2 image can be loaded by supplying the --image option:

[!TIP] Booting real firmware means executing millions of Thumb instructions through a pure-Python interpreter, which is dramatically slower than V8 JIT-compiling the equivalent JS in rp2040js. Measured with demo/benchmark.py booting MicroPython 1.28 + littlefs to the REPL:

Interpreter Time
CPython 3.10 221.11s
CPython 3.14 + PYTHON_JIT=1 121.74s (~1.8x)
PyPy 3.10 9.59s (~23x)

For CPU-bound runs, PyPy is the clear winner: uv run --python pypy3.10 --no-dev -- python demo/micropython_run.py .... See docs/PORTING.md for the full breakdown (including a synthetic instructions/sec benchmark) and CI's python_runtime matrix, which tests all three.

uv run python demo/micropython_run.py --image my_image.uf2

A GDB server on port 3333 can be enabled by specifying the --gdb flag:

uv run python demo/micropython_run.py --gdb

For using the MicroPython demo code in tests, --expect-text can come in handy: it will look for the given text in the serial output and exit with code 0 if found, or 1 if not found. You can find an example in the MicroPython CI test.

Filesystem support

With MicroPython, you can use the filesystem on the Pico. This becomes useful as more than one script file is used in your code. Just put a LittleFS formatted filesystem image called littlefs.img into the rp2040py root directory, and your main.py will be automatically started from there.

Using littlefs-python, you can create such an image like this:

from littlefs import LittleFS

files = ["your.py", "files.py", "here.py", "main.py"]
output_image = "output/littlefs.img"  # symlinked/copied to rp2040py root directory
# disk_version=0x00020000 pins the on-disk format to littlefs v2.0, which both old and new
# MicroPython releases can mount - newer littlefs-python defaults to a newer format (v2.1) that
# MicroPython <=1.21 can't read. See docs/PORTING.md#known-differences-from-rp2040js.
lfs = LittleFS(block_size=4096, block_count=352, prog_size=256, disk_version=0x00020000)
for filename in files:
    with open(filename, "rb") as src_file, lfs.open(filename, "w") as lfs_file:
        lfs_file.write(src_file.read())
with open(output_image, "wb") as fh:
    fh.write(lfs.context.buffer)

See tests/mklittlefs.py for a minimal working example used by this project's own CI.

Currently, the filesystem is not writeable, as the SSI peripheral required for flash writing is not implemented yet.

CircuitPython code

To run the CircuitPython demo, you can follow the directions above for MicroPython, except download adafruit-circuitpython-raspberry_pi_pico-en_US-8.0.2.uf2 instead of the MicroPython UF2 file. Place it in the rp2040py root directory, then run:

uv run python demo/micropython_run.py --circuitpython

and start the CircuitPython REPL! The rest of the experience is the same as the MicroPython demo (Ctrl+X to exit, using the --image and --gdb options, etc).

Filesystem support

For CircuitPython, you can create a FAT12 filesystem in Linux using the truncate and mkfs.vfat utilities:

truncate fat12.img -s 1M  # make the image file
mkfs.vfat -F12 -S512 fat12.img  # create the FAT12 filesystem

You can then mount the filesystem image and add files to it:

mkdir fat12  # create the mounting folder if needed
sudo mount -o loop fat12.img fat12/  # mount the filesystem to the folder
sudo cp code.py fat12/  # copy code.py to the filesystem
sudo umount fat12/  # unmount the filesystem

While CircuitPython does not typically use a writeable filesystem, note that this functionality is unavailable (see the MicroPython filesystem support section for more details).

Learn more

  • rp2040js — the upstream TypeScript emulator this project is ported from.
  • docs/PORTING.md — port status, file by file.

License

Released under the MIT license. Copyright (c) 2021, Uri Shaked. Copyright (c) 2026, Dmytro Yaroshenko.

Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

rp2040py-0.1.0b1.tar.gz (170.5 kB view details)

Uploaded Source

Built Distribution

If you're not sure about the file name format, learn more about wheel file names.

rp2040py-0.1.0b1-py3-none-any.whl (94.6 kB view details)

Uploaded Python 3

File details

Details for the file rp2040py-0.1.0b1.tar.gz.

File metadata

  • Download URL: rp2040py-0.1.0b1.tar.gz
  • Upload date:
  • Size: 170.5 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: uv/0.12.0 {"installer":{"name":"uv","version":"0.12.0","subcommand":["publish"]},"python":null,"implementation":{"name":null,"version":null},"distro":{"name":"Ubuntu","version":"24.04","id":"noble","libc":null},"system":{"name":null,"release":null},"cpu":null,"openssl_version":null,"setuptools_version":null,"rustc_version":null,"ci":true}

File hashes

Hashes for rp2040py-0.1.0b1.tar.gz
Algorithm Hash digest
SHA256 7d02aa3a16c065e7edc9f8621b7f0c30a2d5c920a1f0c5a3030e35ed88f84a44
MD5 aa155ddad8659b4fdba3b432b431ff2a
BLAKE2b-256 2e440c4c31fe70d7d79ae6135e76d85573d1c355df64956f575e369997031f18

See more details on using hashes here.

File details

Details for the file rp2040py-0.1.0b1-py3-none-any.whl.

File metadata

  • Download URL: rp2040py-0.1.0b1-py3-none-any.whl
  • Upload date:
  • Size: 94.6 kB
  • Tags: Python 3
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: uv/0.12.0 {"installer":{"name":"uv","version":"0.12.0","subcommand":["publish"]},"python":null,"implementation":{"name":null,"version":null},"distro":{"name":"Ubuntu","version":"24.04","id":"noble","libc":null},"system":{"name":null,"release":null},"cpu":null,"openssl_version":null,"setuptools_version":null,"rustc_version":null,"ci":true}

File hashes

Hashes for rp2040py-0.1.0b1-py3-none-any.whl
Algorithm Hash digest
SHA256 bdc2ba83a838dbec00cff16df018d2a3f42ccb181336af56728a1c5496dc0852
MD5 9ad986568a30b3bea4e64ead846bae40
BLAKE2b-256 6c8986f8616dfa8ca49ec34f4989602555c6ecea3374dbad08c57a36934e5f70

See more details on using hashes here.

Supported by

AWS Cloud computing and Security Sponsor Datadog Monitoring Depot Continuous Integration Fastly CDN Google Download Analytics Sentry Error logging StatusPage Status page