Wie finde ich Datenkopien einer bestimmten Datei im Btrfs-Dateisystem?

Wie finde ich Datenkopien einer bestimmten Datei im Btrfs-Dateisystem?

Ich habe mein Btrfs-Dateisystem mit bedup dedupliziert, sodass jetzt alle doppelten Dateien (über einer bestimmten Größe) „Reflink“-Kopien sind.

Gibt es eine Möglichkeit, anhand eines Dateinamens zu erkennen, welche anderen Dateien dieselben Reflinks sind?

Antwort1

Der Sinn eines Copy-On-Write (CoW)-Dateisystems wie btrfs besteht darin, dass der Inhalt mehrerer Versionen einer Datei effizient geteilt werden kann. Sie können eine Datei also als eine Sammlung von Bereichen mit Inhalten betrachten, wobei der Inhalt von anderen Dateien geteilt werden kann oder nicht. Oder von anderen Versionen der Datei. Die Implementierung ähnelt eher einem Baum von Erweiterungen, wobei Erweiterungen geteilt werden können.

Derselbe Mechanismus, der beim Schreiben einer Änderung in eine Datei (und damit beim Erstellen einer neuen Version dieser Datei) funktioniert, wird auch für die Deduplizierung verwendet. Die Implementierung ist beschrieben unterhttps://github.com/g2p/bedup:

Die Deduplizierung wird mithilfe einer Btrfs-Funktion implementiert, die das Klonen von Daten von einer Datei in eine andere ermöglicht. Die geklonten Bereiche werden auf der Festplatte freigegeben, wodurch Speicherplatz gespart wird.

Die Implementierung im Kernel ist (zum Beispiel) beihttp://lxr.free-electrons.com/source/fs/btrfs/ioctl.c#L2843; der Kommentar macht deutlich, dass es nicht um das 'Relinken' der Datei geht, sondern um Bereiche:

2843 /**
2844  * btrfs_clone() - clone a range from inode file to another
2845  *
2846  * @src: Inode to clone from
2847  * @inode: Inode to clone to
2848  * @off: Offset within source to start clone from
2849  * @olen: Original length, passed by user, of range to clone
2850  * @olen_aligned: Block-aligned value of olen, extent_same uses
2851  *               identical values here
2852  * @destoff: Offset within @inode to start clone
2853  */

Es ist also nicht die Datei, die neu verknüpft wird, sondern der Bereich, der freigegeben wird. Eine neue Datei könnte auch erstellt worden sein, indem der Bereich mit mehreren Dateien geteilt wird. Oder indem er über mehrere Datenträger hinweg geteilt wird. Oder (ich bin nicht sicher, ob dies derzeit unterstützt wird) sogar indem derselbe Bereich mehrmals in derselben Datei vorhanden ist ;)

Daher gibt es kein High-Level-Tool, um Dateien zu finden, die die gesamte Datei gemeinsam nutzen, da dies ein abgeleitetes Konzept ist. Natürlich wäre es möglich, Unterstützung dafür zu schreiben, aber das ist meines Wissens nicht der Fall ...

Antwort2

Ich habe gerade ein Programm veröffentlicht namensfienode(← Link), der einen SHA1-Hash der physischen Ausdehnung einer Datei berechnet. Identische CoW-Kopien haben denselben Hash.

Im Prinzip können Sie dies für alle Dateien im Dateisystem ausführen und dann nach identischen Hashes suchen.

Hier gibt es auch eine ausführlichere Antwort, warum das notwendig ist.

Beachten Sie jedoch, dass BTRFS die physischen Ausdehnungen beliebig ändern kann. Ich habe beobachtet, dass eine große, neu verknüpfte Datei ihre physischen Ausdehnungen ohne Aufforderung änderte, wodurch die fienodeAusgabe anders wurde, obwohl die Mehrheit der physischen Ausdehnungen noch gemeinsam genutzt wurde.

verwandte Informationen