mfc entries kmalloc without M_ZERO only [0 numvifs) of mfc_ttls/mfc_flags initialized later add_vif exposes uninitialized heap bytes via forwarding decisions
Summary
Both mfc allocation sites use kmalloc no M_ZERO then init_mfc_params/update_mfc_params only initialize mfc_ttls[i]/mfc_flags[i] for i in [0 numvifs). If numvifs later grows (add_vif :853) new vif slots in every existing mfc remain uninitialized heap data. ip_mdq reads them (:1569) to decide whether to forward. Non-zero garbage with ip_ttl>garbage causes multicast replicated onto unauthorized vif. Weak byte-is-nonzero oracle into prior kernel heap. Root-only multicast routing daemon. [VERIFIED pass2: not reproduced in budget - mechanism code-certain kmalloc no M_ZERO with growth and ip_mdq read, full MRTsockopt control-plane succeeded but forwarding oracle stayed 0; M_ZERO fix in combined kernel]
Discussion (0)
PoC verification
Evidence pack
findings/poc/DF-2542 Β· 2 files| File | Type | Description | Size | |
|---|---|---|---|---|
| mroute2542.c | β | 6.8 KB | view raw | |
| run.log | β | 861 B | view raw |
Fix verification
not_testableConfirmed kernel references
Detail
Evidence (decisive lines)
mroute2542_run.log: full control-plane sequence (all sockopts 0); forwarding oracle delta +0
PoC changes
real-API rig (MRT_* sockopts + SIOCGETVIFCNT); data-plane injection added; grooming via freed MFC slot
Verified recommended fix
allocate mfcs with M_ZERO (included in the combined fix kernel)
Verdict
The allocation and partial-initialization mechanics are confirmed in source: both mfc allocations use kmalloc without M_ZERO (ip_mroute.c:1056/1061), update_mfc_params initializes mfc_ttls/mfc_flags only for i<numvifs (:934), add_vif grows numvifs without touching existing mfcs (:853), and ip_mdq reads the stale slots (:1569). The control-plane rig (MRT_INIT/MRT_ADD_VIF/groom-MFC/del-vif/re-add-vif on the real ip_mroute.ko via the real socket API) executed every step cleanly, but the data-plane forwarding oracle (SIOCGETVIFCNT delta after injecting a multicast packet for the crafted (S,G)) stayed 0 in the timeboxed runs: kernel-originated loopback multicast did not reach ip_mdq with a cache hit in this setup (cache-miss handling expects a listening multicast daemon per design). The mechanism remains code-certain; the unprivileged/reachable impact ceiling is as filed (root-configured multicast router).
No comments yet.