1/* SPDX-License-Identifier: GPL-2.0 */ 2#ifndef _H8300_BITOPS_H 3#define _H8300_BITOPS_H 4 5/* 6 * Copyright 1992, Linus Torvalds. 7 * Copyright 2002, Yoshinori Sato 8 */ 9 10#include <linux/compiler.h> 11 12#ifdef __KERNEL__ 13 14#ifndef _LINUX_BITOPS_H 15#error only <linux/bitops.h> can be included directly 16#endif 17 18/* 19 * Function prototypes to keep gcc -Wall happy 20 */ 21 22/* 23 * ffz = Find First Zero in word. Undefined if no zero exists, 24 * so code should check against ~0UL first.. 25 */ 26static inline unsigned long ffz(unsigned long word) 27{ 28 unsigned long result; 29 30 result = -1; 31 __asm__("1:\n\t" 32 "shlr.l %1\n\t" 33 "adds #1,%0\n\t" 34 "bcs 1b" 35 : "=r"(result),"=r"(word) 36 : "0"(result), "1"(word)); 37 return result; 38} 39 40#define H8300_GEN_BITOP(FNAME, OP) \ 41static inline void FNAME(int nr, volatile unsigned long *addr) \ 42{ \ 43 unsigned char *b_addr; \ 44 unsigned char bit = nr & 7; \ 45 \ 46 b_addr = (unsigned char *)addr + ((nr >> 3) ^ 3); \ 47 if (__builtin_constant_p(nr)) { \ 48 __asm__(OP " %1,%0" : "+WU"(*b_addr) : "i"(nr & 7)); \ 49 } else { \ 50 __asm__(OP " %s1,%0" : "+WU"(*b_addr) : "r"(bit)); \ 51 } \ 52} 53 54H8300_GEN_BITOP(set_bit, "bset") 55H8300_GEN_BITOP(clear_bit, "bclr") 56H8300_GEN_BITOP(change_bit, "bnot") 57#define __set_bit(nr, addr) set_bit((nr), (addr)) 58#define __clear_bit(nr, addr) clear_bit((nr), (addr)) 59#define __change_bit(nr, addr) change_bit((nr), (addr)) 60 61#undef H8300_GEN_BITOP 62 63static inline int test_bit(int nr, const volatile unsigned long *addr) 64{ 65 int ret = 0; 66 unsigned char *b_addr; 67 unsigned char bit = nr & 7; 68 69 b_addr = (unsigned char *)addr + ((nr >> 3) ^ 3); 70 if (__builtin_constant_p(nr)) { 71 __asm__("bld %Z2,%1\n\t" 72 "rotxl %0\n\t" 73 : "=r"(ret) 74 : "WU"(*b_addr), "i"(nr & 7), "0"(ret) : "cc"); 75 } else { 76 __asm__("btst %w2,%1\n\t" 77 "beq 1f\n\t" 78 "inc.l #1,%0\n" 79 "1:" 80 : "=r"(ret) 81 : "WU"(*b_addr), "r"(bit), "0"(ret) : "cc"); 82 } 83 return ret; 84} 85 86#define __test_bit(nr, addr) test_bit(nr, addr) 87 88#define H8300_GEN_TEST_BITOP(FNNAME, OP) \ 89static inline int FNNAME(int nr, void *addr) \ 90{ \ 91 int retval = 0; \ 92 char ccrsave; \ 93 unsigned char *b_addr; \ 94 unsigned char bit = nr & 7; \ 95 \ 96 b_addr = (unsigned char *)addr + ((nr >> 3) ^ 3); \ 97 if (__builtin_constant_p(nr)) { \ 98 __asm__("stc ccr,%s2\n\t" \ 99 "orc #0x80,ccr\n\t" \ 100 "bld %4,%1\n\t" \ 101 OP " %4,%1\n\t" \ 102 "rotxl.l %0\n\t" \ 103 "ldc %s2,ccr" \ 104 : "=r"(retval), "+WU" (*b_addr), "=&r"(ccrsave) \ 105 : "0"(retval), "i"(nr & 7) : "cc"); \ 106 } else { \ 107 __asm__("stc ccr,%t3\n\t" \ 108 "orc #0x80,ccr\n\t" \ 109 "btst %s3,%1\n\t" \ 110 OP " %s3,%1\n\t" \ 111 "beq 1f\n\t" \ 112 "inc.l #1,%0\n\t" \ 113 "1:\n" \ 114 "ldc %t3,ccr" \ 115 : "=r"(retval), "+WU" (*b_addr) \ 116 : "0" (retval), "r"(bit) : "cc"); \ 117 } \ 118 return retval; \ 119} \ 120 \ 121static inline int __ ## FNNAME(int nr, void *addr) \ 122{ \ 123 int retval = 0; \ 124 unsigned char *b_addr; \ 125 unsigned char bit = nr & 7; \ 126 \ 127 b_addr = (unsigned char *)addr + ((nr >> 3) ^ 3); \ 128 if (__builtin_constant_p(nr)) { \ 129 __asm__("bld %3,%1\n\t" \ 130 OP " %3,%1\n\t" \ 131 "rotxl.l %0\n\t" \ 132 : "=r"(retval), "+WU"(*b_addr) \ 133 : "0" (retval), "i"(nr & 7)); \ 134 } else { \ 135 __asm__("btst %s3,%1\n\t" \ 136 OP " %s3,%1\n\t" \ 137 "beq 1f\n\t" \ 138 "inc.l #1,%0\n\t" \ 139 "1:" \ 140 : "=r"(retval), "+WU"(*b_addr) \ 141 : "0" (retval), "r"(bit)); \ 142 } \ 143 return retval; \ 144} 145 146H8300_GEN_TEST_BITOP(test_and_set_bit, "bset") 147H8300_GEN_TEST_BITOP(test_and_clear_bit, "bclr") 148H8300_GEN_TEST_BITOP(test_and_change_bit, "bnot") 149#undef H8300_GEN_TEST_BITOP 150 151#include <asm-generic/bitops/ffs.h> 152 153static inline unsigned long __ffs(unsigned long word) 154{ 155 unsigned long result; 156 157 result = -1; 158 __asm__("1:\n\t" 159 "shlr.l %1\n\t" 160 "adds #1,%0\n\t" 161 "bcc 1b" 162 : "=r" (result),"=r"(word) 163 : "0"(result), "1"(word)); 164 return result; 165} 166 167#include <asm-generic/bitops/find.h> 168#include <asm-generic/bitops/sched.h> 169#include <asm-generic/bitops/hweight.h> 170#include <asm-generic/bitops/lock.h> 171#include <asm-generic/bitops/le.h> 172#include <asm-generic/bitops/ext2-atomic.h> 173 174#endif /* __KERNEL__ */ 175 176#include <asm-generic/bitops/fls.h> 177#include <asm-generic/bitops/__fls.h> 178#include <asm-generic/bitops/fls64.h> 179 180#endif /* _H8300_BITOPS_H */ 181