[git] GCRYPT - branch, LIBGCRYPT-1-6-BRANCH, updated. libgcrypt-1.6.2-8-g5e72b6c

by NIIBE Yutaka cvs at cvs.gnupg.org
Thu Feb 26 13:35:42 CET 2015


This is an automated email from the git hooks/post-receive script. It was
generated because a ref change was pushed to the repository containing
the project "The GNU crypto library".

The branch, LIBGCRYPT-1-6-BRANCH has been updated
       via  5e72b6c76ebee720f69b8a5c212f52d38eb50287 (commit)
       via  d9f002899d26dc64f1502ae5050632340a4780fe (commit)
       via  deb6f231ba85f65283c9e1deb3e2dea3b6ca46dc (commit)
      from  d482948ac41768c36c5352a513fca8c50d2da4db (commit)

Those revisions listed above that are new to this repository have
not appeared on any other notification email; so we list those
revisions in full, below.

- Log -----------------------------------------------------------------
commit 5e72b6c76ebee720f69b8a5c212f52d38eb50287
Author: NIIBE Yutaka <gniibe at fsij.org>
Date:   Thu Feb 26 21:07:01 2015 +0900

    mpi: Avoid data-dependent timing variations in mpi_powm.
    
    * mpi/mpi-pow.c (mpi_powm): Access all data in the table by
    mpi_set_cond.
    
    --
    
    Access to the precomputed table was indexed by a portion of EXPO,
    which could be mounted by a side channel attack.  This change fixes
    this particular data-dependent access pattern.

