ホーム

Linux ユーザのためのデータ救出


OSの入ったハードディスクに物理的な障害が起こっているとしましょう。 Linux だけだと楽ですが、Windows が入っている人も多いはず。 読み込みエラーが一ヶ所でも起こるディスクだと @IT:Windowsからのイメージ・バックアップが可能となった.... のようなツールは、さんざん待たせたあげく、エラー箇所で停止して、 役に立たないようです。

そこで、多少エラーの起こるディスクから、 大部分の正常なデータを復旧する方法を、 Linux ユーザの視点から考えてみます。 OS やアプリも丸ごとコピーして、 再インストールせずにすませることを目指します。

なお、OS を再インストールしてよいのであれば、 単に外付けディスクとして認識させて、 Windows からでも KNOPPIX からでも、 自分の作ったファイルだけをコピーしてやる手もあります。 (その中に読めないファイルがあると面倒ですが。)


基本は KNOPPIX!

 OS の入っているディスクが死にかけているのなら、 そのディスクに書き込むことは危険です。 入っている OS を立ち上げたりせずに、 CD からブートできる KNOPPIX を使って、 死にかけているディスクから、新品のディスクへとコピーするのがよいでしょう。 そして古いディスクを取り外し、新品のディスクに交換して完了です。

 KNOPPIX はインストール不要の 1CD Linux としてかなり完成されており、 デバイスの認識性能がよいと言われています。 KNOPPIX 日本語版 も開発されており、 以下では knoppix_20031119-20040202 (3.3)KNOPPIX5.3.1CD日本語版(LCAT対応) について試したことを書いておきます。


ハードディスクの取扱い

 ハードディスクに障害が起こる原因は、いろいろ考えられます。 ベアリング(回転軸)の寿命だとすれば、 ベアリングに負担がかからないよう、 運用してきたままの水平か垂直かのどちらかの姿勢になるようにしましょう。 傾けたり、振ったりしては障害を増やすばかりです。

 冷却することも重要です。触れないぐらい熱くなるようだと、 扇風機で冷ますことも効果があるかもしれません。

 そして重要なことですが、部分的に読み取れない程度の障害だと、 数日放置しておくと、 嘘のようにデータが読めるようになっていることもあります。 読み取れないからといって、むやみにいろいろ試すより、 頭も機械も冷却して落ち着いてから作業しましょう。

 嘘のように復旧してデータが読めるようになっても、 それで直ったとは思わず、すかさずデータを救出しましょう。 数日経てば、また障害が再発することが目に見えています。

 もっとも、ノートパソコンのハードディスクの場合、読み込みエラーが出ても、 その上から書き込んでしまえば正常に動くようになる、 ということを何度も経験しています。 たまたま最初の書き込み時に振動でもあって、 書き込み位置がずれてしまって読み込みエラーになってたのでしょうか。

 また、デスクトップ本体の電源が不安定で、 そのマシンで書き込むと読み込みエラーが起こるけども、 別マシン(あるいは外付けケース)で書き込むと正常、という場面にも遭遇しました。 こういうエラーでも S.M.A.R.T のログに残ってしまうので、 ハードディスクに気の毒な気がしてしまう...


想定するハードウェア

 死にかけのディスクと、新品のディスクがあるとします。 CD-ROM ドライブからブートできる AT 互換機があるとします。 デスクトップですと、2台の 3.5 inch ドライブを内蔵するのが簡単です。

 ノートパソコンでは、内蔵の 2.5 inch ドライブが交換できることを想定します。 新品ドライブをUSB接続のHDケース(実売2000円〜)に入れて作業することにします。 USB は 2.0 で揃えておくことをお薦めします。1.1 ではあまりにも遅すぎます。 もちろん、2.5 inch → 3.5 inch 変換ケーブル(実売1000円〜)を使って、 デスクトップパソコンで操作してもよいです。

 USB 1.1 しかついてないマシンなら、 100BASE-TX のネットワーク経由で別マシンにデータ転送したほうが高速です。 そこで FTP で転送する方法も紹介します。


