Mailing List Archive

[PATCH 1/2] const-time: add functions for generating masks from 0/1 input
* mpi/ec-nist.c (ct_limb_gen_mask, ct_limb_gen_inv_mask): New.
(_gcry_mpi_ec_nist192_mod, _gcry_mpi_ec_nist224_mod)
(_gcry_mpi_ec_nist256_mod, _gcry_mpi_ec_nist384_mod): Use mask generating
functions.
* mpi/mpih-const-time.c (ct_limb_gen_mask, ct_limb_gen_inv_mask): New.
(_gcry_mpih_set_cond, _gcry_mpih_add_n_cond, _gcry_mpih_sub_n_cond)
(_gcry_mpih_sub_n_cond, _gcry_mpih_swap_cond): Use mask generating
functions.
* mpi/mpiutil.c (ct_limb_gen_mask, ct_limb_gen_inv_mask): New.
(_gcry_mpi_set_cond, _gcry_mpi_swap_cond): Use mask generating functions.
* src/const-time.h (DEFINE_CT_TYPE_GEN_MASK, ct_uintptr_gen_mask)
(ct_ulong_gen_mask, DEFINE_CT_TYPE_GEN_INV_MASK, ct_uintptr_gen_inv_mask)
(ct_ulong_gen_inv_mask): New.
(DEFINE_CT_TYPE_SELECT_FUNC): Use mask generating functions.
* src/const-time.c (_gcry_ct_memmov_cond): Use mask generating functions.
--

Provide functions for generating mask for constant time operations.

Signed-off-by: Jussi Kivilinna <jussi.kivilinna@iki.fi>
---
mpi/ec-nist.c | 22 ++++++++++--------
mpi/mpih-const-time.c | 24 +++++++++++---------
mpi/mpiutil.c | 12 ++++++----
src/const-time.c | 4 ++--
src/const-time.h | 52 +++++++++++++++++++++++++++++++++++++++++--
5 files changed, 87 insertions(+), 27 deletions(-)

diff --git a/mpi/ec-nist.c b/mpi/ec-nist.c
index 6dfaa1da..f3b3cd66 100644
--- a/mpi/ec-nist.c
+++ b/mpi/ec-nist.c
@@ -35,6 +35,10 @@
#include "const-time.h"


+DEFINE_CT_TYPE_GEN_MASK(limb, mpi_limb_t)
+DEFINE_CT_TYPE_GEN_INV_MASK(limb, mpi_limb_t)
+
+
static inline
void prefetch(const void *tab, size_t len)
{
@@ -141,8 +145,8 @@ _gcry_mpi_ec_nist192_mod (gcry_mpi_t w, mpi_ec_t ctx)

s_is_negative = LO32_LIMB64(s[3]) >> 31;

- mask2 = _gcry_ct_vzero - s_is_negative;
- mask1 = s_is_negative - _gcry_ct_vone;
+ mask2 = ct_limb_gen_mask(s_is_negative);
+ mask1 = ct_limb_gen_inv_mask(s_is_negative);

STORE64_COND(wp, 0, mask2, o[0], mask1, s[0]);
STORE64_COND(wp, 1, mask2, o[1], mask1, s[1]);
@@ -264,8 +268,8 @@ _gcry_mpi_ec_nist224_mod (gcry_mpi_t w, mpi_ec_t ctx)

s_is_negative = (HI32_LIMB64(s[3]) >> 31);

- mask2 = _gcry_ct_vzero - s_is_negative;
- mask1 = s_is_negative - _gcry_ct_vone;
+ mask2 = ct_limb_gen_mask(s_is_negative);
+ mask1 = ct_limb_gen_inv_mask(s_is_negative);

STORE64_COND(wp, 0, mask2, d[0], mask1, s[0]);
STORE64_COND(wp, 1, mask2, d[1], mask1, s[1]);
@@ -493,9 +497,9 @@ _gcry_mpi_ec_nist256_mod (gcry_mpi_t w, mpi_ec_t ctx)

s_is_negative = LO32_LIMB64(s[4]) >> 31;
d_is_negative = LO32_LIMB64(d[4]) >> 31;
- mask3 = _gcry_ct_vzero - d_is_negative;
- mask2 = (_gcry_ct_vzero - s_is_negative) & ~mask3;
- mask1 = (s_is_negative - _gcry_ct_vone) & ~mask3;
+ mask3 = ct_limb_gen_mask(d_is_negative);
+ mask2 = ct_limb_gen_mask(s_is_negative) & ~mask3;
+ mask1 = ct_limb_gen_inv_mask(s_is_negative) & ~mask3;

s[0] = LIMB_OR64(MASK_AND64(mask2, d[0]), MASK_AND64(mask1, s[0]));
s[1] = LIMB_OR64(MASK_AND64(mask2, d[1]), MASK_AND64(mask1, s[1]));
@@ -764,8 +768,8 @@ _gcry_mpi_ec_nist384_mod (gcry_mpi_t w, mpi_ec_t ctx)
p_mult[0 + 3][1], p_mult[0 + 3][0]);

