blob: fcbd0ac7fccd0ca42117781b2e1caa1585bd726c [file] [log] [blame]
Pierre Ossman687d52c2015-11-12 12:16:08 +01001/* Copyright 2015 Pierre Ossman for Cendio AB
2 *
3 * This is free software; you can redistribute it and/or modify
4 * it under the terms of the GNU General Public License as published by
5 * the Free Software Foundation; either version 2 of the License, or
6 * (at your option) any later version.
7 *
8 * This software is distributed in the hope that it will be useful,
9 * but WITHOUT ANY WARRANTY; without even the implied warranty of
10 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11 * GNU General Public License for more details.
12 *
13 * You should have received a copy of the GNU General Public License
14 * along with this software; if not, write to the Free Software
15 * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307,
16 * USA.
17 */
18
19#ifdef WIN32
20#include <windows.h>
21#else
22#include <pthread.h>
23#endif
24
25#include <rdr/Exception.h>
26
27#include <os/Mutex.h>
28
29using namespace os;
30
31Mutex::Mutex()
32{
33#ifdef WIN32
34 systemMutex = new CRITICAL_SECTION;
35 InitializeCriticalSection((CRITICAL_SECTION*)systemMutex);
36#else
37 int ret;
38
39 systemMutex = new pthread_mutex_t;
40 ret = pthread_mutex_init((pthread_mutex_t*)systemMutex, NULL);
41 if (ret != 0)
42 throw rdr::SystemException("Failed to create mutex", ret);
43#endif
44}
45
46Mutex::~Mutex()
47{
48#ifdef WIN32
49 DeleteCriticalSection((CRITICAL_SECTION*)systemMutex);
50 delete (CRITICAL_SECTION*)systemMutex;
51#else
52 int ret;
53
54 ret = pthread_mutex_destroy((pthread_mutex_t*)systemMutex);
55 delete (pthread_mutex_t*)systemMutex;
56 if (ret != 0)
57 throw rdr::SystemException("Failed to destroy mutex", ret);
58#endif
59}
60
61void Mutex::lock()
62{
63#ifdef WIN32
64 EnterCriticalSection((CRITICAL_SECTION*)systemMutex);
65#else
66 int ret;
67
68 ret = pthread_mutex_lock((pthread_mutex_t*)systemMutex);
69 if (ret != 0)
70 throw rdr::SystemException("Failed to lock mutex", ret);
71#endif
72}
73
74void Mutex::unlock()
75{
76#ifdef WIN32
77 LeaveCriticalSection((CRITICAL_SECTION*)systemMutex);
78#else
79 int ret;
80
81 ret = pthread_mutex_unlock((pthread_mutex_t*)systemMutex);
82 if (ret != 0)
83 throw rdr::SystemException("Failed to unlock mutex", ret);
84#endif
85}
86
87Condition::Condition(Mutex* mutex)
88{
89 this->mutex = mutex;
90
91#ifdef WIN32
92 systemCondition = new CONDITION_VARIABLE;
93 InitializeConditionVariable((CONDITION_VARIABLE*)systemCondition);
94#else
95 int ret;
96
97 systemCondition = new pthread_cond_t;
98 ret = pthread_cond_init((pthread_cond_t*)systemCondition, NULL);
99 if (ret != 0)
100 throw rdr::SystemException("Failed to create condition variable", ret);
101#endif
102}
103
104Condition::~Condition()
105{
106#ifdef WIN32
107 delete (CONDITION_VARIABLE*)systemCondition;
108#else
109 int ret;
110
111 ret = pthread_cond_destroy((pthread_cond_t*)systemCondition);
112 delete (pthread_cond_t*)systemCondition;
113 if (ret != 0)
114 throw rdr::SystemException("Failed to destroy condition variable", ret);
115#endif
116}
117
118void Condition::wait()
119{
120#ifdef WIN32
121 BOOL ret;
122
123 ret = SleepConditionVariableCS((CONDITION_VARIABLE*)systemCondition,
124 (CRITICAL_SECTION*)mutex->systemMutex,
125 INFINITE);
126 if (!ret)
127 throw rdr::SystemException("Failed to wait on condition variable", GetLastError());
128#else
129 int ret;
130
131 ret = pthread_cond_wait((pthread_cond_t*)systemCondition,
132 (pthread_mutex_t*)mutex->systemMutex);
133 if (ret != 0)
134 throw rdr::SystemException("Failed to wait on condition variable", ret);
135#endif
136}
137
138void Condition::signal()
139{
140#ifdef WIN32
141 WakeConditionVariable((CONDITION_VARIABLE*)systemCondition);
142#else
143 int ret;
144
145 ret = pthread_cond_signal((pthread_cond_t*)systemCondition);
146 if (ret != 0)
147 throw rdr::SystemException("Failed to signal condition variable", ret);
148#endif
149}
150
151void Condition::broadcast()
152{
153#ifdef WIN32
154 WakeAllConditionVariable((CONDITION_VARIABLE*)systemCondition);
155#else
156 int ret;
157
158 ret = pthread_cond_broadcast((pthread_cond_t*)systemCondition);
159 if (ret != 0)
160 throw rdr::SystemException("Failed to broadcast condition variable", ret);
161#endif
162}