fix(agent): bound every send so a stalled socket redials instead of waiting #34
Loading…
Reference in a new issue
No description provided.
Delete branch "fix/agent-send-timeout"
Deleting a branch is permanent. Although the deleted branch may continue to exist for a short time before it actually gets removed, it CANNOT be undone in most cases. Continue?
Why
The agent heartbeats, samples metrics and snapshots flows from one
select!loop, and every message awaits its write:When the TCP path stalls, the write stays pending while the kernel backs the retransmission timer off (0.2 s doubling to 51 s). Nothing leaves the socket, so the hub sees a silent agent and pushes a false "down", then "back online" once the timer recovers. On remote hosts this ran 40 to 110 s.
Evidence
Captured on
ewtg-prodwhile the hub had it marked down (thread dump plusss -tinat the moment the agent stopped writing):All ten agent threads idle in their normal wait states, no blocked syscalls, load 0.16, 16.6 GB free. The agent was not sampling slowly or stuck in a lock: its metrics were queued behind a write the kernel would not put on the wire.
The same host pings the hub with 0% loss but heavy jitter (max 82 to 159 ms, mdev up to 38 ms), which is what collapses
cwndto 1.What
send()now wraps the write inSEND_TIMEOUT(15 s):On expiry the error propagates through the existing
.context("sending ...")?sites, the connection is dropped, and the existing reconnect path redials with a fresh congestion window. Worst case silence falls from about two minutes to 15 s, inside the hub's 40 s presence window (10 s stale + 30 s grace). Queued payload is sampled metrics and flows, so nothing worth keeping is lost, and alerts that fail to send already behave this way on any socket error.Verification
cargo check -p agent --locked: clean.cargo test -p agent --locked: 126 + 3 + 2 pass, 0 fail.ssonce a second and dumping thread state on silence; the socket counters above are from that capture.The transport itself (bursty loss and jitter on the IPv6 path between the Contabo agents and the hub) is outside this change; the agent now survives it instead of going quiet.
View command line instructions
Checkout
From your project repository, check out a new branch and test the changes.