Barrieren und journalisierte Dateisysteme

Allen ein hervorragendes Wochenende! Wir laden zu einem kostenlosen Demo-Kurs ein „Konfiguration des Webservers (Apache, Nginx, Nginx Lastverteilung)“, den Andrei Buranov – Spezialist für UNIX-Systeme bei Mail.Ru Group – leitet. Außerdem veröffentlichen wir einen Artikel von Jonathan Corbet – Executive Editor bei LWN.net.

Journalierte Dateisysteme versprechen, Systemadministratoren von Problemen mit Festplattenschäden bei Systemausfällen zu befreien. Sogar ohne die Ausführung der Integritätsprüfung des Dateisystems. In der Realität ist natürlich alles etwas komplizierter. Und wie eine kürzliche Diskussion zeigt, kann es sogar verwirrender sein, als viele von uns denken, da die Sicherstellung der Integrität von journalisierten Dateisystemen die Leistung beeinflusst.

Ein Dateisystem wie ext3 nutzt einen separaten Bereich auf der Festplatte, der als Journal bezeichnet wird. Bei Änderungen an den Metadaten des Dateisystems werden diese Änderungen zuerst in das Journal geschrieben, ohne das restliche Dateisystem zu modifizieren. Nach dem Schreiben aller Änderungen in das Journal wird ein „Commit-Block“ hinzugefügt, der das Ende der Transaktion anzeigt. Erst nach dem Schreiben des Commit-Blocks wird die Transaktion fixiert und die geänderten Metadaten werden auf die Festplatte geschrieben. Wenn das System irgendwann ausfällt, kann mit den Informationen im Journal sicher abgeschlossen und Schäden am Dateisystem vermieden werden, da nur ein Teil der Metadaten aktualisiert wurde.

Es gibt jedoch einen Haken: Der Code des Dateisystems muss vor dem Schreiben des Commit-Blocks absolut sicher sein, dass alle Informationen zur Transaktion bereits im Journal sind. Es reicht nicht aus, die Vorgänge in der richtigen Reihenfolge zu schreiben – moderne Festplatten unterstützen große interne Caches und ordnen Vorgänge zur Leistungsverbesserung neu an. Daher muss vor dem Commit-Block ausdrücklich angegeben werden, dass alle Journal-Daten auf die Festplatte übertragen werden. Wenn der Commit-Block zu früh geschrieben wird, kann das Journal beschädigt werden. Zur Lösung dieses Problems werden Barrieren eingesetzt. Im Wesentlichen verbietet eine Barriere das Schreiben von Blöcken nach der Barriere, bis alle vor der Barriere geschriebenen Blöcke auf die Festplatte übertragen sind. Durch die Verwendung von Barrieren gewährleisten Dateisysteme die Konsistenz der Datei-strukturen.

Es gibt jedoch ein weiteres Problem: Die Dateisysteme ext3 und ext4 verwenden standardmäßig keine Barrieren. Es gibt eine Option, aber wenn der Administrator sie nicht ausdrücklich aktiviert hat, arbeiten diese Dateisysteme ohne Barrieren, obwohl in einigen Distributionen (zum Beispiel SUSE) die Standardwerte anders sind. Eric Sandeen hat kürzlich beschlossen, dass man diese Situation ändern muss und hat einen Patch erstellt, der die Standardkonfigurationen für ext3 und ext4 modifiziert. Und dann begann eine lebhafte Diskussion.

Andrew Morton hat sehr ausführlich geantwortet, warum der Standardwert genau so ist:

Beim letzten Versuch, dies zu ändern, hat sich die Leistung bei vielen Lasten um 30 % verschlechtert, daher habe ich entsetzt alle diese Patches verworfen. Ich denke, wir können es uns nicht leisten, die Leistung aller Maschinen so ernsthaft zu verlangsamen…

Es gibt keine perfekten Lösungen, und ich neige dazu, diese schlafenden Hunde nicht zu wecken und die Standardparameter den Entwicklern der Distributionen zu überlassen.

Somit sind Barrieren standardmäßig deaktiviert, da sie die Leistung erheblich beeinflussen. Darüber hinaus werden die Dateisysteme durchaus erfolgreich ohne Barrieren genutzt. Berichte über Beschädigungen beim ext3-Dateisystem sind rare Ausnahmen.

