Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

reading files provided via $_GET

Tags:

security

php

I have a php script which takes a relative pathname via $_GET, reads that file and creates a thumbnail of it. I dont want the user to be able to read any file from the server. Only files from a certain directory should be allowed, otherwiese the script should exit().

Here is my folder structure:

files/ <-- all files from this folder are public
my_stuff/ <-- this is the folder of my script that reads the files

My script is accessed via mydomain.com/my_stuff/script.php?pathname=files/some.jpg. What should not be allowed e. g.: mydomain.com/my_stuff/script.php?pathname=files/../db_login.php

So, here is the relevant part of the script in my_stuff folder:

...
$pathname = $_GET['pathname'];
$pathname = realpath('../' . $_GET['pathname']); 

if(strpos($pathname, '/files/') === false) exit('Error');
...

I am not really sure about that approach, doesnt seem too safe for me. Anyone with a better idea?

like image 587
Max Avatar asked Dec 14 '25 09:12

Max


1 Answers

I would do a realpath() first (resolving any "../" and other references) and then check whether the result is a sub-directory of the allowed one.

Taking your scenario (I don't understand why you need to use files/ in this case if it's the only directory that is allowed, but anyway):

$basedir = "/etc/www"; 
$allowed = "/etc/www/files";

$pathname = realpath($basedir."/".$_GET["pathname"]);

if (!$pathname) 
 die ("Unknown file path");

// Check whether $pathname begins with $allowed (= is a sub-directory)
if (substring($pathname, 0, strlen($allowed)) != $allowed)
 die ("illegal access!");

As far as I can see, this should be a safe approach.

like image 107
Pekka Avatar answered Dec 16 '25 23:12

Pekka



Donate For Us

If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!