Sven Rautenberg: Universallösung für lokale dynamische Dateinamen

Beitrag lesen

Moin!

Mir ist gerade die Idee gekommen, wie man diesen Code hier einfach und simpel absichern kann:

<?php
if (isset($_GET["show"]) && file_exists($_GET["show"].".php"))
{
  include($_GET["show"].".php");
}
else
{
  include("home.php");
}
?>

  
Das Problem ist, dass der Beginn des Dateinamens dynamisch ist, dort also auch Protokollbezeichner wie ftp:// erscheinen könnten, die unter PHP 5 auch in file\_exists() erlaubt sind und Remote-Zugriffe erlauben - und so zum Includieren von externem bösem Code führen können.  
  
Dagegen hilft lediglich, sicherzustellen, dass in jedem Fall auf eine Datei aus dem lokalen Dateisystem zugegriffen wird. Und das stellt man sicher, indem der Pfadname mit einem statischen, von Angreifern unabänderlichen Bestandteil beginnt. Also beispielsweise einem "/" plus Document-Root plus Unterverzeichnis im Webprojekt.  
  
Allerdings: $\_SERVER['DOCUMENT\_ROOT'] steht IIRC nicht in allen Situationen verläßlich zur Verfügung, sondern hängt vom benutzten Webserver ab - und unter Umständen auch von weiteren Einflüssen wie Pfadverschiebungen durch Aliase oder mod\_rewrite. Der Charme des obigen Codes liegt darin, dass durch den relativen Pfadzugriff Anpassungen an den Einsatzort entfallen.  
  
Aber zum Glück gibts auch einen statischen Bestandteil, der das aktuelle Verzeichnis bezeichnet: "./"  
  
~~~php
  
<?php  
if (isset($_GET["show"]) && file_exists("./" . $_GET["show"] . ".php"))  
{  
  include("./" . $_GET["show"] . ".php");  
}  
else  
{  
  include("./home.php");  
}  
?>  

So abgesichert würde eine eingeschleppte FTP-URL im Endeffekt so aussehen:
./ftp://evil.domain.test/pfad/evilscript.php

Das führt zu einem lokalen Dateisystemzugriff, der diese "Datei" nicht findet.

Ich halte meinen Vorschlag für in jeder Situation sicher und deshalb für extrem empfehlenswert. Gibt es Gegenmeinungen?

- Sven Rautenberg

--
My sssignature, my preciousssss!