expanseElectronics

v7 firmware — what changed

v7.1 was the largest single firmware update we'd shipped since the dualETH-PixelControl launched. It rewrote almost everything you can see — the web UI, the API behind it, the network config, even the device's MAC address. Since then v7 has kept growing through six follow-up releases. This post is the running record of what changed and why.

v7.1 — the rewrite (29 April)

A new web UI, ground up

The old web UI was hand-written HTML and CSS embedded as literal C strings in the firmware source. Every change meant escaping quotes, re-flashing, hoping. The new one is a small single-page application with a proper REST API behind it — the kind of stack you'd expect to find on any modern device.

What you actually get from this:

  • A live status dashboard that polls every few seconds. Uptime, free memory, packet rate per port, last reset reason, status LEDs mirrored in the browser. Everything you'd want when something isn't working as expected.
  • Per-port pages with cleaner forms, validation, and immediate feedback on save.
  • Mobile-friendly layout — the new UI works on a phone in the rack room.

The whole UI is around 38 KB and is served direct from on-chip flash, so it loads instantly even with no internet connection.

Each device gets a unique MAC

Earlier firmware shipped with a single hard-coded MAC address — every dualETH on a network shared the same identifier, and any installation with more than one device ran into ARP collisions. v7 derives the MAC from the chip's factory-burned identifier instead, so every board picks its own.

If you're upgrading from v6.x, your device's MAC will change on first boot of v7.x. DHCP reservations, firewall rules, switch ACLs, and device-management tools that key on MAC will all see the unit as new. The fresh MAC is shown on the status page once the unit is back online.

WiFi is gone

The dualETH hardware never used WiFi — the radio was on the board but every revision of the firmware kept it parked. v7 removes the WiFi stack entirely. This frees roughly 30 KB of RAM and drops idle power draw by about 70 mA, which translates directly into more headroom for everything else: longer pixel runs, more reliable web UI under load, less heat.

If you have somehow been using the WiFi hotspot or station mode (we'd love to hear how — please get in touch), v7 will not work for you. Stay on v6.38 until we understand the use case.

A factory-reset on first boot

The settings format on disk changed shape — new fields, some old fields gone. v7 detects the old format on first boot and resets to factory defaults to avoid loading invalid data into the new struct. You'll need to re-enter your IP, port modes, and universe assignments after upgrading from v6.x. A configuration export/import is on the roadmap so this gets easier in future.

v7.2 / v7.2.1 — Status LEDs (3 May)

A per-direction LED state machine matching the HALO Gen5 board layout: LED 0 mirrors Port A RX, LED 1 mirrors Port A TX, LED 2 mirrors Port B TX. Boot indicator, packet-blip rendering, mode-aware output colours. v7.2.1 added a UI mirror of those LEDs on the web status page, so you can see the device's blink pattern from a browser without leaning into the rack.

v7.3 — Discovery API (4 May)

A new /api/identify endpoint that lets a controller locate every dualETH on a network and learn what each one can do, without hard-coding device knowledge into the manager. This is the groundwork for the masterETH manager's fleet-management view (now shipping as masterETH v1.1).

v7.4 — CORS for cross-origin tools (4 May)

CORS headers on the device's REST API so the masterETH manager — and any third-party dashboard, Home Assistant integration, or browser-based scripting tool — can talk to the node without a proxy.

v7.4.1 — OTA upload fix, take one (4 May)

A fix for a "Failed to save" error in the device's own in-SPA firmware-upload flow, caused by a race between /api/firmware/prepare's reboot and the subsequent /upload request. The fix was real, but it turned out to only be half the story — see v7.5.1.

v7.5.1 — Onboarding wizard, and the real OTA fix (13 May)

A first-boot wizard walks new devices (and v7.4.x upgraders) through: welcome → network → node name → port A → port B → status-LED legend → done. Each port step mirrors the full Ports tab — protocol, merge, net/subnet, universe and sACN universe, plus the WS2812 pixel sub-form. Existing saved settings are preserved; the wizard pre-fills every field and appears exactly once.

The same release fixes the real cause of the OTA "Failed to save" bug that affected every release since v7.1. The PlatformIO esp07 board profile defaulted to a 256 KB filesystem partition, leaving only ~328 KB of OTA staging space — smaller than the firmware binary itself by the time v7.5 was built. v7.5.1 overrides the linker script to a 64 KB FS layout, giving ~496 KB of headroom. Web Serial flashes via this site's updater were never affected; only the device's own in-SPA OTA was broken.

One-time consequence: an existing device running anything pre-v7.5.1 cannot OTA to v7.5.1 — the very bug being fixed prevents it. You'll need to Web Serial flash v7.5.1 once via the updater. After that, future OTAs work normally.

(There was a v7.5 binary that briefly shipped this wizard without the partition fix — we pulled it the same day after the OTA failure reproduced. v7.5.1 supersedes it.)

v7.5.2 — Per-device serial number (13 May)

Each device now reports a human-readable serial number derived deterministically from the ESP8266 chip ID: DE- followed by 12 base36 characters (for example DE-HI98I0YTL2B7). It appears on the Device Status page and in the /api/identify and /api/status REST responses. Re-flashing the same module always produces the same serial. It's intended as a label-printable handle for production fixtures — it's not a security identifier.

Where to land today

If you're upgrading from any earlier build, flash v7.5.2 directly and skip the intermediate steps. The updater lists only v7.5.2 now — a single version to install keeps support straightforward. Older binaries stay in the GitHub repo's tag history if you ever need to roll back.

The migration notes from v7.1 still apply when coming from v6.x:

  • Your MAC will change on first boot of v7.x. Update DHCP reservations, firewall rules, and switch ACLs that key on the old hard-coded MAC.
  • Settings reset to factory defaults when v7 detects the old on-disk format. Re-enter IP, port modes, and universe assignments after the upgrade.
  • WiFi is gone. If you were somehow using it, stay on v6.38 until we understand the use case.

The firmware update guide walks through the post-flash steps in more depth.