I want to manage a WinAPI function pair via std::unique_ptr
:
#include <memory>
int* __stdcall construct(){ return new int{5}; }
void __stdcall destruct(int* v){ delete v; }
int main() {
using Ptr = std::unique_ptr<int, void(&)(int*)>;
Ptr v(construct(), destruct);
}
When I build a 64-bit binary with MSVC 19.33, the code works. If I build a 32-bit binary, then there is an error.
example.cpp
<source>(8): error C2660: 'std::unique_ptr<int,void (__cdecl &)(int *)>::unique_ptr': function does not take 2 arguments
C:/data/msvc/14.33.31631/include\memory(3291): note: see declaration of 'std::unique_ptr<int,void (__cdecl &)(int *)>::unique_ptr'
Compiler returned: 2
It works with both if I explicitly name the __stdcall
in std::unique_ptr<int, void(__stdcall&)(int*)>
, so I assume it is part of the function signature.
Why is there this difference in 32 and 64 bit? Is this a bug in the compiler?
On ARM and x64 processors, __stdcall is accepted and ignored by the compiler; on ARM and x64 architectures, by convention, arguments are passed in registers when possible, and subsequent arguments are passed on the stack.
So __stdcall
is ignored by the 64-bit compiler but meaningful only for the 32-bit compiler.