Summary
CVE-2026-42530 is a use-after-free in NGINX Open Source’s HTTP/3 stack
(ngx_http_v3_module). When NGINX is configured to serve HTTP/3 over QUIC, a
remote, unauthenticated client can craft an HTTP/3 session that reopens a
QPACK encoder stream. NGINX does not expect that stream to be reopened, and
the resulting object lifetime confusion lets a freed structure be referenced
again inside the worker process.
In the common case the bug crashes the affected NGINX worker, which the master process then restarts — a remote denial-of-service against the data plane. On builds where Address Space Layout Randomization (ASLR) is disabled, or where an attacker can otherwise bypass ASLR, the use-after-free can be steered toward remote code execution in the worker context.
This is strictly a data plane issue: there is no control plane exposure.
Impact & exploitability
The attacker model is the strongest one a network service can have — a remote, unauthenticated peer that merely needs to speak HTTP/3 to a vulnerable listener:
- Attacker model: remote, unauthenticated client over HTTP/3 / QUIC
- Precondition: NGINX built and configured with HTTP/3 enabled (a
listendirective carryingquic) - Primitive: use-after-free in the QPACK encoder-stream handling path
- Baseline impact: worker crash and restart → remote denial of service
- Escalated impact: code execution in the worker process when ASLR is disabled or bypassed
F5, the assigning CNA, rates the issue Critical / 9.2 (CVSS v4.0) and High / 8.1 (CVSS v3.1). The “conditions beyond their control” qualifier in the advisory — and the ASLR caveat on RCE — is exactly why the v3.1 and v4.0 scores diverge: a reliable crash is straightforward, but turning it into code execution depends on the target’s memory-layout hardening.
Root cause
HTTP/3 carries its header compression state on dedicated QPACK control streams. Each direction negotiates a single QPACK encoder stream and a single QPACK decoder stream, established once per connection. The protocol treats these as long-lived, singleton unidirectional streams — they are opened once and are not meant to be re-established within the same session.
The vulnerability is a lifetime-management gap: the HTTP/3 module does not robustly reject a peer that opens a second QPACK encoder stream after one already exists for the connection. Reopening the encoder stream tears down or reinitializes state associated with the first stream while a reference to the already-released object is still reachable from the connection’s HTTP/3 context. A subsequent operation on that dangling reference is the use-after-free.
Conceptually, the unsafe shape is “trust that a per-connection singleton stream is created exactly once,” without a guard that fails the connection when the peer violates that assumption:
peer opens QPACK encoder stream ──▶ v3 module allocates encoder state (A)peer opens QPACK encoder stream ──▶ module re-handles "new" encoder stream, releasing/replacing state (A)later frame references the old ──▶ use-after-free on freed object (A)encoder-stream objectThe fix tightens this path so that an attempt to reopen an already-established QPACK encoder stream is treated as a connection error rather than silently re-running first-time setup against live state.
QPACK encoder/decoder streams are per-connection control channels. Allowing a second one to be “opened” is not a benign duplicate — it re-enters initialization logic that assumes a clean slate, which is what frees the object the connection still points at.
Reproducer
Nebula Security will release the PoC around 1 month after the disclosure.
Exploit
Nebula Security will release the exploit around 1 month after the disclosure.
Patch
The issue is fixed in NGINX Open Source 1.31.2. The affected window is the
1.x mainline range 1.31.0 – 1.31.1, all of which ship the vulnerable
ngx_http_v3_module behavior.
Upgrading to 1.31.2 (or later) is the complete remedy. Products that bundle NGINX Open Source inherit the same exposure through their base components; per F5’s advisory the following were evaluated as carrying the vulnerable code with no fix candidate of their own at publication time:
- NGINX Instance Manager 2.17.0 – 2.22.0
- NGINX Gateway Fabric 2.0.0 – 2.6.3 and 1.3.0 – 1.6.2
- NGINX Ingress Controller 5.0.0 – 5.5.0, 4.0.0 – 4.0.1, and 3.5.0 – 3.7.2
For those, the practical fix is to move to a build that incorporates NGINX OSS 1.31.2+, or apply the HTTP/3 mitigation below in the interim.
Mitigation
If you cannot immediately upgrade to NGINX OSS 1.31.2, disable HTTP/3:
# Remove `quic` from every listen directive so the HTTP/3 path is not reachable.# Before (vulnerable surface exposed):listen 443 quic reuseport;listen 443 ssl;
# After (HTTP/3 disabled; HTTP/2 + HTTP/1.1 over TLS still served):listen 443 ssl;Because the bug lives entirely in the HTTP/3 / QUIC code path, removing quic
from all listen directives closes the attack surface completely. Servers that
were never built with HTTP/3, or that do not enable it, are not exposed.
There is no control plane component to this vulnerability and no need to rotate credentials or certificates; the only actions required are patching or disabling HTTP/3.
Timeline & credit
The issue was reported to F5/NGINX under coordinated disclosure, confirmed,
fixed in NGINX Open Source 1.31.2, and published as CVE-2026-42530 (F5 ID
NPS-8), classified as CWE-416: Use After Free.
This vulnerability was autonomously discovered by VEGA agent.