Peripheral status relay - #5
Merged
Merged
Conversation
The right half cannot see layer or BLE-profile state (endpoints.c/ble.c/ keymap.c are central-only at v0.3.0 and the split GATT service has no such characteristic - see zmk-next-steps.md §3). Instead of new GATT, the central pushes a snapshot over the stock RUN_BEHAVIOR channel by invoking a carrier behavior on the peripheral, the same mechanism &bootloader locality uses. - stat_rly behavior (anaphase,behavior-status-relay): node name kept to 8 chars to fit the 9-byte behavior_dev split payload field (cf. upstream's 'bootload'/'sysreset' naming). Never bound in a keymap. - status_relay.c: central listens to layer_state_changed + ble_active_profile_changed and sends (layer id, profile index); a 15s refresh timer heals stale displays after split reconnects. Peripheral side stores the snapshot and raises a local event. - layer_status widget: peripheral branch renders the relayed layer id using a name table generated from this half's own keymap devicetree (present even though keymap.c isn't compiled). '----' until first relay. Studio runtime renames won't propagate (DT names only). - output_status widget: peripheral name row now shows the central's active profile nickname (name_array moved to shared scope); 'ANAPHASE' fallback until the relay lands. Split-link PAIRED/WAITING unchanged. - Gated behind CONFIG_ANAPHASE_STATUS_RELAY (default y) - one line to disable if the relay ever misbehaves. Known risk (accepted): zmk_split_central_invoke_behavior is exported but undocumented; the v0.4 split-transport rework will likely force a re-port. Cost: +320B flash central, +740B peripheral. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
The left screen wakes on any keypress because the central sees both halves' key events; the peripheral has no reverse traffic, so its OLED only woke on its own keys. Fix: the relay payload gains a central-activity flag (param2 bit 8). The central's activity state already represents the whole keyboard, so mirroring its ACTIVE/IDLE transitions onto the peripheral as synthetic zmk_activity_state_changed events gives the right OLED identical semantics to the left - wake ~20ms after the first keypress on either half, blank 60s after the last one. ZMK's stock blank-on-idle machinery does all the work; no per-keystroke traffic (transitions + the existing 15s refresh only), no custom blank manager. Deep sleep deliberately stays local to each half - the mirror never raises SLEEP. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Hardware test caught the hole: the wake worked, but the right half's own activity.c only watches local keys, so 60s after the last RIGHT keypress it raised IDLE and blanked - while the mirror's change-detector stayed silent (the central's state hadn't changed). Fix on the peripheral, two parts: - Local IDLE arriving while the mirrored central state is active AND fresh (relay heard <35s = two refresh periods + slack) is countered by re-asserting ACTIVE from a deferred work item (50ms; worst case a brief blink once per local-idle expiry). - The override is edge-triggered but staleness is a state: a watchdog re-checks at the freshness deadline, so a central that dies AFTER an override kept the screen on gets its claim dropped and the display blanked. A dead left half costs at most ~35s of extra screen-on time in every ordering. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
All three test cases pass: sustained left-only typing keeps the right OLED lit (one blink at local-idle expiry), both screens blank together on whole-keyboard idle, and the watchdog blanks the right screen ~50s after the left half powers off mid-override. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
No description provided.