1
2
3
4
5
6
7
8
9
10
11
12
13
14
15#ifndef _MALI_OSK_LOCKS_H
16#define _MALI_OSK_LOCKS_H
17
18#include <linux/spinlock.h>
19#include <linux/rwsem.h>
20#include <linux/mutex.h>
21
22#include <linux/slab.h>
23
24#include "mali_osk_types.h"
25
26#ifdef _cplusplus
27extern "C" {
28#endif
29
30
31#ifdef DEBUG
32 struct _mali_osk_lock_debug_s {
33 u32 owner;
34 _mali_osk_lock_flags_t orig_flags;
35 _mali_osk_lock_order_t order;
36 struct _mali_osk_lock_debug_s *next;
37 };
38#endif
39
40
41 struct _mali_osk_spinlock_s {
42#ifdef DEBUG
43 struct _mali_osk_lock_debug_s checker;
44#endif
45 spinlock_t spinlock;
46 };
47
48
49 struct _mali_osk_spinlock_irq_s {
50#ifdef DEBUG
51 struct _mali_osk_lock_debug_s checker;
52#endif
53
54 spinlock_t spinlock;
55 unsigned long flags;
56 };
57
58
59 struct _mali_osk_mutex_rw_s {
60#ifdef DEBUG
61 struct _mali_osk_lock_debug_s checker;
62 _mali_osk_lock_mode_t mode;
63#endif
64
65 struct rw_semaphore rw_sema;
66 };
67
68
69 struct _mali_osk_mutex_s {
70#ifdef DEBUG
71 struct _mali_osk_lock_debug_s checker;
72#endif
73 struct mutex mutex;
74 };
75
76#ifdef DEBUG
77
78
79
80 void _mali_osk_locks_debug_init(struct _mali_osk_lock_debug_s *checker, _mali_osk_lock_flags_t flags, _mali_osk_lock_order_t order);
81 void _mali_osk_locks_debug_add(struct _mali_osk_lock_debug_s *checker);
82 void _mali_osk_locks_debug_remove(struct _mali_osk_lock_debug_s *checker);
83
84
85 static inline u32 _mali_osk_lock_get_owner(struct _mali_osk_lock_debug_s *lock)
86 {
87 return lock->owner;
88 }
89#else
90#define _mali_osk_locks_debug_init(x, y, z) do {} while (0)
91#define _mali_osk_locks_debug_add(x) do {} while (0)
92#define _mali_osk_locks_debug_remove(x) do {} while (0)
93#endif
94
95
96 static inline _mali_osk_spinlock_t *_mali_osk_spinlock_init(_mali_osk_lock_flags_t flags, _mali_osk_lock_order_t order)
97 {
98 _mali_osk_spinlock_t *lock = NULL;
99
100 lock = kmalloc(sizeof(_mali_osk_spinlock_t), GFP_KERNEL);
101 if (NULL == lock) {
102 return NULL;
103 }
104 spin_lock_init(&lock->spinlock);
105 _mali_osk_locks_debug_init((struct _mali_osk_lock_debug_s *)lock, flags, order);
106 return lock;
107 }
108
109
110 static inline void _mali_osk_spinlock_lock(_mali_osk_spinlock_t *lock)
111 {
112 BUG_ON(NULL == lock);
113 spin_lock(&lock->spinlock);
114 _mali_osk_locks_debug_add((struct _mali_osk_lock_debug_s *)lock);
115 }
116
117
118 static inline void _mali_osk_spinlock_unlock(_mali_osk_spinlock_t *lock)
119 {
120 BUG_ON(NULL == lock);
121 _mali_osk_locks_debug_remove((struct _mali_osk_lock_debug_s *)lock);
122 spin_unlock(&lock->spinlock);
123 }
124
125
126
127 static inline void _mali_osk_spinlock_term(_mali_osk_spinlock_t *lock)
128 {
129
130 BUG_ON(NULL == lock);
131
132
133 kfree(lock);
134 }
135
136
137
138 static inline _mali_osk_spinlock_irq_t *_mali_osk_spinlock_irq_init(_mali_osk_lock_flags_t flags, _mali_osk_lock_order_t order)
139 {
140 _mali_osk_spinlock_irq_t *lock = NULL;
141 lock = kmalloc(sizeof(_mali_osk_spinlock_irq_t), GFP_KERNEL);
142
143 if (NULL == lock) {
144 return NULL;
145 }
146
147 lock->flags = 0;
148 spin_lock_init(&lock->spinlock);
149 _mali_osk_locks_debug_init((struct _mali_osk_lock_debug_s *)lock, flags, order);
150 return lock;
151 }
152
153
154 static inline void _mali_osk_spinlock_irq_lock(_mali_osk_spinlock_irq_t *lock)
155 {
156 unsigned long tmp_flags;
157
158 BUG_ON(NULL == lock);
159 spin_lock_irqsave(&lock->spinlock, tmp_flags);
160 lock->flags = tmp_flags;
161 _mali_osk_locks_debug_add((struct _mali_osk_lock_debug_s *)lock);
162 }
163
164
165 static inline void _mali_osk_spinlock_irq_unlock(_mali_osk_spinlock_irq_t *lock)
166 {
167 BUG_ON(NULL == lock);
168 _mali_osk_locks_debug_remove((struct _mali_osk_lock_debug_s *)lock);
169 spin_unlock_irqrestore(&lock->spinlock, lock->flags);
170 }
171
172
173
174 static inline void _mali_osk_spinlock_irq_term(_mali_osk_spinlock_irq_t *lock)
175 {
176
177 BUG_ON(NULL == lock);
178
179
180 kfree(lock);
181 }
182
183
184
185 static inline _mali_osk_mutex_rw_t *_mali_osk_mutex_rw_init(_mali_osk_lock_flags_t flags, _mali_osk_lock_order_t order)
186 {
187 _mali_osk_mutex_rw_t *lock = NULL;
188
189 lock = kmalloc(sizeof(_mali_osk_mutex_rw_t), GFP_KERNEL);
190
191 if (NULL == lock) {
192 return NULL;
193 }
194
195 init_rwsem(&lock->rw_sema);
196 _mali_osk_locks_debug_init((struct _mali_osk_lock_debug_s *)lock, flags, order);
197 return lock;
198 }
199
200
201
202 static inline void _mali_osk_mutex_rw_wait(_mali_osk_mutex_rw_t *lock, _mali_osk_lock_mode_t mode)
203 {
204 BUG_ON(NULL == lock);
205 BUG_ON(!(_MALI_OSK_LOCKMODE_RO == mode || _MALI_OSK_LOCKMODE_RW == mode));
206
207 if (mode == _MALI_OSK_LOCKMODE_RO) {
208 down_read(&lock->rw_sema);
209 } else {
210 down_write(&lock->rw_sema);
211 }
212
213#ifdef DEBUG
214 if (mode == _MALI_OSK_LOCKMODE_RW) {
215 lock->mode = mode;
216 } else {
217 lock->mode = mode;
218 }
219 _mali_osk_locks_debug_add((struct _mali_osk_lock_debug_s *)lock);
220#endif
221 }
222
223
224 static inline void _mali_osk_mutex_rw_signal(_mali_osk_mutex_rw_t *lock, _mali_osk_lock_mode_t mode)
225 {
226 BUG_ON(NULL == lock);
227 BUG_ON(!(_MALI_OSK_LOCKMODE_RO == mode || _MALI_OSK_LOCKMODE_RW == mode));
228#ifdef DEBUG
229
230 if (mode == _MALI_OSK_LOCKMODE_RW) {
231 _mali_osk_locks_debug_remove((struct _mali_osk_lock_debug_s *)lock);
232
233 lock->checker.owner = 0;
234 }
235#endif
236
237 if (mode == _MALI_OSK_LOCKMODE_RO) {
238 up_read(&lock->rw_sema);
239 } else {
240 up_write(&lock->rw_sema);
241 }
242 }
243
244
245
246 static inline void _mali_osk_mutex_rw_term(_mali_osk_mutex_rw_t *lock)
247 {
248
249 BUG_ON(NULL == lock);
250
251
252 kfree(lock);
253 }
254
255
256
257 static inline _mali_osk_mutex_t *_mali_osk_mutex_init(_mali_osk_lock_flags_t flags, _mali_osk_lock_order_t order)
258 {
259 _mali_osk_mutex_t *lock = NULL;
260
261 lock = kmalloc(sizeof(_mali_osk_mutex_t), GFP_KERNEL);
262
263 if (NULL == lock) {
264 return NULL;
265 }
266 mutex_init(&lock->mutex);
267
268 _mali_osk_locks_debug_init((struct _mali_osk_lock_debug_s *)lock, flags, order);
269 return lock;
270 }
271
272
273 static inline _mali_osk_errcode_t _mali_osk_mutex_wait_interruptible(_mali_osk_mutex_t *lock)
274 {
275 _mali_osk_errcode_t err = _MALI_OSK_ERR_OK;
276
277 BUG_ON(NULL == lock);
278
279 if (mutex_lock_interruptible(&lock->mutex)) {
280 printk(KERN_WARNING "Mali: Can not lock mutex\n");
281 err = _MALI_OSK_ERR_RESTARTSYSCALL;
282 }
283
284 _mali_osk_locks_debug_add((struct _mali_osk_lock_debug_s *)lock);
285 return err;
286 }
287
288
289 static inline void _mali_osk_mutex_signal_interruptible(_mali_osk_mutex_t *lock)
290 {
291 BUG_ON(NULL == lock);
292 _mali_osk_locks_debug_remove((struct _mali_osk_lock_debug_s *)lock);
293 mutex_unlock(&lock->mutex);
294 }
295
296
297 static inline void _mali_osk_mutex_wait(_mali_osk_mutex_t *lock)
298 {
299 BUG_ON(NULL == lock);
300 mutex_lock(&lock->mutex);
301 _mali_osk_locks_debug_add((struct _mali_osk_lock_debug_s *)lock);
302 }
303
304
305 static inline void _mali_osk_mutex_signal(_mali_osk_mutex_t *lock)
306 {
307 BUG_ON(NULL == lock);
308 _mali_osk_locks_debug_remove((struct _mali_osk_lock_debug_s *)lock);
309 mutex_unlock(&lock->mutex);
310 }
311
312
313 static inline void _mali_osk_mutex_term(_mali_osk_mutex_t *lock)
314 {
315
316 BUG_ON(NULL == lock);
317
318
319 kfree(lock);
320 }
321
322#ifdef _cplusplus
323}
324#endif
325
326#endif
327