refactor(ipc): acknowledge pairing commands#304
Conversation
Greptile SummaryThis PR converts pairing IPC commands from fire-and-forget unit returns to typed
Confidence Score: 5/5Safe to merge — the previous race (cancel injecting a spurious failure after Paired) is correctly resolved, and the new ReceiverAccess arbiter is a clean replacement for the dual-AtomicBool rendezvous. Both concerns from the prior review round are properly addressed: cancel() returns Ok(()) when sessions==0 (no-op, no spurious Failed update), and reply_disconnected now uses AgentRestarted for StartPairing/PairDevice. The ReceiverAccess design is cancellation-safe (PairingRequest RAII guard clears pairing_requested if the acquire_for_pairing future is dropped), the double-check in try_acquire_for_capture prevents TOCTOU between the flag read and the lock acquisition, and SessionAdmission ensures the sessions counter is always rolled back on any early-exit path in start(). Wire-format golden tests and targeted unit tests for ReceiverAccess cover the critical invariants. No files require special attention. Important Files Changed
Sequence Diagram%%{init: {'theme': 'neutral'}}%%
sequenceDiagram
participant GUI as GUI add_device
participant IPC as ipc_client poll_loop
participant Agent as AgentServer tarpc
participant PM as PairingManager
participant RA as ReceiverAccess
participant GW as GestureWatcher ticker
GUI->>IPC: Command::StartPairing
IPC->>Agent: start_pairing(selector)
Agent->>PM: start(selector)
PM->>PM: compare_exchange 0 to 1
PM->>RA: acquire_for_pairing timeout 5s
RA->>RA: "pairing_requested = true"
GW-->>RA: sees pairing_requested stops capture drops lease
RA-->>PM: PairingReceiverLease mutex held
PM->>PM: store lease send Control::Start
PM-->>Agent: Ok(())
Agent-->>IPC: Ok(Ok(()))
IPC->>IPC: pairing_command_result no update sent
Note over PM: terminal event in translate
PM->>PM: sessions fetch_sub to 0 drop PairingReceiverLease
RA->>RA: "pairing_requested = false"
GW-->>RA: acquires CaptureReceiverLease resumes
GUI->>IPC: Command::StartPairing while session active
IPC->>Agent: start_pairing
Agent->>PM: start
PM-->>Agent: Err(AlreadyActive)
Agent-->>IPC: Ok(Err(AlreadyActive))
IPC->>GUI: PairingUpdate::Failed AlreadyActive
%%{init: {'theme': 'base', 'themeVariables': {"darkMode": true, "background": "#0d1117", "primaryColor": "#21262d", "primaryTextColor": "#e6edf3", "primaryBorderColor": "#8b949e", "lineColor": "#8b949e", "textColor": "#e6edf3", "edgeLabelBackground": "#161b22", "actorBkg": "#21262d", "actorBorder": "#8b949e", "actorTextColor": "#e6edf3", "actorLineColor": "#8b949e", "signalColor": "#8b949e", "signalTextColor": "#e6edf3", "noteBkgColor": "#373320", "noteBorderColor": "#d4a72c", "noteTextColor": "#f0e6c0", "labelBoxBkgColor": "#21262d", "labelBoxBorderColor": "#8b949e", "labelTextColor": "#e6edf3", "loopTextColor": "#e6edf3", "activationBkgColor": "#30363d", "activationBorderColor": "#8b949e"}}}%%
sequenceDiagram
participant GUI as GUI add_device
participant IPC as ipc_client poll_loop
participant Agent as AgentServer tarpc
participant PM as PairingManager
participant RA as ReceiverAccess
participant GW as GestureWatcher ticker
GUI->>IPC: Command::StartPairing
IPC->>Agent: start_pairing(selector)
Agent->>PM: start(selector)
PM->>PM: compare_exchange 0 to 1
PM->>RA: acquire_for_pairing timeout 5s
RA->>RA: "pairing_requested = true"
GW-->>RA: sees pairing_requested stops capture drops lease
RA-->>PM: PairingReceiverLease mutex held
PM->>PM: store lease send Control::Start
PM-->>Agent: Ok(())
Agent-->>IPC: Ok(Ok(()))
IPC->>IPC: pairing_command_result no update sent
Note over PM: terminal event in translate
PM->>PM: sessions fetch_sub to 0 drop PairingReceiverLease
RA->>RA: "pairing_requested = false"
GW-->>RA: acquires CaptureReceiverLease resumes
GUI->>IPC: Command::StartPairing while session active
IPC->>Agent: start_pairing
Agent->>PM: start
PM-->>Agent: Err(AlreadyActive)
Agent-->>IPC: Ok(Err(AlreadyActive))
IPC->>GUI: PairingUpdate::Failed AlreadyActive
Reviews (2): Last reviewed commit: "refactor(ipc): acknowledge pairing comma..." | Re-trigger Greptile |
8ceb181 to
ca71e57
Compare
Summary
Validation