Skip to content

feat(hid): recognize Lightspeed receiver (046d:c539) as Unifying-compatible - #510

Merged
davidbudnick merged 1 commit into
AprilNEA:masterfrom
Abnersouza7:feat/lightspeed-receiver-c539
Aug 10, 2026
Merged

feat(hid): recognize Lightspeed receiver (046d:c539) as Unifying-compatible#510
davidbudnick merged 1 commit into
AprilNEA:masterfrom
Abnersouza7:feat/lightspeed-receiver-c539

Conversation

@Abnersouza7

Copy link
Copy Markdown
Contributor

Summary

Devices paired through a Lightspeed gaming receiver (046d:c539) are currently invisible to OpenLogi on Linux: the receiver PID is not in any known-receiver list, so the inventory watcher probes the receiver node as a direct device (HID++ 1.0 → UnsupportedProtocolVersion → skipped) and probes the hid-logitech-dj per-device child node directly — which, as the comment on is_receiver_child_node predicts, times out every tick:

DEBUG openlogi_hid::inventory::features: Device::new failed slot=255 error=Channel(Timeout)
DEBUG openlogi_hid::inventory::probe: slot 0xff exposes no battery or config feature — likely a receiver secondary interface; skipping vid=046d pid=4087 has_model=false
WARN  openlogi_hid::inventory: node probe keeps failing — dropping its channel to reopen next tick   (×2, forever)

The device itself is fine — a manual HID++ 2.0 ping to the child node answers in milliseconds (protocol 4.2). The gap is purely receiver identification.

Lightspeed receivers answer the same HID++ 1.0 registers as Unifying (pairing count, connection state, 0xB5 pairing information — this is also how Solaar routes them), so adding the PID to the two Unifying lists is enough for full detection and settings support:

DEBUG openlogi_hid::inventory::probe: receiver reports pairing count pairing_count=Some(1)
DEBUG openlogi_hid::inventory::probe: unifying paired slot slot=1 online=true wpid=4087 kind=Mouse codename=Some("G903 LS")

Changes

  • openlogi-hid: add 0xc539 to UNIFYING_PIDS (route.rs) so the receiver routes as DeviceRoute::Unifying and its DJ child nodes are filtered out of direct enumeration.
  • openlogi-hidpp: add (0x046d, 0xc539) to unifying::VPID_PAIRS (receiver/unifying.rs) so receiver::detect walks the pairing slots.

Deliberately minimal scope:

  • Only c539 is added — the one Lightspeed PID I verified on real hardware. Other Lightspeed PIDs (c53a, c53f, c541, c545, c547, …) likely behave the same (they do in Solaar), but I did not want to add untested IDs. Happy to extend the list if you prefer.
  • The receiver shows up as "Unifying Receiver" in Receiver::name(). If you would rather have a distinct Lightspeed label (or a dedicated PID list that shares the Unifying protocol path), I am happy to follow up.

Testing

  • cargo fmt --check, cargo clippy -p openlogi-hid -p openlogi-hidpp --all-targets -- -D warnings, and cargo test -p openlogi-hid -p openlogi-hidpp (245 passed) on this branch (rustc 1.96, Linux x86_64).
  • Hardware-verified with this branch's agent + CLI on Arch Linux (kernel 7.1.4), G903 LS on a Lightspeed receiver plus a wired PRO Gaming Keyboard: openlogi list shows the receiver with the G903 LS on slot 1 (online=true wpid=4087, transports=usb+equad), the keyboard still enumerates, and the recurring "node probe keeps failing" warnings are gone. The same two-line change applied to v0.6.22 is running as my daily agent (~15 min soak at time of writing) with no probe-failure warnings.
  • Not runtime-tested: the Unifying pairing/unpairing flow on this receiver (Lightspeed receivers are single-device; I only verified detection, inventory, and the settings write path), and macOS/Windows (change is platform-independent PID data).

…atible

The Lightspeed gaming receiver answers the same HID++ 1.0 enumeration and
pairing-information registers as Unifying receivers, but its PID is not in
any known-receiver list, so devices paired through it are never discovered
on Linux: the receiver node is skipped after an UnsupportedProtocolVersion
ping and the hid-logitech-dj child node is probed directly, timing out on
every inventory tick.

Add the PID to UNIFYING_PIDS (openlogi-hid) and unifying::VPID_PAIRS
(openlogi-hidpp) so the receiver routes as DeviceRoute::Unifying and its
pairing slots are walked. Verified on real hardware with a G903 LS.
@greptile-apps

greptile-apps Bot commented Aug 3, 2026

Copy link
Copy Markdown

Greptile Summary

Recognizes Logitech Lightspeed receiver 046d:c539 as Unifying-compatible.

  • Adds the receiver PID to HID routing so receiver child nodes are filtered and routed through the Unifying path.
  • Adds the vendor/product pair to HID++ receiver detection so paired-device slots are enumerated through the existing Unifying implementation.

Confidence Score: 5/5

The PR appears safe to merge, with both allowlist changes consistently routing the verified Lightspeed receiver through the existing Unifying-compatible path.

The two additions align route selection with receiver detection, and no concrete changed-code-triggered functional or security failure was established.

Important Files Changed

Filename Overview
crates/openlogi-hid/src/route.rs Adds the Lightspeed receiver PID to the existing Unifying-compatible routing and child-node filtering list.
crates/openlogi-hidpp/src/receiver/unifying.rs Adds the Logitech Lightspeed VID/PID pair to Unifying receiver detection for pairing-slot enumeration.

Flowchart

%%{init: {'theme': 'neutral'}}%%
flowchart LR
    A[USB receiver 046d:c539] --> B[Inventory identifies known receiver]
    B --> C[DeviceRoute::Unifying]
    B --> D[Filter direct DJ child-node probing]
    C --> E[HID++ receiver detection]
    E --> F[Unifying-compatible slot enumeration]
    F --> G[Paired Lightspeed device discovered]
Loading

Reviews (1): Last reviewed commit: "feat(hid): recognize Lightspeed receiver..." | Re-trigger Greptile

@Stanley5249

Copy link
Copy Markdown
Contributor

#459 adds Lightspeed the same way (c53f, c547), so these will conflict in UNIFYING_PIDS / VPID_PAIRS. I've carried c539 over there with a co-author trailer, happy either way round.

@davidbudnick davidbudnick added platform: all Cross-platform issue type: feature New feature request labels Aug 4, 2026
@davidbudnick davidbudnick added this to the v0.6.24 milestone Aug 10, 2026
@davidbudnick
davidbudnick merged commit 720475f into AprilNEA:master Aug 10, 2026
29 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

platform: all Cross-platform issue type: feature New feature request

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants