chore(firmware): scaffold Spike 1 Blink crate
Generated from esp-rs/esp-idf-template for the ESP32-S3 std target. src/main.rs toggles GPIO 2 every 500 ms and logs `blink N` over USB- serial — the minimum bring-up surface called out in docs/v0.1-mvp-technical.md (Spike 1: confirm toolchain, flash, and basic GPIO). edition=2024 with rust-version=1.85. No editor/render/git/usb/fs modules yet; those land per the spike methodology when later spikes need them.
This commit is contained in:
111
firmware/README.md
Normal file
111
firmware/README.md
Normal file
@@ -0,0 +1,111 @@
|
||||
# Typoena firmware
|
||||
|
||||
Rust crate targeting `xtensa-esp32s3-espidf`. See the project root
|
||||
[`README.md`](../README.md) and
|
||||
[`docs/v0.1-mvp-technical.md`](../docs/v0.1-mvp-technical.md) for the wider
|
||||
context.
|
||||
|
||||
## Current state
|
||||
|
||||
**Spike 1 — Blink.** Toggles GPIO 2 every 500 ms and logs `blink N` to the
|
||||
USB-serial console. This proves three things only:
|
||||
|
||||
1. The Espressif Rust toolchain (Xtensa) is installed and on PATH.
|
||||
2. The crate links against `esp-idf-svc` and compiles for
|
||||
`xtensa-esp32s3-espidf`.
|
||||
3. Basic GPIO output works on real silicon (verified post-flash, once the
|
||||
board is on the bench).
|
||||
|
||||
Everything past that — EPD, SD, USB host, partial refresh, Wi-Fi/TLS,
|
||||
gitoxide push — is its own follow-up spike per
|
||||
[`docs/v0.1-mvp-technical.md`](../docs/v0.1-mvp-technical.md#hardware-bring-up-order).
|
||||
|
||||
## Build
|
||||
|
||||
Once per shell session, source the espup env (sets `LIBCLANG_PATH` and adds
|
||||
the Xtensa GCC to `PATH`):
|
||||
|
||||
```sh
|
||||
. ~/export-esp.sh
|
||||
```
|
||||
|
||||
Then from this directory:
|
||||
|
||||
```sh
|
||||
cargo build --release
|
||||
```
|
||||
|
||||
The first build is slow (the esp-idf C sources are checked out and built
|
||||
under `.embuild/`). Subsequent builds are incremental.
|
||||
|
||||
## Flash (when hardware is on the bench)
|
||||
|
||||
`cargo run --release` triggers `espflash flash --monitor` via the runner
|
||||
configured in `.cargo/config.toml`. With the ESP32-S3-DevKitC-1 connected
|
||||
over USB you should see:
|
||||
|
||||
```
|
||||
[…] blink 0
|
||||
[…] blink 1
|
||||
[…] blink 2
|
||||
…
|
||||
```
|
||||
|
||||
at 1 Hz on the serial monitor, and — if an LED is wired from GPIO 2 → 330 Ω
|
||||
→ GND — the LED blinks in lockstep.
|
||||
|
||||
## Pin choice
|
||||
|
||||
GPIO 2 is a safe general-purpose pin on the ESP32-S3-DevKitC-1: it's not
|
||||
tied to a strapping function at boot and not muxed to the USB or PSRAM
|
||||
peripherals. If you want to drive the on-board addressable LED instead,
|
||||
that's WS2812 on GPIO 48 and needs a different driver — out of scope for
|
||||
Spike 1.
|
||||
|
||||
## Editor / rust-analyzer
|
||||
|
||||
The repo-level `.zed/settings.json` configures `rust-analyzer` for this
|
||||
crate:
|
||||
|
||||
- `cargo.target` is pinned to `xtensa-esp32s3-espidf` with
|
||||
`allTargets = false`, so RA doesn't try to also check the crate for the
|
||||
host target (which can't build `esp-idf-sys`).
|
||||
- `binary.path` is pinned to the **rustup-managed** rust-analyzer
|
||||
(`stable` toolchain), not Zed's bundled one. Reason: recent Zed builds
|
||||
ship a rust-analyzer that calls `cargo metadata --lockfile-path`, which
|
||||
is still gated behind `-Z unstable-options` in cargo 1.95 and fails on
|
||||
both the `stable` and `esp` toolchains. The rustup-managed RA is
|
||||
version-locked to the cargo it ships with and avoids the flag.
|
||||
|
||||
If a contributor on a different machine has issues, regenerate the path:
|
||||
|
||||
```sh
|
||||
rustup component add rust-analyzer --toolchain stable
|
||||
rustup which rust-analyzer --toolchain stable
|
||||
# put the printed path into .zed/settings.json under lsp.rust-analyzer.binary.path
|
||||
```
|
||||
|
||||
Two things rust-analyzer still needs from the **environment Zed was
|
||||
launched in**:
|
||||
|
||||
- `LIBCLANG_PATH` — required by `bindgen` inside `esp-idf-sys`.
|
||||
- The Xtensa GCC on `PATH` — required by `embuild` during `cargo check`.
|
||||
|
||||
Both are set by `~/export-esp.sh`. The pragmatic workflow:
|
||||
|
||||
```sh
|
||||
. ~/export-esp.sh
|
||||
zed /Users/julien/jclab/typewriter # or: open from this shell
|
||||
```
|
||||
|
||||
If Zed is launched from Finder/Dock instead, rust-analyzer will report
|
||||
`bindgen` errors on the first `esp-idf-sys` check. Close Zed, source the
|
||||
env in a terminal, and relaunch from there.
|
||||
|
||||
## Toolchain pins
|
||||
|
||||
`rust-toolchain.toml` pins the channel to `esp` (installed by `espup
|
||||
install`). Cargo.toml currently includes git `[patch.crates-io]` overrides
|
||||
for `esp-idf-sys` / `esp-idf-hal` / `esp-idf-svc` (template default). These
|
||||
follow master and may need pinning to released versions if a master commit
|
||||
breaks the build.
|
||||
Reference in New Issue
Block a user