Commit 2645b81
fix(dns): back off on TCP accept errors instead of spinning
When the process runs out of file descriptors, `accept()` returns EMFILE
and leaves the pending connection queued. The error arm logged and looped
straight back into `accept()`, which failed on the same connection
immediately - an unbounded hot loop.
Observed in production on a 1 OCPU host: ~1,600 error lines/second, the
container pegged at 149% CPU, and 65-72% CPU steal. TLS handshakes, the
most CPU-hungry part of the request path, went from ~90ms to 12-18
seconds, with roughly 1 in 5 connections timing out entirely. Plain HTTP
returned empty replies and sshd could not be scheduled reliably.
The spin also starved the very tasks that would have closed descriptors,
so the process could not recover on its own.
Back off 100ms after any accept error. A transient failure now costs a
brief pause rather than the CPU the server needs to recover.
Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>1 parent 394fbab commit 2645b81
1 file changed
Lines changed: 12 additions & 1 deletion
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
36 | 36 | | |
37 | 37 | | |
38 | 38 | | |
| 39 | + | |
| 40 | + | |
| 41 | + | |
| 42 | + | |
| 43 | + | |
39 | 44 | | |
40 | 45 | | |
41 | 46 | | |
| |||
173 | 178 | | |
174 | 179 | | |
175 | 180 | | |
176 | | - | |
| 181 | + | |
| 182 | + | |
| 183 | + | |
| 184 | + | |
| 185 | + | |
| 186 | + | |
| 187 | + | |
177 | 188 | | |
178 | 189 | | |
179 | 190 | | |
| |||
0 commit comments