Forking can resend buffered memcached requests and desynchronize the parent's connection
Published: October 05, 2026
SECURITY IDENTIFIERS
- GHSA: GHSA-w39f-xq2m-4g8x
- Vendor Advisory: https://github.com/petergoldstein/dalli/security/advisories/GHSA-w39f-xq2m-4g8x
GEM
PATCHED VERSIONS
~> 3.2.13
~> 4.3.7
~> 5.0.9
~> 5.1.3
>= 5.2.1
DESCRIPTION
Dalli buffered request bytes in Ruby's IO write buffer, and quiet
(multi) blocks don't flush until they end. When the process forks,
the child inherits the buffer, and Ruby flushes it when the child closes
or finalizes the socket, even if the child never uses Dalli, so the
request is sent twice: a buffered write is applied twice, or a buffered
non-quiet request leaves the parent's connection off by one reply, so
later reads return the previous key's value. Affects 4.2.0 and later.
With TLS, the child's close sends close_notify on the shared connection and tears down the parent's session. Affects all versions with TLS.
Applications that fork while threads use a shared client are affected (pre-forking servers, job runners).
The first fix was incomplete on 4.3.6 and 3.2.12: when another library's fork hook (such as connection_pool's, loaded before Dalli) ran first in the child, the parent's TLS session could still be ended, and 4.3.6's write buffer kept a reference to the caller's value string with the meta protocol. Both are fixed in 4.3.7 and 3.2.13.
Workarounds
Call close on Dalli clients before forking, outside any quiet block.
RELATED
- https://github.com/petergoldstein/dalli/security/advisories/GHSA-w39f-xq2m-4g8x
- https://github.com/petergoldstein/dalli/commit/62d5ad1
- https://rubygems.org/gems/dalli/versions/4.3.7
- https://github.com/petergoldstein/dalli/releases/tag/v4.3.7
- https://rubygems.org/gems/dalli/versions/3.2.13
- https://github.com/petergoldstein/dalli/releases/tag/v3.2.13
- https://rubygems.org/gems/dalli/versions/5.2.1
- https://github.com/petergoldstein/dalli/releases/tag/v5.2.1
- https://rubygems.org/gems/dalli/versions/5.1.3
- https://github.com/petergoldstein/dalli/releases/tag/v5.1.3
- https://rubygems.org/gems/dalli/versions/5.0.9
- https://github.com/petergoldstein/dalli/releases/tag/v5.0.9
- https://rubygems.org/gems/dalli/versions/4.3.6
- https://github.com/petergoldstein/dalli/releases/tag/v4.3.6
- https://rubygems.org/gems/dalli/versions/3.2.12
- https://github.com/petergoldstein/dalli/releases/tag/v3.2.12
