]> git.mxchange.org Git - simgear.git/blob - simgear/threads/SGThread.cxx
Merge branch 'next' of git://gitorious.org/fg/simgear into next
[simgear.git] / simgear / threads / SGThread.cxx
1 #include <simgear/compiler.h>
2
3 #if defined(_MSC_VER) || defined(__MINGW32__)
4 #  include <time.h>
5 #else
6 #  if defined ( sgi ) && !defined( __GNUC__ )
7      // This works around a bug triggered when using MipsPro 7.4.1
8      // and (at least) IRIX 6.5.20
9 #    include <iostream>
10 #  endif
11 #  include <sys/time.h>
12 #endif
13 #if _MSC_VER >= 1300
14 #  include <winsock2.h>
15 #endif
16
17 #include "SGThread.hxx"
18
19 void*
20 start_handler( void* arg )
21 {
22     SGThread* thr = static_cast<SGThread*>(arg);
23     thr->run();
24     return 0;
25 }
26
27 void
28 SGThread::set_cancel( cancel_t mode )
29 {
30     switch (mode)
31     {
32     case CANCEL_DISABLE:
33         pthread_setcancelstate( PTHREAD_CANCEL_DISABLE, 0 );
34         break;
35     case CANCEL_DEFERRED:
36         pthread_setcanceltype( PTHREAD_CANCEL_DEFERRED, 0 );
37         pthread_setcancelstate( PTHREAD_CANCEL_ENABLE, 0 );
38         break;
39     case CANCEL_IMMEDIATE:
40         pthread_setcanceltype( PTHREAD_CANCEL_ASYNCHRONOUS, 0 );
41         pthread_setcancelstate( PTHREAD_CANCEL_ENABLE, 0 );
42         break;
43     default:
44         break;
45     }
46 }
47
48 bool
49 SGMutex::trylock()
50 {
51     int status = pthread_mutex_lock( &mutex );
52     if (status == EBUSY)
53     {
54         return false;
55     }
56     assert( status == 0 );
57     return true;
58 }
59
60 #if defined(_MSC_VER) || defined(__MINGW32__)
61 int gettimeofday(struct timeval* tp, void* tzp) {
62     LARGE_INTEGER t;
63
64     if(QueryPerformanceCounter(&t)) {
65         /* hardware supports a performance counter */
66         LARGE_INTEGER f;
67         QueryPerformanceFrequency(&f);
68         tp->tv_sec = t.QuadPart/f.QuadPart;
69         tp->tv_usec = ((float)t.QuadPart/f.QuadPart*1000*1000)
70             - (tp->tv_sec*1000*1000);
71     } else {
72         /* hardware doesn't support a performance counter, so get the
73            time in a more traditional way. */
74         DWORD t;
75         t = timeGetTime();
76         tp->tv_sec = t / 1000;
77         tp->tv_usec = t % 1000;
78     }
79
80     /* 0 indicates that the call succeeded. */
81     return 0;
82 }
83 #endif
84
85 bool
86 SGPthreadCond::wait( SGMutex& mutex, unsigned long ms )
87 {
88     struct timeval now;
89     ::gettimeofday( &now, 0 );
90
91     // Wait time is now + ms milliseconds
92     unsigned int sec = ms / 1000;
93     unsigned int nsec = (ms % 1000) * 1000;
94     struct timespec abstime;
95     abstime.tv_sec = now.tv_sec + sec;
96     abstime.tv_nsec = now.tv_usec*1000 + nsec;
97
98     int status = pthread_cond_timedwait( &cond, &mutex.mutex, &abstime );
99     if (status == ETIMEDOUT)
100     {
101         return false;
102     }
103
104     assert( status == 0 );
105     return true;
106 }
107