⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 protogen.bat

📁 这是asm驱动的开发包
💻 BAT
📖 第 1 页 / 共 5 页
字号:

IsLibExtensionSpecified proc uses esi ebx pLibraryPath:LPSTR

	_mov ebx, FALSE	; assume error

	mov esi, pLibraryPath
	.if esi != NULL
		invoke fstrlen, esi
		add esi, eax
		sub esi, 4			; ".lib"
		invoke lstrcmpi, addr g_szLibExtension, esi
		.if eax == 0
			inc ebx		; OK
		.endif
	.endif

	return ebx

IsLibExtensionSpecified endp

;:::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
;                                  IsFullPathSpecified                                              
;:::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::

IsFullPathSpecified proc uses esi pLibraryPath:LPSTR

	mov esi, pLibraryPath
	mov ecx, $invoke(fstrlen, esi)
	; search for back slash
    .while ecx
	    mov al, [esi]
    	.break .if al == '\'
	    inc esi
	    dec ecx
	.endw

	return ecx

IsFullPathSpecified endp

;:::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
;                                       CloseLibrary                                                
;:::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::

CloseLibrary proc

	.if g_pLibraryImage != NULL
		invoke UnmapViewOfFile, g_pLibraryImage
		_mov g_pLibraryImage, NULL
	.endif

	.if g_hLibraryMapping != NULL
		invoke CloseHandle, g_hLibraryMapping
		_mov g_hLibraryMapping, NULL
	.endif

	.if g_hLibraryFile != INVALID_HANDLE_VALUE
		invoke CloseHandle, g_hLibraryFile
		_mov g_hLibraryFile, INVALID_HANDLE_VALUE
	.endif

	ret

CloseLibrary endp

;:::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
;                                       OpenLibrary                                                 
;:::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::

OpenLibrary proc uses ebx pszLibraryName:LPSTR

	and ebx, FALSE		; clear flag OK

	invoke CreateFile, pszLibraryName, GENERIC_READ, 0, NULL, OPEN_EXISTING, 0, NULL
	.if eax != INVALID_HANDLE_VALUE
		mov g_hLibraryFile, eax
		invoke CreateFileMapping, g_hLibraryFile, NULL, PAGE_READONLY, 0, 0, NULL
		.if eax != NULL
			mov g_hLibraryMapping, eax
			invoke MapViewOfFile, g_hLibraryMapping, FILE_MAP_READ, 0, 0, 0
			.if eax != NULL
				mov g_pLibraryImage, eax
				inc ebx				; set flag OK
			.endif
		.endif
	.endif

	.if ebx == FALSE
		invoke CloseLibrary
	.endif

	return ebx

	ret

OpenLibrary endp

;:::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
;                                     FindAtBackward                                                
;:::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::

FindAtBackward proc pString:LPSTR

; returns zero-based position of '@'

option PROLOGUE:NONE
option EPILOGUE:NONE

Fix It may be buggy if @ symbol is first character and symbol name contains no more @ chars

	invoke fstrlen, [esp+4]
	mov edx, [esp+4]

	mov cl, '@'
	.while eax
		dec eax
		.break .if byte ptr [edx][eax] == cl
	.endw

;	.if ZERO?
;		inc eax		; '@' found
;	.endif

	ret (sizeof DWORD)

option PROLOGUE:PROLOGUEDEF
option EPILOGUE:EPILOGUEDEF

FindAtBackward endp

;:::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
;                                       IsNullImport                                                
;:::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::

IsNullImport proc pSymbol:LPSTR

option PROLOGUE:NONE
option EPILOGUE:NONE

Fix InString strstr

;	assume eax:SDWORD
	mov eax, [esp+4]
	invoke InString, 1, eax, $CTA0("NULL_THUNK_DATA")
	.if sdword ptr eax > 0
		ret (sizeof DWORD)
	.endif

	mov eax, [esp+4]
	invoke InString, 1, eax, $CTA0("IMPORT_DESCRIPTOR")	
	.if sdword ptr eax > 0
		ret (sizeof DWORD)
	.endif

;	assume eax:nothing

;Fix
;	.if $invoke(InString, 1, pSymbol, $CTA0("NULL_IMPORT_DESCRIPTOR"))
;		inc ebx
;	.endif

	xor eax, eax
	ret (sizeof DWORD)

option PROLOGUE:PROLOGUEDEF
option EPILOGUE:EPILOGUEDEF

IsNullImport endp

;:::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
;                             ConvertNumOfParamsFromSymbol                                          
;:::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::

