操作系统试验报告3
三、实验要求 1、至少完成上述实验内容中的一个。 2、自行设定内存总空间,大小单位为 KB,分页管理需要设定每个页的大小。 3、随机设置当前内存分配状态。 4、自行设计作业队列,队列中至少要有 3 个作业,设定各个作业空间大小,大小要适
中。
5、输出结果要尽量详细清晰,如果输出内容比较多,可以考虑把输出结果保存到文件
深 圳 大 学 实 验 报 告
课程名称:
计算机操作系统
实验项目名称: 连续式与分页式主存管理的模拟实现
学院:
计算机与软件
专业:
软件工程
指导教师:
梁正平
报告人: 文 成
学号:
2011150259
班级:
2
实验时间:
2013-6-01
实验报告提交时间:
2013-6-04
教务部制
一、实验目的
模拟在连续分配与分页管理两种方式下,主存空间的分配与回收,帮助学生加深了 解存储器管理的工作过程。 注意,该实验为模拟实验,并不要求进行真正的内存分配与回收,主要是编写程序 模拟其中过程即可。
6、 作业撤销后,需要回收物理块,回收过程如下: a) b) c) 根据页表,修改块表中对应各个物理块的状态 修改空闲块数,记录回收后空白块总数。 撤销页表
7、每次作业装入或回收,都需要输出块表、页表的内容,发生变化的块号,以及空闲
块数。若块表太大,可以用二维表格的方式输出,或只输出发生变化的块号。
二、实验内容
连续式分配
1、 在连续分配方式下,设计一个动态分区分配与回收的内存管理程序。 2、 动态分区分配按作业需要的主存大小来分割分区。当要装入一个作业时,根据作业 需要的主存量查看是否有足够的空闲空间,若有,则按需要量分割一个分区分配给 该作业;若无,则作业不能装入。 3、 设置一张全局分区状态表说明当前内存分配状态,例如下所示:
} int process_num()//随机产生一个进程个数的函数 { int num; int A[10]={1,2,3,4,5,6,7,8,9,10}; srand((unsigned)time(NULL)); num=rand()%10; return A[num]; } char srand_name(int k)//随机产生一个进程的名字 { char A[26]={'A','B','C','D','E','F','G','H','I', 'J','K','L','M','N','O','P','Q','R','S','T','U','V','W','X','Y','Z'}; return A[k]; } void allocate(char PRS_NAME,float X_K) //采用最优分配算法为进程 PRS_NAME 分配 X_K 大小的空间 { int i,k; float ad; k=-1; for(i=0;i<m;i++) //寻找空间大于 X_K 的最小空闲区登记项 k if(Free_table[i].length>=X_K&&Free_table[i].flag==1) if(k==-1||Free_table[i].length<Free_table[k].length) k=i; if(k==-1)//未找到可用空闲分区,返回 { printf("无可用空闲区\n"); return; } //找到可用空闲区,开始分配: if(Free_table[k].length-X_K<=M_SIZE) { Free_table[k].flag=0; ad=Free_table[k].address; X_K=Free_table[k].length; } else { Free_table[k].length=Free_table[k].length-X_K; ad=Free_table[k].address+Free_table[k].length; }
分页式管理
1、 设计一个基本分页存储管理程序 2、 分页式存储器把主存分成大小相等的若干块,作业的信息也按块的大小分页,作业 装入主存时按页分散存放在主存的空闲块中。 3、 系统用一张块表记录物理块分配的情况,如下图所示,其中状态 0 表示未分配,1 表 示已分配。另外增加一个空闲块数,记录当前可用的物理块总数。 状态 第0块 第1块 第2块 第3块 第4块 1 1 0 1 0
struct { float address; float length; int flag; }Free_table[m]; float stand_length(int k)//随机产生一个分区大小的函数 { float st_length[20]; srand((unsigned)time(NULL));//srand()函数产生一个当前时间开始的随机种子 for (int i=0;i<20;i++) st_length[i]=float (rand()%1000); return st_length[k]; } float process_length(int k)//随机产生一个进程大小的函数 { float pt_length[20]; srand((unsigned)time(NULL));//srand()函数产生一个当前时间开始的随机种子 for (int i=0;i<20;i++) pt_length[i]= float (rand()%500); return pt_length[k];
0 5k 10k 14k 26k 32k
操作系统区 作业 1 作业 3 空闲区 作业 2 空闲区
640k
4、 设置一张空闲分区表描述当前空闲分区分布状况,可采用数组或链表来实现,链表 请参考课本 P108 的数据结构设计。数组可参考以下格式: 起 第一栏 第二栏 14 K 32 K 址 长 12 K 96 K 度 状 态
//寻找回收分区的空闲上下邻,上邻表目 k,下邻表目 j while(i<m&&(j==-1||k==-1)) { if(Free_table[i].flag==1) { if(Free_table[i].address+Free_table[i].length==S)k=i;//找到上邻 if(Free_table[i].address==S+L)j=i;//找到下邻 } i++; } if(k!=-1) if(j!=-1) // 上邻空闲区,下邻空闲区,三项合并 { Free_table[k].length=Free_table[j].length+Free_table[k].length+L; Free_table[j].flag=1; } else //上邻空闲区,下邻非空闲区,与上邻合并 Free_table[k].length=Free_table[k].length+L; else if(j!=-1) //上邻非空闲区,下邻为空闲区,与下邻合并 { Free_table[j].address=S; Free_table[j].length=Free_table[j].length+L; } else //上下邻均为非空闲区,回收区域直接填入 { //在空闲区表中寻找空栏目 t=0; while(Free_table[t].flag==1&&t<m) t++; if(t>=m)//空闲区表满,回收空间失败,将已分配表复原 { cout<<"内存空闲表没有空间,回收空间失败"<<endl; Used_Table[s].flag=j; return; } Free_table[t].address=S; Free_table[t].length=L; Free_table[t].flag=1; } return;
4、 需要为每个作业设置一张页表,记录页号与块号的对应关系。
页 0 1 2
号
块 72 56
号
168
5、 作业装入内存时,分配过程如下: a) 将空闲块数乘上每块空间,计算出可用空间总数,然后与作业需要空间比较, 若不能满足需要,提示不能装入。 b) 若能满足需要,为作业创建页表,在块表中寻找足够的空白块,将页号与块号 一一对应,并填入页表。同时修改块表中各个块的状态 c) 修改空闲块数,记录剩下空白块总数。
中,通过文件来查看。
6、程序代码要尽量加入注释,提高程序的清晰度与可读性。
ห้องสมุดไป่ตู้
7、在实验报告中,一方面可以对实验结果进行分析,一方面可以对两种分配方式进行
比较,分析它们的优劣。
四、实验步骤
//分页存储管理代码 #include <stdio.h> #include<iostream.h> #include<string.h> #include <stdlib.h> #include <time.h> #define n 11 //模拟实验中允许的最大进程数为 n #define m 11 //模拟实验中允许的最大分区个数为 m #define M_SIZE 2000 struct { float address; //分配给进程的起始地址 float length; //分配给进程的空闲区长度,单位为字节 int flag; //分配区表标志,用"0"已分配,用"1"表示未分配 }Used_Table[m]; //分配分区表