diff options
| author | Aneesh Kumar K.V <aneesh.kumar@linux.vnet.ibm.com> | 2008-01-28 23:58:27 -0500 | 
|---|---|---|
| committer | Theodore Ts'o <tytso@mit.edu> | 2008-01-28 23:58:27 -0500 | 
| commit | aa02ad67d9b308290fde390682cd039b29f7ab85 (patch) | |
| tree | 1ebf910ab16e6081b5dd3ca526973f09cfd065c4 /lib | |
| parent | c549a95d40efd83fc054785dd1634e8b71fba890 (diff) | |
ext4: Add ext4_find_next_bit()
This function is used by the ext4 multi block allocator patches.
Also add generic_find_next_le_bit
Signed-off-by: Aneesh Kumar K.V <aneesh.kumar@linux.vnet.ibm.com>
Cc: <linux-ext4@vger.kernel.org>
Signed-off-by: Andrew Morton <akpm@linux-foundation.org>
Diffstat (limited to 'lib')
| -rw-r--r-- | lib/find_next_bit.c | 43 | 
1 files changed, 43 insertions, 0 deletions
| diff --git a/lib/find_next_bit.c b/lib/find_next_bit.c index bda0d71a2514..78ccd73a8841 100644 --- a/lib/find_next_bit.c +++ b/lib/find_next_bit.c @@ -178,4 +178,47 @@ found_middle_swap:  EXPORT_SYMBOL(generic_find_next_zero_le_bit); +unsigned long generic_find_next_le_bit(const unsigned long *addr, unsigned +		long size, unsigned long offset) +{ +	const unsigned long *p = addr + BITOP_WORD(offset); +	unsigned long result = offset & ~(BITS_PER_LONG - 1); +	unsigned long tmp; + +	if (offset >= size) +		return size; +	size -= result; +	offset &= (BITS_PER_LONG - 1UL); +	if (offset) { +		tmp = ext2_swabp(p++); +		tmp &= (~0UL << offset); +		if (size < BITS_PER_LONG) +			goto found_first; +		if (tmp) +			goto found_middle; +		size -= BITS_PER_LONG; +		result += BITS_PER_LONG; +	} + +	while (size & ~(BITS_PER_LONG - 1)) { +		tmp = *(p++); +		if (tmp) +			goto found_middle_swap; +		result += BITS_PER_LONG; +		size -= BITS_PER_LONG; +	} +	if (!size) +		return result; +	tmp = ext2_swabp(p); +found_first: +	tmp &= (~0UL >> (BITS_PER_LONG - size)); +	if (tmp == 0UL)		/* Are any bits set? */ +		return result + size; /* Nope. */ +found_middle: +	return result + __ffs(tmp); + +found_middle_swap: +	return result + __ffs(ext2_swab(tmp)); +} +EXPORT_SYMBOL(generic_find_next_le_bit);  #endif /* __BIG_ENDIAN */ | 
