e46a32f11e
build / build (clang / debug) (push) Waiting to run
build / build (clang / default) (push) Waiting to run
build / build (gcc / debug) (push) Waiting to run
build / build (gcc / default) (push) Waiting to run
build / sanitizers (ASan + UBSan) (push) Waiting to run
build / clang-tidy (push) Waiting to run
build / drift-check (CISA KEV + Debian tracker) (push) Waiting to run
build / static-build (push) Waiting to run
Adds the corpus's first XFS module and its first data-oriented kernel bug —
every other kernel entry corrupts memory; this one corrupts file contents.
xfs_direct_write_iomap_begin() reads the data-fork extent map under ILOCK,
then xfs_reflink_fill_cow_hole() drops ILOCK to wait for transaction log
space. On reacquiring it, the code re-queries the refcount btree at the
ORIGINAL imap->br_startblock and never re-reads the data fork. A second
O_DIRECT writer holding only IOLOCK completes a whole CoW cycle in that
window, so the first writer's stale mapping sees refcount 1, treats a
still-shared block as private, and writes to it in place — landing its data
on the reflink source file's on-disk blocks.
The primitive is an arbitrary overwrite of the on-disk contents of any
readable file, which has three consequences that drive the design:
- No offsets, no ROP, no KASLR/SMEP/SMAP; SELinux, containers and seccomp
are all irrelevant.
- The victim's inode is never written, so mtime/ctime/size never change
and nothing is logged — FIM and `-w /etc/passwd -p wa` cannot see it.
- The change persists across reboots.
Introduced 4.11 (3c68d44a2b49); fixed 2f4acd0fcd86 (mainline 7.2-rc4,
merged 2026-07-16), stable backports 7.1.4 / 6.18.39 / 6.12.96. Exposure is
distro-shaped: RHEL/CentOS/Rocky/Alma/Oracle/CloudLinux 8-10, Fedora Server
>= 31 and Amazon Linux 2023 ship XFS+reflink by default.
detect() is not a pure version gate — reachability here is safely
observable, so it pairs the backport table with a real storage precondition
(writable XFS via statfs XFS_SUPER_MAGIC, deliberately not via a successful
FICLONE since btrfs implements that too and is unaffected). --active
confirms reflink via FICLONE; SKELETONKEY_XFS_ASSUME_REFLINK=1/0 overrides.
On rpm-family hosts it warns that vendors backport without bumping the
upstream version, so the verdict speaks only to the upstream base.
exploit() forks a child that works only in a private mkdtemp scratch dir on
two files it owns: it establishes a shared extent (FICLONE, corroborated by
FIEMAP_EXTENT_SHARED) plus an O_DIRECT gate, then races a hard-bounded
8 writers / 2 helpers / 16 rounds / 2s and stops, reading the donor back
with O_DIRECT. Deliberately under-driven, and it never clones or targets a
file it does not own — the /etc/passwd overwrite -> su -> root step is
documented but NOT bundled. Always returns EXPLOIT_FAIL.
Safety rank 55, far above bad_epoll (12) and ghostlock (11): a won race
corrupts 4 KiB of our own scratch file and cannot touch kernel memory, so
there is no oops/KASAN/panic path.
Detection inverts the usual advice. auditd/sigma anchor on ioctl request
0x40049409 (FICLONE, matched exactly) and openat O_DIRECT; falco adds the
cross-uid reflink condition; and the yara rule is genuinely the right tool
here, matching the on-disk artifact because FIM is structurally blind.
VM-VERIFIED 2026-07-23 — the corpus's first rpm-family verification, taking
the empirical count to 29 of 41 CVEs. Rocky Linux 9.8 /
5.14.0-687.10.1.el9_8.0.1.x86_64 under qemu/KVM, stock GenericCloud layout
with no provisioner changes (root is XFS with reflink=1 out of the box).
detect() -> VULNERABLE, --active FICLONE witness confirmed reflink, phase A
observed FIEMAP_EXTENT_SHARED on a real shared extent, scratch self-cleaned,
clean build on el9 gcc. The underlying bug was separately confirmed winnable
on that kernel via tools/verify-vm/refluxfs_verify.c at the public PoC's
parameters (32 writers / 8 helpers, 60s): 4/4 runs won, first divergence
after 69/114/170/494 rounds. The shipped under-driven trigger did NOT win in
its 2s budget on that same vulnerable kernel — intended behaviour, and
exactly why a non-win must never be read as "patched".
14 new detect() unit rows (148 tests total, 0 failures). Bumps to v0.9.14.
Credit: Qualys Threat Research Unit (blog by Saeed Abbasi; the technical
advisory credits model-assisted kernel analysis performed with Anthropic),
and the upstream XFS maintainers who fixed it.
Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_0118iUgHY44hdRtANgyCmu7y
355 lines
30 KiB
YAML
355 lines
30 KiB
YAML
# tools/verify-vm/targets.yaml — VM verification targets per module
|
|
#
|
|
# For each module, the (box, kernel) pair the verifier should spin up to
|
|
# empirically confirm detect() + exploit() against a KNOWN-VULNERABLE
|
|
# kernel. Picked from Debian snapshot / kernel.ubuntu.com / Ubuntu HWE
|
|
# archives — every version below is fetch-able as a .deb package.
|
|
#
|
|
# Schema:
|
|
# <module_name>:
|
|
# box: vagrant box name (matches tools/verify-vm/boxes/<NAME>/)
|
|
# kernel_pkg: apt package name to install for the vulnerable kernel
|
|
# (omit / empty if the stock distro kernel is already vulnerable)
|
|
# kernel_version: expected /proc/version-style major.minor.patch
|
|
# expect_detect: what skeletonkey --explain should say on a confirmed-vulnerable
|
|
# target. One of: VULNERABLE | OK | PRECOND_FAIL.
|
|
# notes: short rationale for the target choice.
|
|
#
|
|
# Boxes available (matches tools/verify-vm/boxes/):
|
|
# debian11 — Debian 11 bullseye (5.10.0 stock)
|
|
# debian12 — Debian 12 bookworm (6.1.0 stock)
|
|
# ubuntu1804 — Ubuntu 18.04 LTS (4.15.0 stock; HWE up to 5.4)
|
|
# ubuntu2004 — Ubuntu 20.04 LTS (5.4.0 stock; HWE up to 5.15)
|
|
# ubuntu2204 — Ubuntu 22.04 LTS (5.15.0 stock; HWE up to 6.5)
|
|
#
|
|
# Adding a new target: pick the oldest LTS box whose stock or HWE kernel
|
|
# is below the module's kernel_range fix threshold; if no LTS works,
|
|
# install a pinned kernel from kernel.ubuntu.com / snapshot.debian.org
|
|
# via the kernel_pkg field.
|
|
#
|
|
# Modules where no fully-automatic vulnerable target exists (need manual
|
|
# kernel build or a special distro variant) are marked manual: true with
|
|
# a comment explaining the constraint.
|
|
|
|
af_packet:
|
|
box: ubuntu1804
|
|
kernel_pkg: "" # stock 4.15.0-213-generic — patch backported
|
|
kernel_version: "4.15.0"
|
|
expect_detect: VULNERABLE
|
|
notes: "CVE-2017-7308; bug fixed mainline 4.10.6 + 4.9.18 backports. Ubuntu 18.04 stock kernel (4.15.0) is post-fix — detect() correctly returns OK. To validate the VULNERABLE path empirically would need a hand-built 4.4 or earlier kernel; deferred."
|
|
|
|
af_packet2:
|
|
box: ubuntu2004
|
|
kernel_pkg: linux-image-5.4.0-26-generic
|
|
kernel_version: "5.4.0-26"
|
|
expect_detect: VULNERABLE
|
|
notes: "CVE-2020-14386; fixed in 5.9 mainline + backports; 5.4.0-26 (Ubuntu 20.04 launch) is pre-fix."
|
|
|
|
af_unix_gc:
|
|
box: ubuntu2204
|
|
kernel_pkg: ""
|
|
mainline_version: "5.15.5" # kernel.ubuntu.com/mainline/v5.15.5/ — below 5.15.130 backport
|
|
kernel_version: "5.15.5"
|
|
expect_detect: VULNERABLE
|
|
notes: "CVE-2023-4622; fix mainline 6.5 + backports 5.15.130/6.1.51/etc. Mainline 5.15.5 (Nov 2021) predates all backports and any silent distro patching. Installed via kernel.ubuntu.com/mainline/v5.15.5/."
|
|
|
|
cgroup_release_agent:
|
|
box: debian11
|
|
kernel_pkg: "" # 5.10.0 stock is pre-fix (fix 5.17)
|
|
kernel_version: "5.10.0"
|
|
expect_detect: VULNERABLE
|
|
notes: "CVE-2022-0492; fix landed 5.17 mainline + 5.16.9 stable; 5.10.0 is below."
|
|
|
|
cls_route4:
|
|
box: ubuntu2004
|
|
kernel_pkg: linux-image-5.15.0-43-generic
|
|
kernel_version: "5.15.0-43"
|
|
expect_detect: VULNERABLE
|
|
notes: "CVE-2022-2588; fix landed 5.19 / backports 5.10.143 / 5.15.67; 5.15.0-43 is below."
|
|
|
|
dirty_cow:
|
|
box: ubuntu1804
|
|
kernel_pkg: "" # 4.15.0 has the COW race fix; need older kernel
|
|
kernel_version: "4.4.0"
|
|
expect_detect: VULNERABLE
|
|
notes: "CVE-2016-5195; ALL 4.4+ kernels have the fix backported. Ubuntu 18.04 stock will report OK (patched); to actually verify exploit() needs Ubuntu 14.04 / kernel ≤ 4.4.0-46. Use a custom box for that."
|
|
manual_for_exploit_verify: true
|
|
|
|
dirty_pipe:
|
|
box: ubuntu2204
|
|
kernel_pkg: "" # 22.04 stock 5.15.0-91-generic
|
|
kernel_version: "5.15.0"
|
|
expect_detect: VULNERABLE
|
|
notes: "CVE-2022-0847; introduced 5.8, fixed 5.16.11 / 5.15.25. Ubuntu 22.04 ships 5.15.0-91-generic, where uname reports '5.15.0' (below the 5.15.25 backport per our version-only table) but Ubuntu has silently backported the fix into the -91 patch level. Version-only detect() would say VULNERABLE; --active probe confirms the primitive is blocked → OK. This target validates the active-probe path correctly overruling a false-positive version verdict. (Originally pointed at Ubuntu 20.04 + pinned 5.13.0-19, but that HWE kernel is no longer in 20.04's apt archive.)"
|
|
|
|
dirtydecrypt:
|
|
box: ubuntu2204
|
|
kernel_pkg: ""
|
|
mainline_version: "6.19.7" # below the 6.19.13 backport → genuinely vulnerable
|
|
kernel_version: "6.19.7"
|
|
expect_detect: VULNERABLE
|
|
notes: "CVE-2026-31635; rxgk RESPONSE oversized auth_len. Per NVD: bug entered at 6.16.1, vulnerable through 6.18.22 / 6.19.12 / 7.0-rc7; fixed at 6.18.23 / 6.19.13 / 7.0 stable. Mainline 6.19.7 is below the .13 backport → genuinely VULNERABLE. (Earlier module code wrongly gated 'predates' on 7.0; fixed in this commit by gating on 6.16.1 + adding 6.18.23 to the backport table.)"
|
|
|
|
entrybleed:
|
|
box: ubuntu2204
|
|
kernel_pkg: "" # any KPTI-enabled x86_64 kernel
|
|
kernel_version: "5.15.0"
|
|
expect_detect: VULNERABLE
|
|
notes: "CVE-2023-0458; side-channel applies to any KPTI-on Intel x86_64 host. Stock Ubuntu 22.04 will report VULNERABLE if meltdown sysfs shows 'Mitigation: PTI'."
|
|
|
|
fragnesia:
|
|
box: ""
|
|
kernel_pkg: ""
|
|
kernel_version: ""
|
|
expect_detect: ""
|
|
manual: true
|
|
notes: "CVE-2026-46300; XFRM ESP-in-TCP bug. Fix lands at 7.0.9. Verifying VULNERABLE needs a pre-fix 7.0.x kernel. Mainline 7.0.5 was tried via Ubuntu 22.04 + kernel.ubuntu.com — fails because the 7.0.5 kernel .debs depend on the t64-transition libs (libssl3t64, libelf1t64) which only exist on Ubuntu 24.04+ / Debian 13+. No Vagrant box with Parallels provider has those libs yet. dpkg --force-depends leaves the kernel image in iHR (broken) state with no /boot/vmlinuz deposited. Resolution: wait for a Parallels-supported ubuntu2404 / debian13 box, or build one locally."
|
|
|
|
fuse_legacy:
|
|
box: debian11
|
|
kernel_pkg: "" # 5.10.0 is pre-fix (fix 5.16)
|
|
kernel_version: "5.10.0"
|
|
expect_detect: VULNERABLE
|
|
notes: "CVE-2022-0185; fix 5.16.2 mainline + 5.10.93 stable; Debian 11 stock 5.10.0 is below."
|
|
|
|
netfilter_xtcompat:
|
|
box: debian11
|
|
kernel_pkg: "" # 5.10.0 (Debian 11 stock) is pre-fix (fix 5.13 + 5.10.46)
|
|
kernel_version: "5.10.0"
|
|
expect_detect: VULNERABLE
|
|
notes: "CVE-2021-22555; 15-year-old bug; Debian 11 stock 5.10.0 below the 5.10.38 fix backport."
|
|
|
|
nf_tables:
|
|
box: ubuntu2204
|
|
kernel_pkg: ""
|
|
mainline_version: "5.15.5"
|
|
kernel_version: "5.15.5"
|
|
expect_detect: VULNERABLE
|
|
notes: "CVE-2024-1086; bug introduced 5.14; fix mainline 6.8 + 5.15.149/6.1.74 backports. Mainline 5.15.5 (Nov 2021) is well below 5.15.149 — empirically vulnerable. Installed via kernel.ubuntu.com/mainline/v5.15.5/."
|
|
|
|
nft_fwd_dup:
|
|
box: debian11
|
|
kernel_pkg: "" # 5.10.0 below the 5.10.103 backport
|
|
kernel_version: "5.10.0"
|
|
expect_detect: VULNERABLE
|
|
notes: "CVE-2022-25636; fix 5.17 mainline + 5.10.103 backport; Debian 11 stock 5.10.0 below."
|
|
|
|
nft_payload:
|
|
box: ubuntu2004
|
|
kernel_pkg: linux-image-5.15.0-43-generic
|
|
kernel_version: "5.15.0-43"
|
|
expect_detect: VULNERABLE
|
|
notes: "CVE-2023-0179; fix 6.2 mainline + 5.15.91 / 5.10.162 backports; 5.15.0-43 is below."
|
|
|
|
nft_set_uaf:
|
|
box: ubuntu2204
|
|
kernel_pkg: ""
|
|
mainline_version: "5.15.5"
|
|
kernel_version: "5.15.5"
|
|
expect_detect: VULNERABLE
|
|
notes: "CVE-2023-32233; bug introduced 5.1; fix mainline 6.4-rc4 + 6.1.27/5.15.110 backports. Mainline 5.15.5 (Nov 2021) is below 5.15.110 — empirically vulnerable. Installed via kernel.ubuntu.com/mainline/v5.15.5/."
|
|
|
|
overlayfs:
|
|
box: ubuntu2004
|
|
kernel_pkg: "" # Ubuntu-specific bug; stock 5.4 is pre-fix
|
|
kernel_version: "5.4.0"
|
|
expect_detect: VULNERABLE
|
|
notes: "CVE-2021-3493; Ubuntu-specific overlayfs userns capability injection. Stock 5.4.0 in Ubuntu 20.04 is below the fixed package."
|
|
|
|
overlayfs_setuid:
|
|
box: ubuntu2204
|
|
kernel_pkg: "" # 5.15.0 stock is pre-fix (5.15.110 backport)
|
|
kernel_version: "5.15.0"
|
|
expect_detect: VULNERABLE
|
|
notes: "CVE-2023-0386; fix 6.3 + 6.1.11 / 5.15.110 / 5.10.179; 5.15.0 stock is below."
|
|
|
|
pack2theroot:
|
|
box: debian12
|
|
kernel_pkg: "" # PackageKit-version bug, not kernel
|
|
kernel_version: "6.1.0"
|
|
expect_detect: PRECOND_FAIL
|
|
notes: "CVE-2026-41651; needs PackageKit ≤ 1.3.5 + polkit + an active D-Bus session bus. Debian 12's generic cloud image is server-oriented and does NOT install PackageKit (the bug's target daemon), so detect() correctly returns PRECOND_FAIL ('PackageKit daemon not registered on the system bus'). To validate the VULNERABLE path empirically, install packagekit in the VM before verifying ('apt install -y packagekit' + 'systemctl start packagekit'); deferred to a follow-up provisioner."
|
|
|
|
ptrace_traceme:
|
|
box: ubuntu1804
|
|
kernel_pkg: "" # 4.15.0 stock is below the 5.1.17 fix
|
|
kernel_version: "4.15.0"
|
|
expect_detect: VULNERABLE
|
|
notes: "CVE-2019-13272; fix 5.1.17 mainline; Ubuntu 18.04 stock 4.15 is below."
|
|
|
|
pwnkit:
|
|
box: ubuntu2004
|
|
kernel_pkg: "" # polkit 0.105 ships in Ubuntu 20.04 → vulnerable
|
|
kernel_version: "5.4.0"
|
|
expect_detect: VULNERABLE
|
|
notes: "CVE-2021-4034; polkit ≤ 0.120 vulnerable. Ubuntu 20.04 ships polkit 0.105."
|
|
|
|
sequoia:
|
|
box: ubuntu2004
|
|
kernel_pkg: linux-image-5.4.0-26-generic
|
|
kernel_version: "5.4.0-26"
|
|
expect_detect: VULNERABLE
|
|
notes: "CVE-2021-33909; fix 5.13.4 / 5.10.52 / 5.4.135; 5.4.0-26 is below."
|
|
|
|
stackrot:
|
|
box: ubuntu2204
|
|
kernel_pkg: ""
|
|
mainline_version: "6.1.10" # below the 6.1.37 backport
|
|
kernel_version: "6.1.10"
|
|
expect_detect: VULNERABLE
|
|
notes: "CVE-2023-3269; bug introduced 6.1; fix mainline 6.4 + 6.1.37/6.3.10 backports. Mainline 6.1.10 (Feb 2023) is below 6.1.37 — empirically vulnerable. Installed via kernel.ubuntu.com/mainline/v6.1.10/."
|
|
|
|
sudo_samedit:
|
|
box: ubuntu1804
|
|
kernel_pkg: "" # ubuntu 18.04 ships sudo 1.8.21 — vulnerable to 1.9.5p1
|
|
kernel_version: "4.15.0"
|
|
expect_detect: VULNERABLE
|
|
notes: "CVE-2021-3156; sudo 1.8.21 vulnerable; Ubuntu 18.04 ships 1.8.21p2."
|
|
|
|
sudoedit_editor:
|
|
box: ubuntu2204
|
|
kernel_pkg: "" # sudo 1.9.9 in Ubuntu 22.04 is vulnerable
|
|
kernel_version: "5.15.0"
|
|
expect_detect: PRECOND_FAIL
|
|
notes: "CVE-2023-22809; sudo ≤ 1.9.12p2 vulnerable, Ubuntu 22.04 ships 1.9.9 — version-wise vulnerable. BUT the default Vagrant 'vagrant' user has no sudoedit grant in /etc/sudoers, so detect() short-circuits to PRECOND_FAIL ('vuln version present, no grant to abuse'). This is correct and documented behaviour. To validate the VULNERABLE-by-version path empirically, provision a sudoers grant (e.g. `vagrant ALL=(ALL) sudoedit /tmp/probe`) before verifying — currently the Vagrantfile doesn't."
|
|
|
|
vmwgfx:
|
|
box: "" # vmware-guest only; no useful Vagrant box
|
|
kernel_pkg: ""
|
|
kernel_version: ""
|
|
expect_detect: PRECOND_FAIL
|
|
notes: "CVE-2023-2008; vmwgfx DRM only reachable on VMware guests. No Vagrant box; verify manually inside a VMware VM with a vulnerable kernel (e.g. Debian 11 / 5.10.0)."
|
|
manual: true
|
|
|
|
# ── v0.8.0 additions ──────────────────────────────────────────────
|
|
|
|
sudo_chwoot:
|
|
box: ubuntu2204 # 22.04 ships sudo 1.9.9 — provisioner builds 1.9.16p1 over it
|
|
kernel_pkg: "" # this bug is sudo-version-gated, not kernel
|
|
kernel_version: "5.15.0"
|
|
expect_detect: VULNERABLE
|
|
notes: "CVE-2025-32463; sudo --chroot NSS shim. Vulnerable range is sudo [1.9.14, 1.9.17p0]. provisioners/sudo_chwoot.sh builds sudo 1.9.16p1 from upstream sources into /usr/local/bin (which precedes /usr/bin in PATH so plain `sudo` resolves to the vulnerable binary)."
|
|
|
|
udisks_libblockdev:
|
|
box: debian12 # 12 ships udisks2 2.10.x + libblockdev 3.0.x — vulnerable
|
|
kernel_pkg: ""
|
|
kernel_version: "6.1.0"
|
|
expect_detect: VULNERABLE
|
|
notes: "CVE-2025-6019; udisks/libblockdev SUID-on-mount. provisioners/udisks_libblockdev.sh installs udisks2 + libblockdev-utils3 and drops a polkit rule allowing the vagrant user to invoke loop-setup/filesystem-mount — simulating the trust polkit would give a logged-in workstation user (the real-world bug-path). Without that rule, the SSH session is not 'active' per polkit and the D-Bus call short-circuits."
|
|
|
|
pintheft:
|
|
box: "" # RDS is blacklisted on every common Vagrant box's stock kernel
|
|
kernel_pkg: ""
|
|
kernel_version: ""
|
|
expect_detect: VULNERABLE
|
|
notes: "CVE-2026-43494; PinTheft. Among Vagrant-supported distros, NONE autoload the rds kernel module (Arch Linux is the only common distro that does, and there's no maintained generic/arch-linux Vagrant box). On Debian/Ubuntu/Fedora boxes the AF_RDS socket() call fails with EAFNOSUPPORT → detect correctly returns OK ('bug exists in kernel but unreachable from userland here'). Verifying the VULNERABLE path needs either an Arch box, or a custom box with the rds module pre-loaded ('modprobe rds && modprobe rds_tcp'). Deferred."
|
|
manual: true
|
|
|
|
# ── v0.9.0 additions (gap fillers 2018 / 2019 / 2020 / 2024) ──────
|
|
|
|
mutagen_astronomy:
|
|
box: ""
|
|
kernel_pkg: ""
|
|
kernel_version: ""
|
|
expect_detect: ""
|
|
manual: true
|
|
notes: "CVE-2018-14634; Qualys Mutagen Astronomy. No good Vagrant verification environment: stock Ubuntu 18.04 (4.15.0-213) returns detect()=VULNERABLE because the module's kernel_range table has no entry for the 4.15.x series (Ubuntu's HWE backports are not modeled), but the kernel IS actually patched — false-positive of the conservative module logic. Mainline 4.14.70 (target VULNERABLE kernel) panics on Ubuntu 18.04's rootfs with 'Failed to execute /init (error -8)' — kernel config mismatch (binfmt_elf as module rather than baked-in). Genuinely vulnerable verification needs a contemporary CentOS 6 / Debian 7 image with original-vintage kernel; deferred to custom-box workflow."
|
|
|
|
sudo_runas_neg1:
|
|
box: ubuntu1804 # ships sudo 1.8.21p2 (vulnerable; pre-1.8.28 fix)
|
|
kernel_pkg: ""
|
|
kernel_version: "4.15.0"
|
|
expect_detect: VULNERABLE
|
|
notes: "CVE-2019-14287; sudo Runas -u#-1. Ubuntu 18.04 ships sudo 1.8.21p2 (vulnerable). provisioners/sudo_runas_neg1.sh adds 'vagrant ALL=(ALL,!root) NOPASSWD: /bin/vi' to /etc/sudoers.d/ so find_runas_blacklist_grant() has a grant to abuse."
|
|
|
|
tioscpgrp:
|
|
box: ubuntu2004 # 5.4 stock kernels (5.4.0-26) are below the 5.4.85 backport
|
|
kernel_pkg: linux-image-5.4.0-26-generic
|
|
kernel_version: "5.4.0-26"
|
|
expect_detect: VULNERABLE
|
|
notes: "CVE-2020-29661; TTY TIOCSPGRP UAF race. Stock Ubuntu 20.04 5.4.0-26 is below the 5.4.85 LTS backport. /dev/ptmx is universally writable in CI containers. Should validate VULNERABLE."
|
|
|
|
vsock_uaf:
|
|
box: "" # vsock module typically not loaded on CI containers (no virtualization)
|
|
kernel_pkg: ""
|
|
kernel_version: ""
|
|
expect_detect: VULNERABLE
|
|
notes: "CVE-2024-50264; Pwn2Own 2024 vsock UAF. AF_VSOCK requires the vsock kernel module, which autoloads only on KVM/QEMU GUESTS. Vagrant VMs running under Parallels are themselves guests, but their guest kernel may or may not have vsock loaded depending on the Parallels host. detect correctly returns OK when AF_VSOCK is unavailable. To validate VULNERABLE, ensure the VM kernel has CONFIG_VSOCKETS + virtio-vsock loaded ('modprobe vsock_loopback' may suffice on newer kernels)."
|
|
manual: true
|
|
|
|
nft_pipapo:
|
|
box: ubuntu2204 # 5.15 stock + HWE — same pipapo set substrate as nf_tables
|
|
kernel_pkg: ""
|
|
mainline_version: "5.15.5"
|
|
kernel_version: "5.15.5"
|
|
expect_detect: VULNERABLE
|
|
notes: "CVE-2024-26581; nft_pipapo destroy-race (Notselwyn II). Same mainline 5.15.5 target as nf_tables works here — 5.15.5 is below the 5.15.149 backport. (Switched from apt-pinned 5.15.0-43 after that package was removed from Ubuntu repos.) Userns gate must be open (sysctl kernel.unprivileged_userns_clone=1)."
|
|
|
|
# ── ptrace_pidfd (CVE-2026-46333) addition ──────────────────────────
|
|
|
|
ptrace_pidfd:
|
|
box: ubuntu2204
|
|
kernel_pkg: ""
|
|
mainline_version: "5.15.5" # >5.6 (has pidfd_getfd) and below every fix backport
|
|
kernel_version: "5.15.5"
|
|
expect_detect: VULNERABLE
|
|
notes: "CVE-2026-46333; __ptrace_may_access dumpable-race credential-fd theft via pidfd_getfd. Qualys disclosure 2026-05-20, fixed 2026-05-14 mainline (Debian backports 5.10.251 / 6.1.172 / 6.12.88 / 7.0.7). Mainline 5.15.5 carries the pidfd_getfd vector (added 5.6) and is below every fix backport, so detect() returns VULNERABLE; installed via kernel.ubuntu.com/mainline/v5.15.5/ (same box/kernel as nf_tables / af_unix_gc / nft_pipapo). Brand-new addition this cycle: exploit() fires the real pidfd_getfd steal primitive and reports a captured root-owned fd, but the full target-specific root-pop is not yet VM-verified — sweep pending."
|
|
|
|
# ── sudo_host (CVE-2025-32462) addition ─────────────────────────────
|
|
|
|
sudo_host:
|
|
box: ubuntu1804 # ships sudo 1.8.21p2 — inside [1.8.8, 1.9.17p0]
|
|
kernel_pkg: ""
|
|
kernel_version: "4.15.0"
|
|
expect_detect: VULNERABLE
|
|
notes: "CVE-2025-32462; sudo -h/--host policy bypass (Stratascale, sibling of sudo_chwoot). Ubuntu 18.04 ships sudo 1.8.21p2, inside the vulnerable range [1.8.8, 1.9.17p0] (fixed 1.9.17p1), so detect() returns VULNERABLE on the version gate. Exercising exploit() empirically needs a sudoers rule scoped to a host other than the box hostname (and not ALL): provision e.g. 'vagrant fakehost = (ALL) NOPASSWD: ALL' in /etc/sudoers.d/, then 'SKELETONKEY_SUDO_HOST=fakehost skeletonkey --exploit sudo_host --i-know' pops root via 'sudo -h fakehost /bin/bash'. Brand-new addition this cycle; provisioner + sweep pending."
|
|
|
|
# ── cifswitch (CVE-2026-46243) addition ─────────────────────────────
|
|
|
|
cifswitch:
|
|
box: ubuntu2404
|
|
kernel_pkg: ""
|
|
kernel_version: "6.8.0-117-generic"
|
|
expect_detect: VULNERABLE
|
|
verified: partial # detect() + add_key primitive confirmed; full root-pop + patched-kernel discriminator pending
|
|
verified_on: "2026-06-08 — Ubuntu 24.04.4 LTS, kernel 6.8.0-117-generic, QEMU/HVF (x86_64)"
|
|
notes: "CVE-2026-46243 'CIFSwitch'; cifs.spnego key type trusts userspace-forged authority fields (Asim Manizada, 2026-05-28). Fixed 5.10.257 / 6.1.174 / 6.12.90 / 7.0.10 (Debian backports of commit 3da1fdf4efbc, mainline 7.1-rc5); a ~19-year-old bug below those. PARTIALLY VM-VERIFIED 2026-06-08 on Ubuntu 24.04.4 / 6.8.0-117 (QEMU/HVF): (1) `modprobe cifs` registers the cifs.spnego key type (dmesg 'Key type cifs.spnego registered') — cifs-utils not required to reach the primitive; (2) an INDEPENDENT python ctypes add_key('cifs.spnego', forged uid/creduid/upcall_target) was ACCEPTED (serial 374940108; a `user`-key control also accepted), and the module's own exploit() reported 'primitive CONFIRMED' (serial 294765294) then honest EXPLOIT_FAIL; (3) detect() correctly returned PRECOND_FAIL with cifs-utils absent, and VULNERABLE under SKELETONKEY_CIFS_ASSUME_PRESENT=1. STILL PENDING: (a) a PATCHED kernel (>=6.12.90 / 7.0.10) to prove add_key is REJECTED there (i.e. that the probe discriminates fixed-from-vulnerable, not merely that the key type always allows userspace creation), and (b) the full user+mount-namespace + malicious-NSS root-pop, which is not bundled. Reproduce via tools/verify-vm or the QEMU offline harness used on 2026-06-08 (cloud image + payload iso, no guest networking needed)."
|
|
|
|
# ── nft_catchall (CVE-2026-23111) addition ──────────────────────────
|
|
|
|
nft_catchall:
|
|
box: ubuntu2204
|
|
kernel_pkg: ""
|
|
mainline_version: "6.1.163" # one below the 6.1.164 backport; userns required
|
|
kernel_version: "6.1.163"
|
|
expect_detect: VULNERABLE
|
|
notes: "CVE-2026-23111; nf_tables nft_map_catchall_activate abort-path UAF (inverted '!'). Public reproduction by FuzzingLabs; fixed upstream f41c5d1, Debian backports 6.1.164 (bookworm) / 6.12.73 (trixie) / 6.18.10 (sid); 5.10/bullseye still unfixed. detect() version-gates (catch-all set elements ~5.13; thresholds 6.1.164/6.12.73/6.18.10) AND requires unprivileged user_ns clone — a vulnerable kernel with userns locked (apparmor_restrict_unprivileged_userns / sysctl 0) is PRECOND_FAIL. exploit() forks an isolated child that builds a verdict map with a catch-all GOTO element and provokes an aborting batch to drive the abort-path UAF, observes nft_chain/cg-256 slabinfo, returns EXPLOIT_FAIL (primitive-only). The per-kernel leak + R/W + modprobe_path ROP is NOT bundled, and the trigger is RECONSTRUCTED from public analysis — NOT yet VM-verified. Provisioner: ensure unprivileged userns enabled (sysctl kernel.unprivileged_userns_clone=1 / drop apparmor restriction). A KASAN kernel will oops on a real fire; sweep + trigger validation pending."
|
|
|
|
# ── bad_epoll (CVE-2026-46242) addition ─────────────────────────────
|
|
|
|
bad_epoll:
|
|
box: ubuntu2404
|
|
kernel_pkg: ""
|
|
kernel_version: "6.8.0-generic" # >= 6.4 (bug introduced 58c9b016e128) and below the 7.0.13 backport → VULNERABLE by version
|
|
expect_detect: VULNERABLE
|
|
notes: "CVE-2026-46242 'Bad Epoll'; epoll ep_remove-vs-__fput teardown race UAF (Jaeyoung Chung / J-jaeyoung kernelCTF PoC). Introduced 6.4 (58c9b016e128); fixed a6dc643c6931 (7.1-rc1), stable backport 7.0.13 (Debian forky 7.0.13-1 / sid 7.0.14-1); trixie 6.12.x still vulnerable, 6.1/5.10 not affected (code not present). detect() is a PURE version gate — no userns/CONFIG probe, because epoll is reachable by every unprivileged user; on Ubuntu 24.04 stock 6.8.0 (in [6.4, 7.0.13)) it returns VULNERABLE. To also confirm the PATCHED verdict, boot a >= 7.0.13 / 7.1 kernel and expect OK. exploit() forks a CPU-pinned child that builds the epoll race pair (waiter eventpoll watching a target eventpoll) and exercises the ep_remove-vs-__fput concurrent-close window a HARD-BOUNDED 48 attempts / 2s, widening it with close(dup()) false-sharing storms, snapshots the eventpoll/kmalloc-192 slab, and returns EXPLOIT_FAIL. DELIBERATELY UNDER-DRIVEN: a won race frees a live struct eventpoll (real corruption that rarely trips KASAN → possible SILENT destabilisation on a vulnerable host), so the module does NOT grind the race to a win, does NOT perform the cross-cache reclaim, and does NOT bundle the /proc/self/fdinfo arb-read + ROP root-pop. Trigger RECONSTRUCTED from the public kernelCTF PoC — NOT VM-verified. Lowest --auto safety rank (12). Provisioner caution: run only in a throwaway VM/snapshot — even the bounded trigger can, on a rare win, corrupt or panic a vulnerable kernel. Detection is intentionally weak (epoll syscalls ubiquitous); no yara. Sweep + trigger validation pending."
|
|
|
|
# ── refluxfs (CVE-2026-64600) addition ──────────────────────────────
|
|
|
|
refluxfs:
|
|
box: rocky9-genericcloud # NOT a Vagrant box — Rocky-9-GenericCloud-Base.latest.x86_64.qcow2 booted under qemu/KVM
|
|
kernel_pkg: "" # stock 5.14.0-687.10.1.el9_8.0.1 — below every backport entry (6.12.96/6.18.39/7.1.4) → VULNERABLE by version
|
|
kernel_version: "5.14.0"
|
|
expect_detect: VULNERABLE
|
|
verified: "2026-07-23 — CONFIRMED on Rocky Linux 9.8 / 5.14.0-687.10.1.el9_8.0.1.x86_64, qemu/KVM, 6 vCPUs. The corpus's FIRST rpm-family verification. Stock GenericCloud layout needed NO provisioner changes: root is /dev/vda4 XFS with reflink=1 out of the box, which is exactly why this CVE hits the RHEL family so broadly. Results: detect() -> VULNERABLE (found writable XFS at /var/tmp); the rpm-family vendor-backport caveat fired correctly; `--active` FICLONE witness -> reflink CONFIRMED; phase A observed FIEMAP_EXTENT_SHARED on a real shared extent (note: btrfs never reported that flag during host-side testing, XFS does — which is why the module treats FICLONE success, not FIEMAP, as the authoritative gate); O_DIRECT available; scratch dir self-cleaned with no artifacts; the source also built clean on el9 gcc. The SHIPPED trigger (8 writers / 2 helpers / 16 rounds / 2s) ran and did NOT win — that is INTENDED under-driving, not a defect. THE UNDERLYING BUG WAS SEPARATELY CONFIRMED WINNABLE on this kernel via the VM-only harness tools/verify-vm/refluxfs_verify.c, driven at the public PoC's parameters (32 writers / 8 helpers, 60s budget): 4/4 runs won, first divergence after 69, 114, 170 and 494 rounds — a racing O_DIRECT write landed on a still-shared block and rewrote the donor's on-disk bytes, i.e. the arbitrary-overwrite primitive observed directly, contained to files the test user owned. No oops, no dmesg output, no instability — consistent with a data-oriented bug. Takeaway for future sweeps: a non-win from the shipped trigger must NEVER be recorded as 'patched'; trust the version gate and the vendor erratum."
|
|
notes: "CVE-2026-64600 'RefluXFS'; XFS reflink CoW ILOCK-cycling TOCTOU race (Qualys TRU, Saeed Abbasi; advisory credits model-assisted analysis with Anthropic; video PoC on RHEL 10.2). Introduced 4.11 (3c68d44a2b49, direct-I/O CoW alloc in iomap_begin); fixed 2f4acd0fcd86 (mainline 7.2-rc4, merged 2026-07-16), stable backports 7.1.4 / 6.18.39 / 6.12.96; the 6.6/6.1/5.15/5.14/5.10/4.19/4.18 lines have no upstream stable fix. PROVISIONER REQUIREMENT — unlike every other module in this matrix, detect() has a STORAGE precondition, and all five boxes here are Debian/Ubuntu with ext4 roots, so a stock box correctly returns PRECOND_FAIL. To exercise the VULNERABLE path the provisioner must create a reflink-enabled XFS volume the unprivileged user can write to, e.g.: `truncate -s 2G /var/tmp/xfs.img && mkfs.xfs -m reflink=1 /var/tmp/xfs.img && mkdir -p /mnt/xfs && mount -o loop /var/tmp/xfs.img /mnt/xfs && chmod 1777 /mnt/xfs` (Ubuntu 22.04 ships xfsprogs 5.13, where reflink=1 is already the mkfs default). detect() finds it by scanning /proc/mounts for fstype xfs and confirming statfs() f_type == XFS_SUPER_MAGIC + write access — note it deliberately does NOT accept a successful FICLONE as proof, since btrfs implements FICLONE and is unaffected. Without the provisioner step, expect_detect is PRECOND_FAIL; with it, VULNERABLE. Both verdicts are worth recording. The version+precondition matrix is also covered by the 14 detect() unit rows in tests/test_detect.c (incl. 4.18/5.14 el8/el9 bases, the 6.13.0 'newer than some entries but not all' case, and the no-XFS PRECOND_FAIL row) driven via SKELETONKEY_XFS_ASSUME_REFLINK=1/0. IDEAL TARGET, NOT IN THIS MATRIX: a Rocky/Alma/CentOS Stream 9 box, where XFS+reflink is the INSTALLER default and no provisioner step is needed — that is the real affected population (RHEL/CentOS/Rocky/Alma/Oracle/CloudLinux 8-10, Fedora Server >= 31, Amazon Linux 2023) and is the reason this module ships unverified. Adding an rpm-family box to boxes/ is the follow-up. CAVEAT for any rpm-family sweep: those vendors backport WITHOUT bumping the upstream version (a patched el8 kernel still reports 4.18.0-*), so a VULNERABLE verdict there reflects the upstream base version only and must be reconciled against the RHSA/ELSA/ALSA/RLSA erratum — detect() prints that warning itself. exploit() forks a child that works ONLY inside a private mkdtemp scratch dir on two files it owns: it establishes a shared extent (FICLONE, corroborated by FIEMAP_EXTENT_SHARED) and an O_DIRECT gate, then races a HARD-BOUNDED 8 writers / 2 ftruncate+fdatasync helpers / 16 rounds / 2s and stops, reading the donor back with O_DIRECT (a buffered read would be served from the page cache the corruption bypasses) and reporting divergence honestly. DELIBERATELY UNDER-DRIVEN (public PoC uses 32 writers / 8 helpers) and it NEVER clones or targets a file it does not own — the /etc/passwd overwrite -> su -> root step persistently rewrites a system file on disk with no undo and is NOT bundled. Returns EXPLOIT_FAIL. Provisioner note — this is SAFER to run than the other reconstructed race triggers, not more dangerous: the bug corrupts file DATA, not kernel memory, so there is no oops/KASAN/panic path, and a won race damages 4 KiB of a scratch file the module then deletes. Safety rank 55. Detection: auditd/sigma anchor on ioctl request 0x40049409 (FICLONE) and openat O_DIRECT; the yara rule matches the on-disk artifact because FIM CANNOT see this attack (the write bypasses the victim inode, leaving mtime/ctime/size untouched). Sweep + trigger validation pending."
|
|
|
|
# ── ghostlock (CVE-2026-43499) addition ─────────────────────────────
|
|
|
|
ghostlock:
|
|
box: ubuntu2404
|
|
kernel_pkg: ""
|
|
kernel_version: "6.8.0-generic" # >= 2.6.39, below the on-branch fix (no 6.8 backport; not newer than all entries) → VULNERABLE by version
|
|
expect_detect: VULNERABLE
|
|
notes: "CVE-2026-43499 'GhostLock'; rtmutex/futex requeue-PI remove_waiter() stack UAF (VEGA / Nebula Security, 'IonStack part II'; public PoC in NebuSec/CyberMeowfia, Apache-2.0). Introduced 2.6.39 (PI-futex requeue); fixed 3bfdc63936dd (7.1-rc1), stable backports 7.0.4 / 6.18.27 / 6.12.86 / 6.6.140 / 6.1.175; 5.15/5.10/5.4/4.19 affected with NO upstream fix. detect() is a PURE version gate over that five-branch table — no userns/CONFIG probe (CVSS PR:L, any local user; CONFIG_FUTEX_PI assumed, near-universal); on Ubuntu 24.04 stock 6.8.0 (below the fix, not newer than all entries) it returns VULNERABLE. To also confirm the PATCHED verdict, boot a >= 7.0.4 / 6.12.86 / 6.6.140 / 6.1.175 on-branch or 7.1 kernel and expect OK; the multi-branch table is exercised by the 9 detect() unit rows in tests/test_detect.c (incl. 6.13.0 → VULNERABLE, the 'newer than some entries but not all' case). exploit() forks an isolated child that (A) deterministically confirms the -EDEADLK remove_waiter() rollback path is reachable (SAFE — without a concurrent priority walk the unwind creates no dangling pointer; validated on real hardware) and (B) exercises the actual race a HARD-BOUNDED 24 iterations / 2s with a sibling-CPU sched_setattr(SCHED_BATCH) storm on the waiter tid, then stops. DELIBERATELY UNDER-DRIVEN: does NOT widen the copy_from_user window (no memfd/PUNCH_HOLE), does NOT spray/reoccupy the freed kernel-stack frame, and does NOT bundle the KernelSnitch page leak → forged rt_mutex_waiter → fops/configfs/ashmem/pipe R/W → cred patch (Android/Pixel-specific, per-build offsets). Trigger RECONSTRUCTED from the public PoC — NOT VM-verified. Lowest --auto safety rank (11). Provisioner caution: run only in a throwaway VM/snapshot — a WON Phase-B race corrupts the kernel STACK and drives a near-arbitrary pointer write (near-certain PANIC on a vulnerable kernel). Detection has a real signature (futex requeue-PI returning EDEADLK + sibling sched_setattr(SCHED_BATCH)); no yara. Sweep + trigger validation pending."
|