Loading
1

暴风影音AviIndexChunk字段堆溢出漏洞分析实战

+0x01c EndStamp         : 0xdcbabbbb
书中P681表23-7也列举了页堆堆块的填充模式:
占用堆块
空闲堆块
头结构的Start Magic
ABCDBBBB
ABCDBBBA
头结构的End Magic
DCBABBBB
DCBABBBA
用户区
C0或用户初始化00
F0
用户数据后的填充部分
D0
N/A
因此,为了满足Windows中8字节的分配粒度,该页堆虽然只申请了4字节,但尾部也填充了4字节的d0d0d0d0。这样也就解释了“为何该堆的大小只有4个字节,而已经写入了8个字节却没有出现异常”这个疑惑。
再看第二个疑惑:
为何memcpy明明从样本倒数第二个字节0x26e开始拷贝,而之前的8个字节已经被写入到堆的前8个字节?难不成在memcpy函数之前,就进行了堆的写入操作?
要想验证memcpy函数之前对该堆的写入操作,就要在堆创建后下内存写断点:
ba w4 eax
首先在在堆创建时下断点,得到堆的起始地址:
0:027> bp AviSplitter+0x0000303e
0:027> g
Breakpoint 1 hit
eax=31786469 ebx=00000000 ecx=00000004 edx=00000002 esi=21ed6f08 edi=00000270
eip=69e6303e esp=2516f338 ebp=2516f38c iopl=0         nv up ei pl zr na pe nc
cs=0023  ss=002b  ds=002b  es=002b  fs=0053  gs=002b             efl=00000246
AviSplitter+0x303e:
69e6303e e869480100      call    AviSplitter!DllGetClassObject+0x337c (69e778ac)
0:027> p
eax=21510ff8 ebx=00000000 ecx=00000004 edx=00000000 esi=21ed6f08 edi=00000270
eip=69e63043 esp=2516f338 ebp=2516f38c iopl=0         nv up ei pl nz na po nc
cs=0023  ss=002b  ds=002b  es=002b  fs=0053  gs=002b             efl=00000202
AviSplitter+0x3043:
69e63043 8986d4000000    mov     dword ptr [esi+0D4h],eax ds:002b:21ed6fdc=00000000
上面申请的页堆起始地址eax=21510ff8,对之后8个字节下内存写断点:
0:027> ba w8 0x21510ff8
0:027> g
Breakpoint 2 hit
eax=21510ff8 ebx=00000000 ecx=00000004 edx=00000000 esi=21ed6f08 edi=00000270
eip=69e6304f esp=2516f338 ebp=2516f38c iopl=0         nv up ei pl nz na po nc
cs=0023  ss=002b  ds=002b  es=002b  fs=0053  gs=002b             efl=00000202
AviSplitter+0x304f:
69e6304f 8b45ec          mov     eax,dword ptr [ebp-14h] ss:002b:2516f378=00000002
0:027> g
Breakpoint 2 hit
eax=00000002 ebx=00000000 ecx=00000004 edx=21510ff8 esi=21ed6f08 edi=00000270
eip=69e6305e esp=2516f33c ebp=2516f38c iopl=0         nv up ei pl nz na pe nc
cs=0023  ss=002b  ds=002b  es=002b  fs=0053  gs=002b             efl=00000206
AviSplitter+0x305e:
69e6305e 8b86d4000000    mov     eax,dword ptr [esi+0D4h] ds:002b:21ed6fdc=21510ff8
细心对比相关指令发现,这些内存写操作就发生在call指令创建页堆之后:
69e6303e e869480100      call    AviSplitter!DllGetClassObject+0x337c (69e778ac)  --创建页堆
69e63043 8986d4000000    mov     dword ptr [esi+0D4h],eax
69e63049 c70069647831    mov     dword ptr [eax],31786469h  --写第1-4字节
69e6304f 8b45ec          mov     eax,dword ptr [ebp-14h]
69e63052 8b96d4000000    mov     edx,dword ptr [esi+0D4h]
69e63058 83c404          add     esp,4
69e6305b 894204          mov     dword ptr [edx+4],eax  --写第5-8字节
69e6305e 8b86d4000000    mov     eax,dword ptr [esi+0D4h]
69e63064 8b4dec          mov     ecx,dword ptr [ebp-14h]
69e63067 6a00            push    0
69e63069 51              push    ecx
69e6306a 83c008          add     eax,8
69e6306d e989010000      jmp     AviSplitter+0x31fb (69e631fb)
由上可知,当页堆被创建后,无论申请的大小是多少,从页堆起始地址开始的8个字节就被赋予了下列内容:
|69 64 78 31 |02 00 00 00|
其中,前4个字节是以固定指令写入的,并不是样本文件中的内容,而后4个字节与样本最后两个字节之前的4字节内容相同:

分页阅读: 1 2 3 4 5 6 7 8 9 10
【声明】:8090安全小组门户(https://www.8090-sec.com)登载此文出于传递更多信息之目的,并不代表本站赞同其观点和对其真实性负责,仅适于网络安全技术爱好者学习研究使用,学习中请遵循国家相关法律法规。如有问题请联系我们:邮箱hack@ddos.kim,我们会在最短的时间内进行处理。