std/*
std/* packages are the higher-level, cross-target library. They may depend on heap allocation or target-specific runtime services.
std/text: Portable Text
std/text is the portable text package that complements the built-in string and char types.
Today it provides:
- read-only string behavior through the
stringmethod surface - allocation-free split results with
text.Split - fixed-capacity mutable text with
text.Buffer[N]
use std/text as text
let text_value = " key?=value\r\n"
let split = text_value.trim().split_once("?=")
let mut buffer = text.buffer(32)
let first = buffer.push_str(split.before())
let middle = buffer.push('=')
let last = buffer.push_str(split.after())
See Text for the actual current std/text API surface.
std/io: Buffered IO
use std/io
let mut buf_writer = io.BufferedWriter.new(uart_port, 256)?
buf_writer.write(data)?
buf_writer.flush()? // flush accumulated bytes to underlying writer
std/fs: Filesystem
Available on host targets and MCU targets with SD card / FAT support:
use std/fs
let text = fs.read_text("config.txt")?
let bytes = fs.read_bytes("firmware.bin")?
let mut file = fs.open("log.txt")?
defer file.close()
file.write(b"log entry\n")?
Collections
List<T>, Deque<T>, Map<K, V>, and Set<T> are always available without an explicit use. They are compiler-known generic types:
let mut items: List<u32> = List.new()
items.push(1)? // fallible: allocation can fail
items.push(2)?
items.push(3)?
let first = items[0] // infallible: after allocation, indexing does not fail
let len = items.len()
for item in items {
process(item)
}
let mut config: Map<string, string> = Map.new()
config.insert("baud", "115200")?
config.insert("target", "rp2040")?
if let Some(baud) = config.get("baud") {
log.info(baud)
}
for entry in config.entries() {
log.info(entry.key)
log.info(entry.value)
}
Collection operations that allocate (push, insert, extend) return Result. Operations that do not allocate (len, get, indexing after allocation) are infallible.
std/sync: Channels and Mutexes
use std/sync
// Create a channel with capacity 16
let ends = sync.channel<u32>(16)?
let tx = ends.tx
let rx = ends.rx
// Send (blocking)
tx.send(42)?
// Non-blocking send
tx.try_send(42)?
// Receive (blocking)
let value = rx.recv()?
// Non-blocking receive
if let Ok(value) = rx.try_recv() {
process(value)
}
Mutex:
use std/sync
let counter: sync.Mutex<u32> = sync.Mutex.new(0)?
{
let mut guard = counter.lock()?
defer guard.release()
guard.value += 1
}
ISR rules: ISR code must not call blocking recv, send, lock, or wait operations. Use try_send and try_recv in interrupt contexts.
std/embed
Higher-level wrappers over core/embed for structured asset loading. Details depend on the specific asset type.