s_is_negative = LO32_LIMB64(s[6]) >> 31;
- mask2 = _gcry_ct_vzero - s_is_negative;
- mask1 = s_is_negative - _gcry_ct_vone;
+ mask2 = ct_limb_gen_mask(s_is_negative);
+ mask1 = ct_limb_gen_inv_mask(s_is_negative);

STORE64_COND(wp, 0, mask2, d[0], mask1, s[0]);
STORE64_COND(wp, 1, mask2, d[1], mask1, s[1]);
diff --git a/mpi/mpih-const-time.c b/mpi/mpih-const-time.c
index 3d854e8c..4ebd072d 100644
--- a/mpi/mpih-const-time.c
+++ b/mpi/mpih-const-time.c
@@ -27,6 +27,10 @@
#define A_LIMB_1 ((mpi_limb_t)1)


+DEFINE_CT_TYPE_GEN_MASK(limb, mpi_limb_t)
+DEFINE_CT_TYPE_GEN_INV_MASK(limb, mpi_limb_t)
+
+
/*
* W = U when OP_ENABLED=1
* otherwise, W keeps old value
@@ -36,8 +40,8 @@ _gcry_mpih_set_cond (mpi_ptr_t wp, mpi_ptr_t up, mpi_size_t usize,
unsigned long op_enable)
{
/* Note: dual mask with AND/OR used for EM leakage mitigation */
- mpi_limb_t mask1 = _gcry_ct_vzero - op_enable;
- mpi_limb_t mask2 = op_enable - _gcry_ct_vone;
+ mpi_limb_t mask1 = ct_limb_gen_mask(op_enable);
+ mpi_limb_t mask2 = ct_limb_gen_inv_mask(op_enable);
mpi_size_t i;

