drivers/timers_win32/timers_win32.c
author greg
Thu, 16 Jul 2009 10:44:32 +0200
changeset 562 9d793667504e
parent 556 8296acd119a9
child 571 6eddab0b7ca8
permissions -rw-r--r--
updated manual_en.pdf with CANOpenShell example
556
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
     1
/*
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
     2
This file is part of CanFestival, a library implementing CanOpen Stack.
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
     3
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
     4
Copyright (C): Edouard TISSERANT and Francis DUPIN
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
     5
Copyright (C) Win32 Port Leonid Tochinski
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
     6
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
     7
See COPYING file for copyrights details.
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
     8
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
     9
This library is free software; you can redistribute it and/or
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    10
modify it under the terms of the GNU Lesser General Public
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    11
License as published by the Free Software Foundation; either
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    12
version 2.1 of the License, or (at your option) any later version.
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    13
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    14
This library is distributed in the hope that it will be useful,
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    15
but WITHOUT ANY WARRANTY; without even the implied warranty of
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    16
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    17
Lesser General Public License for more details.
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    18
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    19
You should have received a copy of the GNU Lesser General Public
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    20
License along with this library; if not, write to the Free Software
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    21
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    22
*/
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    23
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    24
#include <windows.h>
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    25
#include <stdlib.h>
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    26
#include <sys/timeb.h>
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    27
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    28
#include "applicfg.h"
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    29
#include "can_driver.h"
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    30
#include "timer.h"
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    31
#include "timers_driver.h"
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    32
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    33
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    34
struct _timeb timebuffer;
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    35
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    36
/* Synchronization Object Implementation */
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    37
CRITICAL_SECTION CanFestival_mutex;
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    38
HANDLE timer_thread = NULL;
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    39
HANDLE timer = NULL;
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    40
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    41
stop_timer=0;
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    42
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    43
static TimerCallback_t init_callback;
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    44
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    45
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    46
void EnterMutex(void)
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    47
{
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    48
	EnterCriticalSection(&CanFestival_mutex);
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    49
}
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    50
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    51
void LeaveMutex(void)
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    52
{
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    53
	LeaveCriticalSection(&CanFestival_mutex);
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    54
}
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    55
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    56
// --------------- CAN Receive Thread Implementation ---------------
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    57
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    58
void CreateReceiveTask(CAN_HANDLE fd0, TASK_HANDLE* Thread, void* ReceiveLoopPtr)
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    59
{
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    60
	unsigned long thread_id = 0;
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    61
	*Thread = CreateThread(NULL, 0, (LPTHREAD_START_ROUTINE)ReceiveLoopPtr, fd0, 0, &thread_id);
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    62
}
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    63
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    64
void WaitReceiveTaskEnd(TASK_HANDLE *Thread)
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    65
{
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    66
	WaitForSingleObject(*Thread, INFINITE);
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    67
	CloseHandle(*Thread);
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    68
}
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    69
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    70
int TimerThreadLoop(void)
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    71
{
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    72
	int ret = 0;
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    73
	EnterMutex();
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    74
	// At first, TimeDispatch will call init_callback.
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    75
	SetAlarm(NULL, 0, init_callback, 0, 0);
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    76
	LeaveMutex();
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    77
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    78
	while(!stop_timer && ret == WAIT_OBJECT_0)
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    79
	{
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    80
		ret = WaitForSingleObject(timer, INFINITE);
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    81
		_ftime(&timebuffer);
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    82
		EnterMutex();
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    83
		TimeDispatch();
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    84
		LeaveMutex();
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    85
	}
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    86
	return 0;
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    87
}
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    88
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    89
void TimerInit(void)
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    90
{
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    91
	LARGE_INTEGER liDueTime;
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    92
	liDueTime.QuadPart = 0;
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    93
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    94
	InitializeCriticalSection(&CanFestival_mutex);
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    95
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    96
	timer = CreateWaitableTimer(NULL, TRUE, NULL);
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    97
	if(NULL == timer)
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    98
    {
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
    99
        printf("CreateWaitableTimer failed (%d)\n", GetLastError());
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
   100
    }
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
   101
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
   102
	// Take first absolute time ref in milliseconds.
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
   103
	_ftime(&timebuffer);
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
   104
}
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
   105
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
   106
void TimerCleanup(void)
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
   107
{
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
   108
	DeleteCriticalSection(&CanFestival_mutex);
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
   109
}
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
   110
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
   111
void StopTimerLoop(TimerCallback_t exitfunction)
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
   112
{
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
   113
	EnterMutex();
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
   114
	exitfunction(NULL,0);
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
   115
	LeaveMutex();
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
   116
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
   117
	stop_timer = 1;
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
   118
	CloseHandle(timer);
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
   119
	WaitForSingleObject(timer_thread, INFINITE);
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
   120
	CloseHandle(timer_thread);
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
   121
}
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
   122
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
   123
void StartTimerLoop(TimerCallback_t _init_callback)
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
   124
{
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
   125
	unsigned long timer_thread_id;
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
   126
	stop_timer = 0;
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
   127
	init_callback = _init_callback;
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
   128
	timer_thread = CreateThread(NULL, 0, (LPTHREAD_START_ROUTINE)TimerThreadLoop, NULL, 0, &timer_thread_id);
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
   129
}
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
   130
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
   131
/* Set the next alarm */
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
   132
void setTimer(TIMEVAL value)
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
   133
{
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
   134
	if(value == TIMEVAL_MAX)
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
   135
	{
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
   136
		/* cancel timer */
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
   137
		CancelWaitableTimer(timer);
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
   138
	}
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
   139
	else
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
   140
	{
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
   141
		LARGE_INTEGER liDueTime;
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
   142
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
   143
		/* arg 2 of SetWaitableTimer take 100 ns interval */
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
   144
		liDueTime.QuadPart = -value;
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
   145
		//printf("SetTimer(%llu)\n", value);
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
   146
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
   147
		if (!SetWaitableTimer(timer, &liDueTime, 0, NULL, NULL, FALSE))
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
   148
		{
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
   149
			printf("SetWaitableTimer failed (%d)\n", GetLastError());
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
   150
		}
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
   151
	}
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
   152
}
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
   153
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
   154
/* Get the elapsed time since the last occured alarm */
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
   155
TIMEVAL getElapsedTime(void)
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
   156
{
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
   157
	struct _timeb timetmp;
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
   158
	_ftime(&timetmp);
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
   159
	return (timetmp.time - timebuffer.time) * 1000000 + (timetmp.millitm - timebuffer.millitm) * 1000;
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
   160
}
8296acd119a9 Rewrite win32 code (C only)
greg
parents:
diff changeset
   161