Entwickler von Cloudflare haben an der Optimierung der Leistung der Festplattenschlüsselung im Linux-Kernel gearbeitet. Dabei wurden für das Subsystem und die Crypto API entwickelt, die es ermöglichten, die Durchsatzrate beim Lesen und Schreiben im synthetischen Test um mehr als das Doppelte zu erhöhen und gleichzeitig die Latenz um die Hälfte zu senken. Bei Tests auf echter Hardware konnten die durch die Verschlüsselung verursachten Overheads fast auf das Niveau reduziert werden, das bei der Verwendung von Festplatten ohne Datenverschlüsselung zu beobachten ist.
Cloudflare nutzt dm-crypt zur Verschlüsselung von Daten auf den Speichermedien, die zum Caching von Inhalten im CDN-Netz verwendet werden. Dm-crypt arbeitet auf der Ebene des Blockgeräts und führt die Verschlüsselung von Schreib-I/O-Anfragen und die Entschlüsselung von Leseanfragen durch, indem es als Schicht zwischen dem Blockgerät und dem Dateisystemtreiber fungiert.
Zur Bewertung der Leistung von dm-crypt wird das Paket Es wurde eine Geschwindigkeitsmessung der Verarbeitung mit verschlüsselten und unverschlüsselten Partitionen auf einem RAM- Laufwerk, das im RAM platziert ist, durchgeführt, um Schwankungen der Laufwerksleistung auszuschließen und sich auf die Leistung des Codes zu konzentrieren. Bei den unverschlüsselten Partitionen blieb die Lese- und Schreibgeschwindigkeit bei 1126 MB/s, aber mit aktivierter Verschlüsselung fiel die Geschwindigkeit. um das 7-fache und betrug 147 MB/s.
Zunächst gab es den Verdacht, dass ineffiziente Algorithmen im Kern-Kryptosystem verwendet wurden. Bei den Tests wurde jedoch der schnellste Algorithmus aes-xts mit einem 256-Bit-Verschlüsselungsschlüssel verwendet, dessen Leistung bei der Ausführung des „cryptsetup benchmark“ mehr als doppelt so hoch war wie das bei den Tests des RAM-Laufwerks erzielte Ergebnis. Experimente mit den Flags von dm-crypt zur Leistungsoptimierung zeigten keine Ergebnisse: Bei Verwendung des Flags „—perf-same_cpu_crypt“ fiel die Leistung sogar auf 136 MB/s, während sie mit dem Flag „—perf-submit_from_crypt_cpus“ nur auf 166 MB/s anstieg.
Eine tiefere Analyse der Funktionsweise hat gezeigt, dass dm-crypt nicht so einfach ist, wie es scheint – wenn der Dateisystemtreiber einen Schreibantrag sendet, wird dieser nicht sofort von dm-crypt verarbeitet, sondern in die Warteschlange «kcryptd» gelegt, die nicht sofort bearbeitet wird, sondern zu einem geeigneten Zeitpunkt. Aus der Warteschlange wird der Antrag an die Linux Crypto API gesendet, um die Verschlüsselung durchzuführen. Da die Crypto API jedoch ein asynchrones Ausführungsmodell verwendet, erfolgt die Verschlüsselung ebenfalls nicht sofort und überspringt eine weitere Warteschlange. Nach Abschluss der Verschlüsselung kann dm-crypt versuchen, die ausstehenden Schreibanträge mithilfe eines Suchbaums zu sortieren. . Am Ende übernimmt ein separater Kernel-Thread nach einer gewissen Verzögerung die angesammelten Ein-/Ausgabe-Anfragen und sendet sie an den Blockgeräte-Stack.
Beim Lesen fügt dm-crypt zunächst eine Anfrage zum Abrufen von Daten vom Speicher in die Warteschlange «kcryptd_io» ein. Nach einer Weile werden die Daten verfügbar und in die Warteschlange «kcryptd» zur Entschlüsselung gelegt.
Kcryptd sendet eine Anfrage an die Linux Crypto API, die die Informationen asynchron entschlüsselt. Anfragen durchlaufen nicht immer alle Warteschlangen, aber im schlimmsten Fall verbleibt eine Schreibanfrage bis zu 4 Mal in den Warteschlangen, während eine Leseanfrage bis zu 3 Mal verbleiben kann. Jedes Eintreffen in der Warteschlange führt zu Verzögerungen, die die Hauptursache für den signifikanten Leistungsabfall von dm-crypt sind.
Der Einsatz von Warteschlangen ist durch die Notwendigkeit bedingt, in Situationen mit Unterbrechungen zu arbeiten. Im Jahr 2005, als das aktuelle Modell von dm-crypt auf der Basis von Warteschlangen implementiert wurde, war die Crypto API noch nicht asynchron. Nach der Umstellung der Crypto API auf ein asynchrones Ausführungsmodell kam im Wesentlichen ein doppelter Schutz zum Einsatz. Warteschlangen wurden auch zur Einsparung des Speicherverbrauchs des Kernels eingeführt, doch nach dessen Erhöhung im Jahr 2014 verloren diese Optimierungen ihre Relevanz. Eine zusätzliche Warteschlange "kcryptd_io" wurde eingeführt, um das Engpassproblem zu überwinden, das zu Wartezeiten bei der Zuweisung von Speicher führte, wenn eine große Anzahl von Anfragen eintraf. Im Jahr 2015 wurde zusätzlich eine Sortierungsphase eingeführt, da Verschlüsselungsanfragen auf Multiprozessorsystemen nicht in der Reihenfolge abgeschlossen werden konnten, in der sie übermittelt wurden (anstatt sequentiellen Zugriffs auf die Festplatte wurde zufälliger Zugriff durchgeführt, und der CFQ-Scheduler arbeitete ebenfalls ineffizient). Derzeit hat die Sortierung bei der Verwendung von SSD-Speichern an Bedeutung verloren, und der CFQ-Scheduler wird im Kernel nicht mehr verwendet.
Angesichts der Tatsache, dass moderne Speicher schneller und intelligenter geworden sind, wurde das Ressourcenverteilungssystem im Linux-Kernel überarbeitet und einigeSubsysteme neu gestaltet, so die Ingenieure von Cloudflare. In dm-crypt gibt es einen neuen Betriebsmodus, der die Verwendung überflüssiger Warteschlangen und asynchroner Aufrufe vermeidet. Der Modus wird mit einem speziellen Flag „force_inline“ aktiviert und verwandelt dm-crypt in eine einfache Proxy-Anwendung, die eingehende Anfragen verschlüsselt und entschlüsselt. Die Interaktion mit der Crypto API wurde optimiert, indem explizit Verschlüsselungsalgorithmen ausgewählt wurden, die im synchronen Modus arbeiten und keine Anfragereihen verwenden.Für die synchronen Arbeiten mit der Crypto API wurde ein Modul implementiert, das die Verwendung von FPU/AES-NI zur Beschleunigung ermöglicht und Anfragen zur Verschlüsselung und Entschlüsselung direkt weiterleitet.
Insgesamt konnte die Leistung von dm-crypt bei Tests mit RAM-Disk um mehr als das Zweifache gesteigert werden – die Leistung stieg von 294 MB/s (2 x 147 MB/s) auf 640 MB/s, was sehr nah an der Leistung von roher Verschlüsselung (696 MB/s) liegt.
Bei Lasttests auf realen Servern zeigte die neue Implementierung eine Leistung, die der Konfiguration ohne Verschlüsselung sehr ähnlich war, und die Aktivierung der Verschlüsselung auf Servern mit Cloudflare-Cache hatte keinen Einfluss auf die Antwortgeschwindigkeit. In Zukunft plant Cloudflare, die vorbereiteten Patches in den Hauptkern von Linux zu integrieren, muss sie jedoch zuvor überarbeiten, da sie für bestimmte Lasten optimiert sind und nicht alle Anwendungsbereiche abdecken, wie zum Beispiel die Verschlüsselung auf leistungsschwachen eingebetteten Geräten.
Quelle: opennet.ru
