-
fix(rig): the LED watcher had three lifecycles and two could run at once — now it is gear · 901b43a6
The board's colours only persist because a daemon holds a model of every control and repaints from it. That daemon had no home. It could be started three ways: 1. by hand, tools/lcxl-leds.py --watch 2. by gig-up.sh, which `setsid`-spawned its own copy (GIG_LEDS=watch) 3. as a *transient* systemd unit, which is how it was actually running today (systemd-run --unit=lcxl-leds-watch) Every one of those is wrong in a different way. (1) dies with the terminal. (2) does not know about (3), so launching gig-up on a machine that already had the watcher up gave you TWO processes writing SysEx to the same LCXL, fighting over every LED — and neither of them wrong enough to look broken, which is the worst kind of bug this rig produces. (3) has no file on disk, so it evaporates at the next reboot and the board silently stops persisting colours. PLN, on being shown the three: "watcher must be a saved tool part of gear indeed". So: tools/lcxl-leds-watch.service, symlinked into ~/.config/systemd/user/ the same way parvagues-bridge.service already is, enabled, WantedBy=default.target — it starts at boot with linger, before any login. gig-up.sh no longer spawns anything; it `systemctl --user restart`s the unit, which is idempotent AND guarantees exactly one owner even if a stale watcher survived a crash. One owner of the board, always. Two details worth the ink: - StartLimitIntervalSec=0 belongs in [Unit], not [Service]. Put in [Service] systemd says "Unknown key ... ignoring" — a warning in the journal nobody reads — and the default limit of 5 restarts in 10 s stays in force. The LCXL is hot-pluggable and usually absent at boot, so with Restart=always/RestartSec=10 the unit would burn its five retries and fall into `failed`, board dark for the rest of the session. A silent failure one section heading away from working. Caught it because the first install DID log the warning; fixed and re-verified with systemd-analyze. - Cost, measured from the transient unit's own accounting before replacing it: 2.140 s CPU over 1 h 53 m wall = 0.03% of a core, 14.5 M peak RSS. The watcher forks a helper per LED write, which is a real throughput problem for the 1-2 s paint lag — but it is emphatically not a load problem, so it can stay Nice=5 / CPUWeight=20 and never be a candidate when hunting xruns. Verified: unit enabled + active, systemd-analyze verify clean, no Unknown-key warning on reload, `bash -n gig-up.sh` clean, and exactly one watcher process owned by the unit (MainPID matches, NRestarts=0). Note `pgrep -cf 'lcxl-leds.py --watch'` reports 2 — it counts the shell running the pgrep pipeline itself. Read the process list, not the count. Closes #85.PLN (Algolia) authored901b43a6
×