虚拟文件系统_第1页
虚拟文件系统_第2页
虚拟文件系统_第3页
虚拟文件系统_第4页
虚拟文件系统_第5页
已阅读5页,还剩33页未读 继续免费阅读

下载本文档

版权说明:本文档由用户提供并上传,收益归属内容提供方,若内容存在侵权,请进行举报或认领

文档简介

1、虚拟文件系统学生课程设计报告 2014 2015 学年 第 二 学期学 院 XXXXXXXXX 专 业 软件工程 学 号 姓 名 指导教师 起 止 周周数1实习地点课程设计目的:1、 理解文件系统功能2、 完成对文件、目录及磁盘空间的管理并提供操作命令3、 实现文件共享与保护课程设计要求:1、利用索引结点实现目录管理。2、建立一个树形目录系统,目录文件及索引结点均用结构数组表示。3、文件盘块采用FAT方式,空指针用-1表示,并设空闲盘块指针。4、提供对文件、目录及磁盘空间的操作命令。进度安排及主要内容:第一周:完成用户登录,目录管理和文件管理第二周:成绩:指导教师(签字)年 月 日一、概述1.

2、1 本文的目的本文内容用于指导学生对课程设计报告的格式和内容安排进行控制。学生在使用时,可直接用格式刷将本文对应部分的格式内容进行提取并加载到目标位置;对于封面、页眉等部分,请直接修改相关文字。二、需求分析本次要实现虚拟文件系统,主要功能有用户登录、子目录的创建、删除、子目录中项的显示;文件的创建、打开、删除、关闭、对文件进行读写等。实现对目录和文件的基本操作和文件的共享与保护。三、技术方案本次课程设计用VS2013编写C+控制台程序模拟文件系统。系统初始时需要登录,登录成功方能对文件进行操作。本虚拟文件系统采用两级目录,第一级目录对应用户账号,第二级目录对应用户下的文件。文件系统的数据结构包

3、括主目录(虚拟C盘)、子目录及所含文件等。三者都存放在磁盘中,方便进行操作。文件可以在目录中进行记录,表明文件所在目录。四、总体设计4.1功能设计1、首次运行系统需要先格式化磁盘空间,申请一个内存为1M的磁盘空间。2、用户登录,用户需输入正确的用户名和密码方能进入本系统进行文件和目录的操作。3、进入系统后可根据提示对文件和目录进行操作。4.2虚拟文件系统算法流程图 算法流程图4-1五、详细设计5.1系统功能说明1、 创建子目录:输入createdir 目录名,即进行目录创建操作,若当前目录已满或文件名已经存在则创建失败,返回失败信息。否则创建成功,并找到空闲磁盘块,将该磁盘块设为已分配,填写目

4、录项。2、 删除子目录:removedir 目录名,检查当前目录项中有无该目录,判断要删除的目录有无子目录,如果有子目录将其释放,进行删除操作。3、 更改当前目录:cd 目录名,可以进入到子目录并回退上级目录。4、 显示目录中项:showdir可以显示目录和文件,文件显示大小,目录显示目录。5、 文件操作:创建文件、打开文件(创建时自动打开该文件),删除文件,关闭文件、读文件、写文件、6、 退出5.2数据结构struct direct/*文件控制快信息*/struct FCBchar name9; /文件/目录名8位char property; /属性1位目录0位普通文件int size; /

5、文件/目录字节数、盘块数)int firstdisk; /文件/目录起始盘块号int next; /子目录起始盘块号int sign; /1是根目录0不是根目录directitemMSD + 2;/*size 8*/struct fatitemint item; /存放文件下一个磁盘的指针char em_disk; /磁盘块是否空闲标志位0 空闲;struct opentablestruct openttableitemchar name9; /文件名int firstdisk; /起始盘块号int size; /文件的大小openitemMOFN;int cur_size; /当前打文件的数

6、目;struct fatitem *fat; /FAT表struct direct *root; /根目录struct direct *cur_dir; /当前目录struct opentable u_opentable; /文件打开表5.3方法函数void initfile();void format();void enter();void init();int create(char *name);int open(char *name);int close(char *name);int write(int fd, char *buf, int len);int read(int fd,

7、 char *buf);int del(char *name);int createdir(char *name);int removedir(char *name);void showdir();int cd(char *name);void print();void show();void login();5.4全局变量#define MEM_D_SIZE 1024*1024 /总磁盘空间为M#define DISKSIZE 1024/磁盘块的大小K#define DISK_NUM 1024/磁盘块数目K#define FATSIZE DISK_NUM*sizeof(struct fati

