aboutsummaryrefslogtreecommitdiffstats
path: root/tools/lib/find_bit.c
diff options
context:
space:
mode:
Diffstat (limited to 'tools/lib/find_bit.c')
-rw-r--r--tools/lib/find_bit.c39
1 files changed, 29 insertions, 10 deletions
diff --git a/tools/lib/find_bit.c b/tools/lib/find_bit.c
index 42c15f906aac..a88bd507091e 100644
--- a/tools/lib/find_bit.c
+++ b/tools/lib/find_bit.c
@@ -22,22 +22,29 @@
22#include <linux/bitmap.h> 22#include <linux/bitmap.h>
23#include <linux/kernel.h> 23#include <linux/kernel.h>
24 24
25#if !defined(find_next_bit) 25#if !defined(find_next_bit) || !defined(find_next_zero_bit) || \
26 !defined(find_next_and_bit)
26 27
27/* 28/*
28 * This is a common helper function for find_next_bit and 29 * This is a common helper function for find_next_bit, find_next_zero_bit, and
29 * find_next_zero_bit. The difference is the "invert" argument, which 30 * find_next_and_bit. The differences are:
30 * is XORed with each fetched word before searching it for one bits. 31 * - The "invert" argument, which is XORed with each fetched word before
32 * searching it for one bits.
33 * - The optional "addr2", which is anded with "addr1" if present.
31 */ 34 */
32static unsigned long _find_next_bit(const unsigned long *addr, 35static inline unsigned long _find_next_bit(const unsigned long *addr1,
33 unsigned long nbits, unsigned long start, unsigned long invert) 36 const unsigned long *addr2, unsigned long nbits,
37 unsigned long start, unsigned long invert)
34{ 38{
35 unsigned long tmp; 39 unsigned long tmp;
36 40
37 if (unlikely(start >= nbits)) 41 if (unlikely(start >= nbits))
38 return nbits; 42 return nbits;
39 43
40 tmp = addr[start / BITS_PER_LONG] ^ invert; 44 tmp = addr1[start / BITS_PER_LONG];
45 if (addr2)
46 tmp &= addr2[start / BITS_PER_LONG];
47 tmp ^= invert;
41 48
42 /* Handle 1st word. */ 49 /* Handle 1st word. */
43 tmp &= BITMAP_FIRST_WORD_MASK(start); 50 tmp &= BITMAP_FIRST_WORD_MASK(start);
@@ -48,7 +55,10 @@ static unsigned long _find_next_bit(const unsigned long *addr,
48 if (start >= nbits) 55 if (start >= nbits)
49 return nbits; 56 return nbits;
50 57
51 tmp = addr[start / BITS_PER_LONG] ^ invert; 58 tmp = addr1[start / BITS_PER_LONG];
59 if (addr2)
60 tmp &= addr2[start / BITS_PER_LONG];
61 tmp ^= invert;
52 } 62 }
53 63
54 return min(start + __ffs(tmp), nbits); 64 return min(start + __ffs(tmp), nbits);
@@ -62,7 +72,7 @@ static unsigned long _find_next_bit(const unsigned long *addr,
62unsigned long find_next_bit(const unsigned long *addr, unsigned long size, 72unsigned long find_next_bit(const unsigned long *addr, unsigned long size,
63 unsigned long offset) 73 unsigned long offset)
64{ 74{
65 return _find_next_bit(addr, size, offset, 0UL); 75 return _find_next_bit(addr, NULL, size, offset, 0UL);
66} 76}
67#endif 77#endif
68 78
@@ -104,6 +114,15 @@ unsigned long find_first_zero_bit(const unsigned long *addr, unsigned long size)
104unsigned long find_next_zero_bit(const unsigned long *addr, unsigned long size, 114unsigned long find_next_zero_bit(const unsigned long *addr, unsigned long size,
105 unsigned long offset) 115 unsigned long offset)
106{ 116{
107 return _find_next_bit(addr, size, offset, ~0UL); 117 return _find_next_bit(addr, NULL, size, offset, ~0UL);
118}
119#endif
120
121#ifndef find_next_and_bit
122unsigned long find_next_and_bit(const unsigned long *addr1,
123 const unsigned long *addr2, unsigned long size,
124 unsigned long offset)
125{
126 return _find_next_bit(addr1, addr2, size, offset, 0UL);
108} 127}
109#endif 128#endif