ConvertNumOfParamsFromSymbol proc uses esi ebx pszSymbolName:LPSTR

; Returns number of parameters for this symbol or -1 if error

local acMessage[512]:CHAR

	or ebx, -1					; assume error
	mov esi, pszSymbolName

	invoke FindAtBackward, esi
	.if eax
		add eax, esi
		inc eax
		invoke atodw, eax

;		mov ecx, eax
;		and ecx, 011y
		.if !(eax & 011y)	; is argument count is not devisible by 4 ?
			shr eax, 2		; /sizeof arg = num of params
			.if eax < MAX_NUM_OF_PARAMS
				mov ebx, eax
IFDEF DEBUG
			.else
				; Too many params
				invoke wsprintf, addr g_acDebugMessage, $CTA0("\nWarning: Too many params %s\n\n"), esi
				invoke PrintConsole, addr g_acDebugMessage, 0
ENDIF
			.endif
		.else
			invoke wsprintf, addr acMessage, addr g_szArgCountNotDivBy4, esi
			invoke PrintConsole, addr acMessage, 0
		.endif

	.endif

	mov eax, ebx
	ret

ConvertNumOfParamsFromSymbol endp

;:::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
;                                     GetImportType                                                 
;:::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::

GetImportType proc pMemberHeader:PTR IMAGE_ARCHIVE_MEMBER_HEADER

option PROLOGUE:NONE
option EPILOGUE:NONE

; see 8.2. Import Type of Microsoft PExecutable and COFF Specification

	or eax, -1								; assume error
	mov ecx, [esp+4]
	add ecx, sizeof IMAGE_ARCHIVE_MEMBER_HEADER	; eax -> IMPORT_OBJECT_HEADER
	.if word ptr [ecx] == IMAGE_FILE_MACHINE_UNKNOWN		; Sig1	Must be IMAGE_FILE_MACHINE_UNKNOWN.
															; See Section 3.3.1, "Machine Types, " for more information.
		.if word ptr [ecx+2] == 0FFFFh						; Sig2	Must be 0xFFFF.
			movzx eax, (IMPORT_OBJECT_HEADER PTR [ecx]).rImport
			; ImportRec RECORD Reserved:11, NameType:3, Type2:2
			and eax, mask Type2		; return Type
		.endif
	.endif

	ret (sizeof DWORD)

option PROLOGUE:PROLOGUEDEF
option EPILOGUE:EPILOGUEDEF

GetImportType endp

;:::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
;                                   GetImportNameType                                               
;:::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::

GetImportNameType proc pMemberHeader:PTR IMAGE_ARCHIVE_MEMBER_HEADER

option PROLOGUE:NONE
option EPILOGUE:NONE

; see 8.3. Import Name Type of Microsoft PExecutable and COFF Specification

	or eax, -1								; assume error
	mov ecx, [esp+4]
	add ecx, sizeof IMAGE_ARCHIVE_MEMBER_HEADER	; eax -> IMPORT_OBJECT_HEADER
	.if word ptr [ecx] == IMAGE_FILE_MACHINE_UNKNOWN		; Sig1	Must be IMAGE_FILE_MACHINE_UNKNOWN.
															; See Section 3.3.1, "Machine Types, " for more information.
		.if word ptr [ecx+2] == 0FFFFh						; Sig2	Must be 0xFFFF.
			movzx eax, (IMPORT_OBJECT_HEADER PTR [ecx]).rImport
			; ImportRec RECORD Reserved:11, NameType:3, Type2:2
			and eax, mask NameType
			shr eax, 2	; return NameType
		.endif
	.endif

	ret (sizeof DWORD)

option PROLOGUE:PROLOGUEDEF
option EPILOGUE:EPILOGUEDEF

GetImportNameType endp

;:::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
;                                      FillSymEntries                                               
;:::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::

FillSymEntries proc uses ebx esi edi p2ndLinkerMember:LPVOID, pLibraryArrayOfSymbols:LPVOID, uNumberOfSymbols:UINT

