(wrong string) ée

From: <git_AT_suckless.org>
Date: Fri, 4 Mar 2016 23:50:22 +0100 (CET)

commit aff09967d194d062ae8d83c0fbe1edf158804ef9
Author: Mattias Andrée <maandree_AT_kth.se>
AuthorDate: Fri Mar 4 10:45:10 2016 +0100
Commit: Mattias Andrée <maandree_AT_kth.se>
CommitDate: Fri Mar 4 10:47:53 2016 +0100

    Clean up, fix a few bugs, and add a test
    
    Signed-off-by: Mattias Andrée <maandree_AT_kth.se>

diff --git a/.gitignore b/.gitignore
index aef436d..9260786 100644
--- a/.gitignore
+++ b/.gitignore
_AT_@ -3,3 +3,4 @@
 *.su
 *.a
 *.so
+/test
diff --git a/Makefile b/Makefile
index 0670292..f3a6ad7 100644
--- a/Makefile
+++ b/Makefile
_AT_@ -56,7 +56,7 @@ FUN =\
 OBJ = $(FUN:=.o)
 MAN = $(foreach F,$(FUN),man/$(F).3) man/libzahl.7
 
-all: libzahl.a
+all: libzahl.a test
 
 %.o: src/%.c $(HDR) config.mk
         $(CC) $(CFLAGS) $(CPPFLAGS) -c -o $_AT_ $<
_AT_@ -65,7 +65,10 @@ libzahl.a: $(OBJ)
         $(AR) rc $_AT_ $?
         $(RANLIB) $_AT_
 
+test: test.c libzahl.a
+ $(CC) $(LDFLAGS) $(CFLAGS) $(CPPFLAGS) -o $_AT_ $^
+
 clean:
- -rm -- *.o *.su *.a *.so 2>/dev/null
+ -rm -- *.o *.su *.a *.so test 2>/dev/null
 
 .PHONY: all clean
diff --git a/src/internals.h b/src/internals.h
index 77ea29b..5b1f9c3 100644
--- a/src/internals.h
+++ b/src/internals.h
_AT_@ -62,7 +62,8 @@ extern int libzahl_set_up;
 #define zmemcmp(a, b, n) memcmp(a, b, (n) * sizeof(zahl_char_t))
 
 #define SET_SIGNUM(a, signum) ((a)->sign = (signum))
-#define SET(a, b) do { if (a != b) zset(a, b); } while (0)
+#define SET(a, b) do { if ((a) != (b)) zset(a, b); } while (0)
+#define ENSURE_SIZE(a, n) do { if ((a)->alloced < (n)) zahl_realloc(a, (n)); } while (0)
 
 #define MIN(a, b) ((a) < (b) ? (a) : (b))
 #define MAX(a, b) ((a) > (b) ? (a) : (b))
diff --git a/src/zadd.c b/src/zadd.c
index 2aa7e38..6ab3ae8 100644
--- a/src/zadd.c
+++ b/src/zadd.c
_AT_@ -15,8 +15,7 @@ zadd_unsigned(z_t a, z_t b, z_t c)
         }
 
         size = MAX(b->used, c->used);
- if (a->alloced < size + 1)
- zahl_realloc(a, size + 1);
+ ENSURE_SIZE(a, size + 1);
         a->chars[size] = 0;
 
         n = b->used + c->used - size;
diff --git a/src/zand.c b/src/zand.c
index 6b8dc4a..e07705a 100644
--- a/src/zand.c
+++ b/src/zand.c
_AT_@ -28,8 +28,7 @@ found_highest:
                 while (n--)
                         a->chars[n] &= b->chars[n];
         } else {
- if (a->alloced < a->used)
- zahl_realloc(a, a->used);
+ ENSURE_SIZE(a, a->used);
                 zmemcpy(a->chars, c->chars, a->used);
                 while (n--)
                         a->chars[n] &= b->chars[n];
diff --git a/src/zbset.c b/src/zbset.c
index d7b7784..c379e2a 100644
--- a/src/zbset.c
+++ b/src/zbset.c
_AT_@ -5,12 +5,12 @@
 void
 zbset(z_t a, z_t b, size_t bit, int action)
 {
- zahl_char_t x = 1;
+ zahl_char_t mask = 1;
         size_t chars;
 
         chars = FLOOR_BITS_TO_CHARS(bit);
         bit = BITS_IN_LAST_CHAR(bit);
- x <<= bit;
+ mask <<= bit;
 
         SET(a, b);
 
_AT_@ -20,19 +20,19 @@ zbset(z_t a, z_t b, size_t bit, int action)
                         SET_SIGNUM(a, 1);
                 }
                 if (a->used <= chars) {
- if (a->alloced <= chars)
- zahl_realloc(a, chars + 1);
- zmemset(a->chars + a->used, 0, chars - a->used + 1);
+ ENSURE_SIZE(a, chars + 1);
+ zmemset(a->chars + a->used, 0, chars + 1 - a->used);
+ a->used = chars + 1;
                 }
         }
 
         if (action > 0) {
- a->chars[chars] |= x;
+ a->chars[chars] |= mask;
                 return;
         } else if (action < 0) {
- a->chars[chars] ^= x;
- } else if (a->used > chars) {
- a->chars[chars] &= ~x;
+ a->chars[chars] ^= mask;
+ } else if (chars < a->used) {
+ a->chars[chars] &= ~mask;
         }
 
         while (a->used && !a->chars[a->used - 1])
diff --git a/src/zload.c b/src/zload.c
index c708453..ff54afb 100644
--- a/src/zload.c
+++ b/src/zload.c
_AT_@ -6,11 +6,12 @@ size_t
 zload(z_t a, const void *buffer)
 {
         const char *buf = buffer;
- a->sign = *((const int *)buf), buf += sizeof(int);
- a->used = *((const size_t *)buf), buf += sizeof(size_t);
- a->alloced = *((const size_t *)buf), buf += sizeof(size_t);
- if (a->alloced)
- zahl_realloc(a, a->alloced);
+ size_t alloced;
+ a->sign = *((const int *)buf), buf += sizeof(int);
+ a->used = *((const size_t *)buf), buf += sizeof(size_t);
+ alloced = *((const size_t *)buf), buf += sizeof(size_t);
+ if (alloced)
+ ENSURE_SIZE(a, alloced);
         else
                 a->chars = 0;
         if (!zzero(a))
diff --git a/src/zlsh.c b/src/zlsh.c
index e301d44..b631c1a 100644
--- a/src/zlsh.c
+++ b/src/zlsh.c
_AT_@ -22,8 +22,7 @@ zlsh(z_t a, z_t b, size_t bits)
         cbits = BITS_PER_CHAR - 1 - bits;
 
         a->used = b->used + chars;
- if (a->alloced < a->used)
- zahl_realloc(a, a->used);
+ ENSURE_SIZE(a, a->used);
         if (a == b)
                 zmemmove(a->chars + chars, b->chars, a->used);
         else
_AT_@ -36,8 +35,7 @@ zlsh(z_t a, z_t b, size_t bits)
                 a->chars[i] |= carry[i & 1];
         }
         if (carry[i & 1]) {
- if (a->alloced == a->used)
- zahl_realloc(a, a->alloced << 1);
+ ENSURE_SIZE(a, a->alloced << 1);
                 a->chars[i] = carry[i & 1];
                 a->used++;
         }
diff --git a/src/zmodpow.c b/src/zmodpow.c
index fe18060..884e9ff 100644
--- a/src/zmodpow.c
+++ b/src/zmodpow.c
_AT_@ -42,7 +42,7 @@ zmodpow(z_t a, z_t b, z_t c, z_t d)
         zset(td, d);
         zsetu(a, 1);
 
- for (i = 0; i < n; i++) {
+ for (i = 0; i < n; i++) { /* Remember, n is floored. */
                 x = tc->chars[i];
                 for (j = BITS_PER_CHAR; j--; x >>= 1) {
                         if (x & 1)
_AT_@ -50,4 +50,10 @@ zmodpow(z_t a, z_t b, z_t c, z_t d)
                         zmodsqr(tb, tb, td);
                 }
         }
+ x = tc->chars[i];
+ for (; x; x >>= 1) {
+ if (x & 1)
+ zmodmul(a, a, tb, td);
+ zmodsqr(tb, tb, td);
+ }
 }
diff --git a/src/zmul.c b/src/zmul.c
index 578d8a5..f237bc9 100644
--- a/src/zmul.c
+++ b/src/zmul.c
_AT_@ -24,7 +24,7 @@ zmul(z_t a, z_t b, z_t c)
         b_sign = zsignum(b);
         c_sign = zsignum(c);
 
