我有一些代码(我假设是Delphi),它仅使用EAX和EDX寄存器来传递参数(当然,如果需要更多,则使用堆栈)。我查看了哪种调用约定将匹配,但是我还没有找到仅使用EAX和EDX的调用约定。
AFAIK Borland fastcall / register使用的是EAX和EDX,但也使用ECX,这里不是这种情况。

我能以某种方式告诉IDA这个调用约定吗?我该怎么办?

评论

您可以粘贴一些使用EAX,EDX和不使用ECX的堆栈的代码吗?

在更详细地研究之后,似乎确实使用了ECX,并且代码通常不需要两个以上的参数。当我查看带有更多参数的函数时,我意识到这是EAX / EDX / ECX / PUSH的标准...

好的,那谜团就解决了。

#1 楼

您可以通过编辑(键Y)并添加名称来添加函数类型。

我写了一个页面来提醒我有关在ASM级别调用约定的信息。

简介

原始调用是myfunc(0,1,2,3,4)


标准顺序是第一个参数被最后推送。
标准堆栈调整是'callee cleanup'-返回后,堆栈应该没有调用参数。

注意:堆栈看起来像调用顺序一样。

stdcall(仅堆栈)

push    4
push    3
push    2
push    1
push    0
call    myfunc
xor     eax,eax
retn    10


Fastcall (ecx,edx)

这实际上是Microsoft的fastcall。

push    4
push    3
push    2
mov     edx,1
xor     ecx,ecx
call    myfunc
xor     eax,eax
retn    10


CDECL和syscall(调用程序清理)

>
push    4
push    3
push    2
push    1
push    0
call    myfunc
add     esp,014
xor     eax,eax
retn    10


Pascal(反向命令,即使没有使用ebx,也保存ebx ...)

push    ebx
push    0
push    1
push    2
push    3
push    4
call    myfunc
xor     eax,eax
pop     ebx
retn    10


Fortran /警告(eax, edx,ebx,ecx,然后是堆栈-保存了ebx)

显然,尚不清楚fortran调用约定是什么,而且这一点甚至与raymond帖子的__fortran调用约定不同FORTRAN使用的调用约定。

push    ebx
push    4
mov     ecx,3
mov     ebx,2
mov     edx,1
xor     eax,eax
call    myfunc
xor     eax,eax
pop     ebx
retn    10


Delphi“注册”调用约定(默认)

使用eaxecxedx作为前三个参数。其他参数以相反顺序推入堆栈。

push    3
push    4
mov     ecx, 2
mov     edx, 1
xor     eax,eax
call    myfunc
xor     eax,eax
retn    10


评论


每个示例末尾的retn 10行是一条红色鲱鱼,可能会造成混淆。它的值与示例对myfunc的调用无关。

–杂件
17年1月20日在11:17

#2 楼

如果遇到任何标准调用约定都未涵盖的调用约定,则可以使用__usercall或__userpurge调用约定,它们允许您指定将哪些参数传递到哪里。语法为

return_type __usercall function_name<registers>(arg0_type arg0<registers>, arg1_type arg1<registers>, ...)


其中,如果参数占用多个寄存器,则寄存器可以是由':'字符分隔的一组寄存器。

如果您真的很习惯调用约定,可以使用此处描述的完整语法。在这里,您不仅可以简单地输入包含参数的寄存器名称,还可以描述在寄存器或堆栈元素的各个部分中传递的参数。仅当寄存器被

<argoff:register^regoff.size>



<argoff:^stkoff.size>


#3 楼

Delphi和Borland C ++ Builder在EAX调用约定的变体中,将EDXECX__fastcall用作前三个参数。因此,如果在Options-Compiler中选择“ Delphi”或“ C ++ Builder”,则只需在函数原型中使用__fastcall-无需求助于__usercall

评论


原始张贴者说,调用约定仅使用EAX和EDX,而不使用ECX。对我来说听起来很奇怪。

–彼得·安德森(Peter Andersson)
13-10-28在12:13