TL;DR

Ngày 20/04/2026, Alexander Popov (@a13xp0p0v) công bố bài Some notes on the security properties of the pipe_buffer kernel object. Bốn thí nghiệm trong môi trường kernel-hack-drill chứng minh: chỉ cần ghi đè 1 trường duy nhất trong struct pipe_buffer 40 byte là đủ để có AARW (arbitrary read & write) ổn định. Bài viết cũng mổ xẻ vì sao spray pipe vượt 1,024 cái sẽ âm thầm rơi vào slab cache khác, và cách daemonize tiến trình để tránh kernel panic sau khai thác.

Có gì mới

Cộng đồng nghiên cứu kernel Linux đã dùng pipe_buffer làm target object chuẩn cho slab OOB-write và UAF từ thời Dirty Pipe (2022). Nhưng đa phần PoC trước đây phải ghi đè đồng thời ba trường page + offset + len để dựng AARW.

Popov rút gọn yêu cầu xuống 1 trường: chỉ ghi đè page, lợi dụng cơ chế cache tmp_page trong pipe_inode_info. Khi attacker viết một page đầy vào pipe, kernel cache lại trang. OOBW chèn page giả vào slot kế tiếp, attacker đọc về userspace, sửa nội dung, rồi viết lại — lần ghi sau tự động dùng trang đã bị corrupted. AARW gọn, nhanh, ít noise.

Vì sao quan trọng

Một AARW càng ít trường cần ghi đè thì càng dễ áp dụng cho các bug class khó: off-by-one, single-byte heap overflow, type confusion với delta nhỏ. Trước đây những bug này bị coi là yếu, không đủ để chọc thủng KASLR + SMEP + SMAP. Sau bài này, ngưỡng "đủ để làm AARW" xuống mức rất thấp.

Với defender, đây là lời nhắc rằng các trường tưởng read-only trong pipe_buffer vẫn là attack surface và việc tách kmalloc-cg-1k khỏi neighbour cache không đủ — cần cấu hình thêm CONFIG_RANDOM_KMALLOC_CACHES và xem xét đề xuất autoslab.

Số liệu kỹ thuật

PropertyGiá trị
struct pipe_buffer size40 byte
Pipe capacity mặc định65,536 byte = 16 page
Mảng pipe_buffer mỗi pipe16 phần tử = 640 byte
Slab cache mặc địnhkmalloc-1k / kmalloc-cg-1k
Soft limit per-user16,384 page (pipe-user-pages-soft)
Resize knobfcntl(fd, F_SETPIPE_SZ, size) — round-up power-of-two

Bốn primitive chuẩn từ corruption pipe_buffer:

  • flags → Dirty Pipe-style ghi đè file read-only (CVE-2022-0847).
  • ops → control-flow hijack trong kernelspace.
  • page + offset + len → AARW đầy đủ.
  • Partial page overwrite → PageJack / page UAF, trỏ pipe sang trang của pipe khác.

Bẫy heap-spray ít người để ý

Spray 1,024 pipe × 16 page = đúng 16,384 page — chạm trần pipe-user-pages-soft. Pipe thứ 1,025 trở đi tự co lại còn 2 × PAGE_SIZE, mảng pipe_buffer rơi vào kmalloc-96 thay vì kmalloc-1k. Exploit nào spray ngây thơ qua mốc này sẽ trượt mục tiêu mà không hiểu vì sao.

So với các kỹ thuật trước

Kỹ thuậtTrường cần ghi đèNăng lực thu được
Dirty Pipe (2022)flagsGhi đè file read-only
kCTF AARW cổ điểnpage + offset + lenAARW đầy đủ
PageJack1 byte thấp của pagePage UAF cross-pipe
Popov 2026 (Exp 2)page (1 trường)AARW đầy đủ qua tmp_page cache

Ai sẽ dùng được

  • Exploit developer viết PoC cho slab OOB-write hoặc UAF — có thêm option AARW chi phí 1 trường.
  • CTF player (kernelCTF, Pwn2Own) cần một AARW ổn định từ corruption nhỏ.
  • Defender / maintainer kernel đánh giá hardening nào thật sự bẻ được bước nào trong chain.
  • Researcher reproduce CVE-2024-50264 hoặc tìm biến thể trong môi trường kernel-hack-drill có sẵn.

Giới hạn & điều kiện áp dụng

Bài viết là research công khai, không phải 0-day. Tất cả thí nghiệm giả định attacker đã có sẵn một bug memory-corruption sát mảng pipe_buffer. Kỹ thuật bị giảm hiệu lực bởi:

  • CONFIG_RANDOM_KMALLOC_CACHES — randomise variant kmalloc-1k chứa mảng, phá xác định.
  • Đề xuất autoslab / CONFIG_KMALLOC_SPLIT_VARSIZE — tách fixed-size khỏi variable-size allocation.
  • Cgroup-accounted slab (kmalloc-cg-*) — giảm khả năng kiểm soát neighbour cross-cgroup.
  • Soft limit pipe-user-pages-soft = 16,384 — phá spray ngây thơ.

Rủi ro vận hành lớn nhất: đóng pipe đang giữ page bị corrupt sẽ trả trang đó về page allocator → kernel panic. Popov mitigate đơn giản bằng cách không close pipe và daemonize tiến trình exploit.

Tiếp theo

Popov ám chỉ sẽ tích hợp các phát hiện vào Linux Kernel Defence Map và đóng góp upstream cho hướng autoslab / random-kmalloc. Source code các thí nghiệm (drill_uaf_w_pipe_buffer.c, drill_oob_w_pipe_buffer.c) đã có trong repo kernel-hack-drill — nên đọc kèm bài viết để chạy lại trên máy ảo.

Nguồn: a13xp0p0v.github.io, kernel-hack-drill, @linkersec.