0x9. Static Lab
بسم الله الرحمن الرحيم.
في هذا المقال، سوف نقوم بحل تحدي (Lab) بسيط يعتمد بشكل كامل على التحليل الثابت (Static Analysis). الهدف هنا هو تطبيق المفاهيم التي تعلمناها سابقاً لفك تشفير العلم (Flag) المخفي داخل البرنامج.
تجهيز بيئة العمل: يمكنك تحميل الملف التنفيذي الخاص بهذا اللاب من الرابط التالي 5t4t1c_cr4ckm3 في مستودع الدورة كلمة فك الضغط: p01nt
لفتح هذه الملف يجب عليك ان تفتحه داخل VM مع اني انا الذي صممت هذا الملف ولكن لا تثق بالمجتمع السيبراني أبدا نقوم بعمل run للملف بالامر التالي
1. الاستطلاع الأولي (Initial Triage)
بدايةً، نقوم بفتح البرنامج باستخدام أداة Detect It Easy (DIE) لنتعرف على معمارية البرنامج، لغة البرمجة، وهل هو مضغوط (Packed) أم لا.
كما نرى في الصورة، البرنامج يعمل بمعمارية 32-bit، تمت برمجته بلغة C وتم تجميعه بواسطة مترجم GCC. ونوع الملف هو تنفيذي لبيئة ويندوز (PE32)، ولا يوجد أي مؤشر على استخدام أداة ضغط (Packer).
ننتقل بعدها إلى تطبيق PE-Bear لنلقي نظرة سريعة على أقسام الترويسة (Headers). بعد التأكد من أن البرنامج من نوع EXE، نركز على قسم النصوص (Strings) والواردات (Imports) بهدف العثور على أي مؤشر واضح للـ Flag.
بعد البحث، نكتشف أن الـ Flag غير موجود كنص صريح (Plaintext)، مما يعني أنه تم تطبيق عملية إخفاء أو تشفير (Obfuscation) عليه.
2. التحليل داخل IDA Pro
الآن، نقوم بفتح الملف التنفيذي داخل برنامج IDA Pro للبدء في تحليل الكود. سيتعرف البرنامج تلقائياً على معمارية الملف ويقوم بتفكيكه.
استخراج النصوص (Strings)
نبدأ بالبحث عن أي رسائل تفاعلية تساعدنا في تحديد مكان منطق التحقق (Verification Logic). نضغط على الاختصار Shift + F12 لفتح نافذة النصوص (Strings Window)، ونبحث عن الجملة التي تظهر عند إدخال حل صحيح (أو رسالة الخطأ).
نقوم بالنقر المزدوج على الجملة المطلوبة، ليأخذنا IDA إلى مكان تخزين هذا النص في قسم البيانات (.rdata أو .data).
تتبع المراجع (Cross-References)
لمعرفة أين يتم استخدام هذا النص في الكود، ننقر عليه، ثم نضغط على الاختصار X (أو ننقر نقراً مزدوجاً على التعليق الجانبي المؤدي للدالة). سيتم نقلنا مباشرة إلى الدالة التي تستدعي هذه الرسالة.
الآن نحن في الـ Visual Mode. تذكر أنه يمكنك التنقل بين وضع المخطط البياني (Graph View) ووضع النص المتسلسل (Text View) بالضغط على زر Space. في حالتنا، نريد البقاء في الـ Graph View لتتبع مسار البرنامج والشروط (Branches) بوضوح.
3. تحليل خوارزمية التحقق (Algorithm Analysis)
نقوم بتكبير المخطط البياني للتركيز على كتلة الأوامر (Basic Block) التي تسبق رسالة النجاح لنحاول فهم المنطق البرمجي.
نقوم بالنقر على الدالة مرتين
أ) التحقق من الطول (Length Check)
إذا ركزنا على تعليمة المقارنة cmp، نلاحظ أنه يسبقها استدعاء لدالة strlen (والتي تقوم بحساب طول النص المُدخل). يتم مقارنة الناتج مع القيمة 0Bh (وهي تعادل الرقم 11 بالنظام العشري).
- الاستنتاج الأول: الـ Flag الصحيح يجب أن يتكون من 11 محرفاً (Characters).
ب) حلقة التشفير (Encryption Loop)
نتتبع مسار البرنامج لنصل إلى حلقة التكرار (Loop) التالية:
نلاحظ بوضوح وجود تعليمة xor تُنفذ باستخدام القيمة الثابتة 5Ah (أو 0x5A).
- الاستنتاج الثاني: الـ Flag مكون من 11 محرفاً، وتم تشفيره بعملية
XORبسيطة باستخدام المفتاح0x5A.
ج) استخراج القيم المشفرة
لمعرفة المحارف الأصلية، يجب أن نرى ما الذي تتم مقارنته داخل اللوب. نلاحظ وجود تعليمة cmp تقارن بين مسجلين: eax و edx.
- المسجل
edxيحمل المحارف التي أدخلها المستخدم. - المسجل
eaxيحمل محارف الـ Flag المشفرة التي يجلبها البرنامج من الذاكرة (تحديداً من العنوانbyte_407070).
ننقر نقرة واحدة على العنوان byte_407070 ونضغط على زر المراجع X.
تظهر لنا نافذة المراجع. ندقق في عمود النوع (Type) ونختار المرجع الذي يحمل الحرف w (والذي يرمز إلى Write، أي المكان الذي يتم فيه كتابة/تخزين هذه القيم في الذاكرة)، ثم نضغط OK.
الآن تظهر لنا سلسلة القيم المشفرة المخزنة في الذاكرة (كمصفوفة من البايتات)، ويقوم IDA مشكوراً بإظهار التعليقات المرافقة لها. اكتملت المعادلة الآن!
4. كتابة سكريبت فك التشفير (Decryption Script)
لدينا الآن مصفوفة من 11 محرفاً مشفراً، ومفتاح التشفير هو 0x5A. بما أن خوارزمية XOR قابلة للانعكاس (أي أن تشفير النص المشفر بنفس المفتاح يعطينا النص الأصلي)، سنقوم بكتابة سكريبت بسيط بلغة Python لفك التشفير واستخراج الـ Flag.
1
2
3
4
5
6
7
8
9
10
# مصفوفة القيم المشفرة التي استخرجناها من IDA
encrypted_hex = [0x29, 0x2e, 0x6a, 0x28, 0x37, 0x1a, 0x29, 0x32, 0x69, 0x36, 0x36]
# مفتاح التشفير (XOR Key)
key = 0x5A
# فك التشفير عبر Loop يأخذ كل محرف (بايت)، يطبق عليه XOR مع المفتاح، ثم يحوله إلى نص
flag = "".join([chr(b ^ key) for b in encrypted_hex])
print(f"The Flag is: {flag}")
عند تنفيذ هذا الكود، ستكون المخرجات كالتالي:
The Flag is: st0rm@sh3ll
5. التجربة والتأكيد (Verification)
للتأكد من صحة الحل، نقوم بتشغيل البرنامج وإدخال الـ Flag الذي حصلنا عليه:
تظهر لنا رسالة النجاح. لقد قمنا بتحليل الملف ثابتًا، وفهمنا الخوارزمية، وقمنا بفك التشفير بنجاح!












