日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

函数调用方式__stdecl _stdcall _fastcall __thiscall介绍

發布時間:2024/4/11 编程问答 42 豆豆
生活随笔 收集整理的這篇文章主要介紹了 函数调用方式__stdecl _stdcall _fastcall __thiscall介绍 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

__cdecl?是C DECLaration的縮寫(declaration,聲明),表示C語言默認的函數調用方法:所有參數從右到左依次入棧,這些參數由調用者清除,稱為手動清棧。被調用函數不會要求調用者傳遞多少參數,調用者傳遞過多或者過少的參數,甚至完全不同的參數都不會產生編譯階段的錯誤。

?

_stdcall?是StandardCall的縮寫,是C++的標準調用方式:所有參數從右到左依次入棧,如果是調用類成員的話,最后一個入棧的是this指針。這些堆棧中的參數由被調用的函數在返回時清除,使用的指令是 retnX,X表示參數占用的字節數,CPU在ret之后自動彈出X個字節的堆棧空間。稱為自動清棧。函數在編譯的時候就必須確定參數個數,并且調用者必須嚴格的控制參數的生成,不能多,不能少,否則返回后會出錯。

?

_fastcall?是編譯器指定的快速調用方式。由于大多數的函數參數個數很少,使用堆棧傳遞比較費時。因此_fastcall通常規定將前兩個(或若干個)參數由寄存器傳遞,其余參數還是通過堆棧傳遞。不同編譯器編譯的程序規定的寄存器不同。返回方式和_stdcall相當。

?

?

  ?__thiscall?是為了解決類成員調用中this指針傳遞而規定的。__thiscall要求把this指針放在特定寄存器中,該寄存器由編譯器決定。VC使用ecx,Borland的C++編譯器使用eax。返回方式和_stdcall相當。

?

?

  _fastcall?和?__thiscall涉及的寄存器由編譯器決定,因此不能用作跨編譯器的接口。所以Windows上的COM對象接口都定義為_stdcall調用方式。

?

?

調用類型

參數入棧順序

由誰負責清棧

寄存器傳遞

__stdecl

從右到左依次入棧

調用函數

this

_stdcall?

從右到左依次入棧

調用函數

this

_fastcall

從右到左依次入棧

調用函數

this??和參數

__thiscall

從右到左依次入棧

調用函數

this

默認(vs2005)

從右到左依次入棧

調用函數

this

?

?

?

?

?

?

?

?

下面來通過代碼來查看一下他們到底是如何傳遞參數和出入棧:

?

?

