Wiederherstellung von verlorenen Bildern

Angelegt von Andreas Steinel Fri, 29 Sep 2006 16:50:00 GMT

Da macht man schön Bilder … ganze CF-Karten voll und dann sowas. Eingelegt … nix. Er kann es nicht mounten und die CF-Karte war voller Bilder! Dateisystem zerstört, Hilfe!

FreeBSD kann es nicht mounten und Windows kann erst garnix damit anfangen. Klasse, dachte ich mir … was nun?

Als erstes hab ich mir die CF-Karte als Image mittels cp auf den Rechner gezogen. Danach habe ich die Wiederstellungsprozedur gestartet:

Als erstes habe ich mir angeschaut, wie ein Bild eigentlich binär aussieht und konnte die ersten 8 Bytes, die bis auch eine Stelle immer identisch sind, feststellen. Mit diesem Wissen kann man nun grepen. Dabei hatte ich zuerst im Sinn, ein C-Programm zu schreiben, welches die Daten binär identifizieren kann. Schlussendlich habe ich aber nur hexdump und grep zum Finden der Offsets verwendet.

Dabei habe ichzuerst eine Liste der Offsets für jedes Bild erstellen lassen:

hexdump -C ~/CF-Sicherung-mit-Bildern.iso| grep Exif >| grep-result

Eine solche Zeile mit dem Offset sieht wie folgt aus:

00049000 ff d8 ff e1 31 fe 45 78 69 66 00 00 49 49 2a 00 |....1.Exif..II*.|

Die erste Zahl ist das Offset (hexadezimal), danach kommen 16 Bytes an Daten in Bytes und nach der Pipe kommt der Teil als Ascii-Zeichen.

Mit diesen Informationen ist es nun möglich die Bilder zu exrtahieren. Einziger Nachteil bei dieser Rekonstruktion stellt die Dateisystemfragmentation dar. Sobald ein Bild auf dem Dateisystem fragmentiert wurde ist es unmöglich dieses mit dieser Methode wiederherzustellen. Aber es ist zumindest ein Ansatz.

Nun habe ich mir noch ein Ruby-Skript geschrieben, mit dem man die Daten anhand des Offsets wiederherstellen kann. Dabei werden einfach eine gewisse Menge von Bytes (hier 4.6 MB) nach dem gefundenen Offset kopiert. Dies entspricht dem Herauskopieren des vermeindlichen Bildes. Am einfachsten geht dies mit dd und der skip-Option. Aus Performancegründen ist es ratsam, immer 16-Byte-Blöcke zu benutzen, aber nicht notwendig. folgendes Skript wird verwendet, um die Daten zu extrahieren:

1
2
3
4
5
6
7
8
9
#!/usr/bin/env ruby

raw = File.open("grep-result").readlines
raw.each_index do |i|
    size = raw[i].split(" ")[0].to_s.to_i(16) / 16
    puts size
    Kernel.system "dd if=/home/andreas/CF-Sicherung-mit-Bildern.iso" +
        " of=#{i.to_s.rjust(3,"0")}.jpg count=250000 bs=16 skip=#{size}"
end

Viele Bilder wurden komplett wiederhergestellt, leider nicht alle. Dort gab es fragmentierungsprobleme und die Bilder sind teilweise zerstört. Dies ist schade, aber ich muss damit leben. Wenigstens konnte ich mehr als 70% der Bilder retten.

Zu guter letzt habe ich alle Bilder durch convert gejagt, um den Datenmüll, der sich am Ende jedes Bildes befindet, loszuwerden. Dieser Datenmüll ist durch das Kopieren entstanden.

Resultat:

Es wurden 102 Bilder extrahiert, eines ist komplett kaputt, 9 teilweise kaputt und 92 Bilder sind restauriert. Das sind knapp über 90%! Juhuu

Posted in , ,  | 1 comment

Comments

  1. elrodeo sagte 4 days later:

    Hammer!

Kommentare sind deaktiviert