مختبر تحقق Docker و Python PoC لـ CVE-2026-89274، يثبت تنفيذ shortcode عشوائي في WP Recipe Maker <= 10.8.1 عبر rating-comment reviewBody.
مواد بحث أمني لإعادة إنتاج والتحقق من CVE-2026-89274: يقوم WP Recipe Maker <= 10.8.1 بتنفيذ شورت كودات ووردبريس المسجلة التعسفية داخل بيانات JSON-LD الوصفية للوصفة، المزروعة عبر تعليق تقييم معتمد.
do_shortcode_safe الذي يقتصر على الإزالة)AV:N/AC:L/PR:N/UI:N/S:U/C:H/I:H/A:N) - CWE-94استخدم فقط على الأنظمة التي تملكها أو المصرح لك صراحةً باختبارها. يقوم الـ PoC بنشر تعليق تقييم واحد يحتوي على شورت كود علامة مسجل في المختبر. لا يتم استخدام أي شورت كود مدمّر ولا يتم كتابة أي شيء على القرص.
الحالة: مُثبت في المختبر المقدم.
WP Recipe Maker 10.8.1 (ووردبريس 7.1.2، نموذج بطاقة الوصفة الافتراضي):
comment posted : "[cve89274]" + wprm-comment-rating=5 on the recipe's parent post
result : JSON-LD on the rendered page contains
"reviewBody":"CVE89274-SHORTCODE-FIRED"
(marker shortcode executed server-side at render time)
10.8.2 : shortcode stripped, marker absent (patched negative control)
يوضح هذا التنفيذ من جانب الخادم لشورت كود مسجل تعسفي مع إخراج مضمّن في بيانات الصفحة الوصفية، مكشوف لكل زائر. لا يوضح تنفيذ التعليمات عن بُعد (RCE)؛ يعتمد التأثير على الشورت كودات المسجلة على الهدف (كشف المنشورات/البيانات الوصفية، الشورت كودات التي توفرها الإضافات ذات الآثار الجانبية).
تقوم WPRM_Metadata::sanitize_metadata() بتعقيم كل حقل قياسي بشكل متكرر
في مصفوفة البيانات الوصفية المنظمة للوصفة:
// includes/public/class-wprm-metadata.php:553, WP Recipe Maker 10.8.1
$sanitized = strip_shortcodes( wp_strip_all_tags( do_shortcode( $metadata ) ) );
// 10.8.2
$sanitized = strip_shortcodes( wp_strip_all_tags( WPRM_Instacart::do_shortcode_safe( $metadata ) ) );
يقوم do_shortcode() بتنفيذ الشورت كود أولاً؛ غلاف strip_shortcodes()
يزيل فقط الوسوم من الإخراج المنفذ بالفعل. أحد الحقول، reviewBody، يتم
تعبئته حرفياً من comment_content للتعليقات المعتمدة التي تحمل قيمة
وصفية wprm-comment-rating (class-wprm-metadata.php:1016)، يتم الاستعلام
عنها مقابل المنشور الأب للوصفة (post_id => $recipe->parent_post_id()،
السطر 973) - المنشور أو الصفحة التي يتم تضمين بطاقة الوصفة فيها.
البديل في 10.8.2، WPRM_Instacart::do_shortcode_safe()
(class-wprm-instacart.php:501)، يحتفظ فقط بالمحتوى الداخلي ولا ينفذ شيئاً.
[wprm-recipe])./wp-comments-post.php مع الشورت كود في النص
و wprm-comment-rating=5.review الخاصة بـ JSON-LD، ويقوم
sanitize_metadata() بتنفيذ الشورت كود. يحل إخراجه محل نص التعليق داخل
reviewBody، مرئياً لكل زائر.المتطلبات: Docker مع Compose v2، Python 3.10+ على المضيف.
./lab verify
يبني مختبر 10.8.1، يتطلب تفعيل العلامة، ثم يبني مختبر 10.8.2 ويتطلب غيابها.
أزل كل شيء باستخدام ./lab reset.
الضابط القابل للاستغلال:
[!!!] SHORTCODE EXECUTION CONFIRMED
evidence: 'CVE89274-SHORTCODE-FIRED' present in the rendered recipe page
context : ..."reviewBody":"CVE89274-SHORTCODE-FIRED","author":...
RESULT: VULNERABLE CONTROL CONFIRMED
الضابط المُصلَّح:
[=] shortcode text present but NOT executed: output was stripped
RESULT: PATCHED CONTROL CONFIRMED
وجود العلامة في الصفحة فقط داخل التعليق المعروض (نص خام) لا يُقبل كدليل؛ يجب أن تظهر العلامة كمخرجات منفذة في البيانات الوصفية.
./lab start vulnerable # 10.8.1 lab on http://127.0.0.1:9482
./lab test # assert marker fires
./lab start patched # 10.8.2 lab
./lab test # assert absence
./lab status
./lab reset
شغّل الـ PoC يدوياً (الافتراضي هو loopback؛ الأهداف الخارجية المصرح بها تحتاج إلى التجاوز الصريح):
python3 poc/poc_cve_2026_89274.py --url http://127.0.0.1:9482 --post-id 5
python3 poc/poc_cve_2026_89274.py --url https://target.example \
--allow-authorized-non-loopback [--insecure]
قالب nuclei (nuclei/cve-2026-89274.yaml) هو فحص إصدار فقط
(وسم readme.txt المستقر <= 10.8.1). تتطلب السلسلة السلوكية إرسال تعليق
بالإضافة إلى انتقال الموافقة، وهو أمر غير عملي للتعبير عنه في nuclei؛
يقوم PoC بلغة Python بتنفيذ التدفق الكامل.
| الإصدار | التقييم |
|---|---|
| WP Recipe Maker 10.8.1 | تم إعادة إنتاج تنفيذ الشورت كود من البداية إلى النهاية |
| WP Recipe Maker 10.8.2 | تم إعادة إنتاج الضابط السلبي المُصلَّح |
| WP Recipe Maker <= 10.8.0 | متأثر وفقاً للاستشارة؛ لم يُختبر بشكل فردي |
.
├── .github/workflows/validate.yml
├── .gitignore
├── LICENSE
├── README.md
├── SECURITY.md
├── docker-compose.yml
├── lab
├── nuclei/
│ └── cve-2026-89274.yaml
└── poc/
└── poc_cve_2026_89274.py
غير مُلتزم به: assets/ (ملفات zip الإضافات)، .lab-state، __pycache__/.
| الادعاء | الحالة |
|---|---|
| تنفيذ الشورت كود عبر reviewBody لتعليق التقييم | مُثبت (10.8.1) |
| إخراج التنفيذ مكشوف في JSON-LD المعروض | مُثبت |
| الضابط السلبي المُصلَّح (10.8.2) | مُثبت |
| التكوين الافتراضي (نوع منشور الوصفة الخاص + المنشور الأب) | مُثبت (هذه هي طوبولوجيا المختبر) |
| تكوين نوع منشور الوصفة العام | لم يُختبر |
| نقطة نهاية REST الخاصة بتقييم WPRM كمدخل بديل | لم يُختبر |
| التأثير بما يتجاوز إخراج الشورت كود المسجل (RCE) | غير مُدّعى |
شغّل هذا المستودع فقط على الأنظمة التي تملكها أو المصرح لك صراحةً
باختبارها. يرفض مشغّل المختبر أي متغيرات غير vulnerable/patched،
ويرفض الـ PoC الأهداف غير loopback ما لم يتم توفير
--allow-authorized-non-loopback، ومنفذ Compose مرتبط بـ 127.0.0.1.
راجع SECURITY.md للتعامل مع الإفصاح. لا يتضمن هذا المستودع أهداف إنتاج، أو بيانات عملاء، أو رموز وصول، أو أدلة من أنظمة حقيقية.
MIT - راجع LICENSE.