Kernel- und Treiberprogrammierung mit dem Kernel 2.6 – Folge 57
Kern-Technik
Texte mit AES verschlüsseln, Daten komprimieren oder Hashsummen mit MD5 berechnen: Mit dem Crypto-API des Linux-Kernels und etwas Know-how kein Problem!
Texte mit AES verschlüsseln, Daten komprimieren oder Hashsummen mit MD5 berechnen: Mit dem Crypto-API des Linux-Kernels und etwas Know-how kein Problem!
Die umfassende Internetnutzung und das Bedürfnis nach Sicherheit sorgen für stärkere Verbreitung der Kryptographie. Hardwarehersteller bauen aus diesem Grund seit einigen Jahren entsprechende Erweiterungen in die hauseigenen Chips ein, beispielsweise VIA mit Padlock [1] oder Intel mit dem AES-NI-Befehlssatz [2]. Linux wiederum stellt dem Programmierer mit dem Crypto-API Kryptographie-Routinen zur Verfügung, die entweder rein in Software oder aber Hardware-unterstützt ablaufen. Ziel der Kernelentwickler ist es, dies für den Entwickler transparent zu halten.
Das Crypto-API ist nicht nur für Verschlüsselung zuständig, sondern auch für das Bilden von Hash- und Checksummen, für Kompression oder die Generierung von Zufallszahlen. Durch den modularen Aufbau des Crypto-Layers lassen sich auf der unteren Seite die unterschiedlichsten Algorithmen andocken (siehe Tabelle 1), die sich auf der oberen Seite von verschiedenen Subsystemen wie beispielsweise der Festplattenverschlüsselung (DM-Crypt) oder der geschützten VPN-Kommunikation (IPsec) nutzen lassen (siehe Abbildung 1).
Tabelle 1
Unterstützte Krypto-Algorithmen
| Funktion | Algorithmen |
|---|---|
| Hashsummen |
md4, md5, michael.mic, ripemd-128, ripemd-160, ripemd-256, ripemd-320, sha1, sha256, sha512, tiger, vmac, whirlpool |
| Cipher |
3des, aead, aes, anubis, arc4, blowfish, camellia, cast5, cast6, des, fcrypt, khazad, salsa20, seed, serpent, tea,xtea,xeta, twofish |
| Kompression |
deflate, lzo, zlib |
| Sonstiges |
ansi_cprng (Pseudo Random Nummer Generator), kernel random number generator, random number generator, crc32c (Checksummen) |
Basis des Crypto-API im Kernel sind die Transform-Objekte. Für die Bildung von Hashsummen sowie Kompressions- und Verschlüsselungsverfahren gibt es jeweils eigene Objekte. Wenn es um Verschlüsselung geht, hat der Entwickler sogar die Auswahl zwischen vier unterschiedlichen Transforms: Cipher, Blockcipher, Asynchronous Blockcipher und AEAD (Authenticated Encryption with Associated Data). Diese unterscheiden sich bezüglich der Angabe von Quell- und Zielspeicherbereichen und der Funktionalität.
Block-orientierte Transform-Objekte, wozu neben Blockcipher, Asynchronous Blockcipher und AEAD auch Hashsummen gehören, spezifizieren Quelle und Ziel der Operationen auf Basis von Scatter-Gather-Listen (siehe Kasten "Scatter-Gather-Listen"). Stream-orientierte Transforms (Cipher, Compress) verwenden direkt virtuelle Adressen.
Scatter-Gather-Listen
Scatter-Gather-Listen tauchen im Kernel immer dann auf, wenn größere Mengen an Daten zu transferieren sind. Größere Datenmengen – also typischerweise mehr Daten, als in eine so genannte Page (4096 Byte) passen – verteilen sich nämlich im Hauptspeicher häufig über verschiedene physische Adressen.
Scatter-Gather-Listen fassen diese physischen Adressen in einer Datenstruktur zusammen, sodass die Transferfunktionen – etwa das Schreiben der Daten auf die Festplatte – in einem Zug alle notwendigen Informationen besitzen und den Transfer auch per DMA durchführen können. Eigentlich wäre Scatter-Gather-Feld die korrekte Bezeichnung, denn die grundlegende Datenstruktur ist ein Array vom Typ »struct scatterlist«. Jedes Element eines solchen Felds repräsentiert ein zusammenhängendes Fragment im Speicher, das durch eine Page-Adresse, den Startoffset innerhalb der Speicherseite sowie die Länge der dort abgelegten Daten (in Bytes) gekennzeichnet ist.
Ein derartiges Feld kann der Programmierer entweder dynamisch während der Laufzeit allozieren und initialisieren oder dies statisch durch den Compiler erledigen lassen. Im letzteren Fall muss der Code zur Initialisierung »sg_init_table()« aufrufen. Um die einzelnen Feldelemente zu belegen, kommt entweder »sg_set_buf()« oder »sg_set_page()« zum Aufruf – je nachdem, ob die Adresse der Daten als virtuelle oder als Page-Adresse vorliegt. Wurde das Scatter-Gather-Feld per »sg_alloc_table()« angelegt, gibt es »sg_free_table()« nach Gebrauch wieder frei.
Neben den in Tabelle 2 aufgeführten Funktionen gibt es noch eine Reihe weiterer, die insbesondere die Abarbeitung einer Scatter-Gather-Liste vereinfachen.
Tabelle 2
Funktionen zum Aufbau von Scatter/Gather-Listen
| Funktionsprototyp | Kurzbeschreibung |
|---|---|
| int sg_alloc_table(struct sg_table *table, unsigned int nents, gfp_t gfp_mask); |
Reserviert und initialisiert eine Scatter/Gather Liste mit » |
| void sg_init_table(struct scatterlist *sg, unsigned int nents); |
Initialisiert die Liste » |
| void sg_init_one(struct scatterlist *sg, const void *buf, unsigned int length); |
Initialisiert die Liste » |
| static inline void sg_set_page(struct scatterlist *sg, struct page *page, unsigned int len, unsigned int offset); |
Initialisiert das Listenelement » |
| static inline void sg_set_buf(struct scatterlist *sg, const void *buf, unsigned int buflen); |
Initialisiert das Listenelement » |
| static inline void *sg_virt(struct scatterlist *sg); |
Gibt die virtuelle Adresse des Listenelementes » |
Generell arbeiten die Algorithmen synchron, mit dem »ablkcipher«-Transform ist auch eine asynchrone Ver- und Entschlüsselung möglich: Der Crypto-Layer übernimmt Aufträge und übergibt das Ergebnis später per Callback-Funktion dem Auftraggeber. Das AEAD-Transform schließlich kombiniert Verschlüsselung und Hashing, wie es bei IPsec benötigt wird. Vor der Nutzung einer Kryptofunktion im Kernel steht das Anlegen eines geeigneten Transform-Objekts. Dabei ist gleichzeitig der gewünschte Algorithmus anzugeben, beispielsweise »md5«. Vereinfacht ausgedrückt ist hiernach die gewünschte Kryptofunktion mit Übergabe der Quell- und Zielspeicheradressen aufzurufen.
Dass sich der Programmierer im Detail jedoch noch mit Scatter-Gather-Listen, einem Descriptor-Objekt und so etwas wie »digestsize« herumschlagen muss, verdeutlicht dieser Artikel an den Beispielen MD5-Hashsummenbildung und AES-Verschlüsselung.
Umfang: 5 Heftseiten
Preis € 0,99
(inkl. 19% MwSt.)
Alle Rezensionen aus dem Linux-Magazin
Im Insecurity Bulletin widmet sich Mark Vogelsberger aktuellen Sicherheitslücken sowie Hintergründen und Security-Grundlagen. mehr...