vfs_findname() bcmp of buflen+1 bytes can read past the NUL of kernel rodata name tables (match/no-match oracle on adjacent .rodata bytes)
Summary
vfs_findname(nm, buf, buflen) compares buflen+1 bytes via bcmp (:496). vfs_getuserstr permits embedded NULs in the user-supplied string, so a write of e.g. 'attach\0X' to /proc/<pid>/ctl makes the comparison read past the terminating NUL of the rodata entry (procfs_ctl.c ctlnames[]) and into adjacent .rodata - a boolean oracle on rodata content beyond the string; mismatch returns no data. No bytes disclosed to userspace; read cannot fault; practical effect equals invoking the matched control op legitimately. FreeBSD-parity code; hardening only. Fix: bound the comparison to strlen(nm->nm_name). [VERIFIED pass2: buflen-plus-1 bcmp over-read past rodata NUL confirmed oracle-only; strlen-bounded fix compiled]
Discussion (0)
PoC verification
Evidence pack
findings/poc/DF-3185 Β· 4 files| File | Type | Description | Size | |
|---|---|---|---|---|
| README.md | β | 230 B | β raw | |
| fix.diff | β | 512 B | view raw | |
| manifest.json | β | 322 B | view raw | |
| verdict.json | β | 1.5 KB | view raw |
DF-3185 evidence pack
What
vfs_findname bcmp of buflen+1 bytes reads past rodata NUL
Verdict
status=not_reproduced impact=none confidence=certain
See VERDICT.md for the full narrative and fix.diff for the verified fix.
Fix verification
not_testablefix.diff applied in the F40FIX verification kernel build (RC=0, zero -Werror errors); no runtime A/B for this item (line-certain hardening)
Confirmed kernel references
Detail
Evidence (decisive lines)
VERDICT.md with path:line citations; run.log where a live demo exists; fix.diff
PoC changes
n/a - oracle-only, no observable output
Verified recommended fix
require strlen(nm_name)==buflen and compare buflen bytes
Verdict
Line-accurate confirmation; no runtime demonstration attempted (the defect is a boolean oracle with no byte disclosure - practical effect equals invoking the control op). procfs_subr.c:496 compares buflen+1 bytes against nm->nm_name; with an embedded NUL in the /proc/
No comments yet.