操作系统课程设计文件系统.docx
《操作系统课程设计文件系统.docx》由会员分享,可在线阅读,更多相关《操作系统课程设计文件系统.docx(27页珍藏版)》请在冰点文库上搜索。
操作系统课程设计文件系统
模拟一个简单二级文件管理系统
设计目的:
通过具体的文件存储空间的管理、文件的物理结构、目录结构和文件操作的实现,加深对文件系统内部功能和实现过程的理解。
设计内容:
模拟一个简单二级文件管理系统
一、实验内容描述
1实验目标
本实验的目的是通过一个简单多用户文件系统的设计,加深理解文件系统的内部功能及内部实现.
2实验要求
为DOS系统设计一个简单的二级文件系统.要求做到以下几点:
①可以实现下列命令:
login用户登录
dir列文件目录
create创建文件
delete删除文件
open打开文件
close关闭文件
read读文件
write写文件
②列目录时要列出文件名、物理地址、保护码和文件长度.
③源文件可以进行读写保护.
二、程序主要内容
1设计思路
程序中要求每个用户在登陆后才可对其拥有的文件进行操作,用户对于其他用户的文件无操作权.文件操作包括浏览、创建、删除、打开、关闭、阅读、写入、修改模式.其他操作包括新建用户、帮助、用户登入、用户登出、退出系统.
在程序文件夹下有个名为“file”的系统根目录,此目录下包括:
一个名为“mfd”的文件,记录所有注册过的帐号及密码;用户文件,以用户名作为文件名,内容为其拥有的文件名及属性;一个名为“keiji”的文件夹.“keiji”文件夹中包括:
“file.p”指针文件,记录所有已用的物理地址;一些以物理地址为名的文件,内容为文件内容.
2数据结构
file结构体系统文件数据结构:
fpaddrint,文件的物理地址、flengthint,文件长度、fmodeint,文件模式0.只读;1.可写;2.可读写;3.保护、fname[]char,文件名;
filemode结构体文件状态数据结构:
isopenint,文件当前状态,0.关闭;1.打开、modeint,文件模式0.只读;1.可写;2.可读写;3.初始化;
user结构体用户信息数据结构:
uname[]char,用户名、upassword[]char,用户密码;
userfile结构体用户文件数据结构:
uname[]char,用户名、ufile[]file,用户拥有的文件数组.
代码:
#include
#include
#include
#include
#include
#defineMaxUser100//定义最大MDF主目录文件
#defineMaxDisk512*1024//模拟最大磁盘空间
#definecommandAmount12//对文件操作的指令数
//存储空间管理有关结构体和变量
chardisk[MaxDisk];//模拟512K的磁盘存储空间
typedefstructdistTable//磁盘块结构体
{
intmaxlength;
intstart;
intuseFlag;
distTable*next;
}diskNode;
diskNode*diskHead;
structfileTable//文件块结构体
{
charfileName[10];
intstrat;//文件在磁盘存储空间的起始地址
intlength;//文件内容长度
intmaxlength;//文件的最大长度
charfileKind[3];//文件的属性——读写方式
structtm*timeinfo;
boolopenFlag;//判断是否有进程打开了该文件
//fileTable*next;
};
//两级目录结构体
typedefstructuser_file_directory//用户文件目录文件UFD
{
//charfileName[10];
fileTable*file;
user_file_directory*next;
}UFD;
//UFD*headFile;
typedefstructmaster_file_directory//主文件目录MFD
{
charuserName[10];
charpassword[10];
UFD*user;
}MFD;
MFDuserTable[MaxUser];
intused=0;//定义MFD目录中用已有的用户数
//文件管理
voidfileCreate(charfileName[],intlength,charfileKind[]);//创建文件
voidfileWrite(charfileName[]);//写文件
voidfileCat(charfileName[]);//读文件
voidfileRen(charfileName[],charrename[]);//重命名文件
voidfileFine(charfileName[]);//查询文件
voidfileDir(charUserName[]);//显示某一用户的所有文件
voidfileClose(charfileName[]);//关闭已打开的文件
voidfileDel(charfileName[]);//删除文件
voidchmod(charfileName[],charkind[]);//修改文件的读写方式
intrequestDist(int&startPostion,intmaxLength);//磁盘分配查询
voidinitDisk();//初始化磁盘
voidfreeDisk(intstartPostion);//磁盘空间释放
voiddiskShow();//显示磁盘使用情况
//用户管理
voiduserCreate();
intlogin();
intuserID=-1;//用户登录的ID号,值为-1时表示没有用户登录
intmain()
{
charorder[commandAmount][10];
strcpy(order[0],"create");
strcpy(order[1],"rm");
strcpy(order[2],"cat");
strcpy(order[3],"write");
strcpy(order[4],"fine");
strcpy(order[5],"chmod");
strcpy(order[6],"ren");
strcpy(order[7],"dir");
strcpy(order[8],"close");
printf("————————————————————————————————————————\n");
printf("pleaseimputyourcommand:
>");
gets(command);
intselect;
for(i=0;command[i]!
=''&&command[i]!
='\0';i++)//command_str1字符串存储命令的操作类型
command_str1[i]=command[i];
k=i;
command_str1[k]='\0';
for(i=0;i{
if(!
strcmp(command_str1,order[i]))
{
select=i;
break;
}
}
if(i==commandAmount)
{
printf("您输入的命令有误,请重新输入\n");
continue;
}
for(i=k+1,k=0;command[i]!
=''&&command[i]!
='\0';i++,k++)//commmand_str2字符串存储文件名或用户名
command_str2[k]=command[i];
command_str2[k]='\0';
k=i;
switch(select)
{
case0:
for(i=k+1,k=0;command[i]!
='';i++,k++)
command_str3[k]=command[i];
command_str3[k]='\0';
k=i;
j=1;
length=0;//初始化文件长度
for(i=strlen(command_str3)-1;i>=0;i--)//把字符串转换为十进制
{
length+=(command_str3[i]-48)*j;
j*=10;
}
for(i=k+1,k=0;command[i]!
=''&&command[i]!
='\0';i++,k++)
command_str4[k]=command[i];
command_str4[k]='\0';
fileCreate(command_str2,length,command_str4);break;
case1:
fileDel(command_str2);break;
case2:
fileCat(command_str2);break;
case3:
fileWrite(command_str2);break;
case4:
fileFine(command_str2);break;
case5:
for(i=k+1,k=0;command[i]!
=''&&command[i]!
='\0';i++,k++)
command_str3[k]=command[i];
command_str3[k]='\0';
chmod(command_str2,command_str3);break;
case6:
for(i=k+1,k=0;command[i]!
='\0';i++,k++)
command_str3[k]=command[i];
command_str3[k]='\0';
fileRen(command_str2,command_str3);break;
case7:
fileDir(command_str2);break;
case8:
fileClose(command_str2);break;
case9:
UFD*p;
for(p=userTable[userID].user->next;p!
=NULL;p=p->next)//退出用户之前关闭所有打的文件
if(p->file->openFlag)
p->file->openFlag=false;
system("cls");
userID=-1;break;
case10:
exit(0);break;
case11:
diskShow();break;
}
}
}
return0;
}
voiduserCreate()
{
charc;
charuserName[10];
inti;
if(used{
printf("请输入用户名:
");
for(i=0;c=getch();i++)
{
if(c==13)break;
else
userName[i]=c;
printf("%c",c);
}
userName[i]='\0';
for(i=0;i{
if(!
strcmp(userTable[i].userName,userName))
{
printf("\n");
printf("该用户名已存在,创建用户失败\n");
system("pause");
return;
}
}
strcpy(userTable[used].userName,userName);
printf("\n");
printf("请输入密码:
");
for(i=0;c=getch();i++)
{
if(c==13)break;
else
userTable[used].password[i]=c;
printf("*");
}
userTable[userID].password[i]='\0';
printf("\n");
printf("创建用户成功\n");
used++;
system("pause");
}
else
{
printf("创建用户失败,用户已达到上限\n");
system("pause");
}
fflush(stdin);
}
intlogin()
{
charname[10],psw[10];
charc;
inti,times;
printf("请输入用户名:
");
for(i=0;c=getch();i++)
{
if(c==13)break;
else
name[i]=c;
printf("%c",c);
}
name[i]='\0';
for(i=0;i{
if(!
strcmp(userTable[i].userName,name))
break;
}
if(i==used)
{
printf("\n您输入的用户名不存在\n");
system("pause");
return-1;
}
for(times=0;times<3;times++)
{
memset(psw,'\0',sizeof(psw));
printf("\n请输入密码:
");
for(i=0;c=getch();i++)
{
if(c==13)break;
else
psw[i]=c;
printf("*");
}
printf("\n");
for(i=0;i{
if(!
strcmp(psw,userTable[i].password))
{
printf("用户登录成功\n");
system("pause");
break;
}
}
if(i==used)
{
printf("您输入的密码错误,您还有%d次输入机会\n",2-times);
if(times==2)exit(0);
}
elsebreak;
}
fflush(stdin);
returni;
}
voidinitDisk()
{
diskHead=(diskNode*)malloc(sizeof(diskNode));
diskHead->maxlength=MaxDisk;
diskHead->useFlag=0;
diskHead->start=0;
diskHead->next=NULL;
}
intrequestDist(int&startPostion,intmaxLength)
{
intflag=0;//标记是否分配成功
diskNode*p,*q,*temp;
p=diskHead;
while(p)
{
if(p->useFlag==0&&p->maxlength>maxLength)
{
startPostion=p->start;
q=(diskNode*)malloc(sizeof(diskNode));
q->start=p->start;
q->maxlength=maxLength;
q->useFlag=1;
q->next=NULL;
diskHead->start=p->start+maxLength;
diskHead->maxlength=p->maxlength-maxLength;
flag=1;
temp=p;
if(diskHead->next==NULL)diskHead->next=q;
else
{
while(temp->next)temp=temp->next;
temp->next=q;
}
break;
}
p=p->next;
}
returnflag;
}
voidfileCreate(charfileName[],intlength,charfileKind[])
{
//inti,j;
time_trawtime;
intstartPos;
UFD*fileNode,*p;
for(p=userTable[userID].user->next;p!
=NULL;p=p->next)
{
if(!
strcmp(p->file->fileName,fileName))
{
printf("文件重名,创建文件失败\n");
system("pause");
return;
}
}
if(requestDist(startPos,length))
{
fileNode=(UFD*)malloc(sizeof(UFD));
fileNode->file=(fileTable*)malloc(sizeof(fileTable));//这一步必不可少,因为fileNode里面的指针也需要申请地址,否则fileNode->file指向会出错
strcpy(fileNode->file->fileName,fileName);
strcpy(fileNode->file->fileKind,fileKind);
fileNode->file->maxlength=length;
fileNode->file->strat=startPos;
fileNode->file->openFlag=false;
time(&rawtime);
fileNode->file->timeinfo=localtime(&rawtime);
fileNode->next=NULL;
if(userTable[userID].user->next==NULL)
userTable[userID].user->next=fileNode;
else
{
p=userTable[userID].user->next;
while(p->next)p=p->next;
p->next=fileNode;
}
printf("创建文件成功\n");
system("pause");
}
else
{
printf("磁盘空间已满或所创建文件超出磁盘空闲容量,磁盘空间分配失败\n");
system("pause");
}
}
voidfreeDisk(intstartPostion)
{
diskNode*p;
for(p=diskHead;p!
=NULL;p=p->next)
{
if(p->start==startPostion)
break;
}
p->useFlag=false;
}
voidfileDel(charfileName[])
{
UFD*p,*q,*temp;
q=userTable[userID].user;
p=q->next;
while(p)
{
if(!
strcmp(p->file->fileName,fileName))break;
else
{
p=p->next;
q=q->next;
}
}
if(p)
{
if(p->file->openFlag!
=true)//先判断是否有进程打开该文件
{
temp=p;
q->next=p->next;
freeDisk(temp->file->strat);//磁盘空间回收
free(temp);
printf("文件删除成功\n");
system("pause");
}
else
{
printf("该文件已被进程打开,删除失败\n");
system("pause");
}
}
else
{
printf("没有找到该文件,请检查输入的文件名是否正确\n");
system("pause");
}
}
voidfileCat(charfileName[])
{
intstartPos,length;
intk=0;
UFD*p,*q;
q=userTable[userID].user;
for(p=q->next;p!
=NULL;p=p->next)
{
if(!
strcmp(p->file->fileName,fileName))
break;
}
if(p)
{
startPos=p->file->strat;
length=p->file->length;
p->file->openFlag=true;//文件打开标记
printf("*****************************************************\n");
for(inti=startPos;k{
if(i%50==0)printf("\n");//一行大于50个字符换行
printf("%c",disk[i]);
}
printf("\n\n*****************************************************\n");
printf("%s已被read进程打开,请用close命令将其关闭\n",p->file->fileName);
system("pause");
}
else
{
printf("没有找到该文件,请检查输入的文件名是否正确\n");
system("pause"