内核漏洞大多出没于 ring3 到 ring0 的交互中。从 ring3 进入 ring0 的通道,以及操作系统提供的 API 都有可能存在漏洞。例如:驱动程序中 IoControl 的处理函数,SSDT 和 Shadow SSDT 中的系统服务函数(无论是否被 hook 都有可能存在漏洞),系统回调函数,内核钩子程序等。从漏洞数量来看,驱动程序中 IoControl 的处理函数中的漏洞最为多见,尤其是第三方的驱动程序。

本节对几种典型的内核漏洞,用几个真实的内核漏洞案例来详细分析。

远程拒绝服务内核漏洞

对 CVE-2009-3103 / 2009-09-08 Microsoft SMB2 SRV2.sys Remote DOS 36299 进行分析:实现 SMB v2 协议相关的 srv2.sys 没有正确处理包含畸形 SMB 头结构数据的 NEGOTIATE PROTOCOL REQUEST(客户发送给 SMB 服务器的第一个 SMB 查询,用于识别 SMB 语言并用于之后的通信)请求。如果远程攻击者在发送的 SMB 报文的 Process Id High 头字段中包含畸形数据,就会在 srv2.sys 驱动中的 _Smb2ValidateProviderCallback() 触发越界内存引用,导致内核态执行任意指令或发生系统崩溃。漏洞利用无须额外认证过程,只要系统开放了通常的文件共享打印服务并允许远端访问。

书中简单地介绍了下 SMB 数据报的结构,使用了 IDA 来进行分析。通常 SMB 运行于 TCP/IP 之上,其数据报总体结构如下,其它内容见原书。

IDA 载入文件后默认以反汇编的方式显式,不过 Hex-Rays 插件可以显示为 C 语言。安装完 Hex-Rays 后,用鼠标定位到要翻译的反汇编程序段,点击 View - Open Subviews - Pseudocode 或者 F5 即可将代码段用 C 语言显示出来。

本地拒绝服务内核漏洞

对 CVE-2010-1734 / 2010-04-22 Microsoft SfnINSTRING win32k.sys Local DOS 39631 进行分析:win32k.sys 模块在 DispatchMessage 时,会最后调用到 xxxDefWindowProc(),这个函数在处理某些消息时会调用 gapfnScSendMessage() 这个函数表中的函数来处理,其中 Windows 2000/xp/2003 在处理 0x18d 号消息时,会有一个名为 SfnINSTRING() 的函数,这个函数当 lParam 不为空时,直接认为 lParam 是内存指针,并直接从地址中取出数据。虽然使用了 SEH,但只要传递错误内核地址,就会引发系统崩溃。

缓冲区溢出内核漏洞

对 2009-07-31 ALWIL avast4.8.1335_Professionnal aswmon2.sys Local Buffer Overflow - Privilege Escalation 进行分析:aswmon2.sys 对驱动派遣例程的处理中,IoControlCode 为 0xB2C8000C 时,当两次调用这个 IoControl 处理函数后,会导致内存中的函数指针被覆盖成一个固定的 DWORD,该值为 0x57523C00,而这个地址的内存可以在用户态分配。

任意地址写任意数据内核漏洞

对 2010-01-23 Rising Antivirus_2008/2009/2010 RsNTGdi.sys 37951 进行分析:在对驱动派遣例程的处理中,switch 语句对 IoControlCode=0x83003C0B 的处理存在漏洞:首先检查 InputBufferLength 和 OutputBufferLength 是否都大于 4,如果是,则调用 VidSetTextColor(),并将 VidSetTextColor() 的返回值结果写入 UserBuffer,VidSetTextColor() 的参数是 *Type3InputBuffer,即用户态输入的 4 字节 UINT 值。VidSetTextColor() 由 bootvid.dll 导出,该函数会将输入的参数保存到一个全局变量中,并返回这个全局变量之前的值,而瑞星会将这个返回值写入到未验证的 irp->UserBuffer 中。

利用时,调用两次 DeviceIoControl()。第一次将要写入的值(*Type3InputBuffer)用这个 IoControlCode 写入到全局变量中;然后将 UserBuffer 设置为要写入数据的内核地址,再调用这个 IoControlCode,就可以把要输入的值(*Type3InputBuffer)写入到任意的内核地址了。

任意地址写固定数据内核漏洞

对 2009-07-30 Microsoft NtUserConsoleControl win32k.sys Local Privilege Escalation 进行分析。该内核漏洞存在于 XP sp2/sp3 的系统服务函数 NtUserControlControl 中,这个函数在 win32k.sys 中实现。用 IDA 反汇编 win32k.sys 并加载该模块的 PDB 符号文件,可以找到 NtUserConsoleControl()。

函数中通过 PsGetCurrentProcess() 获取当前进程的 PEPROCESS,和 csrss.exe 进程的 PEPROCESS 进行对比,如果不同,将返回值设置为 0XC0000022(STATUS_ACCESS_DENIED),表示访问被拒绝;如果相同,则继续调用 xxxConsoleControl(),参数就是 NtUserConsoleControl() 的前两个参数。

继续关注 xxxConsoleControl(),其对第一个对数 UNIT a1 的处理中,当 al==7 时,Object[3]=0 是将 Object 指向的句柄数组中的第 4 个句柄置 0,但整个过程没有对 Object 指针进行任何检查。也就是说,从 Ring3 传递进来的 Object 指针,经过该函数可以将 Object 指针执行的第 4 个句柄置 0.

最新文章

  1. 【集合框架】JDK1.8源码分析之LinkedList(七)
  2. C++ Primer : 第九章 : 顺序容器的操作以及迭代器失效问题
  3. android.view.WindowManager$BadTokenException: Unable to add window -- token null is not for an application
  4. 实例模拟struts核心流程
  5. 移动端屏幕自适应js与rem
  6. 数字签名.sys文件的步骤
  7. Html5 代码
  8. adhoc-海量数据多维自助即席查询平台-mdrill项目开源啦
  9. python获取实时股票信息
  10. simpleDateFormat日期格式转换
  11. poj1847 Tram 最短路Dijkstra
  12. HDU4812
  13. OSS上传文件到阿里云
  14. java练习:质数,匿名内部类创建接口,抽象类派生子类,画圆,字节截取字符串,数字变钱币,五子棋,梭哈
  15. ELK收集Nginx自定义日志格式输出
  16. findViewById(R.id.btn_first) 给写成 R.layout.
  17. Python:每日一题001
  18. Ubuntn16.04.3配置root权限及启用root用户
  19. hdu 1754 I Hate It(树状数组区间求最值)2007省赛集训队练习赛(6)_linle专场
  20. R语言学习笔记:基础知识

热门文章

  1. __attribute__ ((section(".text")))的测试
  2. PHP框架、库和软件资源大全(整理篇)
  3. Js使用word书签填充内容
  4. [BZOJ 3238] [AHOI 2013] 差异 【后缀数组 + 单调栈】
  5. The Child and Toy
  6. cf E. George and Cards
  7. js eval()函数 接收一个字符串,做为js代码来执行。 如: s='var d="kaka"'; 或者s=‘function (code){return code }’;
  8. Reverse Words in a String——LeetCode
  9. HDOJ(HDU) 2136 Largest prime factor(素数筛选)
  10. div+css模式编写html静态网页例子_仿照网页制作