diff --git a/mpi/mpi-pow.c b/mpi/mpi-pow.c
index 4a79162..70bf9e8 100644
--- a/mpi/mpi-pow.c
+++ b/mpi/mpi-pow.c
@@ -422,6 +422,7 @@ _gcry_mpi_powm (gcry_mpi_t res,
   mpi_size_t W;
   mpi_ptr_t base_u;
   mpi_size_t base_u_size;
+  mpi_size_t max_u_size;
 
   esize = expo->nlimbs;
   msize = mod->nlimbs;
@@ -540,7 +541,7 @@ _gcry_mpi_powm (gcry_mpi_t res,
 
   /* Main processing.  */
   {
-    mpi_size_t i, j;
+    mpi_size_t i, j, k;
     mpi_ptr_t xp;
     mpi_size_t xsize;
     int c;
@@ -559,7 +560,7 @@ _gcry_mpi_powm (gcry_mpi_t res,
     if (W > 1)                  /* X := BASE^2 */
       mul_mod (xp, &xsize, bp, bsize, bp, bsize, mp, msize, &karactx);
     base_u = precomp[0] = mpi_alloc_limb_space (bsize, esec);
-    base_u_size = precomp_size[0] = bsize;
+    base_u_size = max_u_size = precomp_size[0] = bsize;
     MPN_COPY (precomp[0], bp, bsize);
     for (i = 1; i < (1 << (W - 1)); i++)
       {                         /* PRECOMP[i] = BASE^(2 * i + 1) */
@@ -571,9 +572,14 @@ _gcry_mpi_powm (gcry_mpi_t res,
                    mp, msize, &karactx);
         base_u = precomp[i] = mpi_alloc_limb_space (rsize, esec);
         base_u_size = precomp_size[i] = rsize;
+        if (max_u_size < base_u_size)
+          max_u_size = base_u_size;
         MPN_COPY (precomp[i], rp, rsize);
       }
 
+    base_u = mpi_alloc_limb_space (max_u_size, esec);
+    MPN_ZERO (base_u, max_u_size);
+
     i = esize - 1;
 
     /* Main loop.
@@ -659,8 +665,24 @@ _gcry_mpi_powm (gcry_mpi_t res,
               rsize = xsize;
             }
 
-          base_u = precomp[e0];
-          base_u_size = precomp_size[e0];
+          /*
+           *  base_u <= precomp[e0]
+           *  base_u_size <= precomp_size[e0]
+           */
+          base_u_size = 0;
+          for (k = 0; k < (1<< (W - 1)); k++)
+            {
+              struct gcry_mpi w, u;
+              w.alloced = w.nlimbs = precomp_size[k];
+              u.alloced = u.nlimbs = precomp_size[k];
+              w.sign = u.sign = 0;
+              w.flags = u.flags = 0;
+              w.d = base_u;
+              u.d = precomp[k];
+
+              mpi_set_cond (&w, &u, k == e0);
+              base_u_size |= (precomp_size[k] & ((mpi_size_t)0 - (k == e0)) );
+            }
 
           mul_mod (xp, &xsize, rp, rsize, base_u, base_u_size,
                    mp, msize, &karactx);
@@ -687,8 +709,24 @@ _gcry_mpi_powm (gcry_mpi_t res,
 
     if (e != 0)
       {
-        base_u = precomp[(e>>1)];
-        base_u_size = precomp_size[(e>>1)];
+        /*
+         * base_u <= precomp[(e>>1)]
+         * base_u_size <= precomp_size[(e>>1)]
+         */
+        base_u_size = 0;
+        for (k = 0; k < (1<< (W - 1)); k++)
+          {
+            struct gcry_mpi w, u;
+            w.alloced = w.nlimbs = precomp_size[k];
+            u.alloced = u.nlimbs = precomp_size[k];
+            w.sign = u.sign = 0;
+            w.flags = u.flags = 0;
+            w.d = base_u;
+            u.d = precomp[k];
+
+            mpi_set_cond (&w, &u, k == (e>>1));
+            base_u_size |= (precomp_size[k] & ((mpi_size_t)0 - (k == (e>>1))) );
+          }
 
         mul_mod (xp, &xsize, rp, rsize, base_u, base_u_size,
                  mp, msize, &karactx);
@@ -739,6 +777,7 @@ _gcry_mpi_powm (gcry_mpi_t res,
     _gcry_mpih_release_karatsuba_ctx (&karactx );
     for (i = 0; i < (1 << (W - 1)); i++)
       _gcry_mpi_free_limb_space( precomp[i], esec ? precomp_size[i] : 0 );
+    _gcry_mpi_free_limb_space (base_u, esec ? max_u_size : 0);
   }
 
   /* Fixup for negative results.  */

commit d9f002899d26dc64f1502ae5050632340a4780fe
Author: NIIBE Yutaka <gniibe at fsij.org>
Date:   Mon Feb 23 20:10:27 2015 +0900

    mpi: Revise mpi_powm.
    
    * mpi/mpi-pow.c (_gcry_mpi_powm): Rename the table to PRECOMP.
    
    --
    
    The name of precomputed table was b_2i3 which stands for BASE^(2*I+3).
    But it's too cryptic, so, it's renamed.  Besides, we needed to
    distinguish the case of I==0, that was not good.  Since it's OK to
    increase the size of table by one, it's BASE^(2*I+1), now.

diff --git a/mpi/mpi-pow.c b/mpi/mpi-pow.c
index 0f0947f..4a79162 100644
--- a/mpi/mpi-pow.c
+++ b/mpi/mpi-pow.c
@@ -381,7 +381,7 @@ mul_mod (mpi_ptr_t xp, mpi_size_t *xsize_p,
      *xsize_p = rsize + ssize;
 }
 
-#define SIZE_B_2I3 ((1 << (5 - 1)) - 1)
+#define SIZE_PRECOMP ((1 << (5 - 1)))
 
 /****************
  * RES = BASE ^ EXPO mod MOD
@@ -417,8 +417,8 @@ _gcry_mpi_powm (gcry_mpi_t res,
   unsigned int bp_nlimbs = 0;
   unsigned int ep_nlimbs = 0;
   unsigned int xp_nlimbs = 0;
-  mpi_ptr_t b_2i3[SIZE_B_2I3]; /* Pre-computed array: BASE^3, ^5, ^7, ... */
-  mpi_size_t b_2i3size[SIZE_B_2I3];
+  mpi_ptr_t precomp[SIZE_PRECOMP]; /* Pre-computed array: BASE^1, ^3, ^5, ... */
+  mpi_size_t precomp_size[SIZE_PRECOMP];
   mpi_size_t W;
   mpi_ptr_t base_u;
   mpi_size_t base_u_size;
@@ -555,31 +555,23 @@ _gcry_mpi_powm (gcry_mpi_t res,
     memset( &karactx, 0, sizeof karactx );
     negative_result = (ep[0] & 1) && bsign;
 
-    /* Precompute B_2I3[], BASE^(2 * i + 3), BASE^3, ^5, ^7, ... */
+    /* Precompute PRECOMP[], BASE^(2 * i + 1), BASE^1, ^3, ^5, ... */
     if (W > 1)                  /* X := BASE^2 */
       mul_mod (xp, &xsize, bp, bsize, bp, bsize, mp, msize, &karactx);
-    for (i = 0; i < (1 << (W - 1)) - 1; i++)
-      {                         /* B_2I3[i] = BASE^(2 * i + 3) */
-        if (i == 0)
-          {
-            base_u = bp;
-            base_u_size = bsize;
-          }
-        else
-          {
-            base_u = b_2i3[i-1];
-            base_u_size = b_2i3size[i-1];
-          }
-
+    base_u = precomp[0] = mpi_alloc_limb_space (bsize, esec);
+    base_u_size = precomp_size[0] = bsize;
+    MPN_COPY (precomp[0], bp, bsize);
+    for (i = 1; i < (1 << (W - 1)); i++)
+      {                         /* PRECOMP[i] = BASE^(2 * i + 1) */
         if (xsize >= base_u_size)
           mul_mod (rp, &rsize, xp, xsize, base_u, base_u_size,
                    mp, msize, &karactx);
         else
           mul_mod (rp, &rsize, base_u, base_u_size, xp, xsize,
                    mp, msize, &karactx);
-        b_2i3[i] = mpi_alloc_limb_space (rsize, esec);
-        b_2i3size[i] = rsize;
-        MPN_COPY (b_2i3[i], rp, rsize);
+        base_u = precomp[i] = mpi_alloc_limb_space (rsize, esec);
+        base_u_size = precomp_size[i] = rsize;
+        MPN_COPY (precomp[i], rp, rsize);
       }
 
     i = esize - 1;
@@ -667,16 +659,8 @@ _gcry_mpi_powm (gcry_mpi_t res,
               rsize = xsize;
             }
 
-          if (e0 == 0)
-            {
-              base_u = bp;
-              base_u_size = bsize;
-            }
-          else
-            {
-              base_u = b_2i3[e0 - 1];
-              base_u_size = b_2i3size[e0 -1];
-            }
+          base_u = precomp[e0];
+          base_u_size = precomp_size[e0];
 
           mul_mod (xp, &xsize, rp, rsize, base_u, base_u_size,
                    mp, msize, &karactx);
@@ -703,16 +687,8 @@ _gcry_mpi_powm (gcry_mpi_t res,
 
     if (e != 0)
       {
-        if ((e>>1) == 0)
-          {
-            base_u = bp;
-            base_u_size = bsize;
-          }
-        else
-          {
-            base_u = b_2i3[(e>>1) - 1];
-            base_u_size = b_2i3size[(e>>1) -1];
-          }
+        base_u = precomp[(e>>1)];
+        base_u_size = precomp_size[(e>>1)];
 
         mul_mod (xp, &xsize, rp, rsize, base_u, base_u_size,
                  mp, msize, &karactx);
@@ -761,8 +737,8 @@ _gcry_mpi_powm (gcry_mpi_t res,
     MPN_NORMALIZE (rp, rsize);
 
     _gcry_mpih_release_karatsuba_ctx (&karactx );
-    for (i = 0; i < (1 << (W - 1)) - 1; i++)
-      _gcry_mpi_free_limb_space( b_2i3[i], esec ? b_2i3size[i] : 0 );
+    for (i = 0; i < (1 << (W - 1)); i++)
+      _gcry_mpi_free_limb_space( precomp[i], esec ? precomp_size[i] : 0 );
   }
 
   /* Fixup for negative results.  */

commit deb6f231ba85f65283c9e1deb3e2dea3b6ca46dc
Author: NIIBE Yutaka <gniibe at fsij.org>
Date:   Wed Feb 11 21:42:22 2015 +0900

    mpi: Add mpi_set_cond.
    
    * mpi/mpiutil.c (_gcry_mpi_set_cond): New.
    * src/mpi.h (mpi_set_cond): New.

diff --git a/mpi/mpiutil.c b/mpi/mpiutil.c
index fdce578..6bef2a8 100644
--- a/mpi/mpiutil.c
+++ b/mpi/mpiutil.c
@@ -482,6 +482,31 @@ _gcry_mpi_set (gcry_mpi_t w, gcry_mpi_t u)
   return w;
 }
 
+gcry_mpi_t
+_gcry_mpi_set_cond (gcry_mpi_t w, const gcry_mpi_t u, unsigned long set)
+{
+  mpi_size_t i;
+  mpi_size_t nlimbs = u->alloced;
+  mpi_limb_t mask = ((mpi_limb_t)0) - !!set;
+  mpi_limb_t x;
+
+  if (w->alloced != u->alloced)
+    log_bug ("mpi_set_cond: different sizes\n");
+
+  for (i = 0; i < nlimbs; i++)
+    {
+      x = mask & (w->d[i] ^ u->d[i]);
+      w->d[i] = w->d[i] ^ x;
+    }
+
+  x = mask & (w->nlimbs ^ u->nlimbs);
+  w->nlimbs = w->nlimbs ^ x;
+
+  x = mask & (w->sign ^ u->sign);
+  w->sign = w->sign ^ x;
+  return w;
+}
+
 
 gcry_mpi_t
 _gcry_mpi_set_ui (gcry_mpi_t w, unsigned long u)
diff --git a/src/mpi.h b/src/mpi.h
index 8446d23..bb3c26d 100644
--- a/src/mpi.h
+++ b/src/mpi.h
@@ -119,8 +119,11 @@ void _gcry_mpi_immutable_failed (void);
 #define mpi_alloc_set_ui(a)   _gcry_mpi_alloc_set_ui ((a))
 #define mpi_m_check(a)        _gcry_mpi_m_check ((a))
 #define mpi_const(n)          _gcry_mpi_const ((n))
+#define mpi_set_cond(w,u,set)  _gcry_mpi_set_cond ((w),(u),(set))
 
 void _gcry_mpi_clear( gcry_mpi_t a );
+gcry_mpi_t _gcry_mpi_set_cond (gcry_mpi_t w, const gcry_mpi_t u,
+                               unsigned long swap);
 gcry_mpi_t  _gcry_mpi_alloc_like( gcry_mpi_t a );
 gcry_mpi_t  _gcry_mpi_alloc_set_ui( unsigned long u);
 void _gcry_mpi_m_check( gcry_mpi_t a );

-----------------------------------------------------------------------

Summary of changes:
 mpi/mpi-pow.c | 93 ++++++++++++++++++++++++++++++++++-------------------------
 mpi/mpiutil.c | 25 ++++++++++++++++
 src/mpi.h     |  3 ++
 3 files changed, 82 insertions(+), 39 deletions(-)


hooks/post-receive
-- 
The GNU crypto library
http://git.gnupg.org




More information about the Gnupg-commits mailing list