Meet fwm agent
fwm is the FirmwareMaestro CLI — an interactive, AI-powered assistant for Nordic Semiconductor nRF firmware development. Everything happens inside the fwm agent REPL: scaffolding new Zephyr / nRF Connect SDK projects, building, flashing, running validation sequences, cross-referencing datasheets, and asking the AI agent for help on real firmware problems.
Launch the interactive REPL (this is where you spend all your time)
Re-run the installer to upgrade fwm to the latest version
Emit a shell completion script (bash, zsh, fish, powershell)
Everything else — building, flashing, scaffolding, analysis, validation, auth — is available as a slash command inside the REPL, or by asking the AI agent directly.
Install
One-line install on macOS, Linux, and Windows
The installer drops a single fwm binary into ~/.fwm (or %USERPROFILE%\\.fwm on Windows) and adds it to your PATH.
macOS / Linux
curl -fsSL https://firmwaremaestro.com/install.sh | shWindows (PowerShell)
irm https://firmwaremaestro.com/install.ps1 | iexVerify
fwm --version # → fwm 0.5.0
fwm --help # → lists agent, update, helpUpgrade in place
fwm updateInstall options
- FWM_INSTALL — install directory for the fwm binary (default ~/.fwm).
- FWM_VERSION — pin to a specific version tag (e.g. v0.5.0); defaults to latest.
Launch
One command to open the REPL
A full-screen TUI with conversation pane, input box, and a status bar showing the current mode.
fwm agentLaunch flags
| Flag | Purpose |
|---|---|
| -q, --query <TEXT> | Single-shot mode — run one query and exit |
| --plan | Start in plan mode (read-only; requires approval before writes) |
| --compliance <STD> | Enable a safety standard (misra-c-2012, cert-c, iso26262, iec61508, iec62304, do178c) |
| --max-iterations <N> | Cap the agent loop at N iterations |
| --dry-run | Disable tool-call writes (write_file, edit_file, git_commit) |
| --no-history | Don't save or load session history |
Agent modes
Edit, Plan, or Debug — switch on the fly
Pick the right tool surface for the task. Switch between modes at any time with the matching slash command; the conversation carries forward.
Edit /edit
Full read + write access (19 tools)
Day-to-day firmware work — modify code, build, flash
Plan /plan
11 read-only tools
Think first, then do — agent reads, reasons, and produces a plan for your approval before any writes
Debug /debug
13 read-only analysis tools
Datasheet-aware code review — interrupt priorities, memory layout, register config, errata cross-referencing, timing
When a /plan or /debug session finishes with a report, the REPL asks whether to switch into /edit mode and hand the plan/report to the edit agent as a single follow-up — accept, decline, or add a custom follow-up message.
Inside the REPL
A keyboard-driven workspace built for firmware engineers
File attachments, smart paste, tool-use approval, and persistent sessions — all designed for terminal-first workflows.
Key bindings
- EnterSubmit a query, select a menu item, or approve a prompt
- EscInterrupt agent · reject tool-approval · close picker · clear input
- Ctrl+CQuit
- ↑ / ↓Input history — or move selection in slash/file picker
- PageUp / PageDownScroll the conversation 20 lines at a time
- Ctrl+A / HomeCursor to start of input
- Ctrl+E / EndCursor to end of input (empty input: scroll to bottom)
- Ctrl+UClear input line
- Ctrl+WDelete previous word
- Ctrl+LClear the conversation pane
- Mouse wheelScroll the conversation
File attachments with @
Type @ at the start of an empty input to open a file picker. Filter by typing, navigate with arrows, attach with Enter. Multiple files are supported; each is truncated at 30 KB with a hint to use read_file for anything larger.
Smart paste
Bracketed paste prevents premature submission of multi-line content. Long pastes collapse to a [pasted N characters] placeholder and expand back when you press Enter.
Tool-use approval
Dangerous tools (edit_file, write_file, run_command, git_commit, build, flash, run_validation) prompt for approval. Read-only tools never prompt.
Allow run_command $ west flash ? [Y]es [N]o [A]ccept all- Y / Enter — approve this one call
- N — reject and type a reason (the agent sees it)
- A — approve all remaining calls for this turn
- Esc — reject and stop the agent entirely
Session persistence
After each turn, conversations are saved to ~/.fwm/sessions/session_<unix-timestamp>.json. The three most recent are kept; older sessions are pruned automatically. Use /resume to list them or /resume N to reload.
Slash commands
Press / to open the picker
Slash commands are shortcuts when you know exactly what you want. You can also just ask the agent in natural language and it will use its tools to do the same work.
Core TUI
- /helpList the slash commands
- /clearClear the conversation pane
- /contextShow estimated and API-reported context-window usage
- /quitExit the REPL (alias: /exit)
Session management
- /resumeList saved sessions
- /resume NReload session N
- /history clearDelete all saved sessions
Authentication
- /loginOpen browser, authenticate, save token to ~/.fwm/config.toml
- /logoutRemove the stored token
- /whoamiShow the currently authenticated user
Project lifecycle
- /initScaffold a new Zephyr / nRF Connect SDK project for any of 21 Nordic targets
- /buildBuild with auto-detected toolchain (west, cargo, cmake, idf.py, pio)
- /flashFlash via west flash, nrfutil, nrfjprog, probe-rs, openocd, or custom command
- /analyzeLocal parsing of codebase, datasheet PDFs, and KiCad schematics
- /validateRun TOML-defined hardware validation sequences (CI / HIL / production)
- /targetsList every supported MCU with core, clock, flash, RAM, and default board
/init
Scaffold a new project for any of 21 Nordic targets
Project type is auto-selected from the chip's capabilities, and each target ships with a canonical Zephyr Hardware Model v2 board out of the box.
/init --target nrf52840 # BLE, C, on the nRF52840 DK
/init --target nrf9160 --name tracker # Named LTE project
/init --target nrf7002 # Wi-Fi (companion IC)
/init --target nrf52840 --language rust # Rust / Embassy
/init --target nrf52833 --language cpp # C++17
/init --target nrf52840 --rtos freertos # FreeRTOS skeleton
/init --from-docs ./docs/ # AI-driven: inspect docs, pick target + type
/init --from-docs . # Shortcut: AI-driven from current directory| Project type | Auto-selected for | Scaffolded |
|---|---|---|
| BLE | nRF52, nRF53, nRF54 | bt_enable(), bt_le_adv_start() |
| LTE | nRF91 | nrf_modem_lib_init(), lte_lc_connect() |
| Wi-Fi | nRF70 | net_mgmt callbacks |
| Thread | nRF52840, nRF5340 | OpenThread 802.15.4 |
| Matter | nRF52840, nRF5340 | Matter over Thread |
| Zigbee | nRF52840, nRF5340 | Zigbee 3.0 |
| General | Any | GPIO LED blink with GPIO_DT_SPEC_GET() |
Generated trees include the right CMakeLists.txt, prj.conf, and a boards/<board>.overlay devicetree file — all wired up so /build works out of the box. Rust projects produce an Embassy skeleton; C++ projects produce a C++17 skeleton; FreeRTOS produces FreeRTOSConfig.h plus a task-creating main.c.
/build
Custom [build] command in .fwm/project.toml wins. Otherwise fwm auto-detects the toolchain — Zephyr (west build with nRF Connect SDK env auto-set), Rust (cargo build), CMake, Make, ESP-IDF, or PlatformIO.
/build
/build --release
/build --clean
/build -- --pristine/flash
For Zephyr projects: west flash with nCS env auto-set, after verifying a build artifact exists. For other targets fwm prefers modern nrfutil device program and falls back to nrfjprog, probe-rs, openocd, pyocd, picotool, or dfu-util.
/flash
/flash --target nrf52840dk
/flash --erase
/flash --binary build/zephyr/zephyr.hex
/flash -- --runner nrfutil/analyze
Local parsing — no AI call, no authentication required. Output is saved as JSON to .fwm/context.json (override with --output).
/analyze # defaults to --codebase .
/analyze --codebase ./some-project
/analyze --datasheet path/to/nrf52840_ps.pdf
/analyze --schematic path/to/board.kicad_sch/validate
Automated TOML-defined step sequences for CI, hardware-in-the-loop checks, and production validation. Bundled examples include smoke-test, binary-size, and boot-test. Reports in JUnit XML, Markdown, or JSON.
/validate # list available sequences
/validate --init-example smoke-test # copy a bundled example
/validate -s .fwm/validations/smoke-test.toml # run a sequence
/validate -s seq.toml --report-format junit -o outSupported MCUs
21 Nordic targets across 5 families
All running nRF Connect SDK (nCS) on top of Zephyr RTOS. Run /targets inside the REPL to see every chip's default Zephyr board.
nRF52
BLE SoC (Cortex-M4 / M4F)
nRF52805, nRF52810, nRF52811, nRF52820, nRF52832, nRF52833, nRF52840
nRF53
Dual-core BLE SoC (Cortex-M33)
nRF5340
nRF54
Next-gen BLE / multiprotocol
nRF54H20, nRF54L05, nRF54L10, nRF54L15, nRF54LM20A, nRF54LM20B, nRF54LV10A
nRF70
Wi-Fi 6 companion IC
nRF7001, nRF7002
nRF91
Cellular IoT (LTE-M / NB-IoT + GNSS)
nRF9131, nRF9151, nRF9160, nRF9161
Example walkthrough
From install to a flashed BLE app
# 1. Install
curl -fsSL https://firmwaremaestro.com/install.sh | sh
# 2. Launch the REPL
fwm agentThen, inside the REPL:
/login # one-time auth via the browser
/init --target nrf52840 --name my-ble-app # scaffold a BLE project in current dir
/build # west build -b nrf52840dk/nrf52840
/flash # west flash
Why is my UART not receiving data? # ask — agent reads code, checks datasheet
/plan # switch to plan mode for a bigger change
Add a SPI driver for the LIS2DH12 accelerometer
Proceed with implementation? [Y]es [N]o [F]ollow up
/validate -s .fwm/validations/smoke-test.tomlConfiguration
Two TOML files, in priority order
Slash flags > environment variables > per-project .fwm/project.toml > global ~/.fwm/config.toml > built-in defaults.
Global — ~/.fwm/config.toml
[defaults]
language = "c"
compliance = "misra-c-2012"Created automatically by /login. Edit to set defaults.
Per-project — .fwm/project.toml
[project]
name = "ble-sensor-hub"
target = "nrf52840"
board = "nrf52840dk/nrf52840"
language = "c"
[build]
system = "zephyr"
extra_args = "--sysbuild -- -DSHIELD=nrf7002eb2"
artifact = "build/zephyr/zephyr.hex"
[flash]
# command = "nrfutil device program ..."AI backend
A Senior Embedded Firmware Architect, on call
All AI requests are proxied through api.firmwaremaestro.com. Authenticate with /login inside the REPL on first run.
Safety compliance
Enable a standard with fwm agent --compliance <std>:
What the agent emphasizes
- Deep nRF Connect SDK awareness — Zephyr devicetree, Kconfig layering, common subsystems (Shell, NVS, MCUboot, Sensor, I²C, SPI, USB, power management).
- Datasheet-aware code review — errata cross-referencing, register validation, interrupt and timing analysis in /debug mode.
- Memory-constrained, power-aware patterns and idiomatic Nordic CLI usage (west, nrfutil, nrfjprog).
Troubleshooting
Quick fixes for the common stumbling blocks
- /login browser didn't open. The REPL prints the auth URL — open it manually.
- /build fails with "west: unknown command 'build'". Install the nRF Connect SDK or set ZEPHYR_BASE to your nCS zephyr/ directory. fwm auto-detects common install paths (/opt/nordic/ncs/, ~/ncs/); for non-standard locations add a [build] command to .fwm/project.toml.
- /flash says "No build output found". Run /build first.
- Agent runs for a long time. Press Esc — long-running child processes (builds, flashes, validation shell commands) are killed along with the agent.
- Context usage too high. /context shows the current window; /clear resets the display, or restart with fwm agent --no-history.
Install fwm and ship Nordic firmware faster
A single curl command, a /login, and you're inside an AI agent that scaffolds, builds, flashes, and reviews your nRF Connect SDK + Zephyr code.