proc目錄介紹(二):利用proc目錄恢復被刪除的文件

在這篇文章中,我們將演示一個使用proc目錄恢復文件的例子,以加深對proc目錄的理解。

我們將以MySQL資料庫為了來演示,如何在Linux下恢復已經刪除的文件。假設我們有一個正在運行的MySQL實例,但是,因為誤操作,刪除了MySQL資料庫中的文件,如共享表空間(ibdata1)或獨立表空間(table_name.ibd)。由於Linux資料庫沒有回收站的功能,因此,正常情況下,我們無法進行文件恢復。顯然,誤刪數據文件將有可能導致MySQL資料庫啟動失敗,或者導致數據丟失。在了解了proc目錄以後,我們可以嘗試使用proc目錄恢復已經刪除的文件。

假設我們的MySQL資料庫實例在整個實驗過程中都在運行。並且,為了便於實驗,開啟了innodb_file_per_table參數。接下來,在test資料庫下創建了一張表,並且插入了若干條記錄。如下所示:

SQL> SHOW CREATE TABLE tG*************************** 1. row *************************** Table: tCreate Table: CREATE TABLE `t` ( `id` int(11) NOT NULL AUTO_INCREMENT, PRIMARY KEY (`id`)) ENGINE=InnoDB AUTO_INCREMENT=23 DEFAULT CHARSET=latin11 row in set (0.00 sec)SQL> SELECT COUNT(*) FROM t;+----------+| COUNT(*) |+----------+| 22 |+----------+1 row in set (0.02 sec)

然後,刪除表t的表空間。如下所示:

shell> rm -rf /var/lib/mysql/test/t.ibd

表空間刪除以後,依然可以查詢和修改這張表。如下所示:

SQL> INSERT INTO t VALUES (NULL);Query OK, 1 row affected (0.00 sec)SQL> SELECT COUNT(*) FROM t;+----------+| COUNT(*) |+----------+| 23 |+----------+1 row in set (0.00 sec)

如果表空間文件真的被刪除了,那麼,肯定無法繼續在表中插入記錄,也無法查詢表中的記錄。因此,可以確定的是,雖然在文件系統中已經找不到該文件,但是,該文件還沒有真正被刪除。在Linux下,如果我們刪除了較大的文件,但是,使用df命令查看磁碟的空間,磁碟可用空間並沒有增大。那麼,很有可能是因為,你刪除的這個文件正在被某一個進程使用。如果一個文件正在被一個進程使用,那麼,刪除文件時,文件並不會被立即刪除,佔用的磁碟空間也不會釋放。

在我們這個例子中,由於有進程(MySQL進程)打開了該文件,因此,當我們從外部刪除文件時,文件並沒有被真正的刪除。只有當進程關閉該文件的文件句柄時,文件才會被真正刪除。此時,我們依然可以使用lsof命令查看已經被刪除的文件,如下所示:

shell> lsof | grep t.ibdCOMMAND PID USER FD TYPE DEVICE SIZE/OFF NODE NAMEmysqld 11401 mysql 25uW REG 7,0 98304 1010691 /var/lib/mysql/test/t.ibd (deleted)

前面說過,在/proc[pid]/fd目錄下,保存了所有進程打開的文件。也就是說,雖然從文件系統層面,我們已經無法找到已經被刪除的文件,但是,我們還可以在proc目錄下找到該文件的文件句柄。如下所示

shell> ll /proc/11401/fd/25 lrwx------ 1 mysql mysql 64 Feb 28 16:14 /proc/11401/fd/25 -> /var/lib/mysql/test/t.ibd (deleted)

接下來我們嘗試恢復該文件,為了恢復出一個一致性的數據文件,可以現在MySQL資料庫中為該表加上表鎖,以免在恢復文件的過程中,還有新的寫入。如下所示:

SQL> LOCK TABLE t READ; Query OK, 0 rows affected (0.00 sec)

恢復的方式也很簡單,直接對文件句柄進行拷貝即可。將數據文件拷貝到MySQL的資料庫目錄下,並修改文件的許可權。完成以後,重啟MySQL資料庫。如下所示:

shell> cp /proc/11401/fd/25 /var/lib/mysql/test/t.ibdshell> chown mysql:mysql /var/lib/mysql/test/t.ibdshell> service mysql restart..... SUCCESS!..... SUCCESS!

可以看到,當我們理解了proc目錄的作用以後,只需要簡單的幾步,就可以恢復Linux下被誤刪的文件。這裡需要注意的是,在恢復文件的過程中,MySQL進程一直存活著,如果MySQL進程關閉了,這裡介紹的恢復方法也就不起作用了。進程被刪除以後,其在proc目錄下的子目錄也就消失,被誤刪的文件也就沒有辦法恢復了。

歡迎加入MySQL+Python+大數據+NoSQL技術交流QQ群(群號:306706593)。

推薦閱讀:

誰花錢做過硬碟、U盤數據恢復?包括購買數據恢復軟體,花了多少錢?
傳輸數據時突然把U盤拔掉,結果U盤能被識別但打不開怎麼辦?
零基礎如何學數據恢復?
如何恢復移動硬碟近300G心血文件?

TAG:Linux | 数据恢复 |