At a glance
| Item | Detail |
|---|---|
| CVE | CVE-2026-111497 ("Node2Shell", also called HTTP2Shell or Broccoli2Shell) |
| Component | Google Brotli decompression library, bundled in Node.js (node:zlib) and many other runtimes |
| Bug class | Out-of-bounds write (unchecked return value in the decoder) |
| Impact | Process crash, memory disclosure, possible remote code execution |
| Severity | CVSS 9.2 (Node.js rates it High) |
| Fixed in | Node.js 22.23.4, 24.22.1, 26.12.1 · Brotli 1.0.10, 1.1.1, 1.2.1 · Bun 1.4.4 · Python Brotli 1.2.1, brotlicffi 1.2.1.0 |
| Not fixed | Node.js 20.x, 23.x, 25.x and older (end of life) |
| Disclosed | 21 October 2026 (Node.js security release) |
What is wrong
When the Brotli decoder meets a specific kind of invalid data, it treats the error as "needs more input" and keeps writing past the end of a small internal buffer. Anything that decompresses untrusted Brotli data with a vulnerable library can be crashed, and in some builds the corruption can be turned into code execution.
Who is exposed
Node.js applications
- Express 5 / body-parser 2: the
json,raw,textandurlencodedparsers decompressContent-Encoding: brrequest bodies by default. Any client can send one, with no authentication. This is the main internet-facing risk. - Code that calls
zlib.brotliDecompress()orzlib.createBrotliDecompress()on user input. - Outbound
fetch(): clients that automatically decompress Brotli responses from a malicious or compromised server. - A bare Node.js HTTP server that does not decode request bodies is not affected by default.
Beyond Node.js (anything that bundles Brotli)
- Bun (before 1.4.4), Python
Brotliandbrotlicffi, the Ruby brotli gem, Envoy, Linux distribution packages, and tools with their own copy (DuckDB, some PHP extensions,bun build --compileexecutables). - Microsoft and other vendors have shipped updates for products that embed the library.
Exploitation
- A public proof of concept appeared on 22 October.
- Researchers have seen scanners probing for hosts that decompress Brotli bodies, and at least one very large (about 23 MB) exploit request aimed at Node.js 24.22.0 on x86-64, from an address also linked to PHP2Shell exploitation.
- Reliable code execution is harder than crashing: in one test the public chain crashed the target in every attempt without a shell. Treat crashes as the likely first impact, but do not rely on that, because crashes can also write secrets into core dumps.
What to do
1. Patch
- Upgrade Node.js to 22.23.4, 24.22.1 or 26.12.1 or later. Move anything on 20.x, 23.x or 25.x to a supported line.
- Update Bun, Python
Brotli/brotlicffi, Envoy and your OS Brotli packages. - Rebuild container images, refresh lockfiles and restart processes. Version pins in Dockerfiles, CI pipelines, serverless runtimes and
.nvmrcfiles keep deploying the vulnerable build until changed.
2. If you cannot patch today
- Express / body-parser: set
inflate: falseon body parsers if you do not need compressed request bodies. They are then rejected with HTTP 415. - At the edge: block or strip inbound requests with
Content-Encoding: bron APIs that do not need them, and cap request body size at the proxy or WAF. - Restrict network access to internal Node.js services, and limit outbound connections from vulnerable hosts.
3. Detect
- Inventory: list Node.js and Bun runtimes (installed packages and running processes) and compare versions with the fixed releases. Prioritise services with listening ports reachable from the internet.
- Logs: POST requests with
Content-Encoding: brto APIs that never receive compressed bodies, unusually large compressed bodies, and requests from anode2shell-checkuser agent. - Stability: repeated worker crashes or restarts of Node.js processes (PM2, Kubernetes restarts, systemd) since 21 October.
- After a crash: restrict access to core dumps and shorten their retention, because they may contain cookies, tokens and keys. Rotate secrets on any service that crashed unexpectedly.
- Indicator (from ELLIO): source IP
94.154.43.7; exploit payload SHA-2567fcbdaaecd4419e2930927844f3b772668204737a4e7602a2290c991c93c5c4b.
How Kage can help
- Exposure check: we find internet-facing Node.js services and the other places your estate ships Brotli, including containers and third-party appliances.
- Compromise assessment: if a service crashed or was exposed, our incident response team reviews it for follow-on activity.
- Monitoring: our threat intelligence service tracks exploitation of new vulnerabilities against your sector.