# {{PROJECT_NAME}} Arduino project generated by [Anvil](https://github.com/nexusworkshops/anvil) v{{ANVIL_VERSION}}. This project is self-contained. After creation, it only needs `arduino-cli` in PATH -- the Anvil binary is not required for day-to-day work. ## Quick Start On **Linux/macOS**: ```bash ./build.sh # compile only (verify) ./upload.sh # compile + upload to board ./upload.sh --monitor # compile, upload, open serial monitor ./monitor.sh # serial monitor (no compile) ./monitor.sh --watch # persistent monitor (reconnects after reset) ./test/run_tests.sh # host-side unit tests (no board needed) ``` On **Windows**: ```bat build REM compile only upload REM compile + upload upload --monitor REM compile, upload, open serial monitor monitor REM serial monitor test\run_tests REM host-side unit tests ``` All scripts read settings from `.anvil.toml` and port config from `.anvil.local` (if present). ## Selecting a Board The scripts auto-detect your board when you run `upload` or `monitor`. To save a specific device so it persists across sessions: ```bash anvil devices # see what's connected anvil devices --set COM3 # save that port (also captures VID:PID) anvil devices --get # check what's saved ``` This writes `.anvil.local`, which is gitignored. Each machine keeps its own. The VID:PID is captured automatically so the scripts can find your device even if the COM port number changes after a replug. ## Project Structure ``` {{PROJECT_NAME}}/ {{PROJECT_NAME}}/ {{PROJECT_NAME}}.ino Entry point (setup + loop) lib/ hal/ hal.h Hardware abstraction interface hal_arduino.h Real hardware implementation app/ {{PROJECT_NAME}}_app.h Application logic (testable) test/ mocks/ mock_hal.h Google Mock HAL sim_hal.h Stateful simulator HAL test_unit.cpp Unit tests CMakeLists.txt Test build system run_tests.sh / .bat Test runner build.sh / build.bat Compile sketch upload.sh / upload.bat Compile + upload to board monitor.sh / monitor.bat Serial monitor _detect_port.ps1 Port detection helper (Windows) .anvil.toml Project config (tracked by git) .anvil.local Machine-specific config (gitignored) ``` ## Architecture All hardware access goes through the `Hal` interface. The app code (`lib/app/`) depends only on `Hal`, never on `Arduino.h` directly. This means the app can be compiled and tested on the host without any Arduino hardware. Two HAL implementations: - `ArduinoHal` -- passthroughs to real hardware (used in the .ino) - `MockHal` -- Google Mock for verifying exact call sequences in tests ## Configuration ### .anvil.toml (tracked by git) Shared project settings: ```toml [build] fqbn = "arduino:avr:uno" warnings = "more" include_dirs = ["lib/hal", "lib/app"] extra_flags = ["-Werror"] [monitor] baud = 115200 ``` ### .anvil.local (not tracked by git) Machine-specific port assignment, created by `anvil devices --set`: ```toml port = "COM3" vid_pid = "0403:6001" ``` ## Prerequisites - `arduino-cli` in PATH with `arduino:avr` core installed - For host tests: `cmake`, `g++` (or `clang++`), `git` - Install everything at once: `anvil setup`