| @@ -1,3 +1,12 @@ |
| 1 | +/* uses alias to allow building with gcc/clang */ |
| 2 | +#ifdef __TINYC__ |
| 3 | +#define BUILTIN(x) __builtin_##x |
| 4 | +#define BUILTINN(x) "__builtin_" # x |
| 5 | +#else |
| 6 | +#define BUILTIN(x) __tcc_builtin_##x |
| 7 | +#define BUILTINN(x) "__tcc_builtin_" # x |
| 8 | +#endif |
| 9 | + |
| 1 | 10 | /* ---------------------------------------------- */ |
| 2 | 11 | /* This file implements: |
| 3 | 12 | * __builtin_ffs |
| @@ -66,59 +75,90 @@ static const unsigned char table_2_64[] = { · 62 unmodified lines |
| 66 | 75 | |
| 67 | 76 | /* Returns one plus the index of the least significant 1-bit of x, |
| 68 | 77 | or if x is zero, returns zero. */ |
| 69 | | −int __builtin_ffs (int x) { FFSI(x) } |
| 78 | +int BUILTIN(ffs) (int x) { FFSI(x) } |
| 79 | +int BUILTIN(ffsll) (long long x) { FFSL(x) } |
| 70 | 80 | #if __SIZEOF_LONG__ == 4 |
| 71 | | −int __builtin_ffsl (long x) { FFSI(x) } |
| 81 | +int BUILTIN(ffsl) (long x) __attribute__((alias(BUILTINN(ffs)))); |
| 72 | 82 | #else |
| 73 | | −int __builtin_ffsl (long x) { FFSL(x) } |
| 83 | +int BUILTIN(ffsl) (long x) __attribute__((alias(BUILTINN(ffsll)))); |
| 74 | 84 | #endif |
| 75 | | −int __builtin_ffsll (long long x) { FFSL(x) } |
| 76 | 85 | |
| 77 | 86 | /* Returns the number of leading 0-bits in x, starting at the most significant |
| 78 | 87 | bit position. If x is 0, the result is undefined. */ |
| 79 | | −int __builtin_clz (unsigned int x) { CLZI(x) } |
| 88 | +int BUILTIN(clz) (unsigned int x) { CLZI(x) } |
| 89 | +int BUILTIN(clzll) (unsigned long long x) { CLZL(x) } |
| 80 | 90 | #if __SIZEOF_LONG__ == 4 |
| 81 | | −int __builtin_clzl (unsigned long x) { CLZI(x) } |
| 91 | +int BUILTIN(clzl) (unsigned long x) __attribute__((alias(BUILTINN(clz)))); |
| 82 | 92 | #else |
| 83 | | −int __builtin_clzl (unsigned long x) { CLZL(x) } |
| 93 | +int BUILTIN(clzl) (unsigned long x) __attribute__((alias(BUILTINN(clzll)))); |
| 84 | 94 | #endif |
| 85 | | −int __builtin_clzll (unsigned long long x) { CLZL(x) } |
| 86 | 95 | |
| 87 | 96 | /* Returns the number of trailing 0-bits in x, starting at the least |
| 88 | 97 | significant bit position. If x is 0, the result is undefined. */ |
| 89 | | −int __builtin_ctz (unsigned int x) { CTZI(x) } |
| 98 | +int BUILTIN(ctz) (unsigned int x) { CTZI(x) } |
| 99 | +int BUILTIN(ctzll) (unsigned long long x) { CTZL(x) } |
| 90 | 100 | #if __SIZEOF_LONG__ == 4 |
| 91 | | −int __builtin_ctzl (unsigned long x) { CTZI(x) } |
| 101 | +int BUILTIN(ctzl) (unsigned long x) __attribute__((alias(BUILTINN(ctz)))); |
| 92 | 102 | #else |
| 93 | | −int __builtin_ctzl (unsigned long x) { CTZL(x) } |
| 103 | +int BUILTIN(ctzl) (unsigned long x) __attribute__((alias(BUILTINN(ctzll)))); |
| 94 | 104 | #endif |
| 95 | | −int __builtin_ctzll (unsigned long long x) { CTZL(x) } |
| 96 | 105 | |
| 97 | 106 | /* Returns the number of leading redundant sign bits in x, i.e. the number |
| 98 | 107 | of bits following the most significant bit that are identical to it. |
| 99 | 108 | There are no special cases for 0 or other values. */ |
| 100 | | −int __builtin_clrsb (int x) { if (x < 0) x = ~x; x <<= 1; CLZI(x) } |
| 109 | +int BUILTIN(clrsb) (int x) { if (x < 0) x = ~x; x <<= 1; CLZI(x) } |
| 110 | +int BUILTIN(clrsbll) (long long x) { if (x < 0) x = ~x; x <<= 1; CLZL(x) } |
| 101 | 111 | #if __SIZEOF_LONG__ == 4 |
| 102 | | −int __builtin_clrsbl (long x) { if (x < 0) x = ~x; x <<= 1; CLZI(x) } |
| 112 | +int BUILTIN(clrsbl) (long x) __attribute__((alias(BUILTINN(clrsb)))); |
| 103 | 113 | #else |
| 104 | | −int __builtin_clrsbl (long x) { if (x < 0) x = ~x; x <<= 1; CLZL(x) } |
| 114 | +int BUILTIN(clrsbl) (long x) __attribute__((alias(BUILTINN(clrsbll)))); |
| 105 | 115 | #endif |
| 106 | | −int __builtin_clrsbll (long long x) { if (x < 0) x = ~x; x <<= 1; CLZL(x) } |
| 107 | 116 | |
| 108 | 117 | /* Returns the number of 1-bits in x.*/ |
| 109 | | −int __builtin_popcount (unsigned int x) { POPCOUNTI(x, 0x3f) } |
| 118 | +int BUILTIN(popcount) (unsigned int x) { POPCOUNTI(x, 0x3f) } |
| 119 | +int BUILTIN(popcountll) (unsigned long long x) { POPCOUNTL(x, 0x7f) } |
| 110 | 120 | #if __SIZEOF_LONG__ == 4 |
| 111 | | −int __builtin_popcountl (unsigned long x) { POPCOUNTI(x, 0x3f) } |
| 121 | +int BUILTIN(popcountl) (unsigned long x) __attribute__((alias(BUILTINN(popcount)))); |
| 112 | 122 | #else |
| 113 | | −int __builtin_popcountl (unsigned long x) { POPCOUNTL(x, 0x7f) } |
| 123 | +int BUILTIN(popcountl ) (unsigned long x) __attribute__((alias(BUILTINN(popcountll)))); |
| 114 | 124 | #endif |
| 115 | | −int __builtin_popcountll (unsigned long long x) { POPCOUNTL(x, 0x7f) } |
| 116 | 125 | |
| 117 | 126 | /* Returns the parity of x, i.e. the number of 1-bits in x modulo 2. */ |
| 118 | | −int __builtin_parity (unsigned int x) { POPCOUNTI(x, 0x01) } |
| 127 | +int BUILTIN(parity) (unsigned int x) { POPCOUNTI(x, 0x01) } |
| 128 | +int BUILTIN(parityll) (unsigned long long x) { POPCOUNTL(x, 0x01) } |
| 119 | 129 | #if __SIZEOF_LONG__ == 4 |
| 120 | | −int __builtin_parityl (unsigned long x) { POPCOUNTI(x, 0x01) } |
| 130 | +int BUILTIN(parityl) (unsigned long x) __attribute__((alias(BUILTINN(parity)))); |
| 121 | 131 | #else |
| 122 | | −int __builtin_parityl (unsigned long x) { POPCOUNTL(x, 0x01) } |
| 132 | +int BUILTIN(parityl) (unsigned long x) __attribute__((alias(BUILTINN(parityll)))); |
| 133 | +#endif |
| 134 | + |
| 135 | +#ifndef __TINYC__ |
| 136 | +#if defined(__GNUC__) && (__GNUC__ >= 6) |
| 137 | +/* gcc overrides alias from __builtin_ffs... to ffs.. so use assembly code */ |
| 138 | +__asm__(".globl __builtin_ffs"); |
| 139 | +__asm__(".set __builtin_ffs,__tcc_builtin_ffs"); |
| 140 | +__asm__(".globl __builtin_ffsl"); |
| 141 | +__asm__(".set __builtin_ffsl,__tcc_builtin_ffsl"); |
| 142 | +__asm__(".globl __builtin_ffsll"); |
| 143 | +__asm__(".set __builtin_ffsll,__tcc_builtin_ffsll"); |
| 144 | +#else |
| 145 | +int __builtin_ffs(int x) __attribute__((alias("__tcc_builtin_ffs"))); |
| 146 | +int __builtin_ffsl(long x) __attribute__((alias("__tcc_builtin_ffsl"))); |
| 147 | +int __builtin_ffsll(long long x) __attribute__((alias("__tcc_builtin_ffsll"))); |
| 148 | +#endif |
| 149 | +int __builtin_clz(unsigned int x) __attribute__((alias("__tcc_builtin_clz"))); |
| 150 | +int __builtin_clzl(unsigned long x) __attribute__((alias("__tcc_builtin_clzl"))); |
| 151 | +int __builtin_clzll(unsigned long long x) __attribute__((alias("__tcc_builtin_clzll"))); |
| 152 | +int __builtin_ctz(unsigned int x) __attribute__((alias("__tcc_builtin_ctz"))); |
| 153 | +int __builtin_ctzl(unsigned long x) __attribute__((alias("__tcc_builtin_ctzl"))); |
| 154 | +int __builtin_ctzll(unsigned long long x) __attribute__((alias("__tcc_builtin_ctzll"))); |
| 155 | +int __builtin_clrsb(int x) __attribute__((alias("__tcc_builtin_clrsb"))); |
| 156 | +int __builtin_clrsbl(long x) __attribute__((alias("__tcc_builtin_clrsbl"))); |
| 157 | +int __builtin_clrsbll(long long x) __attribute__((alias("__tcc_builtin_clrsbll"))); |
| 158 | +int __builtin_popcount(unsigned int x) __attribute__((alias("__tcc_builtin_popcount"))); |
| 159 | +int __builtin_popcountl(unsigned long x) __attribute__((alias("__tcc_builtin_popcountl"))); |
| 160 | +int __builtin_popcountll(unsigned long long x) __attribute__((alias("__tcc_builtin_popcountll"))); |
| 161 | +int __builtin_parity(unsigned int x) __attribute__((alias("__tcc_builtin_parity"))); |
| 162 | +int __builtin_parityl(unsigned long x) __attribute__((alias("__tcc_builtin_parityl"))); |
| 163 | +int __builtin_parityll(unsigned long long x) __attribute__((alias("__tcc_builtin_parityll"))); |
| 123 | 164 | #endif |
| 124 | | −int __builtin_parityll (unsigned long long x) { POPCOUNTL(x, 0x01) } |