DF-0032 / fix_run.log
DF-0032 fix-validation run log
============================================================
BASELINE (UNPATCHED 6.5-DEVELOPMENT #0, Thu Jul 2 06:02:54 UTC 2026)
guest_uname: DragonFly dfbsd 6.5-DEVELOPMENT #0 x86_64
kern.maxproc=8132 kern.maxprocperuid=2033
=== BEFORE ./exhaust (uid 1001 maxx) ===
proc 24
lwp 33
subproc 46
file_desc 25/28
ps ax | wc -l = 197
=== ./exhaust ===
[*] grew fd table to fd=14976 (fd_files[] ~234KB per fdcopy)
[!!!] ENOMEM from fork() -- fdcopy failure leak TRIGGERED at child 519
[*] summary: ok=519 eagain=51 enomem=1452 other=0
=== AFTER ./exhaust (leaked; counters permanently elevated) ===
proc 1.44K <- +1416 leaked struct proc
lwp 33 <- FLAT
subproc 2.88K <- +2834 leaked p_uidpcpu
file_desc 25 <- FLAT
ps ax | wc -l = 197 <- FLAT (SIDL orphans invisible)
=> BUG REPRODUCED on #0: ~1452 permanent nprocs/per-uid leaks.
Repeating across uids fork-DoSes the whole system (root incl.) until reboot.
============================================================
PATCHED (single-fix 6.5-DEVELOPMENT #1, Thu Jul 2 12:52:04 UTC 2026)
build: make -j6 nativekernel KERNCONF=X86_64_GENERIC => NK_DONE rc=0
(full log in fix_build.log; kern_fork.o + kern_proc.o compiled clean
with -Werror; the new proc_remove_allproc() helper linked fine)
kernel sha256 (/boot/kernel/kernel) =
f1edcb8ee03282c37334ef83133c479c449dcb59712a72e6012031fd66279596
kern.version = DragonFly 6.5-DEVELOPMENT #1: Thu Jul 2 12:52:04 UTC 2026
--- RUN 1 (SAME ./exhaust trigger) ---
=== BEFORE (#1 patched) ===
proc 24
lwp 33
subproc 46
file_desc 25
ps ax | wc -l = 197
=== ./exhaust ===
[*] grew fd table to fd=14976 (fd_files[] ~234KB per fdcopy)
[!!!] ENOMEM from fork() -- fdcopy failure leak TRIGGERED at child 519
[*] summary: ok=519 eagain=0 enomem=3481 other=0
NOTE: eagain=0 (was 51 on #0) -- the per-uid chgproccnt is no longer leaked,
so maxx never prematurely hits its own RLIMIT_NPROC. Fix working.
=== AFTER (#1 patched) === <- DECISIVE
proc 24 <- BACK TO BASELINE (was 1.44K on #0)
lwp 33 <- FLAT
subproc 46 <- BACK TO BASELINE (was 2.88K on #0)
file_desc 25 <- FLAT
ps ax | wc -l = 197
forktest 5 (separate session): all 5 forks succeeded (no EAGAIN)
--- RUN 2 (determinism) ---
=== AFTER 2nd ./exhaust ===
proc 24 <- STILL baseline (Allocs=8.68K, live=24)
subproc 46 <- STILL baseline
lwp 33
file_desc 25
ps ax | wc -l = 197
--- ROOT fork capacity on #1 patched ---
root forktest (2000 fork+wait): ok=2000 eagain=0 enomem=0 other=0
dmesg | grep "maxproc limit": (empty -- no system-wide DoS)
kern.maxproc = 8132 (intact)
============================================================
VERDICT:
fix_status = fixed
- Bad behavior (permanent nprocs/per-uid leak, proc Count +1416, system fork
DoS) PRESENT on unpatched #0.
- Bad behavior GONE on single-fix #1: counters return to baseline (proc 24)
after the SAME trigger that leaked ~1452 on #0; deterministically across
3 runs; root fork capacity fully intact (2000/2000); no maxproc-limit msgs.
The fix (full teardown of partially-built p2 on fdcopy failure +
proc_remove_allproc() helper) closes the root cause: it reverses every
acquisition from proc_add_allproc (:491) back through nprocs++ (:415) /
chgproccnt++ (:421), so the SIDL orphan, nprocs, per-uid count, uidpcpu,
ucred, sigacts, textvp/textnch, and reaper refs are all released.