windows线程调度优先级和关联性.docx

  1. 1、本文档共8页,可阅读全部内容。
  2. 2、原创力文档(book118)网站文档一经付费(服务费),不意味着购买了该文档的版权,仅供个人/单位学习、研究之用,不得用于商业用途,未经授权,严禁复制、发行、汇编、翻译或者网络传播等,侵权必究。
  3. 3、本站所有内容均由合作方或网友上传,本站不对文档的完整性、权威性及其观点立场正确性做任何保证或承诺!文档内容仅供研究参考,付费前请自行鉴别。如您付费,意味着您自己接受本站规则且自行承担风险,本站不退款、不进行额外附加服务;查看《如何避免下载的几个坑》。如果您已付费下载过本站文档,您可以点击 这里二次下载
  4. 4、如文档侵犯商业秘密、侵犯著作权、侵犯人身权等,请点击“版权申诉”(推荐),也可以打举报电话:400-050-0827(电话支持时间:9:00-18:30)。
查看更多
windows线程调度优先级和关联性

线程调度、优先级和关联性?????每个线程都有一个CONTEXT结构,保存在线程内核对象中。大约每隔20ms?windows就会查看所有当前存在的线程内核对象。并在可调度的线程内核对象中选择一个,将其保存在CONTEXT结构的值载入cpu寄存器。这被称为上下文切换。大约又过20ms??windows将当前cpu寄存器存回内核对象,线程被挂起。Windows再次检查内核对象,并在可调度的内核对象中选择一个进行调度。此过程不断重复直到系统关闭。?????Windows被称为抢占式多线程系统,系统可以在任何时刻停止一个线程而另行调度另外一个线程。我们对此可以有一些控制,但是权限很小。我们无法保证线程总在运行或者获得整个处理器。??????由于windows并不是实时操作系统,我们无法保证在某一时间段一定在运行。??????一般情况下,系统中的可调度线程很少。因为它们都在等待某个事件的到来。比如notepad程序在等待用户输入的时候它就是不可调度的。它在等待键盘的输入消息。当我们向notepad中输入时也并不意味着notepad会立即获得cpu时间。原因就是:windows并不是实时调度系统。?????线程内核对象中有一个值表示挂起计数。调用CreateThread时系统创建线程内核对象,并把挂起计数初始化为1。这样cpu就不会调度它。在初始化之后,系统检查是否有CREATE_SUSPEND标识传入。如果有函数返回,进程仍保持挂起状态。否则将挂起计数递减为0,此时线程就可以被调度了。?????通过创建一个挂起的进程或线程我们可以在它们执行任何代码前改变它们的环境,比如将其添加到作业中或是改变优先级。然后将它们设为可调度的。这可以通过调用ResumeThread函数。ResumeThread执行成功将返回前一次的挂起计数。失败则返回0xFFFFFFFF。?????一个线程可以被挂起多次。除了在创建时传入CREATE_SUSPEND标识外,还可以调用SuspendThread函数。第一个参数为想要挂起的线程句柄。任何线程都可以挂起另一个线程。挂起n次的线程要想变为可调度的必须调用ResumeThread()n次。?实际开发中,在调用SuspendThread时必须非常小心,因为我们无法知道线程此时在干什么。如果一个线程在分配堆中的内存,线程将锁定堆,其他想要分配堆的线程将被挂起。直到第一个线程分配完毕。如果第一个线程被挂起,将会出现死锁的情况。?????由于进程不是cpu调度的单位,所以不存在挂起进程的概念。但是我们可以挂起进程中所有的线程。可以调用调试器函数WaitForDebugEvent函数。恢复时可以调用ContinueDebugEvent。?????除了被别人调用SuspendThread挂起外,线程也可以告诉系统在一段时间内,可以将自己挂起,不需要调度。这可以调用Sleep实现。????[cpp]?view plaincopyvoid?Sleep(DWORD?dwMilliseconds);???????参数表示线程自己挂起的时间。但是实际的挂起时间只是近似于所设定的参数。Windows并不是实时操作系统,不能保证线程可以准时醒来。实际时间取决于系统中其他线程的运行情况。当为其传入0时,表示主调线程主动放弃本次时间片的剩余部分。注意是本次。?????系统提供一个名为SwitchToThread函数,如果存在另一个可调度的线程,那么系统将让此线程运行。????BOOL?SwitchToThread();????调用此函数时,系统查看是否存在急需cpu时间的饥饿线程。如没有则函数返回。如果存在,SwitchToThread将调度该线程。它与Sleep(0)很相似。区别在于SwitchToThread允许执行低优先级线程。?????当我们需要计算线程执行某项任务的我的时间时,很多人习惯使用GetTickCount64函数。?[cpp]?view plaincopyULONG?start=GetTickCount64();??????//do?something.????ULONG?end=GetTickCount64();?????????????此段代码有个前提就是代码执行不会被中断。但是在抢占式OS中,线程可以随时被终止。执行上述代码的线程可能在执行第一个函数后就被挂起。一段时间后再次被调度。这时候时间就不准确了。?????Windows提供了一个函数可以返回一个线程以获得cpu时间:??????[cpp]?view plaincopyBOOL?GetThreadTime(????????????HANDLE?hThread,????????????PFILETIME?pftCreationTime,????????????PF

文档评论(0)

haihang2017 + 关注
实名认证
内容提供者

该用户很懒,什么也没介绍

1亿VIP精品文档

相关文档