]> CyberLeo.Net >> Repos - FreeBSD/releng/10.0.git/blob - sys/sys/bitset.h
- Copy stable/10 (r259064) to releng/10.0 as part of the
[FreeBSD/releng/10.0.git] / sys / sys / bitset.h
1 /*-
2  * Copyright (c) 2008, Jeffrey Roberson <jeff@freebsd.org>
3  * All rights reserved.
4  *
5  * Copyright (c) 2008 Nokia Corporation
6  * All rights reserved.
7  *
8  * Redistribution and use in source and binary forms, with or without
9  * modification, are permitted provided that the following conditions
10  * are met:
11  * 1. Redistributions of source code must retain the above copyright
12  *    notice unmodified, this list of conditions, and the following
13  *    disclaimer.
14  * 2. Redistributions in binary form must reproduce the above copyright
15  *    notice, this list of conditions and the following disclaimer in the
16  *    documentation and/or other materials provided with the distribution.
17  *
18  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
19  * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
20  * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
21  * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
22  * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
23  * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
24  * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
25  * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
26  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
27  * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
28  *
29  * $FreeBSD$
30  */
31
32 #ifndef _SYS_BITSET_H_
33 #define _SYS_BITSET_H_
34
35 #define BIT_CLR(_s, n, p)                                               \
36         ((p)->__bits[__bitset_word(_s, n)] &= ~__bitset_mask((_s), (n)))
37
38 #define BIT_COPY(_s, f, t)      (void)(*(t) = *(f))
39
40 #define BIT_ISSET(_s, n, p)                                             \
41         ((((p)->__bits[__bitset_word(_s, n)] & __bitset_mask((_s), (n))) != 0))
42
43 #define BIT_SET(_s, n, p)                                               \
44         ((p)->__bits[__bitset_word(_s, n)] |= __bitset_mask((_s), (n)))
45
46 #define BIT_ZERO(_s, p) do {                                            \
47         __size_t __i;                                                   \
48         for (__i = 0; __i < __bitset_words((_s)); __i++)                \
49                 (p)->__bits[__i] = 0L;                                  \
50 } while (0)
51
52 #define BIT_FILL(_s, p) do {                                            \
53         __size_t __i;                                                   \
54         for (__i = 0; __i < __bitset_words((_s)); __i++)                \
55                 (p)->__bits[__i] = -1L;                                 \
56 } while (0)
57
58 #define BIT_SETOF(_s, n, p) do {                                        \
59         BIT_ZERO(_s, p);                                                \
60         (p)->__bits[__bitset_word(_s, n)] = __bitset_mask((_s), (n));   \
61 } while (0)
62
63 /* Is p empty. */
64 #define BIT_EMPTY(_s, p) __extension__ ({                               \
65         __size_t __i;                                                   \
66         for (__i = 0; __i < __bitset_words((_s)); __i++)                \
67                 if ((p)->__bits[__i])                                   \
68                         break;                                          \
69         __i == __bitset_words((_s));                                    \
70 })
71
72 /* Is p full set. */
73 #define BIT_ISFULLSET(_s, p) __extension__ ({                           \
74         __size_t __i;                                                   \
75         for (__i = 0; __i < __bitset_words((_s)); __i++)                \
76                 if ((p)->__bits[__i] != (long)-1)                       \
77                         break;                                          \
78         __i == __bitset_words((_s));                                    \
79 })
80
81 /* Is c a subset of p. */
82 #define BIT_SUBSET(_s, p, c) __extension__ ({                           \
83         __size_t __i;                                                   \
84         for (__i = 0; __i < __bitset_words((_s)); __i++)                \
85                 if (((c)->__bits[__i] &                                 \
86                     (p)->__bits[__i]) !=                                \
87                     (c)->__bits[__i])                                   \
88                         break;                                          \
89         __i == __bitset_words((_s));                                    \
90 })
91
92 /* Are there any common bits between b & c? */
93 #define BIT_OVERLAP(_s, p, c) __extension__ ({                          \
94         __size_t __i;                                                   \
95         for (__i = 0; __i < __bitset_words((_s)); __i++)                \
96                 if (((c)->__bits[__i] &                                 \
97                     (p)->__bits[__i]) != 0)                             \
98                         break;                                          \
99         __i != __bitset_words((_s));                                    \
100 })
101
102 /* Compare two sets, returns 0 if equal 1 otherwise. */
103 #define BIT_CMP(_s, p, c) __extension__ ({                              \
104         __size_t __i;                                                   \
105         for (__i = 0; __i < __bitset_words((_s)); __i++)                \
106                 if (((c)->__bits[__i] !=                                \
107                     (p)->__bits[__i]))                                  \
108                         break;                                          \
109         __i != __bitset_words((_s));                                    \
110 })
111
112 #define BIT_OR(_s, d, s) do {                                           \
113         __size_t __i;                                                   \
114         for (__i = 0; __i < __bitset_words((_s)); __i++)                \
115                 (d)->__bits[__i] |= (s)->__bits[__i];                   \
116 } while (0)
117
118 #define BIT_AND(_s, d, s) do {                                          \
119         __size_t __i;                                                   \
120         for (__i = 0; __i < __bitset_words((_s)); __i++)                \
121                 (d)->__bits[__i] &= (s)->__bits[__i];                   \
122 } while (0)
123
124 #define BIT_NAND(_s, d, s) do {                                         \
125         __size_t __i;                                                   \
126         for (__i = 0; __i < __bitset_words((_s)); __i++)                \
127                 (d)->__bits[__i] &= ~(s)->__bits[__i];                  \
128 } while (0)
129
130 #define BIT_CLR_ATOMIC(_s, n, p)                                        \
131         atomic_clear_long(&(p)->__bits[__bitset_word(_s, n)],           \
132             __bitset_mask((_s), n))
133
134 #define BIT_SET_ATOMIC(_s, n, p)                                        \
135         atomic_set_long(&(p)->__bits[__bitset_word(_s, n)],             \
136             __bitset_mask((_s), n))
137
138 /* Convenience functions catering special cases. */
139 #define BIT_AND_ATOMIC(_s, d, s) do {                                   \
140         __size_t __i;                                                   \
141         for (__i = 0; __i < __bitset_words((_s)); __i++)                \
142                 atomic_clear_long(&(d)->__bits[__i],                    \
143                     ~(s)->__bits[__i]);                                 \
144 } while (0)
145
146 #define BIT_OR_ATOMIC(_s, d, s) do {                                    \
147         __size_t __i;                                                   \
148         for (__i = 0; __i < __bitset_words((_s)); __i++)                \
149                 atomic_set_long(&(d)->__bits[__i],                      \
150                     (s)->__bits[__i]);                                  \
151 } while (0)
152
153 #define BIT_COPY_STORE_REL(_s, f, t) do {                               \
154         __size_t __i;                                                   \
155         for (__i = 0; __i < __bitset_words((_s)); __i++)                \
156                 atomic_store_rel_long(&(t)->__bits[__i],                \
157                     (f)->__bits[__i]);                                  \
158 } while (0)
159
160 #define BIT_FFS(_s, p) __extension__ ({                                 \
161         __size_t __i;                                                   \
162         int __bit;                                                      \
163                                                                         \
164         __bit = 0;                                                      \
165         for (__i = 0; __i < __bitset_words((_s)); __i++) {              \
166                 if ((p)->__bits[__i] != 0) {                            \
167                         __bit = ffsl((p)->__bits[__i]);                 \
168                         __bit += __i * _BITSET_BITS;                    \
169                         break;                                          \
170                 }                                                       \
171         }                                                               \
172         __bit;                                                          \
173 })
174
175 #endif /* !_SYS_BITSET_H_ */