LKM screen-saver module unload TOCTOU: remove_scrn_saver samples scrn_blanked and clears current_saver with no syscons_lock, so kldunload can unmap the saver module (fade_saver et al.) while fade_saver is still executing β use-after-free of module text and statics
Summary
remove_scrn_saver (syscons.c:2613-2627) waits and publishes current_saver=none_saver with NO syscons_lock while every saver entry runs under it (scrn_timer) or vga_token-only (FBIO_BLANK) - kldunload winning the first-blank transition lets link_elf_unload_file unmap module text/statics while fade_saver executes (palette[768], count at :46,52). Root-gated, microsecond window, panic ceiling. QEMU-live evidence: kldload proves fade_init ran; FBIO_BLANK amplifier dead on this guest (fbi==NULL ENODEV). syscons_lock-across-wait fix (interlocked variant already exists). DISTINCT from DF-5195 (that is a vga_token sleep inversion deadlocking a blanked stop; this is an unlocked removal racing a blank START).
Discussion (0)
PoC verification
Evidence pack
findings/poc/DF-5217 Β· 1 files| File | Type | Description | Size | |
|---|---|---|---|---|
| verdict.json | file | 1.3 KB | view raw |
Fix verification
not_testableConfirmed kernel references
Detail
Evidence (decisive lines)
static trace: syscons.c:2613-2627 unlocked removal vs 2226-2230/2633-2636 locked entry; link_elf.c:665 unmap
Verified recommended fix
hold syscons_lock across wait_scrn_saver_stop + current_saver publication in remove_scrn_saver; wrap sc_*_scrn_saver in syscons_lock (order syscons_lock->vga_token)
Verdict
untested (Low, root-gated timing race; Phase V skipped per contract; kldload liveness evidence in reviewer notes)
No comments yet.