Linux Kernel  3.7.1
 All Data Structures Namespaces Files Functions Variables Typedefs Enumerations Enumerator Macros Groups Pages
bitops_32.h
Go to the documentation of this file.
1 /*
2  * Copyright 2010 Tilera Corporation. All Rights Reserved.
3  *
4  * This program is free software; you can redistribute it and/or
5  * modify it under the terms of the GNU General Public License
6  * as published by the Free Software Foundation, version 2.
7  *
8  * This program is distributed in the hope that it will be useful, but
9  * WITHOUT ANY WARRANTY; without even the implied warranty of
10  * MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE, GOOD TITLE or
11  * NON INFRINGEMENT. See the GNU General Public License for
12  * more details.
13  */
14 
15 #ifndef _ASM_TILE_BITOPS_32_H
16 #define _ASM_TILE_BITOPS_32_H
17 
18 #include <linux/compiler.h>
19 #include <linux/atomic.h>
20 
21 /* Tile-specific routines to support <asm/bitops.h>. */
22 unsigned long _atomic_or(volatile unsigned long *p, unsigned long mask);
23 unsigned long _atomic_andn(volatile unsigned long *p, unsigned long mask);
24 unsigned long _atomic_xor(volatile unsigned long *p, unsigned long mask);
25 
36 static inline void set_bit(unsigned nr, volatile unsigned long *addr)
37 {
38  _atomic_or(addr + BIT_WORD(nr), BIT_MASK(nr));
39 }
40 
55 static inline void clear_bit(unsigned nr, volatile unsigned long *addr)
56 {
57  _atomic_andn(addr + BIT_WORD(nr), BIT_MASK(nr));
58 }
59 
70 static inline void change_bit(unsigned nr, volatile unsigned long *addr)
71 {
72  _atomic_xor(addr + BIT_WORD(nr), BIT_MASK(nr));
73 }
74 
83 static inline int test_and_set_bit(unsigned nr, volatile unsigned long *addr)
84 {
85  unsigned long mask = BIT_MASK(nr);
86  addr += BIT_WORD(nr);
87  smp_mb(); /* barrier for proper semantics */
88  return (_atomic_or(addr, mask) & mask) != 0;
89 }
90 
99 static inline int test_and_clear_bit(unsigned nr, volatile unsigned long *addr)
100 {
101  unsigned long mask = BIT_MASK(nr);
102  addr += BIT_WORD(nr);
103  smp_mb(); /* barrier for proper semantics */
104  return (_atomic_andn(addr, mask) & mask) != 0;
105 }
106 
115 static inline int test_and_change_bit(unsigned nr,
116  volatile unsigned long *addr)
117 {
118  unsigned long mask = BIT_MASK(nr);
119  addr += BIT_WORD(nr);
120  smp_mb(); /* barrier for proper semantics */
121  return (_atomic_xor(addr, mask) & mask) != 0;
122 }
123 
124 /* See discussion at smp_mb__before_atomic_dec() in <asm/atomic_32.h>. */
125 #define smp_mb__before_clear_bit() smp_mb()
126 #define smp_mb__after_clear_bit() do {} while (0)
127 
129 
130 #endif /* _ASM_TILE_BITOPS_32_H */