Address Phase 2 Round 1 review blockers + security item:
1. Fold daemonws teardown into a single cleanup defer so the order is:
cancel heartbeat → wait hbDone → clearWSWrites → close(writes) →
wait writer. The previous LIFO defer ordering let close(writes) run
before the terminal bridge tore down, so an in-flight terminal pump
could panic on send-to-closed-channel.
2. Replace silent drop of terminal.data on a saturated daemonws writer
with real backpressure: pump uses sendWSFrameCtx (blocking with ctx
escape) and bridge.closeAll now waits for every pump goroutine to
exit before returning, giving the wakeup loop a hard barrier before
close(writes).
3. terminalUpgrader now reuses realtime.CheckOrigin instead of
CheckOrigin: true. The terminal endpoint executes shells; it must be
at least as strict as the read-only realtime WS.
Tests:
- TestTerminalBridge_DataBackpressureNoSilentDrop pins that a full
writes channel never loses bytes.
- TestTerminalBridge_TeardownDoesNotPanicOnInFlightSend mirrors the
wakeup defer sequence (closeAll → close(writes)) and asserts no panic.
Co-authored-by: multica-agent <github@multica.ai>