HTML-Ausgabe ohne XSS-Schwachstelle

Bei den „Best practices“ des BSI von 2006 wird unter anderem die Filterung der Ausgabedaten behandelt. Es gibt dazu ein Beispiel einer Filterfunktion für Perl. Für PHP wird nur auf die üblichen Funktionen verwiesen.

[code]
* strips_tags()
* htmlentities()
[/code]

Beide Funktionen können nicht immer sicherstellen, dass XSS-Schwachstellen abgedichtet sind.

strip_tags() entfernt HTML-Tags aus dem Eingabestring. Es werden aber nicht immer Tags gebraucht, um JavaScript-Code zu injizieren. Ist die Feldausgabe (value) nicht mit Hochkommas („) abgeschlossen, kann über JavaScript-Events erfolgreich XSS betrieben werden.

Beispiel: INPUT-Feld mit nicht abgeschlossenem „value“

[code]„; ?>[/code]

Beispiel: JS-XSS-Code

[code]3 onclick=alert(‚XSS‘)[/code]

Beispiel: XSS-Code in INPUT-Tag

[code][/code]

Sobald der Nutzer dort klickt, wird der Code ausgeführt. Was höre ich da? „magic_quotes_gpc“ ist an? Ausgabe wird zuvor mit htmlentities() kodiert und anschließend mit strips_tags() behandelt? (Jetzt zappelt da nix mehr!)

Beispiel: XSS-Code, dem „magic_quotes_gpc“, htmlentities() und strips_tags() nichts anhaben kann

[code]3 onclick=eval(String.fromCharCode(97,108,101,114,116,40,39,88,83,83,39,41))[/code]

Wir sehen: XSS-Schutz ist mit Blacklist-Filter keine gute Idee. Die „Best practices“ des BSI haben aber für Perl einen schönen Whitelist-Filter. Heißt: was nicht erlaubt ist, wird kodiert. Und erlaubt ist wenig:

Beispiel: Erlaubte Zeichen des Whitelist-Filters

[code]a-z A-Z 0-9 _ . -[/code]

Die Übertragung des Filters von Perl nach PHP ist nicht schwer. Ergibt also einen Ausgabefilter für PHP, welches alle Zeichen außer den oben genannten nach Hexadezimal kodiert.

Beispiel: PHP-Whitelist-Filter

[code]

[/code]

ANMERKUNG: Die Funktion „seq_remove_slashes_“ findet sich im Post davor!

Das könnte dich auch interessieren …