diff options
author | Erik Schnetter <schnetter@gmail.com> | 2013-11-25 14:55:11 -0500 |
---|---|---|
committer | Erik Schnetter <schnetter@gmail.com> | 2013-11-25 14:55:11 -0500 |
commit | 36f7de41c871def89b0245748d29ac2c2dae0609 (patch) | |
tree | 45fcc7cfa448f004494949a8dcfc44435bbcaee3 | |
parent | 942b1fa0654668576d3990c9c3ad721aaf703f7e (diff) | |
download | vecmathlib-36f7de41c871def89b0245748d29ac2c2dae0609.zip vecmathlib-36f7de41c871def89b0245748d29ac2c2dae0609.tar.gz |
Correct clz implementation
-rw-r--r-- | vec_pseudo.h | 32 |
1 files changed, 20 insertions, 12 deletions
diff --git a/vec_pseudo.h b/vec_pseudo.h index 2424d40..a79e072 100644 --- a/vec_pseudo.h +++ b/vec_pseudo.h @@ -366,18 +366,26 @@ namespace vecmathlib { { intvec_t res; #if defined __clang__ || defined __gcc__ - if (sizeof(int_t) == sizeof(long long)) { - for (int d=0; d<size; ++d) res.v[d] = __builtin_clzll(v[d]); - } else if (sizeof(int_t) == sizeof(long)) { - for (int d=0; d<size; ++d) res.v[d] = __builtin_clzl(v[d]); - } else if (sizeof(int_t) == sizeof(int)) { - for (int d=0; d<size; ++d) res.v[d] = __builtin_clz(v[d]); - } else if (sizeof(int_t) <= sizeof(short)) { - for (int d=0; d<size; ++d) - res.v[d] = - CHAR_BIT * (sizeof(short) - sizeof(int_t)) + __builtin_clzs(v[d]); - } else { - __builtin_unreachable(); + for (int d=0; d<size; ++d) { + if (v[d] == 0) { + res.v[d] = CHAR_BIT * sizeof v[d]; + } else { + if (sizeof v[d] == sizeof(long long)) { + res.v[d] = __builtin_clzll(v[d]); + } else if (sizeof v[d] == sizeof(long)) { + res.v[d] = __builtin_clzl(v[d]); + } else if (sizeof v[d] == sizeof(int)) { + res.v[d] = __builtin_clz(v[d]); + } else if (sizeof v[d] == sizeof(short)) { + res.v[d] = __builtin_clzs(v[d]); + } else if (sizeof v[d] == sizeof(char)) { + res.v[d] = + __builtin_clzs((unsigned short)(unsigned char)v[d]) - + CHAR_BIT * (sizeof(short) - sizeof(char)); + } else { + __builtin_unreachable(); + } + } } #else res = MF::vml_clz(*this); |