3

I was reading a man page about CreateTimerQueueTimer.

BOOL CreateTimerQueueTimer(
  PHANDLE             phNewTimer,
  HANDLE              TimerQueue,
  WAITORTIMERCALLBACK Callback,
  PVOID               DueTime,
  DWORD               Period,
  DWORD               Flags,
  ULONG               Parameter
);

The doc states:

Period

The period of the timer, in milliseconds. If this parameter is zero, the timer is signaled once.

So I needed to set this to 0 to avoid the callback to be executed periodically. The problem was that modifying the period value has no effect on periodicity. Once loaded in OllyDBG, Olly reconstructed the arguments and the call giving me this function signature :

BOOL CreateTimerQueueTimer(
 PHANDLE             phNewTimer,
 HANDLE              TimerQueue,
 WAITORTIMERCALLBACK Callback,
 ULONG               Parameter,
 PVOID               DueTime,
 DWORD               Period,
 DWORD               Flags
);

Notice that the parameter argument changed position, and thus all my patches was useless. I guess this error might be due to an old version of the API where the Parameter argument was in 4th position, but I can be wrong. Also, I can't find old WinAPIs to confirm my sayings. Am I guessing right or am I missing something?

2

Yep, I think I've seen a similar case before. It happens very rarely, but because you can do some stunts at the C preprocessor level as well as at the linker level, this happens to work.

In this case I looked it up in the 3790.1830 DDK (Windows 2003 Server) and several newer WDKs and SDKs.

Windows 2000/XP target (3790.1830/inc/w2k/winbase.h and 3790.1830/inc/wxp/winbase.h)

WINBASEAPI
BOOL
WINAPI
CreateTimerQueueTimer(
    PHANDLE phNewTimer,
    HANDLE TimerQueue,
    WAITORTIMERCALLBACK Callback,
    PVOID Parameter,
    DWORD DueTime,
    DWORD Period,
    ULONG Flags
    ) ;  

Windows 2003/Vista/7 target (3790.1830/inc/wnet/winbase.h and 6001.18002/inc/api/WINBASE.H and 7600.16385.1/inc/api/WINBASE.H)

WINBASEAPI
BOOL
WINAPI
CreateTimerQueueTimer(                                                                                                                                                                                             
    __deref_out PHANDLE phNewTimer,
    __in_opt    HANDLE TimerQueue,
    __in        WAITORTIMERCALLBACK Callback,
    __in_opt    PVOID Parameter,
    __in        DWORD DueTime,
    __in        DWORD Period,
    __in        ULONG Flags 
    ) ;   

With the Windows 8.1 SDK ...

... this API moved into another header: Include/um/threadpoollegacyapiset.h (check out this study on API sets).

WINBASEAPI
BOOL
WINAPI
CreateTimerQueueTimer(
    _Outptr_ PHANDLE phNewTimer,
    _In_opt_ HANDLE TimerQueue,
    _In_ WAITORTIMERCALLBACK Callback,
    _In_opt_ PVOID Parameter,
    _In_ DWORD DueTime,
    _In_ DWORD Period,
    _In_ ULONG Flags
    );  

... so no change up until this point (other than adopting SAL2 annotations).

For the Windows 10 SDKs 10.0.10240.0, 10.0.16299.0, 10.0.17134.0, 10.0.17134.0, 10.0.17763.0, 10.0.18362.0 it still has the same order for the arguments as for Windows 8.1. So it stands to reason you ran into a documentation issue rather than an actual change here.

There is no pending or old (and closed) pull request mentioning this function, so you may want to consider sending one.

| improve this answer | |
  • Thanks, is there any resource out there that references old versions of the API? Can't find them on the waybackmachine ! – Nark Dec 24 '19 at 1:34
  • @Nark not sure what the point would be, since - as they say - the code doesn't lie. And as I pointed out to you the headers show the same argument order since at least Windows 2000. That new subdomain won't be in the Internet Archive and generally MS has changed URLs so often I'd consider you lucky if you managed to find one. Why not cross-check with the Windows 7 SDK or older ones, if you need to validate my findings?! – 0xC0000022L Dec 24 '19 at 20:22
  • so it is rather a linker/compiler problem if I get it right ? – Nark Dec 25 '19 at 14:39

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.