请求页式存储管理的模拟实现_参考代码_
模拟操作系统的请求分页存储管理JAVA代码
return this.state; } public int getVisitcount(){
return this.visitcount; } public boolean getChange(){
System.out.println("请输入一个页面的页号(0-19):"); k1=a.nextInt(); if(k1>=20||k1<0){
System.out.println("输入数据有错,将退出程序!!"); System.exit(0); }
//检测快表,快表存储当前的页表项,即当快表满时采用最近最久未被使用算法置换快表 System.out.println("进入快表检测"); if(TLB.getCurrent()>0){
this.pagenumb=pagenumb; this.physicsnumb=physicsnumb; this.state=state; this.visitcount=visitcount; this.change=change; this.CRTaddress=CRTaddress; } public void setPagenumb(int pagenumb){ this.pagenumb=pagenumb; } public void setPhysicsnumb(int physicsnumb){ this.physicsnumb=physicsnumb; } public void setState(boolean state){ this.state=state; } public void setVisitcount(int visitcount){ this.visitcount=visitcount; } public void setChange(boolean change){ this.change=change;
请求调页存储管理方式的模拟NRU
NRU#include <stdio.h>#include <stdlib.h>#include <string.h>#ifndef _UNISTD_H#define _UNISTD_H#include <IO.H>#include <PROCESS.H>#endif#define TRUE 1#define FALSE 0#define INVALID -1#define NULL 0#define total_instruction 320 /*指令流长*/ #define total_vp 32 /*虚页长*/#define clear_period 50 /*清0周期*/typedef struct /*页面结构*/{int pn,pfn,counter,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_h ead,*busypf_tail;int diseffect, a[total_instruction];int page[total_instruction], offset[total_instru ction];int initialize(int);int NUR(int)int main( ){int s,i,j;srand(10*getpid()); /*由于每次运行时进程号不同,故可用来作为初始化随机数队列的“种子”*/s=(float)319*rand( )/32767/32767/2+1; // for(i=0;i<total_instruction;i+=4) /*产生指令队列*/{if(s<0||s>319){printf("When i==%d,Error,s==%d\n",i,s);exit(0);}a[i]=s; /*任选一指令访问点m*/a[i+1]=a[i]+1; /*顺序执行一条指令*/a[i+2]=(float)a[i]*rand( )/32767/32767/2; /*执行前地址指令m' */a[i+3]=a[i+2]+1; /*顺序执行一条指令*/s=(float)(318-a[i+2])*rand( )/32767/32767/2 +a[i+2]+2;if((a[i+2]>318)||(s>319))printf("a[%d+2],a number which is :%d and s= =%d\n",i,a[i+2],s);}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---\n",i);NUR(i);}return 0;}int 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=0;i<total_pf-1;i++){pfc[i].next=&pfc[i+1];pfc[i].pfn=i;} /*建立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]*/return 0;}int NUR(total_pf) /*最近未使用算法*/int total_pf;{int i,j,dp,cont_flag,old_dp;pfc_type *t;initialize(total_pf);dp=0;for(i=0;i<total_instruction;i++){ if (pl[page[i]].pfn==INVALID) /*页面失效*/ {diseffect++;if(freepf_head==NULL) /*无空闲页面*/{ cont_flag=TRUE;old_dp=dp;while(cont_flag)if(pl[dp].counter==0&&pl[dp].pfn! =INVALID)cont_flag=FALSE;else{ dp++;if(dp==total_vp)dp=0;if(dp==old_dp)for(j=0;j<total_vp;j++)pl[j].counter=0; }freepf_head=&pfc[pl[dp].pfn];pl[dp].pfn=INVALID;freepf_head->next=NULL;}pl[page[i]].pfn=freepf_head->pfn;freepf_head=freepf_head->next;}elsepl[page[i]].counter=1;if(i%clear_period==0)for(j=0;j<total_vp;j++)pl[j].counter=0;}printf("NUR:%6.4f\n",1-(float)diseffect/320); return 0;}1.设计目的通过对页面、页表、地址转换和页面置换过程的模拟,加深对请求调页系统的原理和实现过程的理解。
请求调页存储管理方式的模拟LFU(含源代码)
课程设计课程设计名称:请求调页存储管理方式的模拟4专业班级:学生姓名:学号:指导教师:课程设计时间:2012.12.24-2012.12.28计算机科学专业课程设计任务书说明:本表由指导教师填写,由教研室主任审核后下达给选题学生,装订在设计(论文)首页填表说明1.“课题性质”一栏:A.工程设计;B.工程技术研究;C.软件工程(如CAI课题等);D.文献型综述;E.其它。
2.“课题来源”一栏:A.自然科学基金与部、省、市级以上科研课题;B.企、事业单位委托课题;C.校、院(系、部)级基金课题;D.自拟课题。
1 需求分析1)假设每个页面中可存放10条指令,分配给作业的内存块数为4。
2)用C语言模拟一个作业的执行过程,该作业共有320条指令,即它的地址空间为32页,目前它的所有页都还未调入内存。
在模拟过程中,如果所访问的指令已在内存,则显示其物理地址,并转下一条指令。
如果所访问的指令还未装入内存,则发生缺页,此时需记录缺页的次数,并将相应页调入内存。
如果4个内存块均已装入该作业,则需进行页面置换,最后显示其物理地址,并转下一条指令。
在所有320指令执行完毕后,请计算并显示作业运行过程中发生的缺页率。
3)置换算法:最少访问(LFU)算法。
通过对页面、页表、地址转换和页面置换过程的模拟,加深对请求调页系统的原理和实现过程的理解。
所有内容均为独立完成。
2 概要设计本实验主要分为以下几个重要实现过程:(1)首先由对应函数按照题目要求产生对应的320条随即指令。
(2)当指令到来时,首先查询4个物理模块中是否含有当前指令,如果有则直接下一条指令,若没有就进行判定查找物理块中是否还有空闲盘块,有该指令则直接调入,无则要发生页面置换。
(3)按照一定规则(LFU)进行页面置换,知道最后一条指令完成后,显示缺页次数和缺页率。
程序中自定义的函数(函数名,参数,以及功能)及结构等如下:#define Bsize 4 定义一个全局的物理块大小4struct BLOCK { 物理块类型的申明int pagenum; //用于存储页号int use; //用于计算最近使用次数};int num=0; //记录指令的序号int n=0; //记录缺页的次数static int temp[320]; //用来存储320条指令struct BLOCK block[4]; //大小为4的物理块数组int findExist(int curpage);//查找物理块中是否有该页面int findSpace(); //查找是否有空闲物理块int findReplace(); //查找应予置换的页面void display(); //显示置换过程void zhiling(); //产生320条指令,显示并存储到temp[320],并调度页号队列void LFU(); //LFU算法3 运行环境软件:Windows 98及以上操作系统,Microsoft Visual C++ 6.0版本硬件: 512M CPU内存及以上的计算机4 开发工具和编程语言开发工具:Microsoft Visual C++ 6.0编程语言:C语言5 详细设计(1)产生320条指令,显示并存储到temp[320],并调度页号队列320条随即指令的产生规则如下:①在[0,319]的指令地址之间随机选取一起点m;②顺序执行一条指令,即执行地址为m+1的指令;③在前地址[0,m+1]中随机选取一条指令并执行,该指令的地址为m′;④顺序执行一条指令,其地址为m′+1的指令;⑤在后地址[m′+2,319]中随机选取一条指令并执行;⑥重复上述步骤①~⑤,直到执行320次指令。
操作系统实验4-请求分页存储管理模拟实验
实验四请求分页存储管理模拟实验一:实验目的通过对页面、页表、地址转换和页面置换过程的模拟,加深对请求分页存储管理系统的原理和实现技术的理解。
二:实验容假设每个页面可以存放10条指令,分配给进程的存储块数为4。
用C语言或Pascal语言模拟一进程的执行过程。
设该进程共有320条指令,地址空间为32个页面,运行前所有页面均没有调入存。
模拟运行时,如果所访问的指令已经在存,则显示其物理地址,并转下一条指令;如果所访问的指令还未装入存,则发生缺页,此时需要记录缺页产生次数,并将相应页面调入存,如果4个存块已满,则需要进行页面置换。
最后显示其物理地址,并转下一条指令。
在所有指令执行完毕后,显示进程运行过程中的缺页次数和缺页率。
页面置换算法:分别采用OPT、FIFO、LRU三种算法。
进程中的指令访问次序按如下原则生成:50%的指令是顺序执行的。
25%的指令是均匀分布在低地址部分。
25%的指令是均匀分布在高地址部分。
三:实验类别分页存储管理四:实验类型模拟实验五:主要仪器计算机六:结果OPT:LRU:FIFO:七:程序# include<stdio.h># include<stdlib.h># include<conio.h># define blocknum 4//页面尺寸大小int m; //程序计数器,用来记录按次序执行的指令对应的页号static int num[320]; //用来存储320条指令typedef struct BLOCK //声明一种新类型--物理块类型{int pagenum; //页号int accessed; //访问量,其值表示多久未被访问}BLOCK;BLOCK block[blocknum]; //定义一大小为8的物理块数组void init() //程序初始化函数,对block初始化{for(int i=0;i<blocknum;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]的一条指令处,设其序号为m2flag=++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;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{ //当前不存在空闲的物理块,需要进行页面置换for(int k=0;k<blocknum;k++){for(int j=i;j<320;j++){//找到在最长(未来)时间不再被访问的页面if(block[k].pagenum!= num[j]/10){block[k].accessed = 1000;} //将来不会被访问,设置为一个很大数else{ //将来会被访问,访问量设为jblock[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}}elseblock[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++;//缺页次数+1display();//显示物理块中的页面号}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;}}}。
Java模拟操作系统实现存储管理
存储器管理1.实验内容:模拟请求页式存储管理中硬件的地址转换和缺页中断,并用先进先出调度算法(FIFO)处理缺页中断;2.要求:①指令序列的设定可以执行拟定,格式如表3;②在完成了FIFO换页策略后,可以选做LRU的换页策略,并进行比较;③作业允许的页架数m在不同情况下的缺页中断率;④程序运行时显示地址转变和页面调入调出过程。
3.实验控制流图:4.数据结构核心代码:package xiao.zhang.bean;public class Instruction {/*** 指令操作符号*/private String op;/*** 页号*/private int pageId;/*** 页内地址*/private int pageInAddress;public Instruction() {}public Instruction(String op, int pageId, int pageInAddress) { this.op = op;this.pageId = pageId;this.pageInAddress = pageInAddress;}public String getOp() {return op;}public void setOp(String op) {this.op = op;}public int getPageId() {return pageId;}public void setPageId(int pageId) {this.pageId = pageId;}public int getPageInAddress() {return pageInAddress;}public void setPageInAddress(int pageInAddress) { this.pageInAddress = pageInAddress;}/** (non-Javadoc)** @see ng.Object#toString()*/@Overridepublic String toString() {return"Instruction [op=" + this.op + ", pageId=" + this.pageId+ ", pageInAddress=" + this.pageInAddress + ", getOp()="+ this.getOp() + ", getPageId()=" + this.getPageId()+ ", getPageInAddress()=" + this.getPageInAddress()+ ", getClass()=" + this.getClass() + ", hashCode()="+ this.hashCode() + ", toString()=" + super.toString() + "]";}}package xiao.zhang.bean;import java.util.LinkedList;public class ExecuteFiFo {/*** 指令队列*/public LinkedList<Instruction> is;/*** 页面存储*/public LinkedList<Page> pages;/*** 是否还有存储页架*/private final int isUseablePageFrame;public static int point = 0;/*** 默认设置页架为4个*/public ExecuteFiFo() {this.isUseablePageFrame = 4;}public ExecuteFiFo(int isUseablePageFrame) {is = new LinkedList<Instruction>();pages = new LinkedList<Page>();this.isUseablePageFrame = isUseablePageFrame;}public ExecuteFiFo(LinkedList<Instruction> is, LinkedList<Page> pages,int isUseablePageFrame) {this.is = is;this.pages = pages;this.isUseablePageFrame = isUseablePageFrame;}/*** 一次性调度完成,装载所有的可用的页*/public void initalExecute() {for (int i = 0; i < isUseablePageFrame; i++) {/*** 从指令队列出一条指令*/Instruction ins = is.poll();/*** 访问指定页号的主存*/Page p = pages.get(i);p.setPageId(ins.getPageId());p.setInMen(true);p.setModifyFlag(isModify(ins.getOp()));printINInformation(ins);}}/*** 执行指令*/public void executeInstruction() {/*** 先判断执行的页是否住存指令序列中将其删除*/while (!is.isEmpty()) {Instruction ins = is.poll();if (isExistMemeroy(ins)) {System.out.println("[页号为:\t" + ins.getPageId() + "\t存在]");Page p = pages.get(ins.getPageId());printOUTInformation(p);printINInformation(ins);} else {System.out.println("[页号为:\t" + ins.getPageId() + "\t不存在]");Page p = pages.get(ins.getPageId());p.setInMen(true);Page outP = pages.get(point % isUseablePageFrame);p.setPageFrameId(outP.getPageFrameId());p.setModifyFlag(isModify(ins.getOp()));printOUTInformation(outP);printINInformation(ins);}point++;}}/*** 判断指定序列是否住存** @return*/public boolean isExistMemeroy(Instruction ins) {for (int i = 0; i < this.pages.size(); i++) {if (this.pages.get(i).getPageId() == ins.getPageId()&& this.pages.get(i).isInMen()) {return true;}}return false;}/*** 打印装载信息** @param ins*/public void printINInformation(Instruction ins) {System.out.println("[页号:" + ins.getPageId() + "\tIN\t" + "执行:"+ ins.getOp() + "操作\t" + "物理地址:"+ (1024 * ins.getPageId() + ins.getPageInAddress()) + "]");}/*** 打印调出信息** @param p*/public void printOUTInformation(Page p) {if (p.isModifyFlag()) {System.out.println("[页号:" + p.getPageId() + "\tOUT\t" + "页架号:"+ p.getPageFrameId() + "\t修改\t" + "写回磁盘:"+ p.getLocationInDisk() + "]");} else {System.out.println("[页号:" + p.getPageId() + "\tOUT\t" + "页架号:"+ p.getPageFrameId() + "\t未修改\t" + "不用写回磁盘]");}}* 判断指令是否修改主存内容** @param op* @return*/public boolean isModify(String op) { if (op.equals("R") || op.equals("W")) { return true;}return false;}/*** @return the isUseablePageFrame*/public int getIsUseablePageFrame() { return isUseablePageFrame;}/*** @return the ispublic LinkedList<Instruction> getIs() { return this.is;}/*** @return the pages*/public LinkedList<Page> getPages() {return this.pages;}/*** @param is* the is to set*/public void setIs(LinkedList<Instruction> is) { this.is = is;}/*** @param pages* the pages to set*/public void setPages(LinkedList<Page> pages) { this.pages = pages;}}package xiao.zhang;import xiao.zhang.bean.ExecuteFiFo;import xiao.zhang.bean.Instruction;import xiao.zhang.bean.Page;public class MainExecute {public static void main(String[] args) {Instruction[] i = new Instruction[12];i[0] = new Instruction("+", 0, 70);i[1] = new Instruction("-", 1, 50);i[2] = new Instruction("*", 2, 15);i[3] = new Instruction("R", 3, 21);i[4] = new Instruction("W", 0, 56);i[5] = new Instruction("-", 6, 40);i[6] = new Instruction("RM", 4, 53);i[7] = new Instruction("+", 5, 23);i[8] = new Instruction("W", 1, 37);i[9] = new Instruction("R", 2, 78);i[10] = new Instruction("+", 4, 1);i[11] = new Instruction("W", 6, 84);Page[] p = new Page[7];p[0] = new Page(0, true, 5, false, 11); p[1] = new Page(2, true, 8, false, 12); p[2] = new Page(3, true, 9, false, 13); p[3] = new Page(4, true, 1, false, 21); p[4] = new Page(5, false, 0, false, 22); p[5] = new Page(6, false, 0, false, 23); p[6] = new Page(7, false, 0, false, 121);ExecuteFiFo xf = new ExecuteFiFo(4); for (int j = 0; j < p.length; j++) {xf.getPages().add(p[j]);}for (int j = 0; j < i.length; j++) {xf.getIs().add(i[j]);}xf.initalExecute();xf.executeInstruction();}}精品6.程序运行结构截图:精品。
操作系统实验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;ﻩ}}}。
请求调页存储管理方式的模拟NRU
请求调页存储管理方式的模拟NRU#i nclude <stdio.h>#in elude <stdlib.h>#in elude <stri ng.h>#ifndef _UNISTD_H#defi ne _UNISTD_H#i nclude <IO.H>#i nclude <PROCESS.H>#en dif#defi ne TRUE 1#defi ne FALSE 0#defi ne INVALID -1#defi ne NULL 0#define total_instruction 320 /* 指令流长*/ #defi ne total_vp 32 /* 虚页长*/#define clear_period 50 /* 清0 周期*/ typedef struct /* 页面结构*/{int pn,pfn ,co un ter,time;}pl_type;pl_type pl[total_vp]; /* 页面结构数组*/struct pfc_struct{ /*页面控制结构*/int pn,pfn;struct pfc_struct *n ex t;};typedef struct pfc_struct pfc_type;pfc_type pfc[total_vp],*freepf_head,*busypf_h ead,*busypf_tail;int diseffect, a[total _in structio n];int page[total_instruction], offset[total_instru ctio n];int in itialize(i nt);int NUR(i nt) int main(){int s,i,j;sra nd(10*getpid());/* 由于每次运行时进程号不同,故可用来作为初始化随机数队列的“种子” */s=(float)319*rand( )/32767/32767/2+1; //for(i=0;i<total_i nstructio n; i+=4) /* 产生指令队列*/{if(s<0||s>319){prin tf("Whe n i==%d,Error,s==%d\n",i,s);exit(O);}a[i]=s; /*任选一指令访问点m*/ a[i+1]=a[i]+1; /* 顺序执行一条指令*/a[i+2]=(float)a[i]*rand( )/32767/32767/2; /* 执行前地址指令m' */a[i+3]=a[i+2]+1;/* 顺序执行一条指令*/s=(float)(318-a[i+2])*rand( )/32767/32767/2+a[i+2]+2;if((a[i+2]>318)||(s>319))prin tf("a[%d+2],a n umber which is :%d and s= =%d\n",i,a[i+2],s);}for (i=0;i<total_i nstructio n;i++) /* 将指令序列变换成页地址流*/{page[i]=a[i]/10;offset[i]=a[i]%10;}for(i=4;i<=32;i++) /* 用户内存工作区从4个页面到32个页面*/{printf("---%2d page frames---\n ",i);NUR(i);}return 0;}int in itialize(total_pf) /* 初始化相关数据结构*/int total_pf; /*用户进程的内存页面数*/{int i;diseffect=0;for(i=0;i<total_vp;i++){pl[i].p n=i;pl[i].pfn=INVALID; /* 置页面控制结构中的页号,页面为空*/pl[i].co un ter=0;pl[i].time=-1; /*页面控制结构中的访问次数为0,时间为-1*/}for(i=0;i<total_pf-1;i++){pfc[i]. next=&pfc[i+1];pfc[i].pf n=i;} /*建立pfc[i-1]和pfc[i]之间的链接*/ pfc[total_pf-1] .n ext=NULL;pfc[total_pf-1].pf n=total_pf-1;freepf_head=&pfc[0]; /* 空页面队列的头指针为pfc[0]*/return 0;}int NUR(total_pf) /* 最近未使用算法*/int total_pf;{int i,j,dp,c on t_flag,old_dp;pfc_type *t;in itialize(total_pf);dp=0;for(i=0;i<total_i nstructio n;i++){ if (pl[page[i]].pfn==INVALID) /* 页面失效*/ {diseffect++;if(freepf_head==NULL) /* 无空闲页面*/{ con t_flag=TRUE;old_dp=dp;while(c on t_flag) if(pl[dp].counter==0&&pl[dp].pfn! =INVALID)co nt_flag=FALSE;else{ dp++;if(dp==total_vp)dp=0;if(dp==old_dp)for(j=0;j<total_vp;j++) pl[j].co unter=0; } freepf_head=&pfc[pl[dp].pf n];pl[dp].pfn=INVALID;freepf_head->n ext=NULL;}pl[page[i]].pf n=freepf_head->pf n;freepf_head=freepf_head->n ex t; }elsepl[page[i]].co un ter=1;if(i%clear_period==0)for(j=0;jvtotal_vp;j++)pl[j].co un ter=0;}prin tf("NUR:%6.4f\n",1-(float)diseffect/320); return 0;}1 •设计目的通过对页面、页表、地址转换和页面置换过程的模拟,加深对请求调页系统的原理和实现过程的理解。
操作系统课程设计模拟请求页式存储管理
操作系统课程设计报告项目:模拟请求页式存储管理一、目的和要求1、实训目的(1)通过编写和调试存储管理的模拟程序以加深对存储管理方案的理解。
熟悉虚存管理的各种页面淘汰算法(2)通过编写和调试地址转换过程的模拟程序以加强对地址转换过程的了解。
2、实训要求编写并调试完成请求页式存储管理程序。
页面置换算法:最佳置换算法(OPT)、先进先出算法(FIFO)和最近最少用算法(LRU)。
要求打印每个页面置换算法的页面置换变化示意图、缺页中断次数和缺页中断率,以比较各种算法的优缺点。
二、设计思路及过程1、概要设计1.1 问题概述根据三种不同的置换算法(FIFO、LRU、OPT),依据其不同的算法方式,分别计算该页面引用串在不同算法下的缺页次数与缺页率,并显示各页面的变化情况。
1.2 内容分析对于该课程设计中模拟的请求页式存储管理的页面置换过程,只要掌握其中最基本的三种算法,包括FIFO、LRU及OPT。
另外,对于同一个页面引用串,要求能够调用不同的算法对它进行操作。
2、过程设计2.1模块设计在下图的主模块设计图中,只注重描绘了请求页式存储管理的三种主要算法,未描绘出细节部分。
图2.1 请求页式存储管理的主模块设计图2.2 算法原理分析要成功实现算法,首先要知道各个方法是怎么做的,即原理是怎样的,下面是三种算法的原理。
(1)FIFO算法:该算法认为刚被调入的页面在最近的将来被访问的可能性很大,而在主存中滞留时间最长的页面在最近的将来被访问的可能性很小。
因此。
FIFO算法总是淘汰最先进入主存的页面,即淘汰在主存中滞留时间最长的页面。
(2)LRU算法是最近最久未使用,当当前内存中没有正要访问的页面时,置换出在当前页面中最近最久没有使用的页面。
该算法总是选择最近一段时间内最长时间没有被访问过的页面调出。
它认为那些刚被访问过的页面可能在最近的将来还会经常访问他们,而那些在较长时间里未被访问的页面,一般在最近的将来再被访问的可能性较小。
实验四 页式虚拟存储管理
页式虚拟存储管理中地址转换和缺页中断一、实验目的模拟请求页式存储管理中硬件的地址转换和缺页中断,并用先进先出调度算法(FIFO)处理缺页中断。
二、实验内容1.内容:模拟请求页式存储管理中硬件的地址转换和缺页中断处理2.思想:装入新页置换旧页时,若旧页在执行中没有被修改过,则不必将该页重写磁盘。
因此,页表中增加是否修改过的标志,执行“存”指令和“写”指令时将对应的三、程序及截图程序主要代码:#include<iostream>#include<iomanip>#include<list>using namespace std;char useSign[12][5]={{'+'},{'-'},{'*'},{"存"},{"取"},{'-'},{"移位"},{'+'},{"存"},{"取"},{'+'},{"存"}};int PageAddress[12]={70,50,15,21,56,40,53,23,37,78,01,84};int PageNum[12]={0,1,2,3,0,6,4,5,1,2,4,6};int S_Station;int pPageNum[7];//页号pPageint pSign[7];int pStool[7];//页架号int pModify[7];//修改标志int pStation[7];//磁盘位置static int z=0;void Store(){for(int i=0;i<7;i++){if(i<4){pSign[i]=1;}elsepSign[i]=0;pPageNum[i]=i;pModify[i]=0;}int p1=1,p2=2,p3=3;for(i=0;i<7;i++){if(i<3){pStation[i]=p1;p1++;}elseif(i<6){pStation[i]=p2;p2++;}elsepStation[i]=p3;}pStool[0]=5;pStool[1]=8;pStool[2]=9;pStool[3]=1;}void CShow(){cout<<"操作";cout<<"页号";cout<<"页内地址";cout<<"标志";cout<<"绝对地址";cout<<"修改页号";cout<<"页架号";cout<<"绝对地址";cout<<endl;}void Find(){int m_Pagenum;int m_Station;int Y_Station;//绝对地址int m_Stool;cout<<"输入页号及页内地址查询操作:";cin>>m_Pagenum>>m_Station;CShow();int i,j=0;//string m_Modify;for(i=0;i<12;i++){if(PageAddress[i]==m_Station){break;}}Y_Station=pStool[m_Pagenum]*1024+m_Station;if(pSign[m_Pagenum]==1){if(strcpy(useSign[i],"存")!=0){pModify[m_Pagenum]=1;}}cout<<useSign[i]<<" ";cout<<m_Pagenum<<" ";cout<<m_Station<<" ";cout<<pSign[m_Pagenum]<<" ";if(Y_Station!=m_Station){cout<<Y_Station<<" ";cout<<" ";cout<<pStool[m_Pagenum]<<" ";cout<<Y_Station<<endl;}else{cout<<"*"<<m_Pagenum<<" ";for(j=z;j<7;j++){if(pSign[j]==1){z++;break;}}cout<<m_Pagenum<<"->"<<j<<" ";pStool[m_Pagenum]=pStool[j];pSign[j]=0;pStool[j]=0;cout<<pStool[m_Pagenum]<<" ";cout<<pStool[m_Pagenum]*1024+m_Station<<endl;}}int main(void){Store();char judge='Y';while(judge=='Y'){Find();cout<<"是否继续输入?Y = 是N=否"<<endl;cin>>judge;}return 0;}运行结果截图:五.心得体会在实验过程中,在调试的过程中遇到了一些问题,导致出现很多错误,在同学的帮助下,基本都解决了所有问题。
请求页式虚拟存储管理(FIFO算法)
{
//内存有空闲
if(bno.Length()<5)
{
page_table[j].state=1;
page_table[j].block_no=i+10;
bno.InQueue(page_table[j].no);
bno.Traverse(Write);
{
a[0]=loc[i]/1024; //计算出的页号
a[1]=loc[i]%1024; //计算出的页内偏移量
//找到页表中的该页
for( j=0;j<64;j++)
{
if(page_table[j].no==a[0]) break;
}
//该页在内存
if(page_table[j].state==1)
{
bno.Traverse(Write); //输出队列里的页面
cout<<endl;
cout<<page_table[j].no<<' '<<page_table[j].state<<' '<<page_table[j].block_no<<endl<<endl; //输出页表信息
}
//该页不在内存,FIFO算法
cout<<endl;
cout<<page_table[j].no<<''<<page_table[j].state<<' '<<page_table[j].block_no<<endl<<endl;
请求页式存储管理的模拟实现_参考代码_
case REQUEST_EXECUTE:
ptr_pageTabIt->count++;
if(!(ptr_pageTabIt->proType&EXECUTABLE)){
do_error(ERROR_EXECUTE_DENY);
return ;
}
info.Format(_T("执行成功\n"));
out->SetSel(-1, -1);
out->ReplaceSel(info);
if(pageTable[page].modified){
info.Format(_T("有修改,写回至外存\n"));
out->SetSel(-1, -1);
out->ReplaceSel(info);
do_page_out(&pageTable[page]);
do_init(){
int i,j;
srand(time(NULL));
for(i=0;i<PAGE_SUM;i++){
pageTable[i].pageNum=i;
pageTable[i].effective=mFALSE;
pageTable[i].modified=mFALSE;
pageTable[i].count=0;
ptr_pageTabIt->blockNum=j;//修改调入页的页表项
ptr_pageTabIt->effective=TRUE;
ptr_pageTabIt->count=0;
info.Format(_T("页面替换成功\n"));
模拟操作系统的请求分页存储管理java代码
请求分页存储管理的实现写出方案实现代码(1)page类package homework;public class Page {private int pagenumb;//页号private int physicsnumb;//物理块号private boolean state;//状态位private int visitcount;//访问字段private boolean change;//修改位private int CRTaddress;//外存地址public Page(){this.pagenumb=-1;this.physicsnumb=-1;this.state=false;this.visitcount=0;this.change=false;this.CRTaddress=-1;}public Page(int pagenumb,int physicsnumb,boolean state,int visitcount,boolean change,int CRTaddress){this.pagenumb=pagenumb;this.physicsnumb=physicsnumb;this.state=state;this.visitcount=visitcount;this.change=change;this.CRTaddress=CRTaddress;}public void setPagenumb(int pagenumb){this.pagenumb=pagenumb;}public void setPhysicsnumb(int physicsnumb){this.physicsnumb=physicsnumb;}public void setState(boolean state){this.state=state;}public void setVisitcount(int visitcount){this.visitcount=visitcount;}public void setChange(boolean change){this.change=change;}public void setCRTaddress(int CRTaddress){this.CRTaddress=CRTaddress;}public int getPagenumb(){return this.pagenumb;}public int getPhysicsnumb(){return this.physicsnumb;}public boolean getState(){return this.state;}public int getVisitcount(){return this.visitcount;}public boolean getChange(){return this.change;}public int getCRTaddress(){return this.CRTaddress;}}(2)Shell类:页表package homework;import java.util.Scanner;public class Shell {Page shell[];private int current;private int length;public Shell(){ };public Shell(int length){this.length=length;this.current=0;shell=new Page[length];for(int i=0;i<length;i++){this.shell[i]=new Page();}}public void setCurrent(int current){this.current=current;} public int getCurrent(){return this.current;}public int searchpage(int pagenumb){int i=0;if(this.current==0){return -2;}else{while(i<this.current){if(this.shell[i].getPagenumb()==pagenumb){return i;}i++;}return -1;}}public void Inchange(int b[],String ch,int number){Scanner a=new Scanner(System.in);switch(ch){case"yes":{System.out.println("请输入一个新的数据");b[this.shell[number].getPhysicsnumb()]=a.nextInt();this.shell[number].setChange(true);System.out.println("修改成功!");break;}case"no":{break;}default:{System.out.println("输入字符有误,将退出程序!!");System.exit(0);}}}public int Isover(){if(this.current>=this.length){return 1;}else return 0;}public int MinVisitcount(){int i,t=0;for(i=1;i<this.current;i++){if(this.shell[i].getVisitcount()<this.shell[t].getVisitcount()){ t=i;}}return t;}public int Ischange(int number){if(this.shell[number].getChange()==true){return 1;}else return 0;}public void printPageShell(){System.out.println("页表:");System.out.println("索引\t"+"页号\t"+"物理块号\t"+"状态\t"+"访问次数\t"+"修改\t"+"外存地址\t");for(int i=0;i<this.length;i++){System.out.println(i+"\t"+this.shell[i].getPagenumb()+"\t"+this.shell[i ].getPhysicsnumb()+"\t"+this.shell[i].getState()+"\t"+this.shell[i].getVisi tcount()+"\t"+this.shell[i].getChange()+"\t"+this.shell[i].getCRTaddress()) ;}}public void programFunction(){System.out.println("****************************请求分页存储系统****************************");System.out.println("功能:");System.out.println("\t 1.查看页表");System.out.println("\t 2.查看快表");System.out.println("\t 3.查看外存");System.out.println("\t 4.在内存修改数据");System.out.println("\t 5.继续访问页面");System.out.println("\t 6.退出程序");}public void Dealfunction(int i,KShell TLB,Source s[],int b[]){ if(i==1){this.printPageShell();}else if(i==2){TLB.printKShell();}else if(i==3){System.out.println("外存:");System.out.println("外存地址\t"+"页号\t"+"数据\n");for(int k=0;k<20;k++){s[k].printSource(k);}}else if(i==4){String ch="yes";int pageNumb;Scanner a=new Scanner(System.in);System.out.print("请输入一个页号:");pageNumb=a.nextInt();int numb=this.searchpage(pageNumb);if(numb<0){System.out.println("内存中没有此页号");}else{this.Inchange(b, ch,numb);}}else if(i==6){System.out.println("结束程序");System.exit(0);}}public static void main(String[] args){Scanner a=new Scanner(System.in);int i,number=-10,k1,k2,result;int k3=0;//当前存储的内存地址int t;//页表中访问次数最小的索引int b[]=new int[10];//内存中存储的数据String ch;int slength,plength,Tlength,data;System.out.print("请输入外存大小:");slength=a.nextInt();System.out.print("请输入页表大小:");plength=a.nextInt();System.out.print("请输入快表大小:");Tlength=a.nextInt();//定义页表,快表,外存Shell pageshell=new Shell(plength);//页表Source s[]=new Source[slength];//外存KShell TLB=new KShell(Tlength);//快表System.out.println("产生一个随机序列作为外存数据!");//录入外存地址和数据for(i=0;i<slength;i++){data=(int)(100*Math.random());System.out.print(data+"\t");s[i]=new Source(i,data);System.out.println("\n外存设置成功");//请求页面do{//TLB.printKShell();//打印当前快表的情况//pageshell.printPageShell();//打印当前页表的情况System.out.println("请输入一个页面的页号(0-19):");k1=a.nextInt();if(k1>=20||k1<0){System.out.println("输入数据有错,将退出程序!!");System.exit(0);}//检测快表,快表存储当前的页表项,即当快表满时采用最近最久未被使用算法置换快表System.out.println("进入快表检测");if(TLB.getCurrent()>0){number=TLB.searchpage(k1);if(number!=-1&&number!=-2){result=b[TLB.shell[number].getPhysicsnumb()];System.out.println("在快表中找到,结果为:"+result);//找出该页号在页表中的位置并修改访问字段number=TLB.shell[number].getIndex();pageshell.shell[number].setVisitcount(pageshell.shell[number].getVisitc ount()+1);}}if(TLB.getCurrent()<=0||number==-1){System.out.println("在快表中找不到!"+"进入内存检测:");//在快表中找不到,去内存区的页表找if(pageshell.current>0){number=pageshell.searchpage(k1);//页号k1所在的下标if(number!=-1&&number!=-2){result=b[pageshell.shell[number].getPhysicsnumb()];System.out.println("在页表中找到,结果为:"+result);//修改访问字段和状态位pageshell.shell[number].setVisitcount(pageshell.shell[number].getVisitc ount()+1);//修改快表TLB.changeKShell(pageshell, number);}if(pageshell.current<=0||number==-1){System.out.println("在内存中找不到!!");System.out.println("从外存中调入内存:");//在页表找不到,去外存区找for(i=0;i<slength;i++){if(k1==s[i].getPagenumb()){//在外存找到了缺页k2=pageshell.Isover();if(k2==1){//内存已满t=pageshell.MinVisitcount();System.out.println("内存已满!即将调出页号"+pageshell.shell[t].getPagenumb());}else{t=pageshell.current;pageshell.setCurrent(pageshell.getCurrent()+1);}//判断是否修改了内存的数据if(pageshell.Ischange(t)==1){s[pageshell.shell[t].getCRTaddress()].setSts(b[pageshell.shell[t].getPh ysicsnumb()]);}//调入内存pageshell.shell[t].setPagenumb(k1);if(k2==1){b[pageshell.shell[t].getPhysicsnumb()]=s[i].getSts();}else{pageshell.shell[t].setPhysicsnumb(k3);//未满则设置物理块号,满了只改变其他5个字段b[k3]=s[i].getSts();k3++;//物理块号}pageshell.shell[t].setState(true);pageshell.shell[t].setVisitcount(1);pageshell.shell[t].setChange(false);pageshell.shell[t].setCRTaddress(i);System.out.println("调入内存成功!");//修改快表TLB.changeKShell(pageshell,t);System.out.println("修改快表成功!");System.out.println("结果为:"+b[k3-1]);break;}}}}do{pageshell.programFunction();System.out.print("请输入一个整数(1-6):");i=a.nextInt();while(i<1||i>6){System.out.println("输入有误,请重新输入(1-6):");i=a.nextInt();}pageshell.Dealfunction(i,TLB,s,b);}while(i!=5);/*System.out.println("是否继续请求访问页面(1 or 0):");i=a.nextInt();while(i!=1&&i!=0){System.out.println("输入有误,请重新输入(1 or 0):");i=a.nextInt();}*/}while(i==5);System.out.println("退出程序!");}}(4)KShell类:快表package homework;public class KShell {KPage shell[];private int current;private int length;private int changenumb;//修改快表的次数public KShell(){ };public KShell(int length){this.length=length;this.current=0;this.changenumb=0;shell=new KPage[length];for(int i=0;i<length;i++){this.shell[i]=new KPage();}public void setCurrent(int current){this.current=current;}public void setChangenumb(int changenumb){this.changenumb=changenumb;} public int getCurrent(){ return current;}public int getChangenumb(){return changenumb;}public int getLength(){ return length;}public int searchpage(int pagenumb){int i=0;if(this.changenumb==0&&this.current==0){return -2;}else if(this.changenumb<this.length){while(i<this.current){if(this.shell[i].getPagenumb()==pagenumb){return i;}i++;}return -1;}else{while(i<this.length){if(this.shell[i].getPagenumb()==pagenumb){return i;}i++;}return -1;}}public void changeKShell(Shell pageshell,int number){if(this.getChangenumb()>=this.getLength()){if(this.getCurrent()==this.getLength()){this.setCurrent(0);}System.out.println("快表已满,快表中即将调出页号"+this.shell[this.current].getPagenumb());}if(this.getCurrent()<this.getLength()){this.shell[this.getCurrent()].setIndex(number);this.shell[this.getCurrent()].setPagenumb(pageshell.shell[number].getPa genumb());this.shell[this.getCurrent()].setPhysicsnumb(pageshell.shell[number].ge tPhysicsnumb());this.setCurrent(this.getCurrent()+1);this.setChangenumb(this.getChangenumb()+1);}}public void printKShell(){System.out.println("快表:");System.out.println("索引\t"+"页号\t"+"物理块号\t"+"在页表下的索引");for(int i=0;i<this.length;i++){System.out.println(i+"\t"+this.shell[i].getPagenumb()+"\t"+this.shell[i ].getPhysicsnumb()+"\t"+this.shell[i].getIndex());}}}(5)Source类:外存package homework;public class Source {private int pagenumb;//页号private int sts; //数据int length;public Source(){}public Source(int pagenumb,int sts){this.pagenumb=pagenumb;this.sts=sts;}public void setPagenumb(int pagenumb){this.pagenumb=pagenumb;}public void setSts(int sts){this.sts=sts;}public int getPagenumb(){return this.pagenumb;}public int getSts(){return this.sts;}public void printSource(int i){System.out.println(i+"\t"+this.pagenumb+"\t"+this.sts+"\n");}}4.用户使用说明答:本程序是使用java语言编写的实现请求分页存储管理的程序,是在eclipise下运行的结果,只需运行Shell类就行了首先先设置外存,页表和快表的大小,然后输入一个请求访问的页面。
动态页式存储管理的模拟实现C语言
在内存划出一块区域,并进行页面划分;设计请求页表;模拟页面分配;分别模拟“先进先出页面淘汰算法FIFO”、“最近最少使用页面淘汰算法LRU”和“理想型淘汰算法OPT”本程序随机产生请求序列,分别模拟FIFO,LRU,OPT三种算法。
将结果保存在FIFO.txt,LRU.txt,OPT.txt三个文件中。
程序代码:#include<stdio.h>#include<stdlib.h>#include<time.h>#define N 20#define P 3struct DuLNode{int data;struct DuLNode *prior;struct DuLNode *next;};int pageFIFO[N+1];int front=0,rear=0;int pageing[N+1],pmem[P+1];int memcount=1;void init(int a[],int T){int i;for(i=0;i<=T;i++)a[i]=-2;}int insert_item(int item,int queue[],int T){if((rear+1)%(T+1)==front)return 1;queue[rear]=item;rear=(rear+1)%(T+1);return 0;}int remove_item(int *item,int queue[],int T){if(front == rear)return 1;*item=queue[front];front=(front+1) % (T+1);return 0;}int findif(int a[],int b,int T){int i;for(i=1;i<=T;i++){if(a[i]==b)return i;}return -1;}void insertintomem(int a[],int b,int n) {if(memcount<=P){a[memcount]=b;memcount++;}elsea[n]=b;}void initpage(int page[]){int temp,i;srand((unsigned)time(0));for(i=1;i<=N;i++){temp=rand()%10;page[i]=temp;}}void addtoLink(struct DuLNode *p,int e) {struct DuLNode *add;add=malloc(sizeof(struct DuLNode));add->data=e;add->prior=p->prior;p->prior->next=add;add->next=p;p->prior=add;}int getI(struct DuLNode *p,int e){struct DuLNode *cd=p;for(i=1;;i++){cd=cd->next;if(cd->data==e)return i;if(cd==p)return -1;}}void deleLink(struct DuLNode *p,int i,int *e) {int n;struct DuLNode *cd=p;for(n=1;n<=i;n++)cd=cd->next;*e=cd->data;cd->prior->next=cd->next;cd->next->prior=cd->prior;free(cd);}void removebottom(struct DuLNode *p,int *e) {struct DuLNode *cd=p->next;*e=cd->data;cd->next->prior=p;p->next=cd->next;free(cd);}int getcount(int a[],int b,int n,int T){int i;for(i=n;i<=T;i++){if(a[i]==b)return (i-n);}return -1;}void getreplacepage(int a[],int b[],int i,int *e) {int t,c[P+1],temp,T,count=0,error[P+1];for(t=1;t<=P;t++)if(getcount(a,b[t],i,N)!=-1)c[t]=getcount(a,b[t],i,N);else{error[++count]=b[t];}}if(count==0){temp=c[1];T=b[1];for(t=1;t<=P;t++){if(c[t]>temp){temp=c[t];T=b[t];}}*e=T;}else{for(t=1;t<=count;t++){c[t]=findif(a,error[t],N);}temp=c[1];T=error[1];for(t=1;t<=count;t++){if(c[t]<temp){temp=c[t];T=error[t];}}*e=T;}}void main(){int i,temp,temp1,error=0,ErrorC[P];FILE *fp1,*fp2,*fp3;struct DuLNode *p;p=(struct DuLNode *)malloc(sizeof(struct DuLNode));p->prior=p->next=p;initpage(pageing);init(pmem,P);if((fp1=fopen("FIFO.txt","a"))==NULL){printf("不能打开文件!\n");exit(1);}for(i=1;i<=N;i++){fprintf(fp1," %d ",pageing[i]);}fprintf(fp1,"\n");for(i=1;i<=N;i++){if(memcount>P&&findif(pmem,pageing[i],P)==-1){remove_item(&temp,pageFIFO,N);insertintomem(pmem,pageing[i],findif(pmem,temp,P));insert_item(pageing[i],pageFIFO,N);fprintf(fp1,"%d被引用,%d被替换->出现第%d 次错误!\n",pageing[i],temp,++error);}else{if(memcount<=P&&findif(pmem,pageing[i],P)==-1){insertintomem(pmem,pageing[i],memcount);insert_item(pageing[i],pageFIFO,N);fprintf(fp1,"页中未满。
请求页式管理实验报告
操作系统请求页式存储管理报告学院:班级:姓名:学号:请求页式存储管理一、问题描述设计一个请求页式存储管理方案,为简单起见。
页面淘汰算法采用 FIFO页面淘汰算法,并且在淘汰一页时,只将该页在页表中修改状态位。
而不再判断它是否被改写过,也不将它写回到辅存。
二、基本要求页面尺寸1K,输入进程大小(例如5300bytes),对页表进行初始化,页表结构:页号物理块号状态位0 2 True (在主存)1 12 False (在辅存)3 04 False (在辅存)5 False (在辅存)系统为进程分配3 个物理块(页框),块号分别为0、1、2,页框管理表(空闲块表):物理块号是否空闲0 true1 true2 true任意输入一个需要访问的指令地址流(例如:3635、3642、1140、0087、1700、5200、4355,输入负数结束),打印页表情况。
每访问一个地址时,首先要计算该地址所在的页的页号,然后查页表,判断该页是否在主存——如果该页已在主存,则打印页表情况;如果该页不在主存且页框未满,则调入该页并修改页表,打印页表情况;如果该页不在主存且页框已满,则按 FIFO页面淘汰算法淘汰一页后调入所需的页,修改页表,打印页表情况。
三、主要代码#include <stdio.h>#include <stdlib.h>#include <string.h>#define N 7#define q 3 //物理块个数#define p 6 //页面个数int JCsize=5300; //进程大小int Psize=1024; //页面长度int phb[q]={0}; //物理块标号int pro[N]={0}; //进程序列号int m = -1, n = -1; //物理块空闲和进程是否相同判断标志int i = 0, j = 0,k = 0; //i表示进程序列号,j表示物理块号int Q[q] = {0}; //进程等待次数(存放最久未被使用的进程标志) int max = -1,maxQ = 0; //标记替换物理块进程下标int count=0; //统计页面缺页次数struct Page{int Ynum; //页号int Wnum; //物理块号int P; //状态位int time; //记录调入内存时间};struct Phb{int Pnum; //物理块号int b; //是否空闲};void scan(struct Page *P,struct Phb *R) //输入页表和物理块页框初始化信息{int i;for(i=0;i<p;i++){P[i].Ynum=i;P[i].Wnum=-1;P[i].P=0;}for(i=0;i<q;i++){R[i].Pnum=i; R[i].b=0;}}void print_Page(struct Page *P,struct Phb *R){int n;printf("按1键打印输出物理块页框管理表如下所示:");scanf("%d",&n);printf("\n------------------------------------\n");if(n==1){printf("\t物理块号 \t是否空闲 \t");for(i=0;i<q;i++){printf("\t\t %d \t",R[i].Pnum);printf("\t\t %d \t",R[i].b);}printf("\n");}}void print(struct Page *P,struct Phb *R){int i,j;printf("\n按0键打印输出页表结构如下所示:");scanf("%d",&j);printf("\n---------------------------------------\n");if(j==0){printf("\t页号 \t物理块号 \t状态位 \t");for(i=0;i<p;i++){printf("\t\t %d ",P[i].Ynum);printf("\t %d ",P[i].Wnum);printf("\t %d \t",P[i].P);}printf("\n");}}int* listnumber(struct Page *P,struct Phb *R){int a[N];printf("请输入一个需要访问的指令地址流:\n"); for(i=0;i<N;i++){scanf("%d",&a[i]);if(a[i]>=0 && a[i]<=JCsize){pro[i]=a[i]/Psize; } elseprintf("访问指令不合理!结束访问");}printf("显示所输入地址流地址对应的页号分别为:");for(i=0;i<N;i++)printf("%d ",pro[i]);printf("\n");return (pro);}//查找空闲物理块int rsearchphb(struct Page *P,struct Phb *R){for(j=0; j<q; j++){if(phb[j] == 0){m = j;return m;break;}}return -1;}//查找相同进程int rsearchpage(struct Page *P,struct Phb *R){for(j = 0; j < q; j++) //物理块{if(phb[j]==pro[i]){n = j;return j; //第j块物理块中的进程与此同步}}return -1;}//FIFO算法void FIFO(struct Page *P,struct Phb *R){int t;for(i = 0; i<N; i++) //依次判断进程序列号{m=rsearchphb(P,R);n=rsearchpage(P,R); for(j = 0; j < q;j++){if(Q[j]>maxQ){maxQ = Q[j]; //进程等待次数最大值max = j; //物理块标号 }}if(n == -1) //该页不在主存中即:不存在相同进程 {if(m != -1) //该页不在主存中且页框未满时 {phb[m] = pro[i]; //进程号填入该空闲物理块count++; //页面缺页次数+1Q[m] = 0; //等待次数置为0for(t=0;t<p;t++) //改变页表结构{if(pro[i]==P[t].Ynum){P[t].Wnum=m;P[t].P=1;}}for(j = 0;j <= m; j++){Q[j]++; } //等待次数分别+1 m = -1;print(P,R); //打印页表结构}//该页不在主存且页框已满,执行FIFO淘汰算法else{phb[max] =pro[i];Q[max] = 0;for(t=0;t<p;t++){if(P[t].Wnum==max){P[t].Wnum=-1;P[t].P=0;}}for(t=0;t<p;t++){if(pro[i]==P[t].Ynum){P[t].Wnum=max;P[t].P=1; }}print(P,R);for(j = 0;j < q; j++){ Q[j]++; }max = -1;maxQ = 0;count++; }}else //该页在主存时打印页表情况{phb[n]=pro[i];for(j = 0 ;j <q; j++){ Q[j]++; }n=-1; print(P,R);}}printf("缺页次数为:%d\n",count); printf("\n");}void main(){struct Page P[p]; struct Phb R[q];printf("*****************************************\n");printf(" \n");printf(" |内存页面调度算法| \n");printf(" \n");printf("*****************************************\n");scan(P,R); print(P,R); print_Page(P,R);listnumber(P,R); FIFO(P,R);}。
请求分页存储管理模拟实验
操作系统模拟实验实验名称:请求分页存储管理模拟实验实验目的:通过实验了解windows系统中的线程同步如何使用,进一步了解操作系统的同步机制。
实验内容:调用Windows API,模拟解决生产者-消费者问题;思考在两个线程函数中哪些是临界资源?哪些代码是临界区?哪些代码是进入临界区?哪些代码是退出临界区?进入临界区和退出临界区的代码是否成对出现?学习Windows API中的如何创建线程,互斥,临界区等。
程序运行结果:源程序:#include "stdAfx.h"//包含头文件以支持多线程#include "windows.h"#include "stdio.h"//用于标志所有的子线程是否结束//每次子线程结束后,此值便加1。
static long ThreadCompleted = 0;//互斥量HANDLE mutex;//信号量,用于生产者通知消费者HANDLE full;//信号量,用于消费者通知生产者HANDLE empty;//信号量,当所有的子线程结束后,通知主线程,可以结束。
HANDLE evtTerminate;//生产标志#define p_item 1//消费标志#define c_item 0//哨兵#define END 10//缓冲区最大长度const int max_buf_size=11;const int cur_size=10;//缓冲区定义int BUFFER[max_buf_size];//放消息指针int in=0;//取消息指针int out=0;int front=0;int tail=0;int sleep_time=1000;bool flag=true;//线程函数的标准格式unsigned long __stdcall p_Thread(void *theBuf);unsigned long __stdcall c_Thread(void *theBuf);//打印缓冲区内容void PrintBuf(int buf[],int buf_size);int main(int argc, char* argv[]){//初始化缓冲区unsigned long TID1, TID2;for(int i=0;i<cur_size;i++)BUFFER[i]=0;//互斥量和信号量的创建,函数用法可查看MSDNmutex=CreateMutex(NULL,false,"mutex");full=CreateSemaphore(NULL,0,1,"full");empty=CreateSemaphore(NULL,max_buf_size,max_buf_size,"empty");evtTerminate = CreateEvent(NULL, FALSE, FALSE, "Terminate");//创建一个生产者线程和消费者线程。
- 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
- 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
- 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。
out->ReplaceSel(info);
switch (ptr_memAccReq.reqType){
case REQUEST_READ:
ptr_pageTabIt->count++;
if(!(ptr_pageTabIt->proType&READABLE)){
do_error(ERROR_READ_DENY);
do_init(){
int i,j;
srand(time(NULL));
for(i=0;i<PAGE_SUM;i++){
pageTable[i].pageNum=i;
pageTable[i].effective=mFALSE;
pageTable[i].modified=mFALSE;
pageTable[i].count=0;
CString info;
info.Format(_T("页面不在内存\n产生缺页中断,开始进行调页。。。\n"));
out->SetSel(-1, -1);
out->ReplaceSel(info);
for(i=0;i<BLOCK_SUM;i++){
if(!blockStatus[i])//有空闲页面
out->SetSel(-1, -1);
out->ReplaceSel(info);
ptr_pageTabIt=&pageTable[pageNum];
if(!ptr_pageTabIt->effective)
do_page_fault(ptr_pageTabIt);
else {
info.Format(_T("页面在内存,不用调页\n"));
out->SetSel(-1, -1);
out->ReplaceSel(info);
if(pageTable[page].modified){
info.Format(_T("有修改,写回至外存\n"));
out->SetSel(-1, -1);
out->ReplaceSel(info);
do_page_out(&pageTable[page]);
}
pageTable[page].effective=FALSE;//修改被淘汰页的页表
pageTable[page].count=0;
pageTable[page].modified=FALSE;
pageTable[page].blockNum=0;
do_page_in(ptr_pageTabIt,j);
Ptr_PageTableItem ptr_pageTabIt;
unsigned int pageNum,offAddr;
unsigned int actAddr;
CString info;
if(ptr_memAccReq.virAddr<0||ptr_memAccReq.virAddr>=VIRTUAL_MEMORY_SIZE){
out->SetSel(-1, -1);
out->ReplaceSel(info);
}
actAddr=ptr_pageTabIt->blockNum*PAGE_SIZE+offAddr;
info.Format(_T("实地址为:%u\n"),actAddr);
out->SetSel(-1, -1);
break;
case 6:
pageTable[i].proType=READABLE|WRITABLE| EXECUTABLE;
break;
default:
break;
pageTable[i].auxAddr = i*PAGE_SIZE*2;//逻辑页的外存址
}
for (j=0;j<BLOCK_SUM;j++)//内存物理页的初始化
do_error(ERROR_OVER_BOUNDARY);
return;
}
pageNum=ptr_memAccReq.virAddr/PAGE_SIZE;
offAddr=ptr_memAccReq.virAddr%PAGE_SIZE;
info.Format(_T("页号:%u\t页内偏移:%u\n\n"),pageNum,offAddr);
unsigned int i,min,page,j;
CString info;
info.Format(_T("没有空闲页面,开始LFU页面置换。。。\n"));
out->SetSel(-1, -1);
out->ReplaceSel(info);
for(i=0,min=0xFFFFFFFF,page=0;i<PAGE_SUM ;i++){//找到count最小的页
ptr_memAccReq.reqType=REQUEST_EXECUTE;
info.Format(_T("\n产生请求:\n类型:执行\t"));
out->SetSel(-1, -1);
out->ReplaceSel(info);
break;
default:
break;
}
}
do_response(){
break;
case REQUEST_EXECUTE:
ptr_pageTabIt->count++;
if(!(ptr_pageTabIt->proType&EXECUTABLE)){
do_error(ERROR_EXECUTE_DENY);
return ;
}
info.Format(_T("执行成功\n"));
do_error(ERROR_WRITE_DENY);
return ;
}
actMem[actAddr]=ptr_memAccReq.value;
ptr_pageTabIt->modified=TRUE;
info.Format(_T("写操作成功\n"));
out->SetSel(-1, -1);
out->ReplaceSel(info);
{
info.Format(_T("有空闲页面\n"));
out->SetSel(-1, -1);
out->ReplaceSel(info);
do_page_in(ptr_pageTabIt,i);
ptr_pageTabIt->blockNum=i;
ptr_pageTabIt->effective=TRUE;
ptr_pageTabIt->modified=FALSE;
ptr_pageTabIt->count=0;
blockStatus[i]=TRUE;
return;
}
}
do_LFU(ptr_pageTabIt);
}
//LFU
void CManager::do_LFU(Ptr_PageTableItem ptr_pageTabIt){
if(pageTable[i].count<min && pageTable[i].effective==TRUE){
min=pageTable[i].count;
j=pageTable[i].blockNum;//获得的物理块号
page=i;//要淘汰页的页号
}
}
info.Format(_T("选择页面%u进行替换\n"),j);
switch(rand()%7){
case 0:
pageTable[i].proType=READABLE;
break;
case 1:
pageTable[i].proType=WRITABLE;
break;
case 2:
pageTable[i].proType=EXECUTABLE;
break;
case 3:
ptr_pageTabIt->blockNum=j;//修改调入页的页表项
ptr_pageTabIt->effective=TRUE;
ptr_pageTabIt->count=0;
info.Format(_T("页面替换成功\n"));
out->SetSel(-1, -1);
out->ReplaceSel(info);
pageTable[i].proType=READABLE | WRITABLE;
break;
case 4:
pageTable[i].proType=READABLE | EXECUTABLE;
break;
case 5:
pageTable[i].proType=WRITABLE | EXECUTABLE;
return ;
}
info.Format(_T("读操作成功:值为%02X\n"),actMem[actAddr]);
out->SetSel(-1, -1);
out->ReplaceSel(info);
break;
case REQUEST_WRITE:
ptr_pageTabIt->count++;
if(!(ptr_pageTabIt->proType&WRITABLE)){