First successful flash: placeholder face live; fix 20MHz PSRAM trap; power ladder
Test, Build and Push / test-gateway (push) Successful in 10s
Test, Build and Push / release (push) Skipped
Test, Build and Push / build-gateway (push) Skipped

- firmware boots to a rendered LVGL face in 1.57s (eyes + smile + tag)
- sdkconfig: CONFIG_IDF_EXPERIMENTAL_FEATURES=y unlocks SPIRAM 200MHz
  (silently degraded to 20MHz before -> MIPI-DSI underrun -> LVGL lock
  starvation -> task watchdog); mirrors official 08_lvgl_demo_v9 config
- architecture.md: power management section (user prime concern) —
  active/ambient/dormant/night ladder, levers, hard edges, <=300ms wake
- AGENTS/CLAUDE: replace stale bring-up warnings with verified commands

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
This commit is contained in:
2026-07-14 20:31:25 +02:00
co-authored by Claude Fable 5
parent 2d5cbd1174
commit 450bac1c81
5 changed files with 119 additions and 29 deletions
+48
View File
@@ -164,6 +164,54 @@ WebSocket disconnected → `error` (quiet, persistent); otherwise `idle`.
The `rage` frames additionally need `╯ ︵ ┻ ━ ┬ ─ ノ ° □ º` in the subset.
- The sim's text glow (`text-shadow`) is browser flair — the device renders flat glyphs.
## Power management (prime concern)
User requirement: the device idles on a wall 95%+ of its life — low power when nothing
is happening is a first-class design goal, not a phase-5 nicety. The face state machine
is therefore built around a **power ladder** from day one:
| Power state | Backlight | Rendering | CPU | Entered when |
|-------------|-----------|-----------|-----|--------------|
| `active` | 100% | full animation | full clock | conversation in progress (listening→speaking) |
| `ambient` | ~35% | idle face, sparse rain | DFS enabled | idle, but activity in the last few minutes |
| `dormant` | off (or ≤5%) | **no redraws** — render loop parked | min clock via DFS | no voice/touch for N min (default 10) |
| `night` | off, panel sleep | none | min clock | schedule or "goodnight" command |
Levers, in order of impact:
1. **Backlight** — this is an IPS LCD: black pixels still burn backlight (unlike OLED),
so brightness is the dominant lever. `bsp_display_brightness_set()` drives it.
2. **Render idleness** — rain off and animations parked means LVGL stops producing
frames, which is what lets DFS actually reach its floor.
3. **DFS / power management** (`CONFIG_PM_ENABLE`) — automatic frequency scaling when
tasks are quiet. Note the MIPI-DSI constraint below.
4. **Radio** — the C6 runs Wi-Fi modem power-save; the gateway WebSocket widens its
ping interval when the device reports `dormant`.
Wake triggers (any → `ambient`/`active`): wake word (phase 5), touch (from phase 2),
local VAD "someone is speaking" pre-warm, a gateway-initiated event (butler wants to
say something), scheduled morning end of `night`.
**Hard edges — what limits how low we can go:**
- **The hands-free promise sets the power floor.** Wake word requires mics + the AFE
pipeline running continuously; deep sleep is permanently off the table while the
device promises to answer its name. The floor is "CPU lightly loaded at min clock,
radios in power-save, backlight off."
- **DSI needs clocks while the panel is active** — the deepest CPU savings only unlock
in `dormant`/`night` when the panel stops being refreshed (panel sleep / blank).
- **Wake latency budget: ≤ ~300 ms** from trigger to visible face (backlight ramp +
first render). Anything slower reads as "it's off," which kills the butler illusion.
- **Touch stays powered** in all states except possibly `night` — its idle draw is
negligible and tap-to-wake must always work.
- **No invented numbers**: actual draw gets measured with a USB power meter at each
phase; working target is `dormant` ≤ ⅓ of `active`. (Always-on device: every watt
saved ≈ 9 kWh/year.)
Implementation order: backlight dimming + `dormant` timeout + touch wake land in
**phase 2** with the face state machine (timeout-driven); voice-linked triggers upgrade
it in phase 5.
## Latency budget & streaming
Measured/known numbers that shape the design (Tatlock figures per tatlock CLAUDE.md,