Rückblick: Das Problem
Wir haben gesehen, dass LFI entsteht, wenn Anwendungen unkontrolliert Dateien anhand von Benutzereingaben laden.
- Beispiel:
include($_GET["page"]);
- Angreifer:
?page=../../etc/passwd
→ Systemdateien werden sichtbar. - In Kombination (Log Poisoning, File Upload) → Remote Code Execution (RCE).
Die gute Nachricht: Mit den richtigen Maßnahmen lässt sich LFI zuverlässig verhindern.
1. Niemals direkte Includes aus Benutzereingaben
Das ist der Kernfehler:
$page = $_GET["page"];
include($page);
Angreifer haben hier freie Hand.
Besser: Whitelisting
$allowed_pages = [
"home" => "home.php",
"about" => "about.php",
"contact" => "contact.php"
];
$page = $_GET["page"] ?? "home";
if (array_key_exists($page, $allowed_pages)) {
include($allowed_pages[$page]);
} else {
include("404.php");
}
- Nur explizit erlaubte Dateien werden geladen.
- Keine Chance für
../
oder fremde Pfade.
2. Mapping statt Dateinamen
Noch besser: Arbeite gar nicht mit Dateinamen, sondern mit internen Slugs oder IDs.
switch ($_GET["page"]) {
case "home":
showHome();
break;
case "about":
showAbout();
break;
default:
show404();
}
So haben Angreifer keinen Einfluss mehr auf Dateipfade.
3. Pfade validieren
Wenn man wirklich Dateien dynamisch laden muss, dann nur mit Validierung:
realpath() nutzen
$base = "/var/www/html/templates/";
$file = realpath($base . $_GET["file"]);
if ($file && strpos($file, $base) === 0) {
include($file);
} else {
include("404.php");
}
realpath()
löst../
auf.strpos($file, $base) === 0
prüft, ob die Datei noch im erlaubten Verzeichnis liegt.
Damit wird Directory Traversal blockiert.
4. Keine unnötigen Fehlermeldungen
Fehlermeldungen verraten Angreifern, dass ein LFI-Versuch gestartet wurde.
Statt:
Warning: include(../../etc/passwd): failed to open stream...
→ Immer Fehlerbehandlung aktivieren:
ini_set("display_errors", 0);
error_log("include error: " . $_GET["file"]);
So sehen nur Admins die Details, Angreifer nicht.
5. Webserver-Härtung
Selbst wenn es in der Anwendung Fehler gibt, kannst du mit Server-Konfiguration das Risiko reduzieren.
Dateirechte minimal halten
- Der Webserver (z. B.
www-data
) sollte nur Zugriff auf das Webroot haben. - Keine Lese-Rechte für
/etc/
,/var/log/
, Home-Verzeichnisse.
Open_basedir in PHP
open_basedir=/var/www/html/
→ PHP darf nur in diesem Verzeichnis Dateien öffnen.
Disable gefährliche Funktionen
disable_functions = system, exec, shell_exec, passthru, popen, proc_open
So verhinderst du, dass eine LFI direkt in RCE eskaliert.
6. Monitoring & Detection
Verdächtige Requests erkennen
- Parameter mit
../
- URL-encoded Traversal (
%2e%2e%2f
) - PHP-Wrapper (
php://filter
)
Ein WAF oder Intrusion Detection System (IDS) kann diese Muster blocken oder melden.
Logs vergleichen
- Auffällige 404-Fehler mit ungewöhnlichen Pfaden.
- Viele aufeinanderfolgende Requests mit
file=
-Parametern.
7. Frameworks & moderne Patterns nutzen
Viele moderne Frameworks (Laravel, Django, Spring Boot) sind von Haus aus sicherer, weil sie:
- Templates nicht direkt über Include-Pfade laden, sondern über ein Rendering-System.
- Keine Dateinamen aus GET/POST übernehmen.
- Strikte Routing-Mechanismen haben.
Wer mit modernen Frameworks arbeitet, reduziert das Risiko enorm.
8. Tests in der Entwicklungsphase
Unit-Tests
Schreibe Tests, die prüfen, ob unautorisierte Pfade blockiert werden:
$response = request("/?file=../../etc/passwd");
assert($response->status == 404);
Penetrationstests
Setze Tools wie Burp Suite oder OWASP ZAP ein, um gezielt auf LFI zu prüfen.
9. Typische Anti-Patterns vermeiden
- Blacklisting: Nur
../
blocken reicht nicht → Angreifer nutzen%2e%2e%2f
. - Anhängen von
.php
: Null Byte Injection oder Encodings können das umgehen. - Vertrauen auf Client-Side Controls: Dropdowns oder versteckte Felder im HTML sind keine Sicherheit – Angreifer ändern Parameter im Request.
10. Defense in Depth
LFI-Prävention funktioniert am besten mit mehreren Schichten:
- Input-Validierung (Whitelist).
- Server-Härtung (Rechte,
open_basedir
). - Fehlerbehandlung (keine Infos nach außen).
- Monitoring (verdächtige Requests erkennen).
- Frameworks (sichere Routing-Systeme).
Analogie: Die Bibliothek mit Sicherheitsstufen
Erinnerst du dich an die Bibliotheks-Analogie?
- Früher konnte jeder jedes Buch verlangen.
- Jetzt gibt es:
- Whitelist: Nur Bücher aus der offiziellen Liste.
- realpath(): Bibliothekar prüft, ob das Buch wirklich aus dem erlaubten Regal kommt.
- Serverrechte: Manche Räume sind für den Bibliothekar verschlossen.
- Monitoring: Kameras melden verdächtige Besucher.
So bleibt die Bibliothek sicher.
Was du bis hier mitnehmen solltest
- Nie direkte Includes aus Benutzereingaben.
- Immer Whitelisting oder Mapping nutzen.
realpath()
+ Basisverzeichnis prüfen.- Serverrechte minimal halten (
open_basedir
, Dateirechte). - Moderne Frameworks statt eigener Include-Logik.
- Monitoring & Tests ergänzen den Schutz.
Schreibe einen Kommentar