aboutsummaryrefslogtreecommitdiffstats
path: root/zahl-internals.h
diff options
context:
space:
mode:
Diffstat (limited to 'zahl-internals.h')
-rw-r--r--zahl-internals.h63
1 files changed, 63 insertions, 0 deletions
diff --git a/zahl-internals.h b/zahl-internals.h
new file mode 100644
index 0000000..4d3389c
--- /dev/null
+++ b/zahl-internals.h
@@ -0,0 +1,63 @@
+/* See LICENSE file for copyright and license details. */
+
+#ifndef ZAHL_INLINE
+# if defined(__STDC_VERSION__) && __STDC_VERSION__ >= 199901L
+# define ZAHL_INLINE static inline
+# else
+# define ZAHL_INLINE static
+# endif
+#endif
+
+
+#if defined(__GNUC__) || defined(__clang__)
+# define ZAHL_LIKELY(expr) __builtin_expect(!!(expr), 1)
+# define ZAHL_UNLIKELY(expr) __builtin_expect(!!(expr), 0)
+# define ZAHL_CONST_P(value) __builtin_constant_p(value)
+#else
+# define ZAHL_LIKELY(expr) (expr)
+# define ZAHL_UNLIKELY(expr) (expr)
+#endif
+
+
+#define ZAHL_BITS_PER_CHAR 64
+#define ZAHL_LB_BITS_PER_CHAR 6
+#define ZAHL_CHAR_MAX UINT64_MAX
+
+
+#define ZAHL_FLOOR_BITS_TO_CHARS(bits) ((bits) >> ZAHL_LB_BITS_PER_CHAR)
+#define ZAHL_CEILING_BITS_TO_CHARS(bits) (((bits) + (ZAHL_BITS_PER_CHAR - 1)) >> ZAHL_LB_BITS_PER_CHAR)
+#define ZAHL_BITS_IN_LAST_CHAR(bits) ((bits) & (ZAHL_BITS_PER_CHAR - 1))
+
+
+#define ZAHL_SET_SIGNUM(a, signum) ((a)->sign = (signum))
+#define ZAHL_SET(a, b) do { if ((a) != (b)) zset(a, b); } while (0)
+#define ZAHL_TRIM(a) for (; (a)->used && !(a)->chars[(a)->used - 1]; (a)->used--)
+#define ZAHL_TRIM_NONZERO(a) for (; !(a)->chars[(a)->used - 1]; (a)->used--)
+#define ZAHL_TRIM_AND_ZERO(a) do { ZAHL_TRIM(a); if (!(a)->used) ZAHL_SET_SIGNUM(a, 0); } while (0)
+#define ZAHL_TRIM_AND_SIGN(a, s) do { ZAHL_TRIM(a); ZAHL_SET_SIGNUM(a, (a)->used ? (s) : 0); } while (0)
+
+
+#if defined(__GNUC__) || defined(__clang__)
+# if ZAHL_CHAR_MAX == LONG_MAX
+# define ZAHL_ADD_CTZ(r, x) ((r) += (size_t)__builtin_ctzl(x))
+# define ZAHL_SUB_CLZ(r, x) ((r) -= (size_t)__builtin_clzl(x))
+# else
+# define ZAHL_ADD_CTZ(r, x) ((r) += (size_t)__builtin_ctzll(x))
+# define ZAHL_SUB_CLZ(r, x) ((r) -= (size_t)__builtin_clzll(x))
+# endif
+#else
+# define ZAHL_ADD_CTZ(r, x) \
+ do { \
+ zahl_char_t zahl_x__ = (x); \
+ for (; zahl_x__ & 1; zahl_x__ >>= 1, (r)++); \
+ } while (0)
+# define ZAHL_SUB_CLZ(r, x) \
+ do { \
+ zahl_char_t zahl_x__ = (x); \
+ (r) -= 8 * sizeof(zahl_char_t); \
+ for (; zahl_x__; zahl_x__ >>= 1, (r)++); \
+ } while (0)
+#endif
+
+
+typedef uint64_t zahl_char_t;