PHP Tricks
कुकीज़ का सामान्य स्थान:
यह phpMyAdmin कुकीज़ के लिए भी मान्य है।
कुकीज़:
स्थान:
PHP तुलना को बायपास करना
ढीली तुलना/टाइप जुगलिंग ( == )
यदि PHP में ==
का उपयोग किया जाता है, तो कुछ अप्रत्याशित मामलों में तुलना अपेक्षित रूप से व्यवहार नहीं करती है। इसका कारण यह है कि "==" केवल उन मूल्यों की तुलना करता है जो समान प्रकार में परिवर्तित होते हैं, यदि आप यह भी तुलना करना चाहते हैं कि तुलना किए गए डेटा का प्रकार समान है, तो आपको ===
का उपयोग करना होगा।
PHP तुलना तालिकाएँ: https://www.php.net/manual/en/types.comparisons.php
"string" == 0 -> True
एक स्ट्रिंग जो संख्या से शुरू नहीं होती है, वह संख्या के बराबर होती है"0xAAAA" == "43690" -> True
दशमलव या हेक्स प्रारूप में संख्याओं से बनी स्ट्रिंग्स अन्य संख्याओं/स्ट्रिंग्स के साथ तुलना की जा सकती हैं, यदि संख्याएँ समान थीं (स्ट्रिंग में संख्याएँ संख्याओं के रूप में व्याख्यायित की जाती हैं)"0e3264578" == 0 --> True
"0e" से शुरू होने वाली और किसी भी चीज़ के बाद आने वाली स्ट्रिंग 0 के बराबर होगी"0X3264578" == 0X --> True
"0" से शुरू होने वाली और किसी भी अक्षर (X कोई भी अक्षर हो सकता है) और उसके बाद किसी भी चीज़ के साथ आने वाली स्ट्रिंग 0 के बराबर होगी"0e12334" == "0" --> True
यह बहुत दिलचस्प है क्योंकि कुछ मामलों में आप "0" के स्ट्रिंग इनपुट और कुछ सामग्री को नियंत्रित कर सकते हैं जो हैश की जा रही है और इसकी तुलना की जा रही है। इसलिए, यदि आप एक ऐसा मान प्रदान कर सकते हैं जो "0e" से शुरू होने वाला हैश बनाए और बिना किसी अक्षर के, तो आप तुलना को बायपास कर सकते हैं। आप इस प्रारूप में पहले से हैश की गई स्ट्रिंग्स यहाँ पा सकते हैं: https://github.com/spaze/hashes"X" == 0 --> True
स्ट्रिंग में कोई भी अक्षर int 0 के बराबर होता है
अधिक जानकारी के लिए https://medium.com/swlh/php-type-juggling-vulnerabilities-3e28c4ed5c09
in_array()
टाइप जुगलिंग डिफ़ॉल्ट रूप से in_array()
फ़ंक्शन को भी प्रभावित करता है (आपको सख्त तुलना करने के लिए तीसरे तर्क को सत्य पर सेट करना होगा):
strcmp()/strcasecmp()
यदि इस फ़ंक्शन का उपयोग किसी भी प्रमाणीकरण जांच के लिए किया जाता है (जैसे पासवर्ड की जांच करना) और उपयोगकर्ता तुलना के एक पक्ष को नियंत्रित करता है, तो वह पासवर्ड के मान के रूप में एक स्ट्रिंग के बजाय एक खाली एरे भेज सकता है (https://example.com/login.php/?username=admin&password[]=
) और इस जांच को बायपास कर सकता है:
strcasecmp()
के साथ भी वही त्रुटि होती है
सख्त प्रकार जुगलिंग
यहां तक कि यदि ===
का उपयोग किया जा रहा है, तब भी ऐसी त्रुटियाँ हो सकती हैं जो तुलना को प्रकार जुगलिंग के प्रति संवेदनशील बनाती हैं। उदाहरण के लिए, यदि तुलना तुलना करने से पहले डेटा को एक अलग प्रकार के ऑब्जेक्ट में परिवर्तित कर रही है:
preg_match(/^.*/)
preg_match()
का उपयोग उपयोगकर्ता इनपुट को मान्य करने के लिए किया जा सकता है (यह जांचता है कि क्या कोई शब्द/regex ब्लैकलिस्ट से उपयोगकर्ता इनपुट में मौजूद है और यदि नहीं है, तो कोड अपनी कार्यवाही जारी रख सकता है)।
नई पंक्ति बायपास
हालांकि, जब regexppreg_match()
के प्रारंभ को सीमित किया जाता है, तो यह केवल उपयोगकर्ता इनपुट की पहली पंक्ति की जांच करता है, फिर यदि किसी तरह आप कई पंक्तियों में इनपुट भेज सकते हैं, तो आप इस जांच को बायपास करने में सक्षम हो सकते हैं। उदाहरण:
इस जांच को बायपास करने के लिए आप नए लाइनों के साथ मान को URL-encoded (%0A
) भेज सकते हैं या यदि आप JSON डेटा भेज सकते हैं, तो इसे कई लाइनों में भेजें:
Find an example here: https://ramadistra.dev/fbctf-2019-rceservice
Length error bypass
(यह बायपास स्पष्ट रूप से PHP 5.2.5 पर आजमाया गया था और मैं इसे PHP 7.3.15 पर काम नहीं करवा सका)
यदि आप preg_match()
को एक मान्य बहुत बड़ा इनपुट भेज सकते हैं, तो यह इसे प्रोसेस नहीं कर पाएगा और आप चेक को बायपास कर सकेंगे। उदाहरण के लिए, यदि यह एक JSON को ब्लैकलिस्ट कर रहा है, तो आप भेज सकते हैं:
From: https://medium.com/bugbountywriteup/solving-each-and-every-fb-ctf-challenge-part-1-4bce03e2ecb0
ReDoS Bypass
Trick from: https://simones-organization-4.gitbook.io/hackbook-of-a-hacker/ctf-writeups/intigriti-challenges/1223 and https://mizu.re/post/pong
संक्षेप में, समस्या इस कारण होती है क्योंकि PHP में preg_*
फ़ंक्शन PCRE लाइब्रेरी पर आधारित होते हैं। PCRE में कुछ नियमित अभिव्यक्तियों को बहुत सारे पुनरावृत्त कॉल का उपयोग करके मिलाया जाता है, जो बहुत अधिक स्टैक स्पेस का उपयोग करता है। पुनरावृत्तियों की अनुमति की गई मात्रा पर एक सीमा निर्धारित करना संभव है, लेकिन PHP में यह सीमा डिफ़ॉल्ट रूप से 100.000 होती है, जो स्टैक में फिट होने से अधिक है।
यह Stackoverflow थ्रेड भी उस पोस्ट में लिंक किया गया था जहाँ इस मुद्दे के बारे में अधिक गहराई से बात की गई है। हमारा कार्य अब स्पष्ट था:
एक इनपुट भेजें जो regex को 100_000+ पुनरावृत्तियों करने के लिए मजबूर करे, जिससे SIGSEGV हो, जिससे preg_match()
फ़ंक्शन false
लौटाए और इस प्रकार एप्लिकेशन को यह सोचने पर मजबूर करे कि हमारा इनपुट दुर्भावनापूर्ण नहीं है, अंत में पैकेज में कुछ ऐसा फेंकते हुए {system(<verybadcommand>)}
जिससे SSTI --> RCE --> ध्वज :)।
खैर, regex के संदर्भ में, हम वास्तव में 100k "पुनरावृत्तियों" को नहीं कर रहे हैं, बल्कि हम "बैकट्रैकिंग स्टेप्स" की गिनती कर रहे हैं, जो PHP दस्तावेज़ के अनुसार pcre.backtrack_limit
चर में डिफ़ॉल्ट रूप से 1_000_000 (1M) होती है।
इस तक पहुँचने के लिए, 'X'*500_001
1 मिलियन बैकट्रैकिंग स्टेप्स (500k आगे और 500k पीछे) का परिणाम देगा:
PHP ऑबफस्केशन के लिए टाइप जगलिंग
Execute After Redirect (EAR)
यदि PHP किसी अन्य पृष्ठ पर रीडायरेक्ट कर रहा है लेकिन die
या exit
फ़ंक्शन हेडर Location
सेट करने के बाद नहीं बुलाया गया है, तो PHP निष्पादन जारी रखता है और डेटा को बॉडी में जोड़ता है:
पथ ट्रैवर्सल और फ़ाइल समावेश शोषण
Check:
File Inclusion/Path traversalऔर ट्रिक्स
register_globals: In PHP < 4.1.1.1 या यदि गलत कॉन्फ़िगर किया गया हो, register_globals सक्रिय हो सकता है (या उनका व्यवहार अनुकरण किया जा रहा है)। इसका मतलब है कि वैश्विक चर जैसे $_GET यदि उनके पास एक मान है जैसे $_GET["param"]="1234", आप इसे $param के माध्यम से एक्सेस कर सकते हैं। इसलिए, HTTP पैरामीटर भेजकर आप उन चर को ओवरराइट कर सकते हैं जो कोड के भीतर उपयोग किए जाते हैं।
एक ही डोमेन के PHPSESSION कुकीज़ एक ही स्थान पर संग्रहीत होते हैं, इसलिए यदि एक डोमेन के भीतर विभिन्न कुकीज़ विभिन्न पथों में उपयोग की जाती हैं तो आप उस पथ को बना सकते हैं जो कुकी को उस पथ का एक्सेस करता है जो दूसरे पथ कुकी के मान को सेट करता है। इस तरह यदि दोनों पथ एक ही नाम के साथ एक चर को एक्सेस करते हैं तो आप path1 में उस चर का मान path2 पर लागू कर सकते हैं। और फिर path2 path1 के चर को मान्य के रूप में लेगा (कुकी को path2 में उसके अनुरूप नाम देकर)।
जब आपके पास मशीन के उपयोगकर्ताओं के उपयोगकर्ता नाम होते हैं। पता जांचें: /~<USERNAME> यह देखने के लिए कि क्या php निर्देशिकाएँ सक्रिय हैं।
password_hash/password_verify
ये फ़ंक्शन आमतौर पर PHP में पासवर्ड से हैश उत्पन्न करने और यह जांचने के लिए उपयोग किए जाते हैं कि क्या एक पासवर्ड हैश के साथ सही है।
समर्थित एल्गोरिदम हैं: PASSWORD_DEFAULT
और PASSWORD_BCRYPT
(जो $2y$
से शुरू होता है)। ध्यान दें कि PASSWORD_DEFAULT अक्सर PASSWORD_BCRYPT के समान होता है। और वर्तमान में, PASSWORD_BCRYPT में 72bytes के इनपुट में आकार की सीमा है। इसलिए, जब आप इस एल्गोरिदम के साथ 72bytes से बड़ा कुछ हैश करने की कोशिश करते हैं, तो केवल पहले 72B का उपयोग किया जाएगा:
HTTP headers bypass abusing PHP errors
Causing error after setting headers
From this twitter thread आप देख सकते हैं कि 1000 से अधिक GET params या 1000 POST params या 20 फ़ाइलें भेजने पर, PHP प्रतिक्रिया में हेडर सेट नहीं करेगा।
उदाहरण के लिए CSP हेडर को बायपास करने की अनुमति देना जो कोड में सेट किए गए हैं:
हेडर सेट करने से पहले एक बॉडी भरना
यदि एक PHP पृष्ठ त्रुटियों को प्रिंट कर रहा है और उपयोगकर्ता द्वारा प्रदान की गई कुछ इनपुट को वापस इको कर रहा है, तो उपयोगकर्ता PHP सर्वर को कुछ इतना लंबा सामग्री प्रिंट करने के लिए मजबूर कर सकता है कि जब यह उत्तर में हेडर जोड़ने की कोशिश करता है, तो सर्वर एक त्रुटि फेंक देगा। निम्नलिखित परिदृश्य में हमलावर ने सर्वर को कुछ बड़े त्रुटियाँ फेंकने के लिए मजबूर किया, और जैसा कि आप स्क्रीन में देख सकते हैं, जब PHP ने हेडर जानकारी को संशोधित करने की कोशिश की, तो यह नहीं कर सका (तो उदाहरण के लिए CSP हेडर उपयोगकर्ता को नहीं भेजा गया):
PHP फ़ंक्शंस में SSRF
पृष्ठ की जांच करें:
PHP SSRFकोड निष्पादन
system("ls"); `ls`; shell_exec("ls");
अधिक उपयोगी PHP फ़ंक्शंस के लिए इसे देखें
preg_replace() के माध्यम से RCE
कोड को निष्पादित करने के लिए "replace" तर्क में कम से कम एक मेल की आवश्यकता है। preg_replace का यह विकल्प PHP 5.5.0 से हटा दिया गया है।
Eval() के माध्यम से RCE
RCE via Assert()
यह फ़ंक्शन php के भीतर आपको एक स्ट्रिंग में लिखे गए कोड को निष्पादित करने की अनुमति देता है ताकि सत्य या असत्य लौटाया जा सके (और इसके आधार पर निष्पादन को बदल सके)। आमतौर पर उपयोगकर्ता चर को एक स्ट्रिंग के बीच में डाला जाएगा। उदाहरण के लिए:
assert("strpos($_GET['page']),'..') === false")
--> इस मामले में RCE प्राप्त करने के लिए आप कर सकते हैं:
आपको कोड सिंटैक्स को तोड़ना, अपना पेलोड जोड़ना, और फिर इसे फिर से ठीक करना होगा। आप लॉजिक ऑपरेशंस जैसे "and" या "%26%26" या "|" का उपयोग कर सकते हैं। ध्यान दें कि "or", "||" काम नहीं करते क्योंकि यदि पहली शर्त सही है तो हमारा पेलोड निष्पादित नहीं होगा। इसी तरह ";" काम नहीं करता क्योंकि हमारा पेलोड निष्पादित नहीं होगा।
दूसरा विकल्प है कि स्ट्रिंग में कमांड के निष्पादन को जोड़ें: '.highlight_file('.passwd').'
दूसरा विकल्प (यदि आपके पास आंतरिक कोड है) है कि कुछ वेरिएबल को संशोधित करें ताकि निष्पादन को बदल सकें: $file = "hola"
RCE via usort()
यह फ़ंक्शन एक विशिष्ट फ़ंक्शन का उपयोग करके आइटम के एक ऐरे को क्रमबद्ध करने के लिए उपयोग किया जाता है। इस फ़ंक्शन का दुरुपयोग करने के लिए:
You can also use // to comment the rest of the code.
To discover the number of parenthesis that you need to close:
?order=id;}//
: हमें एक त्रुटि संदेश मिलता है (Parse error: syntax error, unexpected ';'
). शायद हमें एक या अधिक ब्रैकेट्स की कमी है।?order=id);}//
: हमें एक चेतावनी मिलती है। यह सही लगता है।?order=id));}//
: हमें एक त्रुटि संदेश मिलता है (Parse error: syntax error, unexpected ')' i
). शायद हमारे पास बहुत अधिक क्लोजिंग ब्रैकेट्स हैं।
RCE via .httaccess
If you can upload a .htaccess, then you can configure several things and even execute code (configuring that files with extension .htaccess can be executed).
Different .htaccess shells can be found here
RCE via Env Variables
If you find a vulnerability that allows you to modify env variables in PHP (and another one to upload files, although with more research maybe this can be bypassed), you could abuse this behaviour to get RCE.
LD_PRELOAD
: This env variable allows you load arbitrary libraries when executing other binaries (although in this case it might not work).PHPRC
: PHP को अपनी कॉन्फ़िगरेशन फ़ाइल कहां स्थित है इस पर निर्देशित करता है, जिसे आमतौर परphp.ini
कहा जाता है। यदि आप अपनी खुद की कॉन्फ़िगरेशन फ़ाइल अपलोड कर सकते हैं, तोPHPRC
का उपयोग करके PHP को उस पर इंगित करें। एकauto_prepend_file
प्रविष्टि जोड़ें जो एक दूसरे अपलोड किए गए फ़ाइल को निर्दिष्ट करती है। यह दूसरा फ़ाइल सामान्य PHP कोड है, जिसे फिर PHP रनटाइम द्वारा किसी अन्य कोड से पहले निष्पादित किया जाता है।
हमारे शेलकोड वाला एक PHP फ़ाइल अपलोड करें
एक दूसरा फ़ाइल अपलोड करें, जिसमें एक
auto_prepend_file
निर्देश हो जो PHP प्रीप्रोसेसर को चरण 1 में अपलोड की गई फ़ाइल को निष्पादित करने के लिए निर्देशित करता हैPHPRC
वेरिएबल को चरण 2 में अपलोड की गई फ़ाइल पर सेट करें।
इस श्रृंखला को निष्पादित करने के तरीके के बारे में अधिक जानकारी प्राप्त करें मूल रिपोर्ट से.
PHPRC - एक और विकल्प
यदि आप फाइलें अपलोड नहीं कर सकते, तो आप FreeBSD में "फाइल"
/dev/fd/0
का उपयोग कर सकते हैं जिसमेंstdin
होता है, जोstdin
पर भेजे गए अनुरोध का शरीर है:curl "http://10.12.72.1/?PHPRC=/dev/fd/0" --data-binary 'auto_prepend_file="/etc/passwd"'
या RCE प्राप्त करने के लिए,
allow_url_include
सक्षम करें और base64 PHP कोड के साथ एक फ़ाइल को प्रीपेंड करें:curl "http://10.12.72.1/?PHPRC=/dev/fd/0" --data-binary $'allow_url_include=1\nauto_prepend_file="data://text/plain;base64,PD8KICAgcGhwaW5mbygpOwo/Pg=="'
तकनीक इस रिपोर्ट से.
XAMPP CGI RCE - CVE-2024-4577
The webserver parses HTTP requests and passes them to a PHP script executing a request such as as http://host/cgi.php?foo=bar
as php.exe cgi.php foo=bar
, which allows a parameter injection. This would allow to inject the following parameters to load the PHP code from the body:
इसके अलावा, PHP के बाद के सामान्यीकरण के कारण "-" पैरामीटर को 0xAD वर्ण का उपयोग करके इंजेक्ट करना संभव है। इस पोस्ट से शोषण उदाहरण देखें:
PHP Sanitization bypass & Brain Fuck
इस पोस्ट में बहुत कम अनुमत वर्णों के साथ एक ब्रेन फक PHP कोड उत्पन्न करने के लिए शानदार विचार मिल सकते हैं। इसके अलावा, यह कई जांचों को बायपास करने की अनुमति देने वाले कार्यों को निष्पादित करने का एक दिलचस्प तरीका भी प्रस्तावित किया गया है:
PHP स्थैतिक विश्लेषण
देखें कि क्या आप इन फ़ंक्शनों (से यहाँ) में कॉल में कोड डाल सकते हैं:
यदि आप एक PHP एप्लिकेशन को डिबग कर रहे हैं, तो आप display_errors = On
जोड़कर /etc/php5/apache2/php.ini
में वैश्विक रूप से त्रुटि प्रिंटिंग सक्षम कर सकते हैं और अपाचे को पुनः प्रारंभ कर सकते हैं: sudo systemctl restart apache2
PHP कोड का डिओबफस्केटिंग
आप www.unphp.net का उपयोग PHP कोड को डिओबफस्केट करने के लिए कर सकते हैं।
PHP रैपर और प्रोटोकॉल
PHP रैपर और प्रोटोकॉल आपको एक सिस्टम में लिखने और पढ़ने की सुरक्षा को बायपास करने और इसे समझौता करने की अनुमति दे सकते हैं। अधिक जानकारी के लिए इस पृष्ठ की जांच करें।
Xdebug बिना प्रमाणीकरण वाला RCE
यदि आप देखते हैं कि phpconfig()
आउटपुट में Xdebug सक्षम है, तो आपको https://github.com/nqxcode/xdebug-exploit के माध्यम से RCE प्राप्त करने का प्रयास करना चाहिए।
वेरिएबल वेरिएबल्स
RCE abusing new $_GET["a"]($_GET["b")
यदि किसी पृष्ठ में आप किसी भी मनचाही कक्षा का एक नया ऑब्जेक्ट बना सकते हैं तो आप RCE प्राप्त करने में सक्षम हो सकते हैं, जानने के लिए निम्नलिखित पृष्ठ देखें:
PHP - RCE abusing object creation: new $_GET["a"]($_GET["b"])Execute PHP without letters
https://securityonline.info/bypass-waf-php-webshell-without-numbers-letters/
Using octal
XOR
XOR आसान शेल कोड
According to this writeup यह संभव है कि इस तरीके से एक आसान शेलकोड उत्पन्न किया जा सके:
तो, अगर आप संख्याओं और अक्षरों के बिना मनमाना PHP निष्पादित कर सकते हैं तो आप उस पेलोड का दुरुपयोग करके मनमाना PHP निष्पादित करने के लिए निम्नलिखित अनुरोध भेज सकते हैं:
For a more in depth explanation check https://ctf-wiki.org/web/php/php/#preg_match
XOR Shellcode (inside eval)
पर्ल जैसा
Last updated