source: trunk/packages/xen-3.1/xen-3.1/xen/arch/powerpc/bitops.c @ 34

Last change on this file since 34 was 34, checked in by hartmans, 17 years ago

Add xen and xen-common

File size: 2.5 KB
Line 
1/* from linux/arch/powerpc/lib/bitops.c */
2
3#include <asm/types.h>
4#include <asm/bitops.h>
5
6#define BITOP_WORD(nr)      ((nr) / BITS_PER_LONG)
7
8/**
9 * find_next_bit - find the next set bit in a memory region
10 * @addr: The address to base the search on
11 * @offset: The bitnumber to start searching at
12 * @size: The maximum size to search
13 */
14unsigned long find_next_bit(const unsigned long *addr, unsigned long size,
15                            unsigned long offset)
16{
17    const unsigned long *p = addr + BITOP_WORD(offset);
18    unsigned long result = offset & ~(BITS_PER_LONG-1);
19    unsigned long tmp;
20
21    if (offset >= size)
22        return size;
23    size -= result;
24    offset %= BITS_PER_LONG;
25    if (offset) {
26        tmp = *(p++);
27        tmp &= (~0UL << offset);
28        if (size < BITS_PER_LONG)
29            goto found_first;
30        if (tmp)
31            goto found_middle;
32        size -= BITS_PER_LONG;
33        result += BITS_PER_LONG;
34    }
35    while (size & ~(BITS_PER_LONG-1)) {
36        if ((tmp = *(p++)))
37            goto found_middle;
38        result += BITS_PER_LONG;
39        size -= BITS_PER_LONG;
40    }
41    if (!size)
42        return result;
43    tmp = *p;
44
45found_first:
46    tmp &= (~0UL >> (BITS_PER_LONG - size));
47    if (tmp == 0UL)        /* Are any bits set? */
48        return result + size;    /* Nope. */
49found_middle:
50    return result + __ffs(tmp);
51}
52
53/*
54 * This implementation of find_{first,next}_zero_bit was stolen from
55 * Linus' asm-alpha/bitops.h.
56 */
57unsigned long find_next_zero_bit(const unsigned long *addr, unsigned long size,
58                                 unsigned long offset)
59{
60    const unsigned long *p = addr + BITOP_WORD(offset);
61    unsigned long result = offset & ~(BITS_PER_LONG-1);
62    unsigned long tmp;
63
64    if (offset >= size)
65        return size;
66    size -= result;
67    offset %= BITS_PER_LONG;
68    if (offset) {
69        tmp = *(p++);
70        tmp |= ~0UL >> (BITS_PER_LONG - offset);
71        if (size < BITS_PER_LONG)
72            goto found_first;
73        if (~tmp)
74            goto found_middle;
75        size -= BITS_PER_LONG;
76        result += BITS_PER_LONG;
77    }
78    while (size & ~(BITS_PER_LONG-1)) {
79        if (~(tmp = *(p++)))
80            goto found_middle;
81        result += BITS_PER_LONG;
82        size -= BITS_PER_LONG;
83    }
84    if (!size)
85        return result;
86    tmp = *p;
87
88found_first:
89    tmp |= ~0UL << size;
90    if (tmp == ~0UL)    /* Are any bits zero? */
91        return result + size;    /* Nope. */
92found_middle:
93    return result + ffz(tmp);
94}
Note: See TracBrowser for help on using the repository browser.