当前位置:文档之家› 操作系统存储器管理

操作系统存储器管理

存储器管理(固定分区、可变分区与分页式分配算法)一、目的本课题实验的目的是,使学生实验存储器管理系统的设计方法;加深对所学各种存储器管理方案的了解;要求采用一些常用的存储器分配算法,设计一个存储器管理模拟系统并调试运行。

二、实验内容模拟固定分区分内存的动态分配和回收,并编程实现。

三、要求及提示(1)建立相关的数据结构,作业控制块、已分配分区及未分配分区(2)实现一个固定分区分配算法(实现多个分区只设置一个后备作业队列, 而每个分区设置一个后备作业队列 ,留给大家实现)(3)实现一个分区回收算法(4)要求采用一种常用的存储器分配算法,设计一个存储器管理模拟系统。

允许进行多次的分配和释放,并可向用户反馈分配和释放情况及当前内存的情况;采用“命令菜单”选择和键盘命令输入的会话方式,根据输入请求调用分配模块,或回收模块,或内存查询模块,或最终退出系统。

(5)编程实现。

(6)工具:C语言或其它高级语言四、实验报告1、列出调试通过程序的清单,并附上文档说明。

2、总结上机调试过程中所遇到的问题和解决方法及感想。

五参考代码:// memdos.cpp : 定义控制台应用程序的入口点。