KNOPPIX の tips

 KNOPPIX はそこそこハードウェアを認識してくれて、 大抵 X も動くでしょうが、うまく動かない時や、 X が遅過ぎる時は、Alt + Ctrl + F2 でコンソールに切替えるのも手です。 元に戻るには Alt + Ctrl + F5 です。 あるいはブート時に 'knoppix 2' と指定すれば、 X を使わずにすみますし、起動も早いです。 LCAT 版を使えば、起動時の CD/DVD の読み込みが最適化されていて、 かなり高速です。

 さて、内蔵ディスクですが、 Linux の swap 領域があると KNOPPIX が使ってしまいます。 メモリが十分にあって、下手にディスクに書き込まれたくなければ、 ブート時に 'knoppix noswap' と指定します。

 'hdparm, dd' なんかのコマンドを使うには管理者権限が必要です。 それには 'su -' を実行します。(パスワードはいりません。)

 KNOPPIX3.3 では DMA 転送が有効になっていません。 'hdparm -d1 /dev/hda' しましょう。 KNOPPIX3.4 では自動で有効になるようです。 しかし、読み取りエラーが起こると無効になってしまうこともあります。 転送速度が遅くなったら、読み取り中でも別のシェルから 'hdparm -d1 /dev/hda' としてやることで、 有効にすることができます。

 また古い KNOPPIX 3.3 あたりでは USB が 1.1 のドライバで処理されてしまいます。 'modprobe ehci-hcd' としてモジュールを読み込んでから HD ケースを接続することで USB2.0 で処理することができます。 参考:@IT:USB 2.0のデバイスを使うには

 いずれの場合も、ディスクの転送速度を確認しておきましょう。 10MB/sec 以上の速度が出ていないと、この先の作業は非常につらいと思われます。 以下は手元のマシンの内蔵ディスクの実行例です。

# hdparm -Tt /dev/hda

/dev/hda:
 Timing buffer-cache reads:   128 MB in  0.79 seconds =162.03 MB/sec
 Timing buffered disk reads:  64 MB in  7.15 seconds =  8.95 MB/sec

 USB 接続ならデバイスファイルは /dev/sda になると思います。 dmesg コマンドの出力を確認して下さい。 シリアル ATA の内蔵 HD でも、/dev/sda になります。

 Knoppix のパッケージ選択の変更のあおりか、hdparm コマンドが入ってないケースが増えてきました。 ネットワークが使えれば、'apt-get update && apt-get install hdparm' を実行して、その場だけで使えるようにできます。

 'fdisk /dev/hda' でHDの情報を調べることができます。 パーティション操作をするためのコマンドですが、 プロンプトが出て 'p' コマンドでドライブ容量や ジオメトリ(シリンダ数・ヘッド数・セクタ数)を確認できます。 'q' で終了です。 コンソールで作業していて、日本語が化けるようだと 前もって 'LANG=C' を実行しておきます。

 S.M.A.R.T のログも見ておきましょう。

smartctl -a /dev/hda

 ドライブによっては S.M.A.R.T をサポートしてないこともあります。 内蔵なら使えても、外付け HDD ケースに入れると、サポートしてないと報告されることがあります。 また、smartctl コマンドが Knoppix の CD (DVD) に収録されてなければ、'apt-get update && apt-get install smartmontools' で、ネット経由でインストールすることができます。

 最近の光学ドライブの付いてないノートパソコンだと、 HDの一番後ろにリカバリーの為の隠し領域が3Gぐらいついていることが多いです。 USB ケースで接続すると、ドライブの容量がこの分だけ少なく認識されることがありました。 二種類のUSB ケースで試しても同じでした。 USB ケースの販売店に相談してみると、どうもそういうものらしいです。 内蔵すると普通に認識されました。 (試してはいませんが、この状態で隠し領域を解放してしまえば、 USB ケースに入れても全容量が認識されるようになると思います。)


まったく同じドライブで OS ごとコピー

 もしも死にかけのディスクと容量も同じ、さらにジオメトリ (シリンダ数・ヘッド数・セクタ数)まで同じディスクが用意できたとしましょう。 何も難しいことを考える必要はなく、 単に dd コマンドでコピーすれば、OS 丸ごとコピーできます。 ただし、エラーが起こっても中断してほしくないので、 少しオプションを付け加えます。

dd if=/dev/hdX of=/dev/sdX conv=sync,noerror bs=4096 count=1

 'conv=sync,noerror' がポイントで、 エラーが起こっても少しスキップして続きをコピーし続けます。 スキップする大きさが bs= で指定した大きさです。 あまり小さくすると転送速度が遅くなるようです。 エラーがたくさん起こるディスクだと、この値を大きくしておかないと、 いつまでたっても終わりません。 大きくしすぎると、エラー箇所の巻き添えで捨ててしまうデータが増えてしまいます。 bs=65536 のような値が指定しやすいでしょうか。

 count=1 は最終的には消去しますが、count=10、count=100 と値を増やして、 コピーの方向が合っていることを確認しましょう。 アクセスランプの点滅の順序が正しいでしょうか。 逆向けにコピーしたら元も子もありません。 そして、転送速度を測定しておきましょう。

 数秒でコピーが完了するまでになったら、 表示される転送速度は、キャッシュの影響もなくなり、 信用できる値になっているはずです。 いよいよ count= を消去して、ディスク全体をコピーしましょう。

 途中経過を見たくなったら、別窓から以下のように操作します。 dd の窓で転送量などの情報が表示されます。

killall -USR1 dd

 定期的に実行するには while 〜 sleep でも使えばよいでしょう。 以下の例では1分おきに情報表示させます。

while true; do killall -USR1 dd; sleep 60; done

 手元の環境では、4Mbyte/sec ぐらい、 エラーのある 30G の 2.5 inch IDE ドライブを丸ごとコピーするのに 1時間〜2時間ぐらいかかりました。


異なる容量のドライブで OS ごとコピー

 異なる容量、あるいは容量がほぼ同じでも異なるジオメトリのドライブにデータをコピーする場合、 ファイルの読み書きがある程度できるようになったとしても、 OS が boot できるとか、容量を無駄にせずに使いきるとかいうことを考えると、 MBR や boot フラグ?なんかの設定や、ファイルシステムのサイズ調整をすることになって、 ちょっと敷居が高くなります。保険のために、とにかく最初に

