- 1、原创力文档(book118)网站文档一经付费(服务费),不意味着购买了该文档的版权,仅供个人/单位学习、研究之用,不得用于商业用途,未经授权,严禁复制、发行、汇编、翻译或者网络传播等,侵权必究。。
- 2、本站所有内容均由合作方或网友上传,本站不对文档的完整性、权威性及其观点立场正确性做任何保证或承诺!文档内容仅供研究参考,付费前请自行鉴别。如您付费,意味着您自己接受本站规则且自行承担风险,本站不退款、不进行额外附加服务;查看《如何避免下载的几个坑》。如果您已付费下载过本站文档,您可以点击 这里二次下载。
- 3、如文档侵犯商业秘密、侵犯著作权、侵犯人身权等,请点击“版权申诉”(推荐),也可以打举报电话:400-050-0827(电话支持时间:9:00-18:30)。
- 4、该文档为VIP文档,如果想要下载,成为VIP会员后,下载免费。
- 5、成为VIP后,下载本文档将扣除1次下载权益。下载后,不支持退款、换文档。如有疑问请联系我们。
- 6、成为VIP后,您将拥有八大权益,权益包括:VIP文档下载权益、阅读免打扰、文档格式转换、高级专利检索、专属身份标志、高级客服、多端互通、版权登记。
- 7、VIP文档为合作方或网友上传,每下载1次, 网站将根据用户上传文档的质量评分、类型等,对文档贡献者给予高额补贴、流量扶持。如果你也想贡献VIP文档。上传文档
查看更多
西安电子科技大学
《操作系统课程设计》
实
验
指
导
手
册
名称 Alarm-Clock
作者 西电 Linux 研究小组
创建时间 2013-09-20 修改时间 2013-10-22
1.任务描述
源代码 devices/timer.c 中有一个 timer_sleep() 函数。定义如下:
该函数的功能是让调用它的线程睡眠一段时间 (ticks) ,然后唤醒。
事实上, Pintos已经实现该函数,只是使用的是“忙等待”的方法 (见 while 循环 )。
本实验的要求:重新实现 timer_sleep( )函数,避免“忙等待”的发生(策略有多种,请大家设计一种并实现即可)
2.背景知识
2.1源码阅读
为顺利完成本实验,你至少需要阅读以下源代码文件 (并非每一行都要读懂 ),并了解其中关键数据结构和函数的含义,它们是:
../src/threads/目录下:
thread.h, thread.c:有关线程初始化、阻塞、解除阻塞,线程调度等内容;
interrupt.h, interrupt.c :与中断有关的处理函数。
../src/devices/目录下:
timer.h, timer.c :本实验要修改的 time_sleep( ) 函数就在其中,同时请注意理解定时器中断的处理过程。
2.1.1线程数据结构
在 thread.h 中定义了一个结构体 struct thread,这个结构体用于存放线程的基本信息, 实验中可能 (依你的方案而定 )需要修改 /扩充此结构。
请注意 enum thread_status 这个枚举类型的变量,用于表示线程当前所处的状态。
2.1.2 线程状态
Pintos 中线程的状态有四种,在 threads.h 中定义如下:
2.1.3中断
要完成 Alarm_clock 任务,你还需要对 Pintos中有关线程切换的过程比较熟悉。这对于后
面的实验也很重要。为了帮助大家更快地读懂这些代码,这里把 Pintos中定时器中断与线程
切换的过程做一小结。
定时器中断 (timer interrupt)
在操作系统原理课程的学习中, 我们知道, 多线程的并发执行是通过把 CPU按时间片轮
流分配给各个线程来实现的, Pintos也不例外。在 Pintos中,定时器中断频率定义为
TIMER_FREQ ,也就是说,每秒有 TIMER_FREQ 个定时器中断。在 time.h中定义为:
由此可知一个定时器中断的时长大约为
Pintos中一个时间片的长度 = 4*ticks
10ms,这里称为一个 ticks 。
≈ 40ms。当一个线程运行了一个时间片后,
它必
须放弃处理器给其它的线程。 那么系统是如何知道当前线程的运行时间,
以及何时进行线程
切换呢?现在我们便来进行一个分析。
事实上,当每个定时器中断 (ticks) 到来时,便会引发一次中断,系统对于这种中断的处理过程为:
1) 通过中断管理器 (汇编代码 )调用 intr_handker( ) 函数;
2) 由intr_handler( ) 调用 timer_interrupt( ) 函数。
timer_interrupt( ) 原型为 (timer.c中 ):
全局变量 ticks的含义:记录从系统启动到当前时刻总的定时器中断次数。
可以看出该函数的功能为:将全局变量 ticks++; 然后调用 thread_tick( ) 函数。
3) thread_tick( ) 函数( thread.c中)代码如下:
我们暂且仅关心阴影部分代码,可以看出,该函数会使得 thread_ticks 变量加 1,
如果增加后的 thread_ticks 变量值不大于 4(一个时间片 ),则返回。否则,则调用
intr_yield_on_return( ) 函数。
thread_ticks 和TIME_SLICE 变量定义如下:
4) intr_yield_on_return( ) 函数
该函数的功能为将 yield_on_return 变量置为 true,并返回 intr_handler( ) 函数,定义如
下:
intr_handler( ) 中相关代码如下:
可以看出,当 yield_on_return 为 true时,将调用 thread_yield( ) 函数。
5) thread_yield( ) 函数,代码如下 (thread.c中) :
该函数的功能为: 迫使当前线程 (非 idle 线程 )放弃 CPU ,使其进入 ready_list 末尾排队,并通过 schedule( )函数调度下一个线程执行。
线程切换
1) schedule( )函数定义如下:
可以看到该函数通过 next_th
文档评论(0)