Build & Flash Reference¶
This page is the PlatformIO reference: every environment, the fuses, and the day-to-day commands. For a guided first-time walkthrough, see the hub's Get Started instead.
Repository¶
git clone --recurse-submodules https://github.com/przemczan/lightnet-firmware.git
cd lightnet-firmware
The twiboot bootloader lives in a submodule. If you already cloned without --recurse-submodules, run git submodule update --init --recursive.
The same source tree builds both controller and panel binaries — the active PlatformIO environment selects which one.
Configuration¶
Before building, copy the example config files and edit them to match your hardware:
cp src/controller.config.hpp.example src/controller.config.hpp
cp src/panel.config.hpp.example src/panel.config.hpp
cp platformio_local.ini.example platformio_local.ini # optional: USB/monitor ports
Both *.config.hpp files ship with sane defaults, so no changes are required to do a first build. The *.config.hpp files and platformio_local.ini are gitignored — keep per-device and per-machine settings there without touching the tracked *.example files.
Located at src/controller.config.hpp, included by src/controller/config.hpp.
| Symbol | Default | Description |
|---|---|---|
DEMO_MODE |
0 |
Set to 1 to run the built-in light demo on startup |
CONFIG_PORTAL_TIMEOUT |
120 |
Seconds the Wi-Fi captive portal stays open before timeout |
SERVER_PORT |
80 |
HTTP server port |
Debug sub-switches — all default to 1 when DEBUG=1 is set in platformio.ini. Uncomment and set to 0 to silence a specific area:
| Symbol | Area silenced |
|---|---|
DEBUG_API |
WebSocket / HTTP API logs |
DEBUG_RGB_CTRL |
LED controller logs |
DEBUG_LIGHTNET_BUS |
I²C bus logs |
DEBUG_FLASHER |
OTA / panel flash logs |
DEBUG_DISCOVERY |
Panel discovery / ping logs |
DEBUG_INIT |
Startup / init logs |
DEBUG_DEMO |
Demo logs |
Pin assignments (INITIALIZER_EDGE_PIN_NO, IIC_SDA_PIN, etc.) have platform-specific defaults in src/controller/config.hpp and only need overriding for custom hardware.
Located at src/panel.config.hpp, included by src/panel/config.hpp.
| Symbol | Default | Description |
|---|---|---|
NUMBER_OF_EDGES |
3 |
Physical edges on the panel (3–5) |
EDGE_1_PIN … EDGE_5_PIN |
9–13 | Arduino pin for each edge output |
6-edge panels
Six edges require a separate pin-change ISR — not yet supported.
Panel builds have DEBUG=0 by default. To enable, set DEBUG=1 for your panel environment in platformio.ini, then uncomment DEBUG_RGB_CTRL in this file.
PlatformIO environments¶
All environments are defined in platformio.ini.
| Environment | Board | Notes |
|---|---|---|
controller_esp8266 |
ESP-12E (ESP8266) | USB upload at 230400 baud |
controller_wemos_d1_mini_pro |
Wemos D1 Mini Pro (ESP8266) | USB upload at 460800 baud |
controller_esp32 |
ESP32 DevKit | USB upload at 460800 baud |
controller_s2_mini |
Lolin S2 Mini (ESP32-S2) | USB upload at 460800 baud |
controller_wemos_d1_mini_pro_sim |
Wemos D1 Mini (sim) | Host-side sim — no hardware; mirrors I²C over serial |
controller_esp32_sim |
ESP32 DevKit (sim) | Same as _sim above |
controller_s2_mini_sim |
Lolin S2 Mini (sim) | Same as _sim above |
All controller environments use lib_ldf_mode = chain+, FastLED, ESPAsyncWebServer, and ESPAsyncWiFiManager. *_sim targets define SIM_MODE and drive a virtual panel bus for development and live-preview testing without panels attached.
MQTT / Home Assistant is available on ESP32 controller targets only (controller_esp32, controller_s2_mini, and their _sim variants). ESP8266 builds do not include MQTT. Enable it via the WiFi captive portal (MQTT section) or PATCH /api/mqtt after the controller is on the network. By default the controller auto-discovers the broker (_mqtt._tcp mDNS, then homeassistant.local / hassio.local); set a manual broker host to skip discovery. Home Assistant discovers Lightnet entities automatically when its MQTT integration uses the same broker. See docs/api.md §2.9 for topic layout and discovery modes.
| Environment | Purpose |
|---|---|
native |
Host-side unit tests — pure C++ logic, no Arduino (pio test -e native) |
| Environment | Board | Uploader | Bootloader | Notes |
|---|---|---|---|---|
panel_atmega328_via_controller |
ATmega328P | Custom serial via controller | — | Upload .bin over the controller's 57600-baud serial port |
panel_atmega328pb |
ATmega328PB | USBasp | twiboot at 0x7000 |
-D flag preserves bootloader on erase |
panel_atmega328p |
ATmega328P | USBasp | twiboot at 0x7000 |
Same binary as 328PB |
| Environment | Purpose |
|---|---|
atmega328p_bootloader |
Flash fuses + burn twiboot bootloader onto a 328P panel |
atmega328pb_bootloader |
Same, for 328PB panels |
Panel fuses (ATmega328PB / 328P)¶
Flash fuses through the bootloader environment
Wrong fuse values can lock the microcontroller. Use pio run -e atmega328p_bootloader -t fuses — don't set them by hand unless you know exactly what you're doing.
lfuse = 0xF7 — 16 MHz external full-swing crystal
hfuse = 0xD8 — SPIEN, EESAVE, BOOTRST (4 KB boot section at 0x7000)
efuse = 0xFC — BOD 4.3 V
One-time sequence per panel:
pio run -e atmega328p_bootloader -t fuses # set fuses
pio run -e atmega328p_bootloader -t upload # burn twiboot
pio run -e panel_atmega328pb -t upload # burn panel application
After this, future panel updates are wireless via the controller. See OTA & Updates.
Common commands¶
# Build only
pio run -e controller_esp32
# Build + upload over USB
pio run -e controller_wemos_d1_mini_pro -t upload
# Upload over Wi-Fi (controller OTA via ArduinoOTA + mDNS)
pio run -e controller_wemos_d1_mini_pro -t upload --upload-port lightnet-XXXX.local
# Serial monitor — 57600 baud everywhere
pio device monitor -e controller_wemos_d1_mini_pro
# Build everything
pio run
# Run native host-side unit tests (no device needed — see Testing)
pio test -e native
Post-build .bin generation
The post-build hook tools/generate_bin.py automatically emits both .hex and .bin for every panel environment. Upload the .bin to the controller via POST /api/firmware/panels — no manual conversion needed.
- Hardware — pin assignments and panel connectivity
- Architecture — source tree and internal design
- OTA & Updates — panel updates over I²C and controller self-update
- Testing — native unit tests and how to add new ones