GCC version: 5.3.0
MinGW Version: 3.22.4
The following have declaration mismatches with MSVC:
WINEVENTPROC - missed CALLBACK
SetTimer - arg2 type mismatch
(of course, I do not know about possible more similar mismatches;
I just noticed these two trying to compile one program)
WINEVENTPROC function pointer:
https://msdn.microsoft.com/en-us/library/windows/desktop/dd373882%28v=vs.85%29.aspx
typedef void (CALLBACK *WINEVENTPROC)(...)
MinGW: in winable.h and winuser.h it is defined w/o CALLBACK
and GCC assumes these declaration to be different, thus refuses to compile
a program using a function with WINEVENTPROC argument if the function
specified in argument is written with the CALLBACK, as MSVC requires.
Note the CALLBACK is defined as __stdcall in windef.h and the compiler
says a function with the __stdcall and a function without it do not match.
SetTimer function:
https://msdn.microsoft.com/pl-pl/library/windows/desktop/ms644906%28v=vs.85%29.aspx
specifies args:
In_opt HWND hWnd,
In UINT_PTR nIDEvent,
In UINT uElapse,
In_opt TIMERPROC lpTimerFunc
(note arg2 is pointer)
MinGW: in winuser.h it is declared as:
WINUSERAPI UINT WINAPI SetTimer(HWND, UINT, UINT, TIMERPROC);
(note arg2 is UINT)
Both these bugs cause compilation errors when using MinGW
to compile program written e.g. for MicroSoft Visual C.
Thanks for the report. I take your point about
WINEVENTPROC, (it really shouldn't be in<winable.h>, which is obsolete, and utterly wrong throughout, not just w.r.t. this declaration), but it should be declared in<winuser.h>, with theCALLBACKattribute.I'm less convinced by your reference to
SetTimer(). While I can see that the declaration in MinGW.org's<winuser.h>differs from the current MSDN documentation, it is entirely consistent with its original documentation, as it appears inwinhlp32.exeon my Win7 VM. Furthermore,UINT_PTRdoes not represent a pointer, (as your report implies); it represents anunsigned intwith sufficient range to store a pointer, such that the stored value may be cast back to a pointer, with no difference from the original pointer value. On Win32,UINT_PTRandUINTrefer to identically the same underlyingunsigned intdata type, and for me, G++ does not complain that aUINT_PTRargument passed toSetTimer()is incompatible. Can you please provide a SSCCE, to illustrate this issue?I committed [8d57d9] and [d03bac].
Raymond Chen's blog gives us a compelling reason to update the declaration of
SetTimer(), (and also the declaration forKillTimer()and the typedef forTIMERPROC(), BTW). When these were originally implemented, Win32 was the only game in town, and timer IDs were 32-bit integers; the originalUNITdeclaration suited well enough. With the advent of Win64, timer IDs have become 64-bit integers on the new platform, while remaining 32-bit on Win32, whereasUINTcontinues to represent 32-bit integers on both. Thus, whileUINTis still perfectly adequate for Win32, it is not suitable for the corresponding Win64 declarations; OTOH,UINT_PTRwill DTRT for both.This really is detail which should be included in the MSDN pages for the affected functions; shame on Microsoft, for surreptitiously slipping in such a change, without explanation.
I can now understand how the original declaration may have led to run-time problems, when you compile a Win64 application, (which we don't yet support anyway, so the forward-looking change isn't strictly necessary, for us, at this juncture). It still isn't clear, to me, how it can induce compile-time problems; I'd still like to see your SSCCE to demonstrate that.
Related
Commit: [8d57d9]
Commit: [d03bac]
Last edit: Keith Marshall 2016-11-28
Diff:
Closing, due to lack of timely user response.