《操作系统课程设计实验报告.pdf》由会员分享,可在线阅读,更多相关《操作系统课程设计实验报告.pdf(17页珍藏版)》请在淘文阁 - 分享文档赚钱的网站上搜索。
1、西安郵電西安郵電大大學學操作系统课程设计报 告 书院 系 名 称院 系 名 称 :计算机学院学 生 姓 名学 生 姓 名 :专 业 名 称专 业 名 称 :班班级级 :学号学号 :时间时间 :1实验目的操作系统是控制和管理计算机硬件和软件资源的虚拟机, 其中的文件系统是对软件和设备进行管理的系统,文件系统是操作系统中非常重要的一个模块,它的实现占用了操作系统源码的最大编码量, 其好坏也直接影响着用户对操作系统的感受程度。通过对操作系统课程设计的实践,进一步加深对文件系统的认识和理解, 并在此基础上培养学生的工程应用能力。实验分别从用户态和内核态两个层次实践文件系统的部分功能。2实验任务2.12
2、.1 lsls 实现实现在 linux 下编程实现带参数的 shell 命令 ls,ls 命令必须支持如下功能。1.基本要求(1) 支持 -l 参数;(2) 输出结果按字典排序;(3) 列出“.”文件,支持-a 参数,在没有-a 时候不显示隐藏文件;(4) 显示记录总数。2.高级要求(1) 支持对给定的目录进行操作,如 ls /tmp;(2) 输出结果分栏排序,每栏的宽度由这一栏最长的文件名决定,显示的栏数还受终端显示器的宽度影响,每一列尽可能的等宽;(3) 正确显示文件特殊属性 suid、sgid 和 sticky,参见联机帮助确保程序能处理各种情况;(4) 支持标准的 ls 支持选项-R,
3、它的功能是递归地列出目录中所有的文件包含子目录中的文件;(5) 支持标准的 ls 支持选项-u,它会显示出文件的最后访问时间,如果用了-u 而不用-l,会有什么结果?;(6) 当关掉一个文件的读权限,就不能打开这个文件来读。如果从一个终端登录,打开一个文件,保持文件的打开状态,然后从另外的终端登录,去掉文件的读权限,这时有什么事情会发生?编写一个程序,先用 open()打开一个文件,用 read()读一些内容,调用 sleep()等待 20s 以后,再读一些内容,从另外的终端,再等待的 20s 内去掉文件的读权限,这样会有什么结果?。2.22.2 编写内核模块显示目录或文件的信息。编写内核模块
4、显示目录或文件的信息。(1) 使用内核模块编程;(2) 调试Linux 操作系统原理与应用第 8 章文件系统 P215 的例子;(3)练 习 给 内 核 模 块 传 入 参 数 , 参 考 关 于 带 参 数 的 模 块 编 程http:/ 给内核模块传入参数 path,其中 path 为绝对路径;1) 当 path 为目录时,显示目录对应的 dentrey 结构中的相关信息(可打印的信息);2) 当 path 为文件时,显示文件对应的 indoe 结构中的相关信息(可打印的信息);3) 当路径错误时,有错误提示信息。3开发环境开发环境如下表 2.3-1:设备名称设备名称设备类型设备类型配置类
5、配置类型型参数参数PC-201309291634Pc 机硬件配置内存:4G。64 位操作系统软件配置Ubuntu 虚拟机其 他 配置无表 2.3-14 测试环境设备名称设备名称设备类型设备类型配置类配置类型型参数参数PC-201309291634Pc 机硬件配置内存:4G。64 位操作系统软件配置Ubuntu 虚拟机其 他 配置无5 总体设计5.1 功能组织图Ls 命令的功能组织图如下图 5.1-1:Ls 命令运行Ls命令Ls-l命令显示文件特殊属性修改文件权限Ls-a命令Ls指定目录Ls-u命令从一个终端登录,打开一个文件,保持文件的打开状态,然后从另外的终端登录,去掉文件的读权限输出结果按
6、字典排序,输出结果分栏排序,每栏的宽度由这一栏最长的文件名决定,显示的栏数还受终端显示器的宽度影响,每一列尽可能的等宽打印内核信息的功能组织图如下图 5.1-2:内核模块传入参数的功能组织图如下图 5.1-3:开始运行Sb_block 加锁遍历 super_block打印文件系统所在主设备号和次设备号打印文件系统名称遍历超级块中节点号打印超级块中节点号给内核传入参数当path为 目 录时, 显示目 录 对应的dentrey结 构 中的 相 关信息当path为 文 件时, 显示文 件 对应的indoe 结构 中 的相 关 信息当路 径 错误时, 有错 误 提示信息5.2 原理linux 解释:L
7、inux 是一套免费使用和自由传播的类 Unix 操作系统,是一个基于 POSIX 和 UNIX 的多用户、多任务、支持多线程和多 CPU 的操作系统。它能运行主要的 UNIX 工具软件、应用程序和网络协议。它支持 32 位和 64 位硬件。Linux 继承了 Unix 以网络为核心的设计思想,是一个性能稳定的多用户网络操作系统linux 下 c 编程与 windows 下 c 编程的区别:C 标准都是一样的,但是不同的操作系统下有不同的系统 API 调用,也有不同的编译器!如果只是做简单的练习,不需要调用系统函数的话,是完全一样的,但是在 WINDOWS 下编译生成的可执行文件在 LINUX
8、 下是运行不起来的, 要在 LINUX 下运行必须用 LINUX 下的编译器,比如 GCC,这种编译器可以找到 WINDOWS 版本的,但是编译出来的就在WINDOWS 下运行不了!简单说就是不同操作系统下的可执行文件是不能通用的,因为不同的操作系统有不同的进程结构.文件系统原理:opendir 函数的参数为一个绝对路径或者相对路径,返回值为结构体 dirent 类型的数值或者空值。 结构体 dirent 中包含 d_name 选项,d_name中是文件名称。 Stat函数参数1是文件的绝对路径, 参数 2是struct stat结构体的一个参数,ststat(,&info);返回目录的相关信
9、息,st_mode 文件类型 st_uid 用户(id)st_gid 组(id),st_size 文件大小 st_nlike 文件连接数,st_mtime 文件最后修改时间 st_atime 最后访问时间,st_ctime 文件属性最后改变时间。在有如下定义:#define S_IFMT 0170000 记录文件的类型#define S_IFREG0100000 regular#define S_IFDIR 0040000directory #define S_IBLK 0060000 特殊块#define S_IFCHR 0020000 字符块 #define S_IFIFO 0010000
10、 fifo#define S_IFLNK 0120000 文件连接数 #define S_IFSOCK 0140000 通道if(S_ISDIR(mode) str0 = d;是设备 if(S_ISCHR(mode) str0 = c;字符设备 if(S_ISDIR(mode) str0 = b;块设备 if(S_IRUSR & mode) str1= r;可读 if(S_IWUSR & mode) str2 = w;可写 if(S_IXUSR &mode)str3 = x;可执行 if(S_IRGRP & mode) str4 = r;可读 if(S_IWGRP &mode) str5 =
11、w;可写 if(S_IXGRP & mode) str6 = x; 可执行if(S_IROTH & mode) str7 = r;可读if(S_IWOTH & mode)str8 =w;可写 if(S_IXOTH & mode) str9 = x;可执行。Struct passwd 结构体中 pw_name 用户名,pw_passwd 用户密码,pw_uid 用户 id,pw_gid 组 id,pw_gecos 真是名称 pw_dir 用户目录 pw_shell shell 命令。6 详细设计6.1.1 模块一 ls 命令实现1.功能ls -l:每个文件单独占一行,显示文件的详细属性信息ls
12、-a:显示包括隐藏文件在内的所有文件ls -u:显示出文件的最后访问时间ls:显示的文件名按字典顺序排序ls /指定目录:显示当前目录下的内容ls -lu:每个文件单独占一行,显示文件的详细属性信息,并且显示出文件的最后访问时间ls -la:显示包括隐藏文件在内的所有文件的详细属性信息ls -lua:显示包括隐藏文件在内的所有文件的详细属性信息,并且显示出文件的最后访问时间chmod 权限 文件名: 修改文件的权限, 并且显示出此文件是否受 suid, sgid和 sticky 的控制chmod 权限(3 位) 在一终端运行程序,读取文件信息,在另一终端修改文件权限,看结果。6.1.2 模块一
13、 ls 命令实现编写内核模块, 打印 super_block 结构中一些域的值。 (课本上的例子)遍历系统中的超级块:list_head 结构类型的字段名称为 s_list。list_entry 宏通过指向 list_head 节点的地址来得到外部超级块的首地址。 获取系统中个超级块的地址, 获得某个子进程的地址, 打印文件系统所在的主设备号和次设备号和文件系统名。 遍历打印每个超级块中的所有索引节点号,打印索引结点。给内核模块传入参数 path,其中 path 为绝对路径path=路径时,显示如下信息:1.哈希表2.目录项名3.短目录名4.目录项标志5.目录项长度6.目录项计数器的引用pat
14、h=文件时,显示如下信息:1.版本号2.用户组 ID3.用户 ID4.硬链接数5.引用记数6.文件大小7.文件的块数8.文件类型和权限9.索引节点的状态10.以位为单位的块大小11.文件索引节点的数量12.指定文件系统的读写访问标志2.算法/流程图实现 ls 命令功能流程图如下:ls 命令输入参数lsls-als-lls-uls-rLs指定目录修改文件权限输出结果按字典排序输出当前目录文件,下级目录输出当前目录所有文件目录输出当前目录,详细信息输出当前目录,及下级目录显示文件的最后访问时间输出指定目录从一个终端登录, 打开一个文件, 保持文件的打开状态, 然后从另外的终端登录, 去掉文件的读权
15、限Ls 命令结束内核模块:打印 super_block 结构中的一些域的值。否是给内核模块传入参数 path 流程图,其中 path 为绝对路径;当 path 为目录时,显示目录对应的 dentrey 结构中的相关信息;当 path 为文件时,显示文件对应的 indoe 结构中的相关信息;当路径错误时,有错误提示信息。开始加锁遍历节点打印文件系统所在设备的主设备号和次设备号打印文件系统名遍历,打印索引节点号结束尾节点否是否是开始输 入 的是目录打印 dentrey 结构体信息输 入 的是目录错误打印 dentrey 结构体信息打印错误信息结束3.运行结果(一)lsls -l(1):ls -l以
16、长格式的形式查看当前目录下所有文件ls -a(2):ls -a 将隐藏文件显示出来,并按照字典进行排序ls -R(3):ls -R 递归地列出目录中所有的文件包含子目录中的文件ls -u(4):ls -u 根据文件最后显示时间列出对给定目录进行操作:1)如./ls /tmp(5)2)对绝对路径目录进行操作:./ls /home/weiyue/linux(6)3)对相对路径目录进行操作:./ls ./linux(7)读权限:1)先显示正常情况下:(8)2)再执行一次,然后在另外一个终端里修改文件的权限:chmod 000 abc.txt(9)然后观察结果:再执行一次,观察结果:(11)(二)内核
17、测试结果:1)调试 P215,观察数据结构中的数据:(12)进行内核操作时要在 root 权限下2)给内核模块传入参数 path,其中 path 为绝对路径:1.当 path 为目录时,显示目录对应的 dentrey 结构中的相关信息(可打印的信息);2.当 path 为文件时,显示文件对应的 indoe 结构中的相关信息(可打印的信息);3.当路径错误时,有错误提示信息4.模块使用的主要函数、数据类型和宏(1)主要函数说明1)函数 do_ls();原型;void do_ls(char dirname,int choose,int abcd)功能:输出当前目录,或者指定目录(默认当前目录)的所
18、有文件的信息,结果按字典排序。先按文件名称长度排序,相等长度的名称的按字典排序,无论中文名称的长度是多少,统一排在最后一个英文名称的文件后面,中文名称的文件名称按长度排序,相等长度的按字典排序。参数:char dirname,含有文件名称的字符串,abcd,选项选择输出详细信息或不输出相信信息返回值:void2)函数 do_ls();原型:void do_ls(char *);功能:根据参数进行 ls 命令功能实现返回值:void3)函数 file_info();原型:void file_info( char *filename, struct stat *info_p )功能:输出文件的信息
19、:分配给文件的超级块的节点号,访问控制权限引用计数,硬链接数使用者 ID,使用者组 ID,版本号,以字节为单位的文件大小,文件块数,状态标志返回值:void4)函数 qsort();原型;qsort(filename,i,sizeof(filename0),cmp);功能:根据 cmp 函数比较 filename 中所有名称,返回有序的名称数组。参数:filename 名称数组,i 数组的个数,sizeof(filename0),数组单元的大小,cmp 用于比较函数的的函数。返回值:void7 测试方法与测试结果7.1 测试方法以及测试结果单元测试:测试项目测试结果局部数据结构测试出错处理通路
20、测试边界条件模块接口测试自己测试正常正常正常正常同学不知逻辑结构帮助测试操作错误正常正常正常集成测试:测试项目测试结果Ls 模块Ls-a 模块Ls-l 模块Ls-r 模块自己测试正常正常不正常正常同学帮助测试正常正常正常正常课程设计要求确认测试:基本要求测试:测试项目测试结果Ls 模块Ls-a 模块Ls-l 模块Ls-r 模块自己测试正常正常不正常正常同学帮助测试正常正常正常正常集成测试:测试项目测试结果Ls-rlLs-al 模块Ls-ar 模块Ls-lar 模块自己测试正常正常不正常不正常同学帮助测试正常正常不正常不正常8 调试情况,设计技巧及体会在本次为期两周的课设中,我们完成了通过自己编
21、码实现 ls 的功能,并且可以带部分参数(-l,-a,-R,-u),以及部分内核态的操作,可以给内核模块传入参数 path。设计过程中,要先对代码架构进行构思,然后用结构化分析方法进行分析,将 ls 命令系统清楚的划分为几个模块,再根据每个模块的功能编写代码。而且尽可能的将模块细分,最后在进行函数的调用。在函数的编写过程中,不仅用到了很多系统的结构体,还用到了函数之间的调用(包括递归调用)。只要将每个模块都认真做好,都会很很大的收获。之前已经学习 linux 的一些东西,但是我所学的知识最多也就是在做作业的时候才会用到,很少实现系统一级的代码,平时没有什么练习的机会,这次的课程设计通过自己构思,和同学讨论并且不断查阅资料来设计一项程序。这次设计,不仅巩固了我以前所学的知识,还让我对系统调用有了更深一步的了解,掌握了更多的技巧和技能。虽然两周的时间很短短, 但是收获却是满满的。 希望以后在学习过程中,多加练习,争取更大的进步。9 参考资料1 DANIEL P.BOVET&MARCO CESATI. 深入理解 LINUX 内核M. 陈莉君,张琼声,张宏伟,译.第三版. 北京:中国电力出版社,2007:825-831.2unix、linux 编程实战教程. BruceMolay 著,杨海源,黄海涛译北京:清华大学出版社,2011:293-399,596-608.源程序清单
限制150内