Commit Graph

5 Commits

Author SHA1 Message Date
b4facf04be Fix multicast storm: only re-announce on new peer, not every received packet
The announce thread was being woken (triggering a multicast send) on every
received announcement packet, including ones from already-known peers. With
two or more nodes this created a feedback loop: each incoming packet triggered
an outbound multicast which triggered another incoming packet on the peer, and
so on at full CPU/network speed.

Gate the cond_signal on is_new so we only fast-announce when a genuinely new
peer is seen. The periodic interval-based announcement continues to handle
keepalives and reconnections for existing peers.

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-03-30 04:29:50 +00:00
d6fe653a2e Fix discovery: key peers on (addr, tcp_port) not (addr, name)
Two nodes on the same host with the same name (e.g. unnamed:0) would
collide — the second announcement just updated the first entry's port.
Peer identity is addr+port; name is metadata, not identity.

Same fix applied to the self-skip check.

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-03-29 19:28:15 +00:00
62c25247ef Add protocol module, video-node binary, query/web CLI tools
- Protocol module: framed binary encoding for control requests/responses
  (ENUM_DEVICES, ENUM_CONTROLS, GET/SET_CONTROL, STREAM_OPEN/CLOSE)
- video-node: scans /dev/media* and /dev/video*, serves V4L2 device
  topology and controls over TCP; uses UDP discovery for peer announce
- query_cli: auto-discovers a node, queries devices and controls
- protocol_cli: low-level protocol frame decoder for debugging
- dev/web: Express 5 ESM web inspector — live SSE discovery picker,
  REST bridge to video-node, controls UI with sliders/selects/checkboxes
- Makefile: sequential module builds before cli/node to fix make -j races
- common.mk: add DEPFLAGS (-MMD -MP) for automatic header dependencies
- All module Makefiles: split compile/link, generate .d dependency files
- discovery: replace 100ms poll loop with pthread_cond_timedwait;
  respond to all announcements (not just new peers) for instant re-discovery
- ENUM_DEVICES response: carry device_caps (V4L2_CAP_*) per video node
  so clients can distinguish capture nodes from metadata nodes

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-03-27 01:04:56 +00:00
d6e34ed95b Trigger early announcement when a new peer is first seen
When the receive thread detects a genuinely new peer it sets
early_announce, causing the announce thread to break out of its
sleep and send immediately. The new node receives our announcement
within ~100ms rather than waiting up to interval_ms.

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-03-26 22:23:46 +00:00
fe350e531e Add discovery module: UDP multicast announcements and peer tracking
Sends 6-byte framed announcements to 224.0.0.251:5353 on startup and
every interval_ms (default 5s). Receive thread maintains a peer table
(max 64 entries); fires on_peer_found for new peers, on_peer_lost when
a peer misses timeout_intervals (default 3) consecutive intervals.

Own announcements are filtered by name+site_id. SO_REUSEADDR+REUSEPORT
allows multiple processes on the same host for testing.

discovery_cli: announce <name> <tcp_port> [flags] — prints found/lost events.

Also notes future config module in planning.md.

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-03-26 22:19:56 +00:00