bit_operations.h
Go to the documentation of this file.00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028 #if !defined(_SPANDSP_BIT_OPERATIONS_H_)
00029 #define _SPANDSP_BIT_OPERATIONS_H_
00030
00031 #if defined(__i386__) || defined(__x86_64__)
00032 #if !defined(__SUNPRO_C) || (__SUNPRO_C >= 0x0590)
00033 #define SPANDSP_USE_86_ASM
00034 #endif
00035 #endif
00036
00037 #if defined(__cplusplus)
00038 extern "C"
00039 {
00040 #endif
00041
00042
00043
00044
00045 static __inline__ int top_bit(unsigned int bits)
00046 {
00047 #if defined(SPANDSP_USE_86_ASM)
00048 int res;
00049
00050 __asm__ (" xorl %[res],%[res];\n"
00051 " decl %[res];\n"
00052 " bsrl %[bits],%[res]\n"
00053 : [res] "=&r" (res)
00054 : [bits] "rm" (bits));
00055 return res;
00056 #elif defined(__ppc__) || defined(__powerpc__)
00057 int res;
00058
00059 __asm__ ("cntlzw %[res],%[bits];\n"
00060 : [res] "=&r" (res)
00061 : [bits] "r" (bits));
00062 return 31 - res;
00063 #elif defined(_M_IX86)
00064
00065 __asm
00066 {
00067 xor eax, eax
00068 dec eax
00069 bsr eax, bits
00070 }
00071 #elif defined(_M_X64)
00072
00073
00074 int res;
00075
00076 if (bits == 0)
00077 return -1;
00078 res = 0;
00079 if (bits & 0xFFFF0000)
00080 {
00081 bits &= 0xFFFF0000;
00082 res += 16;
00083 }
00084 if (bits & 0xFF00FF00)
00085 {
00086 bits &= 0xFF00FF00;
00087 res += 8;
00088 }
00089 if (bits & 0xF0F0F0F0)
00090 {
00091 bits &= 0xF0F0F0F0;
00092 res += 4;
00093 }
00094 if (bits & 0xCCCCCCCC)
00095 {
00096 bits &= 0xCCCCCCCC;
00097 res += 2;
00098 }
00099 if (bits & 0xAAAAAAAA)
00100 {
00101 bits &= 0xAAAAAAAA;
00102 res += 1;
00103 }
00104 return res;
00105 #else
00106 int res;
00107
00108 if (bits == 0)
00109 return -1;
00110 res = 0;
00111 if (bits & 0xFFFF0000)
00112 {
00113 bits &= 0xFFFF0000;
00114 res += 16;
00115 }
00116 if (bits & 0xFF00FF00)
00117 {
00118 bits &= 0xFF00FF00;
00119 res += 8;
00120 }
00121 if (bits & 0xF0F0F0F0)
00122 {
00123 bits &= 0xF0F0F0F0;
00124 res += 4;
00125 }
00126 if (bits & 0xCCCCCCCC)
00127 {
00128 bits &= 0xCCCCCCCC;
00129 res += 2;
00130 }
00131 if (bits & 0xAAAAAAAA)
00132 {
00133 bits &= 0xAAAAAAAA;
00134 res += 1;
00135 }
00136 return res;
00137 #endif
00138 }
00139
00140
00141
00142
00143
00144 static __inline__ int bottom_bit(unsigned int bits)
00145 {
00146 int res;
00147
00148 #if defined(SPANDSP_USE_86_ASM)
00149 __asm__ (" xorl %[res],%[res];\n"
00150 " decl %[res];\n"
00151 " bsfl %[bits],%[res]\n"
00152 : [res] "=&r" (res)
00153 : [bits] "rm" (bits));
00154 return res;
00155 #else
00156 if (bits == 0)
00157 return -1;
00158 res = 31;
00159 if (bits & 0x0000FFFF)
00160 {
00161 bits &= 0x0000FFFF;
00162 res -= 16;
00163 }
00164 if (bits & 0x00FF00FF)
00165 {
00166 bits &= 0x00FF00FF;
00167 res -= 8;
00168 }
00169 if (bits & 0x0F0F0F0F)
00170 {
00171 bits &= 0x0F0F0F0F;
00172 res -= 4;
00173 }
00174 if (bits & 0x33333333)
00175 {
00176 bits &= 0x33333333;
00177 res -= 2;
00178 }
00179 if (bits & 0x55555555)
00180 {
00181 bits &= 0x55555555;
00182 res -= 1;
00183 }
00184 return res;
00185 #endif
00186 }
00187
00188
00189
00190
00191
00192 static __inline__ uint8_t bit_reverse8(uint8_t x)
00193 {
00194 #if defined(__i386__) || defined(__x86_64__) || defined(__ppc__) || defined(__powerpc__)
00195
00196 return ((x*0x0802U & 0x22110U) | (x*0x8020U & 0x88440U))*0x10101U >> 16;
00197 #else
00198
00199 x = (x >> 4) | (x << 4);
00200 x = ((x & 0xCC) >> 2) | ((x & 0x33) << 2);
00201 return ((x & 0xAA) >> 1) | ((x & 0x55) << 1);
00202 #endif
00203 }
00204
00205
00206
00207
00208
00209 SPAN_DECLARE(uint16_t) bit_reverse16(uint16_t data);
00210
00211
00212
00213
00214 SPAN_DECLARE(uint32_t) bit_reverse32(uint32_t data);
00215
00216
00217
00218
00219 SPAN_DECLARE(uint32_t) bit_reverse_4bytes(uint32_t data);
00220
00221 #if defined(__x86_64__)
00222
00223
00224
00225 SPAN_DECLARE(uint64_t) bit_reverse_8bytes(uint64_t data);
00226 #endif
00227
00228
00229
00230
00231
00232 SPAN_DECLARE(void) bit_reverse(uint8_t to[], const uint8_t from[], int len);
00233
00234
00235
00236
00237 SPAN_DECLARE(int) one_bits32(uint32_t x);
00238
00239
00240
00241
00242 SPAN_DECLARE(uint32_t) make_mask32(uint32_t x);
00243
00244
00245
00246
00247 SPAN_DECLARE(uint16_t) make_mask16(uint16_t x);
00248
00249
00250
00251
00252
00253 static __inline__ uint32_t least_significant_one32(uint32_t x)
00254 {
00255 return (x & (-(int32_t) x));
00256 }
00257
00258
00259
00260
00261
00262
00263 static __inline__ uint32_t most_significant_one32(uint32_t x)
00264 {
00265 #if defined(__i386__) || defined(__x86_64__) || defined(__ppc__) || defined(__powerpc__)
00266 return 1 << top_bit(x);
00267 #else
00268 x = make_mask32(x);
00269 return (x ^ (x >> 1));
00270 #endif
00271 }
00272
00273
00274
00275
00276
00277 static __inline__ int parity8(uint8_t x)
00278 {
00279 x = (x ^ (x >> 4)) & 0x0F;
00280 return (0x6996 >> x) & 1;
00281 }
00282
00283
00284
00285
00286
00287 static __inline__ int parity16(uint16_t x)
00288 {
00289 x ^= (x >> 8);
00290 x = (x ^ (x >> 4)) & 0x0F;
00291 return (0x6996 >> x) & 1;
00292 }
00293
00294
00295
00296
00297
00298 static __inline__ int parity32(uint32_t x)
00299 {
00300 x ^= (x >> 16);
00301 x ^= (x >> 8);
00302 x = (x ^ (x >> 4)) & 0x0F;
00303 return (0x6996 >> x) & 1;
00304 }
00305
00306
00307 #if defined(__cplusplus)
00308 }
00309 #endif
00310
00311 #endif
00312