跳转到主要内容

神秘的汇编代码

主标签

下面是一段神秘汇编代码,编译后可以给LISP调用,至于方法,以后再说。

 	.data
pStack  qword 0     ;栈位置
dReal8  real8 0.0

	.code
;extern "C" _INT CallAPI64_( _UINT lpFunction, DYNAPARM Param[],size_t nArgs,_INT Flags,LPVOID pRet, size_t nRetSiz);
;参数说明: 函数地址-RCX, 参数-RDX, 参数数目-R8, 调参方式-R9, 返回结果-[rsp+40], 返回大小-[rsp+48]
CallAPI64_ proc pFunc:qword,Param:qword,nArgs:qword,Flags:qword,pRet:qword,nRet:qword
SaveStack:
	mov     pStack,rsp		;保存栈

SaveArgs:
	mov     pFunc,rcx       ;函数地址
	mov     r11,r8          ;参数个数 
    
AdjustStack:               
    sub     rsp,20h         ;留给代码运行空间
	test    r11,1			;测试参数个数是否奇数
	jz      ZeroArg         ;偶数跳转
	sub     rsp,8			;奇数的话要平栈

ZeroArg:
	cmp     r11,0           ;无参数
	jz      CallAPI         ;直接call

SaveData:
	cmp		r11,5           ;是否5个参数
	jb		FourArgs        ;小于则跳转到4个参数段

FromLast:					 
    imul	rax,r8,16		;每个参数16个字节,16*参数个数 
    sub     rax,8           ;每个参数的第8个字节存储参数的值
	add     rax,rdx         ;参数偏移值=Param[n-1]
	mov     rcx,r8          ;参数个数  
	sub		rcx,4           ;大于4则只循环读取4个以上的

GetArgs: 
	push    [rax]           ;参数入栈
	sub		rax,16          ;每个参数16个字节
    loop	GetArgs

FourArgs:
	mov 	rax,rdx         ;rax=参数组  
	cmp     r11,4			;4个参数
	jb      ThreeArgs
	mov     r10b,[rax+30h]
	cmp     r10b,2
    jnz     @F
	movsd   xmm3,mmword ptr [rax+38h]
@@:
    mov     r9,[rax+38h]
	push    r9

ThreeArgs:
	cmp     r11,3			;3个参数
	jb      TwoArgs
	mov     r10b,[rax+20h]
	cmp     r10b,2
    jnz     @F
	movsd   xmm2,mmword ptr [rax+28h]
@@:
	mov     r8,[rax+28h]
	push    r8

TwoArgs:
	cmp     r11,2			;2个参数
	jb      OneArg
	mov     r10b,[rax+10h]
	cmp     r10b,2
    jnz     @F
	movsd   xmm1,mmword ptr [rax+18h]
@@:
	mov     rdx,[rax+18h]
	push    rdx

OneArg:						;1个参数			
	mov     r10b, [rax]
	cmp     r10b, 2
	jnz     @F
	movsd   xmm0,mmword ptr [rax+8]
@@:
	mov     rcx,[rax+8]		
	push    rcx

CallAPI:
    call	pFunc
	cmp     pRet,0
	jz      RestoreStack
	mov     rax,pRet 
	movsd   mmword ptr [rax],xmm0  
	  
RestoreStack:
	mov     rsp,pStack
	ret

CallAPI64_ endp
MyCall_ proc  
    local	pRSP:qword
	local	pFunc:qword

	mov		pRSP,rsp
	mov		pFunc,RCX
	mov		R11,RDX			;参数个数
 
	sub     rsp,100h
	test    R11,1
	jz      @F
	sub     rsp,8
@@:
	cmp     R11,0
	jz      CallAPI

	cmp		R11,5
	jb		FourArgs

FromLast:					 
    imul	RAX,R11,8		;每个参数16个字节,16*参数个数 
	sub     RAX,8           ;每个参数地址
	add     rax,r8			;每个参数地址
	mov		rcx,R11         ;参数个数   
	sub		rcx,4           ;大于4则只是读取4个以上的
    
GetArgs: 
	push	[RAX]           ;参数入栈
	sub		rax,8           ;每个参数16个字节
    loop	GetArgs

FourArgs:
	mov		RAX,R8 
	cmp		R11,4
	jb		ThreeArgs
	mov     R9,[RAX+18h]
	push    R9

ThreeArgs:
	cmp		R11,3
	jb		TwoArgs
	mov     R8,[RAX+10h]
	push    R8
	
TwoArgs:
	cmp     R11,2
	jb      OneArg
	mov     RDX,[RAX+8h]
	push    RDX

OneArg:
	mov     RCX,[RAX]
	push    RCX

CallAPI:

	call	pFunc
	mov     RSP,pRSP
	ret
MyCall_ endp
; int __cdecl sub_18011CC0(int (__cdecl *)(int), int, int)
CallAPI_ proc  
	push    rdi
	push    rbx
	push    r12
	push    r13
	push    r14
	mov     rbx, rcx
	mov     r13, rdx
	mov     r14, r8
	cmp     r13, 5
	jl      short save4
	imul    r12, r13, 8
	jmp     short save5

	save4:                      
	mov     r12, 20h 
    
save5:    
	sub     rsp, r12
	mov     rdi, rsp
	imul    r12, r13, 2
	mov     rcx, r12
	mov     eax, 0CCCCCCCCh
	rep stosd
	mov     r12, rdx

Arg5:                       
	cmp     r12, 5
	jl      short Arg4
	sub     r12, 1
	mov     rcx, qword ptr [r14+r12*8]
	mov     qword ptr [rsp+r12*8], rcx
	jmp     short Arg5

Arg4:                       
	cmp     r12, 4
	jnz     short Arg3
	sub     r12, 1
	mov     r9, [r14+r12*8]

Arg3:
	cmp     r12, 3
	jnz     short Arg2
	sub     r12, 1
	mov     r8, [r14+r12*8]

Arg2:                      
	cmp     r12, 2
	jnz     short Arg1
	sub     r12, 1
	mov     rdx, [r14+r12*8]

Arg1:
	sub     r12, 1
	mov     rcx, [r14]

local_call:
	call    rbx

	cmp     r13, 5
	jl      short Restore4
	imul    r12, r13, 8
	jmp     short Restore

	Restore4:                       
	mov     r12, 20h 

Restore:                      
	add     rsp, r12
	pop     r14
	pop     r13
	pop     r12
	pop     rbx
	pop     rdi
	ret

CallAPI_ endp
    end

分类