17 |
along with this program; if not, write to the Free Software |
along with this program; if not, write to the Free Software |
18 |
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. |
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. |
19 |
|
|
20 |
$Id: atomic.h,v 1.7 2008-11-16 19:19:26 persson Exp $ |
$Id: atomic.h,v 1.8 2009-03-29 18:43:39 schoenebeck Exp $ |
21 |
*/ |
*/ |
22 |
|
|
23 |
//TODO: should we put this into namespace? it might clash with system installed atomic.h, because we need to install atomic.h for the LS API |
/* |
24 |
|
CAUTION: don't ever include this file in header files that are exposed |
25 |
|
to the liblinuxsampler C++ API !!! This file will not be installed along |
26 |
|
with liblinuxsampler's header files! This is due to the fact that |
27 |
|
atomic.h is architecture specific and would in turn require us to include |
28 |
|
and export config.h, which is definitely a bad idea. |
29 |
|
*/ |
30 |
|
|
31 |
#ifndef __linuxsampler_atomic_h__ |
#ifndef __linuxsampler_atomic_h__ |
32 |
#define __linuxsampler_atomic_h__ |
#define __linuxsampler_atomic_h__ |
257 |
/** |
/** |
258 |
* atomic_read - read atomic variable |
* atomic_read - read atomic variable |
259 |
* @v: pointer of type atomic_t |
* @v: pointer of type atomic_t |
260 |
* |
* |
261 |
* Atomically reads the value of @v. Note that the guaranteed |
* Atomically reads the value of @v. Note that the guaranteed |
262 |
* useful range of an atomic_t is only 24 bits. |
* useful range of an atomic_t is only 24 bits. |
263 |
*/ |
*/ |
264 |
#define atomic_read(v) ((v)->counter) |
#define atomic_read(v) ((v)->counter) |
265 |
|
|
266 |
/** |
/** |
267 |
* atomic_set - set atomic variable |
* atomic_set - set atomic variable |
268 |
* @v: pointer of type atomic_t |
* @v: pointer of type atomic_t |
269 |
* @i: required value |
* @i: required value |
270 |
* |
* |
271 |
* Atomically sets the value of @v to @i. Note that the guaranteed |
* Atomically sets the value of @v to @i. Note that the guaranteed |
272 |
* useful range of an atomic_t is only 24 bits. |
* useful range of an atomic_t is only 24 bits. |
273 |
*/ |
*/ |
274 |
#define atomic_set(v,i) (((v)->counter) = (i)) |
#define atomic_set(v,i) (((v)->counter) = (i)) |
275 |
|
|
276 |
/** |
/** |
277 |
* atomic_add - add integer to atomic variable |
* atomic_add - add integer to atomic variable |
278 |
* @i: integer value to add |
* @i: integer value to add |
279 |
* @v: pointer of type atomic_t |
* @v: pointer of type atomic_t |
280 |
* |
* |
281 |
* Atomically adds @i to @v. Note that the guaranteed useful range |
* Atomically adds @i to @v. Note that the guaranteed useful range |
282 |
* of an atomic_t is only 24 bits. |
* of an atomic_t is only 24 bits. |
283 |
*/ |
*/ |
293 |
* atomic_sub - subtract the atomic variable |
* atomic_sub - subtract the atomic variable |
294 |
* @i: integer value to subtract |
* @i: integer value to subtract |
295 |
* @v: pointer of type atomic_t |
* @v: pointer of type atomic_t |
296 |
* |
* |
297 |
* Atomically subtracts @i from @v. Note that the guaranteed |
* Atomically subtracts @i from @v. Note that the guaranteed |
298 |
* useful range of an atomic_t is only 24 bits. |
* useful range of an atomic_t is only 24 bits. |
299 |
*/ |
*/ |
309 |
* atomic_sub_and_test - subtract value from variable and test result |
* atomic_sub_and_test - subtract value from variable and test result |
310 |
* @i: integer value to subtract |
* @i: integer value to subtract |
311 |
* @v: pointer of type atomic_t |
* @v: pointer of type atomic_t |
312 |
* |
* |
313 |
* Atomically subtracts @i from @v and returns |
* Atomically subtracts @i from @v and returns |
314 |
* true if the result is zero, or false for all |
* true if the result is zero, or false for all |
315 |
* other cases. Note that the guaranteed |
* other cases. Note that the guaranteed |
329 |
/** |
/** |
330 |
* atomic_inc - increment atomic variable |
* atomic_inc - increment atomic variable |
331 |
* @v: pointer of type atomic_t |
* @v: pointer of type atomic_t |
332 |
* |
* |
333 |
* Atomically increments @v by 1. Note that the guaranteed |
* Atomically increments @v by 1. Note that the guaranteed |
334 |
* useful range of an atomic_t is only 24 bits. |
* useful range of an atomic_t is only 24 bits. |
335 |
*/ |
*/ |
336 |
static __inline__ void atomic_inc(atomic_t *v) |
static __inline__ void atomic_inc(atomic_t *v) |
337 |
{ |
{ |
338 |
__asm__ __volatile__( |
__asm__ __volatile__( |
344 |
/** |
/** |
345 |
* atomic_dec - decrement atomic variable |
* atomic_dec - decrement atomic variable |
346 |
* @v: pointer of type atomic_t |
* @v: pointer of type atomic_t |
347 |
* |
* |
348 |
* Atomically decrements @v by 1. Note that the guaranteed |
* Atomically decrements @v by 1. Note that the guaranteed |
349 |
* useful range of an atomic_t is only 24 bits. |
* useful range of an atomic_t is only 24 bits. |
350 |
*/ |
*/ |
351 |
static __inline__ void atomic_dec(atomic_t *v) |
static __inline__ void atomic_dec(atomic_t *v) |
352 |
{ |
{ |
353 |
__asm__ __volatile__( |
__asm__ __volatile__( |
359 |
/** |
/** |
360 |
* atomic_dec_and_test - decrement and test |
* atomic_dec_and_test - decrement and test |
361 |
* @v: pointer of type atomic_t |
* @v: pointer of type atomic_t |
362 |
* |
* |
363 |
* Atomically decrements @v by 1 and |
* Atomically decrements @v by 1 and |
364 |
* returns true if the result is 0, or false for all other |
* returns true if the result is 0, or false for all other |
365 |
* cases. Note that the guaranteed |
* cases. Note that the guaranteed |
366 |
* useful range of an atomic_t is only 24 bits. |
* useful range of an atomic_t is only 24 bits. |
367 |
*/ |
*/ |
368 |
static __inline__ int atomic_dec_and_test(atomic_t *v) |
static __inline__ int atomic_dec_and_test(atomic_t *v) |
369 |
{ |
{ |
370 |
unsigned char c; |
unsigned char c; |
377 |
} |
} |
378 |
|
|
379 |
/** |
/** |
380 |
* atomic_inc_and_test - increment and test |
* atomic_inc_and_test - increment and test |
381 |
* @v: pointer of type atomic_t |
* @v: pointer of type atomic_t |
382 |
* |
* |
383 |
* Atomically increments @v by 1 |
* Atomically increments @v by 1 |
384 |
* and returns true if the result is zero, or false for all |
* and returns true if the result is zero, or false for all |
385 |
* other cases. Note that the guaranteed |
* other cases. Note that the guaranteed |
386 |
* useful range of an atomic_t is only 24 bits. |
* useful range of an atomic_t is only 24 bits. |
387 |
*/ |
*/ |
388 |
static __inline__ int atomic_inc_and_test(atomic_t *v) |
static __inline__ int atomic_inc_and_test(atomic_t *v) |
389 |
{ |
{ |
390 |
unsigned char c; |
unsigned char c; |
400 |
* atomic_add_negative - add and test if negative |
* atomic_add_negative - add and test if negative |
401 |
* @v: pointer of type atomic_t |
* @v: pointer of type atomic_t |
402 |
* @i: integer value to add |
* @i: integer value to add |
403 |
* |
* |
404 |
* Atomically adds @i to @v and returns true |
* Atomically adds @i to @v and returns true |
405 |
* if the result is negative, or false when |
* if the result is negative, or false when |
406 |
* result is greater than or equal to zero. Note that the guaranteed |
* result is greater than or equal to zero. Note that the guaranteed |
407 |
* useful range of an atomic_t is only 24 bits. |
* useful range of an atomic_t is only 24 bits. |
408 |
*/ |
*/ |
409 |
static __inline__ int atomic_add_negative(int i, atomic_t *v) |
static __inline__ int atomic_add_negative(int i, atomic_t *v) |
410 |
{ |
{ |
411 |
unsigned char c; |
unsigned char c; |
1191 |
|
|
1192 |
#define __NO_STRICT_ATOMIC |
#define __NO_STRICT_ATOMIC |
1193 |
#ifdef __NO_STRICT_ATOMIC |
#ifdef __NO_STRICT_ATOMIC |
1194 |
|
|
1195 |
/* |
/* |
1196 |
* Because the implementations from the kernel (where all these come |
* Because the implementations from the kernel (where all these come |
1197 |
* from) use cli and spinlocks for hppa and arm... |
* from) use cli and spinlocks for hppa and arm... |
1198 |
*/ |
*/ |
1213 |
{ |
{ |
1214 |
v->counter--; |
v->counter--; |
1215 |
} |
} |
1216 |
|
|
1217 |
static __inline__ int atomic_dec_and_test(atomic_t *v) |
static __inline__ int atomic_dec_and_test(atomic_t *v) |
1218 |
{ |
{ |
1219 |
int res; |
int res; |
1221 |
res = v->counter; |
res = v->counter; |
1222 |
return res == 0; |
return res == 0; |
1223 |
} |
} |
1224 |
|
|
1225 |
static __inline__ int atomic_inc_and_test(atomic_t *v) |
static __inline__ int atomic_inc_and_test(atomic_t *v) |
1226 |
{ |
{ |
1227 |
int res; |
int res; |