GetIA32CodeSize

出自 ProgWiki
前往: 導覽搜尋

用途

  • 計算傳入位址的第一個組合語言的機械碼長度。(未完)

IA32CodeSize.h

#pragma once
 
int getIA32CodeSize(void* pSrc);


IA32CodeSize.cpp

#define _Instruction_1()	\
			nIndex++;
 
#define _Instruction_1_Completion()	\
			nIndex++;		bCompletion = true;
 
#define _Instruction(x)	\
			nIndex+=x;
 
#define _Instruction_Completion(x)	\
			nIndex+=x;		bCompletion = true;
 
//	ModR/M Byte
typedef struct _ModRM_Byte
{
   unsigned _RM		: 3;    // 0..7	(3 bits)
   unsigned _REG	: 3;    // 0..7	(3 bits)
   unsigned _MOD	: 2;    // 0..3	(2 bits)
};
 
 
inline int _getDispSizeOfModRM(BYTE x, bool _bIsAddr16)
{
	//TODO: _getDispSizeOfModRM(BYTE x, bool _bIsAddr16)
 
	BYTE _Mod	= (x & 0xc0) >> 6;
	//BYTE _REG	= (x & 0x38) >> 3;	
	BYTE _RM	= (x & 0x07);	
 
	switch ( _Mod )
	{
		case 0:
			if (_RM == 4)
			{
				return 1;		//SIB Byte	
			}
			else if (_RM == 5)
			{
				if (_bIsAddr16)
					return 2;	//Disp16	
				else	
					return 4;	//Disp32	
			}
			break;
		case 1:
			if (_RM == 4)
				return 2;		//SIB Byte + Disp8	
			else
				return 1;		//Disp8	
		case 2:
			if (_bIsAddr16)
			{
				if (_RM == 4)
					return 3;	//SIB Byte + Disp16
				else
					return 2;	//Disp16	
			}
			else
			{
				if (_RM == 4)
					return 5;	//SIB Byte +Disp32		
				else
					return 4;	//Disp32		
			}
		case 3:
			break;
		}
	}
	return 0;
}
 
