实验四 式虚拟存储管理中地址转换和式中断 FIFO LRU OPT C++版本
OS实验指导四——虚拟存储器管理

OS实验指导四——虚拟存储器管理————————————————————————————————作者:————————————————————————————————日期:2《操作系统》实验指导四开课实验室:A207、A209 2015/11/23 、2015/11/24实验类型设计实验项目(四)虚拟存储器管理实验实验学时 4一、实验目的设计一个请求页式存储管理方案,并编写模拟程序实现。
二、设备与环境1. 硬件设备:PC机一台2. 软件环境:安装Windows操作系统或者Linux操作系统,并安装相关的程序开发环境,如C \C++\Java 等编程语言环境。
三、实验要求1) 上机前认真复习页面置换算法,熟悉FIFO算法和LRU页面分配和置换算法的过程;2) 上机时独立编程、调试程序;3) 根据具体实验要求,完成好实验报告(包括实验的目的、内容、要求、源程序、实例运行结果截图)。
四、实验内容1、问题描述:设计程序模拟FIFO和LRU页面置换算法的工作过程。
假设内存中分配给每个进程的最小物理块数为m,在进程运行过程中要访问的页面个数为n,页面访问序列为P1, … ,Pn,分别利用不同的页面置换算法调度进程的页面访问序列,给出页面访问序列的置换过程,并计算每种算法缺页次数和缺页率。
2、程序具体要求如下:编写程序用来模拟虚拟页式存储管理中的页面置换要求:1)快表页面固定为4块2)从键盘输入N个页面号3)输出每次物理块中的页面号和缺页次数,缺页率4)实现算法选择3、程序流程图3、源程序参考:(1)FIFO 算法部分#include "stdio.h"#define n 12#define m 4void main(){int ym[n],i,j,q,mem[m]={0},table[m][n];char flag,f[n];printf("请输入页面访问序列\n ");for(i =0;i <n;i ++) scanf("%d ",&ym[i]);printf("\n ");for(i =0;i <n;i ++) //查页表,看是否缺页{输入页面取访问查是否是置缺页标按不同算调入所访否q=0;while((ym[i]!=mem[q])&&(q!=m)) q++;if(q==m) flag='*'; //缺页,则置标志flag为‘*’else flag='';if(flag=='*'){for(j=m-1;j>0;j--) //淘汰最先调入的页面调入当前访问的mem[j]=mem[j-1];mem[0]=ym[i];}for(j=0;j<m;j++)table[j][i]=mem[j];f[i]=flag;}printf("输出结果为下表(0代表为空,*代表有缺页):\n");for(i=0;i<m;i++){for(j=0;j<n;j++)printf("%3d",table[i][j]);printf("\n");}for(i=0;i<n;i++)printf("%3c",f[i]);}(2)LRU算法#include "stdio.h"#define n 12#define m 4void main(){int ym[n],i,j,q,mem[m]={0},table[m][n];char flag,f[n];printf("请输入页面访问序列\n");for(i=0;i<n;i++)scanf("%d",&ym[i]);printf("\n");for(i=0;i<n;i++) //查页表,看是否缺页{q=0;while((ym[i]!=mem[q])&&(q!=m)) q++;if(q==m) flag='*'; //缺页,则置标志flag为‘*’else flag=' ';for(j=q;j>0;j--)mem[j]=mem[j-1];mem[0]=ym[i];for(j=0;j<m;j++)table[j][i]=mem[j];f[i]=flag;}printf("输出结果为下表(0代表为空,*代表有缺页):\n");for(i=0;i<m;i++){for(j=0;j<n;j++)printf("%3d",table[i][j]);printf("\n");}for(i=0;i<n;i++)printf("%3c",f[i]);}4.测试用例:见第四章课后习题第26题(P159),(注意用比较的方式对程序的运行结果加以分析,比如令M=3或M=4时,结果各有什么不同。
操作系统存储器管理实验报告.doc