local fOk:BOOL
local dwSymFlags:DWORD
local uNumberOfMembers:UINT
local paOffsetsToMembers:LPVOID
local paIndices:LPVOID
local dwCcType:DWORD
local uNumberOfParameters:UINT
local uAtPosition:UINT					; from the beginning of the string
local ccUndecSymbolNameLength:UINT
local pUndecSymbolNameStart:LPSTR
local uIndex:UINT
local pMemberHeader:LPVOID			; PTR IMAGE_ARCHIVE_MEMBER_HEADER
local byImportType:BYTE				; IMPORT_CODE, IMPORT_DATA, IMPORT_CONST
local byImportNameType:BYTE			; IMPORT_ORDINAL, IMPORT_NAME, IMPORT_NAME_NOPREFIX, IMPORT_NAME_UNDECORATE

	; Walks through String Table pointed by	pLibraryArrayOfSymbols.
	; String Table is a series of null-terminated strings that name all the symbols in the directory.
	; Each string begins immediately after the null byte in the previous string.

	; So we walks through it trying recognize the calling conversion of each symbol
	; And we fill SYM_ENTRYs

	and fOk, 0						; clear flag OK
	mov eax, p2ndLinkerMember

	push dword ptr [eax]
	pop uNumberOfMembers

	add eax, 4						; skip m = Number of Members
	mov paOffsetsToMembers, eax		; paOffsetsToMembers points to the first member address

	mov ecx, uNumberOfMembers
	shl ecx, 2						; sizeof pointer

	add eax, ecx					; eax -> Number of Symbols
	add eax, 4						; skip m = Number of Symbols
	mov paIndices, eax

	_try

	mov esi, pLibraryArrayOfSymbols
	assume esi:ptr CHAR
	lea edi, g_paCcEntries
	assume edi:ptr CC_ENTRY
	xor ebx, ebx
	.while ebx < uNumberOfSymbols

		; Skip _IMPORT_DESCRIPTOR_XXX, _NULL_IMPORT_DESCRIPTOR, XXX_NULL_THUNK_DATA etc...
		.if $invoke(IsNullImport, esi)
IFDEF DEBUG
			mov dwCcType, CC_WEIRD
			invoke wsprintf, addr g_acDebugMessage, $CTA0("Skip: %s\n"), esi
			invoke PrintConsole, addr g_acDebugMessage, 0
ENDIF
			jmp @F
		.endif

		Fix May be init dwCcType with CC_WEIRD
		or dwCcType, -1					; init calling convention type
		and dwSymFlags, 0							; reset
		or uNumberOfParameters, -1					; reset to not recognized
		and ccUndecSymbolNameLength, 0				; init with 0
		and pUndecSymbolNameStart, NULL
;		or dwImportType, 0							; init with IMPORT_CODE

		mov ecx, ebx
		shl ecx, 1					; * sizeof Indice
		add ecx, paIndices
		movzx ecx, word ptr [ecx]
		mov uIndex, ecx

		; VA to symbol's IMAGE_ARCHIVE_MEMBER_HEADER
		dec ecx						; make it zero-based
		shl ecx, 2					; * sizeof pointer
		add ecx, paOffsetsToMembers
		mov ecx, [ecx]
		add ecx, g_pLibraryImage
		mov pMemberHeader, ecx


		invoke GetImportType, pMemberHeader
		mov byImportType, al
		.if ( eax == IMPORT_OBJECT_DATA ) || ( eax == IMPORT_OBJECT_CONST )
			or dwSymFlags, FF_SYM_VARIABLE
		.endif


		invoke GetImportNameType, pMemberHeader
		mov byImportNameType, al


		invoke InString, 1, esi, addr g_sz__imp_
		.if eax == 1
			or dwSymFlags, FF_SYM___IMP_
			add esi, sizeof g_sz__imp_ - 1			; skip '__imp_'
		.endif


		invoke ConvertNumOfParamsFromSymbol, esi
		mov uNumberOfParameters, eax


		.if [esi] == '@'							; is it fastcall here ?
			invoke FindAtBackward, esi
			.if eax

				mov ecx, eax
				dec eax
				mov ccUndecSymbolNameLength, eax

				mov eax, esi
				inc eax
				mov pUndecSymbolNameStart, eax

				mov dwCcType, CC_FASTCALL
IFDEF DEBUG
			.else
				mov dwCcType, CC_WEIRD
ENDIF
			.endif

		.elseif [esi] == '_'						; is it stdcall or cdecl here ?
			invoke FindAtBackward, esi
			mov uAtPosition, eax
			.if eax
				; stdcall here

				mov ecx, eax
				dec eax
				mov ccUndecSymbolNameLength, eax

				mov dwCcType, CC_STDCALL
			.else
				; cdecl here

				invoke fstrlen, esi
				dec eax
				mov ccUndecSymbolNameLength, eax

				mov dwCcType, CC_CDECL

comment ^

				g_NumOfVariables

				; cdecl here
				; les't decide is it a function or exported variable
				mov eax, pOffsets
				mov edx, ebx
				shl edx, 2

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -