Line data Source code
1 0 : /*
2 : * Copyright (c) 2015, Wind River Systems, Inc.
3 : * Copyright (c) 2017, Oticon A/S
4 : *
5 : * SPDX-License-Identifier: Apache-2.0
6 : */
7 :
8 : #ifndef ZEPHYR_INCLUDE_ARCH_COMMON_FFS_H_
9 : #define ZEPHYR_INCLUDE_ARCH_COMMON_FFS_H_
10 :
11 : #ifndef _ASMLANGUAGE
12 :
13 : #include <zephyr/types.h>
14 : #include <zephyr/toolchain.h>
15 :
16 : #ifdef __cplusplus
17 : extern "C" {
18 : #endif
19 :
20 : /**
21 : *
22 : * @brief find most significant bit set in a 32-bit word
23 : *
24 : * This routine finds the first bit set starting from the most significant bit
25 : * in the argument passed in and returns the index of that bit. Bits are
26 : * numbered starting at 1 from the least significant bit. A return value of
27 : * zero indicates that the value passed is zero.
28 : *
29 : * @return most significant bit set, 0 if @a op is 0
30 : */
31 :
32 1 : static ALWAYS_INLINE unsigned int find_msb_set(uint32_t op)
33 : {
34 : if (op == 0) {
35 : return 0;
36 : }
37 :
38 : return 32 - __builtin_clz(op);
39 : }
40 :
41 :
42 : /**
43 : *
44 : * @brief find least significant bit set in a 32-bit word
45 : *
46 : * This routine finds the first bit set starting from the least significant bit
47 : * in the argument passed in and returns the index of that bit. Bits are
48 : * numbered starting at 1 from the least significant bit. A return value of
49 : * zero indicates that the value passed is zero.
50 : *
51 : * @return least significant bit set, 0 if @a op is 0
52 : */
53 :
54 1 : static ALWAYS_INLINE unsigned int find_lsb_set(uint32_t op)
55 : {
56 : #ifdef CONFIG_TOOLCHAIN_HAS_BUILTIN_FFS
57 : return __builtin_ffs(op);
58 :
59 : #else
60 : /*
61 : * Toolchain does not have __builtin_ffs(). Leverage find_lsb_set()
62 : * by first clearing all but the lowest set bit.
63 : */
64 :
65 : op = op ^ (op & (op - 1));
66 :
67 : return find_msb_set(op);
68 : #endif /* CONFIG_TOOLCHAIN_HAS_BUILTIN_FFS */
69 : }
70 :
71 : #ifdef __cplusplus
72 : }
73 : #endif
74 :
75 : #endif /* _ASMLANGUAGE */
76 :
77 : #endif /* ZEPHYR_INCLUDE_ARCH_COMMON_FFS_H_ */
|