關于_stdcall和_cdecl
參考網址:
https://blog.csdn.net/myjisgreat/article/details/46477769
https://bbs.csdn.net/topics/390435293?page=1#post-394308806
https://docs.microsoft.com/en-us/cpp/cpp/argument-passing-and-naming-conventions?view=vs-2019
- _stdcall和_cdecl,這兩種方式的差別為調用後誰來恢複棧資料。
即:
_stdcall為被調用者恢複棧上資料
_cdecl為調用者恢複棧上資料
- 空間方面
_cdecl為調用者恢複棧上資料,假設有一百個不同的函數調用函數a,那麼記憶體中就有一個段恢複堆棧的代碼。
_stdcall為被調用者恢複棧,隻有在函數代碼的結尾出現一次恢複堆棧代碼,是以節約空間。
注意,這些恢複堆棧的代碼是編譯器根據你給他的call方式自動生成的,是以你無需考慮…而告訴編譯器call方式的意義就在這裡,如果一方用cdecl一方用stdcall可能出現沒有人釋放堆棧的情況,這明顯是不允許的
_cdecl為被調用函數傳回後,由調用者恢複堆棧
_stdcall為被調用函數傳回前由被調用函數自己恢複堆棧
- 函數變參方面
_cdecl的優勢在于他可以不定參數個數,參考printf函數。原因在于是調用者存入參數,調用者釋放參數占有的空間,都是調用者完成的,是以有參數個數的自由性
_stdcall在結束函數時,恢複的空間是編譯時決定的,函數負責釋放,但他無法知道你實際壓入幾個參數,于是stdcall在編譯時就規定了參數個數,無法實作不定個數的參數調用