summaryrefslogtreecommitdiff
path: root/mpi/mpiutil.c
diff options
context:
space:
mode:
authorJussi Kivilinna <jussi.kivilinna@iki.fi>2021-04-03 19:59:47 +0300
committerJussi Kivilinna <jussi.kivilinna@iki.fi>2021-04-09 17:22:27 +0300
commit1266f5bb02b7f76f2e4697ecfb85ef19c2ae04a9 (patch)
treecdd1262c99d0a7bc637f22b8eb014e52d389a5d2 /mpi/mpiutil.c
parent840713de1a685920b6b1e1379902d545eccc74cf (diff)
downloadlibgcrypt-1266f5bb02b7f76f2e4697ecfb85ef19c2ae04a9.tar.gz
mpi: harden swap_cond functions against EM leakage
* mpi/mpih-const-time.c (vzero, vone): New. (_gcry_mpih_swap_cond): Use two masks for selecting output. * mpi/mpiutil.c (vzero, vone): New. (_gcry_mpi_swap_cond): Use to masks for selecting output. -- GnuPG-bug-id: T5330 Signed-off-by: Jussi Kivilinna <jussi.kivilinna@iki.fi>
Diffstat (limited to 'mpi/mpiutil.c')
-rw-r--r--mpi/mpiutil.c34
1 files changed, 23 insertions, 11 deletions
diff --git a/mpi/mpiutil.c b/mpi/mpiutil.c
index 86b8361e..a1ac1c43 100644
--- a/mpi/mpiutil.c
+++ b/mpi/mpiutil.c
@@ -46,6 +46,11 @@
/* Constants allocated right away at startup. */
static gcry_mpi_t constants[MPI_NUMBER_OF_CONSTANTS];
+/* These variables are used to generate masks from conditional operation
+ * flag parameters. Use of volatile prevents compiler optimizations from
+ * converting AND-masking to conditional branches. */
+static volatile mpi_limb_t vzero = 0;
+static volatile mpi_limb_t vone = 1;
const char *
@@ -608,8 +613,12 @@ _gcry_mpi_swap_cond (gcry_mpi_t a, gcry_mpi_t b, unsigned long swap)
{
mpi_size_t i;
mpi_size_t nlimbs;
- mpi_limb_t mask = ((mpi_limb_t)0) - swap;
- mpi_limb_t x;
+ mpi_limb_t mask1 = vzero - swap;
+ mpi_limb_t mask2 = swap - vone;
+ mpi_limb_t *ua = a->d;
+ mpi_limb_t *ub = b->d;
+ mpi_limb_t xa;
+ mpi_limb_t xb;
if (a->alloced > b->alloced)
nlimbs = b->alloced;
@@ -620,18 +629,21 @@ _gcry_mpi_swap_cond (gcry_mpi_t a, gcry_mpi_t b, unsigned long swap)
for (i = 0; i < nlimbs; i++)
{
- x = mask & (a->d[i] ^ b->d[i]);
- a->d[i] = a->d[i] ^ x;
- b->d[i] = b->d[i] ^ x;
+ xa = ua[i];
+ xb = ub[i];
+ ua[i] = (xa & mask2) | (xb & mask1);
+ ub[i] = (xa & mask1) | (xb & mask2);
}
- x = mask & (a->nlimbs ^ b->nlimbs);
- a->nlimbs = a->nlimbs ^ x;
- b->nlimbs = b->nlimbs ^ x;
+ xa = a->nlimbs;
+ xb = b->nlimbs;
+ a->nlimbs = (xa & mask2) | (xb & mask1);
+ b->nlimbs = (xa & mask1) | (xb & mask2);
- x = mask & (a->sign ^ b->sign);
- a->sign = a->sign ^ x;
- b->sign = b->sign ^ x;
+ xa = a->sign;
+ xb = b->sign;
+ a->sign = (xa & mask2) | (xb & mask1);
+ b->sign = (xa & mask1) | (xb & mask2);
}