dd if=/dev/hdX of=/dev/sdX

 を実行して MBR をコピーして、数秒で Ctrl-C で止めてしまうのがよいと思います。 もちろん、嘘のパーティション情報までコピーされてしまうので、 直後に 'fdisk' コマンドで全パーティション削除して、 必要なサイズでパーティションを切り直します。 新しいパーティションを認識しなおすために、外付け USB ドライブなら抜き差し、 内蔵ドライブなら KNOPPIX の再起動を行います。

 VFAT や Linux の ext2/3 等なら一つのパーティションを コピーすればなんとかなるようです。

 VFAT なら、cp コマンドでもコピーできるかもしれませんが、 日本語ファイル名の扱いに不安が残るので、 パーティションごとコピーするのが安心です。 ただし、パーティションのサイズはほぼ同じ、 若干大きめにしておかないといけないでしょう。 パーティションのコピーには、 あらかじめ fdisk コマンドで確保したところに、 'dd if=/dev/hdX1 of=/dev/sdX1 conv=sync,noerror' のようなコマンドでコピーすればよいです。 ドライブ丸ごとコピーの手順とほぼ同じです。

 注意すべきは、起動したいパーティションに ブート可能フラグをつけることです。 fdisk コマンドの中の a コマンドで行えます。 (ひょっとするとパーティション確保も Windows の fdisk コマンドを使ったほうがよいかもしれません。)

 NTFS も、dd コマンドでも原理的にはコピーできるようです。 また、ntfsclone コマンドを用いれば、 ファイルシステムの不要な領域を読み書きせずにすむので早いです。 読み込みエラーが起こっても -rescue オプションを付けておけば大丈夫なようです。 (が、まだ試していません。) 'ntfsclone --rescue -O /dev/hdX1 /dev/sdX1' とすればよいのでしょう。 パーティションサイズの調整には ntfsresize なるコマンドもあるようですが、試していません。 VFAT と同じく、マウントしてファイルコピーするのはやめたほうがよいでしょう。 ところで、もし boot できなかったら、どうすればよいのでしょう? Win のインストールディスクから fixmbr でも実行すればよい?

 ext2/3 でも VFAT と同じく dd コマンドで大丈夫でしょうし、 エラーのないディスクだと、rsync などでファイルコピーするのもよいでしょう。

 コピーの前には fdisk でパーティションを分割して、 mkfs.ext3 コマンドでフォーマットし、 e2label でファイルシステムにラベルをつけておきます。 'rsync -nvaHx --delete /mnt/hda1/ /mnt/sda1/ | less' でコピーされるファイルを確認してから n オプションと "| less" を消して本当に実行します。 コピー元のディレクトリの最後に '/' を忘れずに付けて下さい。 (忘れると /mnt/sda1/hda1/ 以下にコピーされてしまいます。)

 tar でコピーするものもちろんよいのですが、 作業を中断してやりなおすと、最初からになってしまいます。 rsync だと差分だけをコピーするので、 気軽に作業を中断してやり直せます。

 さて、ファイルコピーした場合、Linux OS が boot するためには ここで lilo や grub をインストールする必要がたぶんあって(grub なら不用?)、 KNOPPIX から chroot コマンドか何かを使うと思うのですが、 毎回苦労して、どうやって成功したのか覚えてません。;-) パーティションごと dd でコピーしていれば避けられる作業かもしれません。


イメージファイル

 ドライブやパーティションをコピーする要領で、コピー先をファイルにすれば、 イメージファイルを作ることができます。 これを複数保存すればバックアップにもなります。

 ext2/3 上には巨大なファイルを作ることができますが、 VFAT 上だと1ファイルあたり 2GB (FAT16の場合) や 4GB (FAT32の場合) の上限がありますので、 ファイルを分割する必要が出てきます。 それには 'split' コマンドを使います。 連結は 'cat' です(cat は conCATenate (つなぐ) の意味)。

保存
dd if=/dev/hdX conv=sync,noerror bs=4096 | split -b 4095m - /media/sda1/broken-hda.img.

書き戻し
cat /media/sda1/broken-hda.img.* | dd of=/dev/hdX conv=sync,noerror bs=4096

 NTFS のパーティションだと、次のようにするとイメージのサイズを節約できます。 gzip 圧縮と組み合わせてみます。

保存
ntfsclone --rescue -s -o - /dev/hdX1 | gzip --fast | split -b 4095m - /media/sda1/broken-hda1.ntimg.gz.

書き戻し
cat /media/sda1/broken-hda1.ntimg.gz.* | zcat | ntfsclone -r -O /dev/hdX1 -

 さらに NTFS 上の pagefile.sys や hiberfil.sys の巨大ファイルは、 消しても Win 起動時に自動的に作られる上に中身には意味がないので、 消してからイメージを作るのも手です。

 VFAT でも ntfsclone で効率のよいイメージを作れるようです。 ext2/3 だと dump/restore コマンドが使えると聞いたことがありますが、 いつも tar で固めているので確かめたことがありません。


