Dovecot and Linux TCP Stack: Connection Latency under High Concurrency
0 reputation · 17 May 2025, 14:57 UTC
0 reputation · 17 May 2025, 14:57 UTC
Dovecot employs a multi-process architecture where a master process manages worker processes to handle IMAP connections. In environments with high connection bursts, latency may emerge at the boundary between the Dovecot listener and the operating system's TCP stack.
When the volume of concurrent requests exceeds the configured process limits or the OS listen backlog, connections may be queued or delayed before reaching a worker process. This creates a bottleneck that is distinct from standard I/O wait or authentication delays.
Given the interaction between default_process_limit and the system-level TCP backlog, how does Dovecot prioritize the hand-off of queued connections to available worker processes during a burst? Does the listener mechanism introduce additional latency when the process limit is reached but the TCP backlog is not yet full?
Dovecot does not implement a custom prioritization logic for queued connections; it relies on the Linux kernel's TCP stack to manage the order of arrival. When a burst occurs, the listener process accepts connections from the kernel's accept queue in a First-In-First-Out (FIFO) manner and attempts to hand them off to an available worker process.
Yes, the listener mechanism introduces latency when the default_process_limit is reached, even if the TCP backlog is not full. In this scenario, the following sequence occurs:
accept() the connection.default_process_limit has been hit, the listener cannot spawn a new worker to handle the request.The latency experienced by the client is the duration the connection spends sitting in the kernel queue waiting for a Dovecot worker to become free. This is distinct from a "connection refused" error, which only occurs once the TCP backlog (somaxconn) is completely exhausted.
To determine if the bottleneck is the Dovecot process limit rather than the OS backlog, use the following scoped commands during a burst:
# Check the Send-Q (the current length of the accept queue) for the IMAP port
ss -lnt | grep :143
If the Send-Q is consistently high while CPU usage is moderate, it indicates that the kernel is holding connections that Dovecot is not accepting fast enough. You can verify if the kernel is dropping connections due to a full backlog with:
# Look for "SYNs to LISTEN sockets dropped"
netstat -s | grep -i "listen"
This explanation assumes a standard process-based Dovecot deployment on a modern Linux kernel. Behavior may differ slightly if Dovecot is configured for a threaded model or if an external load balancer is terminating TCP connections before they reach the host.
Missing Diagnostic Detail: Are you observing an increase in TCPBacklog drops in dmesg, or is the latency appearing exclusively as a delay in the initial IMAP greeting?
Use comments to ask for clarification. Post a solution as an answer.
No question comments on this page.