
Ich muss Daten von einer 2 TB großen Festplatte retten und mache das in einem Live-Linux in einer VM, an die die problematische Festplatte über USB 3 angeschlossen ist und die VM lokal eine virtuelle Festplatte der benötigten Größe bereitstellt, um die Daten zu empfangen. Ich habe dann den folgenden Aufruf ausgeführt, einfach um zu sehen, wie es läuft:
ddrescue -f /dev/sdc /dev/sdb /mnt/sda1/ddrescue.map
sdc
Das defekte Gerät befindet sich am USB-Port, sdb
ist die virtuelle Festplatte zum Empfangen der Daten, sda1
dient zur temporären Speicherung und ist mit Ext4 formatiert.
Die Dinge begannen schnell zu funktionieren, ddrescue
ich konnte innerhalb von Minuten ~45 GB Daten lesen, dann wurden die Dinge massiv langsamer und lasen tagelang nur einige Bytes pro Sekunde. Das Gerät war also offensichtlich an diesen Stellen defekt und ich versuchte, diese einfach zu überspringen, indem ich mehrere Aufrufe nacheinander durchführte --input-position=[...]GB
. Je nachdem, wohin ich sprang, begannen die Dinge wieder schnell zu lesen, bis sie wieder langsam wurden und ich mit einem anderen Aufruf erneut sprang. Wichtig zu beachten ist, dass die von ausgegebenen Eingabe- und Ausgabepositionen ddrescue
immer synchron waren! Ich habe auch in der bereitgestellten Map-Datei nichts manuell geändert oder gelöscht oder was auch immer, es war immer ein und dieselbe Datei und wurde nur von ddrescue
sich selbst verwaltet.
Anschließend habe ich die Vorgehensweise etwas abgeändert und mich dazu entschlossen, nicht --input-position
mehr manuell vorzugehen, sondern stattdessen Folgendes zu verwenden:
ddrescue -f --min-read-rate=1MB --skip-size=1MB /dev/sdc /dev/sdb /mnt/sda1/ddrescue.map
Wenn also ddrescue
langsame Teile erkannt wurden, übersprang es logischerweise defekte Datenblöcke und setzte das Lesen fort. Wieder waren Eingabe- und Ausgabeposition synchron und der Zähler der gelesenen und geretteten Daten stieg ständig an. Bis zu diesem Punkt waren wir ddrescue
fertig und angeblich wurden ~650 GB Daten gerettet.
Das Problem ist, dass nach einem Blick auf die Dateien der virtuellen Festplatte selbst anscheinend nur etwa 160 GB Daten gespeichert sind. Außerdem war der letzte Schreibzeitstempel einige Tage zu alt. Aus irgendeinem Grund ddrescue
dachte ich also, dass viele Daten gelesen wurden, aber es schien, als ob sie nicht richtig an den Stellen auf der virtuellen Festplatte geschrieben wurden, wo sie von der defekten Festplatte gelesen wurden. Letztendlich hätte die virtuelle Festplatte meines Wissens nach mindestens die ddrescue
angegebene Größe haben müssen, was die Menge der geretteten Daten betrifft.
Ich habe das Gefühl, dass ddrescue
es zwar alle Daten richtig gelesen hat, aber bei nachfolgenden Aufrufen bereits gerettete Daten einfach überschrieben hat. Während es also vermutlich erkannt hat, --input-position
dass es gelesen hat, scheint es beim Ziel immer wieder ab Position 0 neu geschrieben zu haben.
Offensichtlich habe ich nicht die Startposition angegeben, an die Daten geschrieben werden sollen, aber lautDokumentedas sollte nicht nötig sein und ddrescue
die gedruckte Eingabe- und Ausgabeposition sollte sowieso immer gleich sein.
-o bytes
--output-position=bytes
Starting position of the image of the rescue domain in outfile, in bytes.
Defaults to '--input-position'. The bytes below bytes aren't touched if
they exist and truncation is not requested. Else they are set to 0.
Natürlich habe ich keine Kürzung angefordert, denn laut Dokumentation ist sie standardmäßig nicht aktiviert und hätte für das von mir angegebene Ziellaufwerk nicht einmal funktioniert:
-t
--truncate
Truncate outfile to zero size before writing to it. Only works for regular
files, not for drives or partitions.
Also, irgendeine Idee, was schiefgelaufen sein könnte? Waren meine mehrfachen Aufrufe mit unterschiedlichen Werten --input-position
bereits falsch? Hat es mit dem Lesen und Schreiben auf Laufwerken statt auf Partitionen oder Dateien zu tun?
Vielleicht ein Problem beim Schreiben auf eine virtuelle Festplatte? Ich sehe allerdings nicht, warum das einen Unterschied machen sollte, da ich auf eine virtuelle Festplatte schreiben muss und keinen Rohgerätespeicher der erforderlichen Größe bereitstellen kann.
Danke!
Antwort1
--input-position
Ist es sicher , mit ddrescue mehrere verschiedene zu verwenden ?
Scheint, als hätte ich dieses Beispiel zuvor übersehen, aber genau das habe ich getan und es deutet darauf hin, dass mein Ansatz unterstützt wird:
Example 5: While rescuing a partition in /dev/sda1 to the file hdimage, /dev/sda1 stops responding and begins returning read errors, causing ddrescue to mark the rest of the partition as non-scraped.
ddrescue -n /dev/sda1 hdimage mapfile <-- /dev/sda1 fails here
(restart /dev/sda or reboot computer)
ddrescue -n -A -i<pos> -O /dev/sda1 hdimage mapfile
(if /dev/sda1 fails again, restart /dev/sda or reboot computer and
then repeat the above command as many times as needed until it
succeeds. <pos> is the position where the drive stopped responding)
ddrescue -d -r3 /dev/sda1 hdimage mapfile
https://www.gnu.org/software/ddrescue/manual/ddrescue_manual.html#Beispiele
Der zweite Aufruf ist eindeutig so dokumentiert, dass er an verschiedenen Positionen wiederholt wird. In Anbetracht der Funktionsweise ddrescue
anhand der Map-Datei ist dies auch sinnvoll, da anhand dieser Datei immer bekannt ist, welche Blöcke bereits gelesen wurden.
Es ist also sehr wahrscheinlich, dass das Problem in meinem Fall anders ist. Besonders der zu alte Zeitstempel, den ich zu erkennen glaube, ist seltsam. Vielleicht habe ich einfach Nachrichten übersehen, die ddrescue
aus irgendeinem Grund nicht auf das echte Zielgerät geschrieben werden. Die VM selbst befand sich ebenfalls auf einem anderen USB-Laufwerk, vielleicht gab es Verbindungsfehler, die dazu führten, dass das Gerät während der Laufzeit vom Live-Linux nicht erkannt wurde oder so. Ich hätte solche Fehler aufgrund dmesg -T
der vielen protokollierten Lesefehler leicht übersehen können.
Klingt, als müsste ich den gesamten Vorgang wiederholen ...
Antwort2
Ich habe das ddrescue
Handbuch gelesen und nirgends wird die Möglichkeit mehrerer input-position
Parameter erwähnt.
Dieser Parameter wird immer als „a“ oder „the“ erwähnt, daher scheint es, dass er eindeutig sein muss.
Die Ursache Ihres Problems könnte dieser Satz aus dem Handbuch sein:
Beachten Sie, dass Sie den ursprünglichen Offset zwischen „--input-position“ und „--output-position“ des ursprünglichen Rettungslaufs beibehalten müssen.
Dies scheint mit dem folgenden anderen Absatz übereinzustimmen:
Ddrescue schreibt keine Nullen in die Ausgabe, wenn es fehlerhafte Sektoren in der Eingabe findet, und kürzt die Ausgabedatei nicht, wenn es nicht dazu aufgefordert wird. Jedes Mal, wenn Sie es auf derselben Ausgabedatei ausführen, versucht es, die Lücken zu füllen, ohne die bereits geretteten Daten zu löschen.
Das bedeutet, dass ddrescue
die Parameter vom ersten Durchlauf gespeichert werden, sodass Sie immer dieselben Parameter beibehalten oder sie bei nachfolgenden Durchläufen einfach nicht angeben sollten (ich kann nicht sagen, was richtig ist). Es ist durchaus möglich, dass einige Parameter gespeichert wurden und Ihre neuen bei nachfolgenden Durchläufen ignoriert wurden.
Wenn Teile der Metatabellen der Festplatte beschädigt wurden, werden Ihnen möglicherweise weniger Daten angezeigt, als tatsächlich gerettet werden konnten, da diese Teile scheinbar in keiner Datei enthalten sind.
Die Daten, die ddrescue
nicht gerettet werden können, müssen mit anderen Wiederherstellungsprodukten wiederhergestellt werden. Dies kann lange dauern und ist mit den Produkten, die Ihnen zur Verfügung stehen, möglicherweise sogar unmöglich. Wenn die Daten unbedingt wiederhergestellt werden müssen, kann dies möglicherweise ein professionelles Wiederherstellungsunternehmen von der Originalfestplatte aus tun, aber diese Dienste sind kostspielig.
Antwort3
Da die Manpage von ddrescue
lang ist, ist die Verwendung von ddrescue
je nach Ziel und Benutzerebene sehr unterschiedlich. Wenn Sie Live Linux verwenden, sollten Sie es grundsätzlich besser auf der physischen Maschine statt auf einer VM ausführen und die Festplatte auch ohne SATA/USB-Adapter an SATA anschließen.
Zu den weiteren Funktionen ddrescue
gehört, dass der Kernel-Festplattentreiber und die Puffer umgangen werden können, wodurch das nutzlose wiederholte Lesen fehlerhafter Cluster reduziert werden kann. Die Map-Datei (früher Logdatei genannt) enthält Informationen zu allen nicht/erfolgreich gelesenen Clustern, und deshalb können Sie den abgestürzten Schritt einfach wiederholen. Das Programm ddrescue
sucht nach der Map-Datei, bevor es seinen Job startet, erstellt sie, wenn sie nicht existiert, liest sie, wenn sie verfügbar ist, und beginnt mit der Fortsetzung des Rettungsjobs an der letzten aufgezeichneten Position. Sie müssen die Startposition nicht jedes Mal manuell verschieben, wenn das Programm abstürzt!
Sie können verschiedene Optionen nutzen, um den Rettungsvorgang schneller und sicherer zu machen. Sie können den Rettungsvorgang auch in zwei oder mehr Schritten durchführen (was empfohlen wird):
Erster Schritt: Lesen Sie schnell die guten Cluster und überspringen Sie die schlechten sofort.
Zweiter Schritt: Behandeln Sie die ungelesenen Cluster aus dem vorherigen Schritt und verwenden Sie spezielle Optionen, um die Festplattenfunktionen (NCQ, Vorauslesen ...) auszutricksen, damit ein Sektor auf einmal gelesen werden kann. Die entsprechenden Befehle (die ich verwende):
ddrescue -n -p -d -r1 /dev/sdd $IMGPATH/disk.img $IMGPATH/disk.log;
ddrescue -d -r3 -R /dev/sdd $IMGPATH/disk.img $IMGPATH/disk.log;
# | | | | |
# | | | | revers reading
# | | | retry read 1x (3x)
# | | direct access to disk (bypass the kernel)
# | preallocate diskspace
# nonscrap
Wenn Ihre Festplatte zu heiß wird oder nicht zu viele Lesevorgänge pro Sekunde verträgt, können Sie den Lesevorgang mit der folgenden Option verlangsamen:--max-read-rate=50M
Dies gilt also nur für den ersten Kontakt, aber Sie können in spezialisierten Clubs oder Foren viele Ratschläge dazu finden ddrescue
.