8、tem)/FAT表大小#define ROOT_DISK_NO FATSIZE/DISKSIZE+1/根目录起始盘块号#define ROOT_DISK_SIZE sizeof(struct direct)/根目录大小#define DIR_MAXSIZE 1024/路径最大长度为KB#define MSD 6/最大子目录数#define MOFN 4/最大文件深度为#define MAX_WRITE 1024*128/最大写入文字长度KB char *username = (char *)malloc(sizeof(char) * 100);char *password = (char *)

9、malloc(sizeof(char) * 100);六、软件测试6.1格式化磁盘空间测试6.2用户登录测试6.3创建子目录测试6.4进入子目录测试6.5创建文件测试6.6写入文件测试6.7读文件测试6.8返回上级目录测试6.9显示目录中项测试6.10读写权限测试七、总结本次课程设计我初步完成了虚拟文件系统的目录管理和文件管理。让我对于文件系统有了深层次的理解和掌握,通过自己编写程序逐步提高自己的编程能力,并从中体会到了很多乐趣和知识。同时让我对C语言中的指针有了一个更深的了解。由于以前对于C+知识没有掌握牢固,使我在编程中出现了很多错误。费了很多时间,但是我通过不断学习也提高了很多,对一些细

10、节的结构体等也有了一个更深的理解。这次课程设计让我进行了以前课堂很少有的实践训练,虽然掌握的知识有限,但是这次经历让我提高了编程能力和编程思想,使我受益匪浅。附录1参考文献1 谭浩强,C+程序设计(第2版)清华大学出版社,2012.2 汤小丹、梁红兵、哲凤屏,计算机操作系统西安电子科技大学出版社,2014. 3 严蔚敏数据结构清华大学出版社.,2007附录2源码/ kcsj001.cpp : Defines the entry point for the console application./#include "stdafx.h"#include<stdio.h&

11、gt; #include<string.h> #include<stdlib.h> #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)/根目录大小

12、#define DIR_MAXSIZE 1024/路径最大长度为KB#define MSD 6/最大子目录数#define MOFN 4/最大文件深度为#define MAX_WRITE 1024*128/最大写入文字长度KB char *username = (char *)malloc(sizeof(char) * 100);char *password = (char *)malloc(sizeof(char) * 100);struct direct/*文件控制快信息*/struct FCBchar name9; /文件/目录名8位char property; /属性1位目录0位普通文

13、件int size; /文件/目录字节数、盘块数)int firstdisk; /文件/目录起始盘块号int next; /子目录起始盘块号int sign; /1是根目录0不是根目录directitemMSD + 2;/*size 8*/struct fatitemint item; /存放文件下一个磁盘的指针char em_disk; /磁盘块是否空闲标志位0 空闲;struct opentablestruct openttableitemchar name9; /文件名int firstdisk; /起始盘块号int size; /文件的大小openitemMOFN;int cur_si

14、ze; /当前打文件的数目;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 *name);int open(char *name);

15、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 login();main()FILE *fp;char ch;char a100;char code1110;char name10;int i, flag, r_size;c