//以下代码为4种分区,8K分区四块,16K分区3块,32分区2块, 64分区1块, 共10块#include "stdafx.h"#include <string.h>#include <stdlib.h>//#include <conio.h>#define TRUE 1#define FALSE 0void InitCSolid( );void ExitSolid();int MallocArea(int nSize,char* sName);//申请一个分区函数int FreeArea(char *sName); //释放一个分区函数void ShowArea( );//显示所有分区状态函数{char *pmem; //每分区内存的起始地址int size; // 每分区的大小int useSize; //已使用大小,若为0 ,表示此分区尚未使用char jobName[20]; //此分区的作业(进程)名};int nSizes[4];//共4种分区,每种分区的大小为 8k,16k,32k,64k ,每K为1024字节char *pmems; //起始分区内存地址Solid *psolids;int snum; //定义总的内存分区数int main( ){int jobCount=1; //已申请的作业个数char str[100];char jobName[14];int nSize; //申请的作业大小InitCSolid( ); //初始化数据while(1){ShowArea( ); //显示内存的分配与使用情况printf(" 固定分区内存管理\n x退出 1申请内存 2释放内存\n");scanf("%s",str);if(strlen(str)!=1) continue;if(str[0]=='x' || str[0]=='X')break; //退出if(str[0]=='1') //申请内存while(1){printf("请输入申请内存的大小 (按x退出,按0返回上一级): ");scanf("%s",str);if(strlen(str)==1){if(str[0]=='x' || str[0]=='X')goto exit; // 退出if(str[0]=='0')break; //返回上一级}nSize=atoi(str);//获取申请的内存大小 (atoi函数功能为字符串转换成数字类型)if(nSize<=0) { printf("输入错误! ");continue;}sprintf(jobName,"作业%03d",jobCount); //自动定义一个作业名if( !MallocArea(nSize,jobName)) //分配内存,并判断是否成功{printf( "申请内存大小为%d,但没有空间可分配,请重新输入\n",nSize);}jobCount++; //已申请的作业个数ShowArea(); //显示内存的分配与使用情况}if(str[0]=='0')continue; //返回上一级}if(str[0]=='2') //释放内存{printf("请输入释放内存的作业名 (按x退出,按0返回上一级): ");while(1)scanf("%s",str);if(strlen(str)==1){if(str[0]=='x' || str[0]=='X')goto exit; // 退出if(str[0]=='0')break; //返回上一级}if(strlen(str)==3)sprintf(jobName,"作业%s",str); //获取作业名else strcpy(jobName,str);if(FreeArea(jobName)) //根据作业名释放内存,并判断是否释放成功{printf("已释放%s所占用的内存\n\n\n",str);ShowArea();printf("请输入释放内存的作业名 (按x退出,按0返回上一级): ");}else printf("无此作业,请重新输入释放内存的作业名 (按x退出,按0返回上一级): ");}if(str[0]=='0')continue;}}exit:ExitSolid(); //释放资源////getchar();return 0;}void InitCSolid( ) //生成初始数据{//this->snum=sNum;int i,ntotalSize=0;snum=10; //总共分成10分区psolids=(Solid *)malloc(sizeof(Solid)*snum); //new Solid[snum];//申请堆内存nSizes[0]=8192;nSizes[1]=16384;nSizes[2]=32768;nSizes[3]=65536; //nSizes[4]=165536;psolids[0].size=nSizes[0]; psolids[0].useSize=0; //其中8K分区4块,并设置其大小与使用标志为0, 表示未使用psolids[1].size=nSizes[0]; psolids[1].useSize=0;psolids[2].size=nSizes[0]; psolids[2].useSize=0;psolids[3].size=nSizes[0]; psolids[3].useSize=0;psolids[4].size=nSizes[1]; psolids[4].useSize=0; //其中16K分区3块psolids[5].size=nSizes[1]; psolids[5].useSize=0;psolids[6].size=nSizes[1]; psolids[6].useSize=0;psolids[7].size=nSizes[2]; psolids[7].useSize=0;//其中32K分区2块psolids[8].size=nSizes[2]; psolids[8].useSize=0;psolids[9].size=nSizes[3]; psolids[9].useSize=0; //其中64K分区1块for(i=0;i<snum;i++)ntotalSize+=psolids[i].size; //获取总的内存大小pmems=(char *)malloc(ntotalSize);psolids[0].pmem=pmems; //设置每分区的起始地址for(i=1;i<snum;i++){psolids[i].pmem=psolids[i-1].pmem +psolids[i-1].size;}}void ExitSolid() //释放// delete []psolids;free(psolids);//释放内存free(pmems);}//申请内存函数,参数nrSize为要申请的内存大小,参数sName为申请的作业名称,申请成功返回TRUE, 否则返回FALSEint MallocArea(int nrSize,char *sName){int i;for(i=0;i<4;i++){if(nrSize>nSizes[i]) continue; //根据要申请的nrSize内存大小,判断落在哪个分区(8k,16k,32k,64k分区)break;}if(i==4) return false; //申请的nrSize内存太大,没有大内存分配int n=i; //记住要分配的分区//循环查找可用分区for(i=0;i<snum;i++){if(psolids[i].size<nSizes[n]) //找出分区位置continue;if(psolids[i].useSize!=0) //此分区块已分配出去否?continue; //是,寻找下一分区块psolids[i].useSize=nrSize; //否,分配此块分区strcpy(psolids[i].jobName,sName);//保存作业名}if(i==snum)return FALSE; //申请不成功return TRUE;//申请成功}//根据作业名释放内存,找到作业名并成功释放返回TRUE ,否则返回FALSEint FreeArea(char *sName){int i;for(i=0;i<snum;i++){if( strcmp(sName,psolids[i].jobName)==0) //是否由此作业名?if(psolids[i].useSize!=0){psolids[i].useSize=0; //是 ,释放内存,即设置此块分区为未使用 return TRUE;}}return FALSE;}void ShowArea( )//显示{int i=0;printf("\n");for(i=0;i<snum;i++) //循环显示每一块分区的状态{if(psolids[i].useSize==0) //此分区块是否已使用printf("空闲区间起始地址%dK \t内存大小%dK\n", (psolids[i].pmem - psolids[0].pmem)/1024 ,psolids[i].size/1024 );}else { //是printf("%s 起始地址%dK \t内存大小%dK 已使用%dK%d字节\n",psolids[i].jobName, (psolids[i].pmem - psolids[0].pmem)/1024, psolids[i].size/1024,psolids[i].useSize/1024,psolids[i].useSize%1024 );}}printf("\n");}。

相关主题