
بحث رسالة الماجستير حول CVE-2024-30051 (Windows DWM Heap Overflow). يتميز باستغلال عالي الموثوقية مع تحسين تلقائي لرش الكومة، وتسجيل فوري، وتحليل تجريبي لمعدل النجاح. قطعة محفظة توضح استغلال ثنائي متقدم لنظام Windows، والتلاعب بتخطيط الكومة، و LPE عبر Desktop Window Manager.
تجاوز سعة المخزن المؤقت على الكومة في مدير نوافذ سطح المكتب لنظام Windows (
dwmcore.dll)
رفع الامتيازات المحلية → مستوى سلامة SYSTEM عبر عملية DWM
هدف البناء: Windows 11 22H2 (10.0.22621.3447) · التصحيح: KB5037771
يحتوي هذا المستودع على بحث رسالة الماجستير الخاص بي حول CVE-2024-30051، وهي ثغرة رفع امتيازات عالية الخطورة (CVSS 7.8) في مكتبة مدير نوافذ سطح المكتب الأساسية (dwmcore.dll).
تنشأ الثغرة من خطأ في حساب حجم القسمة الصحيحة في CCommandBuffer::Initialize. يختلف الحجم المستخدم لـ new() عن الحجم المستخدم لـ memcpy() بسبب هذا الخطأ، مما ينتج تجاوز سعة الكومة بمقدار 0x8F بايت. يؤدي الاستغلال الناجح إلى تحميل dwm.exe لمكتبة DLL يتحكم بها المهاجم، وتنفيذ كود عشوائي تحت حساب window manager\dwm-1 بمستوى سلامة SYSTEM.
| الجانب | الوصف |
|---|---|
| تحليل الفروق في التصحيح | تحليل كامل باستخدام BinDiff يحدد CCommandBuffer::Initialize كموقع الثغرة الدقيق (درجة التشابه 0.32 مقابل 0.98 عالميًا عبر 14,062 دالة متطابقة) |
| التحليل الديناميكي باستخدام WinDbg | التحقق خطوة بخطوة من جميع الخطافات الأربعة، الكتابة فوق حقل الحجم، وبناء الحمولة |
| التحليل التجريبي لرش الكومة | 50 جلسة مضبوطة عبر تكوينين للذاكرة (8,192 MB و 4,096 MB) مع اختبارات إحصائية رسمية |
| النتائج الإحصائية | اختبار Mann-Whitney U (p = 0.031) واختبار t لـ Welch (p = 0.011) يؤكدان تأثير الذاكرة؛ المتوسطات المرصودة أفضل بـ 12.9–19 مرة من التوقع النظري البالغ ~64 محاولة |
| مركزية مسار DLL الحمولة | استخراج المسار الثابت إلى ثابت المعالج المسبق #define PAYLOAD_DLL_PATH |
| تسجيل الجلسات | سجل كامل مع طابع زمني لكل جلسة يُكتب إلى %TEMP%\cve_30051_log.txt |
| التوثيق الأكاديمي | السبب الجذري، تحليل رش الكومة من 50 جلسة، والتسلسل الزمني لـ CVE |
CVE-2024-30051-Masters-Thesis/
├── README.md
├── LICENSE
├── setup.bat # Copies s11.dll to required location
│
├── exploit/
│ ├── C21.sln # Visual Studio 2022 solution
│ ├── exploit_src/
│ │ ├── c26f.vcxproj
│ │ ├── c26f.filters
│ │ └── main.cpp # Exploit — heap spray + hooking + overflow
│ └── payload/
│ ├── payload.vcxproj
│ ├── payload.vcxproj.filters
│ ├── dllmain.cpp # Payload DLL — spawns SYSTEM shell + cleanup
│ ├── framework.h
│ ├── pch.h
│ └── pch.cpp
│
└── docs/
├── screenshots/ # Patch diffing, WinDbg, and forensic captures
└── analysis/
├── 01-root-cause.md # Integer division bug in CCommandBuffer::Initialize
├── 02-heap-spray.md # 50-session empirical data and statistical findings
└── 03-timeline.md # Discovery, disclosure, and patch chronology
افتح C21.sln في Visual Studio 2022. قم ببناء مشروع payload في Release x64.
قم بتشغيل setup.bat من جذر المستودع. يقوم بنسخ s11.dll إلى C:\Users\Public\Documents\s11.dll (المسار المحدد بواسطة PAYLOAD_DLL_PATH).
⚠️ يجب أن تكون DLL في هذا المسار المحدد قبل تشغيل
C26f.exe. لن يعمل وضعها بجانب الملف التنفيذي.
قم ببناء مشروع C26f في Release x64.
x64\Release\C26f.exe
قم بتشغيله من CMD قياسي (غير مرتفع). يقوم الاستغلال بإعادة المحاولة تلقائيًا حتى 10 مرات. عند النجاح، يقوم dwm.exe بتحميل s11.dll ويُفتح CMD بمستوى سلامة SYSTEM. يتم كتابة سجل الجلسة إلى %TEMP%\cve_30051_log.txt.
#define MAX_ATTEMPTS 10 // Max auto-retry attempts per session
#define SPRAY_STEP 0x10 // Hole spacing index (1024 holes)
#define SPRAY_RANGE_START 0x3000 // Spray range start index
#define SPRAY_RANGE_END 0x7000 // Spray range end index
#define SLEEP_POST_SPRAY 0xC8 // ms wait after spray (200ms)
#define SLEEP_POST_HOLES 0xC8 // ms wait after freeing holes (200ms)
#define PAYLOAD_DLL_PATH "C:\\Users\\Public\\Documents\\s11.dll"
في CCommandBuffer::Initialize (dwmcore.dll 10.0.22621.3447)، يتم استدعاء CD2DSharedBuffer::GetBufferSize مرتين. يخضع الحجم الممرر إلى new() للقسمة الصحيحة على 0x90 قبل الضرب، بينما يستخدم memcpy() القيمة الخام:
buffer_size = GetBufferSize() → e.g. 0x23F
size_new = (0x23F / 0x90) * 0x90 = 0x1B0 ← allocated
size_memcpy = 0x23F ← copied
overflow = 0x23F - 0x1B0 = 0x8F bytes
BinDiff comparison between build 10.0.22621.3447 (vulnerable) and 10.0.22621.3593 (patched):
| المقياس | القيمة |
|---|---|
| التشابه العالمي | 0.98 |
| الثقة | 0.99 |
| الدوال المتطابقة | 14,062 (99.1%) |
تشابه CCommandBuffer::Initialize | 0.32 |
| الكتل الأساسية — النسخة الضعيفة | 4 |
| الكتل الأساسية — النسخة المُصحّحة | 20 (16 validation blocks added) |
الدرجة الشاذة 0.32 مقابل تشابه عالمي 0.98 هي التوقيع المباشر لموقع الثغرة.
1. خطاف RtlCreateHeap → التقاط مقبض كومة dwmcore
2. خطاف RtlAllocateHeap → التقاط عنوان القطعة الأساسية
3. خطاف NtDCompositionCreateChannel → التقاط MappedAddress (منطقة الذاكرة المشتركة)
4. خطاف NtDCompositionCommitChannel → الكتابة فوق حقل الحجم (0x120 → 0x23F)
حقن أوامر دفعة إضافية
5. رش الكومة بـ 0x10000 كائن CHolographicInteropTexture (الحجم=0x1B0)
6. تحرير الفجوات كل 0x10 مؤشر → إنشاء ثغرات لهبوط التجاوز
7. كتابة الحمولة في مخزن التجاوز → KCBTable+0x388 + LoadLibraryA + مسار DLL
8. تحرير جميع كائنات الرش → تشغيل التجاوز → LoadLibraryA("s11.dll")
9. يقوم dwm.exe بتحميل DLL الحمولة → يفتح CMD كسلامة SYSTEM
هل تؤثر الذاكرة المتاحة على عدد المحاولات المطلوبة لرش الكومة بنجاح؟
كتلتان كل منهما 25 جلسة. البروتوكول لكل جلسة: استعادة لقطة نظيفة بعد الإقلاع → انتظار 100 ثانية للاستقرار → تشغيل الاستغلال → تسجيل محاولة النجاح.
| الكتلة | الذاكرة | الجلسات | النجاحات | الإخفاقات |
|---|---|---|---|---|
| A | 8,192 MB | 25 | 24 | 1 |
| B | 4,096 MB | 25 | 24 | 1 |
| الكتلة | الذاكرة | متوسط المحاولات | الانحراف المعياري | فاصل الثقة 95% | العامل مقابل النظرية (64) |
|---|---|---|---|---|---|
| A | 8,192 MB | 3.375 | 1.135 | [2.896; 3.854] | ≈ 19× أسرع |
| B | 4,096 MB | 4.958 | 2.645 | [3.841; 6.076] | ≈ 12.9× أسرع |
| الاختبار | الإحصائية | القيمة p | الاستنتاج |
|---|---|---|---|
| Mann-Whitney U | U = 184.0 | p = 0.031 | يرفض H₀ |
| Welch's t-test | t(23) = −2.695 | p = 0.011 | يرفض H₀ |