- if (m <= 16 && m2 <= 16) {
+ if (m <= BITS_PER_CHAR / 2 && m2 <= BITS_PER_CHAR / 2) {
                 zsetu(a, b->chars[0] * c->chars[0]);
                 SET_SIGNUM(a, b_sign * c_sign);
                 return;
diff --git a/src/zor.c b/src/zor.c
index 1d3952d..f594828 100644
--- a/src/zor.c
+++ b/src/zor.c
_AT_@ -21,8 +21,7 @@ zor(z_t a, z_t b, z_t c)
         m = MAX(b->used, c->used);
         n = b->used + c->used - m;
 
- if (a->alloced < m)
- zahl_realloc(a, m);
+ ENSURE_SIZE(a, m);
 
         if (a == b) {
                 zmemcpy(a->chars + n, m == b->used ? b->chars : c->chars, m - n);
diff --git a/src/zpow.c b/src/zpow.c
index 16988f7..c064f60 100644
--- a/src/zpow.c
+++ b/src/zpow.c
_AT_@ -37,7 +37,7 @@ zpow(z_t a, z_t b, z_t c)
         zset(tc, c);
         zsetu(a, 1);
 
- for (i = 0; i < n; i++) {
+ for (i = 0; i < n; i++) { /* Remember, n is floored. */
                 x = tc->chars[i];
                 for (j = BITS_PER_CHAR; j--; x >>= 1) {
                         if (x & 1)
_AT_@ -45,4 +45,10 @@ zpow(z_t a, z_t b, z_t c)
                         zsqr(tb, tb);
                 }
         }
+ x = tc->chars[i];
+ for (; x; x >>= 1) {
+ if (x & 1)
+ zmul(a, a, tb);
+ zsqr(tb, tb);
+ }
 }
diff --git a/src/zrand.c b/src/zrand.c
index c5c8e8a..cb0b375 100644
--- a/src/zrand.c
+++ b/src/zrand.c
_AT_@ -16,15 +16,16 @@
 static void
 zrand_get_random_bits(z_t r, size_t bits, int fd)
 {
- size_t read_total, n, chars = CEILING_BITS_TO_CHARS(bits);
+ size_t read_total = 0, n, chars = CEILING_BITS_TO_CHARS(bits);
         ssize_t read_just;
- uint32_t mask = 1;
+ zahl_char_t mask = 1;
+ char *buf;
 
- if (r->alloced < chars)
- zahl_realloc(r, chars);
+ ENSURE_SIZE(r, chars);
+ buf = (char *)(r->chars);
 
- for (n = chars << LB_BITS_PER_CHAR; n;) {
- read_just = read(fd, (char *)(r->chars) + read_total, n);
+ for (n = chars * sizeof(zahl_char_t); n;) {
+ read_just = read(fd, buf + read_total, n);
                 if (read_just < 0)
                         FAILURE_JUMP();
                 read_total += (size_t)read_just;
_AT_@ -75,6 +76,10 @@ zrand(z_t r, enum zranddev dev, enum zranddist dist, z_t n)
 
         switch (dist) {
         case QUASIUNIFORM:
+ if (zsignum(n) < 0) {
+ errno = EDOM; /* n must be non-negative. */
+ FAILURE_JUMP();
+ }
                 bits = zbits(n);
                 zrand_get_random_bits(r, bits, fd);
                 zadd(r, r, libzahl_const_1);
_AT_@ -83,10 +88,14 @@ zrand(z_t r, enum zranddev dev, enum zranddist dist, z_t n)
                 break;
 
         case UNIFORM:
+ if (zsignum(n) < 0) {
+ errno = EDOM; /* n must be non-negative. */
+ FAILURE_JUMP();
+ }
                 bits = zbits(n);
                 do
                         zrand_get_random_bits(r, bits, fd);
- while (zcmp(r, n) > 0);
+ while (zcmpmag(r, n) > 0);
                 break;
 
         default:
diff --git a/src/zrsh.c b/src/zrsh.c
index c3bd63e..c5a1a05 100644
--- a/src/zrsh.c
+++ b/src/zrsh.c
_AT_@ -27,8 +27,7 @@ zrsh(z_t a, z_t b, size_t bits)
                 zmemmove(a->chars, a->chars + chars, a->used);
         } else if (a != b) {
                 a->used = b->used - chars;
- if (a->alloced < a->used)
- zahl_realloc(a, a->used);
+ ENSURE_SIZE(a, a->used);
                 zmemcpy(a->chars, b->chars + chars, a->used);
         }
 
diff --git a/src/zset.c b/src/zset.c
index 989bb1c..b67fe4a 100644
--- a/src/zset.c
+++ b/src/zset.c
_AT_@ -8,8 +8,7 @@ zset(z_t a, z_t b)
         if (zzero(b)) {
                 SET_SIGNUM(a, 0);
         } else {
- if (a->alloced < b->alloced)
- zahl_realloc(a, b->alloced);
+ ENSURE_SIZE(a, b->alloced);
                 a->sign = b->sign;
                 a->used = b->used;
                 zmemcpy(a->chars, b->chars, b->used);
diff --git a/src/zsetu.c b/src/zsetu.c
index f37be7e..37fbf7c 100644
--- a/src/zsetu.c
+++ b/src/zsetu.c
_AT_@ -11,8 +11,7 @@ zsetu(z_t a, unsigned long long int b)
                 SET_SIGNUM(a, 0);
                 return;
         }
- if (a->alloced < SIZE_MULTIPLE(b, *(a->chars)))
- zahl_realloc(a, SIZE_MULTIPLE(b, *(a->chars)));
+ ENSURE_SIZE(a, SIZE_MULTIPLE(b, *(a->chars)));
         SET_SIGNUM(a, 1);
         a->used = 0;
         while (b) {
diff --git a/src/zsqr.c b/src/zsqr.c
index be89c37..a9cebd0 100644
--- a/src/zsqr.c
+++ b/src/zsqr.c
_AT_@ -20,7 +20,7 @@ zsqr(z_t a, z_t b)
 
         m2 = zbits(b);
 
- if (m2 <= 16) {
+ if (m2 <= BITS_PER_CHAR / 2) {
                 zsetu(a, b->chars[0] * b->chars[0]);
                 SET_SIGNUM(a, 1);
                 return;
diff --git a/src/ztrunc.c b/src/ztrunc.c
index ffbbbe0..f86fb8e 100644
--- a/src/ztrunc.c
+++ b/src/ztrunc.c
_AT_@ -18,9 +18,10 @@ ztrunc(z_t a, z_t b, size_t bits)
         a->used = MIN(chars, b->used);
         if (a->used < chars)
                 bits = 0;
- if (a->alloced < b->alloced)
- zahl_realloc(a, b->alloced);
- zmemcpy(a->chars, b->chars, a->used);
+ if (a != b) {
+ ENSURE_SIZE(a, b->alloced);
+ zmemcpy(a->chars, b->chars, a->used);
+ }
         bits = BITS_IN_LAST_CHAR(bits);
         if (bits) {
                 mask <<= bits;
diff --git a/src/zxor.c b/src/zxor.c
index f570fdf..fcbb3ae 100644
--- a/src/zxor.c
+++ b/src/zxor.c
_AT_@ -26,8 +26,7 @@ zxor(z_t a, z_t b, z_t c)
                 return;
         }
 
- if (a->alloced < m)
- zahl_realloc(a, m);
+ ENSURE_SIZE(a, m);
 
         if (a == b) {
                 zmemcpy(a->chars + n, m == b->used ? b->chars : c->chars, m - n);
diff --git a/test.c b/test.c
new file mode 100644
index 0000000..d82c7bc
--- /dev/null
+++ b/test.c
_AT_@ -0,0 +1,724 @@
+/* See LICENSE file for copyright and license details. */
+#include "zahl.h"
+
+#include <stdio.h>
+#include <string.h>
+
+#define assert(expr, expected)\
+ do {\
+ int got = (expr);\
+ if (!(got expected)) {\
+ fprintf(stderr,\
+ "Failure at line %i: %s, expected %s, but got %i.\n",\
+ __LINE__, #expr, #expected, got);\
+ return 1;\
+ }\
+ } while (0)
+
+#define assert_zu(expr, expected)\
+ do {\
+ size_t got = (expr);\
+ if (got != (expected)) {\
+ fprintf(stderr,\
+ "Failure at line %i: %s, expected %zu, but got %zu.\n",\
+ __LINE__, #expr, (size_t)(expected), got);\
+ return 1;\
+ }\
+ } while (0)
+
+#define assert_s(expr, expected)\
+ do {\
+ const char *got = (expr);\
+ if (strcmp(got, expected)) {\
+ fprintf(stderr,\
+ "Failure at line %i: %s, expected %s, but got %s.\n",\
+ __LINE__, #expr, expected, got);\
+ return 1;\
+ }\
+ } while (0)
+
+int
+main(void)
+{
+ /* static because otherwise it would have to be volatile yeilding a lot of stupid
+ * warnings. auto variables are not guaranteed to be readable after a long jump. */
+ static z_t a, b, c, d, _0, _1, _2, _3;
+
+ jmp_buf env;
+ char buf[1000];
+ int ret = 0;
+ size_t n;
+
+ if (setjmp(env)) {
+ ret = 1;
+ goto done;
+ }
+
+ zsetup(env);
+ zinit(a), zinit(b), zinit(c), zinit(d), zinit(_0), zinit(_1), zinit(_2), zinit(_3);
+
+ zsetu(_0, 0);
+ zsetu(_1, 1);
+ zsetu(_2, 2);
+ zsetu(_3, 3);
+
+ assert(zeven(_0), == 1);
+ assert(zodd(_0), == 0);
+ assert(zzero(_0), == 1);
+ assert(zsignum(_0), == 0);
+ assert(zeven(_1), == 0);
+ assert(zodd(_1), == 1);
+ assert(zzero(_1), == 0);
+ assert(zsignum(_1), == 1);
+ assert(zeven(_2), == 1);
+ assert(zodd(_2), == 0);
+ assert(zzero(_2), == 0);
+ assert(zsignum(_2), == 1);
+
+ zswap(_1, _2);
+ assert(zeven(_2), == 0);
+ assert(zodd(_2), == 1);
+ assert(zzero(_2), == 0);
+ assert(zsignum(_2), == 1);
+ assert(zeven(_1), == 1);
+ assert(zodd(_1), == 0);
+ assert(zzero(_1), == 0);
+ assert(zsignum(_1), == 1);
+ zswap(_2, _1);
+ assert(zeven(_1), == 0);
+ assert(zodd(_1), == 1);
+ assert(zzero(_1), == 0);
+ assert(zsignum(_1), == 1);
+ assert(zeven(_2), == 1);
+ assert(zodd(_2), == 0);
+ assert(zzero(_2), == 0);
+ assert(zsignum(_2), == 1);
+
+ assert((zneg(_2, _2), zsignum(_2)), == -1); zneg(_2, _2);
+ assert(zsignum(_2), == 1);
+
+ assert(zcmp(_0, _0), == 0);
+ assert(zcmp(_1, _1), == 0);
+ assert(zcmp(_0, _1), < 0);
+ assert(zcmp(_1, _0), > 0);
+ assert(zcmp(_1, _2), < 0);
+ assert(zcmp(_2, _1), > 0);
+ assert(zcmp(_0, _2), < 0);
+ assert(zcmp(_2, _0), > 0);
+
+ zbset(a, _0, 0, 1);
+ assert(zcmp(a, _1), == 0);
+ zbset(a, a, 1, 1);
+ assert(zcmp(a, _3), == 0);
+ zbset(a, a, 0, 0);
+ assert(zcmp(a, _2), == 0);
+ zbset(a, a, 0, 0);
+ assert(zcmp(a, _2), == 0);
+ zbset(a, a, 0, -1);
+ assert(zcmp(a, _3), == 0);
+ zbset(a, a, 0, -1);
+ assert(zcmp(a, _2), == 0);
+
+ zadd(a, _0, _1);
+ assert(zsignum(a), == 1);
+ assert(zcmp(a, _1), == 0);
+ assert(zcmpi(a, 1), == 0);
+ assert(zcmpu(a, 1), == 0);
+ zneg(a, a);
+ assert(zsignum(a), == -1);
+ assert(zcmp(a, _1), < 0);
+ assert(zcmpi(a, 1), < 0);
+ assert(zcmpu(a, 1), < 0);
+ zadd(a, _2, _0);
+ assert(zsignum(a), == 1);
+ assert(zcmp(a, _2), == 0);
+ assert(zcmpi(a, 2), == 0);
+ assert(zcmpu(a, 2), == 0);
+ zneg(a, a);
+ assert(zsignum(a), == -1);
+ assert(zcmp(a, _2), < 0);
+ assert(zcmpi(a, 2), < 0);
+ assert(zcmpu(a, 2), < 0);
+ assert(zsignum(_1), == 1);
+ zadd(a, _1, _1);
+ assert(zsignum(a), == 1);
+ assert(zcmp(a, _2), == 0);
+ assert(zcmpi(a, 2), == 0);
+ assert(zcmpu(a, 2), == 0);
+ zset(b, _1);
+ zadd(a, b, _1);
+ assert(zsignum(a), == 1);
+ assert(zcmp(a, _2), == 0);
+ assert(zcmpi(a, 2), == 0);
+ assert(zcmpu(a, 2), == 0);
+ zneg(a, a);
+ zset(b, _2);
+ zneg(b, b);
+ assert(zsignum(a), == -1);
+ assert(zcmp(a, b), == 0);
+ assert(zcmp(a, _2), < 0);
+ assert(zcmpmag(a, b), == 0);
+ assert(zcmpmag(a, _2), == 0);
+ assert(zcmpi(a, 2), < 0);
+ assert(zcmpu(a, 2), < 0);
+ assert(zcmpi(a, -2), == 0);
+ assert((zneg(_2, _2), zcmp(a, _2)), == 0); zneg(_2, _2);
+ zadd(a, _1, _2);
+ assert(zsignum(a), == 1);
+ assert(zcmp(a, _2), > 0);
+ assert(zcmpi(a, 2), > 0);
+ assert(zcmpu(a, 2), > 0);
+ zneg(a, a);
+ zset(b, _2);
+ zneg(b, b);
+ assert(zsignum(a), == -1);
+ assert(zcmpmag(a, _2), > 0);
+ assert(zcmpmag(a, b), > 0);
+ assert(zcmp(a, b), < 0);
+ assert(zcmp(a, _2), < 0);
+ assert(zcmpi(a, 2), < 0);
+ assert(zcmpu(a, 2), < 0);
+ assert(zcmpi(a, -2), < 0);
+ assert((zneg(_2, _2), zcmp(a, _2)), < 0); zneg(_2, _2);
+ zneg(b, _3);
+ assert(zcmp(a, b), == 0);
+
+ zsub(a, _2, _1);
+ assert(zcmpmag(_2, _1), > 0);
+ assert(zcmpmag(_2, _0), > 0);
+ assert(zcmpmag(_1, _0), > 0);
+ zsub(b, _1, _2);
+ assert(zcmpmag(_2, _0), > 0);
+ assert(zcmpmag(_1, _0), > 0);
+ assert(zcmpmag(_2, _1), > 0);
+ assert(zcmpmag(a, b), == 0);
+ assert(zcmpmag(a, _1), == 0);
+ assert(zcmp(a, b), > 0);
+ assert(zcmp(a, _1), == 0);
+ assert(zcmp(b, _1), < 0);
+ zsub(a, _1, _1);
+ assert(zcmp(a, _0), == 0);
+ zseti(b, 0);
+ zsetu(c, 0);
+ zsub(a, b, c);
+ assert(zcmp(a, _0), == 0);
+ assert(zcmpmag(_2, _1), > 0);
+ assert(zcmp(_2, _1), > 0);
+ zsub(a, _2, _1);
+ assert(zsignum(a), == 1);
+ assert(zcmpmag(a, _1), == 0);
+ assert(zcmp(a, _1), == 0);
+ zsub(a, a, _1);
+ assert(zcmp(a, _0), == 0);
+ zsub(a, a, _0);
+ assert(zcmp(a, _0), == 0);
+ zsub(a, _1, _2);
+ assert(zcmp(a, _1), < 0);
+ assert(zcmpmag(a, _1), == 0);
+ zabs(a, a);
+ assert(zcmp(a, _1), == 0);
+ zabs(a, a);
+ assert(zcmp(a, _1), == 0);
+ zabs(a, _1);
+ assert(zcmp(a, _1), == 0);
+ zabs(a, _0);
+ assert(zcmp(a, _0), == 0);
+
+ zseti(b, -1);
+ zseti(c, -2);
+ zadd(a, _0, b);
+ assert(zcmp(a, _0), < 0);
+ assert(zcmpi(a, -1), == 0);
+ assert(zcmpmag(a, _1), == 0);
+ assert(zcmp(a, _1), < 0);
+ zadd(a, b, _0);
+ assert(zcmp(a, _0), < 0);
+ assert(zcmpi(a, -1), == 0);
+ assert(zcmpmag(a, _1), == 0);
+ assert(zcmp(a, _1), < 0);
+ zadd(a, b, c);
+ assert(zcmp(a, c), < 0);
+ assert(zcmpmag(a, _2), > 0);
+ zadd(a, c, b);
+ assert(zcmp(a, c), < 0);
+ assert(zcmpmag(a, _2), > 0);
+ zadd(a, b, _1);
+ assert(zcmp(a, _0), == 0);
+ assert(zcmpmag(a, _0), == 0);
+ zadd(a, _1, b);
+ assert(zcmp(a, _0), == 0);
+ assert(zcmpmag(a, _0), == 0);
+
+ zneg(b, _1);
+ zneg(c, _2);
+ zsub(a, _0, b);
+ assert(zcmp(a, _1), == 0);
+ zsub(a, b, _0);
+ assert(zcmpmag(a, _1), == 0);
+ assert(zcmp(a, _1), < 0);
+ zsub(a, b, c);
+ assert(zcmpmag(a, _1), == 0);
+ assert(zcmp(a, _1), == 0);
+ zsub(a, c, b);
+ assert(zcmpmag(a, _1), == 0);
+ assert(zcmp(a, _1), < 0);
+ zsub(a, b, _1);
+ assert(zcmpmag(a, _2), == 0);
+ assert(zcmp(a, _2), < 0);
+ assert(zcmp(a, c), == 0);
+ zsub(a, _1, b);
+ assert(zcmp(b, _1), < 0);
+ assert(zcmpmag(b, _1), == 0);
+ assert(zcmp(a, _2), == 0);
+
+ zsetu(a, 1000);
+ zsetu(b, 0);
+ assert(zcmp(a, b), != 0);
+ n = zsave(a, buf);
+ assert(n, > 0);
+ assert_zu(zload(b, buf), n);
+ assert(zcmp(a, b), == 0);
+
+ zneg(b, _1);
+ zneg(c, _2);
+
+ assert((zadd_unsigned(a, b, c), zcmp(a, _3)), == 0);
+ assert((zadd_unsigned(a, b, c), zcmp(a, _3)), == 0);
+ assert((zadd_unsigned(a, b, _2), zcmp(a, _3)), == 0);
+ assert((zadd_unsigned(a, _1, c), zcmp(a, _3)), == 0);
+
+ assert((zsub_unsigned(a, _2, _1), zcmp(a, _1)), == 0);
+ assert((zsub_unsigned(a, _2, b), zcmp(a, _1)), == 0);
+ assert((zsub_unsigned(a, c, _1), zcmp(a, _1)), == 0);
+ assert((zsub_unsigned(a, c, b), zcmp(a, _1)), == 0);
+
+ assert((zsub_unsigned(a, _1, _2), zcmp(a, b)), == 0);
+ assert((zsub_unsigned(a, b, _2), zcmp(a, b)), == 0);
+ assert((zsub_unsigned(a, _1, c), zcmp(a, b)), == 0);
+ assert((zsub_unsigned(a, b, c), zcmp(a, b)), == 0);
+
+ assert_zu(zbits(_0), 1);
+ assert_zu(zbits(_1), 1);
+ assert_zu(zbits(_2), 2);
+ assert_zu(zbits(_3), 2);
+
+ assert_zu(zlsb(_0), SIZE_MAX);
+ assert_zu(zlsb(_1), 0);
+ assert_zu(zlsb(_2), 1);
+ assert_zu(zlsb(_3), 0);
+
+ assert((zand(a, _0, _0), zcmp(a, _0)), == 0);
+ assert(zzero(a), == 1);
+ assert((zand(a, _0, _1), zcmp(a, _0)), == 0);
+ assert(zzero(a), == 1);
+ assert((zand(a, _0, _2), zcmp(a, _0)), == 0);
+ assert(zzero(a), == 1);
+ assert((zand(a, _0, _3), zcmp(a, _0)), == 0);
+ assert(zzero(a), == 1);
+ assert((zand(a, _1, _1), zcmp(a, _1)), == 0);
+ assert((zand(a, _1, _2), zcmp(a, _0)), == 0);
+ assert(zzero(a), == 1);
+ assert((zand(a, _1, _3), zcmp(a, _1)), == 0);
+ assert((zand(a, _2, _2), zcmp(a, _2)), == 0);
+ assert((zand(a, _2, _3), zcmp(a, _2)), == 0);
+ assert((zand(a, _3, _3), zcmp(a, _3)), == 0);
+
+ assert((zor(a, _0, _0), zcmp(a, _0)), == 0);
+ assert(zzero(a), == 1);
+ assert((zor(a, _0, _1), zcmp(a, _1)), == 0);
+ assert((zor(a, _0, _2), zcmp(a, _2)), == 0);
+ assert((zor(a, _0, _3), zcmp(a, _3)), == 0);
+ assert((zor(a, _1, _1), zcmp(a, _1)), == 0);
+ assert((zor(a, _1, _2), zcmp(a, _3)), == 0);
+ assert((zor(a, _1, _3), zcmp(a, _3)), == 0);
+ assert((zor(a, _2, _2), zcmp(a, _2)), == 0);
+ assert((zor(a, _2, _3), zcmp(a, _3)), == 0);
+ assert((zor(a, _3, _3), zcmp(a, _3)), == 0);
+
+ assert((zxor(a, _0, _0), zcmp(a, _0)), == 0);
+ assert(zzero(a), == 1);
+ assert((zxor(a, _0, _1), zcmp(a, _1)), == 0);
+ assert((zxor(a, _0, _2), zcmp(a, _2)), == 0);
+ assert((zxor(a, _0, _3), zcmp(a, _3)), == 0);
+ assert((zxor(a, _1, _1), zcmp(a, _0)), == 0);
+ assert(zzero(a), == 1);
+ assert((zxor(a, _1, _2), zcmp(a, _3)), == 0);
+ assert((zxor(a, _1, _3), zcmp(a, _2)), == 0);
+ assert((zxor(a, _2, _2), zcmp(a, _0)), == 0);
+ assert(zzero(a), == 1);
+ assert((zxor(a, _2, _3), zcmp(a, _1)), == 0);
+ assert((zxor(a, _3, _3), zcmp(a, _0)), == 0);
+ assert(zzero(a), == 1);
+
+ zneg(b, _1);
+ zneg(c, _3);
+ zneg(_1, _1);
+ zand(a, b, c);
+ assert(zcmpmag(a, _1), == 0);
+ assert(zcmp(a, _1), == 0);
+ zneg(_1, _1);
+ assert((zand(a, b, _3), zcmp(a, _1)), == 0);
+ assert((zand(a, _1, c), zcmp(a, _1)), == 0);
+ assert((zand(a, _0, c), zcmp(a, _0)), == 0);
+ assert((zand(a, b, _0), zcmp(a, _0)), == 0);
+
+ zneg(b, _1);
+ zneg(c, _2);
+ zneg(_3, _3);
+ zor(a, b, c);
+ assert(zcmpmag(a, _3), == 0);
+ assert(zcmp(a, _3), == 0);
+ zor(a, b, _2);
+ assert(zcmpmag(a, _3), == 0);
+ assert(zcmp(a, _3), == 0);
+ zor(a, _1, c);
+ assert((zcmpmag(a, _3)), == 0);
+ assert((zcmp(a, _3)), == 0);
+ assert((zor(a, _0, c), zcmp(a, c)), == 0);
+ assert((zor(a, b, _0), zcmp(a, b)), == 0);
+ zneg(_3, _3);
+
+ zneg(b, _1);
+ zneg(c, _2);
+ zxor(a, b, c);
+ assert(zcmpmag(a, _3), == 0);
+ assert(zcmp(a, _3), == 0);
+ zneg(_3, _3);
+ zxor(a, b, _2);
+ assert(zcmpmag(a, _3), == 0);
+ assert(zcmp(a, _3), == 0);
+ zxor(a, _1, c);
+ assert(zcmpmag(a, _3), == 0);
+ assert(zcmp(a, _3), == 0);
+ zxor(a, b, _0);
+ assert(zcmpmag(a, b), == 0);
+ assert(zcmp(a, b), == 0);
+ zxor(a, _0, c);
+ assert(zcmpmag(a, c), == 0);
+ assert(zcmp(a, c), == 0);
+ zneg(_3, _3);
+
+ assert((zlsh(a, _0, 0), zcmp(a, _0)), == 0);
+ assert(zzero(a), == 1);
+ assert((zlsh(a, _0, 1), zcmp(a, _0)), == 0);
+ assert(zzero(a), == 1);
+ assert((zlsh(a, _1, 0), zcmp(a, _1)), == 0);
+ assert((zlsh(a, _1, 1), zcmp(a, _2)), == 0);
+ assert((zlsh(a, _1, 2), zcmp(a, _2)), > 0);
+ assert((zlsh(a, _2, 0), zcmp(a, _2)), == 0);
+ assert((zlsh(a, _2, 1), zcmp(a, _2)), > 0);
+
+ zset(a, _0);
+ assert((zlsh(a, a, 0), zcmp(a, _0)), == 0);
+ assert(zzero(a), == 1);
+ assert((zlsh(a, a, 1), zcmp(a, _0)), == 0);
+ assert(zzero(a), == 1);
+ zset(a, _1);
+ assert((zlsh(a, a, 0), zcmp(a, _1)), == 0);
+ assert((zlsh(a, a, 1), zcmp(a, _2)), == 0);
+ assert((zlsh(a, a, 2), zcmp(a, _2)), > 0);
+ zset(a, _2);
+ assert((zlsh(a, a, 0), zcmp(a, _2)), == 0);
+ assert((zlsh(a, a, 1), zcmp(a, _2)), > 0);
+
+ assert((zrsh(a, _0, 0), zcmp(a, _0)), == 0);
+ assert(zzero(a), == 1);
+ assert((zrsh(a, _0, 1), zcmp(a, _0)), == 0);
+ assert(zzero(a), == 1);
+ assert((zrsh(a, _1, 0), zcmp(a, _1)), == 0);
+ assert((zrsh(a, _1, 1), zcmp(a, _0)), == 0);
+ assert(zzero(a), == 1);
+ assert((zrsh(a, _1, 2), zcmp(a, _0)), == 0);
+ assert(zzero(a), == 1);
+ assert((zrsh(a, _2, 0), zcmp(a, _2)), == 0);
+ assert((zrsh(a, _2, 1), zcmp(a, _1)), == 0);
+ assert((zrsh(a, _2, 2), zcmp(a, _0)), == 0);
+ assert(zzero(a), == 1);
+
+ zset(a, _0);
+ assert((zrsh(a, a, 0), zcmp(a, _0)), == 0);
+ assert(zzero(a), == 1);
+ assert((zrsh(a, a, 1), zcmp(a, _0)), == 0);
+ assert(zzero(a), == 1);
+ zset(a, _1);
+ assert((zrsh(a, a, 0), zcmp(a, _1)), == 0);
+ assert((zrsh(a, a, 1), zcmp(a, _0)), == 0);
+ assert(zzero(a), == 1);
+ assert((zrsh(a, a, 2), zcmp(a, _0)), == 0);
+ assert(zzero(a), == 1);
+ zset(a, _2);
+ assert((zrsh(a, a, 0), zcmp(a, _2)), == 0);
+ assert((zrsh(a, a, 1), zcmp(a, _1)), == 0);
+ assert((zrsh(a, a, 2), zcmp(a, _0)), == 0);
+ assert(zzero(a), == 1);
+
+ assert(zbtest(_0, 0), == 0);
+ assert(zbtest(_1, 0), == 1);
+ assert(zbtest(_2, 0), == 0);
+ assert(zbtest(_3, 0), == 1);
+ assert(zbtest(_0, 1), == 0);
+ assert(zbtest(_1, 1), == 0);
+ assert(zbtest(_2, 1), == 1);
+ assert(zbtest(_3, 1), == 1);
+ assert(zbtest(_0, 2), == 0);
+ assert(zbtest(_1, 2), == 0);
+ assert(zbtest(_2, 2), == 0);
+ assert(zbtest(_3, 2), == 0);
+
+ znot(a, _2);
+ assert(zcmpmag(a, _1), == 0);
+ assert(zcmp(a, _1), != 0);
+ znot(a, a);
+ assert(zcmp(a, _0), == 0);
+
+ zsetu(a, 0xEEFF);
+ zsetu(c, 0xEE);
+ zsetu(d, 0xFF);
+ zsplit(a, b, a, 8);
+ assert(zcmpmag(a, c), == 0);
+ assert(zcmpmag(b, d), == 0);
+ zsetu(a, 0xEEFF);
+ zsplit(b, a, a, 8);
+ assert(zcmpmag(b, c), == 0);
+ assert(zcmpmag(a, d), == 0);
+
+ zmul(a, _2, _3);
+ assert(zcmpi(a, 6), == 0);
+ zneg(_3, _3);
+ zmul(a, _2, _3);
+ assert(zcmpi(a, -6), == 0);
+ zneg(_3, _3);
+ zneg(_2, _2);
+ zmul(a, _2, _3);
+ assert(zcmpi(a, -6), == 0);
+ zneg(_3, _3);
+ zmul(a, _2, _3);
+ assert(zcmpi(a, 6), == 0);
+ zneg(_3, _3);
+ zneg(_2, _2);
+
+ zmul(a, _3, _3);
+ assert(zcmpi(a, 9), == 0);
+ zsqr(a, _3);
+ assert(zcmpi(a, 9), == 0);
+ zneg(_3, _3);
+ zmul(a, _3, _3);
+ assert(zcmpi(a, 9), == 0);
+ zsqr(a, _3);
+ assert(zcmpi(a, 9), == 0);
+ zneg(_3, _3);
+
+ zseti(a, 8);
+ zseti(b, 2);
+ zdiv(c, a, b);
+ assert(zcmpi(c, 4), == 0);
+ zseti(b, -2);
+ zdiv(c, a, b);
+ assert(zcmpi(c, -4), == 0);
+ zseti(a, -8);
+ zseti(b, 2);
+ zdiv(c, a, b);
+ assert(zcmpi(c, -4), == 0);
+ zseti(b, -2);
+ zdiv(c, a, b);
+ assert(zcmpi(c, 4), == 0);
+
+ zseti(a, 1000);
+ zseti(b, 10);
+ zdiv(c, a, b);
+ assert(zcmpi(c, 100), == 0);
+ zseti(b, -10);
+ zdiv(c, a, b);
+ assert(zcmpi(c, -100), == 0);
+ zseti(a, -1000);
+ zseti(b, 10);
+ zdiv(c, a, b);
+ assert(zcmpi(c, -100), == 0);
+ zseti(b, -10);
+ zdiv(c, a, b);
+ assert(zcmpi(c, 100), == 0);
+
+ zseti(a, 7);
+ zseti(b, 3);
+ zmod(c, a, b);
+ assert(zcmpi(c, 1), == 0);
+ zseti(b, -3);
+ zmod(c, a, b);
+ assert(zcmpi(c, 1), == 0);
+ zseti(a, -7);
+ zseti(b, 3);
+ zmod(c, a, b);
+ assert(zcmpi(c, 1), == 0);
+ zseti(b, -3);
+ zmod(c, a, b);
+ assert(zcmpi(c, 1), == 0);
+
+ zseti(a, 7);
+ zseti(b, 3);
+ zdivmod(d, c, a, b);
+ assert(zcmpi(d, 2), == 0);
+ assert(zcmpi(c, 1), == 0);
+ zseti(b, -3);
+ zdivmod(d, c, a, b);
+ assert(zcmpi(d, -2), == 0);
+ assert(zcmpi(c, 1), == 0);
+ zseti(a, -7);
+ zseti(b, 3);
+ zdivmod(d, c, a, b);
+ assert(zcmpi(d, -2), == 0);
+ assert(zcmpi(c, 1), == 0);
+ zseti(b, -3);
+ zdivmod(d, c, a, b);
+ assert(zcmpi(d, 2), == 0);
+ assert(zcmpi(c, 1), == 0);
+
+ zseti(a, 10);
+ zseti(b, -1);
+ zpow(a, a, b);
+ assert(zcmp(a, _0), == 0);
+
+ zseti(a, 10);
+ zseti(b, -1);
+ zseti(a, 20);
+ zmodpow(a, a, b, c);
+ assert(zcmp(a, _0), == 0);
+
+ zseti(a, 10);
+ zseti(c, 100000L);
+ zpowu(a, a, 5);
+ assert(zcmpmag(a, c), == 0);
+ assert(zcmp(a, c), == 0);
+
+ zseti(a, -10);
+ zseti(c, -100000L);
+ zpowu(a, a, 5);
+ assert(zcmpmag(a, c), == 0);
+ assert(zcmp(a, c), == 0);
+
+ zseti(a, -10);
+ zseti(c, 10000L);
+ zpowu(a, a, 4);
+ assert(zcmpmag(a, c), == 0);
+ assert(zcmp(a, c), == 0);
+
+ zseti(a, 10);
+ zseti(c, 3);
+ zmodpowu(a, a, 5, c);
+ assert(zcmpmag(a, _1), == 0);
+ assert(zcmp(a, _1), == 0);
+
+ zseti(a, 10);
+ zseti(b, 5);
+ zseti(c, 100000L);
+ zpow(a, a, b);
+ assert(zcmpmag(a, c), == 0);
+ assert(zcmp(a, c), == 0);
+
+ zseti(a, -10);
+ zseti(b, 5);
+ zseti(c, -100000L);
+ zpow(a, a, b);
+ assert(zcmpmag(a, c), == 0);
+ assert(zcmp(a, c), == 0);
+
+ zseti(a, -10);
+ zseti(b, 4);
+ zseti(c, 10000L);
+ zpow(a, a, b);
+ assert(zcmpmag(a, c), == 0);
+ assert(zcmp(a, c), == 0);
+
+ zseti(a, 10);
+ zseti(b, 5);
+ zseti(c, 3);
+ zmodpow(a, a, b, c);
+ assert(zcmpmag(a, _1), == 0);
+ assert(zcmp(a, _1), == 0);
+
+ zseti(a, 102);
+ zseti(b, 501);
+ zseti(c, 5);
+ zmodmul(a, a, b, c);
+ assert(zcmp(a, _2), == 0);
+
+ zseti(b, 2 * 3 * 3 * 7);
+ zseti(c, 3 * 7 * 11);
+ zseti(d, 3 * 7);
+ assert((zgcd(a, _0, _0), zcmp(a, _0)), == 0);
+ assert((zgcd(a, b, _0), zcmp(a, b)), == 0);
+ assert((zgcd(a, _0, c), zcmp(a, c)), == 0);
+ assert((zgcd(a, b, b), zcmp(a, b)), == 0);
+ assert((zgcd(a, b, _2), zcmp(a, _2)), == 0);
+ assert((zgcd(a, _2, b), zcmp(a, _2)), == 0);
+ assert((zgcd(a, _2, _2), zcmp(a, _2)), == 0);
+ assert((zgcd(a, c, _2), zcmp(a, _1)), == 0);
+ assert((zgcd(a, _2, c), zcmp(a, _1)), == 0);
+ assert((zgcd(a, b, _1), zcmp(a, _1)), == 0);
+ assert((zgcd(a, _1, c), zcmp(a, _1)), == 0);
+ assert((zgcd(a, _1, _1), zcmp(a, _1)), == 0);
+ assert((zgcd(a, b, c), zcmp(a, d)), == 0);
+ assert((zgcd(a, c, b), zcmp(a, d)), == 0);
+
+ zsets(a, "1234");
+ assert(zcmpi(a, 1234), == 0);
+ zsets(b, "+1234");
+ assert(zcmp(a, b), == 0);
+ assert_zu(zstr_length(_0, 10), 1);
+ assert_zu(zstr_length(_1, 10), 1);
+ assert_zu(zstr_length(_2, 10), 1);
+ assert_zu(zstr_length(_3, 10), 1);
+ zneg(_2, _2);
+ assert_zu(zstr_length(_2, 10), 2);
+ zneg(_2, _2);
+ assert_zu(zstr_length(a, 10), 4);
+ zstr(a, buf);
+ assert_s(buf, "1234");
+ zsets(a, "-1234");
+ zseti(b, -1234);
+ zseti(c, 1234);
+ assert(zcmp(a, _0), < 0);
+ assert(zcmp(a, b), == 0);
+ assert(zcmpmag(a, c), == 0);
+ assert(zcmp(a, c), < 0);
+ zstr(a, buf);
+ assert_s(buf, "-1234");
+ assert_s(zstr(a, buf), "-1234");
+
+ zsetu(d, 100000UL);
+ zrand(a, FAST_RANDOM, UNIFORM, d);
+ assert(zcmp(a, _0), >= 0);
+ assert(zcmp(a, d), <= 0);
+ zrand(b, SECURE_RANDOM, UNIFORM, d);
+ assert(zcmp(b, _0), >= 0);
+ assert(zcmp(b, d), <= 0);
+ zrand(c, FAST_RANDOM, UNIFORM, d);
+ assert(zcmp(c, _0), >= 0);
+ assert(zcmp(c, d), <= 0);
+ assert(zcmp(a, b), != 0);
+ assert(zcmp(a, c), != 0);
+ assert(zcmp(b, c), != 0);
+
+ assert((zseti(a, -5), zptest(0, a, 100)), == NONPRIME);
+ assert((zseti(a, -4), zptest(0, a, 100)), == NONPRIME);
+ assert((zseti(a, -3), zptest(0, a, 100)), == NONPRIME);
+ assert((zseti(a, -2), zptest(0, a, 100)), == NONPRIME);
+ assert((zseti(a, -1), zptest(0, a, 100)), == NONPRIME);
+ assert((zseti(a, 0), zptest(0, a, 100)), == NONPRIME);
+ assert((zseti(a, 1), zptest(0, a, 100)), == NONPRIME);
+ assert((zseti(a, 2), zptest(0, a, 100)), == PRIME);
+ assert((zseti(a, 3), zptest(0, a, 100)), == PRIME);
+ assert((zseti(a, 4), zptest(0, a, 100)), == NONPRIME);
+ assert((zseti(a, 5), zptest(0, a, 100)), != NONPRIME);
+ assert((zseti(a, 6), zptest(0, a, 100)), == NONPRIME);
+ assert((zseti(a, 7), zptest(0, a, 100)), != NONPRIME);
+ assert((zseti(a, 8), zptest(0, a, 100)), == NONPRIME);
+ assert((zseti(a, 9), zptest(0, a, 100)), == NONPRIME);
+ assert((zseti(a, 10), zptest(0, a, 100)), == NONPRIME);
+ assert((zseti(a, 11), zptest(0, a, 100)), != NONPRIME);
+ assert((zseti(a, 101), zptest(0, a, 100)), != NONPRIME);
+
+done:
+ zfree(a), zfree(b), zfree(c), zfree(d), zfree(_0), zfree(_1), zfree(_2), zfree(_3);
+ zunsetup();
+ return ret;
+}
Received on Fri Mar 04 2016 - 23:50:22 CET

This archive was generated by hypermail 2.3.0 : Sat Mar 05 2016 - 00:00:36 CET