Using php://filter for local file inclusion

Published on by

I came across a website where the site was vulnerable to LFI (local file inclusion) however the inclusion was done using a require_once and the script appended a .php extension to the end of the file; furthermore it was not vulnerable to null byte injection which meant that if I did include a file that:

  1. The file would have to be valid PHP syntax
  2. I would not be able to see anything contained between <? ?> tags
  3. Anything I could include would be executed.
  4. The file would have to end in the PHP extension

I tried to see if I could include remote files by specifying a URL as the parameter, sadly allow_url_include was turned off so that failed. When I specified a valid PHP page it simply returned the normal page as expected.

The solution that allowed me to view the source of any PHP file was to use the function php://filter/convert.base64_encode/resource which has been available since PHP 5.0.0

http://xqi.cc/index.php?m=php://filter/convert.base64-encode/resource=index

This forces PHP to base64 encode the file before it is used in the require statement. From this point its a matter of then decoding the base64 string to obtain the source code for the PHP files. Simple yet effective..

curl http://xqi.cc/index.php?m=php://filter/convert.base64-encode/resource=index
PD9waHAgZWNobygkX0dFVFsneCddKTsgLy8gT01HIHlvdSBib3RoZXJlZCB0byBkZWNvZGUgYmFzZSA2ND8gPz4=

Once you've got the source code for one file you can inspect it for further vulnerabilities such as SQL injections and additional PHP files referenced via include or require_once.