一目的与要求(1) 请求页式虚存管理是常用的虚拟存储管理方案之一。
(2) 通过请求页式虚存管理中对页面置换算法的模拟,加深理解虚拟存储技术的特点。
(3) 模拟页式虚拟存储管理中硬件的地址转换和缺页中断,并用先进先出调度算法(FIFO)处理缺页中断.二实验内容或题目(1)本实验要求使用C语言编程模拟一个拥有若干个虚页的进程在给定的若干个实页中运行、并在缺页中断发生时分别使用FIFO和LRU算法进行页面置换的情形。
(2)虚页的个数可以事先给定(例如10个),对这些虚页访问的页地址流(其长度可以事先给定,例如20次虚页访问)可以由程序随机产生,也可以事先保存在文件中。
(3)要求程序运行时屏幕能显示出置换过程中的状态信息并输出访问结束时的页面命中率。
(4)程序应允许通过为该进程分配不同的实页数,来比较两种置换算法的稳定性。
三实验步骤与源程序(1)实验步骤1、理解好相关实验说明。
2、根据实验说明,画出相应的程序流程图。
3、按照程序流程图,用C语言编程并实现。
(2)流程图如下:①虚页和实页结构在虚页结构中,pn代表虚页号,因为共10个虚页,所以pn的取值范围是0—9。
pfn代表实页号,当一虚页未装入实页时,此项值为-1;当该虚页已装入某一实页时,此项值为所装入的实页的实页号pfn。
time项在FIFO算法中不使用,在LRU中用来存放对该虚页的最近访问时间。
在实页结构中中,pn代表虚页号,表示pn所代表的虚页目前正放在此实页中。
pfn代表实页号,取值范围(0—n-1)由动态指派的实页数n所决定。
next是一个指向实页结构体的指针,用于多个实页以链表形式组织起来,关于实页链表的组织详见下面第4点。
②程序流程图如下:(3)源程序如下:#include<iostream.h>#define M 40int N;struct Pro{int num,time;};int Input(int m,Pro p[M]){cout<<"请输入实际页数:";do{cin>>m;if(m>M)cout<<"数目太多,请重试"<<endl;else break;}while(1);//cout<<"请输入各页面号:";for(int i=0;i<m;i++){cout<<"第"<<i<<"个页面号为:";cin>>p[i].num;p[i].time=0;}return m;}void print(Pro *page1)//打印当前的页面{Pro *page=new Pro[N];page=page1;for(int i=0;i<N;i++)cout<<page[i].num<<" ";cout<<endl;}int Search(int e,Pro *page1 ){Pro *page=new Pro[N];page=page1;for(int i=0;i<N;i++)if(e==page[i].num)return i; return -1;}int Max(Pro *page1){Pro *page=new Pro[N];page=page1;int e=page[0].time,i=0;while(i<N)//找出离现在时间最长的页面{if(e<page[i].time)e=page[i].time;i++;}for( i=0;i<N;i++)if(e==page[i].time)return i;return -1;}int Compfu(Pro *page1,int i,int t,Pro p[M]){Pro *page=new Pro[N];page=page1;int count=0;for(int j=i;j<M;j++){if(page[t].num==p[j].num )break;else count++;}return count;}int main(){cout<<"可用内存页面数:";cin>>N;Pro p[M];Pro *page=new Pro[N];char c;int m=0,t=0;float n=0;m=Input(m,p);do{for(int i=0;i<N;i++)//初试化页面基本情况{page[i].num=0;page[i].time=2-i;}i=0;cout<<"************************"<<endl;cout<<"*****f:FIFO页面置换*****"<<endl;cout<<"*****l:LRU页面置换******"<<endl;cout<<"*****o:OPT页面置换******"<<endl;cout<<"*****按其它键结束*******"<<endl;cout<<"************************"<<endl;cout<<"请选择操作类型(f,l,o):";cin>>c;if(c=='f')//FIFO页面置换{n=0;cout<<"页面置换情况: "<<endl;while(i<m){if(Search(p[i].num,page)>=0)i++;//找到相同的页面else{if(t==N)t=0;else{n++;//page[t].num=p[i].num;print(page);t++;}}}cout<<"缺页次数:"<<n<<" 缺页率:"<<n/m<<endl; }if(c=='l')//LRU页面置换{ n=0;cout<<"页面置换情况: "<<endl;while(i<m){int k;k=t=Search(p[i].num,page);if(t>=0)page[t].time=0;else{n++;t=Max(page);page[t].num=p[i].num;page[t].time=0;}if(t==0){page[t+1].time++;page[t+2].time++;}if(t==1){page[2].time++;page[0].time++;}if(t==2){page[1].time++;page[0].time++;}if(k==-1) print(page); i++;}cout<<"缺页次数:"<<n<<" 缺页率:"<<n/m<<endl;}if(c=='o')//OPT页面置换{n=0;while(i<m){if(Search(p[i].num,page)>=0)i++;else{int temp=0,cn;for(t=0;t<N;t++){if(temp<Compfu(page,i,t,p)){temp=Compfu(page,i,t,p); cn=t;}}page[cn]=p[i];n++;print(page);i++;}}cout<<"缺页次数:"<<n<<" 缺页率:"<<n/m<<endl; }}while(c=='f'||c=='l'||c=='o');return 0;});四测试数据与实验结果五结果分析与实验体会通过上机,我了解了许多关于操作系统的专业知识。
实验四 存储管理

