A 9.8 Linux kernel flaw in the TCP handshake is fixed upstream and in Debian, while Ubuntu and RHEL kernels are still on the way. One tested firewall rule closes the gap today. Here is how to check your servers, apply it and remove it after the patch.
On October 15, 2026, the Linux kernel team published CVE-2026-98432, a use-after-free in the code that handles the start of every IPv4 TCP connection. The kernel's own scoring puts it at 9.8, because a remote machine with no login can reach it by sending crafted connection requests to any listening service. On October 27 Anthropic described a working remote root exploit for it, written by its Claude model in a lab.
The fix is small and it has already shipped. It reached the upstream stable kernels on October 11 and 15, and Debian has packaged it. Ubuntu and Red Hat are still preparing their kernels. For servers on those systems, Red Hat has published a firewall rule that removes the way in until the new kernel arrives. We tested it before writing this, and it does exactly what it says.
Where the Fix Stands on November 2
| Platform | Status | Fixed in |
|---|---|---|
| Upstream stable kernels | Fixed | 7.2.10, 6.18.56, 6.12.113, 6.6.159, 6.1.190, 5.15.223, 5.10.272 |
| Debian 13 trixie | Fixed, DSA-6568-1 | linux 6.12.113-1 |
| Debian 12 bookworm | Fixed, DLA-4841-1 and DLA-4850-1 | linux 6.1.190-1, linux-6.12 6.12.113-1~deb12u1 |
| Ubuntu 16.04 to 26.10 | Vulnerable, fix in progress | Not released yet |
| RHEL 8, 9 and 10 | Rated Critical, fix in progress | Not released yet, stopgap in RHSB-2026-016 |
Ubuntu's tracker already names the kernel builds it is preparing, for example 6.8.0-149 for 24.04 and 5.15.0-203 for 22.04, and the same work covers the AWS, Google Cloud and Azure kernels. Red Hat lists OpenShift and other products built on the RHEL kernel as potentially affected too.
There is no sign of attacks. The flaw is not in CISA's catalogue of exploited vulnerabilities, and Anthropic has not released its exploit. That leaves time to do this properly, one server group at a time.
What the Bug Is, in Plain Terms
A TCP connection starts with a short exchange. The client sends a SYN, the server answers with a SYN-ACK, and the client confirms. A SYN can carry IPv4 options such as Record Route or Timestamp, which ordinary traffic almost never uses today. When one does, the kernel keeps those options with the half-open connection.
The bug is a race. When the connection completes, the kernel hands the stored options to the new socket and later frees them. If the client sends the same SYN again at the right moment, another CPU core can still be building a SYN-ACK from those options while they are released. The kernel then reads memory it has already given back. Depending on what lands there, the result is kernel data leaking into the reply, a write outside the buffer, or a crash.
Eric Dumazet's fix waits until every reader has finished before the memory is freed. It changes two lines, one in net/ipv4/af_inet.c and one in net/ipv4/tcp_ipv4.c, and the report is credited to Xinyang Ge of Anthropic.
Two details matter for planning. The race happens inside the kernel before any application sees the connection, so every service that accepts IPv4 TCP is in scope. And a failed attempt costs the attacker nothing. Anthropic notes that a lost race only fails one handshake without crashing the server, so the attempts can simply repeat.
Why Multipath TCP Keeps Coming Up
Anthropic's exploit targeted servers with a Multipath TCP listener. MPTCP is a TCP extension that lets one connection use several network paths at once, and current distribution kernels usually ship with it built in.
Few teams ever switched it on deliberately, yet many servers use it. Since Go 1.24, the standard library's ListenConfig opens listening sockets with MPTCP by default on Linux wherever the kernel supports it. A lot of today's infrastructure software is written in Go, so a server can have MPTCP listeners without anyone choosing that. Go takes the default from the Go version a program declares in its go.mod, which means it varies from binary to binary, and the quickest way to know is to look.
Keep the order of things clear. MPTCP is the path that has been demonstrated, not the bug itself. The flaw sits in plain IPv4 TCP, so switching MPTCP off narrows the exposure without closing it. What an MPTCP check does tell you is whether a server matches the published exploit, which is useful for deciding where to start.
Check Your Servers
Start with the kernel version.
uname -r
Compare it with the table above. On Debian, the fixed packages are enough once the machine has rebooted into them. On Ubuntu and RHEL, every kernel released so far is affected.
Then see whether MPTCP is on and whether anything listens with it.
sysctl net.mptcp.enabled
ss -Mltn
A value of 1 means the kernel accepts MPTCP. If sysctl says the key does not exist, MPTCP is not built into that kernel at all. The ss -M flag lists only MPTCP sockets, so an empty table means none of your services listens with it.
Last, note which ports are open to the internet. A service reachable only on a private network is a lower priority than one on a public address.
The Stopgap That Closes the Gap
Red Hat's bulletin RHSB-2026-016 gives a short nftables rule. It drops incoming IPv4 TCP packets whose header carries options, and those options are the only way to reach the bug. A normal IPv4 header is five 32-bit words long, so a header length above five means options are present.
Save this as /etc/cve-2026-98432.nft.
table inet cve_2026_98432 {
chain input {
type filter hook input priority -310; policy accept;
ip protocol tcp ip hdrlength > 5 counter drop
}
}
Check it, load it and look at it.
sudo nft --check --file /etc/cve-2026-98432.nft
sudo nft --file /etc/cve-2026-98432.nft
sudo nft list table inet cve_2026_98432
We ran exactly this in a Debian 13 container. An ordinary SYN passed through untouched. A SYN carrying a Record Route option, sent with hping3 --rroute, was dropped, and the rule's counter showed those two packets and nothing else.
The rule lives in a table of its own and lets everything else through, so it sits alongside ufw, firewalld, Docker and Kubernetes rules without touching them. It works the same on Ubuntu, where iptables already runs on top of nftables. Legitimate TCP traffic with IP options is rare enough that most servers will never notice, but Red Hat advises trying it on one non-production machine first, and that is sound advice.
Keep It Across Reboots
A table loaded by hand is gone after a reboot. Do not persist it by enabling the stock nftables service, because the default /etc/nftables.conf begins with flush ruleset, which would wipe Docker's and Kubernetes' rules along with everything else. A small service of its own is safer.
# /etc/systemd/system/cve-2026-98432.service
[Unit]
Description=Stopgap filter for CVE-2026-98432
After=network-pre.target
Before=network.target
[Service]
Type=oneshot
RemainAfterExit=yes
ExecStartPre=-/usr/sbin/nft delete table inet cve_2026_98432
ExecStart=/usr/sbin/nft --file /etc/cve-2026-98432.nft
[Install]
WantedBy=multi-user.target
The first line of the service removes any older copy of the table, so running it twice never stacks duplicate rules.
sudo systemctl daemon-reload
sudo systemctl enable --now cve-2026-98432.service
See Who Is Knocking
The rule's counter doubles as a cheap early warning. Ordinary clients almost never send TCP with IP options, so a number that keeps rising on a public server most likely means someone is scanning for this flaw. The nft list table command above shows it at any time.
To see where those packets come from, put a rate-limited log line in front of the drop.
table inet cve_2026_98432 {
chain input {
type filter hook input priority -310; policy accept;
ip protocol tcp ip hdrlength > 5 limit rate 5/minute counter log prefix "cve-2026-98432 "
ip protocol tcp ip hdrlength > 5 counter drop
}
}
The entries land in the kernel log, so journalctl -k | grep cve-2026-98432 lists the sending addresses. Keep the limit and the drop on separate lines, as here. Written as a single rule, the limit would cap the drop as well, and packets above the rate would get through. We checked this version in the same container, and both counters moved together.
A server that was hit before the filter went in is more likely to have crashed than to show anything subtle. An unexplained reboot, or skb_under_panic in the kernel log of the boot before it, deserves a closer look.
journalctl -k -b -1 | grep -E "skb_under_panic|Oops|BUG"
A Second Layer, If You Want One
If nothing on a server needs MPTCP, and on most servers nothing does, switching it off removes the path Anthropic demonstrated. Go programs notice that MPTCP is unavailable and fall back to plain TCP by themselves.
echo "net.mptcp.enabled = 0" | sudo tee /etc/sysctl.d/90-disable-mptcp.conf
sudo sysctl --system
To change one Go service rather than the whole host, set GODEBUG=multipathtcp=0 in that service's environment.
Containers, Kubernetes and Load Balancers
Containers share the host's kernel. The fix and the stopgap both belong on the host or node, and rebuilding an image changes nothing for this bug.
On self-managed Kubernetes, the rule goes on every node. A configuration management run or a short Ansible play is usually simpler to apply and to undo than a privileged DaemonSet. On managed platforms the provider publishes new node images with the fixed kernel, and moving node groups onto them is usually up to you, so watch the provider's bulletin.
A proxy that ends the TCP connection, such as an HTTP load balancer or Cloudflare's proxy, opens its own connection to your server, so a client's IP options never reach you through it. Anything with a public address and an open port is still reachable directly, and that includes SSH.
When the Fixed Kernel Arrives
Install it the usual way and reboot, because a new kernel protects nothing until the machine is running it.
sudo apt update && sudo apt full-upgrade
On RHEL and its relatives the equivalent is sudo dnf update kernel. After the reboot, confirm the version with uname -r, then take the stopgap away.
sudo systemctl disable --now cve-2026-98432.service
sudo nft delete table inet cve_2026_98432
sudo rm /etc/systemd/system/cve-2026-98432.service /etc/cve-2026-98432.nft
The MPTCP setting can stay off if nothing missed it.
What This Means for Your Team
This is a serious flaw with a calm way through it. The fix exists, Debian users can patch today, and everyone else has a tested one-line filter until their kernel lands. A sensible order is public-facing servers first, then anything with an MPTCP listener, then the rest, with the filter applied as you go and removed once each machine runs the fixed kernel.
If you would rather hand the rounds over, we manage Linux servers and can check a fleet, apply the filter and roll out the kernel updates when Ubuntu and Red Hat publish them, with a scope and a price agreed before we start. For an earlier kernel flaw that needed the same kind of triage, see our note on GhostLock.
Sources
- CVE-2026-98432 record from the Linux kernel CNA
- Upstream fix, "ipv4: free inet_opt and ireq_opt after an RCU grace period"
- Linux 6.12.113 changelog
- Ubuntu security tracker, CVE-2026-98432
- Red Hat, CVE-2026-98432
- Red Hat bulletin RHSB-2026-016
- Debian security tracker, CVE-2026-98432
- Anthropic, Discovering vulnerabilities with Claude
- Go 1.24 release notes and Go GODEBUG settings
- CISA Known Exploited Vulnerabilities catalog
Or read how we handle it in Servers Management.
Related Articles
A cPanel Account With Email Access Can Reach Root, and Every Supported Version Is Affected
CVE-2026-67401 lets an authenticated cPanel account holder with mail privileges create arbitrary files and run code as root. cPanel lists all supported versions as affected and has shipped patched builds. The precondition is an ordinary customer account, which on a hosting platform anyone can buy.
SecurityThe Brotli Flaw Behind Node2Shell and How to Patch Node.js
A Brotli decoder flaw fixed on October 21 can let crafted data run code in Node.js apps that fetch remote content or inflate request bodies. How to patch.
SecurityHow to Set Up SPF, DKIM and DMARC So Mail Actually Lands
Three DNS records decide whether your invoices reach the inbox or the spam folder, and most setups have all three and still fail. The reason is alignment: DMARC does not ask whether SPF passed, it asks whether the domain SPF authenticated matches the domain in the From header. This is the working order to set them up, why SPF alone breaks the moment a message is forwarded, the ten lookup limit that silently voids your record, and how to move from p=none to p=reject without losing a week of mail.