
Abbildung 1: Der Angreifer schleust ein Skript in einen Forumsbeitrag ein (1), den der Server speichert (2). Beim Abrufen des Forums (3) setzt der Server den Rumpf der Webseite (4a) und die Einträge der Datenbank (4b) zusammen und liefert die Seite an den Besucher (5). Dessen Browser führt das Skript aus.
Gegenmaßnahmen
Cross-Site-Skripting ist zwar weit verbreitet, aber vergleichsweise leicht zu vereiteln. Eine sichere Anwendung entfernt aus den Eingaben allen Skriptcode oder weist zweifelhafte Texte gleich ganz zurück. Bei HTML finden sich Skriptanweisungen immer in Tags, also zwischen spitzen Klammern »<…>«. Die einfache Holzhammerlösung wäre, vor dem Weiterverarbeiten sämtliche Metazeichen in ihre ungefährliche HTML-Kodierung zu übersetzen (siehe Tabelle 1).
Aber wer den Anwendern etwas Markup erlauben will, kommt so nicht ans Ziel. Javascript-Code kann sich fast überall verbergen, etwa in den Tags »<img …>«, »<div …>« oder »<body …>«. In [2] finden sich zahlreiche weitere Beispiele. Deshalb kommt Blacklisting nicht in Betracht, aber Whitelisting verspricht Erfolg [1]: nur wenige bekanntermaßen gutartige HTML-Tags zulassen und den Rest als gefährlich zurückweisen, einschließlich aller Tags mit Attributen. Ungefährlich sind die Tags in Tabelle 2. Wem diese nicht ausreichen, der sollte das Problem an die Entwicklungsabteilung weitergeben oder die Literatur bemühen ([2], [3]).
|
Tabelle 1: |
|
|---|---|
|
Zeichen |
HTML-Kodierung |
|
< |
< |
|
> |
> |
|
& |
& |
|
“ |
" |
Lösung für C und C++: Die Bibliothek Gateguardian [9] gibt dem Entwickler Mittel an die Hand, um diese Untiefen zu umschiffen. Die Funktion »inputg_escape_html()« codiert die HTML-Metazeichen »<>”&« mittels HTML-Escaping als »<«, »>«, »"« und »&«, lässt aber einige bekannt harmlose Tags wie »<h1>« oder »<br>« unverändert passieren. Auch skriptfreie Links wie »<a href=”http://Foo”>« bleiben unangetastet. Der Aufruf sieht so aus:
#include <inputguardian.c> [...] char *escaped; escaped = inputg_escape_html(eingabe);
Die Funktion gibt einen Zeiger auf das modifizierte HTML-Dokument zurück, der auf einen mit »malloc()« reservierten Speicher zeigt, den der Programmierer später mit »free(escaped)« freigeben muss. Einen Nullzeiger retourniert die Funktion nur, wenn sie keinen Speicher reservieren konnte.
|
Tabelle 2: |
|---|
|
abbr |
|
acronym |
|
b |
|
bdo |
|
big |
|
blink |
|
blockquote |
|
br |
|
center |
|
cite |
|
code |
|
dd |
|
del |
|
dfn |
|
dir |
|
dl |
|
dt |
|
em |
|
h1 |
|
h2 |
|
h3 |
|
h4 |
|
h5 |
|
h6 |
|
hr |
|
i |
|
ins |
|
kbd |
|
li |
|
menu |
|
nobr |
|
ol |
|
p |
|
plaintext |
|
pre |
|
q |
|
s |
|
samp |
|
small |
|
spacer |
|
strike |
|
strong |
|
sub |
|
sup |
|
tt |
|
u |
|
ul |
|
var |
Maskenball
Die Variante »inputg_escape_all_html()« verwandelt alle HTML-Metazeichen in ihre harmlose Web-Kodierung. Bei »inputg_escape_html_with_tag_table()« darf der Anwender die Liste der erlaubten Tags selbst bestimmen.
Achtung: Die Funktionen in Gateguardian stammen von »spc_escape_html()« aus dem Secure Programming Cookbook [4] ab. Im Original haben sich leider viele Bugs eingeschlichen. Als Ersatz für den fehlerhaften Code liefert der Autor ein Archiv [5] mit korrigierten Versionen. Seit Folge 3 sind neue Bugfixes hinzugekommen; wer dieses Archiv verwendet, sollte es neu herunterladen.
Lösung für die Shell: Am einfachsten ist ein kleines Wrapperprogramm, das die Funktion aus Gateguardian verwendet. Das Programm »escape-html« (Listing 1) ruft der Admin dann einfach mit »ESCAPED=`escape-html “$INPUT”`« aus seinen Shellskripten heraus auf.
Falle 2: E-Mail-Adressen
Administrative Skripte oder Programme erwarten oft Eingaben in Form von E-Mail-Adressen. Meist bestimmt der Admin die Adresse selbst, etwa wenn ihn ein nächtliches Skript detailliert über die gelaufenen Aktionen informieren soll. In anderen Fällen geben Benutzer Mailadressen vor, so etwa in einem Bugreport-Formular. Wer nicht gerade einen Mailclient oder gar Mailserver entwickelt, wertet die eingegebenen Adressen vermutlich nicht selbst aus. Trotzdem gilt “Cautela abundans non nocet” (zu viel Vorsicht schadet nicht).





