LCOV - code coverage report
Current view: top level - common - bitops.h (source / functions) Hit Total Coverage
Test: a simple test Lines: 52 52 100.0 %
Date: 2024-06-05 20:10:43 Functions: 2 2 100.0 %
Legend: Lines: hit not hit

          Line data    Source code
       1             : #ifndef __BITOPS_H__
       2             : #define __BITOPS_H__
       3             : 
       4             : /*
       5             :  * Non-atomic bitops.
       6             :  */
       7             : 
       8             : #include <stdbool.h>
       9             : #include <bits/wordsize.h>
      10             : 
      11             : #define BITS_PER_LONG                   __WORDSIZE
      12             : #define DIV_ROUND_UP(n, d)              (((n) + (d) - 1) / (d))
      13             : #define BITS_TO_LONGS(nr)               DIV_ROUND_UP(nr, BITS_PER_LONG)
      14             : 
      15             : #define BIT_MASK(nr)                    (1UL << ((nr) % BITS_PER_LONG))
      16             : #define BIT_WORD(nr)                    ((nr) / BITS_PER_LONG)
      17             : #define BITMAP_FIRST_WORD_MASK(start)   (~0UL << ((start) & (BITS_PER_LONG - 1)))
      18             : 
      19             : static inline void __set_bit(int nr, volatile unsigned long *addr)
      20             : {
      21   148238006 :         unsigned long mask = BIT_MASK(nr);
      22   148238006 :         unsigned long *p = ((unsigned long *)addr) + BIT_WORD(nr);
      23             : 
      24   148238006 :         *p  |= mask;
      25             : }
      26             : 
      27             : static inline void set_bit(int nr, volatile unsigned long *addr)
      28             : {
      29   145657373 :         __set_bit(nr, addr);
      30             : }
      31             : 
      32             : static inline void __clear_bit(int nr, volatile unsigned long *addr)
      33             : {
      34     4752341 :         unsigned long mask = BIT_MASK(nr);
      35     4752341 :         unsigned long *p = ((unsigned long *)addr) + BIT_WORD(nr);
      36             : 
      37     4752341 :         *p &= ~mask;
      38             : }
      39             : 
      40             : static inline void clear_bit(int nr, volatile unsigned long *addr)
      41             : {
      42     1426678 :         __clear_bit(nr, addr);
      43             : }
      44             : 
      45             : static inline bool test_bit(int nr, const volatile unsigned long *addr)
      46             : {
      47  6967274119 :         unsigned long mask = BIT_MASK(nr);
      48  6967274119 :         unsigned long *p = ((unsigned long *)addr) + BIT_WORD(nr);
      49             : 
      50  6967274119 :         return (*p & mask) != 0;
      51             : }
      52             : 
      53             : /* Sets and returns original value of the bit */
      54             : static inline int test_and_set_bit(int nr, volatile unsigned long *addr)
      55             : {
      56   115585472 :         if (test_bit(nr, addr))
      57             :                 return 1;
      58     2562098 :         set_bit(nr, addr);
      59             :         return 0;
      60             : }
      61             : 
      62             : /**
      63             :  * fls - find last (most-significant) bit set
      64             :  * @x: the word to search
      65             :  *
      66             :  * This is defined the same way as ffs.
      67             :  * Note fls(0) = 0, fls(1) = 1, fls(0x80000000) = 32.
      68             :  */
      69       19300 : static inline int fls(int x)
      70             : {
      71       19300 :         int r = 32;
      72             : 
      73       19300 :         if (!x)
      74             :                 return 0;
      75       19300 :         if (!(x & 0xffff0000u)) {
      76       15258 :                 x <<= 16;
      77       15258 :                 r -= 16;
      78             :         }
      79       19300 :         if (!(x & 0xff000000u)) {
      80       11061 :                 x <<= 8;
      81       11061 :                 r -= 8;
      82             :         }
      83       19300 :         if (!(x & 0xf0000000u)) {
      84       13458 :                 x <<= 4;
      85       13458 :                 r -= 4;
      86             :         }
      87       19300 :         if (!(x & 0xc0000000u)) {
      88       11914 :                 x <<= 2;
      89       11914 :                 r -= 2;
      90             :         }
      91       19300 :         if (!(x & 0x80000000u)) {
      92        8210 :                 x <<= 1;
      93        8210 :                 r -= 1;
      94             :         }
      95             :         return r;
      96             : }
      97             : 
      98             : /**
      99             :  * __ffs - find first bit in word.
     100             :  * @word: The word to search
     101             :  *
     102             :  * Undefined if no bit exists, so code should check against 0 first.
     103             :  */
     104       19640 : static inline unsigned long __ffs(unsigned long word)
     105             : {
     106       19640 :         int num = 0;
     107             : 
     108             : #if BITS_PER_LONG == 64
     109       19640 :         if ((word & 0xffffffff) == 0) {
     110        9452 :                 num += 32;
     111        9452 :                 word >>= 32;
     112             :         }
     113             : #endif
     114       19640 :         if ((word & 0xffff) == 0) {
     115        9643 :                 num += 16;
     116        9643 :                 word >>= 16;
     117             :         }
     118       19640 :         if ((word & 0xff) == 0) {
     119        9595 :                 num += 8;
     120        9595 :                 word >>= 8;
     121             :         }
     122       19640 :         if ((word & 0xf) == 0) {
     123        9679 :                 num += 4;
     124        9679 :                 word >>= 4;
     125             :         }
     126       19640 :         if ((word & 0x3) == 0) {
     127        9694 :                 num += 2;
     128        9694 :                 word >>= 2;
     129             :         }
     130       19640 :         if ((word & 0x1) == 0)
     131        9628 :                 num += 1;
     132       19640 :         return num;
     133             : }
     134             : 
     135             : unsigned long _find_next_bit(const unsigned long *addr,
     136             :                 unsigned long nbits, unsigned long start, unsigned long invert);
     137             : 
     138             : /*
     139             :  * Find the next set bit in a memory region.
     140             :  */
     141             : static inline unsigned long find_next_bit(const unsigned long *addr,
     142             :                         unsigned long size, unsigned long offset)
     143             : {
     144             :         return _find_next_bit(addr, size, offset, 0UL);
     145             : }
     146             : 
     147             : static inline unsigned long find_next_zero_bit(const unsigned long *addr,
     148             :                         unsigned long size, unsigned long offset)
     149             : {
     150       19640 :         return _find_next_bit(addr, size, offset, ~0UL);
     151             : }
     152             : 
     153             : #endif

Generated by: LCOV version 1.13