16、har *contect;contect = (char *)malloc(MAX_WRITE*sizeof(char);if (fp = fopen("disk.dat", "rb") = NULL)printf("您还没有格式化,是否格式化?(y/n)");scanf("%c", &ch);if (ch = 'y')initfile();printf("格式化成功! n");elsereturn 0;printf("您还未登录,请先登录! n");

17、GotoTest:login();if (strcmp(username, "readonly") != 0 | strcmp(password, "1234") != 0)&& (strcmp(username, "root") != 0 | strcmp(password, "root") != 0) && (strcmp(username, "nopower") != 0 | strcmp(password, "1234") != 0)p

18、rintf("登录失败,请重新登录! n");goto GotoTest;printf("登录成功! n");enter();print();show();strcpy(code0, "exit");strcpy(code1, "create");strcpy(code2, "open");strcpy(code3, "close");strcpy(code4, "write");strcpy(code5, "read");strcpy

19、(code6, "del");strcpy(code7, "createdir");strcpy(code8, "removedir");strcpy(code9, "showdir");strcpy(code10, "cd");while (1)scanf("%s", a);for (i = 0; i<11; i+)if (!strcmp(codei, a)break;switch (i)case 0: /退出文件系统free(contect);halt();retu

20、rn 0;case 1: /创建文件scanf("%s", name);flag = create(name);if (flag = -1)printf("Error: n 长度太长 !n");else if (flag = -2)printf("Error: n 子目录已满 !n");else if (flag = -3)printf("Error: n 打开文件次数过多 !n");else if (flag = -4)printf("Error: n 名字已经在子目录中 !n");else

21、if (flag = -5)printf("Error: n 磁盘空间已满!n");elseprintf("创建文件成功! n");show();break;case 2:/打开文件scanf("%s", name);fd = open(name);if (fd = -1)printf("Error: n 打开的文件不存在! n");else if (fd = -2)printf("Error: n 文件已经打开! n");else if (fd = -3)printf("Error:

22、 n 打开文件次数过多! n");else if (fd = -4)printf("Error: n 这是一个子目录,不能打开进行读写! n");elseprintf("打开成功! n");show();break;case 3:/关闭文件scanf("%s", name);flag = close(name);if (flag = -1)printf("Error:n 文件没有打开 ! n");elseprintf("关闭成功! n");show();break;case 4:/写文

23、件if (fd = -1)printf("Error:n文件没有打开 ! n");elseif (strcmp(username, "readonly") != 0 && strcmp(username, "nopower") != 0)printf("请输入文件内容:");scanf("%s", contect);flag = write(fd, contect, strlen(contect);if (flag = 0)printf("写入成功! n");

24、elseprintf("Error:n 磁盘大小没满! n");elseprintf("您没有写入权限!n");show();break;case 5:/读文件if (fd = -1)printf("Error:n 文件没有打开 ! n");elseif (strcmp(username, "nopower") != 0)flag = read(fd, contect);if (flag = 0)for (i = 0; i<u_opentable.openitemfd.size; i+)printf(&quo

25、t;%c", contecti);printf("tn");elseprintf("您没有读取权限!n");show();break;case 6:/删除文件scanf("%s", name);flag = del(name);if (flag = -1)printf("Error:n 文件不存在! n");else if (flag = -2)printf("Error:n 文件已经打开,请先关闭它 ! n");else if (flag = -3)printf("Erro

26、r:n 删除的不是文件 ! n");elseprintf("删除成功! n");show();break;case 7:/创建子目录scanf("%s", name);flag = mkdir(name);if (flag = -1)printf("Error:n 名称长度太长! n");else if (flag = -2)printf("Error:n 子目录已满 ! n");else if (flag = -3)printf("Error:n 名称已在子目录中 ! n");els

27、e if (flag = -4)printf("Error: n '.' 或 '.' 不能作为子目录名称!n");else if (flag = -5)printf("Error: n 磁盘空间已满!n");else if (flag = 0)printf("创建子目录成功! n");show();break;case 8:/删除子目录scanf("%s", name);flag = rmdir(name);if (flag = -1)printf("Error:n 子目录

28、不存在! n");else if (flag = -2)printf("Error:n子目录中含有子目录,请删除子目录中的子目录!n");else if (flag = -3)printf("Error:n 删除的不是子目录 ! n");else if (flag = 0)printf("删除子目录成功! n");show();break;case 9:/显示当前子目录dir();show();break;case 10:/更改当前目录scanf("%s", name);flag = cd(name);i

29、f (flag = -1)printf("Error:n 路径不正确!n");else if (flag = -2)printf("Error:n打开的不是子目录!n");show();break;default:printf("n Error!n 命令错误! n");show();void login()printf("请输入用户名:n");scanf("%s", username);printf("请输入密码:n");scanf("%s", passw

30、ord);void format()int i;FILE *fp;fat = (struct fatitem *)(fdisk + DISKSIZE); /计算FAT表地址,引导区向后偏移1k/*初始化FAT表*/fat0.item = -1; /引导块fat0.em_disk = '1'for (i = 1; i<ROOT_DISK_NO - 1; i+) /存放FAT表的磁盘块号fati.item = i + 1;fati.em_disk = '1'fatROOT_DISK_NO.item = -1; /存放根目录的磁盘块号fatROOT_DISK_N

31、O.em_disk = '1'for (i = ROOT_DISK_NO + 1; i<DISK_NUM; i+)fati.item = -1;fati.em_disk = '0'root = (struct direct *)(fdisk + DISKSIZE + FATSIZE); /根目录的地址/*初始化目录*/指向当前目录的目录项root->directitem0.sign = 1;root->directitem0.firstdisk = ROOT_DISK_NO;strcpy(root->, &

32、quot;.");root->directitem0.next = root->directitem0.firstdisk;root->perty = '1'root->directitem0.size = ROOT_DISK_SIZE;/指向上一级目录的目录项root->directitem1.sign = 1;root->directitem1.firstdisk = ROOT_DISK_NO;strcpy(root->, ".");root

33、->directitem1.next = root->directitem0.firstdisk;root->perty = '1'root->directitem1.size = ROOT_DISK_SIZE;if (fp = fopen("disk.dat", "wb") = NULL)printf("Error:n 不能打开文件 n");return;for (i = 2; i<MSD + 2; i+) /子目录初始化为空root->directi

34、temi.sign = 0;root->directitemi.firstdisk = -1;strcpy(root->, "");root->directitemi.next = -1;root->perty = '0'root->directitemi.size = 0;if (fp = fopen("disk.dat", "wb") = NULL)printf("Error:n 不能打开文件 n");r

35、eturn;if (fwrite(fdisk, MEM_D_SIZE, 1, fp) != 1) /把虚拟磁盘空间保存到磁盘文件中printf("Error:n 文件写入出错! n");fclose(fp);void initfile()fdisk = (char *)malloc(MEM_D_SIZE*sizeof(char); /申请1M空间format();printf("install.n");void enter()FILE *fp;int i;fdisk = (char *)malloc(MEM_D_SIZE*sizeof(char); /申

36、请1M空间if (fp = fopen("disk.dat", "rb") = NULL)printf("Error:n不能打开文件n");return;if (!fread(fdisk, MEM_D_SIZE, 1, fp) /把磁盘文件disk.dat 读入虚拟磁盘空间(内存)printf("Error:n不能读取文件n");exit(0);fat = (struct fatitem *)(fdisk + DISKSIZE); /找到FAT表地址root = (struct direct *)(fdisk +

37、DISKSIZE + FATSIZE);/找到根目录地址fclose(fp);/*初始化用户打开表*/for (i = 0; i<MOFN; i+)strcpy(u_, "");u_opentable.openitemi.firstdisk = -1;u_opentable.openitemi.size = 0;u_opentable.cur_size = 0;cur_dir = root; /当前目录为根目录bufferdir = (char *)malloc(DIR_MAXSIZE*sizeof(char);strc

38、py(bufferdir, "C:Usersbenchao");void halt()FILE *fp;int i;if (fp = fopen("disk.dat", "wb") = NULL)printf("Error:n不能打开文件n");return;if (!fwrite(fdisk, MEM_D_SIZE, 1, fp) /把虚拟磁盘空间(内存)内容读入磁盘文件disk.datprintf("Error:n文件写入出错!n");fclose(fp);free(fdisk);free(

39、bufferdir);return;int create(char *name)int i, j;if (strlen(name)>8) /文件名大于8位return(-1);for (j = 2; j<MSD + 2; j+) /检查创建文件是否与已存在的文件重名if (!strcmp(cur_dir->, name)break;if (j<MSD + 2) /文件已经存在return(-4);for (i = 2; i<MSD + 2; i+) /找到第一个空闲子目录if (cur_dir->directitemi.fir

40、stdisk = -1)break;if (i >= MSD + 2) /无空目录项return(-2);if (u_opentable.cur_size >= MOFN) /打开文件太多return(-3);for (j = ROOT_DISK_NO + 1; j<DISK_NUM; j+) /找到空闲盘块j 后退出if (fatj.em_disk = '0')break;if (j >= DISK_NUM)return(-5);fatj.em_disk = '1' /将空闲块置为已经分配/*填写目录项*/strcpy(cur_dir-

41、>, name);cur_dir->directitemi.firstdisk = j;cur_dir->directitemi.size = 0;cur_dir->directitemi.next = j;cur_dir->perty = '0'fd = open(name);return 0;int open(char *name)int i, j;for (i = 2; i<MSD + 2; i+) /文件是否存在if (!strcmp(cur_dir->directi

42、, name)break;if (i >= MSD + 2)return(-1);/是文件还是目录if (cur_dir->perty = '1')return(-4);/文件是否打开for (j = 0; j<MOFN; j+)if (!strcmp(u_, name)break;if (j<MOFN) /文件已经打开return(-2);if (u_opentable.cur_size >= MOFN) /*文件打开太多*/return(-3);/查

43、找一个空闲用户打开表项for (j = 0; j<MOFN; j+)if (u_opentable.openitemj.firstdisk = -1)break;/填写表项的相关信息u_opentable.openitemj.firstdisk = cur_dir->directitemi.firstdisk;strcpy(u_, name);u_opentable.openitemj.size = cur_dir->directitemi.size;u_opentable.cur_size+;/返回用户打开表表项的序号retu

44、rn(j);int close(char *name)int i;for (i = 0; i<MOFN; i+)if (!strcmp(u_, name)break;if (i >= MOFN)return(-1);/清空该文件的用户打开表项的内容strcpy(u_, "");u_opentable.openitemi.firstdisk = -1;u_opentable.openitemi.size = 0;u_opentable.cur_size-;return

45、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; i<len; i+)if (bufi = '$')bufi = Space;else if (bufi = '#')bufi = Endter;/取用户打开表对应表项第一个盘块号item = u_opentable.o

46、penitemfd.firstdisk;/找到当前目录所对应表项的序号for (i = 2; i<MSD + 2; i+)if (cur_dir->directitemi.firstdisk = item)break;temp = i; /存放当前目录项的下标/找到的item 是该文件的最后一块磁盘块while (fatitem.item != -1)item = fatitem.item; /查找该文件的下一盘块/计算出该文件的最末地址first = fdisk + item*DISKSIZE + u_opentable.openitemfd.size%DISKSIZE;/如果最

47、后磁盘块剩余的大小大于要写入的文件的大小if (DISKSIZE - u_opentable.openitemfd.size%DISKSIZE>len)strcpy(first, buf);u_opentable.openitemfd.size = u_opentable.openitemfd.size + len;cur_dir->directitemtemp.size = cur_dir->directitemtemp.size + len;elsefor (i = 0; i<(DISKSIZE - u_opentable.openitemfd.size%DISKS

48、IZE); i+)/写一部分内容到最后一块磁盘块的剩余空间(字节)firsti = bufi;/计算分配完最后一块磁盘的剩余空间(字节) 还剩下多少字节未存储ilen1 = len - (DISKSIZE - u_opentable.openitemfd.size%DISKSIZE);ilen2 = ilen1 / DISKSIZE;modlen = ilen1%DISKSIZE;if (modlen>0)ilen2 = ilen2 + 1; /还需要多少块磁盘块for (j = 0; j<ilen2; j+)for (i = ROOT_DISK_NO + 1; i<DISK

49、_NUM; i+)/寻找空闲磁盘块if (fati.em_disk = '0')break;if (i >= DISK_NUM) /如果磁盘块已经分配完了return(-1);first = fdisk + i*DISKSIZE; /找到的那块空闲磁盘块的起始地址if (j = ilen2 - 1) /如果是最后要分配的一块for (k = 0; k<len - (DISKSIZE - u_opentable.openitemfd.size%DISKSIZE) - j*DISKSIZE; k+)firstk = bufk;else/如果不是要最后分配的一块for (

50、k = 0; k<DISKSIZE; k+)firstk = bufk;fatitem.item = i; /找到一块后将它的序号存放在上一块的指针中fati.em_disk = '1' /置找到的磁盘快的空闲标志位为已分配fati.item = -1; /它的指针为-1 (即没有下一块)/修改长度u_opentable.openitemfd.size = u_opentable.openitemfd.size + len;cur_dir->directitemtemp.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%DISKSIZE;if (modlen != 0)ilen1

温馨提示

  • 1. 本站所有资源如无特殊说明,都需要本地电脑安装OFFICE2007和PDF阅读器。图纸软件为CAD,CAXA,PROE,UG,SolidWorks等.压缩文件请下载最新的WinRAR软件解压。
  • 2. 本站的文档不包含任何第三方提供的附件图纸等,如果需要附件,请联系上传者。文件的所有权益归上传用户所有。
  • 3. 本站RAR压缩包中若带图纸,网页内容里面会有图纸预览,若没有图纸预览就没有图纸。
  • 4. 未经权益所有人同意不得将文件中的内容挪作商业或盈利用途。
  • 5. 人人文库网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对用户上传分享的文档内容本身不做任何修改或编辑,并不能对任何下载内容负责。
  • 6. 下载文件中如有侵权或不适当内容,请与我们联系,我们立即纠正。
  • 7. 本站不保证下载资源的准确性、安全性和完整性, 同时也不承担用户因使用这些下载资源对自己和他人造成任何形式的伤害或损失。

评论

0/150

提交评论