操作系统课程设计报告基于时间片的轮转调度算法Word格式.docx
《操作系统课程设计报告基于时间片的轮转调度算法Word格式.docx》由会员分享,可在线阅读,更多相关《操作系统课程设计报告基于时间片的轮转调度算法Word格式.docx(46页珍藏版)》请在冰豆网上搜索。
处理机调度的效率甚至可能成为提高计算机处理速度的瓶颈。
处理机调度就是对系统的资源做出合理的分配,因而,提高处理机的调度算法也变得尤为重要。
1.2目的和意义
在多道程序设计系统中,内存中有多道程序运行,他们相互争夺处理机这一重要的资源。
处理机调度就是从就绪队列中,按照一定的算法选择一个进程并将处理机分配给它运行,以实现进程并发地执行。
一般情况下,当占用处理机的进程因为某种请求得不到满足而不得不放弃CPU进入等待状态时,或者当时间片到,系统不得不将CPU分配给就绪队列中另一进程的时候,都要引起处理机调度。
除此之外,进程正常结束、中断处理等也可能引起处理机的调度。
因此,处理机调度是操作系统核心的重要组成部分,它的主要功能如下:
记住进程的状态,如进程名称、指令计数器、程序状态寄存器以及所有通用寄存器等现场信息,将这些信息记录在相应的进程控制块中;
根据一定的算法,决定哪个进程能获得处理机,以及占用多长时间;
收回处理机,即正在执行的进程因为时间片用完或因为某种原因不能再执行的时候,保存该进程的现场,并收回处理机。
1.3调度算法发展过程
调度算法[1]是根据系统的资源分配策略所规定的资源分配算法。
对于不同的的系统和系统目标,通常采用不同的调度算法,例如,在批处理系统中,为了照顾为数众多的段作业,应采用短作业优先的调度算法;
又如在分时系统中,为了保证系统具有合理的响应时间,应当采用轮转法进行调度。
目前存在的多种调度算法中,有的算法适用于作业调度,有的算法适用于进程调度;
但也有些调度算法既可以用于作业调度,也可以用于进程调度。
各种调度算法都有其具有的优点和缺点。
因此,在这里便要对一种结合了多种算法的具有极强的适应性的调度算法—基于优先级的时间片调度算法作研究。
1)FCFS(Firstcomefirstserve),或者称为FIFO算法,先来先处理。
这个算法的优点是简单,实现容易,并且似乎公平;
缺点在于短的任务有可能变的非常慢,因为其前面的任务占用很长时间,造成了平均响应时间非常慢。
2)时间片轮询算法,这是对FIFO算法的改进,目的是改善短程序(运行时间短)的响应时间,其方法就是周期性地进行进程切换。
这个算法的关键点在于时间片的选择,时间片过大,那么轮转就越接近FIFO,如果太小,进程切换的开销大于执行程序的开销,从而降低了系统效率。
因此选择合适的时间片就非常重要。
选择时间片的两个需要考虑的因素:
一次进程切换所使用的系统消耗以及我们能接受的整个系统消耗、系统运行的进程数。
时间片轮询看上起非常公平,并且响应时间非常好,然而时间片轮转并不能保证系统的响应时间总是比FIFO短,这很大程度上取决于时间片大小的选择,以及这个大小与进程运行时间的相互关系。
3)STCF算法(Shorttimetocompletefirst),顾名思义就是短任务优先算法。
这种算法的核心就是所有的程序都有一个优先级,短任务的优先级比长任务的高,而OS总是安排优先级高的进程运行。
STCF又分为两类:
非抢占式和抢占式。
非抢占式STCF就是让已经在CPU上运行的程序执行到结束或者阻塞,然后在所有的就绪进程中选择执行时间最短的来执行;
而抢占式STCF就不是这样,在每进来一个新的进程时,就对所有进程(包括正在CPU上执行的进程)进行检查,谁的执行时间短,就运行谁。
STCF总是能提供最优的响应时间,然而它也有缺点,第一可能造成长任务的程序无法得到CPU时间而饥饿,因为OS总是优先执行短任务;
其次,关键问题在于我们怎么知道程序的运行时间,怎么预测某个进程需要的执行时间?
通常有两个办法:
使用启发式方法估算(例如根据程序大小估算),或者将程序执行一遍后记录其所用的CPU时间,在以后的执行过程中就可以根据这个测量数据来进行STCF调度。
4)优先级调度,STCF遇到的问题是长任务的程序可能饥饿,那么优先级调度算法可以通过给长任务的进程更高的优先级来解决这个问题;
优先级调度遇到的问题可能是短任务的进程饥饿,这个可以通过动态调整优先级来解决。
实际上动态调整优先级(称为权值)+时间片轮询的策略正是linux的进程调度策略之一的SCHED_OTHER分时调度策略,它的调度过程如下:
(1)创建任务指定采用分时调度策略,并指定优先级nice值(-20~19)。
(2)将根据每个任务的nice值确定在cpu上的执行时间(counter)。
(3)如果没有等待资源,则将该任务加入到就绪队列中。
(4)调度程序遍历就绪队列中的任务,通过对每个任务动态优先级的计算(counter+20-nice)结果,选择计算结果最大的一个去运行,当这个时间片用完后(counter减至0)或者主动放弃cpu时,该任务将被放在就绪队列末尾(时间片用完)或等待队列(因等待资源而放弃cpu)中。
(5)此时调度程序重复上面计算过程,转到第4步。
(6)当调度程序发现所有就绪任务计算所得的权值都为不大于0时,重复第2步。
linux还有两个实时进程的调度策略:
FIFO和RR,实时进程会立即抢占非实时进程。
5)显然,没有什么调度算法是毫无缺点的,因此现代OS通常都会采用混合调度算法。
例如将不同的进程分为几个大类,每个大类有不同的优先级,不同大类的进程的调度取决于大类的优先级,同一个大类的进程采用时间片轮询来保证公平性。
6)其他调度算法,保证调度算法保证每个进程享用的CPU时间完全一样;
彩票调度算法是一种概率调度算法,通过给进程“发彩票”的多少,来赋予不同进程不同的调用时间,彩票调度算法的优点是非常灵活,如果你给短任务发更多“彩票”,那么就类似STCF调度,如果给每个进程一样多的“彩票”,那么就类似保证调度;
用户公平调度算法,是按照每个用户,而不是按照每个进程来进行公平分配CPU时间,这是为了防止贪婪用户启用了过多进程导致系统效率降低甚至停顿。
7)实时系统的调度算法,实时系统需要考虑每个具体任务的响应时间必须符合要求,在截止时间前完成。
(1)EDF调度算法,就是最早截止任务优先(Earliestdeadlinefirst)算法,也就是让最早截止的任务先做。
当新的任务过来时,如果它的截止时间更靠前,那么就让新任务抢占正在执行的任务。
EDF算法其实是贪心算法的一种体现。
如果一组任务可以被调度(也就是所有任务的截止时间在理论上都可以得到满足),那么EDF可以满足。
如果一批任务不能全部满足(全部在各自的截止时间前完成),那EDF满足的任务数最多,这就是它最优的体现。
EDF其实就是抢占式的STCF,只不过将程序的执行时间换成了截止时间。
EDF的缺点在于需要对每个任务的截止时间做计算并动态调整优先级,并且抢占任务也需要消耗系统资源。
因此它的实际效果比理论效果差一点。
(2)RMS调度算法,EDF是动态调度算法,而RMS(ratemonotonicscheduling)算法是一种静态最优算法;
该算法在进行调度前先计算出所有任务的优先级,然后按照计算出来的优先级进行调度,任务执行中间既不接收新任务,也不进行优先级调整或者CPU抢占。
因此它的优点是系统消耗小,缺点就是不灵活了。
对于RMS算法,关键点在于判断一个任务组是否能被调度,这里有一个定律,如果一个系统的所有任务的CPU利用率都低于ln2,那么这些任务的截止时间均可以得到满足,ln2约等于0.693147,也就是此时系统还剩下有30%的CPU时间。
这个证明是Liu和Kayland在1973年给出的。
1.4使用到的开发工具
在本次课程设计中,我们选择了C++语言作为我们所使用的开发语言,开发工具则选用了MicrosoftVisualC++6.0。
MFC借助C++的优势为Windows开发开辟了一片新天地,同时也借助ApplicationWizzard使开发者摆脱离了那些每次都必写基本代码,借助ClassWizard和消息映射使开发者摆脱了定义消息处理时那种混乱和冗长的代码段。
更重要的是利用C++的封装功能使开发者摆脱Windows中各种句柄的困扰,只需要面对C++中的对象,这样一来使开发更接近开发语言而远离系统。
正因为MFC是建立在C++的基础上,所以我强调C/C++语言基础对开发的重要性。
利用C++的封装性开发者可以更容易理解和操作各种窗口对象;
利用C++的派生性开发者可以减少开发自定义窗口的时间和创造出可重用的代码;
利用虚拟性可以在必要时更好的控制窗口的活动。
而且C++本身所具备的超越C语言的特性都可以使开发者编写出更易用,更灵活的代码。
MicrosoftVisualC++6.0[2]:
VisualC++6.0,简称VC或者VC6.0,是微软推出的一款C++编译器,将“高级语言”翻译为“机器语言(低级语言)”的程序。
VisualC++是一个功能强大的可视化软件开发工具。
自1993年Microsoft公司推出VisualC++1.0后,随着其新版本的不断问世,VisualC++已成为专业程序员进行软件开发的首选工具。
虽然微软公司推出了VisualC++.NET(VisualC++7.0),但它的应用有很大的局限性,只适用于Windows2000、WindowsXP和WindowsNT4.0。
所以实际中,更多的是以VisualC++6.0为平台。
1.4.1特色
VisualC++6.0由Microsoft开发,它不仅是一个C++编译器,而且是一个基于Windows操作系统的可视化集成开发环境(integrateddevelopmentenvironment,IDE)。
VisualC++6.0由许多组件组成,包括编辑器、调试器以及程序向导AppWizard、类向导ClassWizard等开发工具。
这些组件通过一个名为DeveloperStudio的组件集成为和谐的开发环境。
Microsoft的主力软件产品。
虽然微软公司推出了VisualC++.NET(VisualC++7.0),但它的应用的很大的局限性,只适用于Windows2000,WindowsXP和WindowsNT4.0。
VisualC++6.0以拥有“语法高亮”,自动编译功能以及高级除错功能而著称。
比如,它允许用户进行远程调试,单步执行等。
还有允许用户在调试期间重新编译被修改的代码,而不必重新启动正在调试的程序。
其编译及创建预编译头文件(stdafx.h)、最小重建功能及累加连结(link)著称。
这些特征明显缩短程序编辑、编译及连结的时间花费,在大型软件计划上尤其显著。
1.4.2缺点
由于C++是由C语言发展起来的,也支持C语言的编译。
6.0版本是使用最多的版本,很经典。
最大的缺点是对于模版的支持比较差。
现在最新补丁为SP6,推荐安装,否则易出现编译时假死状态。
仅支持Windows操作系统。
目前发现与windows7兼容性不好,安装成功后可能会出现无法打开cpp文件的现象。
现在的最新版C++编译器集合在MicrosoftVisualStudio2010软件里面,包含C++,Visualbasic,C#,J#,.net。
等,其中,VC开发环境的版本已经升级至MicrosoftVisualC++2010,对C++的支持更加全面稳定,建议电脑性能好的可以使用此版本。
目前微软公司已经停止对VC++6.0系列产品的维护,继而转向.NET平台环境,新的MS2008、MS2010等将更符合新世纪通用开发需求。
不要随便加空行!
!
2需求分析
2.1需求背景
无论是在批处理系统还是分时系统中,用户进程数一般都多于处理机数、这将导致它们互相争夺处理机。
另外,系统进程也同样需要使用处理机。
这就要求进程调度程序按一定的策略,动态地把处理机分配给处于就绪队列中的某一个进程,以使之执行。
众所周知,现在的操作系统都是多任务的操作系统,实际上并不是真正同时运行多个进程,只不过是进程在频繁切换,而这种切换用户基本上感觉不到,进程调度就是操作系统来完成的。
当以下情况出现时需要操作系统来调度进程:
时间片到,即每个进程所分配的时间片用完后,要跳转到调度程序;
占用CPU的当前运行进程提出I/O操作,发起对内核的系统调用时,在系统调用结束后,跳转到调度程序;
当前运行进程对所有内核系统调用的结束时都要跳转到调度程序,根据当前的调度信息来决定下一个可以占用CPU的进程。
然而进程调度的实现需要一系列的算法。
如短作业优先调度算法,但该算法仅照顾了短作业而忽略了长进程,而且如果并未指明进程的长度,则短进程优先和基于进程长度的抢占式调度算法都将无法使用。
在早期的时间片轮转算法[3]中,系统将所有的就绪进程按先来先服务的原则排成一个队列,每次调度时,把CPU分配给队首进程,并令其执行一个时间片。
时间片的大小从几ms到几百ms。
当执行的时间片用完时,由一个计时器发出时钟中断请求,调度程序便据此信号来停止该进程的执行,并将它送往就绪队列的末尾;
然后,再把处理机分配给就绪队列的队首进程,同时也让它执行一个时间片。
这样就可以保证就绪队列中的所有进程在一给定的时间内均能获得一时间的处理机执行时间。
换言之,系统能在给定的时间内响应所有用户的请求。
但该算法存在未考虑优先级的不足。
而基于时间片的高优先级调度算法则不必事先知道各种进程所需的执行时间,而且还可以满足各种类型进程的需要。
本次试验就是依据该算法的原理进行设计的。
首先设置多个就绪队列并为各个队列赋予不同的优先级,第一个队列的优先级最高,依次降低;
当新进程进入内存后将其放入第一队列的队尾,然后再按先来先服务的原则排队等待调度;
仅当第一个队列为空闲时,调度程序才调度第二队列中的进程运行。
根据分析,得到如下结果:
(1)系统组成
系统由虚拟内核(VKernel)、命令解释程序(Commander)、用户程序(Application)、编译器(Compiler)四部分组成。
VKernel首先运行,并常驻内存。
Kernel启动后,创建Commander进程。
根据用户请求创建多个Application进程。
Kernel负责维护6个数据结构,包括时间(Time),处理器状态(CPUstate),进程表(PCBTable),就绪队列(ReadyState),等待队列(BlockedState),运行进程(RunningState)。
Time是系统时间片。
CPUstate应包括程序计数器PC,累加器A、B,状态寄存器F的值。
PCBTable的每一项是一个进程的进程控制块(PCB)。
Commander程序、Application程序是用下列CPU虚拟指令书写的程序:
#include<
stdio.h>
/*定义头文件(本程序自带的)*
stdlib.h>
string.h>
math.h>
typedefstructnode/*进程节点信息*/
{
charname[20];
/*进程的名字*/
intprio;
/*进程的优先级*/
intround;
/*分配CPU的时间片*/
intcputime;
/*CPU执行时间*/
intneedtime;
/*进程执行所需要的时间*/
charstate;
/*进程的状态,W--就绪态,R--执行态,F--完成态*/
intcount;
/*记录执行的次数*/
structnode*next;
/*链表指针*/
}PCB;
typedefstructQueue/*多级就绪队列节点信息*/
PCB*LinkPCB;
/*就绪队列中的进程队列指针*/
/*本就绪队列的优先级*/
/*本就绪队列所分配的时间片*/
structQueue*next;
/*指向下一个就绪队列的链表指针*/
}ReadyQueue;
PCB*run=NULL,*finish=NULL;
/*定义三个队列,就绪队列,执行队列和完成队列*/
ReadyQueue*Head=NULL;
/*定义第一个就绪队列*/
intnum;
/*进程个数*/
intReadyNum;
/*就绪队列个数*/
voidOutput();
/*进程信息输出函数*/
voidInsertFinish(PCB*in);
/*将进程插入到完成队列尾部*/
voidInsertPrio(ReadyQueue*in);
/*创建就绪队列,规定优先数越小,优先级越低*/
voidPrioCreate();
/*创建就绪队列输入函数*/
voidGetFirst(ReadyQueue*queue);
/*取得某一个就绪队列中的队头进程*/
voidInsertLast(PCB*in,ReadyQueue*queue);
/*将进程插入到就绪队列尾部*/
voidProcessCreate();
/*进程创建函数*/
voidRoundRun(ReadyQueue*timechip);
/*时间片轮转调度算法*/
voidMultiDispatch();
/*多级调度算法,每次执行一个时间片*/
(2)命令解释程序
命令解释程序从标准输入重复读入用户命令,然后以消息形式发送给内核。
命令解释程序处理的命令由设计者定义并实现。
(3)编译器
编译器把虚拟指令和虚拟系统调用编译为可执行字节码。
可执行字节码由内核解释执行。
2.2课程设计任务
1)设计进程控制块;
2)设计优先级对应的时间片;
3)实现高优先级非抢占式调度算法;
4)实现时间片轮转调度算法;
5)实现基于高优先级的时间片轮转算法。
2.2.1课题目的
1)理解进程调度相关理论;
2)掌握时间片调度原理;
3)掌握高优先级调度原理。
2.2.2课题内容
1)设计进程控制块;
2)设计多个进程队列;
3)设计多个进程;
4)动态生成时间片、执行时间和优先级;
5)设计基于时间片的多优先级调度算法;
2.2.3测试要求
要求输出进程名以及与其对应的优先级、轮数、CPU时间、需要时间、进程状态、计数器,可执行文件的输出格式如下:
进程名优先级轮数CPU时间需要时间进程状态计数器
Jc22802W0
Jc11801R0
2.3课程设计要求
1)编写程序完成课题内容;
2)在课程设计报告中画出基于时间片的高优先级调度函数流程图;
3)撰写课程设计报告,并参加答辩。
2.4课程设计思想
FCFS、SJF和优先级调度算法仅对某一类作业有利,相比之下,它能全面满足不同类型作业的需求,较好实现公平性与资源利用率之间的平衡。
对交互型作业,由于通常较短,这些作业在第一队列规定的时间片内完成,可使用户感到满意;
对短批作业,开始时在第一队列中执行一个时间片就可完成,便可与交互型作业一样获得快速晌应,否则通常也仅需在第二、第三队列中各执行一个时间片即可完成,其周转时间仍较短;
对长批作业,它们依次在第一至第n个队列中轮番执行,不必担心长时间得不到处理。
3概要设计
3.1课程设计所用方法及其原理
3.1.1优先级
优先级[4]体现了进程的重要程度或紧迫程度,在大多数现代操作系统中,都采用了优先级调度策略。
优先级从小到大(如0-127),0优先级最低,127最高。
在本实验中,要求优先级为0-8。
3.1.2基于时间片调度
将所有的就绪进程按照先来先服务[5]的原则,排成一个队列,每次调度时,将CPU分配给队首进程,并令其执行一个时间片。
当时间片用完时,由一个计时器发出时钟中断请求,调度程序把此进程终止,把该进程放到队尾。
在调度过程中,需要通过时间函数检测进程的执行时间,当该进程执行时间≥时间片大小时,进行调度。
3.1.3高优先级调度
优先级高的进程优先得到cpu,等该进程执行完毕后,另外的进程才能执行。
3.1.4基于时间片的高优先级调度
时间片和优先级调度的结合,在系统中,每个优先级对应一个就绪队列,在每个就绪队列内,采用时间片调度。
当高优先级进程队列调度完成后,才能转入更低优先级的就绪队列调度。
3.2主要的数据结构
表3.1PCB的数据结构
字段名
类型
宽度
别名
name
字符型
10
进出名
prio
数值型
1
进程的优先级
round
日期时间型
8
分配CPU的时间片