《虚拟文件系统的实现要点.pdf》由会员分享,可在线阅读,更多相关《虚拟文件系统的实现要点.pdf(33页珍藏版)》请在三一文库上搜索。
1、渤海大学 操作系统课程设计 实验报告书 题目:虚拟文件系统的实现 题目编号: 院系:软件服务与外包学院 班级:11 级 2 班 小组成员:陈镜欢学号: 111810040 王晨学号: 111810035 2013-06-30 目 录 一、课程设计任务划分 1 二、基本原理 . 1 2.1 主要操作函数 1 2.2 数据结构 1 2.3 算法流程图 3 三、基本思路 . 4 3.1 设计简介 . 4 3.2 设计方案论述 . 4 3.3 文件基本操作 . 4 四、调试及实验结果 5 运行结果分析 8 五、个人体会 . 8 1 一、课程设计任务划分 陈镜欢 : 主要编写代码熟悉课题的任务和要求,查
2、阅相关文献和资料, 并做好 编码准备,调试,验收 王晨: 程序编码、调试和测试,书写报告 二、基本原理 2.1 主要操作函数 int create( char *name); intopen(char *name); intclose(char *name); int write(int fd,char *buf,int len); intread(int fd,char *buf); intdel(char *name); int mkdir(char *name); int rmdir(char *name); void dir(); int cd(char *name); void pr
3、int(); void show(); 2.2 数据结构 struct fatitem /* size 8*/ 2 int item; /*存放文件下一个磁盘的指针*/ char em_disk; /*磁盘块是否空闲标志位 0 空闲*/ ; struct direct /*- 文件控制快信息 -*/ struct FCB char name9; /*文件/目录名8位*/ charproperty; /*属性1位目录 0位普通文件 */ int size; /*文件/目录字节数、盘块数 )*/ int firstdisk; /*文件/目录起始盘块号 */ int next; /*子目录起始盘块号
4、 */ int sign; /*1是根目录 0不是根目录 */ directitemMSD+2; ; struct opentable struct openttableitem char name9; /*文件名 */ int firstdisk; /*起始盘块号 */ int size; /*文件的大小 */ openitemMOFN; int cur_size; /*当前打文件的数目 */ ; 3 2.3 算法流程图 开始 初始化磁盘 登 Y N 创 建 打开 文件 关闭 文件 读文写文列文件 目录 删 除 注 销 退 出 提示错误 指令成功 执行? N 4 三、基本思路 3.1 设计简
5、介 本系统是模拟实现多用户多目录的文件系统, 在系统出现登录后 , 输入用户 与口令 , 在用户登录系统后 , 可建立文件卷 , 将用户输入的文件保存在指定的文件 中。系统的命令与其命令的具体实现,此模拟系统共提供了上述命令, 并根据命 令的含义与要求 , 用 C+ 编程来完成所有具体操作。该系统可以模拟完成用户的 登陆和验证 , 列出文件和目录 , 新建目录 , 改变目录 , 创立和编写文件 , 删除文件和 退出系统等功能 3.2 设计方案论述 本文件系统采用两级目录, 其中第一级对应于用户账号, 第二级对应于用户 帐号下的文件。 另外,为了简便文件系统未考虑文件共享,文件系统安全以及管 道
6、文件与设备文件等特殊内容。 首先应确定文件系统的数据结构:主目录、子目录及活动文件等。主目录和 子目录都以文件的形式存放于磁盘,这样便于查找和修改。 用户创建的文件,可以编号存储于磁盘上。如:file0,file1,file2并以 编号作为物理地址,在目录中进行登记。 3.3 文件基本操作 创建文件:创建一个新文件时,系统首先要为新文件申请必要的外存空间, 并在 FAT中为文件分配一个目录项。 目录项中应记录新建文件的文件名、文件总 容量、当前已经使用的容量、文件属性、文件在磁盘中的起始位置。 删除文件:当已不在需要某文件时,可将它从文件系统中删除。在删除时, 5 首先在 FAT的文件链表中找
7、到与该文件对应的文件结点,然后确认文件是否处于 关闭状态, 若以上条件都满足, 则系统就可以把结点从文件链表中删除,然后回 收改结点对应的磁盘空间。 打开文件:只有处于打开状态的文件才能被读取、写入、重复关闭且不能被 删除。 关闭文件:只有处于关闭状态的文件才能被删除,且不能被重复关闭。 列文件目录:用户只能获取自己建立的文件或其他用户共享的文件的列表, 并可以查看所用户建立的文件列表。 写文件:用户可以把相关数据写入到用户自定义的文件中(磁盘上);待写 文件必须处于打开状态,且不能是其他用户共享的文件。 读文件:用户可以把文件中存储的数据读取出来;待读文件必须处于打开状 态;用户既可以读取自
8、己建立的文件,也可以读取其他用户共享的文件。 建子目录:输入目录名, 若存在于该文件名相同的目录, 这创建失败;若无, 则查找空闲的磁盘,将该磁盘置为分配状态,填写目录项,分配地址后,子目录 创建成功。 删除目录:输入名字,查找是否存在该文件或目录, 若为文件,则不能删除; 若存在,找到起始盘块号,并将其释放,修改目录项,删除成功。 四、调试及实验结果 (1)login用户登录 6 (2)mkdir 创建子目录 (3)cd 进出目录 (4)create 创建文件 (5)close 关闭文件 (6)open打开文件 7 (7)write 写文件 (8)read 读文件 (9)dir列目录 (10
9、)delete 删除文件 (11)rmdir 删除子目录 8 运行结果分析 从上述运行过程可以看出, 用户登录系统后, 界面将显示文件或目录的基本 操作,然后根据相应操作,完成系统的基本要求。 本次程序的运行结果与预期结果最终达到了一致。自运行阶段, 虽然每次都 能得到运行结果, 但是操作界面有时不是很完美,于是通过修改程序代码, 不断 执行程序,进行完善,直到得出满意的操作界面为止。在该过程中,验证了本次 课程设计所要求的基本功能, 虽然有些操作不是很完善, 但大体上都能实现。 其 中最令我不满意的是dir功能。 该功能只是列出目录名, 不能显示目录其他信息, 是本次课程设计最大败笔。 五、
10、个人体会 课程设计是对我们平时学习的一种考察,我们要正确地对待。 不断地锻炼自 己动手动脑的能力、把知识赋予实践就是我们学习的目标! 既然学校给我们这么好的机会, 让我们自己在实验室作操作, 我们应该好好 抓住机会, 把我们平时学习的东西用自己的作品展现出来。这次,给了我们充分 锻炼的机会。我们会用自己学到的东西的设计出一副好的作品。 而对于我们来说,这种最灵活的知识却是最难掌握的。也因为对其基本知识 掌握的不好, 在这一次的设计过程中遇到很多的困难,特别是物理盘块和逻辑文 件之间的对应。 在经过与同学进行沟通和交流并反复的测试之后,才明白了设计 的函数,而且完善了部分函数的主要功能。 通过两
11、星期的操作系统课程设计实习,让我们对 Linux 文件系统有了深层次 的了解和掌握, 也通过了自己的能力体会到了编程的乐趣。最重要的是学会了关 于设计分析和以前C语言学习过程中没有及时巩固的知识,对 C程序设计又有了 更进一步的认识,对一些细节的结构体语句有了更深刻的理解。 所以这是一次很难得的实践机会,让我们真正用心编程, 学到了课本以外更 深刻更重要的实践经验。 非常感谢老师提供这次机会, 在这个课程设计过程中我 受益匪浅, 希望以后在这样的锻炼中不断成长,提高自己各方面的能力, 我们相 信通过我们以后很加刻苦的学习,我们会更加热爱我们的专业课程。 - 1 - 附录 主要代码源程序: #i
12、nclude #include #include #define MEM_D_SIZE 1024*1024 /总磁盘空间为M #define DISKSIZE 1024 /磁盘块的大小K #define DISK_NUM 1024 /磁盘块数目 K #define FATSIZE DISK_NUM*sizeof(struct fatitem) /FAT表大小 #define ROOT_DISK_NO FATSIZE/DISKSIZE+1 /根目录起始盘块号 #define ROOT_DISK_SIZE sizeof(struct direct) /根目录大小 #define DIR_MAXSI
13、ZE 1024 /路径最大长度为KB #define MSD 5 /最大子目录数 #define MOFN 5 /最大文件深度为 #define MAX_WRITE 1024*128 /最大写入文字长度KB struct fatitem /* size 8*/ int item; /*存放文件下一个磁盘的指针*/ char em_disk; /* 磁盘块是否空闲标志位0 空闲 */ ; struct direct /*- 文件控制快信息-*/ struct FCB char name9; /*文件 /目录名 8位*/ char property; /*属性 1位目录 0位普通文件 */ int
14、 size; /*文件 /目录字节数、盘块数)*/ int firstdisk; /*文件 /目录起始盘块号*/ int next; /*子目录起始盘块号*/ int sign; /*1 是根目录 0不是根目录 */ directitemMSD+2; ; struct opentable struct openttableitem 渤海大学计算机科学与技术学院实验设计报告书 - 2 - char name9; /* 文件名 */ int firstdisk; /* 起始盘块号 */ int size; /*文件的大小 */ openitemMOFN; int cur_size; /*当前打文件
15、的数目*/ ; struct fatitem *fat; /*FAT 表*/ struct direct *root; /*根目录 */ struct direct *cur_dir; /*当前目录 */ struct opentable u_opentable; /* 文件打开表 */ int fd=-1; /*文件打开表的序号*/ char *bufferdir; /*记录当前路径的名称*/ char *fdisk; /*虚拟磁盘起始地址*/ void initfile(); void format(); void enter(); void halt(); int create(char
16、 *name); int open(char *name); int close(char *name); int write(int fd,char *buf,int len); int read(int fd,char *buf); int del(char *name); int mkdir(char *name); int rmdir(char *name); void dir(); int cd(char *name); void print(); void show(); void initfile() fdisk = (char *)malloc(MEM_D_SIZE*sizeo
17、f(char); /*申请 1M空间 */ format(); void format() int i; FILE *fp; 渤海大学计算机科学与技术学院实验设计报告书 - 3 - fat = (struct fatitem *)(fdisk+DISKSIZE); /*计算 FAT表地址,引导区向后偏移1k)*/ /*- 初始化 FAT表-*/ fat0.item=-1; /*引导块 */ fat0.em_disk=1; for(i=1;idirectitem0.sign = 1; root-directitem0.firstdisk = ROOT_DISK_NO; strcpy(root-d
18、irectitem0.name,“.“); root-directitem0.next = root-directitem0.firstdisk; root-directitem0.property = 1; root-directitem0.size = ROOT_DISK_SIZE; /*- 指向上一级目录的目录项-*/ root-directitem1.sign = 1; root-directitem1.firstdisk = ROOT_DISK_NO; strcpy(root-directitem1.name,“); root-directitem1.next = root-dire
19、ctitem0.firstdisk; root-directitem1.property = 1; root-directitem1.size = ROOT_DISK_SIZE; if(fp = fopen(“disk.dat“,“wb“)=NULL) printf(“Error:n Cannot open file n“); return; for(i=2;idirectitemi.sign = 0; root-directitemi.firstdisk = -1; strcpy(root-directitemi.name,“); root-directitemi.next = -1; ro
20、ot-directitemi.property = 0; root-directitemi.size = 0; if(fp = fopen(“disk.dat“,“wb“)=NULL) printf(“Error:n Cannot open file n“); return; if(fwrite(fdisk,MEM_D_SIZE,1,fp)!=1) /*把虚拟磁盘空间保存到磁盘文件中*/ printf(“Error:n File write error! n“); fclose(fp); void enter() FILE *fp; int i; fdisk = (char *)malloc(
21、MEM_D_SIZE*sizeof(char); /*申请 1M空间 */ if(fp=fopen(“disk.dat“,“rb“)=NULL) printf(“Error:nCannot open filen“); return; if(!fread(fdisk,MEM_D_SIZE,1,fp) /*把磁盘文件 disk.dat 读入虚拟磁盘空间(内存 )*/ printf(“Error:nCannot read filen“); exit(0); fat = (struct fatitem *)(fdisk+DISKSIZE); /*找到 FAT表地址 */ root = (struct
22、direct *)(fdisk+DISKSIZE+FATSIZE);/*找到根目录地址*/ fclose(fp); /*-初始化用户打开表-*/ for(i=0;i8) /* 文件名大于 8位 */ return(-1); for(j=2;jdirectitemj.name,name) break; 渤海大学计算机科学与技术学院实验设计报告书 - 6 - if(jdirectitemi.firstdisk=-1) break; if(i=MSD+2) /*无空目录项 */ return(-2); if(u_opentable.cur_size=MOFN) /*打开文件太多*/ return(-
23、3); for(j=ROOT_DISK_NO+1;j=DISK_NUM) return(-5); fatj.em_disk = 1; /*将空闲块置为已经分配*/ /*- 填写目录项 -*/ strcpy(cur_dir-directitemi.name,name); cur_dir-directitemi.firstdisk = j; cur_dir-directitemi.size = 0; cur_dir-directitemi.next = j; cur_dir-directitemi.property = 0; /*-*/ fd = open(name); return 0; int
24、 open(char *name) int i, j; for(i=2;idirectitemi.name,name) break; 渤海大学计算机科学与技术学院实验设计报告书 - 7 - if(i=MSD+2) return(-1); /*- 是文件还是目录-*/ if(cur_dir-directitemi.property=1) return(-4); /*- 文件是否打开-*/ for(j=0;j=MOFN) /*文件打开太多*/ return(-3); /*- 查找一个空闲用户打开表项-*/ for(j=0;jdirectitemi.firstdisk; strcpy(u_opent
25、able.openitemj.name,name); u_opentable.openitemj.size = cur_dir-directitemi.size; u_opentable.cur_size+; /*- 返回用户打开表表项的序号-*/ return(j); int close(char *name) int i; for(i=0;i=MOFN) 渤海大学计算机科学与技术学院实验设计报告书 - 8 - return(-1); /*- 清空该文件的用户打开表项的内容-*/ strcpy(u_opentable.openitemi.name,“); u_opentable.openit
26、emi.firstdisk = -1; u_opentable.openitemi.size = 0; u_opentable.cur_size-; return 0; int write(int fd, char *buf, int len) char *first; int item, i, j, k; int ilen1, ilen2, modlen, temp; /*- 用$ 字符作为空格 # 字符作为换行符-*/ char Space = 32; char Endter= n; for(i=0;idirectitemi.firstdisk=item) break; temp = i;
27、 /*- 存放当前目录项的下标-*/ /*- 找到的 item 是该文件的最后一块磁盘块-*/ while(fatitem.item!=-1) item =fatitem.item; /*-查找该文件的下一盘块-*/ 渤海大学计算机科学与技术学院实验设计报告书 - 9 - /*- 计算出该文件的最末地址-*/ first = fdisk+item*DISKSIZE+u_opentable.openitemfd.size%DISKSIZE; /*- 如果最后磁盘块剩余的大小大于要写入的文件的大小-*/ if(DISKSIZE-u_opentable.openitemfd.size%DISKSIZ
28、Elen) strcpy(first,buf); u_opentable.openitemfd.size = u_opentable.openitemfd.size+len; cur_dir-directitemtemp.size = cur_dir-directitemtemp.size+len; else for(i=0;i0) ilen2 = ilen2+1; /*- 还需要多少块磁盘块-*/ for(j=0;j=DISK_NUM) /*-如果磁盘块已经分配完了-*/ return(-1); first = fdisk+i*DISKSIZE; /*-找到的那块空闲磁盘块的起始地址-*/
29、if(j=ilen2-1) /*-如果是最后要分配的一块-*/ for(k=0;kdirectitemtemp.size = cur_dir-directitemtemp.size+len; return 0; int read(int fd, char *buf) int len = u_opentable.openitemfd.size; char *first; int i, j, item; int ilen1, modlen; item = u_opentable.openitemfd.firstdisk; ilen1 = len/DISKSIZE; modlen = len%DIS
30、KSIZE; if(modlen!=0) ilen1 = ilen1+1; /*- 计算文件所占磁盘的块数-*/ first = fdisk+item*DISKSIZE; /*-计算文件的起始位置-*/ for(i=0;idirectitemi.name,name) break; cur_item = i; /*- 用来保存目录项的序号,供释放目录中-*/ if(i=MSD+2) /*-如果不在当前目录中-*/ return(-1); if(cur_dir-directitemcur_item.property!=0) /*-如果删除的 (不)是目录 -*/ return(-3); for(i
31、=0;idirectitemcur_item.firstdisk;/*-该文件的起始盘块号-*/ while(item!=-1) /*-释放空间 ,将FAT表对应项进行修改-*/ temp = fatitem.item; fatitem.item = -1; fatitem.em_disk = 0; item = temp; /*-释放目录项 -*/ cur_dir-directitemcur_item.sign = 0; cur_dir-directitemcur_item.firstdisk = -1; strcpy(u_opentable.openitemcur_item.name,“)
32、; cur_dir-directitemcur_item.next = -1; cur_dir-directitemcur_item.property = 0; cur_dir-directitemcur_item.size = 0; return 0; 渤海大学计算机科学与技术学院实验设计报告书 - 12 - int mkdir(char *name) int i,j; struct direct *cur_mkdir; if(!strcmp(name,“.“) return(-4); if(!strcmp(name,“) return(-4); if(strlen(name)8) /*-
33、如果目录名长度大于8位-*/ return(-1); for(i=2;idirectitemi.firstdisk=-1) break; if(i=MSD+2) /*-目录 /文件已满 -*/ return(-2); for(j=2;jdirectitemj.name,name) break; if(j=DISK_NUM) return(-5); fatj.em_disk=1; /*-将该空闲块设置为已分配-*/ /*-填写目录项 -*/ strcpy(cur_dir-directitemi.name,name); cur_dir-directitemi.firstdisk=j; cur_di
34、r-directitemi.size=ROOT_DISK_SIZE; cur_dir-directitemi.next=j; cur_dir-directitemi.property=1; 渤海大学计算机科学与技术学院实验设计报告书 - 13 - /*- 所创目录在虚拟磁盘上的地址(内存物理地址)-*/ cur_mkdir=(struct direct *)(fdisk+cur_dir-directitemi.firstdisk*DISKSIZE); /*- 初始化目录 -*/ /*- 指向当前目录的目录项-*/ cur_mkdir-directitem0.sign=0; cur_mkdir-
35、directitem0.firstdisk=cur_dir-directitemi.firstdisk; strcpy(cur_mkdir-directitem0.name,“.“); cur_mkdir-directitem0.next=cur_mkdir-directitem0.firstdisk; cur_mkdir-directitem0.property=1; cur_mkdir-directitem0.size=ROOT_DISK_SIZE; /*- 指向上一级目录的目录项-*/ cur_mkdir-directitem1.sign=cur_dir-directitem0.sign
36、; cur_mkdir-directitem1.firstdisk=cur_dir-directitem0.firstdisk; strcpy(cur_mkdir-directitem1.name,“); cur_mkdir-directitem1.next=cur_mkdir-directitem1.firstdisk; cur_mkdir-directitem1.property=1; cur_mkdir-directitem1.size=ROOT_DISK_SIZE; for(i=2;idirectitemi.sign=0; cur_mkdir-directitemi.firstdisk
37、=-1; strcpy(cur_mkdir-directitemi.name,“); cur_mkdir-directitemi.next=-1; cur_mkdir-directitemi.property=0; cur_mkdir-directitemi.size=0; return 0; int rmdir(char *name) int i,j,item; struct direct *temp_dir; /*- 检查当前目录项中有无该目录-*/ for(i=2;idirectitemi.name,name) break; if(i=MSD+2) /*-没有这个文件或目录-*/ ret
38、urn(-1); if(cur_dir-directitemi.property!=1)/*-删除的不是目录-*/ 渤海大学计算机科学与技术学院实验设计报告书 - 14 - return(-3); /*- 判断要删除的目录有无子目录-*/ temp_dir=(struct direct *)(fdisk+cur_dir-directitemi.next*DISKSIZE); for(j=2;jdirectitemj.next!=-1) break; if(jdirectitemi.firstdisk; fatitem.em_disk=0; /*- 修改目录项 -*/ cur_dir-direc
39、titemi.sign=0; cur_dir-directitemi.firstdisk=-1; strcpy(cur_dir-directitemi.name,“); cur_dir-directitemi.next=-1; cur_dir-directitemi.property=0; cur_dir-directitemi.size=0; return 0; void dir() int i; for(i=2;idirectitemi.firstdisk!=-1) /*-如果存在子目录-*/ printf(“%st“,cur_dir-directitemi.name); if(cur_d
40、ir-directitemi.property=0) /*-文件 -*/ printf(“%dttn“,cur_dir-directitemi.size); else printf(“ttn“); int cd(char *name) 渤海大学计算机科学与技术学院实验设计报告书 - 15 - int i,j,item; char *str; char *temp,*point,*point1; struct direct *temp_dir; temp_dir=cur_dir; str=name; if(!strcmp(“,name) cur_dir = root; strcpy(buffer
41、dir,“Root:“); return 0; temp = (char *)malloc(DIR_MAXSIZE*sizeof(char);/*-最长路径名字分配空间-*/ for(i=0;idirectitemj.name,temp) break; free(temp);/* 释放申请的临时空间*/ /if(temp_dir-directitemj.property!=1) /*-打开的不是目录-*/ /return(-2); if(j=MSD+2) /*- 不在当前目录-*/ return(-1); item=temp_dir-directitemj.firstdisk; /*- 当前目
42、录在磁盘中位置-*/ temp_dir=(struct direct *)(fdisk+item*DISKSIZE); if(!strcmp(“,name) if(cur_dir-directitemj-1.sign!=1) /*-如果上级目录不是根目录-*/ point=strchr(bufferdir,); /查找字符串 bufferdir 中首次出现字符 的位置 while(point!=NULL) 渤海大学计算机科学与技术学院实验设计报告书 - 16 - point1=point+1; /*- 减去 所占的空间 ,记录下次查找的起始地址-*/ point=strchr(point1,)
43、; *(point1-1)=0; /*-将上一级目录删除-*/ else /if(name0 !=) bufferdir = strcat(bufferdir,“); /*-修改当前目录-*/ bufferdir = strcat(bufferdir,name); cur_dir=temp_dir; /*- 将当前目录确定下来-*/ return 0; void show() printf(“%s“,bufferdir); void print() printf(“*n“); printf(“*文件系统设计*n“); printf(“*t 命令格式说明*n“); printf(“*tcd 目录
44、名更改当前目录*n“); printf(“*tmkdir 目录名创建子目录*n“); printf(“*trmdir 目录名删除子目录*n“); printf(“*tdir 显示当前目录的子目录*n“); printf(“*tcreate 文件名创建文件*n“); printf(“*tdel 文件名删除文件*n“); printf(“*topen 文件名打开文件*n“); printf(“*tclose 文件名关闭文件*n“); printf(“*tread 读文件*n“); printf(“*twrite 写文件*n“); printf(“*texit 退出系统*n“); printf(“*
45、n“); 渤海大学计算机科学与技术学院实验设计报告书 - 17 - main() FILE *fp; char ch; char a100; char code1110; char name10; int i,flag,r_size; char *contect; contect = (char *)malloc(MAX_WRITE*sizeof(char); if(fp=fopen(“disk.dat“,“rb“)=NULL) printf(“You have not format,Do you want format?(y/n)“); scanf(“%c“, if(ch=y) initfile(); printf(“Successfully format! n“); else return 0; enter(); print(); show(); strcpy(code0,“exit“); strcpy(code1,“create“); strcpy(code2,“open“); strcpy(code3,“close“); strcpy(code4,“write“); strcpy(code5,“read“); strcpy(code6,“del“); strcpy(code7,“mkdir“); strcpy(code8,
链接地址:https://www.31doc.com/p-5211979.html