Skip to content

Refactor: drop the dead latch/rearm machinery now that the lightbar uses raw HID #5

Description

@NicolasPogorzelski

Behaviour-preserving cleanup, to do after the raw-HID lightbar fix has soaked in real use. Follow-up to the shipped fix (38a1fc3, 2f128e6; see docs/decisions/steam-coexistence.md).

Why

The lightbar is now driven by a raw HID colour report (controller-led lightbar-raw) that clears the DualSense firmware "light out" latch directly. Several pieces in controller-manager.py exist only for the old, now-disproven assumption that a driver rebind was the only way to clear that latch. With the raw path they are dead weight:

  • ControllerInstance.apply_mode adoption rearm (the if adopt and not target and hidraw_holders(...) block that forces hidraw_gate("rearm", …)): its sole job was to rebind a freshly-paired, Steam-held pad to clear the latch. The raw _apply_led at the end of apply_mode now clears it — and in native mode we do not want to revoke Steam's fd anyway. Removing it also drops a driver rebind + node renumber from every first adoption (faster, less churn).
  • _latch_risk + the rearm branch in watch_holders (fires when a raw fd closed): the "rebind → fresh lightbar setup" rationale is gone. Keep only what is still needed for fd revocation / security, if anything — confirm the gate's restore/block paths already cover revocation without this.

Keep (unrelated to the latch): _repaint_at delayed re-assert (Steam re-stomps with its own colour, not just the latch), _assert_at backstop, refresh_led renumber detection, player-LED re-assert, the whole hidraw gate (security).

Order of work — do NOT skip step 1

Step 1 — harden tests FIRST (lock in behaviour, then refactor against it)

A refactor may only claim "behaviour-preserving" if tests pin the behaviour before the code moves.

  • Colour on adoption (test_lightbar_latch.py): assert the resting colour is written when a native pad is adopted while Steam holds it — asserted on the colour reaching led_set_raw with the pad's hidraw, independent of whether a rearm happened. (Today Scenario A couples the two; decouple them.)
  • No unnecessary rebind on adoption: after the refactor, assert clean and Steam-held native adoption performs no rearm (only restore). Add as pending/xfail now, flip when the code changes.
  • Mode switch native↔xbox writes the correct colour (blue/green) exactly once per switch — extend test_reconcile.py Scenario F to assert the hidraw target.
  • Steam reopen re-assert still fires (_repaint_at) — guard against deleting it with the latch code (test_steam_ownership.py).
  • Multi-pad independence: two pads (one native, one xbox) each keep their colour across a rebind of the other (test_multi_pad.py). Covers the two-firmware finding at the daemon level.

Run bash scripts/validate-repo.sh green before touching daemon code.

Step 2 — remove the dead latch machinery (only after step 1 is green + fix soaked)

  • Drop the adoption rearm block in apply_mode (confirm colour-on-adoption test still passes; confirm native-mode Steam fd is intentionally not revoked).
  • Remove _latch_risk and the watch_holders rearm branch, preserving any still-needed fd revocation via the existing gate paths.
  • Simplify the now-overlong docstrings/comments that explain the rebind-clears-latch model; point them at the raw-HID mechanism.
  • Re-tune _repaint_at / _assert_at only if the soak shows the native-mode "few seconds until blue" is worth shortening (with the adoption rearm gone there may be no rebind to race).

Acceptance

  • validate-repo.sh green; all tests/ pass.
  • Live: native (blue) + xbox (green), both pads, mode switches, Steam running — no regression vs. the shipped fix; adoption at least as fast.
  • Diff removes complexity without changing observable behaviour (bar the possibly shorter native-switch latency).

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions