[libmath-prime-util-perl] 150/181: Add clz and ctz

Partha P. Mukherjee ppm-guest at moszumanska.debian.org
Thu May 21 18:51:16 UTC 2015


This is an automated email from the git hooks/post-receive script.

ppm-guest pushed a commit to annotated tag v0.36
in repository libmath-prime-util-perl.

commit f5cc2197393efe3348f9e396d842ed6fd76a0493
Author: Dana Jacobsen <dana at acm.org>
Date:   Thu Jan 9 14:14:43 2014 -0800

    Add clz and ctz
---
 util.h | 63 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
 1 file changed, 63 insertions(+)

diff --git a/util.h b/util.h
index 59743fe..1c65466 100644
--- a/util.h
+++ b/util.h
@@ -119,5 +119,68 @@ static int is_perfect_square(UV n)
 }
 #endif
 
+/* clz gives floor(log2(n)).  ctz gives number of times divisible by 2 */
+#if defined(FUNC_clz) || defined(FUNC_ctz)
+#ifdef __GNUC__
+ #if BITS_PER_WORD == 64
+  #define ctz(n)  ((n)?__builtin_ctzll(n):64)
+  #define clz(n)  ((n)?__builtin_clzll(n):64)
+ #else
+  #define ctz(n)  ((n)?__builtin_ctzl(n):32)
+  #define clz(n)  ((n)?__builtin_clzl(n):32)
+ #endif
+#elif defined (_MSC_VER)
+ #include <intrin.h>
+ #ifdef FUNC_ctz
+  static int ctz(UV n) {
+    UV tz = 0;
+    if (_BitScanForward(&tz, n)) return tz; else return BITS_PER_WORD;
+  }
+ #endif
+ #ifdef FUNC_clz
+  static int clz(UV n) {
+    UV lz = 0;
+    if (_BitScanReverse(&lz, n)) return BITS_PER_WORD-1-lz; else return BITS_PER_WORD;
+  }
+ #endif
+#elif BITS_PER_WORD == 64
+ static const unsigned char _debruijn64[64] = {
+     63, 0,58, 1,59,47,53, 2, 60,39,48,27,54,33,42, 3, 61,51,37,40,49,18,28,20,
+     55,30,34,11,43,14,22, 4, 62,57,46,52,38,26,32,41, 50,36,17,19,29,10,13,21,
+     56,45,25,31,35,16, 9,12, 44,24,15, 8,23, 7, 6, 5 };
+ #ifdef FUNC_ctz
+   static unsigned int ctz(UV n) {
+     return n ? _debruijn64[((n & -n)*UVCONST(0x07EDD5E59A4E28C2)) >> 58] : 64;
+   }
+ #endif
+ #ifdef FUNC_clz
+   static unsigned int clz(UV n) {
+     if (n == 0) return 64;
+     n |= n >> 1;   n |= n >> 2;   n |= n >> 4;
+     n |= n >> 8;   n |= n >> 16;  n |= n >> 32;
+     return 63 - _debruijn64[((n-(n>>1))*UVCONST(0x07EDD5E59A4E28C2)) >> 58];
+   }
+ #endif
+#else
+ #ifdef FUNC_ctz
+   static const unsigned char _trail_debruijn32[32] = {
+      0, 1,28, 2,29,14,24, 3,30,22,20,15,25,17, 4, 8, 
+     31,27,13,23,21,19,16, 7,26,12,18, 6,11, 5,10, 9 };
+   static unsigned int ctz(UV n) {
+     return n ? _trail_debruijn32[((n & -n) * UVCONST(0x077CB531)) >> 27] : 32;
+   }
+ #endif
+ #ifdef FUNC_clz
+   static const unsigned char _lead_debruijn32[32] = {
+      0, 9, 1, 10, 13, 21, 2, 29, 11, 14, 16, 18, 22, 25, 3, 30,
+      8, 12, 20, 28, 15, 17, 24, 7, 19, 27, 23, 6, 26, 5, 4, 31 };
+   static unsigned int clz(UV n) {
+     if (n == 0) return 32;
+     n |= n >> 1;   n |= n >> 2;   n |= n >> 4;   n |= n >> 8;   n |= n >> 16;
+     return 31 - _lead_debruijn32[(n * UVCONST(0x07C4ACDD)) >> 27];
+   }
+ #endif
+#endif
+#endif  /* End of clz and ctz */
 
 #endif

-- 
Alioth's /usr/local/bin/git-commit-notice on /srv/git.debian.org/git/pkg-perl/packages/libmath-prime-util-perl.git



More information about the Pkg-perl-cvs-commits mailing list