mp.c: Check that CRT moduli are pairwise coprime.
authorMark Wooding <mdw@distorted.org.uk>
Sun, 10 Nov 2019 22:46:35 +0000 (22:46 +0000)
committerMark Wooding <mdw@distorted.org.uk>
Fri, 22 Nov 2019 22:18:10 +0000 (22:18 +0000)
mp.c

diff --git a/mp.c b/mp.c
index fff4aec..bad566d 100644 (file)
--- a/mp.c
+++ b/mp.c
@@ -1718,10 +1718,11 @@ static void mpcrt_pydealloc(PyObject *me)
 static PyObject *mpcrt_pynew(PyTypeObject *ty, PyObject *arg, PyObject *kw)
 {
   mpcrt_mod *v = 0;
-  int n, i = 0;
+  int n, i = 0, j;
   char *kwlist[] = { "mv", 0 };
   PyObject *q = 0, *x;
-  mp *xx = MP_NEW;
+  mp *xx = MP_NEW, *y = MP_NEW, *g = MP_NEW;
+  mpmul mm;
   mpcrt_pyobj *c = 0;
 
   if (PyTuple_Size(arg) > 1)
@@ -1740,10 +1741,19 @@ static PyObject *mpcrt_pynew(PyTypeObject *ty, PyObject *arg, PyObject *kw)
     if (MP_CMP(xx, <=, MP_ZERO)) VALERR("moduli must be positive");
     v[i].m = xx; v[i].n = 0; v[i].ni = 0; v[i].nni = 0; xx = MP_NEW;
   }
+  mpmul_init(&mm);
+  for (j = 0; j < i; j++) mpmul_add(&mm, v[j].m);
+  xx = mpmul_done(&mm);
+  for (j = 0; j < i; j++) {
+    mp_div(&y, 0, xx, v[j].m);
+    mp_gcd(&g, 0, 0, y, v[j].m);
+    if (!MP_EQ(g, MP_ONE)) VALERR("moduli must be pairwise coprime");
+  }
+
   c = (mpcrt_pyobj *)ty->tp_alloc(ty, 0);
   mpcrt_create(&c->c, v, n, 0);
   Py_DECREF(q);
-  mp_drop(xx);
+  mp_drop(xx); mp_drop(y); mp_drop(g);
   return ((PyObject *)c);
 
 end:
@@ -1754,7 +1764,7 @@ end:
     xfree(v);
   }
   Py_XDECREF(q);
-  mp_drop(xx);
+  mp_drop(xx); mp_drop(y); mp_drop(g);
   return (0);
 }