summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authortb <>2023-07-04 14:59:32 +0000
committertb <>2023-07-04 14:59:32 +0000
commitc6e12a51459163768f29eb01b0356016f3f5b793 (patch)
treecab8a358a80130c18566b00e2392af599047d40b
parent1f34fd05738e4ace8b7be84c9441adc6f601d5f8 (diff)
downloadopenbsd-c6e12a51459163768f29eb01b0356016f3f5b793.tar.gz
openbsd-c6e12a51459163768f29eb01b0356016f3f5b793.tar.bz2
openbsd-c6e12a51459163768f29eb01b0356016f3f5b793.zip
Clean up ECDSA verification
Use variable names that correspond more closely to the standard. Use an additional variable for s^-1 for readability. Annotate the code with the corresponding steps from FIPS 186-5. ok jsing
-rw-r--r--src/lib/libcrypto/ecdsa/ecs_ossl.c43
1 files changed, 29 insertions, 14 deletions
diff --git a/src/lib/libcrypto/ecdsa/ecs_ossl.c b/src/lib/libcrypto/ecdsa/ecs_ossl.c
index 685ba6e6c7..de51d3aa4a 100644
--- a/src/lib/libcrypto/ecdsa/ecs_ossl.c
+++ b/src/lib/libcrypto/ecdsa/ecs_ossl.c
@@ -1,4 +1,4 @@
1/* $OpenBSD: ecs_ossl.c,v 1.69 2023/07/04 14:57:05 tb Exp $ */ 1/* $OpenBSD: ecs_ossl.c,v 1.70 2023/07/04 14:59:32 tb Exp $ */
2/* 2/*
3 * Written by Nils Larsch for the OpenSSL project 3 * Written by Nils Larsch for the OpenSSL project
4 */ 4 */
@@ -506,6 +506,11 @@ ossl_ecdsa_verify(int type, const unsigned char *digest, int digest_len,
506 return ret; 506 return ret;
507} 507}
508 508
509/*
510 * FIPS 186-5, section 6.4.2: ECDSA signature verification.
511 * The caller provides us with the hash of the message, so has performed step 2.
512 */
513
509int 514int
510ossl_ecdsa_verify_sig(const unsigned char *digest, int digest_len, 515ossl_ecdsa_verify_sig(const unsigned char *digest, int digest_len,
511 const ECDSA_SIG *sig, EC_KEY *key) 516 const ECDSA_SIG *sig, EC_KEY *key)
@@ -515,7 +520,7 @@ ossl_ecdsa_verify_sig(const unsigned char *digest, int digest_len,
515 EC_POINT *point = NULL; 520 EC_POINT *point = NULL;
516 const BIGNUM *order; 521 const BIGNUM *order;
517 BN_CTX *ctx = NULL; 522 BN_CTX *ctx = NULL;
518 BIGNUM *u1, *u2, *e, *x; 523 BIGNUM *e, *sinv, *u, *v, *x;
519 int ret = -1; 524 int ret = -1;
520 525
521 if (key == NULL || sig == NULL) { 526 if (key == NULL || sig == NULL) {
@@ -538,11 +543,13 @@ ossl_ecdsa_verify_sig(const unsigned char *digest, int digest_len,
538 543
539 BN_CTX_start(ctx); 544 BN_CTX_start(ctx);
540 545
541 if ((u1 = BN_CTX_get(ctx)) == NULL) 546 if ((e = BN_CTX_get(ctx)) == NULL)
542 goto err; 547 goto err;
543 if ((u2 = BN_CTX_get(ctx)) == NULL) 548 if ((sinv = BN_CTX_get(ctx)) == NULL)
544 goto err; 549 goto err;
545 if ((e = BN_CTX_get(ctx)) == NULL) 550 if ((u = BN_CTX_get(ctx)) == NULL)
551 goto err;
552 if ((v = BN_CTX_get(ctx)) == NULL)
546 goto err; 553 goto err;
547 if ((x = BN_CTX_get(ctx)) == NULL) 554 if ((x = BN_CTX_get(ctx)) == NULL)
548 goto err; 555 goto err;
@@ -552,7 +559,7 @@ ossl_ecdsa_verify_sig(const unsigned char *digest, int digest_len,
552 goto err; 559 goto err;
553 } 560 }
554 561
555 /* Verify that r and s are in the range [1, order). */ 562 /* Step 1: verify that r and s are in the range [1, order). */
556 if (BN_cmp(sig->r, BN_value_one()) < 0 || BN_cmp(sig->r, order) >= 0) { 563 if (BN_cmp(sig->r, BN_value_one()) < 0 || BN_cmp(sig->r, order) >= 0) {
557 ECDSAerror(ECDSA_R_BAD_SIGNATURE); 564 ECDSAerror(ECDSA_R_BAD_SIGNATURE);
558 ret = 0; 565 ret = 0;
@@ -564,28 +571,35 @@ ossl_ecdsa_verify_sig(const unsigned char *digest, int digest_len,
564 goto err; 571 goto err;
565 } 572 }
566 573
574 /* Step 3: convert the hash into an integer. */
567 if (!ecdsa_prepare_digest(digest, digest_len, key, e)) 575 if (!ecdsa_prepare_digest(digest, digest_len, key, e))
568 goto err; 576 goto err;
569 577
570 if (BN_mod_inverse_ct(u2, sig->s, order, ctx) == NULL) { /* w = inv(s) */ 578 /* Step 4: compute the inverse of s modulo order. */
579 if (BN_mod_inverse_ct(sinv, sig->s, order, ctx) == NULL) {
571 ECDSAerror(ERR_R_BN_LIB); 580 ECDSAerror(ERR_R_BN_LIB);
572 goto err; 581 goto err;
573 } 582 }
574 if (!BN_mod_mul(u1, e, u2, order, ctx)) { /* u1 = ew */ 583 /* Step 5: compute u = s^-1 * e and v = s^-1 * r (modulo order). */
584 if (!BN_mod_mul(u, e, sinv, order, ctx)) {
575 ECDSAerror(ERR_R_BN_LIB); 585 ECDSAerror(ERR_R_BN_LIB);
576 goto err; 586 goto err;
577 } 587 }
578 if (!BN_mod_mul(u2, sig->r, u2, order, ctx)) { /* u2 = rw */ 588 if (!BN_mod_mul(v, sig->r, sinv, order, ctx)) {
579 ECDSAerror(ERR_R_BN_LIB); 589 ECDSAerror(ERR_R_BN_LIB);
580 goto err; 590 goto err;
581 } 591 }
582 592
583 /* Compute the x-coordinate of G * u1 + pub_key * u2. */ 593 /*
594 * Steps 6 and 7: compute R = G * u + pub_key * v = (x, y). Reject if
595 * it's the point at infinity - getting affine coordinates fails. Keep
596 * the x coordinate.
597 */
584 if ((point = EC_POINT_new(group)) == NULL) { 598 if ((point = EC_POINT_new(group)) == NULL) {
585 ECDSAerror(ERR_R_MALLOC_FAILURE); 599 ECDSAerror(ERR_R_MALLOC_FAILURE);
586 goto err; 600 goto err;
587 } 601 }
588 if (!EC_POINT_mul(group, point, u1, pub_key, u2, ctx)) { 602 if (!EC_POINT_mul(group, point, u, pub_key, v, ctx)) {
589 ECDSAerror(ERR_R_EC_LIB); 603 ECDSAerror(ERR_R_EC_LIB);
590 goto err; 604 goto err;
591 } 605 }
@@ -593,13 +607,14 @@ ossl_ecdsa_verify_sig(const unsigned char *digest, int digest_len,
593 ECDSAerror(ERR_R_EC_LIB); 607 ECDSAerror(ERR_R_EC_LIB);
594 goto err; 608 goto err;
595 } 609 }
596 if (!BN_nnmod(u1, x, order, ctx)) { 610 /* Step 8: convert x to a number in [0, order). */
611 if (!BN_nnmod(x, x, order, ctx)) {
597 ECDSAerror(ERR_R_BN_LIB); 612 ECDSAerror(ERR_R_BN_LIB);
598 goto err; 613 goto err;
599 } 614 }
600 615
601 /* If the signature is correct, the x-coordinate is equal to sig->r. */ 616 /* Step 9: the signature is valid iff the x-coordinate is equal to r. */
602 ret = (BN_cmp(u1, sig->r) == 0); 617 ret = (BN_cmp(x, sig->r) == 0);
603 618
604 err: 619 err:
605 BN_CTX_end(ctx); 620 BN_CTX_end(ctx);