Example of WaitableTimer

  1 Basic functions

HANDLE  CreateWaitableTimer(
    LPSECURITY_ATTRIBUTES lpTimerAttributes,
    BOOL bManualReset,
    LPCSTR lpTimerName);

lpTimerAttributes,
SECURITY_ATTRIBUTES, specify a structure used to set the security characteristics of the object, you can use the object's default security settings.

bManualReset
BOOL, if TRUE, creates a manual reset timer; if FALSE, creates an automatic reset timer.

lpTimerName
LPCSTR, specifies the name of the waitable timer object. If a waitable timer with this name already exists, the ready-made waitable timer is opened directly. This name cannot be the same as the name of an existing mutex, event, signal, or file mapping.

The difference between manual reset and automatic reset
With manual reset, all waiting threads become schedulable threads after the timer expires; with automatic reset, only one thread becomes schedulable.

BOOL SetWaitableTimer(
         HANDLE hTimer,
         const LARGE_INTEGER *lpDueTime,
         LONG lPeriod,
         PTIMERAPCROUTINE pfnCompletionRoutine,
         LPVOID lpArgToCompletionRoutine,
         BOOL fResume ); 


hTimer timer handle.
lpDueTime Sets the timer interval. When set to a positive value, it is an absolute time; when set to a negative value, it is a relative time.
lPeriod period.
pfnCompletionRoutine sets the callback function.
lpArgToCompletionRoutine parameter passed to the callback function.
fResume sets whether the system will resume automatically.

2 Console program example

  (Clever use of the event object to implement the callback function of the console program)


HANDLE g_hHelpEvent;

void CALLBACK TimerCallback( LPVOID lpArgToCompletionRoutine, DWORD dwTimerLowValue, DWORD dwTimerHighValue )
{//The timer trigger is processed here
	SetEvent (g_hHelpEvent);

	SYSTEMTIME st;
	GetLocalTime(&st);
	printf("%02d:%02d\n",st.wMinute,st.wSecond);
}
int _tmain(int argc, _TCHAR* argv[])
{
	//Create an event kernel object, the default is not triggered
	HANDLE hTimer = CreateWaitableTimer(NULL, TRUE, NULL);
	//Create an event, set it to an untriggered state
	g_hHelpEvent = CreateEvent(NULL, TRUE, FALSE, NULL);


	SYSTEMTIME st;
	GetLocalTime(&st);
	//st.wSecond += 40;
	FILETIME ft;
	SystemTimeToFileTime(&st, &ft);
	//Convert to UTC time
	FILETIME ftUtc;
	LocalFileTimeToFileTime(&ft, &ftUtc);
	LARGE_INTEGER fTime={0};//-2*10000000
	//fTime.LowPart	= ftUtc.dwLowDateTime;
	//fTime.HighPart	= ftUtc.dwHighDateTime;
	//当前时间的后一分钟触发,以后每10秒钟触发一次
	BOOL bRet = SetWaitableTimer(hTimer, &fTime, 2*1000, TimerCallback, (LPVOID)hTimer, FALSE);
	DWORD dwError = GetLastError();
	//将TimerCallback回调加入到系统APC队列后,只能通过SleepEx、WaitForSingleObjectEx、WaitForMultipObjectEx、
	//或者SignalObjectAndWait 进入等待状态APC回调函数才能被同一线程调用。
	DWORD dwRet=WaitForSingleObject(g_hHelpEvent, 1000);
	
	while( WAIT_TIMEOUT == dwRet)
		SleepEx(1000*60, TRUE);
	switch( dwRet )
	{
	case WAIT_OBJECT_0://
		printf("定时器对象已经触发\n");
		break;
	case WAIT_TIMEOUT:
		printf("等待超时,自动终止定时器对象\n");
		CancelWaitableTimer(hTimer);
		break;
	case WAIT_FAILED:
		printf("WaitForSingleObject调用失败,系统错误码\n");
		break;
	}
	CloseHandle(hTimer);
	CloseHandle(g_hHelpEvent);
	getchar();
	return 0;
}



Guess you like

Origin http://43.154.161.224:23101/article/api/json?id=325889265&siteId=291194637