ktrcanset dereferences targetp->p_ucred with no token and no crhold β freed-cred read / stale-cred TOCTOU racing cratom_proc (distinct from DF-0103's p_tracenode scope)
| Field | Value |
|---|---|
| ID | DF-2868 |
| Status | new |
| Severity | Low |
| CVSS 3.1 | CVSS:3.1/AV:L/AC:H/PR:L/UI:N/S:U/C:L/I:N/A:N |
| CWE | CWE-367 / CWE-416 |
| File | sys/kern/kern_ktrace.c |
| Lines | ktrcanset (:668-684 self-grant area) |
| Area | kern |
| Confidence | speculative |
| Discovered | 2026-09-02 |
| Pass | 2 (GLM 5.3 second pass) |
| Bucket | memcorrupt |
| Reported | pending |
| Known CVE | none |
| CVE match | novel |
Summary
ktrcanset dereferences targetp->p_ucred with no token and no crhold,
racing cratom_proc's swap+crfree and the per-thread td_ucred refresh β
a freed-cred read / stale-cred TOCTOU (stale cr_uid check decides
whether the tracer may attach). Distinct from DF-0103's p_tracenode
scope. Nanosecond window; Phase V skipped (Low/speculative per
contract). Fix: take target's p_token (shared) + crhold around the
check, mirroring the pcredcache discipline.
Timeline
- 2026-09-02 Discovered during pass-2 audit of kern_ktrace.c (GLM 5.3).
Discussion (0)
PoC verification
Evidence pack
findings/poc/DF-2868 Β· 5 files| File | Type | Description | Size | |
|---|---|---|---|---|
| ktrace_race2.c | β | 1.7 KB | view raw | |
| flip.c | β | 210 B | view raw | |
| fliptarget.c | β | 160 B | view raw | |
| run.log | β | 539 B | view raw | |
| fix.diff | β | 1.5 KB | view raw |
Fix verification
not_testablep_token + crhold fix compile-validated; race not attributable at runtime (inconclusive), no differential A/B.
compile-validated in the fix-all kernel build (make nativekernel, 0 errors)
Confirmed kernel references
Detail
Exploit chain
unpriv ktrace(2) hammer vs setuid-exec cred churn: 8/1813 attaches sampled euid=0 - not attributable (skew) -> inconclusive
Evidence (decisive lines)
ktrace_race2.c + flip.c + fliptarget.c; df2868_ktrace.log: attempts=4633 ok=1813 ok_while_root=8 root_phase=61%
PoC changes
direct ktrace(2) syscall (45) + KERN_PROC_PID euid sampling; setuid flip helper installed by root as test setup
Verified recommended fix
--- sys/kern/kern_ktrace.c 2026-06-29 12:51:19.000000000 +0000
Verdict
Hammered; results are consistent with the race but cannot be attributed to it, so the honest verdict is inconclusive. ktrcanset (sys/kern/kern_ktrace.c:667-685) reads targetp->p_ucred with no token and no crhold (:671) while cratom_proc swaps and frees creds. The rig: an unprivileged target loops exec of a setuid-root helper that immediately drops back (two cred swaps per cycle, ~61% of wall time at euid=0); an unprivileged tracer hammers ktrace(2) KTROP_SET on it. Result: 4633 attempts, 1813 attaches granted, 8 of which sampled target euid=0 immediately after the granted attach. However, the euid sample happens AFTER ktrace returns, and the target flips creds on a millisecond scale, so post-check transition skew cannot be excluded; no persistent privileged-phase tracing was demonstrated (the trace was cleared immediately, and DF clears ktrace on SUGID exec). The code gap is real (getpgid-style token discipline absent); the nanosecond window is not provably hit by this rig. Fix (p_token shared + crhold around the check) compile-validated.
No comments yet.