[cpp]?view plaincopyprint?
  • class?TestCallType??
  • {??
  • public:??
  • ????int?default_call(int?,int);??
  • ????int?__cdecl?????__cdecl_call(int?a,?int?b);??
  • ????int?_stdcall????_stdcall_call(int?a,?int?b);??
  • ????int?_fastcall???_fastcall_call(int?a,?int?b);??
  • ????int?__thiscall??_thiscall_call(int,int);??
  • ????int?x;??
  • };??
  • int?TestCallType::default_call(int?a,?int?b)??
  • {??
  • ????this->x?=?a?+?b;??
  • ????return?this->x;??
  • }??
  • int?TestCallType::__cdecl_call(int?a,?int?b)??
  • {??
  • ????this->x?=?a?+?b;??
  • ????return?this->x;??
  • }??
  • int?TestCallType::_stdcall_call(int?a,?int?b)??
  • {??
  • ????this->x?=?a?+?b;??
  • ????return?this->x;??
  • }??
  • int?TestCallType::_fastcall_call(int?a,?int?b)??
  • {??
  • ????this->x?=?a?+?b;??
  • ????return?this->x;??
  • }??
  • int?TestCallType::_thiscall_call(int?a,?int?b)??
  • {??
  • ????this->x?=?a?+?b;??
  • ????return?this->x;??
  • }??
  • ?

    ?

    調用的地方反匯編出來如下:

    [cpp]?view plaincopyprint?
  • int?_tmain(int?argc,?_TCHAR*?argv[])??
  • {??
  • 004115B0??push????????ebp????
  • 004115B1??mov?????????ebp,esp???
  • 004115B3??sub?????????esp,0CCh???
  • 004115B9??push????????ebx????
  • 004115BA??push????????esi????
  • 004115BB??push????????edi????
  • 004115BC??lea?????????edi,[ebp-0CCh]???
  • 004115C2??mov?????????ecx,33h???
  • 004115C7??mov?????????eax,0CCCCCCCCh???
  • 004115CC??rep?stos????dword?ptr?es:[edi]???
  • ????TestCallType?call_type;??
  • ????call_type.default_call(1,?2);??
  • 004115CE??push????????2??????????????????????/*?參數入棧?*/??
  • 004115D0??push????????1??????????????????????/*?參數入棧?*/??
  • 004115D2??lea?????????ecx,[call_type]????????/*?this指針?*/??
  • 004115D5??call????????TestCallType::default_call?(411113h)???
  • ????call_type.__cdecl_call(1,?2);??
  • 004115DA??push????????2?????????????????????/*?參數入棧?*/??
  • 004115DC??push????????1?????????????????????/*?參數入棧?*/??
  • 004115DE??lea?????????eax,[call_type]???????/*?this指針?*/??
  • 004115E1??push????????eax????
  • 004115E2??call????????TestCallType::__cdecl_call?(41112Ch)???
  • 004115E7??add?????????esp,0Ch???????????????/*?調用者負責清棧?*/??
  • ????call_type._fastcall_call(1,2);??
  • 004115EA??push????????2?????????????????????/*?參數入棧?*/??
  • 004115EC??mov?????????edx,1?????????????????/*?第一個參數通過寄存器傳遞?*/??
  • 004115F1??lea?????????ecx,[call_type]???????/*?this指針?*/??
  • 004115F4??call????????TestCallType::_fastcall_call?(41100Ah)???
  • ????call_type._stdcall_call(1,2);??
  • 004115F9??push????????2??????
  • 004115FB??push????????1??????
  • 004115FD??lea?????????eax,[call_type]???????/*?this指針?*/??
  • 00411600??push????????eax????
  • 00411601??call????????TestCallType::_stdcall_call?(4110EBh)???
  • ????call_type._thiscall_call(1,?2);??
  • 00411606??push????????2??????
  • 00411608??push????????1??????
  • 0041160A??lea?????????ecx,[call_type]???????/*?this指針?*/??
  • 0041160D??call????????TestCallType::_thiscall_call?(41117Ch)???
  • ????return?0;??
  • 0041161E??xor?????????eax,eax???
  • }??
  • ?

    ?

    函數定義的地方反匯編:

    [cpp]?view plaincopyprint?
  • int?TestCallType::default_call(int?a,?int?b)??
  • {??
  • 004113D0??push????????ebp????
  • 004113D1??mov?????????ebp,esp???
  • 004113D3??sub?????????esp,0CCh???
  • 004113D9??push????????ebx????
  • 004113DA??push????????esi????
  • 004113DB??push????????edi????
  • 004113DC??push????????ecx????
  • 004113DD??lea?????????edi,[ebp-0CCh]???
  • 004113E3??mov?????????ecx,33h???
  • 004113E8??mov?????????eax,0CCCCCCCCh???
  • 004113ED??rep?stos????dword?ptr?es:[edi]???
  • 004113EF??pop?????????ecx????
  • 004113F0??mov?????????dword?ptr?[ebp-8],ecx???
  • ????this->x?=?a?+?b;??
  • 004113F3??mov?????????eax,dword?ptr?[a]???
  • 004113F6??add?????????eax,dword?ptr?[b]???
  • 004113F9??mov?????????ecx,dword?ptr?[this]???
  • 004113FC??mov?????????dword?ptr?[ecx],eax???
  • ????return?this->x;??
  • 004113FE??mov?????????eax,dword?ptr?[this]???
  • 00411401??mov?????????eax,dword?ptr?[eax]???
  • }??
  • 00411403??pop?????????edi????
  • 00411404??pop?????????esi????
  • 00411405??pop?????????ebx????
  • 00411406??mov?????????esp,ebp???
  • 00411408??pop?????????ebp???????????????????/*?默認調用是_stdcall?被調用函數負責清棧?*/??
  • 00411409??ret?????????8??????
  • ---?No?source?file?-------------------------------------------------------------??
  • ??
  • int?TestCallType::__cdecl_call(int?a,?int?b)??
  • {??
  • 00411420??push????????ebp????
  • 00411421??mov?????????ebp,esp???
  • 00411423??sub?????????esp,0C0h???
  • 00411429??push????????ebx????
  • 0041142A??push????????esi????
  • 0041142B??push????????edi????
  • 0041142C??lea?????????edi,[ebp-0C0h]???
  • 00411432??mov?????????ecx,30h???
  • 00411437??mov?????????eax,0CCCCCCCCh???
  • 0041143C??rep?stos????dword?ptr?es:[edi]???
  • ????this->x?=?a?+?b;??
  • 0041143E??mov?????????eax,dword?ptr?[a]???
  • 00411441??add?????????eax,dword?ptr?[b]???
  • 00411444??mov?????????ecx,dword?ptr?[this]???
  • 00411447??mov?????????dword?ptr?[ecx],eax???
  • ????return?this->x;??
  • 00411449??mov?????????eax,dword?ptr?[this]???
  • 0041144C??mov?????????eax,dword?ptr?[eax]???
  • }??
  • 0041144E??pop?????????edi????
  • 0041144F??pop?????????esi????
  • 00411450??pop?????????ebx????
  • 00411451??mov?????????esp,ebp???
  • 00411453??pop?????????ebp????
  • 00411454??ret????????????????????????????/*?__cdecl?不用負責棧清除?*/??
  • ---?No?source?file?-------------------------------------------------------------??
  • ??
  • int?TestCallType::_stdcall_call(int?a,?int?b)??
  • {??
  • 00411470??push????????ebp????
  • 00411471??mov?????????ebp,esp???
  • 00411473??sub?????????esp,0C0h???
  • 00411479??push????????ebx????
  • 0041147A??push????????esi????
  • 0041147B??push????????edi????
  • 0041147C??lea?????????edi,[ebp-0C0h]???
  • 00411482??mov?????????ecx,30h???
  • 00411487??mov?????????eax,0CCCCCCCCh???
  • 0041148C??rep?stos????dword?ptr?es:[edi]???
  • ????this->x?=?a?+?b;??
  • 0041148E??mov?????????eax,dword?ptr?[a]???
  • 00411491??add?????????eax,dword?ptr?[b]???
  • 00411494??mov?????????ecx,dword?ptr?[this]???
  • 00411497??mov?????????dword?ptr?[ecx],eax???
  • ????return?this->x;??
  • 00411499??mov?????????eax,dword?ptr?[this]???
  • 0041149C??mov?????????eax,dword?ptr?[eax]???
  • }??
  • 0041149E??pop?????????edi????
  • 0041149F??pop?????????esi????
  • 004114A0??pop?????????ebx????
  • 004114A1??mov?????????esp,ebp???
  • 004114A3??pop?????????ebp????
  • 004114A4??ret?????????0Ch??????????????????//清除棧,字節數和參數入棧對應??
  • ---?No?source?file?-------------------------------------------------------------??
  • ??
  • int?TestCallType::_fastcall_call(int?a,?int?b)??
  • {??
  • 004114C0??push????????ebp????
  • 004114C1??mov?????????ebp,esp???
  • 004114C3??sub?????????esp,0D8h???
  • 004114C9??push????????ebx????
  • 004114CA??push????????esi????
  • 004114CB??push????????edi????
  • 004114CC??push????????ecx????
  • 004114CD??lea?????????edi,[ebp-0D8h]???
  • 004114D3??mov?????????ecx,36h???
  • 004114D8??mov?????????eax,0CCCCCCCCh???
  • 004114DD??rep?stos????dword?ptr?es:[edi]???
  • 004114DF??pop?????????ecx????
  • 004114E0??mov?????????dword?ptr?[ebp-8],edx???
  • 004114E3??mov?????????dword?ptr?[ebp-14h],ecx???
  • ????this->x?=?a?+?b;??
  • 004114E6??mov?????????eax,dword?ptr?[a]???
  • 004114E9??add?????????eax,dword?ptr?[b]???
  • 004114EC??mov?????????ecx,dword?ptr?[this]???
  • 004114EF??mov?????????dword?ptr?[ecx],eax???
  • ????return?this->x;??
  • 004114F1??mov?????????eax,dword?ptr?[this]???
  • 004114F4??mov?????????eax,dword?ptr?[eax]???
  • }??
  • 004114F6??pop?????????edi????
  • 004114F7??pop?????????esi????
  • 004114F8??pop?????????ebx????
  • 004114F9??mov?????????esp,ebp???
  • 004114FB??pop?????????ebp????
  • 004114FC??ret?????????4????????????????????//清除棧,字節數和參數入棧對應??
  • ---?No?source?file?-------------------------------------------------------------??
  • ??
  • int?TestCallType::_thiscall_call(int?a,?int?b)??
  • {??
  • 00411510??push????????ebp????
  • 00411511??mov?????????ebp,esp???
  • 00411513??sub?????????esp,0CCh???
  • 00411519??push????????ebx????
  • 0041151A??push????????esi????
  • 0041151B??push????????edi????
  • 0041151C??push????????ecx????
  • 0041151D??lea?????????edi,[ebp-0CCh]???
  • 00411523??mov?????????ecx,33h???
  • 00411528??mov?????????eax,0CCCCCCCCh???
  • 0041152D??rep?stos????dword?ptr?es:[edi]???
  • 0041152F??pop?????????ecx????
  • 00411530??mov?????????dword?ptr?[ebp-8],ecx???
  • ????this->x?=?a?+?b;??
  • 00411533??mov?????????eax,dword?ptr?[a]???
  • 00411536??add?????????eax,dword?ptr?[b]???
  • 00411539??mov?????????ecx,dword?ptr?[this]???
  • 0041153C??mov?????????dword?ptr?[ecx],eax???
  • ????return?this->x;??
  • 0041153E??mov?????????eax,dword?ptr?[this]???
  • 00411541??mov?????????eax,dword?ptr?[eax]???
  • }??
  • 00411543??pop?????????edi????
  • 00411544??pop?????????esi????
  • 00411545??pop?????????ebx????
  • 00411546??mov?????????esp,ebp???
  • 00411548??pop?????????ebp????
  • 00411549??ret?????????8???????????????????//清除棧,字節數和參數入棧對應??
  • ---?No?source?file?-------------------------------------------------------------??
  • 總結

    以上是生活随笔為你收集整理的函数调用方式__stdecl _stdcall _fastcall __thiscall介绍的全部內容,希望文章能夠幫你解決所遇到的問題。

    如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。