存储管理1 实验目的:通过请求页式存储管理中页面置换算法模拟设计,了解虚拟存储技术的特点,掌握请求页式存储管理的页面置换算法。
2 实验内容:1)通过随机数产生一个指令序列,共320条指令;2)将指令序列变换为页面号;3)计算FIFO算法在分配不同内存块下的命中率。
(假设分配的内存块从4块至32块。
)<程序设计>设计一个虚拟存储区和内存工作区,使用FIFO算法计算访问命中率。
首先用Srand()和rand()函数定义和产生指令序列,然后将指令序列变换成相应的页面号,并针对FIFO算法计算相应的命中率。
命中率=1-缺页率相关定义如下:1.数据结构(1)页面类型结构pl_type中pn页号,pfn块号,counter为一个周期内访问页面次数,time为访问时间(2)页面控制结构中pfc[total_vp]定义用户进程虚页控制结构*freepf_head为空页面头的指针*busypf_head为忙页面头的指针*busypf_tail为忙页面尾的指针2.函数定义(1)void initialize():初始化函数,给每个相关的页面赋值(2)void FIFO():计算使用FIFO算法时的命中率3.变量定义(1)int a[total_instruction]:指令流数组(2)int page[total_instruction]:每条指令所属页号(3)int offset[total_instruction]:每页装入10条指令后取模运算页号偏移值(4)int total_pf:用户进程的内存块数(5)int diseffect:页面失效次数,即缺页次数[root@localhost ~]# cd wuxiaofeng[root@localhost wuxiaofeng]# pwd/root/wuxiaofeng[root@localhost wuxiaofeng]# cat >fifo.c#include <stdio.h>#include <stdlib.h>#include <sys/types.h>#include <unistd.h>#define TRUE 1#define FALSE 0#define INVALID -1#define NULL 0#define total_instruction 320 //指令流长#define total_vp 32 //虚页长#define clear_period 50 //清零周期typedef struct{ //定义页面类型int pn; //pn为页号int pfn; //pfn为块号int counter; //为一个周期内访问页面次数int time; //为访问时间}pl_type;pl_type pl[total_vp]; //页面结构数组struct pfc_struct{ //定义页面控制结构int pn,pfn;struct pfc_struct *next;};typedef struct pfc_struct pfc_type;pfc_type pfc[total_vp],*freepf_head,*busypf_head,*busypf_tail;[root@localhost wuxiaofeng]# cp www.c mmm.c//pfc[total_vp]定义用户进程虚页控制结构//*freepf_head为空内存块号的头指针//*busypf_head为忙内存块的头指针//*busypf_tail为忙内存块的尾指针int diseffect, a[total_instruction];int page[total_instruction], offset[total_instruction];//int a[total_instruction]:指令流数组//int page[total_instruction]:每条指令所属页号//int offset[total_instruction]:每页装入10条指令后取模运算页号偏移值//int diseffect:页面失效次数void initialize();void FIFO();main(){int S,i,j,temp;srand(getpid()*10); //由于每次运行时进程号不同,故可用来作为初始化[root@localhost wuxiaofeng]# cp www.c mmm.c随机数队列的“种子”S=(float)319*rand()/32767+1;for(i=0;i<total_instruction;i+=4) //产生指令队列{a[i]=S; //任选一指令访问点a[i+1]=a[i]+1; //顺序执行一条指令a[i+2]=(float)a[i]*rand()/RAND_MAX; //执行前地址指令m'a[i+3]=a[i+2]+1; //执行后地址指令S=(float)rand()*(318-a[i+2])/RAND_MAX+a[i+2]+2;}for(i=0;i<total_instruction;i++) //将指令序列变换成页地址流{page[i]=a[i]/10;offset[i]=a[i]%10;}for(i=4;i<=32;i++) //用户内存工作区从4个块到32个块{printf("%2d page frames",i);[root@localhost wuxiaofeng]# cp www.c mmm.cFIFO(i);printf("\n");}}void FIFO(total_pf)int total_pf; //用户进程的内存块数{int i,j;pfc_type *p,*t;initialize(total_pf); //初始化相关内存块控制用数据结构busypf_head=busypf_tail=NULL;for(i=0;i<total_instruction;i++){if(pl[page[i]].pfn==INVALID) //页面失效{diseffect+=1; // 失效次数if(freepf_head==NULL) //无空闲块{p=busypf_head->next;pl[busypf_head->pn].pfn=INVALID;freepf_head=busypf_head; //释放忙内存块队列中的第一个块freepf_head->next=NULL;busypf_head=p;[root@localhost wuxiaofeng]# cp www.c mmm.c}p=freepf_head->next; //按FIFO方式调新页面入内存块freepf_head->next=NULL;freepf_head->pn=page[i];pl[page[i]].pfn=freepf_head->pfn;if(busypf_tail==NULL)busypf_head=busypf_tail=freepf_head;else{busypf_tail->next=freepf_head;busypf_tail=freepf_head;}freepf_head=p;}}printf(" FIFO:%6.4f",1-(float)diseffect/320);}void initialize(total_pf) //初始化相关数据结构int total_pf; //用户进程的内存页面数{int i;diseffect=0;for(i=0;i<total_vp;i++){pl[i].pn=i;pl[i].pfn=INVALID; //置页面控制结构中的页号,页面为空pl[i].counter=0;pl[i].time=-1; //页面控制结构中的访问次数为0,时间为-1}for(i=1;i<total_pf;i++){pfc[i-1].next=&pfc[i];pfc[i-1].pfn=i-1; //建立pfc[i-1]和pfc[i]之间的连接}pfc[total_pf-1].next=NULL;pfc[total_pf-1].pfn=total_pf-1;freepf_head=&pfc[0]; //空页面队列的头指针为pfc[0]}[root@localhost wuxiaofeng]# lsa.out fifo.c[root@localhost wuxiaofeng]# /root/wuxiaofeng/a.out4 page frames FIFO:0.54065 page frames FIFO:0.56256 page frames FIFO:0.58137 page frames FIFO:0.59068 page frames FIFO:0.60629 page frames FIFO:0.612510 page frames FIFO:0.637511 page frames FIFO:0.656212 page frames FIFO:0.671913 page frames FIFO:0.681314 page frames FIFO:0.696915 page frames FIFO:0.715616 page frames FIFO:0.728117 page frames FIFO:0.750018 page frames FIFO:0.759419 page frames FIFO:0.771920 page frames FIFO:0.775021 page frames FIFO:0.781222 page frames FIFO:0.809423 page frames FIFO:0.843824 page frames FIFO:0.843825 page frames FIFO:0.843826 page frames FIFO:0.843827 page frames FIFO:0.850028 page frames FIFO:0.887529 page frames FIFO:0.893830 page frames FIFO:0.893831 page frames FIFO:0.893832 page frames FIFO:0.9000[root@localhost wuxiaofeng]#实验小结:通过本次实验,我收获很多。
模拟分页式存储管理中硬件的地址转换和产生缺页中断

实验三
课程名称:操作系统
课程类型:必修
实验项目名称:存储器管理
实验题目:模拟分页式存储管理中硬件的地址转换和产生缺页中断。
一、实验目的
在计算机系统中,为了提高主存利用率,往往把辅助存储器(如磁盘)作为主存储器的扩充,使多道运行的作业的全部逻辑地址空间总和可以超出主存的绝对地址空间。
用这种办法扩充的主存储器称为虚拟存储器。
通过本实验帮助同学理解在分页式存储管理中怎样实现虚拟存储器。
二、实验要求
模拟分页式存储管理中硬件的地址转换。
需要为作业建立页表,应说明哪些页已在主存,哪些页尚未装入主存。
作业执行时,指令中的逻辑地址指出了参加运算的操作存放的页号和单元号,硬件的地址转换机构按页号查页表,若该页对应标志为“1”,则表示该页已在主存,这时根据关系式“绝对地址=块号×块长+单元号”计算出欲访问的主存单元地址。
若产生缺页中断,引出操作系统来处理这个中断事件。
如果主存中已经没有空闲块,则可用FIFO 页面调度算法把该作业中最先进入主存的一页调出,存放到磁盘上,然后再把当前要访问的页装入该块。
调出和装入后都要修改页表页表中对应页的标志。
三、设计思想
1、物理设计
全局变量定义如下:
struct info//页表
{
int block;//物理页架号
int disk;//在磁盘上的物理块号
int flag; //内外标志
}pagelist[10];
int po;//队列标记
int t[4];
2、程序流程图
(见下图)
图1-1主程序的流程图
图1-2 init( )的流程图。
操作系统实验4-请求分页存储管理模拟实验

实验四请求分页存储管理模拟实验一:实验目得通过对页面、页表、地址转换与页面置换过程得模拟,加深对请求分页存储管理系统得原理与实现技术得理解.二:实验内容假设每个页面可以存放10条指令,分配给进程得存储块数为4。
用C语言或Pascal语言模拟一进程得执行过程。
设该进程共有320条指令,地址空间为32个页面,运行前所有页面均没有调入内存。
模拟运行时,如果所访问得指令已经在内存,则显示其物理地址,并转下一条指令;如果所访问得指令还未装入内存,则发生缺页,此时需要记录缺页产生次数,并将相应页面调入内存,如果4个内存块已满,则需要进行页面置换。
最后显示其物理地址,并转下一条指令。
在所有指令执行完毕后,显示进程运行过程中得缺页次数与缺页率.页面置换算法:分别采用OPT、FIFO、LRU三种算法。
进程中得指令访问次序按如下原则生成:50%得指令就是顺序执行得。
25%得指令就是均匀分布在低地址部分.25%得指令就是均匀分布在高地址部分.三:实验类别分页存储管理四:实验类型模拟实验五:主要仪器计算机六:结果OPT:LRU:FIFO:七:程序# i nclude 〈stdio 、h 〉# incl ude 〈stdlib 、h 〉# include 〈conio 、h># def ine blockn um 4//页面尺寸大小int m; //程序计数器,用来记录按次序执行得指令对应得页号s ta ti c in t num [320]; //用来存储320条指令typedef s truct BLOCK //声明一种新类型—-物理块类型{ﻩint pagenum; //页号ﻩint acces sed; //访问量,其值表示多久未被访问}BLOCK ;BLOCK bl ock [bl ocknum ]; //定义一大小为8得物理块数组void init () //程序初始化函数,对bl ock 初始化{for (int i=0;i <blo cknum;i++)block[i]、pagenum=—1;block[i]、accessed=0;ﻩm=0;}}int pageExist(int curpage)//查找物理块中页面就是否存在,寻找该页面curpage就是否在内存块block中,若在,返回块号{ﻩfor(int i=0;i<blocknum; i++)ﻩ{ﻩﻩif(block[i]、pagenum == curpage )ﻩﻩreturn i; //在内存块block中,返回块号ﻩ}return -1;}int findSpace()//查找就是否有空闲物理块,寻找空闲块block,返回其块号{for(int i=0;i<blocknum;i++)ﻩ{if(block[i]、pagenum==-1)ﻩreturn i;//找到了空闲得block,返回块号}ﻩreturn -1;}int findReplace()//查找应予置换得页面{ﻩint pos = 0;ﻩfor(int i=0;i〈blocknum;i++){if(block[i]、accessed 〉block[pos]、accessed)ﻩpos = i; //找到应该置换页面,返回BLOCK中位置ﻩ}return pos;}void display()//显示物理块中得页面号{ﻩﻩfor(int i=0; i〈blocknum; i++)ﻩ{ﻩif(block[i]、pagenum != -1)ﻩ{ﻩﻩprintf(” %02d ",block[i]、pagenum);ﻩﻩﻩprintf("%p |”,&block[i]、pagenum);ﻩﻩ}printf("\n");}void randam()//产生320条随机数,显示并存储到num[320]{int flag=0;printf(”请为一进程输入起始执行指令得序号(0~320):\n”);ﻩscanf("%d",&m);//用户决定得起始执行指令printf("******进程中指令访问次序如下:(由随机数产生)*******\n");for(int i=0;i〈320;i++){//进程中得320条指令访问次序得生成ﻩﻩnum[i]=m;//当前执行得指令数,ﻩﻩif(flag%2==0)ﻩm=++m%320;//顺序执行下一条指令ﻩﻩif(flag==1)ﻩﻩm=rand()%(m-1);//通过随机数,跳转到低地址部分[0,m—1]得一条指令处,设其序号为m1if(flag==3)ﻩﻩm=m+1+(rand()%(320-(m+1)));//通过随机数,跳转到高地址部分[m1+2,319]得一条指令处,设其序号为m2ﻩﻩflag=++flag%4;ﻩprintf(” %03d”,num[i]);//输出格式:3位数ﻩﻩif((i+1)%10==0)//控制换行,每个页面可以存放10条指令,共32个页面ﻩprintf(”\n”);}}void pagestring() //显示调用得页面序列,求出此进程按次序执行得各指令所在得页面号并显示输出{for(int i=0;i〈320;i++)ﻩ{printf(”%02d",num[i]/10);//输出格式:2位数if((i+1)%10==0)//控制换行,每个页面可以存放10条指令,共32个页面ﻩﻩprintf("\n”);}}void OPT() //最佳替换算法{ﻩint n=0;//记录缺页次数int exist,space,position;ﻩintcurpage;//当前指令得页面号ﻩfor(int i=0;i<320;i++)ﻩ{ﻩm=num[i];ﻩcurpage=m/10;ﻩﻩexist=pageExist(curpage);ﻩif(exist==-1)ﻩﻩ{ //当前指令得页面号不在物理块中space=findSpace();ﻩﻩif(space != -1)ﻩﻩ{//当前存在空闲得物理块ﻩﻩblock[space]、pagenum= curpage;//将此页面调入内存ﻩﻩﻩdisplay();//显示物理块中得页面号ﻩﻩn++;//缺页次数+1ﻩ}ﻩﻩelseﻩﻩ{ //当前不存在空闲得物理块,需要进行页面置换for(intk=0;k<blocknum;k++)ﻩﻩﻩﻩ{for(int j=i;j〈320;j++)ﻩ{//找到在最长(未来)时间内不再被访问得页面ﻩﻩﻩﻩif(block[k]、pagenum!= num[j]/10)ﻩﻩﻩ{ﻩﻩblock[k]、accessed = 1000;ﻩﻩﻩ} //将来不会被访问,设置为一个很大数ﻩﻩﻩelseﻩﻩﻩ{ //将来会被访问,访问量设为jﻩﻩﻩblock[k]、accessed = j;ﻩﻩﻩﻩﻩbreak;ﻩﻩﻩﻩ}ﻩﻩﻩ}ﻩ}ﻩposition = findReplace();//找到被置换得页面,淘汰ﻩblock[position]、pagenum = curpage;// 将新页面调入display();ﻩﻩn++; //缺页次数+1ﻩ}}ﻩ}ﻩprintf(”缺页次数:%d\n",n);printf("缺页率:%f%%\n",(n/320、0)*100);}void LRU() //最近最久未使用算法{int n=0;//记录缺页次数ﻩint exist,space,position ;ﻩint curpage;//当前指令得页面号ﻩfor(int i=0;i<320;i++)ﻩ{ﻩm=num[i];ﻩﻩcurpage=m/10;ﻩexist = pageExist(curpage);ﻩif(exist==-1)ﻩﻩ{ //当前指令得页面号不在物理块中space = findSpace();ﻩﻩif(space!= —1)ﻩ{ //当前存在空闲得物理块ﻩﻩblock[space]、pagenum = curpage;//将此页面调入内存ﻩﻩdisplay();//显示物理块中得页面号ﻩn++;//缺页次数+1ﻩﻩ}else{ //当前不存在空闲得物理块,需要进行页面置换ﻩﻩposition= findReplace();ﻩblock[position]、pagenum = curpage;ﻩﻩdisplay();ﻩn++;//缺页次数+1ﻩ}ﻩﻩ}elseﻩﻩblock[exist]、accessed = -1;//恢复存在得并刚访问过得BLOCK中页面accessed为-1for(int j=0; j<blocknum; j++)ﻩﻩ{//其余得accessed++ﻩﻩblock[j]、accessed++;}ﻩ}printf("缺页次数:%d\n”,n);ﻩprintf("缺页率:%f%%\n",(n/320、0)*100);}void FIFO(){int n=0;//记录缺页次数int exist,space,position ;ﻩ int curpage;//当前指令得页面号int blockpointer=-1;for(int i=0;i<320;i++)ﻩ{ﻩ m=num[i];curpage=m/10;ﻩexist = pageExist(curpage);ﻩ if(exist==-1){//当前指令得页面号不在物理块中ﻩ space = findSpace();ﻩﻩif(space !=-1)ﻩ { //当前存在空闲得物理块ﻩﻩ blockpointer++;ﻩﻩﻩblock[space]、pagenum=curpage; //将此页面调入内存ﻩ n++;//缺页次数+1ﻩﻩﻩ display();//显示物理块中得页面号ﻩ}ﻩ elseﻩ { //没有空闲物理块,进行置换ﻩﻩﻩﻩposition = (++blockpointer)%4;ﻩ block[position]、pagenum = curpage;//将此页面调入内存ﻩﻩn++;ﻩﻩ display();ﻩ}ﻩ }}printf("缺页次数:%d\n",n);printf("缺页率:%f%%\n",(n/320、0)*100);}void main(){ﻩint choice;ﻩprintf("************请求分页存储管理模拟系统*************\n");ﻩrandam();printf("************此进程得页面调用序列如下**************\n”);pagestring();ﻩwhile(choice!= 4){ﻩﻩprintf("********1:OPT 2:LRU 3:FIFO 4:退出*********\n”);ﻩprintf("请选择一种页面置换算法:”);ﻩscanf("%d",&choice);ﻩinit();ﻩswitch(choice)ﻩ{ﻩcase 1:ﻩﻩﻩprintf(”最佳置换算法OPT:\n");ﻩprintf("页面号物理地址页面号物理地址页面号物理地址页面号物理地址\n");ﻩﻩﻩOPT();ﻩbreak;ﻩcase 2:ﻩﻩprintf("最近最久未使用置换算法LRU:\n");ﻩprintf("页面号物理地址页面号物理地址页面号物理地址页面号物理地址\n");ﻩLRU();ﻩﻩﻩbreak;ﻩﻩcase 3:ﻩprintf("先进先出置换算法FIFO:\n");ﻩprintf("页面号物理地址页面号物理地址页面号物理地址页面号物理地址\n");FIFO();ﻩﻩbreak;ﻩ}}}。
实验四 操作系统存储管理实验报告

实验四操作系统存储管理实验报告一、实验目的本次操作系统存储管理实验的主要目的是深入理解操作系统中存储管理的基本原理和方法,通过实际操作和观察,掌握内存分配、回收、地址转换等关键技术,提高对操作系统存储管理机制的认识和应用能力。
二、实验环境操作系统:Windows 10开发工具:Visual Studio 2019三、实验原理1、内存分配方式连续分配:分为单一连续分配和分区式分配(固定分区和动态分区)。
离散分配:分页存储管理、分段存储管理、段页式存储管理。
2、内存回收算法首次适应算法:从内存低地址开始查找,找到第一个满足要求的空闲分区进行分配。
最佳适应算法:选择大小最接近作业需求的空闲分区进行分配。
最坏适应算法:选择最大的空闲分区进行分配。
3、地址转换逻辑地址到物理地址的转换:在分页存储管理中,通过页表实现;在分段存储管理中,通过段表实现。
四、实验内容及步骤1、连续内存分配实验设计一个简单的内存分配程序,模拟固定分区和动态分区两种分配方式。
输入作业的大小和请求分配的分区类型,程序输出分配的结果(成功或失败)以及分配后的内存状态。
2、内存回收实验在上述连续内存分配实验的基础上,添加内存回收功能。
输入要回收的作业号,程序执行回收操作,并输出回收后的内存状态。
3、离散内存分配实验实现分页存储管理的地址转换功能。
输入逻辑地址,程序计算并输出对应的物理地址。
4、存储管理算法比较实验分别使用首次适应算法、最佳适应算法和最坏适应算法进行内存分配和回收操作。
记录不同算法在不同作业序列下的内存利用率和分配时间,比较它们的性能。
五、实验结果与分析1、连续内存分配实验结果固定分区分配方式:在固定分区大小的情况下,对于作业大小小于或等于分区大小的请求能够成功分配,否则分配失败。
内存状态显示清晰,分区的使用和空闲情况一目了然。
动态分区分配方式:能够根据作业的大小动态地分配内存,但容易产生内存碎片。
2、内存回收实验结果成功回收指定作业占用的内存空间,内存状态得到及时更新,空闲分区得到合并,提高了内存的利用率。
OS实验4
实验四存储管理实验内容一、分区存储管理模拟二、请求页式存储管理模拟注:以上内容任选其一,运行环境、开发工具不限。
实验学时:2+2学时实验性质:综合设计性一、分区存储管理模拟【实验目的】设计一个虚拟内存工作区,并使用下述算法分配回收内存。
(1)最先适应分配算法(First Fit)(2)最差适应分配算法(Worst Fit)(3)最佳适应分配算法(Best Fit)二、请求页式存储管理模拟【实验目的】设计一个虚拟存储区和内存工作区,并使用下述算法计算访问命中率。
(1)先进先出的算法(FIFO)(2)最近最久未用算法(LRU)(3)最近最不经常使用算法(NUR)*(4)最佳淘汰算法(OPT)*(5)最少访问页面算法(LFU)*命中率=1-页面失效次数/页面地址流长度程序设计中,首先用Srand()和Rand()函数定义和产生指令序列,然后将指令序列变换成相应的页地址流,针对不同的算法计算出相应的命中率。
报告格式:统一封皮(学院统一格式)(一页)目录(一页)实验题目实验要求(一页)正文(另起一页)一、方案设计(技术方案、功能设计)二、结构设计1、数据结构设计2、程序结构设计(主函数、子函数结构设计或类结构设计)三、程序设计程序流程(方法或函数流程)四、编码调试(主要问题及其解决办法)五、实验总结六、程序清单(如程序太长,只附关键代码)排版要求:标题黑体四号居左正文宋体五号首行缩进请求页式存储管理模拟参考代码一【数据结构】(1)页面类型typedef struct{int pn’pfn,counter ,time;}pl-type;其中pn为页号,pfn为一个周期内访问该页面的次数,time为访问时间。
(2)页面控制结构pfc_struct{int pn,pfn;struct pfc_struct *next;};typedef struct pfc_struct pfc_type;pfc_type pfc[totle_vp], freepf_heed ,*busypf_head;pfc_type *busypf_tail;其中pfc[totle_vp]定义用户进程虚页控制结构,freepf_heed为空页面头的指针,busypf_head为忙页面头的指针,busypf_tail为忙页面尾的指针。
实验四操作系统存储管理实验报告
实验四操作系统存储管理实验报告一、实验目的本次实验的主要目的是深入理解操作系统中存储管理的基本原理和方法,通过实际操作和观察,掌握内存分配与回收、页面置换算法等关键概念,并能够分析和解决存储管理中可能出现的问题。
二、实验环境本次实验在装有 Windows 操作系统的计算机上进行,使用了 Visual Studio 等编程工具和相关的调试环境。
三、实验内容(一)内存分配与回收算法实现1、首次适应算法首次适应算法从内存的起始位置开始查找,找到第一个能够满足需求的空闲分区进行分配。
在实现过程中,我们通过建立一个空闲分区链表来管理内存空间,每次分配时从表头开始查找。
2、最佳适应算法最佳适应算法会选择能够满足需求且大小最小的空闲分区进行分配。
为了实现该算法,在空闲分区链表中,分区按照大小从小到大的顺序排列,这样在查找时能够快速找到最合适的分区。
3、最坏适应算法最坏适应算法则选择最大的空闲分区进行分配。
同样通过对空闲分区链表的排序和查找来实现。
(二)页面置换算法模拟1、先进先出(FIFO)页面置换算法FIFO 算法按照页面进入内存的先后顺序进行置换,即先进入内存的页面先被置换出去。
在模拟过程中,使用一个队列来记录页面的进入顺序。
2、最近最久未使用(LRU)页面置换算法LRU 算法根据页面最近被使用的时间来决定置换顺序,最近最久未使用的页面将被置换。
通过为每个页面设置一个时间戳来记录其最近使用的时间,从而实现置换策略。
3、时钟(Clock)页面置换算法Clock 算法使用一个环形链表来模拟内存中的页面,通过指针的移动和页面的访问标志来决定置换页面。
四、实验步骤(一)内存分配与回收算法的实现步骤1、初始化内存空间,创建空闲分区链表,并为每个分区设置起始地址、大小和状态等信息。
2、对于首次适应算法,从链表表头开始遍历,找到第一个大小满足需求的空闲分区,进行分配,并修改分区的状态和大小。
3、对于最佳适应算法,在遍历链表时,选择大小最接近需求的空闲分区进行分配,并对链表进行相应的调整。
实验--编程实现请求分页存储管理页面Optimal、FIFO、LRU置换算法
for(int i=0;i<fS;i++){
if(((Couple)(i)).time<temp){
temp=((Couple)(i)).time;
index=i;
}
}
for(int i=0;i<fS;i++){
if(i!=index){
((Couple)(i)).time--;
for(int i=0;i<;i++){
"Frame size: "+frameSize[i]+"\n");
(frameSize[i]);
(frameSize[i]);
"Total errors found: "+errorCount);
"\n************************************\n");
(frameSize[i]);
(frameSize[i]);
"Total errors found: "+errorCount);
"\n************************************\n");
errorCount=0;
}
"----------------Using LRU----------------");
(new Couple(0));
}
}
public void LRUReplace(int fS){
boolean findThesame=false;
int pre=-1;alue==digitalArray[j]){
模拟分页式虚拟存储管理中硬件的地址转换和缺页中断--选择页面调度算法处理缺页中断
操作系统实验二〔第一题〕一.实验内容模拟分页式虚拟存储管理中硬件的地址转换和缺页中断,以及选择页面调度算法处理缺页中断。
二.实验目的在电脑系统总,为了提高主存利用率,往往把辅助存储器作为主存储器的扩充,使多道运行的作业的全部逻辑地址空间综合可以超出主存的绝对地址空间。
用这种方法扩充的主存储区成为虚拟存储器。
三.实验题目模拟分页式存储管理中硬件的地址转换和产生缺页中断。
四.程序清单//// 操作实验二.cpp : 定义控制台应用程序的入口点。
//#include "stdafx.h"#include<iostream>#include<string>#include<fstream>using namespace std;class ins{private:string ope;long int page;long int unit;public:ins(){ }ins(string o,long int p,long int u):ope(o),page(p),unit(u){}void setope(string o){ ope=o;}void setpage(long int p){ page=p;}void setunit(long int u){ unit=u;}string getope(){return ope;}long int getpage(){return page;}long int getunit(){return unit;}};class work{private:long int Page;int sym;long int inum;long int onum;public:work(){}work(long int P, int s,long int i,long int o):Page(P),sym(s),inum(i),onum(o){} void setPage(long int P){ Page=P;}void setsym( int s){ sym=s;}void setinum(long int i){ inum=i;}void setonum(long int o){ onum=o;}long int getPage(){return Page;}int getsym(){return sym;}long int getinum(){return inum;}long int getonum(){return onum;}};void diaodu(work *w,ins * i,int numofins){ for(int j=0;j<numofins;j++){long int tempofk;long int a =i[j].getpage();for(int k=0;k<7;k++) //7是页表的页数if(w[k].getPage()!=a)continue;else{tempofk=k;break;}if(w[tempofk].getsym()==1)cout<<"绝对地址:"<<w[tempofk].getinum()*128+i[j].getunit()<<" "<<"磁盘地址为:"<<w[tempofk].getonum()<<" "<<"操作为:"<<i[j].getope()<<endl;else cout<<"*"<<"发生缺页中断"<<endl;}}int main(){ins*INS=new ins[12];INS[0].setope ("+");INS[0].setpage(0);INS[0].setunit(70);INS[1].setope ("+");INS[1].setpage(1);INS[1].setunit(50);INS[2].setope ("×");INS[2].setpage(2);INS[2].setunit(15);INS[3].setope ("存"); INS[3].setpage(3);INS[3].setunit(21);INS[4].setope ("取"); INS[4].setpage(0);INS[4].setunit(56);INS[5].setope ("-");INS[5].setpage(6);INS[5].setunit(40);INS[6].setope ("移位"); INS[6].setpage(4);INS[6].setunit(53);INS[7].setope ("+");INS[7].setpage(5);INS[7].setunit(23);INS[8].setope ("存"); INS[8].setpage(1);INS[8].setunit(37);INS[9].setope ("取"); INS[9].setpage(2);INS[9].setunit(78);INS[10].setope ("+"); INS[10].setpage(4);INS[10].setunit(1);INS[11].setope ("存"); INS[11].setpage(6);INS[11].setunit(84);work*W =new work[7]; ifstream in("g://operate1.txt");long int p;int s;long int i;long int o;for(int jj=0;jj<7 ;jj++){in>>p;in>>s;in>>i;in>>o ;W[jj].setPage(p);W[jj].setsym(s);W[jj].setinum(i);W[jj].setonum(o);}diaodu(W,INS,12);}五.结果显示操作系统实验二〔第二题〕一.用先进先出〔FIFO〕九.程序清单/ 操作系统实验二.cpp : 定义控制台应用程序的入口点。
- 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
- 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
- 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。
实验四 式虚拟存储管理中地址转换和式中断 FIFO LRU OPT C++版本 实验四 页式虚拟存储管理中地址转换与页式中断 FIFO 一、实验目的 深入了解页式存储管理如何实现地址转换;进一步认识页式虚拟存储管理中如何处理缺页中断以及页面置换算法。 二、实验主要内容 编写程序完成页式虚拟存储管理中地址转换过程与模拟缺页中断的处理。实验具体内容包括:首先对给定的地址进行转换工作,若发现缺页则先进行缺页中断处理,然后再进行地址转换;最后编写主函数对所做工作进行测试。 假定主存64KB,每个主存块1024字节,作业最大支持到64KB,系统中每个作业分得主存块4块。 三、实验原理 1)地址转换过程: 首先从逻辑地址中的高位取得页号,然后根据页号查页表,得到块号;然后从逻辑地址中的低位取得页内地址,将块号与页内地址合并即得到物理地址。 2)缺页中断处理 根据页号查找页表,判断该页就是否在主存储器中,若该页标志位“0”,形成缺页中断。操作系统让调出中断处理程序处理中断。 四、实验方法与步骤 实现地址转换与缺页中断处理,主要考虑三个问题:第一,设计页式虚拟存储管理方式中页表的数据结构;第二,地址转换算法的实现;第三,缺页中断处理算法的实现。 1) 设计页表的数据结构 页式虚拟存储管理方式中页表除了页号与该页对应的主存块号外,至少还要包括存在标志(该页就是否在主存),磁盘位置(该页的副本在磁盘上的位置)与修改标志(该页就是否修改过)。在实验中页表用数组模拟,其数据结构定义如下: struct{ int lnumber; //页号 int flag; //表示页就是否在主存中,“1”表示在,“0”表示不在 int pnumber; // 该页所在主存块的块号 int write; //该页就是否被修改过,“1”表示修改过,“0“表示没有修改过 int dnumber; //该页存放在磁盘上的位置,即磁盘块号 }page[n]; //页表定义 2)地址转换算法的实现 地址转换就是由硬件完成的,实验中使用软件程序模拟地址转换过程。在实验中,每个主存块1024字节,则块内地址占10位;主存64KB,则主存共64块,即块号占6位;物理地址共占16位;作业最大64KB,则作业最大占64块,即页号占6位,逻辑地址共占16位。(用主存的大小计算物理地址位数,用最大作业大小计算逻辑地址位数)。 在页式虚拟存储管理方式中,作业信息作为副本放在磁盘上,作业执行时仅把作业信息的部分页面装入主存储器,作业执行时若访问的页面在主存中,则进行地址转换,若访问的页面不在主存中,则产生一个“缺页中断”,由操作系统把当前所需要的页面装入主存储器后,再次执行时才可以按上述方法进行地址转换。 实验四 式虚拟存储管理中地址转换和式中断 FIFO LRU OPT C++版本 模拟地址转换流程度 3) 缺页中断处理算法的实现 缺页处理过程简单阐述如下: a) 根据当前执行指令中逻辑地址的页号查找页表,判断该页就是否在主存储器中,若该页标志为“0”,形成缺页中断。中断装置通过交换PSW让操作系统的中断处理程序占用处理器。 b) 操作系统处理缺页中断的方法及时查主存分配表,找一个空闲主存块;若无空闲块,查页表,选择一个已在主存的页面,把它暂时调出主存。若在执行过程中该页被修改过,则需将该页信息写回磁盘,否则不比写回; c) 找出该页的位置,启动磁盘读出该页的信息,把磁盘上读出的信息装入第2不找到的主存块,修改页表中该页的标志为“1”; d) 由于产生缺页中断的那条指令还没有执行完,所以页面装入后应该重新执行被中断的指令。当重新执行该指令时,由于要访问的页面已在主存中,所以可以正常执行。 关于第二步的查找装入新页面的主存块处理方式,不同系统采用的策略可能有所不同,这里采用局部置换算法,就就是每个作业分得一定的主存块,只能在分得的主存块内查找空闲块,若无空闲主存块,则从该作业中选择一个页面淘汰出主存。实验中采用局部置换算法。 使用局部置换算法时,存在这样一个问题:就就是在分配给作业主存空间时,装入哪些页?有的系统采取不装入任何一页,当执行过程中需要时才将其调入。有点系统采用页面预置的方法,事先估计可能某些页面会先用到,在分配主存块后将这些页面装入。在本实验中采用第二种方法,分配主存空间时将前几页调入主存,假定系统中每个作业分得主存块m 块,则将第 0~m-1页装入主存。 因为就是模拟硬件工作,所有在实验中如果访问的页不再主存中时,则输入该页页号,表示硬件产生缺页中断,然后直接转去缺页中断处理;由于采用页面预置方法,在给定的主存块中一定无空闲块,只能淘汰已在主存的一页;没有启动磁盘的工作,淘汰的页面需要写回磁盘时,用输入页号表示,调入新的一页时,将该页在页表中的存在标志置为“1”,输出页号表示将该页调入主存。 当主存中无空闲块时,为装入一个页面,必须按照某种算法从已在主存的页中选择一页,将它暂时调出主存,让出主存空间,用来存放装入的页面,这个工作称为“页面调度”。常用的页面调度算法有:先进现出、最近最少用算法、与最近最不常用算法。在本实验中采用先进现出调度算法。先进现出算法总就是选择驻留在主存时间最长的一页调出。实验中把主存储器的页的页号按照进入主存的先后次序拍成队列,每次总就是调出对首的页,当装入一个新页后,把新页的页号排入对尾。实验中,用一个数组存放页号的队列。假定分配给作业的主存块数为m,数组可由m个元素组成,p[0],p[1],p[2]……p[m-1];对首指针head;采用页面预置的方法,页号队列的长度总就是m,tail等于(head+1)%m。因此可以使用一个指针,只用head即可。在装入一个新的页时,装入页与淘汰页同时执行,当装入一个新的页时,将其页号存入数组: 淘汰页的页号=p[head]; p[head]=新装入页的页号; 实验四 式虚拟存储管理中地址转换和式中断 FIFO LRU OPT C++版本 head=(head+1)%m; 实验执行一条指令时,不模拟指令的执行,只就是考虑指令执行就是否修改页面,若修改页面,则将该页的页表中的修改标志位置“1”,然后输出转换后的物理地址,并输出物理地址来表示一条指令执行完成;如果访问的页不在主存时,则产生缺页中断,然后直接转去缺页中断处理,最后模拟中断返回,就就是返回冲进进行地址转换。 因为没有实际主存,所有在模拟程序中首先手工输入页表信息,创建该作业的页表;然后循环执行假定的指令,观察地址转换情况。 五、练习题 采用LRU页面调度算法编程实现上述虚拟页式存储管理的地址转换。 源代码 #include #define n 64 //页表的最大长度 #define length 4 //系统为每个作业分配的主存块数 struct{ int lnumber; //页号 int flag; //表示页就是否在主存中,“1”表示在,“0”表示不在 int pnumber; // 该页所在主存块的块号 int write; //该页就是否被修改过,“1”表示修改过,“0“表示没有修改过 int dnumber; //该页存放在磁盘上的位置,即磁盘块号 }page[n]; //页表定义 int m; int page_length; //页表的实际长度 int p[length]; //用向量模拟主存 int head; void page_interrupt(int); //缺页中断处理函数 void command(unsigned, int); //命令处理函数 void main() { int lnumber,pnumber,write,dnumber; unsigned laddress; int i; cout<<"输入页表的信息,创建页表(页号从0开始,若页号为-1,则结束输入)\n"; cout<<"请输入页号与辅存地址:"; cin>>lnumber>>dnumber; cin、ignore (); i=0; while(lnumber!=-1) { page[i]、lnumber=lnumber; page[i]、flag=0; page[i]、write=0; page[i]、dnumber=dnumber; 实验四 式虚拟存储管理中地址转换和式中断 FIFO LRU OPT C++版本 i++; cout<<"请输入页号与辅存地址:"; cin>>lnumber>>dnumber; } //预先将输入的页调入主存块中 page_length=i; cout<<"输入主存块号(输入少于或者等于"<结束输入):"; cin>>pnumber; cin、ignore (); m=0; head=0; while(m{ if(m{ page[m]、pnumber=pnumber; page[m]、flag=1;//调入主存后,标志为置1 p[m]=m; //记录主存中的页号 m++; } cout<<"输入主存块号(输入少于或者等于"<则结束输入):"; cin>>pnumber; cin、ignore (); }//while cout<<"输入指令性质(1-修改,0-不需要,其她-结束程序运行)与逻辑地址\n" <<"逻辑地址最大能支持2的16次方-1=65535。\n"; cout<<"输入指令性质:"; cin>>write; cin、ignore (); cout<<"输入逻辑地址:"; cin>>laddress; cin、ignore (); while(write==0||write==1) { command(laddress,write); //将输入的逻辑地址转换成物理地址 cout<<"输入指令性质:"; cin>>write; cin、ignore (); if(write!=0&&write!=1) break; cout<<"输入逻辑地址:"; cin>>laddress;