1 #ifndef INCLUDE_AL_CONVERSION_HPP
2 #define INCLUDE_AL_CONVERSION_HPP
55 #define UINT32_C(v) v##UL
59 #define UINT64_C(v) v##ULL
62 #define CONST_(N, vf, vd) \
67 operator uint32_t() const { return UINT32_C(vf); } \
71 operator uint64_t() const { return UINT64_C(vd); } \
74 CONST_(MaskExpo, 0x7F800000,
76 CONST_(MaskFrac, 0x007FFFFF,
78 CONST_(MaskSign, 0x80000000,
80 CONST_(Expo1, 0x3F800000,
90 Twiddle(
const float& v) : f(v) {}
91 Twiddle(
const uint32_t& v) : u(v) {}
92 Twiddle(
const int32_t& v) : i(v) {}
102 Twiddle(
const double& v) : f(v) {}
103 Twiddle(
const uint64_t& v) : u(v) {}
104 Twiddle(
const int64_t& v) : i(v) {}
157 float fraction(uint32_t bits, uint32_t phase);
211 template <
typename T>
215 template <
typename T>
220 std::string
toString(
const char* fmt,
const T& v);
228 std::string
toString(
const T* v,
int num,
int stride = 1);
261 static const char* c =
"0123456789abcdefghijklmnopqrstuvwxyz";
262 if (v >= 0 && v <= 35)
return c[v];
268 if (v >=
'0' && v <=
'9')
return v -
'0';
269 if (v >=
'a' && v <=
'z')
return v -
'a' + 10;
275 size_t n = strlen(
string);
276 for (
size_t i = 0; i < n; ++i)
277 if (
string[i] ==
'1') v |= 1 << (n - 1 - i);
290 const uint32_t i =
punFU(v);
291 const uint32_t frac = i & MaskFrac<float>();
292 const uint32_t expo = i & MaskExpo<float>();
293 if (expo == 0 && frac != 0) v = 0.f;
299 const uint64_t i =
punFU(v);
300 const uint64_t frac = i & MaskFrac<double>();
301 const uint64_t expo = i & MaskExpo<double>();
302 if (expo == 0 && frac != 0) v = 0.;
314 uint32_t frac =
punFU(v);
315 frac = (frac & MaskFrac<float>()) | Expo1<float>();
316 return punUF(frac) - 1.f;
319 inline float fraction(uint32_t bits, uint32_t phase) {
320 phase = phase << bits >> 9 | Expo1<float>();
321 return punUF(phase) - 1.f;
325 uint32_t vu = (((uint32_t)v) + 0x808000)
327 return punUF(vu) - 3.f;
331 template <
int NumBytes>
332 void swapBytesN(
void* word);
335 inline void swapBytesN<1>(
void* word) {}
338 inline void swapBytesN<2>(
void* word) {
339 uint16_t& v = *(uint16_t*)word;
340 v = (v >> 8) | (v << 8);
344 inline void swapBytesN<3>(
void* word) {
345 uint8_t* v = (uint8_t*)word;
352 inline void swapBytesN<4>(
void* word) {
353 uint32_t& v = *(uint32_t*)word;
354 v = ((v >> 24)) | ((v >> 8) & 0x0000ff00UL) | ((v << 8) & 0x00ff0000UL) |
359 inline void swapBytesN<8>(
void* word) {
360 uint64_t& v = *(uint64_t*)word;
361 v = ((v >> 56)) | ((v >> 40) & 0x000000000000ff00ULL) |
362 ((v >> 24) & 0x0000000000ff0000ULL) | ((v >> 8) & 0x00000000ff000000ULL) |
363 ((v << 8) & 0x000000ff00000000ULL) | ((v << 24) & 0x0000ff0000000000ULL) |
364 ((v << 40) & 0x00ff000000000000ULL) | ((v << 56));
367 template <
typename T>
369 swapBytesN<sizeof(v)>(&v);
374 for (
unsigned i = 0; i < count; ++i)
swapBytes(data[i]);
378 std::string
toString(
const char* fmt,
const T& v) {
380 snprintf(buf,
sizeof(buf), fmt, v);
381 return std::string(buf);
387 for (
int i = 0; i < n; ++i) {
389 if (i < (n - 1)) r +=
", ";
397 stringstream ss(stringstream::in | stringstream::out);
405 inline float uintToUnit<float>(uint32_t v) {
406 v = v >> 9 | Expo1<float>();
407 return punUF(v) - 1.f;
411 inline float uintToUnitS<float>(uint32_t v) {
412 v = v >> 9 | 0x40000000;
413 return punUF(v) - 3.f;
418 return int16_t((
al::punFU(r) >> 7) + (1 << 15));
423 return punFU(v) << 9;
428 uint32_t normalU =
punFU(v);
429 uint32_t rbs = 126UL - (normalU >> 23UL);
432 return (((normalU | 0x800000UL) << 8UL) & (~ULONG_MAX | 0xffffffffUL)) >> rbs;
449 return (
punFU(u) >> 15) & MaskFrac<float>();
uint32_t floatExponent(float v)
Returns biased decimal value of 32-bit float exponent field.
uint32_t punFU(float v)
Type-pun 32-bit float to 32-bit unsigned int.
int base36To10(char ascii36)
Convert ascii base-36 character to decimal integer.
int16_t unitToInt16(float v)
Convert float in [-1, 1) to 16-bit signed int in [0, 2^16)
uint32_t bitsToUInt(const char *strBin)
Convert a string of 1s and 0s to an integer.
float floatMantissa(float v)
Returns mantissa field as float between [0, 1).
float punUF(uint32_t v)
Type-pun 32-bit unsigned int to 32-bit float.
int endian()
Returns 1 if little endian, 0 if big endian.
T clone(const T &obj)
Returns temporary copy-constructed object.
float blockSubnormal(float v)
Returns zero if argument is subnormal, otherwise returns argument.
float fraction(uint32_t bits, uint32_t phase)
Converts linear integer phase to fraction.
char base10To36(int dec10)
Convert decimal integer to ascii base-36 character.
uint32_t unitToUInt(float u)
Convert float in [0, 1) to 32-bit unsigned int in [0, 2^32)
T uintToUnitS(uint32_t v)
Convert 32-bit unsigned integer to unit float in [-1, 1)
uint32_t unitToUInt2(float u)
Convert float in [0, 1) to 32-bit unsigned int in [0, 2^32)
void swapBytes(T &word)
Swap the bytes of a word in-place.
T uintToUnit(uint32_t v)
Convert 32-bit unsigned integer to unit float in [0, 1)
float intToUnit(int16_t v)
Convert 16-bit signed integer to floating point in [-1, 1)
int32_t punFI(float v)
Type-pun 32-bit float to 32-bit signed int.
uint8_t unitToUInt8(float u)
Convert float in [0, 1) to 8-bit unsigned int in [0, 256)
std::string toString(const char *fmt, const T &v)
Convert argument to a string using snprintf.
double punIF(int64_t v)
Type-pun 64-bit signed int to 64-bit float.
Union for twiddling bits of floats.