www.88bifa.com:函数调用约定

总结

除了__cdecl(以及__clrcall卡塔 尔(阿拉伯语:قطر‎,别的的都以被调用者清除货仓。

and C++ Calling Convention 调用约定(Calling
Convention) 是Computer编制程序中二个相比底层的布置性,它最主要涉嫌:
函数参数通过存放器传递照旧栈? 函数…

1.导出函数名的标题

 

__fastcall

法斯特 Calling
Convention,飞速调用约定。通过行使存放器消释功效难点。特点:

函数参数部分通过寄放器传递,函数中最左的七个DWO凯雷德D(寄存器大小是双字卡塔尔恐怕更加小的参数,通过存放器传递。剩下的从右到左货仓传递。
函数名整顿:“@函数名@函数参数字节大小十进制”。 再次来到形式同__stdcall。

在project中树立三个def文件,写入

www.88bifa.com 1

__cdecl

C Declaration Calling
Convention,C表明调用约定。它是C和C++默许的调用约定。特点:

旅馆由调用者湮灭(手动消亡卡塔尔。 参数从右到左压栈。
扶植可变参数(函数本身并不知道本身有稍许个参数,由此要求调用者来消灭卡塔尔国。
编写翻译后函数名改编为:“_函数名”。如_funcname。

__stdcall 超级多时候被DLL中程导弹出函数(函数名及其调用约定卡塔尔国??

干什么只有__cdecl的调用约定协理可变参数,而__stdcall就不辅助?

C and C++ Calling Convention

调用约定(Calling Convention)
是Computer编制程序中三个相比较底层的两全,它首要涉及:

函数参数通过寄放器传递照旧栈? 函数参数从左到右照旧从右到左压栈?
是不是扶助可变参数函数(vararg function or variadic function卡塔尔。
是或不是要求函数原型? 调用者(caller)依然被调用者(called or
callee)清理货仓?

在C和C++中有三种调用约定:__cdecl, __stdcall, __fastcall,
__thiscall, __clrcall, __vectorcall。下直面比下二种调用约定。

C 语言有 __cdecl、__stdcall、__fastcall、naked、__pascal。

上面详细介绍如上种种调用方式:

__stdcall

Standard Calling Convention,规范调用约定。特点:

调用者解除仓库。
参数从右到坐压栈(和__cdecl同样卡塔尔,如若调用类的积极分子函数,最后压入this指针。
必要贰个函数原型,不协理变参函数。
函数名整顿:“_函数名@参数字节大小十进制”。如[email protected]。

C++ 语言有
__cdecl、__stdcall、__fastcall、naked、__pascal、__thiscall,比
C 语言多出豆蔻梢头种 __thiscall 调用方式。

_fastcall 和
__thiscall涉及的贮存器由编写翻译器决定,由此不可能用作跨编译器的接口。所以Windows上的COM对象接口都定义为_stdcall调用情势。

__vectorcall

渴求尽量在寄放器中传送参数。函数名整编为”@@函数名@参数字节数十进制”。这是微软温馨加上的正规。

另外,关键字
__stdcall、__cdecl和__fastcall能够平素加在要出口的函数前。它们对应的命令行参数分别为/Gz、/Gd和/Gr。缺省状态为/Gd,即__cdecl。为
pascal 调用约定。pascal
语言是中期很宽泛的生机勃勃种传授用微Computer程序设计语言,其语法严厉。参数依照从右至左的办法入栈,函数自个儿清理旅舍,重临值在EAX中。

__cdecl调用约定又称作 C 调用约定,是 C/C++ 语言缺省的调用约定。表示C语言暗中同意的函数调用方法,参数依照从右至左的方法入栈,函数自身不清理栈,此专门的学业由调用者担当,再次回到值在EAX中。由于由调用者清理栈,所以同意可变参数函数存在,如int
sprintf(char* buffer,const char* format,…);。

__88必发在线娱乐 ,clrcall

__clrcall是C++ .Net里面的。

extern “C” void__declspec(dllexport) fun();

除此以外还要理解函数参数字传送递进度中饭店是何等生长和转移的,从仓库低地址到高地址,依次存款和储蓄被调用函数局地变量,上风姿罗曼蒂克函数货仓桢基址,函数再次回到地址,参数1, 参数2,
参数3..

__thiscall

重视用以缓和this指针难题,使用存放器传递this指针。再次来到格局同__stdcall.

Ps,如果导出的函数名带一些修饰,如:?fun@@YAXXZ,用GetProcAddress()函数直接调用“?fun@@YAXXZ”也是可以找到函数的。

调用饭店清理

1.调用者灭亡栈。

2.被调用函数回去后消亡栈。

 

X64下

调用约定简化了:生机勃勃律选择__fastcall,前四个参数用 RCX、卡宴DX、Wrangler8 和
奥迪Q39传递,除了这八个外加RAX、RAV410、昂Cora11,别的存放器都以非易失的。

 

stdcall cdecl fastcall thiscall naked call

 

在函数名修饰约定方面,它和前两个均差别。__fastcall格局的函数接纳存放器传递参数,VC将函数编写翻译后会在函数名前边加上”@”前缀,在函数名后拉长”@”和参数的字节数。

那是 C++ 语言特有的风流罗曼蒂克种调用方式,用于类成员函数的调用约定。假使参数明确,this 指针寄存于 ECX 贮存器,函数本人清理酒馆;要是参数不分明,this指针在具有参数入栈后再入栈,调用者清理栈。__thiscall 不是至关心珍惜要字,技术员不可能采纳。参数依据从右至左的章程入栈。

_fastcall

C++ 语言有 __cdecl、__stdcall、__fastcall、naked、__pascal、__thiscall,比 C 语言多出少年老成种 __thiscall 调用情势。

是帕斯Carl方式清理C情势压栈,平时用于Win32
Api中,函数选择从右到左的压栈方式,
本人在脱离时清空仓库。VC将函数编译后会在函数名前面加上下划线前缀,在函数名后增进”@”和参数的字节数。

C 语言有 __cdecl、__stdcall、__fastcall、naked、__pascal。

_stdcall

实际上__cdecl和__stdcall函数参数都以从右到左入栈,它们的界别在于由什么人来清栈,__cdecl由外界调用函数清栈,而__stdcall由被调用函数自身清栈,
显明对于可变参数的函数,函数本人无法通晓外界函数调用它时传了有个别参数,所以不得已援救被调用函数本身清栈(__stdcall),
所以可变参数只好用__cdecll.

    在VC中,能够安装默许的调用约定,设置路线为:

那是 pascal 语言的调用约定,跟 __stdcall 雷同,参数依据从右至左的法子入栈,函数本人清理旅社,再次来到值在EAX中。VC 中已经废除了这种调用方式,因而在写 VC 程序时,建议使用 __stdcall 代替。

导出函数的调用约定和平运动用那么些函数时宣称的调用约定必得大器晚成致,不然程序会崩溃。

针对参数列表类型的函数。就可以变参数函数:

当使用1-4的调用约准时,尽管必要的话,进入函数时编写翻译器会发生代码来保存ESI,EDI,EBX,EBP寄放器,退出函数时则发出代码苏醒这么些寄放器的内容。

3、__fastcall

  

2、__stdcall

别的,在函数名修饰约定方面也迥然分化。
_cdecl是C和C++程序的缺省调用情势。每一个调用它的函数都包罗清空货仓的代码,所以产生的可推行文件大小会比调用_stdcall函数的大。函数接纳从右到左的压栈形式。VC将函数编译后会在函数名后边加上下划线前缀。

naked 是一个相当少见的调用约定,日常不建议选取。编写翻译器不会给这种函数增添开头化和清理代码,更出格的是,你无法用return重回重临值,只可以用插队汇编重回结果,此调用约定必需跟 __declspec 同一时候选用。比方定义二个求和次序,如__declspec(naked)
int  add(int a,int b);。

那是 pascal 语言的调用约定,跟 __stdcall
同样,参数遵照从右至左的不二诀窍入栈,函数本身清理旅馆,重临值在EAX中。VC
中曾经打消了这种调用方式,由此在写 VC 程序时,提出使用 __stdcall
代替。

参数字传送递顺序

1.从右到左依次入栈:__stdcall,__cdecl,__thiscall,__fastcall

2.从左到右依次入栈:__pascal

②      Def文件

 

参预extern
“C”是报告编写翻译器,用C的编写翻译方式变通文书,无需走入参数作为修饰

 

3、__fastcall