1.__cdecl:C 和C++ 程序的缺省调用规范。
2.__stdcall:标准调用约定(即WINAPI调用约定),也就是pascal调用约定。
3.Delphi就是采用__stdcall约定,所以在调用和C程序的动态库时就会出现因为函数名称改编问题导致找不到函数名的问题。
4.函数调用约定的作用:
1).指定函数在被调用时形参的压栈顺序(__cdecl和__stdcall都是采用从右到左的形参压栈顺序),以及指定函数调用结束形参出栈顺序(__cdecl由调用方把参数弹出栈;__stdcall函数体在返回前把参数弹出栈)。
2).函数名改编(添加修饰)约定:__cdecl和__stdcall生成的函数修饰名机制不一样。
5.__cdecl:可通过在前面加上 extern “C”以去除函数名修饰。也可通过 .def 文件去除函数名修饰。注:__cdecl调用方式在没有指定extern “C”时会改编函数名。
6.__stdcall:好像只能通过 .def 文件去除函数名修饰。注:__stdcall调用方式不管是否指定extern “C”都会改编函数名,只不过在指定了extern “C”后改编的函数名更短而与。
7.关于程序编译时函数改名相关。以函数 int add(int a,int b) 为例
1).__cdecl(缺省调用规范):?add@@YAHHH@Z 函数名被改编了。
l 分析:?函数名开头;@Z函数名结束;@@YA表示__cdecl调用方式;HHH三个H中第一个表示返回类型,第二个指第一形参类型,第三个指第二个形参类型,以此类推。
2).extern “C” __cdecl:add 函数名没有改编。
3).__stdcall(标准调用规范):?add@@YGHHH@Z 函数名被改编了。
l 分析:?函数名开头;@Z函数名结束;@@YG表示__stdcall调用方式;HHH三个H中第一个表示返回类型,第二个指第一形参类型,第三个指第二个形参类型,以此类推。
4).extern “C” __ stdcall:_add@8 函数名被改编了。
分析:_函数开始;@形参字节开始;8表示形参有8个字节。