操作系統課程設計報告_第1頁
操作系統課程設計報告_第2頁
操作系統課程設計報告_第3頁
操作系統課程設計報告_第4頁
操作系統課程設計報告_第5頁
已閱讀5頁,還剩36頁未讀 繼續免費閱讀

下載本文檔

版權說明:本文檔由用戶提供并上傳,收益歸屬內容提供方,若內容存在侵權,請進行舉報或認領

文檔簡介

長沙理工大學繼續教育學院操作系統課程設計年級:專業:計算機科學與技術姓名:學號:指導老師:時間:2018年月日 模擬Linux文件系統目錄一、課程設計任務書 1二、課程設計內容 21、詳細設計及編碼 51.1初始化命令——format 91.2系統初始化——自動完成 101.3建立文件——mffilename 101.4建立子目錄——mdfilename 111.5打開文件——openfilename 121.6刪除文件——delfilename 141.7刪除目錄——rdfilename 151.8顯示目錄——dir(即顯示目錄下的信息,包括文件、子目錄等) 151.9正常退出指令exit 16三、存在問題及改進意見 39四、參考資料 39 一、課程設計任務書模擬Linux文件系統。在任一OS下,建立一個大文件,把它假象成一張盤,在其中實現一個簡單的模擬Linux文件系統。1.在現有機器硬盤上開辟20M的硬盤空間,作為設定的硬盤空間。2.編寫一管理程序對此空間進行管理,以模擬Linux文件系統,具體要求如下:(1)要求盤塊大小1k正規文件(2)i結點文件類型目錄文件(共1byte)塊設備管道文件物理地址(索引表)共有13個表項,每表項2byte文件長度4byte。聯結計數1byte(3)0號塊超級塊棧長度50空閑盤塊的管理:成組鏈接(UNIX)位示圖法(Linux)(4)每建一個目錄,分配4個物理塊文件名14byte(5)目錄項信息i結點號2byte(6)結構:0#:超級塊1#-20#號為i結點區20#-30#號為根目錄區3.該管理程序的功能要求如下:(1)能夠顯示整個系統信息,源文件可以進行讀寫保護。目錄名和文件名支持全路徑名和相對路徑名,路徑名各分量間用“/”隔開。(2)改變目錄:改變當前工作目錄,目錄不存在時給出出錯信息。(3)顯示目錄:顯示指定目錄下或當前目錄下的信息,包括文件名、物理地址、保護碼、文件長度、子目錄等(帶/s參數的dir命令,顯示所有子目錄)。(4)創建目錄:在指定路徑或當前路徑下創建指定目錄。重名時給出錯信息。(5)刪除目錄:刪除指定目錄下所有文件和子目錄。要刪目錄不空時,要給出提示是否要刪除。(6)建立文件(需給出文件名,文件長度)。(7)打開文件(顯示文件所占的盤塊)。(8)刪除文件:刪除指定文件,不存在時給出出錯信息。4.程序的總體流程為:(1)初始化文件目錄;(2)輸出提示符,等待接受命令,分析鍵入的命令;(3)對合法的命令,執行相應的處理程序,否則輸出錯誤信息,繼續等待新命令,直到鍵入EXIT退出為止。二、課程設計內容在現有機器硬盤上開辟20M的硬盤空間(利用一個循環操作,在Disk中寫入20M的零,創建一個20M的文件即是),作為設定的硬盤空間。 磁盤塊物理模型如下:空閑盤塊棧(存放空閑盤塊)空閑盤塊棧(存放空閑盤塊)目錄區各盤塊(每個占1KB)存放文件內容,為程序設計方便,iNode節點也存放在此處。1kb(目錄快)30kB20480kb0kb(超級塊信息)文件則是指具有文件名的若干相關元素的集合。文件屬性主要如下文件名:實現了按名存取,文件名和目錄文件允許重名。文件類型:可以從不同的角度來規定文件的類型。普通文件、管道文件、塊文件。文件長度:指文件的當前長度,長度的單位可以是KB。文件的物理位置:文件在磁盤中物理的存儲,并打印出來。此次UNIX文件系統最簡單的目錄結構。整個文件系統中只建立一張目錄表,每個文件一個目錄項,目錄項含有文件相關信息。每建立一個新文件要先檢索所有的目錄項保證文件名唯一。然后找出一空白目錄項填入相關信息,并修改狀態位。刪除文件是找到對應目錄項,回收所占用空間,清除該目錄。邏輯結構如下文件名索引節點編號文件名1INode文件名2INode文件名3INode….…. Unix文件系統當文件很多時,文件目錄要占用大量的盤塊。在查找目錄的過程中,可能需要多次啟動磁盤讀入目錄文件的盤塊。在檢索目錄文件中只用到了文件名,顯然,文件的物理地址等文件的描述信息在檢索目錄時不需調入內存。為此,可以把文件名與文件描述信息分開。使文件描述信息單獨形成一個索引結點。把文件描述信息單獨形成一個稱為索引結點的數據結構,簡稱為inode;文件目錄中的每個目錄項,則僅由文件名及指向該文件所對應的inode的指針所構成。這樣,為找到一個文件的平均啟動磁盤的次數減少很多模型如下:RootFan.txtINodeINode節點目錄節點節點INode節點目錄節點節點INode節點AB存儲空間的分配與回收成組鏈接法首先,建立操作系統課程的設計模型。這個系統將利用一個20M的文件作為自己的磁盤空間,設計時由于一個盤塊占用1KB,所以20M空間可以產生20480個盤塊系統本身將0#-30#塊作為系統區,所以用戶區便剩下20450個盤塊,每50個盤塊為一組,一共可以分為409個組。將每一組含有的盤塊總數N和該組的盤塊號,記入其前一組的第一個盤塊的S.free(1)~S.free(50)。這樣由各組的第一個盤塊形成了一條鏈。將第一組的盤塊總數和所有的盤塊號,記入空閑盤塊號棧中,作為當前可供分配的空閑盤塊號。最末一組只有49個盤塊,其盤塊號分別記入其前一組的S.free(1)~S.free(99)中,而在S.free(0)中則存放0,作為空閑盤塊鏈的結束標志。基本功能:初始化;建立文件;建立子目錄;打開文件;刪除文件;刪除目錄;顯示目錄1、詳細設計和編碼正規文件i結點文件類型目錄文件(共1byte)塊設備管道文件。物理地址(索引表)共有13個表項,每表項2byte。文件長度4byte。聯結計數1bytestructINode{ FileSpecfileSpec; shortiaddr[13]; intfileLength; intlinkCount;};文件名14byte(5)目錄項信息i結點號2bytestructDirChild{charfilename[14];shorti_BNum;};structDirNode{DirChildchildItem[64];short DirCount;};定義磁盤文件名constcharFileName[]="os.txt";默認為空的文件名constcharNullName[]="0000000000000";默認目錄文件的長度constintDirLen=1;默認超級塊的快號constshortSSNum=-1; //superblocknum定義枚舉類型,普通,目錄,塊文件,管道文件enumFileSpec{NORMAL,DIR,BLOCK,PIP};//0,1,2,3shortSS[51]; //超級棧,指針為SS[0],保存當前可用盤快shortfreeBlockNum=0; //當前可用盤快所在組記錄的盤快號shortfreeTotalB=20450; 文件總長度shortfreeDirNode[29]; //可用索引節點棧shortfreeDirCount=30; //索引節點棧指針shortcurrDirNum; //當前目錄所在的磁盤號shortcurrINum; DirNode*currDir; //當前目錄節點INode *iNode; //當前iNode

節點系統調用函數列表系統調用原型功能入口、出口參數說明VoidArrarEqual(shortarr[51],shortbegin,shortend)arr[51]數組賦值,在成組鏈接初始化時使用voidBWrite(shortarr[51],shortdiskNum)往磁盤中寫入短數組voidBWriteArr(shortarr[512],shortdiskNum)重構BWrite,實現一個數組的寫入,數組長度不確定voidBRead(INode*iNode,shortdiskNum)從磁盤中讀出iNode節點voidBRead(shortarr[51],shortdiskNum)從磁盤中讀出數組voidBReadArr(shortarr[512],shortdiskNum)從磁盤中讀出數組,成組鏈接多級索引使用BWrite(DirNode*currDir,shortdiskNum)寫入一個目錄項VoidBWrite(INode*iNode,shortdiskNum)寫入一個iNodeVoidAssAnEmpty()分配一個空閑的普通快shortAssAnDir()分配一個空閑的目錄快shortIsFileExist(DirNode*currDir,charfileName[14])判斷一個文件是否存在-1不存在,否則返回文件所在磁盤號boolIsFile(INode*iNode,shortdiskNum)判斷一個文件是一個普通文件boolIsDir(INode*iNode,shortdiskNum)判斷一個文件是一個索引文件voidCreateINode(INode*iNode,FileSpecfileSpec,shortlinkCount,shortlength)創建一個iNode,并分配磁盤空間voidCleanINode(INode*iNode)清空iNode信息,并分配磁盤空間voidInsertDir(DirNode*currDir,charfileName[14],shortblockNum)將當前目錄項插入到內存中目錄項中voidShowFileInfo(INode*iNode,charfileName[14])打開一個文件,顯示文件信息voidShowBlockInfo(INode*iNode)打開一個文件,顯示文件占用磁盤空間信息voidDelDirItem(DirNode*currDir,charfileName[14])刪除索引中一項voidCallBackOne(shortdiskNum)回收一塊空余磁盤片voidCallBackINode(shortdiskNum)回收文件的iNOde節點主要函數列表函數原型功能入口、出口參數說明Format創建20M磁盤voidInit(DirNode*currDir,FileSpecfielSpec,charfilename[14],INode*iNode,shortdiskNum)初始化,創建個目錄節點并初始化超級棧Init()初始化索引棧voidLinkdisk()成組鏈接初始化voidInitCreate(DirNode*currDir,FileSpecfielSpec,charfilename[14],INode*iNode,shortdiskNum)創建一個文件節點,并分配INOde和磁盤空間voidCreate(DirNode*currDir,charfileName[14],INode*iNode,shortlength,FileSpecfileSpec)存在文件,并分配iNOde節點和磁盤空間voidMf(DirNode*currDir,charfileName[14],INode*iNode,shortlength)創建一個文件voidMd(DirNode*currDir,charfileName[14],INode*iNode,shortlength)在當前目錄創建一個子目錄voidOpen(DirNode*currDir,charfileName[14],INode*iNode)打開文件,顯示文件信息voidDel(DirNode*currDir,charfileName[14],INode*iNode)刪除一個文件voidRd(DirNode*currDir,charfileName[14],INode*iNode)刪除一個目錄voidDir(DirNode*currDir,INode*iNode)顯示目錄項的內容voidexit(DirNode*currDir,INode*iNode)退出,并銷毀資源voidAuthorMessage()打印版權信息voidhelp()提示信息主框架開開始打印作者信息初始化磁盤合法性檢查輸入命令顯示:命令錯誤falseo有新建文件新建目錄打開文件刪除文件刪除目錄顯示目錄立退出1.1初始化命令——format利用文件創建命令可在硬盤上創建一個名為Disk的20M的空間,并將該磁盤空間整體假想成一個獨立硬盤,我們將在這張封閉的磁盤上進行各種關于文件的操作。Format具體操作如下:利用一個循環操作,在Disk中寫入20M的零。然后將0#塊,即超級塊中寫入31#-80#的盤塊號,并將全部可用剩余盤塊數FreeBlock=20450記錄在0#塊中。同時將80#,130#,180#(間距50)等408個(第409個組頭不存在下一組)盤組的組頭中寫入成組連接好的下一組盤塊號。1.2系統初始化——自動完成假如Disk已被格式化完畢,那么系統便將進行下一步,那就是初始化。初始化主要完成將根目錄項讀入內存,便于文件操作,并將0#超級塊中保存的當前可用盤塊號寫入內存中的超級棧中,具體操作如下:初始化一個超級棧,將超級塊中保存的當前可分配盤塊號讀入棧中。定義一個全局變量FreeBlock,用來記錄當前全部可用的盤塊總數。1.3建立文件——mffilename如果終端發來的命令格式為mffilename,則可以判斷出這是建立文件的命令。要想成功建立一個文件,首先需要判斷在同級目錄下是否有重名的文件,并且需要判斷是否有足夠的空間允許建立一個指定長度的文件。mf(代表makefile)具體操作如下:(1)判斷所要建立的文件是否重名。首先將終端輸入的文件名filename在RootDir[640]進行檢索,看是否可以找到相同的名字,假如找到了相同的名字還不能立刻判斷是重名了,因為同級目錄下允許文件夾與文件重名,然后利用DirItem結構中的最后2個Byte要找到暫時重名文件的i結點,從i結點中讀出該文件的屬性,看是為正規文件還是文件夾。如果重名了,系統會提示,否則進行下一步。(2)如果不重名,則要根據用戶輸入的文件長度來判斷當前的剩余盤塊總數是否足夠分配,這項工作不僅僅是用終端輸入來的length與剩余盤塊總數FreeBlock比較,因為Unix本身采取混合索引方式,所以根據文件的長度會分配不同的索引盤塊數。所以判斷盤塊數是否足夠同時要計算出相應的索引盤塊數。如果文件數據本身盤塊數加上相應的索引盤塊數不會超過總剩余盤塊數,則可進行分配。開開始獲得文件名獲得文件名獲得文件長度獲得文件長度合法性檢查合法性檢查返返回分配目錄項分配磁盤空間分配磁盤空間分配索引節點分配索引節點返返回1.4建立子目錄——mdfilename建立子目錄,即建立一個文件夾。其可以看作是建立文件的一個特殊情況,建立一個文件夾的過程和上述的建立文件非常相似,也要判斷重名,也要判斷是否盤塊數足夠分配,以及分配時所要考慮到的全部情況(文件夾利用0級索引)。開開始獲得目錄名獲得目錄名讀取目錄節點讀取目錄節點合法性檢查合法性檢查返返回創建創建iNode,分配索引節點分配磁盤空間分配磁盤空間分配目錄項分配目錄項返返回1.5打開文件——openfilename(顯示文件所占的盤塊)開開始檢查當前目錄目錄中有文件么?檢查iNode文件屬性與操作類型相符?打開文件:顯示文件信息打印iNode中盤快信息顯示:“打開”成功返回顯示:不存在該文件,打開失敗返回顯示:文件類型不匹配返回有無否是讀取iNode這個命令就是所謂的讀文件命令,在這個模擬Unix的系統中,我們將顯示文件所占的盤塊以及文件的相關信息。要打開文件,當然首先要判斷是否有這樣一個文件名,然后才是讀出全部的盤塊數1.6刪除文件——delfilename開始查該用目錄表currDircurrDir中有該文件?檢查iNode文件類型匹配?歸還文件所占的存儲區域在UFD中清除該文件登記欄在清除iNode信息,釋放磁盤節點currDir中清除該文件的登記欄顯示:文件已撤消是是否返回開始查該用目錄表currDircurrDir中有該文件?檢查iNode文件類型匹配?歸還文件所占的存儲區域在UFD中清除該文件登記欄在清除iNode信息,釋放磁盤節點currDir中清除該文件的登記欄顯示:文件已撤消是是否返回返返回刪除文件同創建文件都是非常復雜的操作,要有多種情況需要考慮。要想成功刪除一個文件,首先需要判斷在同級目錄下是否有該文件名,然后在根據該文件為幾級索引文件進行相應的回收1.7刪除目錄——rdfilename就如同建立目錄好似建立文件的一種特殊情況,刪除目錄也和刪除文件差不多,但是有一點是絕對不同的,要特別注意。當子目錄下建立了文件或者文件夾時,即表示子目錄不為空,那么系統本身為了保持數據的完整性,是不對該目錄進行刪除操作的,而提示用戶該目錄不為空。除非用戶刪除了該目錄下的全部文件后,返回到根目錄,此時子目錄為空,才允許系統刪除該文件夾。刪除時的具體過程同刪除0級索引文件極為相似,這里就不作過多說明。文件流程如刪除文件,此處不再贅述。1.8顯示目錄——dir(即顯示目錄下的信息,包括文件、子目錄等)Dir是一個很容易實現的命令,在目錄下輸入此命令,即可以獲得目錄下的信息,包括文件、子目錄等。開開始讀取當前目錄讀取iNode顯示完所有目錄顯示文件信息打印iNode中顯示:成功返回否是1.9正常退出指令exit不要小看了這條指令,它可以幫你完成許多被你遺忘的操作,由于此次代碼編寫超過了3000行,而且涉及到大量的文件操作函數,所以難免會對文件的關閉,棧的釋放等結束工作考慮不周全,為了提高數據的可靠性與完整性,建議退出系統時用此命令,它可以自動完成文件的關閉。程序源代碼#include<fstream>#include<iostream>#include<string>usingnamespacestd;constcharFileName[]="os.txt";constcharNullName[]="0000000000000";constintDirLen=1;constshortSSNum=-1; //superblocknumenumFileSpec{NORMAL,DIR,BLOCK,PIP};//0,1,2,3//i節點結構信息structINode{ FileSpecfileSpec; shortiaddr[13]; intfileLength; intlinkCount;};structDirChild{charfilename[14];shorti_BNum;};structDirNode{DirChildchildItem[64];short DirCount;};shortSS[51]; //超級棧,指針為SS[0]shortfreeBlockNum=0; //當前可用盤快所在組記錄的盤快號shortfreeTotalB=20450;shortfreeDirNode[29]; //可用索引節點棧shortfreeDirCount=30; //索引節點棧指針shortcurrDirNum; //當前目錄所在的磁盤號shortcurrINum;DirNode*currDir;INode *iNode;//================================================================//函數描述:創建20M磁盤//入口參數:無//返回值:無//===============================================================voidFormat(){ cout<<"系統正在初始化"<<endl; //打開文件 FILE*f=fopen(FileName,"w+"); if(f==NULL) { cout<<"程序創建錯誤,請重新輸入"<<endl; return; } for(inti=0;i<20971520;i++)//20971520=20Mb,暫時2mb fprintf(f,"%c",'0'); //關閉文件 fclose(f);}//================================================================//函數描述:數組賦值//入口參數:無//返回值:無//===============================================================voidArrarEqual(shortarr[51],shortbegin,shortend){ for(shorti=0;i<end-begin+1;i++) arr[50-i]=begin+i;}//================================================================//函數描述:數組賦值//入口參數:無//返回值:無//===============================================================/*voidBWrite(shortarr[51],shortdiskNum){ FILE*f=fopen(FileName,"r+"); if(f==NULL) { cout<<"寫文件處錯誤,請重新輸入"<<endl; return; } //設置文件指針 if(fseek(f,1024*diskNum,0)) cout<<"文件指針錯誤"<<endl; fwrite(arr,sizeof(short),51,f); fclose(f); }*///================================================================//函數描述:重構BWrite,實現一個數組的寫入//入口參數:無//返回值:無//===============================================================voidBWrite(shortarr[51],shortdiskNum){ FILE*f=fopen(FileName,"r+"); if(f==NULL) { cout<<"寫文件處錯誤,請重新輸入"<<endl; return; } //設置文件指針 if(fseek(f,1024*diskNum,0)) cout<<"文件指針錯誤"<<endl; fwrite(arr,sizeof(short),51,f); fclose(f); }//================================================================//函數描述:重構BWrite,實現一個數組的寫入,數組長度不確定//入口參數:無//返回值:無//===============================================================voidBWriteArr(shortarr[512],shortdiskNum){ FILE*f=fopen(FileName,"r+"); if(f==NULL) { cout<<"寫文件處錯誤,請重新輸入"<<endl; return; } //設置文件指針 if(fseek(f,1024*diskNum,0)) cout<<"文件指針錯誤"<<endl; fwrite(arr,sizeof(short),512,f); fclose(f); }//================================================================//函數描述:重構BWrite,實現一個數組的寫入//入口參數:無//返回值:無//===============================================================voidMyBWrite(shortarr[51],shortdiskNum){ FILE*f=fopen(FileName,"r+"); if(f==NULL) { cout<<"寫文件處錯誤,請重新輸入"<<endl; return; } //設置文件指針 if(fseek(f,1024*diskNum,0)) cout<<"文件指針錯誤"<<endl; for(shorti=0;i<51;i++) fprintf(f,"%d",arr[i]); fclose(f); }//================================================================//函數描述:從磁盤中讀出數組//入口參數:無//返回值:無//===============================================================voidMyBRead(shortarr[51],shortdiskNum){ FILE*f=fopen(FileName,"r+"); if(f==NULL) { cout<<"讀文件處錯誤,請重新輸入"<<endl; return; } //設置文件指針 if(fseek(f,1024*diskNum,0)) cout<<"文件指針錯誤"<<endl; for(shorti=0;i<51;i++) fscanf(f,"%d",&arr[i]); fclose(f); }//================================================================//函數描述:從磁盤中讀出iNode節點//入口參數:無//返回值:無//===============================================================voidBRead(INode*iNode,shortdiskNum){ FILE*f=fopen(FileName,"r+"); if(f==NULL) { cout<<"寫文件處錯誤,請重新輸入"<<endl; return; } //設置文件指針 if(fseek(f,1024*diskNum,0)) cout<<"文件指針錯誤"<<endl; fscanf(f,"%d",&iNode->fileLength); inttemp=int(fgetc(f)); switch(temp){ case0: iNode->fileSpec=NORMAL; break; case1: iNode->fileSpec=DIR; break; case2: iNode->fileSpec=BLOCK; break; case3: iNode->fileSpec=PIP; break; } fread(iNode->iaddr,2,13,f); fscanf(f,"%d",&iNode->linkCount); fclose(f); }//================================================================//函數描述:從磁盤中讀出數組//入口參數:無//返回值:無//===============================================================voidBRead(shortarr[51],shortdiskNum){ FILE*f=fopen(FileName,"r+"); if(f==NULL) { cout<<"讀文件處錯誤,請重新輸入"<<endl; return; } //設置文件指針 if(fseek(f,1024*diskNum,0)) cout<<"文件指針錯誤"<<endl; fread(arr,sizeof(short),51,f); fclose(f); }//================================================================//函數描述:從磁盤中讀出數組,放入到iNOde中//入口參數:無//返回值:無//===============================================================voidBReadArr(shortarr[512],shortdiskNum){ FILE*f=fopen(FileName,"r+"); if(f==NULL) { cout<<"讀文件處錯誤,請重新輸入"<<endl; return; } //設置文件指針 if(fseek(f,1024*diskNum,0)) cout<<"文件指針錯誤"<<endl; fread(arr,sizeof(short),512,f); fclose(f); }//================================================================//函數描述:寫入一個目錄項//入口參數:無//返回值:無//===============================================================voidBWrite(DirNode*currDir,shortdiskNum){ FILE*f=fopen(FileName,"r+"); if(f==NULL) { cout<<"寫文件處錯誤,請重新輸入"<<endl; return; } //設置文件指針 if(fseek(f,long(1024*diskNum),0)) cout<<"文件指針錯誤"<<endl; for(inti=0;i<64;i++) { fprintf(f,"%hd",currDir->childItem[i].i_BNum); fputs(currDir->childItem[i].filename,f); } fclose(f); }//================================================================//函數描述:寫入一個iNode//入口參數:無//返回值:無//===============================================================voidBWrite(INode*iNode,shortdiskNum){ FILE*f=fopen(FileName,"r+"); if(f==NULL) { cout<<"寫文件處錯誤,請重新輸入"<<endl; return; } //設置文件指針 if(fseek(f,1024*diskNum,0)) cout<<"文件指針錯誤"<<endl; fprintf(f,"%d",iNode->fileLength); fputc(iNode->fileSpec,f); fwrite(iNode->iaddr,2,13,f); fprintf(f,"%d",iNode->linkCount); fclose(f); }//================================================================//函數描述:分配一個空閑的普通快//入口參數:無//返回值:無//===============================================================shortAssAnEmpty(){ shorttemp; if(SS[0]>1){ SS[0]--; temp=SS[SS[0]+1];// SS[SS[0]+1]=-1; freeTotalB--;//總剩余數-1 returntemp; }else{ if(SS[1]==0){ cout<<"盤片用盡"<<endl; return-1; } temp=freeBlockNum; freeBlockNum=SS[1]; BRead(SS,SS[1]); if(temp==0){ SS[0]--; temp=SS[SS[0]+1];// SS[SS[0]+1]=-1; } freeTotalB--; returntemp; } }//================================================================//函數描述:分配一個空閑的目錄快//入口參數:無//返回值:無//===============================================================shortAssAnDir(){ if(freeDirCount==0){ cout<<"無空余目錄節點"<<endl; return-1; } else{ freeDirCount--; shorts=freeDirNode[freeDirCount]; freeDirNode[freeDirCount]=-1; returns; //可用索引節點棧 } }//================================================================//函數描述:創建一個文件節點,并分配INOde和磁盤空間//入口參數:無//返回值:無//===============================================================voidInitCreate(DirNode*currDir,FileSpecfielSpec,charfilename[14],INode*iNode,shortdiskNum){ // intblockNum=AssertAnEmpty(); if(fielSpec==DIR){ //initdirNodeandwrite intblockNum=AssAnDir(); currDirNum=blockNum; for(inti=0;i<64;i++){ strcpy(currDir->childItem[i].filename,"0000000000000"); currDir->childItem[i].i_BNum=-1; } BWrite(currDir,blockNum);/* //initINodeandwrite blockNum=AssertAnEmpty(); iNode->fileLength=DirLen; iNode->fileSpec=DIR; iNode->iaddr[0]=blockNum; iNode->linkCount=1; BWrite(iNode,distNum); //為文件分配磁盤空間*/ }//endif(fileSpec==DIR) }//================================================================//函數描述:初始化//入口參數:無//返回值:無//===============================================================voidInit(DirNode*currDir,FileSpecfielSpec,charfilename[14],INode*iNode,shortdiskNum){ InitCreate(currDir,fielSpec,filename,iNode,diskNum); BRead(SS,0);}//================================================================//函數描述:初始化索引棧//入口參數:無//返回值:無//===============================================================voidInit(){for(inti=0;i<30;i++)freeDirNode[i]=30-i; //可用索引節點棧freeDirCount=30; //索引節點棧指針 }//================================================================//函數描述:成組鏈接初始化//入口參數:無//返回值:無//===============================================================voidLinkdisk(){ //臨時空閑棧 SS[0]=50; ArrarEqual(SS,31,80); BWrite(SS,0); for(shorti=1;i<408;i++){ SS[0]=50; ArrarEqual(SS,i*50+31,i*50+80); BWrite(SS,i*50+30); BRead(SS,0); } ArrarEqual(SS,408*50+31,408*50+79); SS[1]=0;//49 BWrite(SS,408*50+30); cout<<"磁盤disk.txt完成創建,大小20MB"<<endl; }//================================================================//函數描述:判斷一個文件是否存在//入口參數:無//返回值:-1,不存在,文件號//===============================================================shortIsFileExist(DirNode*currDir,charfileName[14]){ for(inti=0;i<64;i++){ if(strcmp(fileName,currDir->childItem[i].filename)==0) returncurrDir->childItem[i].i_BNum; } return-1;}//================================================================//函數描述:判斷一個文件是一個普通文件//入口參數:無//返回值:-1,不存在,文件號//===============================================================boolIsFile(INode*iNode,shortdiskNum){ BRead(iNode,diskNum); if(iNode->fileSpec==NORMAL) returntrue; else returnfalse;}//================================================================//函數描述:判斷一個文件是一個普通文件//入口參數:無//返回值:-1,不存在,文件號//===============================================================boolIsDir(INode*iNode,shortdiskNum){ BRead(iNode,diskNum); if(iNode->fileSpec==DIR) returntrue; else returnfalse;} //================================================================//函數描述:創建一個iNode,并分配磁盤空間//入口參數:無//返回值:無AssAnEmpty(),BWrite(dirChild,dir[512-i])未實現//===============================================================voidCreateINode(INode*iNode,FileSpecfileSpec,shortlinkCount,shortlength){ iNode->fileSpec=fileSpec; iNode->linkCount=linkCount; iNode->fileLength=length; //為目錄磁盤,分配目錄節點 if(fileSpec==DIR){ iNode->iaddr[0]=AssAnDir(); return; } //根據文件長度分配文件磁盤節點 //直接尋址 shorti; i=10; shortleft=length; while(left&&i){ iNode->iaddr[10-i]=AssAnEmpty(); left--; i--; } if(left>0){ //一級索引 i=512; shortdir[512]; iNode->iaddr[10]=AssAnEmpty(); while(left&&i){ dir[512-i]=AssAnEmpty(); i--; left--; } if(i!=0) dir[512-i+1]=-1;//標志文件結束 BWriteArr(dir,iNode->iaddr[10]); if(left>0){ //二級索引 shortk=512; shortj=512; shortdirChild[512]; iNode->iaddr[11]=AssAnEmpty(); while(left&&k){ //二級索引1次尋址 dir[512-k]=AssAnEmpty(); while(left&&j){ //二級索引二次尋址 dirChild[512-j]=AssAnEmpty(); left--; j--; } if(j!=0) dir[512-j+1]=-1; //標志二級索引二次尋址結束 BWriteArr(dirChild,dir[512-k]); BWriteArr(dir,iNode->iaddr[11]);//寫二級索引一次尋址中盤快記錄的一次尋的盤快號 k--; } if(k!=0) dir[512-k+1]=-1;//標志文件結束 } }}//================================================================//函數描述:清空iNode信息,并分配磁盤空間//入口參數:無//返回值:無AssAnEmpty(),BWrite(dirChild,dir[512-i])未實現//===============================================================voidCleanINode(INode*iNode){ iNode->fileSpec=PIP; iNode->linkCount=-1; iNode->fileLength=-1; //根據文件長度非配文件磁盤節點 //直接尋址 for(shorti=0;i<13;i++) iNode->iaddr[i]=-1; }//================================================================//函數描述:創建一個iNode,并分配磁盤空間//入口參數:無//返回值:無//===============================================================voidInsertDir(DirNode*currDir,charfileName[14],shortblockNum){ strcpy(currDir->childItem[currDir->DirCount].filename,fileName); currDir->childItem[currDir->DirCount].i_BNum=blockNum; currDir->DirCount++; return;}//================================================================//函數描述:存在文件,并分配iNOde節點和磁盤空間//入口參數:無//返回值:無//===============================================================voidCreate(DirNode*currDir,charfileName[14],INode*iNode,shortlength,FileSpecfileSpec){ intblockNum; if(length>freeTotalB){ cout<<"當前文件超出長度"<<endl; return; } CreateINode(iNode,fileSpec,0,length); blockNum=AssAnEmpty();//分配一個空余磁盤存儲iNOde InsertDir(currDir,fileName,blockNum); BWrite(iNode,blockNum); CleanINode(iNode); BWrite(currDir,currDirNum);//此處}//================================================================//函數描述:創建一個文件,//入口參數:無//返回值:無//===============================================================voidMf(DirNode*currDir,charfileName[14],INode*iNode,shortlength){ intblockNum=IsFileExist(currDir,fileName); if(blockNum!=-1){//有重名名,進一步判斷 if(IsFile(iNode,blockNum)) cout<<"當前文件已經存在,請重新輸入文件名"<<endl; }else{//存在文件,為索引文件,或者無重名現象,創建文件,并分配iNOde節點和磁盤空間 //BRead(iNode,1059);//此處出錯 Create(currDir,fileName,iNode,length,NORMAL); } }//================================================================//函數描述:在當前目錄創建一個子目錄//入口參數:無//返回值:無//===============================================================voidMd(DirNode*currDir,charfileName[14],INode*iNode,shortlength){ intblockNum=IsFileExist(currDir,fileName); if(blockNum!=-1){//有重名名,進一步判斷 if(IsDir(iNode,blockNum)) cout<<"當前目錄已經存在,請重新輸入目錄名"<<endl; }else{//存在文件但為普通文件,或者無重名現象。創建文件,并分配iNOde節點和磁盤空間 Create(currDir,fileName,iNode,length,DIR); CleanINode(iNode); } }//================================================================//函數描述:打開一個文件,//入口參數:無//返回值:無//=============================================================== voidShowBlockInfo(INode*iNode){ shortdir[512]; shorti; i=10; shortleft=iNode->fileLength; while(left&&i){ cout<<(iNode->fileLength-left)<<":"<<iNode->iaddr[10-i]<<""; left--; i--; } if(left>0){ i=512; shortdir1[512]; BReadArr(dir1,iNode->iaddr[10]); while(left&&i){ cout<<(iNode->fileLength-left)<<":"<<dir1[512-i]<<""; i--; left--; } } if(left>0){ //二級索引 shortk=512; shortj=512; shortdirChild[512]; BReadArr(dir,iNode->iaddr[11]); while(left&&k){ //二級索引1次尋址 BReadArr(dirChild,dir[512-k]); while(left&&j){ //二級索引二次尋址 cout<<(iNode->fileLength-left)<<":"<<dirChild[512-j]<<""; left--; j--; } k--; } } }//================================================================//函數描述:打開一個文件,//入口參數:無//返回值:無//=============================================================== voidShowFileInfo(INode*iNode,charfileName[14]){ cout<<"文件名"<<fileName; cout<<"文件類型"; switch(iNode->fileSpec){ caseNORMAL: cout<<"<文件>"; break; caseDIR: cout<<"<目錄>";break; caseBLOCK: cout<<"<INode節點>";break; casePIP: cout<<"管道";break; } cout<<""<<iNode->fileLength<<"KB"<<endl;}//================================================================//函數描述:打開一個文件,//入口參數:無//返回值:無//===============================================================voidOpen(DirNode*currDir,charfileName[14],INode*iNode){ intblockNum=IsFileExist(currDir,fileName); if(blockNum==-1){//不存在該文件,退出 cout<<"該文件按不存在"<<endl; return; } else{ if(IsFile(iNode,blockNum)){ ShowFileInfo(iNode,fileName); ShowBlockInfo(iNode); } } }//================================================================//函數描述:回收一塊空余磁盤片//入口參數:無//返回值:無//===============================================================voidCallBackOne(shortdiskNum){ freeTotalB++; if(SS[0]<=49){ SS[0]++; SS[SS[0]]=diskNum; }else{//SS[0]==50 BWrite(SS,freeBlockNum); //將空白的一組回寫到上一組記錄空閑盤快號的磁盤 freeBlockNum=SS[1]; //將當前空白的一組第一個盤快作為下一個盤組的記錄盤 //修改超級棧 SS[1]=diskNum; SS[0]=1; } }//================================================================//函數描述:回收文件占用的磁盤//入口參數:無//返回值:無//===============================================================voidCallBackDisk(INode*iNode){ shorti; i=10; shortleft=iNode->fileLength; while(left&&i){//直接索引回收 CallBackOne(iNode->iaddr[10-i]); left--; i--; } if(left>0){ //一級索引回收 i=512; shortdir1[512]; BReadArr(dir1,iNode->iaddr[10]); while(left&&i){ CallBackOne(dir1[512-i]); i--; left--; } CallBackOne(iNode->iaddr[10]); } if(left>0){ //二級索引 shortk=512; shortj=512; shortdir[512]; shortdirChild[512]; BReadArr(dir,iNode->iaddr[11]);//二級索引1次尋址 while(left&&k){ //二級索引1次尋址 BReadArr(dirChild,dir[512-k]); while(left&&j){ //二級索引二次回收 CallBackOne(dirChild[512-j]); left--; j--; } CallBackOne(dir[512-k]);//二級索引一次尋址 k--; } CallBackOne(iNode->iaddr[11]); } }//================================================================//函數描述:回收文件的iNOde節點//入口參數:無//返回值:無//===============================================================voidCallBackINode(shortdiskNum){ CallBackOne(diskNum); }//================================================================//函數描述:刪除索引中一項//入口參數:無//返回值:-1,不存在,文件號//===============================================================voidDelDirItem(DirNode*currDir,charfileName[14]){ for(inti=0;i<64;i++){ if(strcmp(fileName,currDir->childItem[i].filename)==0){ // currDir->DirCount--; strcpy(currDir->childItem[i].filename,NullName); currDir->childItem[i].i_BNum=-1; return; } } cout<<"刪除失敗"<<endl;}//================================================================//函數描述:刪除一個文件//入口參數:無//返回值:無//===============================================================voidDel(DirNode*currDir,charfileName[14],INode*iNode){ shortblockNum=IsFileExist(currDir,fileName); if(blockNum==-1){//不存在該文件,退出 cout<<"文件不存在,刪除失敗"<<endl; }else{ if(IsFile(iNode,blockNum)){ CallBackDisk(iNode); DelDirItem(currDir,fileName); CleanINode(iNode); }else{ cout<<"文件不存在,刪除失敗"<<endl; } } }//================================================================//函數描述:刪除一個目錄//入口參數:無//返回值:無//===============================================================voidRd(DirNode*currDir,charfileName[14],INode*iNode){ shortblockNum=IsFileExist(currDir,fileName); if(blockNum==-1){//不存在該文件,退出 cout<<"目錄不存在,刪除失敗"<<endl; }else{ if(IsDir(iNode,blockNum)){ CallBackDisk(iNode); DelDirItem(currDir,fileName); CleanINode(iNode); }else{ cout<<"目錄不存在,刪除失敗"<<endl; } } }//================================================================//函數描述:顯示目錄項的內容//入口參數:無//返回值:無//===============================================================voidDir(DirNode*currDir,INode*iNode){ for(inti=0;i<currDir->DirCount;i++){ if(currDir->childItem[i].i_BNum!=-1){ BRead(iNode,currDir->childItem[i].i_BNum); ShowFileInfo(iNode,currDir->childItem[i].filename); } CleanINode(iNode); }}//================================================================//函數描述:銷毀資源//入口參數:無//返回值:無//===============================================================voidexit(DirNode*currDir,INode*iNode){ deleteiNode; deletecurrDir;}//=======================================================

溫馨提示

  • 1. 本站所有資源如無特殊說明,都需要本地電腦安裝OFFICE2007和PDF閱讀器。圖紙軟件為CAD,CAXA,PROE,UG,SolidWorks等.壓縮文件請下載最新的WinRAR軟件解壓。
  • 2. 本站的文檔不包含任何第三方提供的附件圖紙等,如果需要附件,請聯系上傳者。文件的所有權益歸上傳用戶所有。
  • 3. 本站RAR壓縮包中若帶圖紙,網頁內容里面會有圖紙預覽,若沒有圖紙預覽就沒有圖紙。
  • 4. 未經權益所有人同意不得將文件中的內容挪作商業或盈利用途。
  • 5. 人人文庫網僅提供信息存儲空間,僅對用戶上傳內容的表現方式做保護處理,對用戶上傳分享的文檔內容本身不做任何修改或編輯,并不能對任何下載內容負責。
  • 6. 下載文件中如有侵權或不適當內容,請與我們聯系,我們立即糾正。
  • 7. 本站不保證下載資源的準確性、安全性和完整性, 同時也不承擔用戶因使用這些下載資源對自己和他人造成任何形式的傷害或損失。

最新文檔

評論

0/150

提交評論