int getIA32CodeSize(void* pSrc)
{
	//TODO: getIA32CodeSize(void* pSrc)
 
	LPBYTE	pTest = (LPBYTE)pSrc;
	int		nIndex = 0;
 
	bool	bCompletion = false;
	bool	bIsAddr16 = false;
	bool	bIsData16 = false;
 
	do
	{
		const BYTE	_Opcode1 = pTest[nIndex];	
		switch ( _Opcode1 )
		{
			case 0x00:	//	add	r/m8, r8
			case 0x01:	//	add	r/m16, r16
						//	add	r/m32, r32
			case 0x02:	//	add	r8, r/m8
			case 0x03:	//	add	r16, r/m16
						//	add	r32, r/m32
				_Instruction_Completion( 2 +
										_getDispSizeOfModRM(pTest[nIndex+1], bIsAddr16));
												break;	
			case 0x04:	//	add	al, imm8
				_Instruction_Completion(2);		break;
			case 0x05:	//	add	ax, imm16
						//	add	eax, imm32
				if (bIsData16 != true)
					_Instruction_Completion(5);		
				else
					_Instruction_Completion(3);	
												break;
			case 0x06:	//	push	es
			case 0x07:	//	pop	es	
				_Instruction_1_Completion();	break;
			case 0x08:	//	or	r/m8, r8
			case 0x09:	//	or	r/m16, r16
						//	or	r/m32, r32
			case 0x0a:	//	or	r8, r/m8
			case 0x0b:	//	or	r16, r/m16
						//	or	r32, r/m32
				_Instruction_Completion( 2 +
										_getDispSizeOfModRM(pTest[nIndex+1], bIsAddr16));
												break;
			case 0x0c:	//	or	al, imm8
				_Instruction_Completion(2);		break;
			case 0x0d:	//	or	ax, imm16
						//	or	eax, imm32
				if (bIsData16 != true)
					_Instruction_Completion(5);		
				else
					_Instruction_Completion(3);	
												break;
			case 0x0e:	//	push cs
				_Instruction_1_Completion();	break;
			case 0x0f:
				{
					//TODO: opcode_0x0f
					BYTE	_Opcode2 = pTest[nIndex+1];	
					switch ( _Opcode2 )
					{
						case 0x00:
						{
							//TODO: opcode_0x0f-0x00
							BYTE _REG	= (pTest[nIndex+2] & 0x38) >> 3;	
							switch ( _REG )
							{
								case 0:	//	sldt	r/m16
								case 1:	//	sidt	m
								case 2:	//	lldt	r/m16
								case 3:	//	ltr	r/m16
									_Instruction_Completion( 3 +
													_getDispSizeOfModRM(pTest[nIndex+2], bIsAddr16));
															break;
								case 4:	//	
								case 5:	//	
								case 6:	//	
								case 7:	//	
							}
						}									break;
 
						case 0x01:
						{
							//TODO: opcode_0x0f-0x01
							BYTE _REG	= (pTest[nIndex+2] & 0x38) >> 3;	
							switch ( _REG )
							{
								case 0:	//	sgdt	m
								case 1:	//	sidt	m
								case 2:	//	lgdt	r/m16
										//	lgdt	r/m32	
								case 3:	//	lidt	r/m16
										//	lidt	r/m32	
								case 4:	//	smsw	r/m16
										//	smsw	r/m32
									_Instruction_Completion( 3 +
													_getDispSizeOfModRM(pTest[nIndex+2], bIsAddr16));
															break;
								case 5:	//	
								case 6:	//	lmsw		r/m16
								case 7:	//	invlpg	m
							}
						}									break;
 
						case 0x02:	//	lar	r16, r16/m16
									//	lar	r32, r32/m16
						case 0x03:	//	lsl	r16, r16/m16
									//	lsl	r32, r32/m16
							_Instruction_Completion( 3 +
													_getDispSizeOfModRM(pTest[nIndex+2], bIsAddr16));
															break;
						//case 0x04:
						case 0x05:	//	syscall
						case 0x06:	//	clts
						case 0x07:	//	sysret
						case 0x08:	//	invd
						case 0x09:	//	wbinvd
							_Instruction_Completion(2);		break;
						//case 0x0a:
						case 0x0b:	//	ud2
							_Instruction_Completion(2);		break;
						//case 0x0c:
						//case 0x0d:
						//case 0x0e:
						//case 0x0f:
						case 0x10:	//	movups		xmm1, xmm2/m128
						case 0x11:	//	movups		 xmm2/m128, xmm1
							_Instruction_Completion( 3 +
													_getDispSizeOfModRM(pTest[nIndex+2], bIsAddr16));
															break;
						//case 0x12:
						//case 0x13:
						case 0x14:	//	unpacklps	xmm1, xmm2/m128
						case 0x15:	//	unpackhps	xmm1, xmm2/m128
							_Instruction_Completion( 3 +
													_getDispSizeOfModRM(pTest[nIndex+2], bIsAddr16));
															break;
						//case 0x16:
						//case 0x17:
						//case 0x18:
						//case 0x19:
						//case 0x1a:
						//case 0x1b:
						//case 0x1c:
						//case 0x1d:
						//case 0x1e:
						//case 0x1f:
						case 0x20:	//	mov		r32, CRx
						case 0x21:	//	mov		r32, DRx
						case 0x22:	//	mov		CRx, r32
						case 0x23:	//	mov		DRx, r32
							_Instruction_Completion(3);		break;
						//case 0x24:
						//case 0x25:
						//case 0x26:
						//case 0x27:
						//case 0x28:
						//case 0x29:
						//case 0x2a:
						//case 0x2b:
						//case 0x2c:
						//case 0x2d:
						case 0x2e:	//	ucomiss		xmm1, xmm2/m128
							_Instruction_Completion( 3 +
													_getDispSizeOfModRM(pTest[nIndex+2], bIsAddr16));
															break;
						//case 0x2f:
						case 0x30:	//	wrmsr
							_Instruction_Completion(2);		break;
						case 0x31:	//	rdtsc
						case 0x32:	//	rdmsr
						case 0x33:	//	rdpmc
						case 0x34:	//	sysenter
						case 0x35:	//	sysexit
							_Instruction_Completion(2);		break;
						//case 0x36:
						//case 0x37:
						//case 0x38:
						//case 0x39:
						//case 0x3a:
						//case 0x3b:
						//case 0x3c:
						//case 0x3d:
						//case 0x3e:
						//case 0x3f:
						//case 0x40:
						//case 0x41:
						//case 0x42:
						//case 0x43:
						//case 0x44:
						//case 0x45:
						//case 0x46:
						//case 0x47:
						//case 0x48:
						//case 0x49:
						//case 0x4a:
						//case 0x4b:
						//case 0x4c:
						//case 0x4d:
						//case 0x4e:
						//case 0x4f:
						//case 0x50:
						//case 0x51:
						//case 0x52:
						//case 0x53:	//	rcpps	xmm1, xmm2/m128
						//case 0x54:
						//case 0x55:
						//case 0x56:
						case 0x57:	//	xorps		xmm1, xmm2/m128
							_Instruction_Completion( 3 +
													_getDispSizeOfModRM(pTest[nIndex+2], bIsAddr16));
															break;
						//case 0x58:
						case 0x59:	//	mulps		xmm1, xmm2/m128
							_Instruction_Completion( 3 +
													_getDispSizeOfModRM(pTest[nIndex+2], bIsAddr16));
															break;
						//case 0x5a:
						//case 0x5b:
						case 0x5c:	//	subpss	xmm1, xmm2/m128
							_Instruction_Completion( 3 +
													_getDispSizeOfModRM(pTest[nIndex+2], bIsAddr16));
															break;
						//case 0x5d:
						//case 0x5e:
						//case 0x5f:
						//case 0x60:
						//case 0x61:
						//case 0x62:
						//case 0x63:
						//case 0x64:
						//case 0x65:
						//case 0x66:
						//case 0x67:
						//case 0x68:
						//case 0x69:
						//case 0x6a:
						//case 0x6b:
						//case 0x6c:
						//case 0x6d:
						//case 0x6e:
						//case 0x6f:
						//case 0x70:
						//case 0x71:
						//case 0x72:
						//case 0x73:
						//case 0x74:
						//case 0x75:
						//case 0x76:
						case 0x77:	//	emms
							_Instruction_Completion(2);		break;
						//case 0x78:
						//case 0x79:
						//case 0x7a:
						//case 0x7b:
						//case 0x7c:
						//case 0x7d:
						//case 0x7e:
						//case 0x7f:
						//case 0x80:
						//case 0x81:
						//case 0x82:
						//case 0x83:
						//case 0x84:
						//case 0x85:
						//case 0x86:
						//case 0x87:
						//case 0x88:
						//case 0x89:
						//case 0x8a:
						//case 0x8b:
						//case 0x8c:
						//case 0x8d:
						//case 0x8e:
						//case 0x8f:
						case 0x90:	//	seto	r/m8
						case 0x91:	//	setno	r/m8
						case 0x92:	//	setc	r/m8
						case 0x93:	//	setae	r/m8
						case 0x94:	//	sete	r/m8
						case 0x95:	//	setne	r/m8
						case 0x96:	//	setbe	r/m8
						case 0x97:	//	seta	r/m8
						case 0x98:	//	sets	r/m8
						case 0x99:	//	setns	r/m8
						case 0x9a:	//	setp	r/m8
						case 0x9b:	//	setnp	r/m8
						case 0x9c:	//	setnge	r/m8
						case 0x9d:	//	setge	r/m8
						case 0x9e:	//	setle	r/m8
						case 0x9f:	//	setg	r/m8
							_Instruction_Completion( 3 +
													_getDispSizeOfModRM(pTest[nIndex+2], bIsAddr16));
															break;
						case 0xa0:	//	push	fs
						case 0xa1:	//	pop		fs
						case 0xa2:	//	cpuid
							_Instruction_Completion(2);		break;
						case 0xa3:	//	bt		r/m16, r16
									//	bt		r/m32, r32						
							_Instruction_Completion( 3 +
													_getDispSizeOfModRM(pTest[nIndex+2], bIsAddr16));
															break;
						//case 0xa4:
						//case 0xa5:
						//case 0xa6:
						//case 0xa7:
						case 0xa8:	//	push		gs
						case 0xa9:	//	pop		gs
						case 0xaa:	//	rsm
							_Instruction_Completion(2);		break;
						case 0xab:	//	bts	r/m16, r16
									//	bts	r/m32, r32		
							_Instruction_Completion( 3 +
													_getDispSizeOfModRM(pTest[nIndex+2], bIsAddr16));
															break;
						//case 0xac:
						//case 0xad:
						//case 0xae:
						//case 0xaf:
						//case 0xb0:
						//case 0xb1:
						//case 0xb2:
						//case 0xb3:
						//case 0xb4:
						//case 0xb5:
						case 0xb6:	//	movzx	r16,  r/m8
									//	movzx	r32, r/m8
						case 0xb7:	//	movzx	r32, r/m16
							_Instruction_Completion( 3 +
													_getDispSizeOfModRM(pTest[nIndex+2], bIsAddr16));
															break;
						//case 0xb8:
						//case 0xb9:
						//case 0xba:
						case 0xbb:	//	btc	r/m16, r16
									//	btc	r/m32, r32	
						case 0xbc:	//	bsf	r16, r/m16
									//	bsf	r32, r/m32
						case 0xbd:	//	bsr	r16, r/m16
									//	bsr	r32, r/m32
							_Instruction_Completion( 3 +
													_getDispSizeOfModRM(pTest[nIndex+2], bIsAddr16));
															break;
						//case 0xbe:
						//case 0xbf:
						case 0xc0:	//	xadd	r/m8, r8
						case 0xc1:	//	xadd	r/m16, r16
									//	xadd	r/m32, r32
							_Instruction_Completion( 3 +
													_getDispSizeOfModRM(pTest[nIndex+2], bIsAddr16));
															break;
						//case 0xc2:
						//case 0xc3:
						//case 0xc4:
						//case 0xc5:
						//case 0xc6:
						//case 0xc7:		
						//case 0xc8:	//	bswap	r32
						//case 0xc9:
						//case 0xca:
						//case 0xcb:
						//case 0xcc:
						//case 0xcd:
						//case 0xce:
						//case 0xcf:
						//case 0xd0:
						//case 0xd1:
						//case 0xd2:
						//case 0xd3:
						//case 0xd4:
						//case 0xd5:
						//case 0xd6:
						//case 0xd7:
						//case 0xd8:
						//case 0xd9:
						//case 0xda:
						//case 0xdb:	//	por	mm, mm/m64
						//case 0xdc:
						//case 0xdd:
						//case 0xde:
						//case 0xdf:
						//case 0xe0:
						//case 0xe1:
						//case 0xe2:
						//case 0xe3:
						//case 0xe4:
						//case 0xe5:
						//case 0xe6:
						//case 0xe7:
						//case 0xe8:
						//case 0xe9:
						//case 0xea:
						//case 0xeb:
						//case 0xec:
						//case 0xed:
						//case 0xee:
						case 0xef:	//	pxor		mm, mm/m64
							_Instruction_Completion( 3 +
													_getDispSizeOfModRM(pTest[nIndex+2], bIsAddr16));
															break;
						//case 0xf0:
						//case 0xf1:
						//case 0xf2:
						//case 0xf3:
						//case 0xf4:
						//case 0xf5:
						//case 0xf6:
						//case 0xf7:
						//case 0xf8:
						//case 0xf9:
						//case 0xfa:
						//case 0xfb:
						//case 0xfc:
						//case 0xfd:
						//case 0xfe:
						//case 0xff:
 
					}
				}
												break;
			case 0x10:	//	adc	r/m8, r8
			case 0x11:	//	adc	r/m16, r16
						//	adc	r/m32, r32
			case 0x12:	//	adc	r8, r/m8
			case 0x13:	//	adc	r16, r/m16
						//	adc	r32, r/m32
				_Instruction_Completion( 2 +
										_getDispSizeOfModRM(pTest[nIndex+1], bIsAddr16));
												break;	
			case 0x14:	//	adc	al, imm8
				_Instruction_Completion(2);		break;
			case 0x15:	//	adc	ax, imm16
						//	adc	eax, imm32
				if (bIsData16 != true)
					_Instruction_Completion(5);		
				else
					_Instruction_Completion(3);	
												break;						
			case 0x16:	//	push	ss
			case 0x17:	//	pop	ss
				_Instruction_1_Completion();	break;
			case 0x18:	//	sbb	r/m8, r8
			case 0x19:	//	sbb	r/m16, r16
						//	sbb	r/m32, r32
			case 0x1a:	//	sbb	r8, r/m8
			case 0x1b:	//	sbb	r16, r/m16
						//	sbb	r32, r/m32
				_Instruction_Completion( 2 +
										_getDispSizeOfModRM(pTest[nIndex+1], bIsAddr16));
												break;
			case 0x1c:	//	sbb	al, imm8
				_Instruction_Completion(2);		break;
			case 0x1d:	//	sbb	ax, imm16
						//	sbb	eax, imm32
				if (bIsData16 != true)
					_Instruction_Completion(5);		
				else
					_Instruction_Completion(3);	
												break;	
			case 0x1e:	//	push	ds
			case 0x1f:	//	pop	ds	
				Instruction_1_Completion();	break;
			case 0x20:	//	and	r/m8, r8
			case 0x21:	//	and	r/m16, r16
						//	and	r/m32, r32
			case 0x22:	//	and	r8, r/m8
			case 0x23:	//	and	r16, r/m16
						//	and	r32, r/m32
				_Instruction_Completion( 2 +
										_getDispSizeOfModRM(pTest[nIndex+1], bIsAddr16));
												break;	
			case 0x24:	//	and	al, imm8
				_Instruction_Completion(2);		break;
			case 0x25:	//	and	ax, imm16
						//	and	eax, imm32
				if (bIsData16 != true)
					_Instruction_Completion(5);
				else
					_Instruction_Completion(3);	
												break;
			case 0x26:	//	ES:
				_Instruction_1();				break;
			case 0x27:	//	daa
				_Instruction_1_Completion();	break;
			case 0x28:	//	sub	r/m8, r8
			case 0x29:	//	sub	r/m16, r16
						//	sub	r/m32, r32
			case 0x2a:	//	sub	r8, r/m8
			case 0x2b:	//	sub	r16, r/m16
						//	sub	r32, r/m32
				_Instruction_Completion( 2 +
										_getDispSizeOfModRM(pTest[nIndex+1], bIsAddr16));
												break;
			case 0x2c:	//	sub	al, imm8
				_Instruction_Completion(2);		break;
			case 0x2d:	//	sub	ax, imm16
						//	sub	eax, imm32
				if (bIsData16 != true)
					_Instruction_Completion(5);
				else
					_Instruction_Completion(3);	
												break;
			case 0x2e:	//	cs:
				_Instruction_1();				break;
			case 0x2f:	//	das
				_Instruction_1_Completion();	break;
			case 0x30:	//	xor	r/m8, r8
			case 0x31:	//	xor	r/m16, r16
						//	xor	r/m32, r32
			case 0x32:	//	xor	r8, r/m8
			case 0x33:	//	xor	r16, r/m16
						//	xor	r32, r/m32
				_Instruction_Completion( 2 +
										_getDispSizeOfModRM(pTest[nIndex+1], bIsAddr16));
												break;
			case 0x34:	//	xor	al, imm8
				_Instruction_Completion(2);		break;
			case 0x35:	//	xor	ax, imm16
						//	xor	eax, imm32
				if (bIsData16 != true)
					_Instruction_Completion(5);		
				else
					_Instruction_Completion(3);	
												break;
			case 0x36:	//	SS:
				_Instruction_1();				break;
			case 0x37:	//	aaa
				_Instruction_1_Completion();	break;
			case 0x38:	//	and	r/m8, r8
			case 0x39:	//	and	r/m16, r16
						//	and	r/m32, r32
			case 0x3a:	//	and	r8, r/m8
			case 0x3b:	//	and	r16, r/m16
						//	and	r32, r/m32
				_Instruction_Completion( 2 +
										_getDispSizeOfModRM(pTest[nIndex+1], bIsAddr16));
												break;
			case 0x3c:	//	cmp	al, imm8
				_Instruction_Completion(2);		break;
			case 0x3d:	//	cmp	ax, imm16
						//	cmp	eax, imm32
				if (bIsData16 == true)
					_Instruction_Completion(3);		
				else
					_Instruction_Completion(5);	
												break;
			case 0x3e:	//	DS:
				_Instruction_1();				break;
			case 0x3f:	//	aas
				_Instruction_1_Completion();	break;
			case 0x40:	//	inc		eax
			case 0x41:	//	inc		ecx
			case 0x42:	//	inc		edx
			case 0x43:	//	inc		ebx
			case 0x44:	//	inc		esp
			case 0x45:	//	inc		ebp
			case 0x46:	//	inc		esi
			case 0x47:	//	inc		edi
			case 0x48:	//	dec		eax
			case 0x49:	//	dec		ecx	
			case 0x4a:	//	dec		edx
			case 0x4b:	//	dec		ebx
			case 0x4c:	//	dec		esp
			case 0x4d:	//	dec		ebp
			case 0x4e:	//	dec		esi
			case 0x4f:	//	dec		edi
			case 0x50:	//	push	eax
			case 0x51:	//	push	ecx
			case 0x52:	//	push	edx
			case 0x53:	//	push	ebx
			case 0x54:	//	push	esp
			case 0x55:	//	push	ebp
			case 0x56:	//	push	esi
			case 0x57:	//	push	edi
			case 0x58:	//	pop		eax
			case 0x59:	//	pop		ecx
			case 0x5a:	//	pop		edx
			case 0x5b:	//	pop		ebx
			case 0x5c:	//	pop		esp
			case 0x5d:	//	pop		ebp
			case 0x5e:	//	pop		esi
			case 0x5f:	//	pop		edi
			case 0x60:	//	pushad
			case 0x61:	//	popad
				_Instruction_1_Completion();	break;
			case 0x62:	//	bound	r16, m16:16
						//	bound	r32, m16:32
				_Instruction_Completion( 2 +
										_getDispSizeOfModRM(pTest[nIndex+1], bIsAddr16));
												break;
			case 0x63:	//	arpl		r/m16, r16
						//	arpl		r/m32, r32
				_Instruction_Completion( 2 +
										_getDispSizeOfModRM(pTest[nIndex+1], bIsAddr16));
												break;
			case 0x64:	//	FS:
			case 0x65:	//	GS:
				_Instruction_1();				break;
 
			case 0x66:	//	資料長度轉換16bits模式
				bIsData16 = true;				break;
			case 0x67:	//	定址長度轉換16bits模式
				bIsAddr16 = true;				break;
			case 0x68:	//	push	imm16
						//	push	imm32
				if (bIsData16 != true)
					_Instruction_Completion(5);
				else
					_Instruction_Completion(3);	
												break;
			case 0x69:	//	imul	r16, r/m16, imm16
						//	imul	r32, r/m32, imm32
				if (bIsData16 == true)
					_Instruction_Completion( 4 +
										_getDispSizeOfModRM(pTest[nIndex+1], bIsAddr16));
				else
					_Instruction_Completion( 6 +
										_getDispSizeOfModRM(pTest[nIndex+1], bIsAddr16));
												break;
			case 0x6a:	//	push	imm8
				_Instruction_Completion(2);		break;
			case 0x6b:	//	imul	r16, r/m16, imm8
						//	imul	r32, r/m32, imm8
				_Instruction_Completion( 3 +
										_getDispSizeOfModRM(pTest[nIndex+1], bIsAddr16));
												break;
			case 0x6c:	//	insb
			case 0x6d:	//	insd
			case 0x6e:	//	outsb
			case 0x6f:	//	outsd
				_Instruction_1_Completion();	break;
			case 0x70:	//	jo	rel8
			case 0x71:	//	jno	rel8
			case 0x72:	//	jb	rel8
			case 0x73:	//	jnb	rel8
			case 0x74:	//	je	rel8
			case 0x75:	//	jne	rel8
			case 0x76:	//	jbe	rel8
			case 0x77:	//	ja	rel8
			case 0x78:	//	js	rel8
			case 0x79:	//	jns	rel8
			case 0x7a:	//	jpe	rel8	
			case 0x7b:	//	jpo	rel8
			case 0x7c:	//	jl	rel8
			case 0x7d:	//	jge	rel8
			case 0x7e:	//	jle	rel8
			case 0x7f:	//	jg	rel8		
				_Instruction_Completion(2);		break;
 
			case 0x80:
			case 0x81:
			case 0x82:		
			case 0x83:	
				{
					//TODO: opcode_0x80~83		
					//BYTE _REG	= (pTest[nIndex+1] & 0x38) >> 3;	
					//bool _DataW		= (pTest[nIndex] & 0x1);	
					//bool _SignExt	= (pTest[nIndex] & 0x2);	
 
					//80		op	r/m8, imm8
					//81		op	r/m16, imm16
					//		op	r/m32, imm32
					//82		op	r/m8, imm8
					//83		op	r/m16, imm8
					//		op	r/m32, imm8
 
					//switch ( _REG )
					//{
					//	case 0:	//	add
					//	case 1:	//	or
					//	case 2:	//	adc
					//	case 3:	//	sbb
					//	case 4:	//	and
					//	case 5:	//	sub
					//	case 6:	//	xor
					//	case 7:	//	cmp
					//}
 
					if (_Opcode1 == 0x81)
					{
						if (bIsData16 == true)
							_Instruction_Completion( 4 +
											_getDispSizeOfModRM(pTest[nIndex+1], bIsAddr16));
						else
							_Instruction_Completion( 6 +
											_getDispSizeOfModRM(pTest[nIndex+1], bIsAddr16));
					}
					else
					{
						_Instruction_Completion( 3 +
											_getDispSizeOfModRM(pTest[nIndex+1], bIsAddr16));
 
					}
				}								break;
 
			case 0x84:	//	test		r/m8, r8
			case 0x85:	//	test		r/m16, r16
						//	test		r/m32, r32
			case 0x86:	//	xchg		r8, r/m8
			case 0x87:	//	xchg		r16, r/m16
						//	xchg		r32, r/m32
			case 0x88:	//	mov		r/m8, r8	
			case 0x89:	//	mov		r/m16, r16
						//	mov		r/m32, r32			
			case 0x8a:	//	mov		r8, r/m8
			case 0x8b:	//	mov		r16, r/m16
						//	mov		r32, r/m32
			case 0x8c:	//	mov		r/m16, Sreg	
			case 0x8d:	//	lea		r16,m
						//	lea		r32,m
				_Instruction_Completion( 2 +
										_getDispSizeOfModRM(pTest[nIndex+1], bIsAddr16));
												break;
			case 0x8e:	//	mov		Sreg, r/m16,
				_Instruction_Completion( 2 +
										_getDispSizeOfModRM(pTest[nIndex+1], bIsAddr16));
												break;
			case 0x8f:	//	pop		r/m32
				_Instruction_Completion( 2 +
										_getDispSizeOfModRM(pTest[nIndex+1], bIsAddr16));
												break;
			case 0x90:	//	nop
			case 0x91:	//	xchg		eax, ecx
			case 0x92:	//	xchg		eax, edx
			case 0x93:	//	xchg		eax, ebx	
			case 0x94:	//	xchg		eax, esp
			case 0x95:	//	xchg		eax, ebp
			case 0x96:	//	xchg		eax, esi	
			case 0x97:	//	xchg		eax, edi
			case 0x98:	//	cwde
			case 0x99:	//	cwq		
				_Instruction_1_Completion();	break;
			case 0x9a:	//	call 		ptr16:16
						//	call 		ptr16:32
				if (bIsAddr16 != true)
					_Instruction_Completion(7);
				else
					_Instruction_Completion(5);
												break;
			case 0x9b:	//	wait
			case 0x9c:	//	pushfd
			case 0x9d:	//	popfd
			case 0x9e:	//	sahf
			case 0x9f:	//	lahf
				_Instruction_1_Completion();	break;
			case 0xa0:	//	mov	al, byte ptr [7C883728]	
			case 0xa1:	//	mov	eax, dword ptr [7C8836CC]
			case 0xa2:	//	mov	byte ptr [F50000D5], al
			case 0xa3:	//	mov	dword ptr [39FD0006], eax
				_Instruction_Completion(5);		break;
			case 0xa4:	//	movsb
			case 0xa5:	//	movsd
			case 0xa6:	//	cmpsb
			case 0xa7:	//	cmpsd
				_Instruction_1_Completion();	break;
			case 0xa8:	//	test		al, imm8	
				_Instruction_Completion(2);		break;
			case 0xa9:	//	test 		ax, imm16	
						//	test		eax, imm32
				if (bIsData16 != true)
					_Instruction_Completion(5);
				else
					_Instruction_Completion(3);
												break;		
			case 0xaa:	//	stosb
			case 0xab:	//	stosd
			case 0xac:	//	lodsb		
			case 0xad:	//	lodsd
			case 0xae:	//	scasb		
			case 0xaf:	//	scasd		
				_Instruction_1_Completion();	break;		
		//	case 0xb0:
		//	case 0xb1:
		//	case 0xb2:
		//	case 0xb3:
		//	case 0xb4:
		//	case 0xb5:
		//	case 0xb6:
		//	case 0xb7:
		//	case 0xb8:
		//	case 0xb9:
		//	case 0xba:
		//	case 0xbb:
		//	case 0xbc:
		//	case 0xbd:
		//	case 0xbe:
		//	case 0xbf:
		//	case 0xc0:		
		//	case 0xc1:			
			case 0xc2:	//	ret	imm16 (near return)
				_Instruction_Completion(3);		break;
			case 0xc3:	//	ret (near return)
				_Instruction_1_Completion();	break;
			case 0xc4:	//	les		r16, m16:16
						//	les		r32, m16:32
			case 0xc5:	//	lds		r16, m16:16
						//	lds		r32, m16:32
				_Instruction_Completion( 2 +
										_getDispSizeOfModRM(pTest[nIndex+1], bIsAddr16));
												break;
			case 0xc6:	//	mov	r/m8, imm8	
			case 0xc7:	//	mov	r/m16, imm16		
						//	mov	r/m32, imm32
				{
					//TODO: opcode_0xc6~c7		
					BYTE _REG	= (pTest[nIndex+1] & 0x38) >> 3;	
					switch ( _REG )
					{
						case 0:	//	mov
						case 1:	//	
						case 2:	//	
						case 3:	//	
						case 4:	//	
						case 5:	//	
						case 6:	//	
						case 7:	//	
					}
				}								break;
			case 0xc8:	//	enter	imm16, imm8		
				_Instruction_Completion(4);		break;
			case 0xc9:	//	leave
				_Instruction_1_Completion();	break;
			case 0xca:	//	ret		imm16  (for return)
				_Instruction_Completion(3);		break;
			case 0xcb:	//	retf
			case 0xcc:	//	int		3
				_Instruction_1_Completion();	break;
			case 0xcd:	//	int		imm8		
				_Instruction_Completion(2);		break;
			case 0xce:	//	into
			case 0xcf:	//	iret
				_Instruction_1_Completion();	break;
			case 0xd0:		
			case 0xd1:		
			case 0xd2:		
			case 0xd3:		
				{
					//TODO: opcode_0xd0~d3		
					BYTE _REG	= (pTest[nIndex+1] & 0x38) >> 3;	
					switch ( _REG )
					{
						case 0:	//	rol
						case 1:	//	ror
						case 2:	//	rcl
						case 3:	//	rcr
						case 4:	//	sal
						case 5:	//	shr
						case 6:	//	
						case 7:	//	sar
					}
				}								break;
			case 0xd4:	//	aam		imm8
			case 0xd5:	//	aad		imm8
				_Instruction_Completion(2);		break;
		//	case 0xd6:		
			case 0xd7:	//	xlat
				_Instruction_1_Completion();	break;
		//	case 0xd8:		
		//	case 0xd9:				
		//	case 0xda:			
		//	case 0xdb:			
		//	case 0xdc:			
		//	case 0xdd:			
		//	case 0xde:			
		//	case 0xdf:		
			case 0xe0:	//	loopne	rel8
			case 0xe1:	//	loope	rel8
			case 0xe2:	//	loop	rel8
			case 0xe3:	//	jecxz	rel8
				_Instruction_Completion(2);		break;
 
			case 0xe4:	//	in		al, imm8
			case 0xe5:	//	in		eax, imm8	
				_Instruction_Completion(2);		break;
			case 0xe6:	//	out		imm8, al	
				_Instruction_Completion(2);		break;
			case 0xe7:	//	out		imm8, ax
				_Instruction_Completion(2);		break;
			case 0xe8:	//	call	rel16
						//	call	rel32
				if (bIsAddr16 != true)
					_Instruction_Completion(5);
				else
					_Instruction_Completion(3);	
												break;							
			case 0xe9:	//	jmp		rel16
						//	jmp		rel32	
				if (bIsAddr16 != true)
					_Instruction_Completion(5);
				else
					_Instruction_Completion(3);
												break;
			case 0xea:	//	jmp 	ptr16:16
						//	jmp 	ptr16:32
				if (bIsAddr16 != true)
					_Instruction_Completion(7);
				else
					_Instruction_Completion(5);
												break;
			case 0xeb:	//	jmp		rel8	
				_Instruction_Completion(2);		break;
			case 0xec:	//	in		al, dx
			case 0xed:	//	in		eax, dx
			case 0xee:	//	out		dx, al	
			case 0xef:	//	out		dx, eax
				_Instruction_1_Completion();	break;
			case 0xf0:	//	lock
				_Instruction_1();				break;
		//	case 0xf1:	
			case 0xf2:	//	repnz
			case 0xf3:	//	repz
				_Instruction_1();				break;
			case 0xf4:	//	hlt
				_Instruction_1_Completion();	break;
			case 0xf5:	//	cmc
				_Instruction_1_Completion();	break;
			case 0xf6:	
				{
					//TODO: opcode_0xf6		
					BYTE _REG	= (pTest[nIndex+1] & 0x38) >> 3;	
					switch ( _REG )
					{
						case 0:	//	test	r/m8, imm8
						case 1:	//
						case 2:	//	not		r/m8
						case 3:	//	neg		r/m8
						case 4:	//	mul		r/m8
						case 5:	//	imul	r/m8
						case 6:	//	div		r/m8
						case 7:	//	idiv	r/m8
					}
				}								break;
			case 0xf7:	
				{
					//TODO: opcode_0xf7		
					BYTE _REG	= (pTest[nIndex+1] & 0x38) >> 3;	
					switch ( _REG )
					{
						case 0:	//	test		r/m16, imm16
								//	test		r/m32, imm32
						case 1:	//
						case 2:	//	not		r/m16
								//	not		r/m32
						case 3:	//	neg		r/m16
								//	neg		r/m32
						case 4:	//	mul		r/m16
								//	mul		r/m32
						case 5:	//	imul		r/m16
								//	imul		r/m32
						case 6:	//	div		r/m16
								//	div		r/m32
						case 7:	//	idiv		r/m16
								//	idiv		r/m32
					}
				}								break;
			case 0xf8:	//	clc
			case 0xf9:	//	stc
			case 0xfa:	//	cli
			case 0xfb:	//	sti
			case 0xfc:	//	cld
			case 0xfd:	//	std
				_Instruction_1_Completion();	break;
			case 0xfe:
				{
					//TODO: opcode_0xfe		
					BYTE _REG	= (pTest[nIndex+1] & 0x38) >> 3;	
					switch ( _REG )
					{
						case 0:	//	inc	r/m8
						case 1:	//	dec	r/m8
						case 2:	//
						case 3:	//
						case 4:	//
						case 5:	//
						case 6:	//
						case 7:	//
					}
				}								break;
			case 0xff:	
				{
					//TODO: opcode_0xff		
					BYTE _REG	= (pTest[nIndex+1] & 0x38) >> 3;	
 
					switch ( _REG )
					{
						case 0:	//	inc	r/m16
								//	inc	r/m32
						case 1:	//	dec	r/m16
								//	dec	r/m32
						case 2:	//
						case 3:	//
						case 4:	//	jmp	r/m16
								//	jmp	r/m32
						case 5:	//	jmp	m16:16
								//	jmp	m16:32
						case 6:	//
						case 7:	//
					}
				}								break;
			default:
				bCompletion = true;
		}
	} while (bCompletion != true);
 
	return nInde;
}