diff options
author | tb <> | 2025-01-06 11:59:02 +0000 |
---|---|---|
committer | tb <> | 2025-01-06 11:59:02 +0000 |
commit | 52f13317baa428db8efa6305c98bcca1c8d6b93e (patch) | |
tree | 0ee2fc6379d14a64692dcf7f36e8c5180d72a607 | |
parent | 1d5dc8af4f29575850958ce2ca4c6ffcc27dece5 (diff) | |
download | openbsd-52f13317baa428db8efa6305c98bcca1c8d6b93e.tar.gz openbsd-52f13317baa428db8efa6305c98bcca1c8d6b93e.tar.bz2 openbsd-52f13317baa428db8efa6305c98bcca1c8d6b93e.zip |
Stop caching one in the Montgomery domain
This is only used by ec_points_make_affine(), which is only used by the
wNAF multiplication, which is only used by ECDSA. We can afford computing
that one once per ECDSA verification given the cost of the rest of this.
Thus, the field_set_to_one() member disappears from the EC_METHOD and the
mont_one member disappears from EC_GROUP and with it all the complications
when setting/copying/freeing the group.
ok jsing
-rw-r--r-- | src/lib/libcrypto/ec/ec_lib.c | 6 | ||||
-rw-r--r-- | src/lib/libcrypto/ec/ec_local.h | 6 | ||||
-rw-r--r-- | src/lib/libcrypto/ec/ecp_methods.c | 60 |
3 files changed, 16 insertions, 56 deletions
diff --git a/src/lib/libcrypto/ec/ec_lib.c b/src/lib/libcrypto/ec/ec_lib.c index 03c6f3aa90..170bdedc57 100644 --- a/src/lib/libcrypto/ec/ec_lib.c +++ b/src/lib/libcrypto/ec/ec_lib.c | |||
@@ -1,4 +1,4 @@ | |||
1 | /* $OpenBSD: ec_lib.c,v 1.95 2025/01/06 10:56:46 tb Exp $ */ | 1 | /* $OpenBSD: ec_lib.c,v 1.96 2025/01/06 11:59:02 tb Exp $ */ |
2 | /* | 2 | /* |
3 | * Originally written by Bodo Moeller for the OpenSSL project. | 3 | * Originally written by Bodo Moeller for the OpenSSL project. |
4 | */ | 4 | */ |
@@ -107,8 +107,7 @@ EC_GROUP_new(const EC_METHOD *meth) | |||
107 | goto err; | 107 | goto err; |
108 | 108 | ||
109 | /* | 109 | /* |
110 | * generator and seed are optional. mont_ctx, mont_one are only for | 110 | * generator, seed and mont_ctx are optional. |
111 | * curves using EC_GFp_mont_method() | ||
112 | */ | 111 | */ |
113 | 112 | ||
114 | return group; | 113 | return group; |
@@ -131,7 +130,6 @@ EC_GROUP_free(EC_GROUP *group) | |||
131 | BN_free(group->b); | 130 | BN_free(group->b); |
132 | 131 | ||
133 | BN_MONT_CTX_free(group->mont_ctx); | 132 | BN_MONT_CTX_free(group->mont_ctx); |
134 | BN_free(group->mont_one); | ||
135 | 133 | ||
136 | EC_POINT_free(group->generator); | 134 | EC_POINT_free(group->generator); |
137 | BN_free(group->order); | 135 | BN_free(group->order); |
diff --git a/src/lib/libcrypto/ec/ec_local.h b/src/lib/libcrypto/ec/ec_local.h index 2bddaddd8a..1b7ca5b645 100644 --- a/src/lib/libcrypto/ec/ec_local.h +++ b/src/lib/libcrypto/ec/ec_local.h | |||
@@ -1,4 +1,4 @@ | |||
1 | /* $OpenBSD: ec_local.h,v 1.47 2025/01/06 10:56:46 tb Exp $ */ | 1 | /* $OpenBSD: ec_local.h,v 1.48 2025/01/06 11:59:02 tb Exp $ */ |
2 | /* | 2 | /* |
3 | * Originally written by Bodo Moeller for the OpenSSL project. | 3 | * Originally written by Bodo Moeller for the OpenSSL project. |
4 | */ | 4 | */ |
@@ -143,7 +143,6 @@ struct ec_method_st { | |||
143 | int (*field_decode)(const EC_GROUP *, BIGNUM *r, const BIGNUM *a, | 143 | int (*field_decode)(const EC_GROUP *, BIGNUM *r, const BIGNUM *a, |
144 | BN_CTX *); | 144 | BN_CTX *); |
145 | 145 | ||
146 | int (*field_set_to_one)(const EC_GROUP *, BIGNUM *r, BN_CTX *); | ||
147 | int (*blind_coordinates)(const EC_GROUP *group, EC_POINT *p, | 146 | int (*blind_coordinates)(const EC_GROUP *group, EC_POINT *p, |
148 | BN_CTX *ctx); | 147 | BN_CTX *ctx); |
149 | } /* EC_METHOD */; | 148 | } /* EC_METHOD */; |
@@ -184,9 +183,8 @@ struct ec_group_st { | |||
184 | /* Enables optimized point arithmetics for special case. */ | 183 | /* Enables optimized point arithmetics for special case. */ |
185 | int a_is_minus3; | 184 | int a_is_minus3; |
186 | 185 | ||
187 | /* Montgomery context and values used by EC_GFp_mont_method. */ | 186 | /* Montgomery context used by EC_GFp_mont_method. */ |
188 | BN_MONT_CTX *mont_ctx; | 187 | BN_MONT_CTX *mont_ctx; |
189 | BIGNUM *mont_one; | ||
190 | } /* EC_GROUP */; | 188 | } /* EC_GROUP */; |
191 | 189 | ||
192 | struct ec_key_st { | 190 | struct ec_key_st { |
diff --git a/src/lib/libcrypto/ec/ecp_methods.c b/src/lib/libcrypto/ec/ecp_methods.c index 7bdeb351da..2297b07175 100644 --- a/src/lib/libcrypto/ec/ecp_methods.c +++ b/src/lib/libcrypto/ec/ecp_methods.c | |||
@@ -1,4 +1,4 @@ | |||
1 | /* $OpenBSD: ecp_methods.c,v 1.19 2025/01/06 10:56:46 tb Exp $ */ | 1 | /* $OpenBSD: ecp_methods.c,v 1.20 2025/01/06 11:59:02 tb Exp $ */ |
2 | /* Includes code written by Lenka Fibikova <fibikova@exp-math.uni-essen.de> | 2 | /* Includes code written by Lenka Fibikova <fibikova@exp-math.uni-essen.de> |
3 | * for the OpenSSL project. | 3 | * for the OpenSSL project. |
4 | * Includes code written by Bodo Moeller for the OpenSSL project. | 4 | * Includes code written by Bodo Moeller for the OpenSSL project. |
@@ -1003,7 +1003,7 @@ ec_points_make_affine(const EC_GROUP *group, size_t num, EC_POINT *points[], | |||
1003 | BN_CTX *ctx) | 1003 | BN_CTX *ctx) |
1004 | { | 1004 | { |
1005 | BIGNUM **prod_Z = NULL; | 1005 | BIGNUM **prod_Z = NULL; |
1006 | BIGNUM *tmp, *tmp_Z; | 1006 | BIGNUM *one, *tmp, *tmp_Z; |
1007 | size_t i; | 1007 | size_t i; |
1008 | int ret = 0; | 1008 | int ret = 0; |
1009 | 1009 | ||
@@ -1012,11 +1012,16 @@ ec_points_make_affine(const EC_GROUP *group, size_t num, EC_POINT *points[], | |||
1012 | 1012 | ||
1013 | BN_CTX_start(ctx); | 1013 | BN_CTX_start(ctx); |
1014 | 1014 | ||
1015 | if ((one = BN_CTX_get(ctx)) == NULL) | ||
1016 | goto err; | ||
1015 | if ((tmp = BN_CTX_get(ctx)) == NULL) | 1017 | if ((tmp = BN_CTX_get(ctx)) == NULL) |
1016 | goto err; | 1018 | goto err; |
1017 | if ((tmp_Z = BN_CTX_get(ctx)) == NULL) | 1019 | if ((tmp_Z = BN_CTX_get(ctx)) == NULL) |
1018 | goto err; | 1020 | goto err; |
1019 | 1021 | ||
1022 | if (!ec_encode_scalar(group, one, BN_value_one(), ctx)) | ||
1023 | goto err; | ||
1024 | |||
1020 | if ((prod_Z = calloc(num, sizeof *prod_Z)) == NULL) | 1025 | if ((prod_Z = calloc(num, sizeof *prod_Z)) == NULL) |
1021 | goto err; | 1026 | goto err; |
1022 | for (i = 0; i < num; i++) { | 1027 | for (i = 0; i < num; i++) { |
@@ -1033,13 +1038,8 @@ ec_points_make_affine(const EC_GROUP *group, size_t num, EC_POINT *points[], | |||
1033 | if (!bn_copy(prod_Z[0], points[0]->Z)) | 1038 | if (!bn_copy(prod_Z[0], points[0]->Z)) |
1034 | goto err; | 1039 | goto err; |
1035 | } else { | 1040 | } else { |
1036 | if (group->meth->field_set_to_one != NULL) { | 1041 | if (!bn_copy(prod_Z[0], one)) |
1037 | if (!group->meth->field_set_to_one(group, prod_Z[0], ctx)) | 1042 | goto err; |
1038 | goto err; | ||
1039 | } else { | ||
1040 | if (!BN_one(prod_Z[0])) | ||
1041 | goto err; | ||
1042 | } | ||
1043 | } | 1043 | } |
1044 | 1044 | ||
1045 | for (i = 1; i < num; i++) { | 1045 | for (i = 1; i < num; i++) { |
@@ -1118,13 +1118,8 @@ ec_points_make_affine(const EC_GROUP *group, size_t num, EC_POINT *points[], | |||
1118 | if (!group->meth->field_mul(group, p->Y, p->Y, tmp, ctx)) | 1118 | if (!group->meth->field_mul(group, p->Y, p->Y, tmp, ctx)) |
1119 | goto err; | 1119 | goto err; |
1120 | 1120 | ||
1121 | if (group->meth->field_set_to_one != NULL) { | 1121 | if (!bn_copy(p->Z, one)) |
1122 | if (!group->meth->field_set_to_one(group, p->Z, ctx)) | 1122 | goto err; |
1123 | goto err; | ||
1124 | } else { | ||
1125 | if (!BN_one(p->Z)) | ||
1126 | goto err; | ||
1127 | } | ||
1128 | p->Z_is_one = 1; | 1123 | p->Z_is_one = 1; |
1129 | } | 1124 | } |
1130 | 1125 | ||
@@ -1458,9 +1453,6 @@ ec_mont_group_clear(EC_GROUP *group) | |||
1458 | { | 1453 | { |
1459 | BN_MONT_CTX_free(group->mont_ctx); | 1454 | BN_MONT_CTX_free(group->mont_ctx); |
1460 | group->mont_ctx = NULL; | 1455 | group->mont_ctx = NULL; |
1461 | |||
1462 | BN_free(group->mont_one); | ||
1463 | group->mont_one = NULL; | ||
1464 | } | 1456 | } |
1465 | 1457 | ||
1466 | static int | 1458 | static int |
@@ -1478,11 +1470,7 @@ ec_mont_group_copy(EC_GROUP *dest, const EC_GROUP *src) | |||
1478 | if (!BN_MONT_CTX_copy(dest->mont_ctx, src->mont_ctx)) | 1470 | if (!BN_MONT_CTX_copy(dest->mont_ctx, src->mont_ctx)) |
1479 | goto err; | 1471 | goto err; |
1480 | } | 1472 | } |
1481 | if (src->mont_one != NULL) { | 1473 | |
1482 | dest->mont_one = BN_dup(src->mont_one); | ||
1483 | if (dest->mont_one == NULL) | ||
1484 | goto err; | ||
1485 | } | ||
1486 | return 1; | 1474 | return 1; |
1487 | 1475 | ||
1488 | err: | 1476 | err: |
@@ -1498,7 +1486,6 @@ ec_mont_group_set_curve(EC_GROUP *group, const BIGNUM *p, const BIGNUM *a, | |||
1498 | const BIGNUM *b, BN_CTX *ctx) | 1486 | const BIGNUM *b, BN_CTX *ctx) |
1499 | { | 1487 | { |
1500 | BN_MONT_CTX *mont = NULL; | 1488 | BN_MONT_CTX *mont = NULL; |
1501 | BIGNUM *one = NULL; | ||
1502 | int ret = 0; | 1489 | int ret = 0; |
1503 | 1490 | ||
1504 | ec_mont_group_clear(group); | 1491 | ec_mont_group_clear(group); |
@@ -1510,16 +1497,8 @@ ec_mont_group_set_curve(EC_GROUP *group, const BIGNUM *p, const BIGNUM *a, | |||
1510 | ECerror(ERR_R_BN_LIB); | 1497 | ECerror(ERR_R_BN_LIB); |
1511 | goto err; | 1498 | goto err; |
1512 | } | 1499 | } |
1513 | one = BN_new(); | ||
1514 | if (one == NULL) | ||
1515 | goto err; | ||
1516 | if (!BN_to_montgomery(one, BN_value_one(), mont, ctx)) | ||
1517 | goto err; | ||
1518 | |||
1519 | group->mont_ctx = mont; | 1500 | group->mont_ctx = mont; |
1520 | mont = NULL; | 1501 | mont = NULL; |
1521 | group->mont_one = one; | ||
1522 | one = NULL; | ||
1523 | 1502 | ||
1524 | ret = ec_group_set_curve(group, p, a, b, ctx); | 1503 | ret = ec_group_set_curve(group, p, a, b, ctx); |
1525 | if (!ret) | 1504 | if (!ret) |
@@ -1527,7 +1506,6 @@ ec_mont_group_set_curve(EC_GROUP *group, const BIGNUM *p, const BIGNUM *a, | |||
1527 | 1506 | ||
1528 | err: | 1507 | err: |
1529 | BN_MONT_CTX_free(mont); | 1508 | BN_MONT_CTX_free(mont); |
1530 | BN_free(one); | ||
1531 | 1509 | ||
1532 | return ret; | 1510 | return ret; |
1533 | } | 1511 | } |
@@ -1576,19 +1554,6 @@ ec_mont_field_decode(const EC_GROUP *group, BIGNUM *r, const BIGNUM *a, | |||
1576 | return BN_from_montgomery(r, a, group->mont_ctx, ctx); | 1554 | return BN_from_montgomery(r, a, group->mont_ctx, ctx); |
1577 | } | 1555 | } |
1578 | 1556 | ||
1579 | static int | ||
1580 | ec_mont_field_set_to_one(const EC_GROUP *group, BIGNUM *r, BN_CTX *ctx) | ||
1581 | { | ||
1582 | if (group->mont_one == NULL) { | ||
1583 | ECerror(EC_R_NOT_INITIALIZED); | ||
1584 | return 0; | ||
1585 | } | ||
1586 | if (!bn_copy(r, group->mont_one)) | ||
1587 | return 0; | ||
1588 | |||
1589 | return 1; | ||
1590 | } | ||
1591 | |||
1592 | static const EC_METHOD ec_GFp_simple_method = { | 1557 | static const EC_METHOD ec_GFp_simple_method = { |
1593 | .field_type = NID_X9_62_prime_field, | 1558 | .field_type = NID_X9_62_prime_field, |
1594 | .group_copy = ec_group_copy, | 1559 | .group_copy = ec_group_copy, |
@@ -1647,7 +1612,6 @@ static const EC_METHOD ec_GFp_mont_method = { | |||
1647 | .field_sqr = ec_mont_field_sqr, | 1612 | .field_sqr = ec_mont_field_sqr, |
1648 | .field_encode = ec_mont_field_encode, | 1613 | .field_encode = ec_mont_field_encode, |
1649 | .field_decode = ec_mont_field_decode, | 1614 | .field_decode = ec_mont_field_decode, |
1650 | .field_set_to_one = ec_mont_field_set_to_one, | ||
1651 | .blind_coordinates = ec_blind_coordinates, | 1615 | .blind_coordinates = ec_blind_coordinates, |
1652 | }; | 1616 | }; |
1653 | 1617 | ||