
kasld v0.4.0
يقوم KASLD بإزالة العشوائية من تخطيط الذاكرة الافتراضية والفيزيائية لنواة Linux من عملية محلية، باستخدام ما تسمح به وجهة نظره — من صلاحيات وتكوين وحصر.
يستعيد KASLD التخطيط الافتراضي للذاكرة في نواة لينكس — الفعلية والظاهرية — وبشكل أساسي قاعدة نص النواة — من عملية محلية. وما يمكنه استعادته هو دالة على منظور تلك العملية: امتيازاتها وقدراتها، وإعدادات النظام، وأي حجز داخل حاوية. وهو يستعيد القاعدة مباشرةً حيث يسمح تسريب أو قناة جانبية بذلك، وإلا فإنه يضيّقها إلى أصغر مجموعة من المواضع التي تدعمها الأدلة المتاحة.
يدمج محرك الاستدلال الأدلة من عشرات التقنيات المستقلة مع الثوابت المعروفة للمعمارية، فيضيّق موضع النواة إلى نافذة متبقية — تُقرَّر بعدد الخانات (slots) الباقية (المواضع التي كان يمكن لـ KASLR اختيارها) وعدد بتات العشوائية التي تمثلها: حد أعلى للحماية التي يحتفظ بها KASLR من هذا المنظور، وليس ضمانًا بأن القاعدة خارج متناول المهاجم (انظر docs/limitations.md).
غالبًا ما يكون الاستعادة الكاملة مستحيلة على هدف مُحصَّن — هدف لا ينجو فيه أي تسريب مباشر لنص النواة وتكون القنوات الجانبية التي تكشفها معماريتها ومعالجها مغلقة — لكن مجموعة القيود نادرًا ما تكون فارغة. وعلى المعماريات التي لا تحتوي على KASLR، يحدد المحرك عنوان التحميل الذي اختاره محمّل الإقلاع.
يدعم:
- x86 (i386+, amd64)
- ARM (armv6, armv7, armv8, aarch64)
- MIPS (mipsbe, mipsel, mips64, mips64el)
- PowerPC (ppc, ppcle, ppc64, ppc64le)
- RISC-V (riscv32, riscv64)
- LoongArch (loongarch64)
- s390
البدء السريع
sudo apt install libc-dev make gcc binutils git
git clone https://github.com/bcoles/kasld
cd kasld
make
./build/<arch>/kasld
دليل build/<arch>/ مكتفٍ ذاتيًا ويمكن نشره على نظام الهدف:
build/<arch>/
kasld <- run this
components/ <- leak components
إن الإعدادات المُحصَّنة (kernel.dmesg_restrict=1،
kernel.kptr_restrict=1، kernel.perf_event_paranoid=2 أو أعلى،
kernel.unprivileged_bpf_disabled=1، وتجزئة المؤشرات %pK) تضيّق مسار
أوراكل نظام الملفات، لكنها محور واحد فقط من المنظور: تقنيات القنوات الجانبية
والعشوائية الضعيفة والقدرات الممنوحة مستقلة عن هذه الإعدادات. لأغراض
الاختبار، يمكن لسكربت
extra/weaken-kernel-hardening
أن يخفف هذه الإعدادات مؤقتًا (يتطلب صلاحيات root).
مثال على المخرجات
يطبع الوضع النصي الافتراضي نظرة عامة تبدأ بالجواب:
KASLD 0.4.2-dev -- Kernel Address Space Layout Derandomization
Target: x86_64 / 7.0.0
Running 117 of 120 components (3 experimental skipped; use -x to enable)...
[####################] 100% 117/117 40.9s
1 component timed out after 30s and was killed (prefetch_directmap)
Quantity Certainty Window Candidates Grain
------------------- ---------- --------------------------------------- ---------------- -----
Virtual Image Base guaranteed 0xffffffff81000000 - 0xffffffffbd400000 483 of 512 2 MiB
Virtual Image Base likely 0xffffffff93400000 slide +0x12400000 1 2 MiB
Physical Image Base guaranteed 0x1000000 - 0x3d400000 474 2 MiB
Physical Image Base likely 0x1000000 - 0x3c29d000 474 2 MiB
Direct Map Base guaranteed 0xffff800000000000 - 0xffffa4aa80000000 37,547 1 GiB
Vmalloc Base guaranteed 0xffff898000000000 - 0xffffd6d580000000 79,191 of 79,191 1 GiB
Vmemmap Base guaranteed 0xffffa98040000000 - 0xfffffd0000000000 85,504 1 GiB
Module Region Base guaranteed 0xffffffffa0000000 - 0xffffffffff000000 389,121 4 KiB
Module Region Base likely 0xffffffffc0000000 - 0xffffffffc0400000 1,025 4 KiB
Paging Level guaranteed 48 1 of 2 -
Note: physical and virtual text randomize independently
Note: 1 sub-range excluded from the windows above; the counts
already reflect them (-v lists the ranges).
Evidence (1 finding, 2 components)
Region Position Address Sources
----------------- -------- ------------------ -------
virt kernel image base 0xffffffff93400000 2
[-v: detailed results, memory map, system info] [-H: hardening assessment]
يفصل عمود Certainty بين ادعاءين مختلفين حول الكمية نفسها. الصف guaranteed
مُثبَت: القيمة الحقيقية تقع داخل تلك النافذة. أما الصف likely فهو أفضل
تقدير واحد تدعمه الأدلة — وهو دائمًا مجموعة فرعية من النافذة المضمونة، وقد
يكون خاطئًا، لأنه يعتمد على إشارات دون حد المتانة مثل قنوات التوقيت الجانبية.
والنتيجة الجديرة بالتصرف المباشر هي صف guaranteed مُضيَّق إلى مرشح واحد؛ أما
قيمة likely فهي خيط للتحقق، وليست حقيقة يُعتمد عليها.
يضيف -v القراءة المطوَّلة الكاملة (اللافتة، كتلة إعدادات النظام، سجلات كل
مكوّن، تحليل KASLR، خرائط تخطيط الذاكرة). ويُخرج -j ملف JSON قابلًا للقراءة
آليًا — العرض المنظم الكامل، متضمنًا دائمًا سجلات كل مكوّن وتقييم التحصين.
ويُخرج -1 سطرًا واحدًا قابلًا للتمرير عبر الأنابيب في الصدفة. ويُنسّق -m
لأجل متتبعات المشكلات. ويضيف -H تقييم التحصين إلى تقارير النص/Markdown.
انظر docs/usage.md للاطلاع على واجهة سطر الأوامر الكاملة، وتفاصيل أوضاع المخرجات، ووضع الشرح، وتقييم التحصين.
المنظور
يعتمد ما يمكن لـ KASLD استعادته على منظور العملية الجارية — وهو ليس مستوى امتياز واحدًا، بل مزيج من ثلاثة أمور مستقلة:
- الامتيازات والمجموعات والقدرات — معرّف مستخدم غير مميز، أو عضوية في
مجموعة مثل
adm(التي تمنح سجلات النواة تحت/var/log/)، أو مهمة حاوية تحمل قدرة إضافية، أو root. وهذه لا تشكّل سلّمًا واحدًا، لأن أذونات نظام الملفات تُبوّب كل مصدر بشكل مستقل: فحاوية مُنحتCAP_SYS_RAWIOتكون root في نطاق الاسم الأولي (init namespace) بالنسبة لذلك الفحص ويمكنها قراءة/proc/kcore— وهو تسريب لا يستطيع مستخدم عادي الوصول إليه — بينما تختلف التوزيعات حول ما إذا كان ملف مثل/boot/System.mapمقروءًا للجميع أصلًا. - إعدادات النظام —
kptr_restrict،dmesg_restrict،perf_event_paranoid، BPF غير المميز، قفل النواة (kernel lockdown). والإعدادات مستقلة عن الامتياز: فلا يستطيع root قراءة/proc/kallsymsتحتkptr_restrict=2، بينما قد يمنح sysctl مخفف أو BPF غير مميز مستخدمًا عاديًا تسريبًا كان نظام مُحصَّن سيمنعه. - الحجز (Confinement) — نطاق أسماء (namespace) أو صندوق رملي seccomp
يحجب أوراكل
/procأو يحظر استدعاءات النظام، فيضيّق ما يلاحظه أي مستوى امتياز.
تُبوّب المحاور الثلاثة كل مصدر تسريب بشكل مستقل — لذا فإن امتيازًا أكبر ليس مجموعة شاملة لما هو أقل: فالإعدادات قد تحجب مصدرًا عن root، والقنوات الجانبية تتجاوز إعدادات sysctl بالكامل. يحتوي docs/usage.md على مصفوفة تربط كل مصدر تسريب بالبوابة التي تتحكم به.