广工12届操作系统实验报告.docx

上传人:b****5 文档编号:8071091 上传时间:2023-01-28 格式:DOCX 页数:91 大小:582.10KB
下载 相关 举报
广工12届操作系统实验报告.docx_第1页
第1页 / 共91页
广工12届操作系统实验报告.docx_第2页
第2页 / 共91页
广工12届操作系统实验报告.docx_第3页
第3页 / 共91页
广工12届操作系统实验报告.docx_第4页
第4页 / 共91页
广工12届操作系统实验报告.docx_第5页
第5页 / 共91页
点击查看更多>>
下载资源
资源描述

广工12届操作系统实验报告.docx

《广工12届操作系统实验报告.docx》由会员分享,可在线阅读,更多相关《广工12届操作系统实验报告.docx(91页珍藏版)》请在冰豆网上搜索。

广工12届操作系统实验报告.docx

广工12届操作系统实验报告

 

操作系统实验报告

 

学生学院计算机学院

专业班级

学号

学生姓名

指导教师

 

2015年1月14日

1实验一进程调度单道…………………………………………………………1

2实验二作业调度单道批处理…………………………………………………16

3实验三可变式分区分配………………………………………………………26

4实验四文件系统………………………………………………………………71

1实验一进程调度

1、实验目的

用高级语言编写和调试一个进程调度程序,以加深对进程的概念及进程调度算法的理解。

2、实验内容及要求

设计一个有N个进程共行的进程调度程序。

进程调度算法:

采用多队列时间片轮转法。

每个进程有一个进程控制块(PCB)表示。

进程控制块可以包含如下信息:

进程名、优先数、到达时间、需要运行时间、已用CPU时间、进程状态等等。

进程需要的运行时间可以事先人为地指定(也可以由随机数产生)。

进程的到达时间为进程输入的时间。

进程的运行时间以时间片为单位进行计算。

每个进程的状态可以是就绪W(Wait)、运行R(Run)、或完成F(Finish)三种状态之一。

就绪进程获得CPU后都只能运行一个时间片。

用已占用CPU时间加1来表示。

每进行一次调度程序都打印一次运行进程、就绪队列、以及各个进程的PCB,以便进行检查。

重复以上过程,直到所要进程都完成为止。

3、实验设计方案及原理

程序一开始先从第一个队列读取进程,每个进程运行一个时间片后,如果还没有结束就排到下一个队列的队尾等待下一次运行,当第一个队列为空时,读取第二个队列的首进程,执行相同的过程,直到所有的队列都为空程序流程图

4、重要数据结构或源程序中疑难部分的说明,需附详细注释

#include"stdio.h"

#include

#include

#definegetpch(type)(type*)malloc(sizeof(type))

#defineNULL0

structpcb{/*定义进程控制块PCB*/

charname[10];

charstate;

intntime;

intrtime;

introw;

structpcb*link;

}*ready=NULL,*p,*q;

typedefstructpcbPCB;

inth=0;/*全局变量在running函数中记录进程执行次数*/

insert()

{

if(ready==NULL)

{

p->link=ready;

ready=p;

q=p;

}

else

{

p->link=q->link;

q->link=p;

q=p;

}

}

input()/*建立进程控制块函数*/

