Open Source im professionellen Einsatz

OpenSSL: Integer Overflow lässt entfernte Angreifer Befehle ausführen

Eine Sicherheitslücke in den ASN.1-Routinen von OpenSSL führt dazu, dass ein entfernter Angreifer Befehle mit den Rechten der Anwendung ausführen kann.

Ursache ist ein Programmierfehler in der Funktion "asn1_d2i_read_bio()", der dazu führt, dass der Angreifer einen Heap Overflow provozieren kann. Die Schwachstelle lässt sich durch geschickt konstruierte X.509-Zertifikate oder öffentliche RSA-Schlüssel ausnützen.

Zum Verwalten des Dekodierungsprozesses legt OpenSSL ASN.1-Kontextdaten in der folgenden Struktur ab:

typedef struct asn1_const_ctx_st
{
    const unsigned char *p;/* work char pointer */
    int eos;    /* end of sequence read for indefinite encoding */
    int error;  /* error code to use when returning an error */
    int inf;    /* constructed if 0x20, indefinite is 0x21 */
    int tag;    /* tag from last 'get object' */
    int xclass; /* class from last 'get object' */
    long slen;  /* length of last 'get object' */
    const unsigned char *max; /* largest value of p allowed */
    const unsigned char *q;/* temporary variable */
    const unsigned char **pp;/* variable */
    int line;   /* used in error processing */
} ASN1_const_CTX;

Der Code speichert Längeneinträge wie beispielsweise "slen" als (signed) "long". Die verschiedenen Einträge dieser Struktur werden dabei von den beiden Funktionen "ASN1_get_object()" und "asn1_get_length()" gefüllt. Der Programmierfehler besteht darin, dass die später aufgerufene Funktion "asn1_d2i_read_bio()" den Struktureintrag "ASN1_const_CTX->slen" an mehreren Stellen vom Datentyp "long" auf (signed) "int" castet. Dies geschieht beispielsweise an folgender Stelle:

/* suck in c.slen bytes of data */
want=(int)c.slen;

Dadurch kann es zu einem typischen Integer Overflow kommen, wenn der Angreifer das Paket so präpariert, dass "slen" einen entsprechenden Wert hat. Baut sich der Angreifer beispielsweise ein DER-Paket (Distinguished Encoding Rule) mit gesetztem Bit 31 für die Länge zusammen

$ dumpasn1 testcase.crt
0 NDEF: [PRIVATE 3] {
   2 2147483648:   [1]
        ...
} 

so führt dies im Programmablauf von OpenSSL zu einem negativen "want"-Wert wie folgender GDB-Auszug demonstriert:

Breakpoint 2, asn1_d2i_read_bio (in=0x9173a0, pb=0x7fffffffd8f0) at a_d2i_fp.c:224
224             if (want > (len-off))
(gdb) list
219             }
220         else
221             {
222             /* suck in c.slen bytes of data */
223             want=(int)c.slen;
224             if (want > (len-off))
225                 {
226                 want-=(len-off);
227                 if (!BUF_MEM_grow_clean(b,len+want))
228                     {
(gdb) p c.slen
$18 = 2147483648
(gdb) p want
$19 = -2147483648

Dieser Integer Overflow alleine wäre noch nicht dramatisch. Allerdings findet sich eine weitere Schwachstelle in OpenSSL, welche zusammen mit dem Overflow dazu führt, dass ein Angreifer Befehle ausführen kann. Dieser zweite Fehler befindet sich in den Routinen zur Speicherallokation. OpenSSL implementiert eine eigene "realloc()"-Funktion namens "CRYPTO_realloc_clean()", die folgendermaßen aussieht:

void *CRYPTO_realloc_clean(void *str, int old_len, int num, const char *file, int line)
{
    /* ... */
    ret=malloc_ex_func(num,file,line);
    if(ret)
        {
        memcpy(ret,str,old_len);
        OPENSSL_cleanse(str,old_len);
        free_func(str);
        }
    /* ... */
    return ret;
}

Kritisch ist hier die "memcpy()"-Anweisung, welche die alten Daten auf die neue Adresse kopiert, ohne zu prüfen, ob der neu allozierte Speicherbereich hierfür ausreicht. Dies ist gefährlich, weil so Speicher überschrieben werden kann. Ein entfernter Angreifer kann das in Kombination mit dem Integer Overflow ausnutzen, um beliebige Befehle mit den Rechten des OpenSSL-Prozesses auszuführen.

Anfällig für dieses Sicherheitsleck sind Applikationen, die "BIO"- oder "FILE"-basierte Funktionen zum Einlesen von DER-Daten verwenden.

Betroffen sind die OpenSSL-Versionen vor 0.9.8v und 1.0.0i.

comments powered by Disqus

Ausgabe 08/2014

Digitale Ausgabe: Preis € 6,40
(inkl. 19% MwSt.)

Artikelserien und interessante Workshops aus dem Magazin können Sie hier als Bundle erwerben.

Insecurity Bulletin

Insecurity Bulletin

Im Insecurity Bulletin widmet sich Mark Vogelsberger aktuellen Sicherheitslücken sowie Hintergründen und Security-Grundlagen. mehr...

Linux-Magazin auf Facebook