FTP経由でディスクイメージを転送

 ここで紹介する操作は、古い KNOPPIX ならできたのですが、最近のものでは試していません。 ひょっとするとできなくなってるかもしれませんが、念のために残しておきます。

 ディスクドライブが高速なインターフェイスで1台しか接続できない場合、 FTP サーバが別にあれば、そちらにイメージを転送するのも良いでしょう。 100BASE-TX なら 10Mbyte/sec 以上の速度が出るので、 USB 1.1よりも1桁高速です。

 まず、ネットワークの設定です。 KNOPPIX は自動的に DHCP で IP アドレスを探すようですが、 手動で設定したいなら 'netcardconfig' というコマンドがあります。

 これからの作業は、2つのシェルが必要です。 X が動いていれば窓を2つ開けて、 コンソールで作業していれば ALT + F1 や ALT + F2 で切替えて作業して下さい。

 片方のシェルで FTP クライアントを立ち上げます。 lftp は named pipe に対応していないようなので、 ncftp を使います。

# mkfifo img  named pipe を作る
# ncftp -u username 192.168.0.3
ncftp> put img

 のようにします。

 もう片方のシェルでは、さきほど作った named pipe (特殊ファイル)に向かって書き込みます。

# dd if=/dev/hdX of=img conv=sync,noerror bs=4096 count=1

 put と dd を実行するタイミングは、どちらが先でもかまいません。 これでディスクのイメージを別マシンに転送することができます。

 逆向けにディスクイメージを転送するときは、 当然ながら put でなくて get、dd の if と of を入れ換えればよいです。 ncftp が「存在するファイルがあるがどうする?」と 聞いてきますので、上書きを選べば大丈夫です。

 マシンが十分に高速なら、gzip しながら転送してもよいでしょう。 'dd if=/dev/hdX | gzip -1 > img' のようにすればよいです。 ただ、PentiumM 1.3G ぐらいでも 100BASE-TX を使いきることはできないようです。 あらかじめディスクの未使用領域をゼロクリアでもしておかないと、 速度メリットは得られないでしょう。 なお、正常な VFAT/ext2/3 のディスクの場合、 未使用領域をゼロクリアするのは簡単です。 マウントして 'cat /dev/zero > hoge; rm hoge' とするだけです。 NTFS もそろそろ書き込みができるようになってきているようです。

 前述のとおり、ファイルシステムの必要部分だけを効率良く抽出するのには、 ゼロクリアせずとも、 ext2/3 なら 'dump'、FAT/NTFS なら 'ntfsclone' を使う手もあります。


データ消去

 機密データ(?)が入っていたディスクは、 破棄する前にデータ消去しておきたくなります。 ファイルを消去しただけでは、結構な確率で復元できます。 例えば 'cat /dev/hdX1 | strings | less' しただけで、テキストデータがほとんど読めてしまいます。

 少なくともディスク全体をゼロクリア 'cat /dev/zero > /dev/hdX' すればそれなりに安心でしょう。 HDドライブを分解しない範囲では復元できませんから。 ちなみに、乱数を書き込むのは 'cat /dev/urandom > /dev/hdX' とすればよいようですが、とても時間がかかるようです。 手元では Athlon64 の十分高速な CPU を使っていてるのですが、 ゼロクリアなら 50MB/sec で書き込める S-ATA ドライブが、 4.5MB/sec と 1/10 以下の速度になってしまいました。

 手間暇をかければそれでも復元できることになっています。 ([linux-users:78671] Re: HD内のデータ消去法) まぁしかし「機密データが入っていたことを悟られないようにこっそり捨てる」 ぐらいでよいと思います。 念を入れるなら、ハンマーで物理的に破壊しましょう。 (内部にはガラスの部品が使われていることもあるので、怪我にはご注意を。)


ホーム
リンクはご自由にどうぞ。
土村 展之(tutimura(a)nn.iij4u.or.jp) '(a)'は'@'に置き換えて
更新日 5/ 8 22:35, 2010