C# 係統應用之調用SDelete程序粉碎文件及基礎原理知識
在“個人電腦清除軟件”中需要對文件進行徹底粉碎,使其不可恢複.這篇文章主要講述的是Windows文件係統及調用SDelete程序徹底粉碎文件,希望文章對大家有所幫助.
一.Windows文件係統
首先,我回顧湯子丹西電版《計算機操作係統》(此篇部分參考該書)課程中學過的知識,也希望大家去閱讀了解,如果不想知道這部分知識的可以跳過.為了文章的完整,我覺得這部分還是必要的.
1.文件及文件係統
(1).文件係統
為了方便用戶使用軟件資源,由OS提供的管理文件的軟件機構.負責管理在外存上的文件,並把對文件的存取、共享和保護等手段提供給用戶,文件係統的管理功能是通過把它所管理的程序和數據組織成一係列文件的方法實現.它是操作係統用於明確磁盤或分區上的文件的方法和數據結構,即在磁盤上的組織文件的方法.
(2).文件
它是指具有文件名的若幹相關元素的集合,元素通常是記錄,而記錄又是一組有意義的數據項的集合.基於文件係統的概念將數據組成分為數據項、記錄和文件三級.
(3).文件控製塊
每個文件都有唯一的標識符(FCB,File Control Block,文件控製塊),通過該標識符存取文件中的信息.通過文件目錄表中文件的名字及物理地址的映射表及FCB可以獲取文件中的信息,包括:文件名、文件類型、文件物理位置、文件邏輯結構、存取控製塊信息(存取權限)、使用信息(文件創建時間、上次使用時間、當前使用信息)等.
PS:這部分信息隻是簡單進行了介紹,詳細的可看書或自己查閱資料.那麼微軟的文件係統又是什麼呢?
2.FAT和NTFS技術
在微軟早期的MS-DOS中使用12位的FAT12文件係統,後來使用FAT16.在Windows 95和Windows98操作係統中升級為32位的FAT32,Windows NT、2000、XP操作係統使用新技術文件係統NTFS.而它們所采用的文件分配方式基本都類似於顯示鏈接的方法.
(1).顯示鏈接
在外存分配中鏈接分配方式采取離散的分配方法,有效的消除了外部碎片,提高外存空間利用率.同時,動態分配文件和盤塊,十分方便.而顯示鏈接用於鏈接各物理塊的指針,顯示地存放在內存的一張鏈接表中.
其中文件分配表的序列號是物理盤塊號,從0開始,文件的第一個盤塊號都被存儲在相應的FCB中,通過它可查到相應的文件內容,同時在表中存放有鏈接指針,指向下一個盤塊號(鏈式存儲時一個文件可由多個盤塊組成).
由於分配給文件的所有盤塊號都存儲在該表中,故把該表叫文件分配表FAT(File Allocation Table).
(2).FAT
文件分配表(File Allocation Table,FAT)文件係統因它使用了文件分配表來描述文件係統內存儲單元簇的分配情況和文件內容的前後連接關係而得名.包括FAT12、FAT16和FAT32.
簇(cluster)是一個新的分配單位,是一組連續的扇區,在FAT中作為一個虛擬扇區.其大小一般為2n(n為整數)個盤塊.在MS-DOS實際中,簇容量可為僅一個扇區(512B)、兩個扇區(1KB)、四個扇區(2KB)、八個扇區(4KB).簇的優點是能適應磁盤容量不斷增大.
FAT12的簇標識為12位(二進製數),在FAT12表中最多允許有4096個表項,即最多隻能將一個磁盤分區分為4096個簇.如果采用以盤塊作為基本分配單位,每個盤塊(扇區)大小是512字節,每個磁盤分區容量是2MB(4096*512B).
這裏,FAT16和FAT32就不過多講述,希望讀者自己研究,感覺能力有限,有點講述不清楚.
FAT文件係統可分為三部分:保留區(DBR)、FAT區和數據區.如下圖所示:
a.保留區:存儲一個重要的數據結構——係統引導扇區(DBR),其位於文件係統的0號扇區,DBR存儲了其所在文件係統有關的重要信息.
b.FAT區:具有兩個大小、數據內容相同的FAT表組成,緊跟在保留區後.FAT表用於描述數據區中數據存儲單元的分配狀態及為文件或目錄內容分配的存儲單元的前後連接關係.
c.數據區:它被劃分為一個個簇,用於存儲用戶數據.
(3).NTFS
NTFS(New Technology File System,新技術文件係統)是一個為Windows NT開發的、為特別網絡和磁盤配額、文件加密管理安全特性的全新文件係統,並適用於Windows 2000\XP\2003.NTFS也是以簇為單位存儲數據文件的,其簇的大小並不依賴磁盤或分區的大小,由於簇尺寸有縮小,故能減少產生磁盤碎片、降低磁盤空間浪費.
在NTFS文件係統中,使用卷表示一個邏輯磁盤.它存在一張主控文件表MFT(Master File Table),將一個卷中的所有文件信息、目錄信息及可用的未分配空間信息記錄在MFT中.NTFS利用B-Tree文件管理方法跟蹤文件在磁盤上的位置.現在使用的Win7/Win8/Vista都是NTFS文件係統.如圖:
二.恢複文件簡單原理
(該例參考戴士劍的《數據恢複技術》書籍)
在日常生活中我們可能清空回收站或使用Shift+Delete刪除文件,但其實它是可以恢複的.
這就好比磁盤文件係統想象成一本書,需要找到某部分內容時,一般通過書最開始部分目錄索引查找,當刪除一部分內容時,隻簡單的刪除目錄索引,而內容可以通過其他方式找到(如一頁頁查找).同樣,OS存取文件時是以簇為單位進行,一簇包括若幹實際磁盤空間(扇區),同時以簇鏈的形式保存文件分配表(FAT),相當於索引.當刪除一個文件會將文件在分配表中簇標識記為"空簇".但數據區會保留著文件內容,因此可以恢複.
下麵是通過數據恢複精靈恢複例子:使用Shift+Delete永久刪除F盤下兩個文件"獲取Cookies.txt"和"C#WinForm學習.docx",使用數據恢複精靈可以實現恢複.(我的是未注冊版本,僅成功嚐試恢複了txt和word文件).
三.cmd調用SDelete程序及參數
微軟提供了SDelete程序安全刪除文件並使磁盤數據無法恢複,使用SDelete安全刪除文件也可以安全地擦除存在磁盤的未分配部分中的任意文件數據(包括已刪除或加密的文件).SDelete程序實施了美國國防部摧毀標準(Clearing and Sanitizing Standard) DOD 5220.22-M.
//SDelete程序刪除一個或多個文件或目錄,亦可清理邏輯磁盤上可用空間 sdelete [-p passes] [-s] [-q] <文件或目錄> //<file or directory> sdelete [-p passes] [-z] [驅動器符號] //[drive letter] //參數含義 -a Remove Read-Only attribute -c Clean free space -p passes 指定覆蓋操作的執行遍數(default is 1,默認是1) -s or -r 對子目錄執行遞歸操作 -q 不顯示錯誤(靜默模式) -z 清理可用空間(good for virtual disk optimization)
由於SDelete是一個命令行工具,需要從官方地址下載:放置於%system%目錄"C:\Windows\System32\sdelete.exe".https://technet.microsoft.com/en-us/sysinternals/bb897443.aspx
我在移動硬盤H中放入兩張圖片"程序刪除.jpg"和"回收站刪除",刪除過程如下圖所示,cmd程序中輸入sdelete -p 2 "H:\程序刪除.jpg".調用SDelete並執行2次覆蓋操作.
下麵是使用EasyRecovery軟件能實現對回收站刪除的圖片恢複,而使用SDelete刪除不能恢複的圖片.最後實現了回收站刪除圖片的恢複功能.
思考:為啥需要覆蓋操作執行多遍呢?我的老師給我說刪除6遍時較幹淨,Why?
四.C#實現粉碎文件(未實現)
(部分參考丁士鋒的《C#典型模塊與項目實戰大全》)
我打算通過創建Process,並設置其參數實現刪除文件功能,代碼如下:
private void button1_Click(object sender, EventArgs e) { try { //檢查文件是否存在 if (!File.Exists(textBox1.Text.ToString())) { MessageBox.Show("輸入文件不存在!"); } else if (Convert.ToInt32(textBox2.Text) < 1) //覆蓋次數大於1 { MessageBox.Show("覆蓋次數要大於1"); } else { //初始化進程 命名空間 using System.Diagnostics Process da = new Process(); //設置要啟動應用程序或文檔名 da.StartInfo.FileName = @"C:\WINDOWS\system32\sdelete.exe"; //設置要啟動應用程序使用的一組命令行參數 //參數:執行覆蓋操作次數 刪除文件路徑 da.StartInfo.Arguments = string.Format("-p {0} -q \"{1}\"", Convert.ToInt32(textBox2.Text), textBox1.Text.ToString()); //設置窗口狀態 隱藏窗口顯示 da.StartInfo.WindowStyle = System.Diagnostics.ProcessWindowStyle.Hidden; //直接執行程序 不使用Shell打開 da.StartInfo.UseShellExecute = false; //輸入流 輸出流 錯誤寫入流 da.StartInfo.RedirectStandardInput = true; da.StartInfo.RedirectStandardOutput = true; da.StartInfo.RedirectStandardError = true; //不創建窗口,靜默模式 da.StartInfo.CreateNoWindow = true; //開始執行進程 da.Start(); //從輸出流中讀取程序輸出 string output = da.StandardOutput.ReadToEnd(); //等待程序退出 da.WaitForExit(); //文件不存在記錄輸出流信息 if(File.Exists(textBox1.Text.ToString())) { richTextBox1.AppendText(output); } } } catch (Exception msg) //異常處理 { MessageBox.Show(msg.Message); } }
但是,雖然已經把sdelete.exe放置於“C:\windows\system32”文件夾下,使用cmd運行才能正確刪除,但當通過C#代碼調用時總是會顯示錯誤"係統找不到指定文件".這讓我萬分傷心啊,但同時該方法的不足之處是需要用戶放置sdelete程序,因此我需要尋求新的方法實現粉碎文件.
但是代碼中所涉及的使用Process的方法還是值得大家學習的,我們還可以通過它實現很多功能,如下:
//IE瀏覽器打開百度 Process.Start("IExplore.exe", "https://www.baidu.com/"); //打開庫 Process.Start("explorer.exe"); //打開Excel辦公軟件 Process.Start("EXCEL.exe"); //打開cmd Process.Start("cmd.exe");
關於Process的詳細用法建議大家閱讀下麵這篇優秀文章:https://blog.csdn.net/chen_zw/article/details/7896264
下麵是調用cmd.exe程序實現ipconfig查看功能,但是當使用"sdelete -p 2 "F:\test.txt""時還是不能運行,我也不知道為什麼?不知道怎麼訪問Sdelete.exe程序,使用管理員權限運行也不行.
string command = ""; System.Diagnostics.Process p = new System.Diagnostics.Process(); p.StartInfo.FileName = "cmd.exe"; //文件名 command = "/c" + "ipconfig"; //command = "/c" + "sdelete -p 3 \"F:\\bbb.txt\""; p.StartInfo.Arguments = command; //參數 p.StartInfo.UseShellExecute = false; //是否使用操作係統shell啟動 p.StartInfo.RedirectStandardInput = true; //接受來自調用程序的輸入信息 p.StartInfo.RedirectStandardOutput = true; //由調用程序獲取輸出信息 p.StartInfo.RedirectStandardError = true; //重定向標準錯誤輸出 p.StartInfo.CreateNoWindow = true; //不顯示程序窗口 p.Start(); //啟動程序 string output = p.StandardOutput.ReadToEnd(); richTextBox1.AppendText(output);
cmd中ipconfig的運行結果如下,但使用sdelete參數就是不行(>.<):
總結:最後希望該篇文章對大家有所幫助,它僅僅是一篇基礎性的設計文件係統的文章,如果文章中有錯誤或不足之處,還請海涵!同時文章主要參考了文中提到的3本書籍,如果有認為文章過於囉嗦或不喜歡的,也請見諒!寫這篇文章真心有點難,最難過的是沒有實現,如果有知道的請說聲.我開始尋找更好的粉碎文件的方法了.
楊友山老師的粉碎文件:https://blog.csdn.net/yysyangyangyangshan/article/details/18423731
(By:Eastmount 2014-4-19 下午4點 原創CSDNhttps://blog.csdn.net/eastmount/)
最後更新:2017-04-03 12:56:18