{

inti,num;

//clrscr();/*清屏*/

printf("\n请输入进程个数:

");

scanf("%d",&num);

for(i=0;i

{

printf("\n进程号No.%d:

\n",i+1);

p=getpch(PCB);

printf("\n输入进程名:

");

scanf("%s",p->name);

printf("\n输入进程运行时间:

");

scanf("%d",&p->ntime);

printf("\n");

p->rtime=0;p->state='w';p->row=1;

p->link=NULL;

insert();/*调用insert函数*/

}

}

 

disp(PCB*pr)/*建立进程显示函数,用于显示当前进程*/

{

printf("\nqname\tstate\tndtime\truntimerow\n");

printf("|%s\t",pr->name);

printf("|%c\t",pr->state);

printf("|%d\t",pr->ntime);

printf("|%d\t",pr->rtime);

printf("|%d\t",pr->row);

printf("\n");

}

check()/*建立进程查看函数*/

{

intj;

PCB*pr;

printf("\n****当前正在运行的进程是:

%s",p->name);/*显示当前运行进程*/

disp(p);

pr=ready;

printf("\n****当前就绪队列状态为:

\n");/*显示就绪队列状态*/

for(j=1;j<=3;j++)

{

printf("\n");

printf("*****************************************\n");

printf("第%d个队列",j);

while(pr!

=NULL&&pr->row==j)

{

disp(pr);

pr=pr->link;

}

printf("\n");

}

}

destroy()/*建立进程撤消函数(进程运行结束,撤消进程)*/

{

printf("\n进程[%s]已完成.\n",p->name);

free(p);

}

running()/*建立进程就绪函数(进程运行时间到,置就绪状态*/

{

inti,timepiece=1;

for(i=1;irow;i++)timepiece*=2;

for(i=1;i<=timepiece;i++)

{

h++;

printf("\nTheexecutenumber:

%d\n",h);

check();

(p->rtime)++;

if(p->rtime>=p->ntime)break;

getchar();

}

if(p->row==3)

{

if(p->rtime>=p->ntime)

destroy();/*调用destroy函数*/

else

{

p->state='w';

insert();/*调用insert函数*/

}

}

elseif(p->rtime>=p->ntime)

destroy();/*调用destroy函数*/

else

{

p->state='w';

p->row++;

insert();/*调用insert函数*/

}

}

main()/*主函数*/

{

charch;

input();

//ch=getchar();

while(ready!

=NULL)

{

p=ready;

ready=p->link;

p->link=NULL;

p->state='R';

running();

printf("\n按任一键继续......");

ch=getchar();

}

printf("\n\n进程已经完成.\n");

ch=getchar();

}

多队列轮转法代码说明:

本程序巧妙地只用了一个队列实现了多队列功能,实现方法是,先在进程控制块设置一个记录进程当前所在队列的变量row,取值范围是1~3,程序只设置了三个队列,而每个队列所运行的时间片用timepiece记录,第一队列为1,第二队列为(2×timepiece)第一队列的两倍。

5、程序运行结果

输入5个进程和进程信息

队列的初始状态

a进程运行一个时间片后进入第二个队列:

6、结果分析与实验小结

在设计实验的时候本来想参考实验册的做法,但是后来觉得直接用数组好像更加容易编,所以就这样写了,但是后来发现这样写有缺点,就是数组空间没有释放,以后有机会再想想别的方法。

实验二作业调度

1、实验目的FCFS

  本实验要求学生模拟作业调度的实现,用高级语言编写和调试一个或多个作业调度的模拟程序,了解作业调度在操作系统中的作用,以加深对作业调度算法的理解。

2、实验内容和要求

(1)、编写并调试一个单道处理系统的作业调度模拟程序。

  

(2)、作业调度算法:

分别采用先来先服务(FCFS),最短作业优先(SJF)的调度算法。

  (3)、由于单道批处理系统中,作业一投入运行后,它就占有计算机的一切资源直到作业完成为止,因此调度作业时不必考虑它所需要的资源是否得到满足,它占用的CPU时限等因素。

  (4)、每一个作业由一个作业控制块JCB表示,JCB可以包含如下信息:

作业名、提交时间、所需要的运行时间、所需资源、作业状态、链指针等等。

作业的状态可以是等待(Wait)、运行(Run)和完成(Finish)三种状态之一。

每个作业的最初状态总是等待W。

  (5)、对每种调度算法都要求要打印每个作业开始运行时刻、完成时刻、周转时间、带权周转时间,以及这组作业的平均周转时间以及带权平均周转时间,并比较各种算法的优缺点。

3、实验设计方案和原理

先确定进程个数,把进程的信息输入到结构体pcb中,然后使用冒泡排序按到达时间的大小对进程排序。

调用进程,每调用一次,该进程的需要的时间-1,当需要的时间为0时,判断该进程结束,并调用下一进程,如果下一进程不存在,则计算平均周转时间和带权平均周转时间,程序结束。

4、程序流程图

5、重要数据结构或源程序中疑难部分的说明,需附详细注释

#include

#include

structpcb

{

charname;//作业名

intntime;//需要时间

intatime;//到达时间

intstime;//开始运行时间

};

intmain()

{

intn,i,j;

inttime,t;

intnt[100];

time=0;

intftime[100],ttime[100];/*ftime完成时间ttime周转时间*/

floatdtime[100],attime,adtime;/*dtime带权周转时间,attime平均周转时间,adtime平均带权周转时间*/

structpcba[100],b;

printf("请输入作业数目:

");

scanf("%d",&n);

getchar();

for(i=1;i<=n;i++)

{

printf("作业%d's名字:

如ABC...\n",i);

scanf("%s",&a[i].name);

getchar();

printf("作业%d的到达时间:

",i);

scanf("%d",&a[i].atime);//输入作业的名字、到达时间和需要时间

getchar();

printf("作业%d的需要时间:

",i);

scanf("%d",&a[i].ntime);

getchar();

}

for(i=1;i<=n;i++)

{

for(j=1;j<=n;j++)

if(a[j].atime>a[j+1].atime)

{

b=a[j];

a[j]=a[j+1];//按到达时间大小冒泡排序

a[j+1]=b;

nt[i]=a[i].ntime;

}

}

for(i=1;i<=n;i++)

nt[i]=a[i].ntime;

for(i=1;i<=n;i++)

{

while(a[i].atime>time)

time++;

a[i].stime=time;

for(;a[i].ntime!

=0;)

{

printf("正在运行的作业是%c\n",a[i].name);

printf("名字\t需要的时间\t\n");//输出运行的作业

printf("%c\t%d\n",a[i].name,a[i].ntime);

a[i].ntime--;

time++;

printf("-------------------------------\n");

for(j=i+1;j<=n;j++)

{printf("waitingprocessis%c\n",a[j].name);//输出等待的作业

}

printf("-------------------------------\n\n");

getch();

}

if(a[i].ntime==0)

{

printf("作业%c已经完成.\n",a[i].name);

ftime[i]=time;

ttime[i]=time-a[i].atime;

dtime[i]=(float)ttime[i]/nt[i];

printf("作业%c的开始时间:

%d\n",a[i].name,a[i].stime);//作业完成时,打印开始时间、完成时间、周转时间和带权周转时间

printf("作业%c的完成时间:

%d\n",a[i].name,ftime[i]);

printf("作业%c的周转时间:

%d\n",a[i].name,ttime[i]);

printf("作业%c的带权周转时间:

%f\n",a[i].name,dtime[i]);

printf("***************************\n\n");

getch();

}

}

for(i=1;i<=n;i++)

{

attime=attime+ttime[i];

adtime=adtime+dtime[i];

}

attime=(float)attime/n;

adtime=(float)adtime/n;//最后计算平均周转时间和带权平均周转时间

printf("平均周转时间:

%f\n",attime);

printf("带权平均周转时间:

%f\n",adtime);

getch();

}

6、运行结果

输入:

运行:

SJF

1、实验目的  本实验要求学生模拟作业调度的实现,用高级语言编写和调试一个或多个作业调度的模拟程序,了解作业调度在操作系统中的作用,以加深对作业调度算法的理解。

2、实验内容和要求

(1)、编写并调试一个单道处理系统的作业调度模拟程序。

  

(2)、作业调度算法:

分别采用先来先服务(FCFS),最短作业优先(SJF)的调度算法。

  (3)、由于单道批处理系统中,作业一投入运行后,它就占有计算机的一切资源直到作业完成为止,因此调度作业时不必考虑它所需要的资源是否得到满足,它占用的CPU时限等因素。

  (4)、每一个作业由一个作业控制块JCB表示,JCB可以包含如下信息:

作业名、提交时间、所需要的运行时间、所需资源、作业状态、链指针等等。

作业的状态可以是等待(Wait)、运行(Run)和完成(Finish)三种状态之一。

每个作业的最初状态总是等待W。

  (5)、对每种调度算法都要求要打印每个作业开始运行时刻、完成时刻、周转时间、带权周转时间,以及这组作业的平均周转时间以及带权平均周转时间,并比较各种算法的优缺点。

3、实验设计方案和原理

先确定进程个数,把进程的信息输入到结构体pcb中,然后使用冒泡排序按需要的时间的大小对进程排序。

调用进程,每调用一次,该进程的需要的时间-1,当需要的时间为0时,判断该进程结束,并调用下一进程,如果下一进程不存在,则计算平均周转时间和带权平均周转时间,程序结束。

4、程序流程图:

N

Y

5、程序清单:

#include

#include

structpcb

{

charname;//作业名

intntime;//需要时间

intatime;//到达时间

intstime;//开始运行时间

};

intmain()

{

intn,i,j;

inttime,t;

intnt[100];

time=0;

intftime[100],ttime[100];//完成时间,周转时间

floatdtime[100],attime,adtime;//带权周转时间、平均周转时间、平均带权周转时间

structpcba[100],b;

printf("Pleaseinputthenumberofprocess:

");

scanf("%d",&n);

getchar();

for(i=1;i<=n;i++)

{

printf("Process%d'sname:

如ABC...\n",i);

scanf("%s",&a[i].name);

getchar();//输入作业的名字、到达时间和需要时间

printf("Process%d'sarrivaltime:

",i);

scanf("%d",&a[i].atime);

getchar();

printf("Process%d'sneedtime:

",i);

scanf("%d",&a[i].ntime);

getchar();

}

for(i=1;i<=n;i++)

{

for(j=1;j<=n;j++)

if(a[j].ntime>a[j+1].ntime)

{

b=a[j];

a[j]=a[j+1];//按需要时间大小冒泡排序

a[j+1]=b;

nt[i]=a[i].ntime;

}

}

for(i=1;i<=n;i++)

nt[i]=a[i].ntime;

for(i=1;i<=n;i++)

{

while(a[i].atime>time)

time++;

a[i].stime=time;

for(;a[i].ntime!

=0;)

{

printf("runningprocessis%c\n",a[i].name);

printf("name\tneedtime\t\n");//输出运行的作业

printf("%c\t%d\n",a[i].name,a[i].ntime);

a[i].ntime--;

time++;

printf("-------------------------------\n");

for(j=i+1;j<=n;j++)

{printf("waitingprocessis%c\n",a[j].name);

}//输出等待的作业

printf("-------------------------------\n\n");

getch();

}

if(a[i].ntime==0)

{

printf("process%chasfinished.\n",a[i].name);

ftime[i]=time;

ttime[i]=time-a[i].atime;

dtime[i]=(float)ttime[i]/nt[i];//作业完成时,打印开始时间、完成时间、周转时间和带权周转时间

printf("process%c'sstarttime:

%d\n",a[i].name,a[i].stime);

printf("process%c'sfinishtime:

%d\n",a[i].name,ftime[i]);

printf("process%c'scycletime:

%d\n",a[i].name,ttime[i]);

printf("process%c'sdaiquantime:

%f\n",a[i].name,dtime[i]);

printf("***************************\n\n");

getch();

}

}

for(i=1;i<=n;i++)

{

attime=attime+ttime[i];

adtime=adtime+dtime[i];

}

attime=(float)attime/n;

adtime=(float)adtime/n;//最后计算平均周转时间和带权平均周转时间

printf("平均周转时间:

%f\n",attime);

printf("带权平均周转时间:

%f\n",adtime);

getch();

}

6、运行结果:

输入:

运行:

7、实验小结

在设计实验的时候本来想参考实验册的做法,但是后来觉得直接用数组好像更加容易编,所以就这样写了,但是后来发现这样写有缺点,就是数组空间没有释放,以后有机会再想想别的方法。

SFJ的程序和这个大同小异。

实验三可变式分区分配

1、实验目的

熟悉主存的分配与回收。

理解在不同的存储管理方式下,如何实现主存空间的分配与回收。

掌握动态分区分配方式中的数据结构与分配算法及动态分区存储管理方式及其实现过程。

2、实验内容和要求

实验要求使用可变分区存储管理方式,分区分配中所用的数据结构采用空闲分区表和空闲分区链来进行,分区分配中所用的算法采用首次适应算法、最坏适应算法、最佳适应算法三种算法来实现主存的分配与回收。

同时,要求设计一个实用友好的用户界面,并显示分配与回收的过程。

3、实验设计方案和原理

《主存空间分配过程设计》

数据结构:

使用链指针把所有的空闲分区链成一条链,用指针实现分区分配和链接。

空闲分区链:

双向链非循环链

分区首地址:

记录空闲内存空间块首地址

分区大小:

记录空闲内存块大小

分区状态n:

空间空闲可用r:

空间不可用

分区前指针:

链接前一空闲内存块,首指针前一指针置空

分区后指针:

链接后一空闲内存块,尾指针后一指针置空

structsubarea{//分区块

charname[10];

intaddr;//分区首地址

intsize;//分区大小

charstate;//分区状态

structsubarea*pre;//空闲分区前一指针

structsubarea*next;//空闲分区后一指针

}*sub=NULL,*r,*s;//空闲分区队列指针sub,

typedefstructsubareaSUB;

当有进程要求分配XKB主存时,按照进程的需要量XKB,从链头开始找到第一个空闲区;

A,若空闲区小于XKB,则沿链找下一个空闲区;

B,若

展开阅读全文
相关资源
猜你喜欢
相关搜索

当前位置:首页 > 高中教育 > 高考

copyright@ 2008-2022 冰豆网网站版权所有

经营许可证编号:鄂ICP备2022015515号-1