Reduino lets you write a small, Pythonic DSL that transpiles to clean Arduino C++ and optionally flashes your board via PlatformIO. You get readable Python during development and reliable C++ on the device.
Requirements: Python 3.10+, PlatformIO for building/flashing.
pip install Reduino
pip install platformio # required for uploadsIf upload=True, Reduino will run pio run -t upload for you in a temporary PlatformIO project (Arduino Uno by default). You can re-run pio run later to rebuild or flash again.
- Parse –
Reduino.transpile.parser.parse()builds an intermediate representation (IR) from your script. - Analyze – Constant folding, control-flow preservation, and safety checks happen on the IR.
- Emit –
Reduino.transpile.emitter.emit()produces Arduino-ready C++ (main.cpp). - Toolchain –
Reduino.target()writes aplatformio.ini(serial port & board), and optionally calls PlatformIO to build/flash.
Hardware side effects only occur on the device after upload—host-side execution is side-effect free.
| Member | Description |
|---|---|
Led(pin=13) |
Create a virtual LED bound to an Arduino pin. |
on() / off() |
Turn LED fully on/off. |
toggle() |
Flip between on/off. |
get_state() |
True if LED is currently on. |
get_brightness() / set_brightness(v) |
PWM level (0–255) read/write. Raises ValueError if out of range. |
blink(duration_ms, times=1) |
Blink helper with internal waits. |
fade_in(step=5, delay_ms=10) / fade_out(step=5, delay_ms=10) |
Gradual brightness ramp. |
flash_pattern(pattern, delay_ms=200) |
Iterate over [0/1 or 0–255] values. |
Example
from Reduino.Actuators import Led
led = Led(5)
led.set_brightness(128)
led.blink(250, times=3)| Member | Description |
|---|---|
Ultrasonic(trig, echo, sensor="HC-SR04", *, distance_provider=None, default_distance=0.0) |
Factory returning an ultrasonic sensor helper. Only the HC-SR04 model is supported today; the selector is reserved for future expansion. |
UltrasonicSensor.measure_distance() |
Return the simulated distance reading (centimetres). Uses the optional provider when supplied, otherwise falls back to default_distance. |
The generated HC-SR04 helpers throttle trigger pulses to the recommended 60 ms interval, retry short reads, and reuse the most recent valid distance (or 400 cm when none exist yet) whenever the sensor reports a timeout. This prevents spurious zero-centimetre results that can occur when the module is polled too quickly.
Note
HC-SR04 helpers wait at least 60 ms between trigger pulses, retry up to three reads when pulseIn() reports zero microseconds, and only reuse a cached value after a successful measurement. When no reading has ever succeeded they fall back to the sensor's approximate maximum range (400 cm).
Example
from Reduino.Sensors import Ultrasonic
sensor = Ultrasonic(trig=7, echo=6)
reading = sensor.measure_distance()| Member | Description |
|---|---|
Sleep(ms, sleep_func=None) |
Delay helper; custom sleep_func is injectable for tests. |
Example
from Reduino.Time import Sleep
Sleep(500)| Member | Description |
|---|---|
target(port, upload=True) |
Transpile the current module; return generated C++. If upload is true, also build & flash via PlatformIO. The last call wins if used multiple times at top level. |
Example
from Reduino import target
cpp = target("/dev/ttyACM0", upload=False)
print(cpp)Reduino.Utils collects helper utilities that complement the core transpiler
APIs. They are designed to be imported piecemeal:
from Reduino.Utils import SerialMonitor| Member | Description |
|---|---|
SerialMonitor(baud_rate=9600, port=None, timeout=1.0) |
Configure an Arduino-style serial console. Optionally auto-connect to port. |
connect(port) |
Open a host-side serial connection using the configured baud rate. |
close() |
Tear down the active serial connection if one exists. |
write(value) |
Send text to the MCU. Returns the string sent (without newline). |
read() |
Read the next message from the MCU and echo it to stdout. Returns the text. |
Usage pattern
from Reduino import target
from Reduino.Utils import SerialMonitor
monitor = SerialMonitor(baud_rate=115200)
monitor.connect("/dev/ttyACM0") # requires the optional 'pyserial' dependency
cpp = target("/dev/ttyACM0", upload=True)
print("Generated C++:\n", cpp)
monitor.write("hello from host")
message = monitor.read()Call monitor.close() when you no longer need the serial session. When
running on a system without pyserial installed, instantiate the monitor
without calling connect until the dependency is available.
Control flow
while True:becomes the Arduinoloop()body.foroverrange(...), lists/tuples, or generator expressions.if/elif/else, ternaries,break/continue.
Variables & assignment
- Regular assignment, tuple unpacking, pythonic swap
a, b = b, a. - Augmented ops (
+=,-=, ...). Branch-local vars are promoted safely.
Collections & comprehensions
- Lists/tuples/dicts, membership tests, list methods (
append,extend, ...). - List comps & generators (evaluated eagerly into temps for safety).
Functions & expressions
def/return, defaults, lambdas (on supported expressions).- Literals: int/float/str/bool; casts:
int/float/bool/str. - Built-ins:
len,abs,max,min,sum,range.
Device primitives
- LED pin init creates
pinMode; actions becomedigitalWrite/PWM; sleeps becomedelay(ms). - Ultrasonic
HC-SR04sensors configure trig/echo pins and emit helper functions formeasure_distance().
Target directive
target("PORT")can appear anywhere at top level; the last call wins and is written toplatformio.ini.
pip install pytest
pytestThe suite covers parsing, emission, runtime helpers, and public primitives.
PRs for new actuators/sensors and transpiler improvements are welcome. See CONTRIBUTING.md for guidelines and the IR/emitter architecture.
Reduino is distributed under GPL-3.0.
You may:
- Use, modify, and distribute under GPL-3.0.
- Build upon it in your open-source projects (derivatives must also be GPL-3.0).
For closed-source or commercial use, dual/custom licensing is available.
Commercial inquiries: arnavbajaj9@gmail.com
© 2025 Arnav Bajaj. All rights reserved.