Aber das ist nicht einfach Glück. Ted Ts'o erklärt liegt daran, dass das Journal bei ext3/ext4 normalerweise kontinuierlich angelegt wird. Erstens versucht der Treiber des Dateisystems, es kontinuierlich zu erstellen. Zweitens wird das Journal in der Regel gleichzeitig mit dem Dateisystem erstellt, wenn es einfach ist, einen kontinuierlichen Speicherplatz zu finden. Kontinuität und Ordnung sind nicht nur für die Leistung nützlich, sondern auch, um eine Neuanordnung zu verhindern. Normalerweise wird der Commit-Block direkt nach den anderen Daten im Journal platziert, sodass es für das Laufwerk keinen Grund gibt, umzustrukturieren. Der Commit-Block wird natürlich unmittelbar nach den anderen Journalaufzeichnungen auf das Laufwerk geschrieben.

Dennoch behauptet niemand, dass dies immer so sein wird. Festplatten können sich auch anders verhalten. Darüber hinaus ist das Journal ein Ringpuffer. Wenn eine Transaktion also ans Ende des Journals geschrieben wird, kann der Commit-Block in einem früheren Block erscheinen, vor anderen Journalaufzeichnungen. Daher besteht immer die Wahrscheinlichkeit einer Beschädigung. Tatsächlich hat Chris Mason dafür TestsEs besteht kein Zweifel, dass die Arbeit ohne Barrieren weniger sicher ist als mit ihnen.

Wenn Sie bereit sind, einen Leistungseinbruch in Kauf zu nehmen, können Sie die Barrieren aktivieren. Vorausgesetzt, Ihr Dateisystem basiert nicht auf LVM (wie es bei einigen Distributionen standardmäßig der Fall ist). Es stellt sich heraus, dass der Device Mapper Barrieren nicht unterstützt. In anderen Fällen wäre es nicht schlecht, den Leistungsverlust zu verringern. Und anscheinend lässt sich das umsetzen.

Die aktuelle Implementierung von ext3 (wenn Barrieren aktiviert sind) führt für jede Transaktion die folgende Folge von Operationen aus:

  1. Daten werden in das Journal geschrieben

  2. Ein Barrier wird ausgeführt

  3. Ein Commit-Block wird geschrieben

  4. Der nächste Barrier wird ausgeführt

  5. Später werden Metadaten auf die Festplatte geschrieben

In ext4 kann der erste Barrier (Schritt 2) weggelassen werden, da das Dateisystem ext4 Prüfziffern im Journal unterstützt.

Wenn die Journal-Daten und der Commit-Block neu angeordnet sind und die Operation infolge eines Fehlers unterbrochen wird, stimmt die Prüfziffer des Journals nicht mit der im Commit-Block überein, und die Transaktion wird abgelehnt. 

Chris Mason glaubt, dass es „im Allgemeinen sicher“ wäre, diesen Barrier auch in ext3 zu entfernen, mit möglicher Ausnahme, wenn das Journal zu Ende kommt und von vorne zu schreiben beginnt. 

Eine weitere Idee zur Leistungssteigerung ist es, Barrier-Operationen, wenn möglich, zu verzögern. Wenn es nicht dringend erforderlich ist, Daten sofort auf die Festplatte zu schreiben, können mehrere Transaktionen im Journal erstellt werden, die dann mit einem Barrier auf die Festplatte geschrieben werden.

Es gibt auch ein gewisses Potenzial zur Verbesserung durch sorgfältige Anordnung der Operationen, damit die Barrieren (die normalerweise als Abfragen „alle ausstehenden Operationen auf die Festplatte zurücksetzen“ implementiert sind) die Schreibvorgänge von Blöcken, die keine Ordnung erfordern, nicht erzwingen.

Es scheint an der Zeit zu sein, darüber nachzudenken, wie die Kosten für Barrieren akzeptabel gestaltet werden können. Ted Tso scheint ähnlich zu denken:

Ich denke, wir sollten Barrieren in ext3/4 einführen und dann an der Verringerung der Overheadkosten in ext4/jbd2 arbeiten. Höchstwahrscheinlich arbeiten die überwiegende Mehrheit der Systeme nicht in Bedingungen, die denen ähneln, die Chris zur Demonstration des Problems verwendet hat, und die Sicherheit des Dateisystems sollte Priorität haben.

Der gesunde Menschenverstand sagt mir, dass dieser Hund jetzt nicht mehr schläft und wahrscheinlich eine Weile bellen wird. Das könnte einige Nachbarn beunruhigen, aber es ist besser, als ihm zu erlauben, zu beißen.

Interessiert es Sie, sich in diesem Bereich weiterzuentwickeln? Melden Sie sich für eine kostenlose Demo-Stunde an „Konfiguration des Webservers (Apache, Nginx, Nginx Lastverteilung)“ und nehmen Sie an der Übertragung teil „Arbeiten mit Protokolldateien in Linux“, die von Pawel Wikiryuk — MVNO-Operator, DevOps-Ingenieur, durchgeführt wird.

Quelle: habr.com

60GB SSD 8Gb DDR4