windows内核情景分析之—— KeRaiseIrql函数与KeLowerIrql()函数

1.KeRaiseIrql函数

这个 KeRaiseIrql() 只是简单地调用 hal 模块的 KfRaiseIrql() 函数,返回原来的 IRQL 写入 KeRaiseIrql() 的第 2 个参数里,将它写回 C 代码如下:

  1. VOID KeRaiseIrql(KIRQL NewIrql, PKIRQL OldIrql)
  2. {
  3. KIRQL Irql = KfRaiseIrql(NewIrql);
  4. *OldIrql = Irql;
  5. }
  6. KIRQL KfRaiseIrql(KIRQL Irql)
  7. {
  8. KIRQL OldIrql = GetCurrentKPcr()->Irql; // 从 _KPCR.Irql(fs:[24])得到 Irql 值
  9. if (HalpEnableIrqlAudit != 0)
  10. {
  11. eflags = GetCurrentElfags(); // 得到 eflags 值
  12. DisableInterrupt(); // 关闭中断
  13. HalpValidatePendingInterrts();
  14. if (HalpEnableIrqlAudit == 0
  15. || OldIrql >= DPC_LEVE
  16. || OldIrql >= ((USHORT *)GetCurrentKPcr()->HalReserved)[1]; // fs:[96h]
  17. || HalpAssertFailedOnce != 0)
  18. {
  19. if (eflags.IF == 0)
  20. EnableInterrupt(): // 开中断
  21. }
  22. }
  23. if (HalpEnableIrqlAudit == 0 || OldIrql <= Irql)
  24. {
  25. // 空,跳出 if()
  26. }
  27. else
  28. {
  29. HalpAssertFailedOnce = 1;
  30. DbgBreakPoint(); // 被断下
  31. }
  32. GetCurrentKPcr()->Irql = Irql; // 设置新的 IRQL 值
  33. return OldIrql;// 返回旧的 IRQL 值
  34. }
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39
  • 40
  • 41

KfRaiseIrql() 函数能提升 IRQL 需符合下面的条件之一:

1.HalpEnableIrqlAudit 为 0(HalpEnableIrqlAudit 是个 hal 模块内的全局变量,但我不知道它是什么意思

2.NewIrql >= OldIrql(也就是要提升的 IRQL 必须大于或等于原值)

2.KeLowerIrql()函数

  1. #define KeLowerIrql(a) KfLowerIrql(a)
  2. VOID FASTCALL KfLowerIrql (KIRQLNewIrql)
  3. {
  4. if (NewIrql > KeGetPcr()->Irql)
  5. {
  6. KEBUGCHECK(0);
  7. for(;;);
  8. }
  9. HalpLowerIrql(NewIrql);
  10. }
  11. VOID HalpLowerIrql(KIRQL NewIrql) //主要函数
  12. {
  13. if (NewIrql >= PROFILE_LEVEL) //如果所要降到的中断请求级大于PROFILE_LEVEL,则直接设置当前的中断请求级
  14. {
  15. KeGetPcr()->Irql = NewIrql;
  16. return;
  17. }
  18. HalpExecuteIrqs(NewIrql);
  19. if (NewIrql >= DISPATCH_LEVEL) //如果所要降到的中断请求级大于DISPATCH_LEVEL,则直接设置当前的中断请求级
  20. {
  21. KeGetPcr()->Irql = NewIrql;
  22. return;
  23. }
  24. //NewIrql低于DISPATCH_LEVEL
  25. KeGetPcr()->Irql = DISPATCH_LEVEL; //所要降到的中断请求级小于DISPATCH_LEVEL,设置当前的中断请求级为DISPATCH_LEVEL,
  26. //然后扫描dpc队列,如果不为空,则触发dpc软件中断
  27. if (((PKIPCR)KeGetPcr())->HalReserved[HAL_DPC_REQUEST])
  28. { //DPC请求队列非空
  29. ((PKIPCR)KeGetPcr())->HalReserved[HAL_DPC_REQUEST] = FALSE;
  30. KiDispatchInterrupt();
  31. }
  32. KeGetPcr()->Irql = APC_LEVEL; //所要降到的中断请求级小于APC_LEVEL,设置当前的中断请求级为APC_LEVEL,
  33. //然后扫描apc队列,如果不为空,则触发apc软件中断
  34. if (NewIrql == APC_LEVEL)
  35. {
  36. return;
  37. }
  38. //NewIrql低于APC_LEVEL
  39. if (KeGetCurrentThread() != NULL &&
  40. KeGetCurrentThread()->ApcState.KernelApc Pending)
  41. {
  42. KiDeliverApc(KernelMode, NULL, NULL);
  43. }
  44. KeGetPcr()->Irql = PASSIVE_LEVEL;
  45. }
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39
  • 40
  • 41
  • 42
  • 43
  • 44
  • 45
  • 46
  • 47
  • 48
  • jpg 改 rar 

windows内核情景分析之—— KeRaiseIrql函数与KeLowerIrql()函数的更多相关文章

  1. 几个常用内核函数(《Windows内核情景分析》)

    参考:<Windows内核情景分析> 0x01  ObReferenceObjectByHandle 这个函数从句柄得到对应的内核对象,并递增其引用计数. NTSTATUS ObRefer ...

  2. [1]windows 内核情景分析---说明

    本文说明:这一系列文章(笔记)是在看雪里面下载word文档,现转帖出来,希望更多的人能看到并分享,感谢原作者的分享精神. 说明 本文结合<Windows内核情景分析>(毛德操著).< ...

  3. [14]Windows内核情景分析 --- 文件系统

    文件系统 一台机器上可以安装很多物理介质来存放资料(如磁盘.光盘.软盘.U盘等).各种物理介质千差万别,都配备有各自的驱动程序,为了统一地访问这些物理介质,windows设计了文件系统机制.应用程序要 ...

  4. [4]Windows内核情景分析---内核对象

    写过Windows应用程序的朋友都常常听说"内核对象"."句柄"等术语却无从得知他们的内核实现到底是怎样的, 本篇文章就揭开这些技术的神秘面纱. 常见的内核对象 ...

  5. [15]Windows内核情景分析 --- 权限管理

    Windows系统是支持多用户的.每个文件可以设置一个访问控制表(即ACL),在ACL中规定每个用户.每个组对该文件的访问权限.不过,只有Ntfs文件系统中的文件才支持ACL. (Ntfs文件系统中, ...

  6. [11]Windows内核情景分析---设备驱动

    设备驱动 设备栈:从上层到下层的顺序依次是:过滤设备.类设备.过滤设备.小端口设备[过.类.过滤.小端口] 驱动栈:因设备堆栈原因而建立起来的一种堆栈 老式驱动:指不提供AddDevice的驱动,又叫 ...

  7. [7] Windows内核情景分析---线程同步

    基于同步对象的等待.唤醒机制: 一个线程可以等待一个对象或多个对象而进入等待状态(也叫睡眠状态),另一个线程可以触发那个等待对象,唤醒在那个对象上等待的所有线程. 一个线程可以等待一个对象或多个对象, ...

  8. [5]windows内核情景分析---进程线程

    本篇主要讲述进程的启动过程.线程的调度与切换.进程挂靠 进程的启动过程: BOOL CreateProcess ( LPCTSTR lpApplicationName,                 ...

  9. [2]windows内核情景分析--系统调用

    Windows的地址空间分用户模式与内核模式,低2GB的部分叫用户模式,高2G的部分叫内核模式,位于用户空间的代码不能访问内核空间,位于内核空间的代码却可以访问用户空间 一个线程的运行状态分内核态与用 ...

随机推荐

  1. (笔记)Linux延时及时间函数总结

    一. 基础知识1.时间类型.Linux下常用的时间类型有4个:time_t,struct timeval,struct timespec,struct tm.(1)time_t是一个长整型,一般用来表 ...

  2. 使用Eclipse的JUnit实例

    在本节中,我们将展示使用JUnit的一个完整的例子.我们将详细了解如何创建和运行测试,我们将展示如何使用特定的注释和JUnit断言. 1. 初始步骤 让我们创建一个名为 JUnitGuide 的Jav ...

  3. e839. 使JTabbedPane中的卡片可滚动

    By default, all the tabs in a tabbed pane are displayed. When the tabs are wider than the width of t ...

  4. Java NIO案例

    Java 网络IO编程总结(BIO.NIO.AIO均含完整实例代码)   http://blog.csdn.net/anxpp/article/details/51512200 Java NIO框架N ...

  5. Ubuntu 安装IntelliJ IDEA

    1. 下载IDEA    官网地中:http://www.jetbrains.com/idea/download/index.html    选择对应操作系统的版本.下载后,我的文件名称为: idea ...

  6. Linux入门教程:如何检查Linux系统的最后重启时间

    问题: 是否有一个命令可以快速地检查系统已经运行了多久? 也就是我怎么知道Linux系统最后的重启时间? 有许多方法来查询系统最后的重启时间. 方法一 第一种方法是使用last命令. $ last r ...

  7. mysql错误代码对照表较完整 mysql_errno()

    From: http://blog.csdn.net/aidenliu/article/details/5925604 mysql错误代码对照表较完整  0101 属于其他进程的专用标志. 0102 ...

  8. MySql:charset和collation的设置

    From: http://www.2cto.com/database/201302/189920.html MySql:charset和collation的设置   charset 和 collati ...

  9. HttpURLConnection如何添加请求头?

    1.conn.setRequestProPerty(name,value),两个参数都是字符串.... 2.用httpURLConnection的setRequestProPerty(name,val ...

  10. MATLAB错误:下标索引必须是正整数类型或者逻辑类型

    背景: Matlab R2015b 问题: 在运行BP算法时出现错误: 下标索引必须是正整数类型或者逻辑类型 output( i , class( i )  ) = 1 ; 解决办法: 根目录下运行, ...