kostenloser Webspace werbefrei: lima-city


Sicherheit in PHP

lima-cityForumProgrammiersprachenPHP, MySQL & .htaccess

  1. Autor dieses Themas

    finch

    Kostenloser Webspace von finch, auf Homepage erstellen warten

    finch hat kostenlosen Webspace.

    Hallo Leute, hab was gfunden mit dem man lernt halbwegs sicher PHP zu programmieren:

    Serverseitige Scripte koennen auf einem Server ein Scheunentor einer
    Sicherheitsluecke aufreissen. In diesem Text werde ich ein paar Tips zum
    besten geben, was man bei der Programmierung von PHP Scripts beachten
    sollte und was man zusaetzlich tun kann um boesen Buben auf die Finger
    schauen/klopfen zu koennen.

    GET & POST
    ==========
    Kaum einer weiss eigetlich so richtig was der Unterschied zwischen den
    Methoden GET und POST ist. Die gefinition laut Self HTML ist wie folgt:
    ZITAT: Stefan Muenz SELFHTML Version 7.0 \"Formular definieren\" -->
    tcha.htm#a2
    Wenn Sie method=get wählen, werden die Daten des ausgefüllten Formulars
    auf WWW-Servern mit installiertem HTTP-Protokoll in der CGI-
    Umgebungsvariablen QUERY_STRING gespeichert (method = Methode, get =
    bekommen). Das CGI-Programm muß den Inhalt dieser Umgebungsvariablen
    auslesen und verarbeiten.
    Wenn Sie method=post wählen, werden die Daten des augefüllten Formulars
    auf dem Server-Rechner von \"stdin\" zur Verfügung gestellt, und das CGI-
    Programm muß sie behandeln wie eine Benutzereingabe, die auf der
    Kommandozeile gemacht wurde (post = verschicken). Da in diesem Fall
    kein EndOfFile-Signal (EOF) gesendet wird, muß das CGI-Programm die
    CGI-Umgebungsvariable CONTENT_LENGTH auslesen, um die Länge der
    übermittelten Daten und damit deren Ende zu ermitteln.
    ZITAT ENDE
    In der Regel ist es bei PHP egal welche Methode man verwendet. Jedoch
    wuerde ich immer zu POST raten da:

    a) die Daten genauso wie bei GET gehandelt werden
    b) bei GET Datenlaenge auf die laenge des Referer des Browsers beschraenkt
    ist
    c) die Variablennamen und deren Inhalte NICHT in der Addressleiste
    erscheinen

    Im Gegensatz zu GET ist es bei POST nicht ganz so einfach bei einer
    Bruteforce Attacke, die Variableninhalte auszutauschen, denn was nicht
    angezeigt wird kann auch nivht veraendert werden. Meiner Einschaetzung nach
    gilt das aber nur fuer Scriptkiddies oder Beginner, die sich nciht die
    Muehe machen wuerden ein eigenes Tool fuer solch eine Aktion zu schreiben.
    Ich habe hier einmal den Header des Browsers bei beiden Methoden
    aufgelistet:
    GET


    GET /test.php?ZAHLEN=1234567890 HTTP/1.0
    Referer: http://127.0.0.1/test.php
    Connection: Keep-Alive
    User-Agent: Mozilla/4.73 [de] (Win98; U)
    Host: 127.0.0.1
    Accept: image/gif, image/x-xbitmap, image/jpeg, image/pjpeg, image/png,
    */*
    Accept-Encoding: gzip
    Accept-Language: de
    Accept-Charset: iso-8859-1,*,utf-8


    POST


    POST /test.php HTTP/1.0
    Referer: http://127.0.0.1/test.php
    Connection: Keep-Alive
    User-Agent: Mozilla/4.73 [de] (Win98; U)
    Host: 127.0.0.1
    Accept: image/gif, image/x-xbitmap, image/jpeg, image/pjpeg, image/png,
    */*
    Accept-Encoding: gzip
    Accept-Language: de
    Accept-Charset: iso-8859-1,*,utf-8
    Content-type: application/x-www-form-urlencoded
    Content-length: 17

    ZAHLEN=1234567890

    Schon alleine wenn man sich den rot unterlegten Text anschaut wird einem
    der unterschied klar. Bei POST muss man die Daten hinter dem Header her
    schicken und nicht enfach bequem in die URL einbauen. Die erklaert auch
    warum GET auf eine bestimmte groeße begrenzt ist. Bei POST gibt das
    Attribut \"Content-length: 17\" gibt die laenge der Nachgesendeten Daten
    (inklusive Variablen-/Feldernamen) an. Dies macht es fuer unwissende nicht
    umbedingt sehr einfach, schon alleine weil man sich erstmal mit dem HTTP
    vertraut machen muss. Also keine 100% Absicherung, aber Menschen neigen ja
    dazu jeden noch so kleinen Ast zu ergreifen um nicht unter zu gehen.

    Doch sollte jemand auf die Idee kommen die Feldernamen herauszupicken und
    die ganze Sache mit einem Programm ueber GET laufen zu lassen, was ist
    dann?

    Keine Panik, in diesem Fall koennen wir die PHP interne Variable,
    $REQUEST_METHOD. Diese enthaelt dann in upcase Letter (Grossbuchstaben)
    entweder den Wert GET oder POST. Alles was wir jetzt noch benoetigen ist
    eine kleine If-Clause und schon koennen wir die Aktion von aussen
    angemessen behandeln.
    SAMPLE SOURCE:post_check.php

    <?

    if($REQUEST_METHOD != \"POST\")
    die(\"Hier wird nur gepostet!\");

    echo \"Hier geht die Post ab!\";

    ?>


    Das obige Beispiel ist nur kurz zur Veranschaulichung gedacht und wuerde in
    der Praxis bestimmt nicht so gehandhabt werden.


    Error Parsing
    =============
    Wenn mal das ganze ein wenig zu paranoid sieht ist jede Eingabe durch den
    Client eine Risiko fuer die Anwendung. Wenige Zeichen koennen genuegen um
    Guestbooks/Foren unbrauchbar zu machen, in einem CSV Datenbestant die
    integrietaet zu nichte zu machen, oder sogar um die kontrolle auf dem
    gesamtmen Serversystem zu erlangen. Das mag sich vielleicht erstmal ein
    wenig dumm und uebertrieben anhoeren, aber ich werde hier einmal ein
    Beispielscript zeigen, wie es mit Sicherheit noch zu hauf im Internet zu
    finden ist.
    !VERY-BAD! SOURCE: printdata.php

    <?

    if($isset($data))
    readfile($data);
    else
    echo \"Keine Datei zum ausgeben...\";


    ?>
    Dies ist jetzt die warscheinlich trivialste Variante, jedoch aendert sich
    nichts am Prinzip. Das Script soll lediglich die Datei, die durch die
    Variable $data definiert wird, an den Client senden. Das waere zum Beispiel
    bei Einer Textreihe gut denkbar, weil der Autor sich (warum auch immer)
    nicht die Muehe machen wollte alle in HTML zu konvertieren. Nun denn,
    zumindest erlaubt die Person uns jetzt netter Weise auf alle Datenbestaende
    auf dem Rechner zu zugriefen. Nehmen wir (um dem ganzen noch die Krone
    aufzusetzten) dazu noch an, dass der Webserver auf einem schlecht
    konfiguriertem UNIX System laeuft. Wir Manipulieren die URL ein wenig...
    SAMPLE


    Vorher:http://www.host.de/printdata.php?data=text1.txt
    Nacher:http://www.host.de/printdata.php?data=../../../../home/user
    oder sogar:http://www.host.de/printdata.php?data=../../../../etc/shadow

    So etwas sollte niemals passieren. Ein gut konfiguriertes Serversystem ist
    mehr als die halbe Miete! Nun aber einmal zur Problem behebung. Wie folgt
    wuerde das Script schon ein wenig besser aussehen:
    !BAD! SOURCE: printdata.php


    function chkstr($string)
    {
    if(($string[0] . $string[1]) == \"..\") return 1;
    for($i=0;$i <= strlen($string);$i++)
    if(($string[$i] == \"/\") || ($string[$i] == \"\\\")) return 1;

    return 0;
    }

    if($isset($data))
    {

    $stat = chkstr($data);
    if($stat != 0) die(\"Ungueltiger Dateipfad angegeben...\");
    readfile($data);
    }
    else
    echo \"Keine Datei angegeben...\";

    Schon ein wenig sicherer. Ich persoenlich wuerde eine ganz andere Technick
    anwenden, aber dazu ein anderes mal. Wenn man ein Guestbook hat mochte man
    natuerlich vermeiden, dass jemand darin wie wild mit HTML oder gar
    clientseitigen Scripten rumspielt. PHP4 bietet die Funktion
    htmlspecialchars() die einen String auf Browsersensiebele Zeichen
    untersucht, und diese in HTML-Code umsetzt. Dass heisst im klartext:
    \"Keine Manipulationsmoeglichkeiten, da Sonderzeichen wie < oder > vom
    Script als &lt; bzw. &gt; ausgeschreiben werden, und somit vom Browser als
    brave Sonderzeichnen erkannt und angezeigt werden. Kein fremder Syntax
    moeglich!\".


    Externe Dateien
    ===============
    Viele Lagern haeufig verwendete Funktionen aus und Laden Sie am Anfang des
    Scripts. Diese koennen unter anderem Sensiebele Daten wie
    Datenbankzugaenge, Passwoerter oder Systempfade enthalten. Deshalb ist es
    besonders wichtig diese Dateien zu schuetzen. Die meisten verwenden als
    Endung fuer solche Dateien \".inc\". Der Webserver erkennt diesen Dateitypen
    (sofern nicht eingetragen) nicht als ein PHP-Script an und wuerde die
    Gesamte Source ueber den Webserver zum Client schleusen, ganz unabhaengig
    davon ob der Quelltext mit Kommentaren, PHP-Tags oder aenlichem markiert
    ist. Aus diesem Grunde sollte man die externen Dateien, immer mit einer
    beim Webserver als PHP-Script eingetragenen Dateiendung benennen:
    Beispiele:
    ==========
    test.inc.php
    test.inc.php3
    test.inc.php4
    test.inc.phtml
    So wird die Datei bei einem direktem Aufruf verarbeitet und der Quelltext
    wird nicht preis gegeben.


    <input type=\"hidden\">
    =====================
    Hidden Fields sind nciht umbedingt dazu gedacht etwas vor dem Client zu
    verstecken. Das waere ziemlich unsinnig, da in der Source sowieso alles im
    Klartext sichtbar ist. Geheime Daten sollte man lieber auf dem Server
    zwischenspeichern.

    Artikel ist von D.Wilson


    Is glaub ich ganz brauchbar, mfg :-) Finch :-)
  2. Diskutiere mit und stelle Fragen: Jetzt kostenlos anmelden!

    lima-city: Gratis werbefreier Webspace für deine eigene Homepage

  3. t*****b

    Und was willst du uns damit sagen? Jeder der sich intensiv mit PHP beschäftigt ist das bekannt.
    Keine Diskussionsgrundlage: closed.
  4. Diskutiere mit und stelle Fragen: Jetzt kostenlos anmelden!

    lima-city: Gratis werbefreier Webspace für deine eigene Homepage

Dir gefällt dieses Thema?

Über lima-city

Login zum Webhosting ohne Werbung!