for (i = 0; i < usize; i++)
@@ -56,8 +60,8 @@ _gcry_mpih_add_n_cond (mpi_ptr_t wp, mpi_ptr_t up, mpi_ptr_t vp,
mpi_size_t usize, unsigned long op_enable)
{
/* Note: dual mask with AND/OR used for EM leakage mitigation */
- mpi_limb_t mask1 = _gcry_ct_vzero - op_enable;
- mpi_limb_t mask2 = op_enable - _gcry_ct_vone;
+ mpi_limb_t mask1 = ct_limb_gen_mask(op_enable);
+ mpi_limb_t mask2 = ct_limb_gen_inv_mask(op_enable);
mpi_size_t i;
mpi_limb_t cy;

@@ -88,8 +92,8 @@ _gcry_mpih_sub_n_cond (mpi_ptr_t wp, mpi_ptr_t up, mpi_ptr_t vp,
mpi_size_t usize, unsigned long op_enable)
{
/* Note: dual mask with AND/OR used for EM leakage mitigation */
- mpi_limb_t mask1 = _gcry_ct_vzero - op_enable;
- mpi_limb_t mask2 = op_enable - _gcry_ct_vone;
+ mpi_limb_t mask1 = ct_limb_gen_mask(op_enable);
+ mpi_limb_t mask2 = ct_limb_gen_inv_mask(op_enable);
mpi_size_t i;
mpi_limb_t cy;

@@ -120,8 +124,8 @@ _gcry_mpih_swap_cond (mpi_ptr_t up, mpi_ptr_t vp, mpi_size_t usize,
unsigned long op_enable)
{
/* Note: dual mask with AND/OR used for EM leakage mitigation */
- mpi_limb_t mask1 = _gcry_ct_vzero - op_enable;
- mpi_limb_t mask2 = op_enable - _gcry_ct_vone;
+ mpi_limb_t mask1 = ct_limb_gen_mask(op_enable);
+ mpi_limb_t mask2 = ct_limb_gen_inv_mask(op_enable);
mpi_size_t i;

for (i = 0; i < usize; i++)
@@ -143,8 +147,8 @@ _gcry_mpih_abs_cond (mpi_ptr_t wp, mpi_ptr_t up, mpi_size_t usize,
unsigned long op_enable)
{
/* Note: dual mask with AND/OR used for EM leakage mitigation */
- mpi_limb_t mask1 = _gcry_ct_vzero - op_enable;
- mpi_limb_t mask2 = op_enable - _gcry_ct_vone;
+ mpi_limb_t mask1 = ct_limb_gen_mask(op_enable);
+ mpi_limb_t mask2 = ct_limb_gen_inv_mask(op_enable);
mpi_limb_t cy = op_enable;
mpi_size_t i;

diff --git a/mpi/mpiutil.c b/mpi/mpiutil.c
index f7506718..954bb1ea 100644
--- a/mpi/mpiutil.c
+++ b/mpi/mpiutil.c
@@ -30,6 +30,10 @@
#include "const-time.h"


+DEFINE_CT_TYPE_GEN_MASK(limb, mpi_limb_t)
+DEFINE_CT_TYPE_GEN_INV_MASK(limb, mpi_limb_t)
+
+
#if SIZEOF_UNSIGNED_INT == 2
# define MY_UINT_MAX 0xffff
/* (visual check: 0123 ) */
@@ -509,8 +513,8 @@ gcry_mpi_t
_gcry_mpi_set_cond (gcry_mpi_t w, const gcry_mpi_t u, unsigned long set)
{
/* Note: dual mask with AND/OR used for EM leakage mitigation */
- mpi_limb_t mask1 = _gcry_ct_vzero - set;
- mpi_limb_t mask2 = set - _gcry_ct_vone;
+ mpi_limb_t mask1 = ct_limb_gen_mask(set);
+ mpi_limb_t mask2 = ct_limb_gen_inv_mask(set);
mpi_size_t i;
mpi_size_t nlimbs = u->alloced;
mpi_limb_t xu;
@@ -611,8 +615,8 @@ void
_gcry_mpi_swap_cond (gcry_mpi_t a, gcry_mpi_t b, unsigned long swap)
{
/* Note: dual mask with AND/OR used for EM leakage mitigation */
- mpi_limb_t mask1 = _gcry_ct_vzero - swap;
- mpi_limb_t mask2 = swap - _gcry_ct_vone;
+ mpi_limb_t mask1 = ct_limb_gen_mask(swap);
+ mpi_limb_t mask2 = ct_limb_gen_inv_mask(swap);
mpi_size_t i;
mpi_size_t nlimbs;
mpi_limb_t *ua = a->d;
diff --git a/src/const-time.c b/src/const-time.c
index 73bf8b40..55edd979 100644
--- a/src/const-time.c
+++ b/src/const-time.c
@@ -75,8 +75,8 @@ _gcry_ct_memmov_cond (void *dst, const void *src, size_t len,
unsigned long op_enable)
{
/* Note: dual mask with AND/OR used for EM leakage mitigation */
- unsigned char mask1 = _gcry_ct_vzero - op_enable;
- unsigned char mask2 = op_enable - _gcry_ct_vone;
+ unsigned char mask1 = ct_ulong_gen_mask(op_enable);
+ unsigned char mask2 = ct_ulong_gen_inv_mask(op_enable);
unsigned char *b_dst = dst;
const unsigned char *b_src = src;
size_t i;
diff --git a/src/const-time.h b/src/const-time.h
index e324dcb7..cfb59f9a 100644
--- a/src/const-time.h
+++ b/src/const-time.h
@@ -80,6 +80,54 @@ unsigned int _gcry_ct_not_memequal (const void *b1, const void *b2, size_t len);
any structure. */
unsigned int _gcry_ct_memequal (const void *b1, const void *b2, size_t len);

+/*
+ * Return all bits set if A is 1 and return 0 otherwise.
+ */
+#ifdef HAVE_GCC_ASM_VOLATILE_MEMORY
+# define DEFINE_CT_TYPE_GEN_MASK(name, type) \
+ static inline type \
+ ct_##name##_gen_mask (unsigned long op_enable) \
+ { \
+ type mask = -(type)op_enable; \
+ asm volatile ("\n" :: "r" (mask) : "memory"); \
+ return mask; \
+ }
+#else
+# define DEFINE_CT_TYPE_GEN_MASK(name, type) \
+ static inline type \
+ ct_##name##_gen_mask (unsigned long op_enable) \
+ { \
+ type mask = (type)_gcry_ct_vzero - (type)op_enable; \
+ return mask; \
+ }
+#endif
+DEFINE_CT_TYPE_GEN_MASK(uintptr, uintptr_t)
+DEFINE_CT_TYPE_GEN_MASK(ulong, unsigned long)
+
+/*
+ * Return all bits set if A is 0 and return 1 otherwise.
+ */
+#ifdef HAVE_GCC_ASM_VOLATILE_MEMORY
+# define DEFINE_CT_TYPE_GEN_INV_MASK(name, type) \
+ static inline type \
+ ct_##name##_gen_inv_mask (unsigned long op_enable) \
+ { \
+ type mask = (type)op_enable - (type)1; \
+ asm volatile ("\n" :: "r" (mask) : "memory"); \
+ return mask; \
+ }
+#else
+# define DEFINE_CT_TYPE_GEN_INV_MASK(name, type) \
+ static inline type \
+ ct_##name##_gen_inv_mask (unsigned long op_enable) \
+ { \
+ type mask = (type)op_enable - (type)_gcry_ct_vone; \
+ return mask; \
+ }
+#endif
+DEFINE_CT_TYPE_GEN_INV_MASK(uintptr, uintptr_t)
+DEFINE_CT_TYPE_GEN_INV_MASK(ulong, unsigned long)
+
/*
* Return A when OP_ENABLED=1
* otherwise, return B
@@ -88,8 +136,8 @@ unsigned int _gcry_ct_memequal (const void *b1, const void *b2, size_t len);
static inline type \
ct_##name##_select (type a, type b, unsigned long op_enable) \
{ \
- type mask_b = (type)op_enable - (type)_gcry_ct_vone; \
- type mask_a = (type)_gcry_ct_vzero - (type)op_enable; \
+ type mask_b = ct_##name##_gen_inv_mask(op_enable); \
+ type mask_a = ct_##name##_gen_mask(op_enable); \
return (mask_a & a) | (mask_b & b); \
}
DEFINE_CT_TYPE_SELECT_FUNC(uintptr, uintptr_t)
--
2.40.1


_______________________________________________
Gcrypt-devel mailing list
Gcrypt-devel@gnupg.org
https://lists.gnupg.org/mailman/listinfo/gcrypt-devel