]> git.ipfire.org Git - thirdparty/openssl.git/commitdiff
Add ossl_bn_is_word_fixed_top()
authorTomas Mraz <tomas@openssl.org>
Thu, 25 Apr 2024 13:35:36 +0000 (15:35 +0200)
committerTomas Mraz <tomas@openssl.org>
Thu, 9 May 2024 07:32:02 +0000 (09:32 +0200)
Also correct some BN_FLG_FIXED_TOP flag handling.

Reviewed-by: Paul Dale <ppzgs1@gmail.com>
Reviewed-by: Neil Horman <nhorman@openssl.org>
(cherry picked from commit 2d285fa873028f6cff9484a0cdf690fe05d7fb16)

(Merged from https://github.com/openssl/openssl/pull/24317)

crypto/bn/bn_lib.c
crypto/bn/bn_local.h
crypto/bn/bn_rand.c
crypto/bn/bn_shift.c
include/crypto/bn.h
include/internal/constant_time.h

index d7a17560dcaa92ac8256858d8948c8fdf297fd8e..3bd7adb39f439dc156728bf273000366cef028a0 100644 (file)
@@ -769,6 +769,7 @@ int ossl_bn_mask_bits_fixed_top(BIGNUM *a, int n)
         a->top = w + 1;
         a->d[w] &= ~(BN_MASK2 << b);
     }
+    a->flags |= BN_FLG_FIXED_TOP;
     return 1;
 }
 
@@ -956,6 +957,22 @@ int BN_is_word(const BIGNUM *a, const BN_ULONG w)
     return BN_abs_is_word(a, w) && (!w || !a->neg);
 }
 
+int ossl_bn_is_word_fixed_top(const BIGNUM *a, BN_ULONG w)
+{
+    int res, i;
+    const BN_ULONG *ap = a->d;
+
+    if (a->neg || a->top == 0)
+        return 0;
+
+    res = constant_time_select_int(constant_time_eq_bn(ap[0], w), 1, 0);
+
+    for (i = 1; i < a->top; i++)
+        res = constant_time_select_int(constant_time_is_zero_bn(ap[i]),
+                                       res, 0);
+    return res;
+}
+
 int BN_is_odd(const BIGNUM *a)
 {
     return (a->top > 0) && (a->d[0] & 1);
index d355d1fce30b73788c8d6ec89d7d709f7ddd0ed3..50e9d26e215b3383f35c4df4b1707782c4385f8b 100644 (file)
@@ -676,6 +676,5 @@ static ossl_inline BIGNUM *bn_expand(BIGNUM *a, int bits)
 
 int ossl_bn_check_prime(const BIGNUM *w, int checks, BN_CTX *ctx,
                         int do_trial_division, BN_GENCB *cb);
-int ossl_bn_mask_bits_fixed_top(BIGNUM *a, int n);
 
 #endif
index fb3d7057dfd174a078127bfe5821e26ac0d3b786..b0b3d3ffe29edd1ff59d7eaa82725e5a77ac72be 100644 (file)
@@ -322,7 +322,7 @@ int BN_generate_dsa_nonce(BIGNUM *out, const BIGNUM *range,
             goto end;
 
         /* Clear out the top bits and rejection filter into range */
-        BN_set_flags(out, BN_FLG_CONSTTIME | BN_FLG_FIXED_TOP);
+        BN_set_flags(out, BN_FLG_CONSTTIME);
         ossl_bn_mask_bits_fixed_top(out, BN_num_bits(range));
 
         if (BN_ucmp(out, range) < 0) {
index 8fcb04324e6d593296f8a3e8b0e5888d35a5eeb4..a6976c71306e1e6389f63c81772fa247c64b7625 100644 (file)
@@ -156,6 +156,9 @@ int BN_rshift(BIGNUM *r, const BIGNUM *a, int n)
         return 0;
     }
 
+    bn_check_top(r);
+    bn_check_top(a);
+
     ret = bn_rshift_fixed_top(r, a, n);
 
     bn_correct_top(r);
@@ -177,9 +180,6 @@ int bn_rshift_fixed_top(BIGNUM *r, const BIGNUM *a, int n)
     BN_ULONG *t, *f;
     BN_ULONG l, m, mask;
 
-    bn_check_top(r);
-    bn_check_top(a);
-
     assert(n >= 0);
 
     nw = n / BN_BITS2;
index 00544d9d2509a6519e43d9b54d8fd17255a1b54a..a080a3b462cd037c2e2127f0e2ce14746c720803 100644 (file)
@@ -87,6 +87,8 @@ int bn_lshift_fixed_top(BIGNUM *r, const BIGNUM *a, int n);
 int bn_rshift_fixed_top(BIGNUM *r, const BIGNUM *a, int n);
 int bn_div_fixed_top(BIGNUM *dv, BIGNUM *rem, const BIGNUM *m,
                      const BIGNUM *d, BN_CTX *ctx);
+int ossl_bn_mask_bits_fixed_top(BIGNUM *a, int n);
+int ossl_bn_is_word_fixed_top(const BIGNUM *a, BN_ULONG w);
 
 #define BN_PRIMETEST_COMPOSITE                    0
 #define BN_PRIMETEST_COMPOSITE_WITH_FACTOR        1
index e8244cd57b7b86c984f8b70656967c33ee663fa1..f2572ded519984ecb76ec1610224cf0aa5a55883 100644 (file)
@@ -150,6 +150,17 @@ static ossl_inline BN_ULONG constant_time_lt_bn(BN_ULONG a, BN_ULONG b)
 {
     return constant_time_msb_bn(a ^ ((a ^ b) | ((a - b) ^ b)));
 }
+
+static ossl_inline BN_ULONG constant_time_is_zero_bn(BN_ULONG a)
+{
+    return constant_time_msb_bn(~a & (a - 1));
+}
+
+static ossl_inline BN_ULONG constant_time_eq_bn(BN_ULONG a,
+                                                BN_ULONG b)
+{
+    return constant_time_is_zero_bn(a ^ b);
+}
 #endif
 
 static ossl_inline unsigned int constant_time_ge(unsigned int a,