📄 os.cpp
字号:
//存储器管理系统设计
#include <iostream>
using namespace std;
const int pagesize=1024;
//页面大小
const int blocknum=4;
//系统分配的物理块数
int block[blocknum];
//存放物理块状态的数组,空闲时为1,不空闲时为0
int pg[blocknum];
//存放物理块中的页号
class page
{
int pno; //页号
int bno; //物理块号
int status;
//页的状态,1为在主存,0为在辅存
static int n; //表态成员,为实现页的编号
public:
page() //构造函数
{
pno=n++; //编号
bno=-1; //不在任何物理块中
status=0; //初始值
}
int getstatus()
{ return status; }
int getbno()
{ return bno; }
int getpno()
{ return pno; }
void print()
{
cout<<"页号:"<<pno<<" 地址范围:"<<pagesize*pno+1<<"~"<<pagesize*(pno+1)<<" 物理块号:"<<bno<<" 状态:";
if(status)
cout<<"在主存"<<endl;
else
cout<<"在辅存"<<endl;
}
void load(int b) //装入主存b号物理块
{
bno=b;
status=1; //装入主存页号为1
block[b]=0; //数组状态不空闲
}
//调出主存,用于页面置换
void out()
{ status=0;
bno=-1; //相应页对应物理块号变为初始值
}
};
int page::n=0; //初始化页号
int freebno() //查出空闲的物理块号
{
int i;
for(i=0;i<blocknum;i++)
if(block[i])
return i; //返回空闲的物理块
return i; //没有空闲的物理块,返回的块号溢出
}
void inc(int &t) //以物理块数为模自加
{
if(t>=0&&t<blocknum-1)
t++;
else if(t==blocknum-1)
t=0;
else
cout<<"出错!!"<<endl;
}
//判断是否在物理块的最后一位,是否加1
int add(int m,int n) {
if(m%n) //不能整除,有余数,则需加1
return 1;
else //刚好能整除
return 0;
}
void main()
{
int j;
for(j=0;j<blocknum;j++) //初始化,物理块都置为空闲
{
block[j]=1;
pg[j]=-1;
}
int i,set;
int process_size,pagenum,address,pageNO;
page *p;
int next=0; //下一个该替换的物理块号
cout<<"************************存储器管理模拟系统*************************"<<endl;
cout<<"请输入进程的大小(注意:仅为数据有效):"<<endl;
cin>>process_size;
pagenum=process_size/pagesize+add(process_size,pagesize);
cout<<"进程的页数为:"<<pagenum<<endl;
p=new page[pagenum]; //new动态分配空间
cout<<"各页面状态如下:"<<endl;
for(i=0;i<pagenum;i++)
p[i].print();
while(1)
{
cout<<"--------------------------------------------------------------"<<endl;
cout<<"1.指令地址信息读取 2.输出程序所用页面信息 3.快表信息 0.退出"<<endl;
cout<<endl;
cout<<"请选择相应操作:"<<endl;
cin>>set;
switch(set)
{
case 1:
cout<<"请输入要读入的指令地址:"<<endl;
cin>>address;
if(address<0)
{
cout<<"您所输入的是负数,不符合要求。"<<endl;
break;
}
else
if(address>process_size)
{
cout<<"您输入的数据太大,不符合要求。"<<endl;
break;
}
else
if(address<pagesize)
pageNO=0; //判定指令地址页面号
else
pageNO=address/pagesize+add(address,pagesize)-1;
//因为数组从0开始计数,故减1
if(p[pageNO].getstatus())
//判断是否在主存
{
cout<<"此模块已在主存中."<<endl;
p[pageNO].print();
}
else
{
cout<<"此模块在辅存中,调入主存."<<endl;
int fno;
fno=freebno(); //获取空闲的物理块号
if(fno>=0&&fno<blocknum) //有空闲物理块
{
p[pageNO].load(fno);
cout<<"装入页框表,查询并放入空闲物理块:"<<fno<<endl;
pg[fno]=pageNO;
p[pageNO].print();
}
//物理块已满,执行淘汰操作
else
{
cout<<"页框已满,淘汰物理块:"<<next<<" 中的原有页面 "<<pg[next]<<endl;
for(i=0;i<pagenum;i++)
if(p[i].getstatus()&&p[i].getbno()==next)
p[i].out(); //换出
p[pageNO].load(next); //装入
pg[next]=pageNO;
p[pageNO].print();
inc(next); //next自加,指向下一个即将换出的块
}
}
break;
case 2:
for(i=0;i<pagenum;i++)
p[i].print();
break;
case 3:
for(i=0;i<4;i++)
{
cout<<i<<":";
if(block[i])
cout<<" 空闲"<<endl;
else
{
cout<<" 占用 ";
int a=pg[i];
cout<<"页号:"<<a<<" 地址范围:"<<pagesize*a+1<<"~"<<pagesize*(a+1)<<endl;
}
}
break;
case 0:
delete []p; //释放资源
return;
default:cout<<"非法操作,请根据提示选择 1、2、3或0操作 "<<endl;
}
}
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -