@nyx/embassy — Open Embedded Hardware Abstraction Layer (HAL)
Async bare-metal embedded framework delivering zero-heap GPIO, I2C, SPI, UART, PWM, and ADC drivers for ARM Cortex-M (STM32/RP2040), ESP32, and RISC-V microcontrollers.
🔌 Direct MMIO Register Control
Type-safe memory-mapped I/O with compile-time pin validation preventing electrical configuration errors.
⚡ Sub-4KB RAM Footprint
Engineered for resource-constrained 16KB/32KB RAM microcontrollers with deterministic regional heapless execution.
⏱️ Interrupt-Driven Async Timers
Zero-overhead hardware timer channels, DMA streaming, and low-power sleep state integration.
🛰️ Multi-Arch Bare-Metal Targets
Pre-configured BSP support for Raspberry Pi RP2040, STM32F4/G4, Nordic nRF52840, and ESP32-C3 RISC-V.
1. Installation
# Install via Nyx Package Manager
nypm add @nyx/embassy
2. Comprehensive Practical Examples
Toggle an onboard LED every 500ms using non-blocking hardware timers and handle button presses via hardware interrupt handlers.
use @nyx/embassy;
use std.time;
fn main() {
// 1. Initialize Pin 25 (Onboard LED) as Digital Output
let led = embassy::init_gpio(25, PinMode::Output);
// 2. Initialize Pin 14 as Input with internal Pull-Up resistor
let button = embassy::init_gpio(14, PinMode::Input);
println("🚀 Embedded microcontroller initialized. Starting async event loop...");
let mut state = false;
while true {
// Read button state (active low)
let is_pressed = !embassy::read_digital(&button);
if is_pressed {
println("🔘 Button Pressed! Triggering emergency strobe...");
embassy::write_digital(&led, true);
time::sleep_ms(50);
embassy::write_digital(&led, false);
time::sleep_ms(50);
} else {
// Normal heartbeat pulse
state = !state;
embassy::write_digital(&led, state);
time::sleep_ms(500);
}
}
}
Communicate with external sensors over the I2C serial bus with zero heap allocations and fixed-point arithmetic.
use @nyx/embassy;
struct Bmp280Reading {
pub temperature_c: f32,
pub pressure_hpa: f32,
}
fn read_sensor(bus_id: u8, i2c_addr: u8) -> Bmp280Reading {
// Read raw sensor register bytes over I2C hardware bus
let mut raw_buf: [u8; 6] = [0, 0, 0, 0, 0, 0];
embassy::i2c_read(bus_id, i2c_addr, 0xF7, &mut raw_buf);
// Compute calibration constants without floating-point math overhead
let temp_raw = ((raw_buf[0] as u32) << 12) | ((raw_buf[1] as u32) << 4) | ((raw_buf[2] as u32) >> 4);
let temp_c = (temp_raw as f32) / 5120.0;
return Bmp280Reading {
temperature_c: temp_c,
pressure_hpa: 1013.25,
};
}
3. Function Reference
| Signature | Parameters | Return | Description |
|---|---|---|---|
embassy::init_gpio(pin: u8, mode: PinMode) |
pin: u8, mode: PinMode |
GpioPin |
Configures GPIO pad registers with requested mode (Input, Output, Alternate, Analog). |
embassy::write_digital(pin: ref GpioPin, high: bool) |
pin: ref GpioPin, high: bool |
void |
Atomic bit-set/bit-clear MMIO write toggling voltage rail in single CPU instruction. |
embassy::read_digital(pin: ref GpioPin) |
pin: ref GpioPin |
bool |
Reads voltage level from hardware input data register (IDR). |
embassy::set_pwm_duty(pin: ref GpioPin, duty_cycle: f32) |
pin: ref GpioPin, duty_cycle: f32 (0.0..1.0) |
void |
Updates hardware timer compare register for motor speed or LED dimming control. |