summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorinoguchi <>2018-03-12 13:14:21 +0000
committerinoguchi <>2018-03-12 13:14:21 +0000
commit7232fedecfd1782f7a08e49519de4e1c7990edb6 (patch)
tree70fcd8bdcb756233389e3bf8967307f6b2d3072c
parent52e498cc6e72760b900f1eda649a36103523e200 (diff)
downloadopenbsd-7232fedecfd1782f7a08e49519de4e1c7990edb6.tar.gz
openbsd-7232fedecfd1782f7a08e49519de4e1c7990edb6.tar.bz2
openbsd-7232fedecfd1782f7a08e49519de4e1c7990edb6.zip
Fix for processing of EC public key
Prevents segmentation fault while reading EC private key without public key. Generates missing EC public key when reading EC private key. Refer to these OpenSSL commits: 1f2b943254ce590867717375e4f364860a9b7154 2083f7c465d07867dd9867b8742bb71c03d1f203 Reported on GitHub https://github.com/libressl-portable/portable/issues/395 by Anton Bukov (@k06a) . ok beck@
-rw-r--r--src/lib/libcrypto/ec/ec_ameth.c14
-rw-r--r--src/lib/libcrypto/ec/ec_asn1.c28
2 files changed, 27 insertions, 15 deletions
diff --git a/src/lib/libcrypto/ec/ec_ameth.c b/src/lib/libcrypto/ec/ec_ameth.c
index 8d0cdb733b..0932f1e3c9 100644
--- a/src/lib/libcrypto/ec/ec_ameth.c
+++ b/src/lib/libcrypto/ec/ec_ameth.c
@@ -1,4 +1,4 @@
1/* $OpenBSD: ec_ameth.c,v 1.18 2017/01/29 17:49:23 beck Exp $ */ 1/* $OpenBSD: ec_ameth.c,v 1.19 2018/03/12 13:14:21 inoguchi Exp $ */
2/* Written by Dr Stephen N Henson (steve@openssl.org) for the OpenSSL 2/* Written by Dr Stephen N Henson (steve@openssl.org) for the OpenSSL
3 * project 2006. 3 * project 2006.
4 */ 4 */
@@ -433,13 +433,15 @@ do_EC_KEY_print(BIO * bp, const EC_KEY * x, int off, int ktype)
433 } 433 }
434 if (ktype > 0) { 434 if (ktype > 0) {
435 public_key = EC_KEY_get0_public_key(x); 435 public_key = EC_KEY_get0_public_key(x);
436 if ((pub_key = EC_POINT_point2bn(group, public_key, 436 if (public_key != NULL) {
437 if ((pub_key = EC_POINT_point2bn(group, public_key,
437 EC_KEY_get_conv_form(x), NULL, ctx)) == NULL) { 438 EC_KEY_get_conv_form(x), NULL, ctx)) == NULL) {
438 reason = ERR_R_EC_LIB; 439 reason = ERR_R_EC_LIB;
439 goto err; 440 goto err;
441 }
442 if (pub_key)
443 buf_len = (size_t) BN_num_bytes(pub_key);
440 } 444 }
441 if (pub_key)
442 buf_len = (size_t) BN_num_bytes(pub_key);
443 } 445 }
444 if (ktype == 2) { 446 if (ktype == 2) {
445 priv_key = EC_KEY_get0_private_key(x); 447 priv_key = EC_KEY_get0_private_key(x);
diff --git a/src/lib/libcrypto/ec/ec_asn1.c b/src/lib/libcrypto/ec/ec_asn1.c
index b64b7e14d3..381addfcf6 100644
--- a/src/lib/libcrypto/ec/ec_asn1.c
+++ b/src/lib/libcrypto/ec/ec_asn1.c
@@ -1,4 +1,4 @@
1/* $OpenBSD: ec_asn1.c,v 1.24 2017/05/26 16:32:14 jsing Exp $ */ 1/* $OpenBSD: ec_asn1.c,v 1.25 2018/03/12 13:14:21 inoguchi Exp $ */
2/* 2/*
3 * Written by Nils Larsch for the OpenSSL project. 3 * Written by Nils Larsch for the OpenSSL project.
4 */ 4 */
@@ -1380,17 +1380,18 @@ d2i_ECPrivateKey(EC_KEY ** a, const unsigned char **in, long len)
1380 goto err; 1380 goto err;
1381 } 1381 }
1382 1382
1383 if (ret->pub_key)
1384 EC_POINT_clear_free(ret->pub_key);
1385 ret->pub_key = EC_POINT_new(ret->group);
1386 if (ret->pub_key == NULL) {
1387 ECerror(ERR_R_EC_LIB);
1388 goto err;
1389 }
1390
1383 if (priv_key->publicKey) { 1391 if (priv_key->publicKey) {
1384 const unsigned char *pub_oct; 1392 const unsigned char *pub_oct;
1385 size_t pub_oct_len; 1393 size_t pub_oct_len;
1386 1394
1387 EC_POINT_clear_free(ret->pub_key);
1388 ret->pub_key = EC_POINT_new(ret->group);
1389 if (ret->pub_key == NULL) {
1390 ECerror(ERR_R_EC_LIB);
1391 goto err;
1392 }
1393
1394 pub_oct = ASN1_STRING_data(priv_key->publicKey); 1395 pub_oct = ASN1_STRING_data(priv_key->publicKey);
1395 pub_oct_len = ASN1_STRING_length(priv_key->publicKey); 1396 pub_oct_len = ASN1_STRING_length(priv_key->publicKey);
1396 if (pub_oct == NULL || pub_oct_len <= 0) { 1397 if (pub_oct == NULL || pub_oct_len <= 0) {
@@ -1405,6 +1406,14 @@ d2i_ECPrivateKey(EC_KEY ** a, const unsigned char **in, long len)
1405 ECerror(ERR_R_EC_LIB); 1406 ECerror(ERR_R_EC_LIB);
1406 goto err; 1407 goto err;
1407 } 1408 }
1409 } else {
1410 if (!EC_POINT_mul(ret->group, ret->pub_key, ret->priv_key,
1411 NULL, NULL, NULL)) {
1412 ECerror(ERR_R_EC_LIB);
1413 goto err;
1414 }
1415 /* Remember the original private-key-only encoding. */
1416 ret->enc_flag |= EC_PKEY_NO_PUBKEY;
1408 } 1417 }
1409 1418
1410 EC_PRIVATEKEY_free(priv_key); 1419 EC_PRIVATEKEY_free(priv_key);
@@ -1429,7 +1438,8 @@ i2d_ECPrivateKey(EC_KEY * a, unsigned char **out)
1429 size_t buf_len = 0, tmp_len; 1438 size_t buf_len = 0, tmp_len;
1430 EC_PRIVATEKEY *priv_key = NULL; 1439 EC_PRIVATEKEY *priv_key = NULL;
1431 1440
1432 if (a == NULL || a->group == NULL || a->priv_key == NULL) { 1441 if (a == NULL || a->group == NULL || a->priv_key == NULL ||
1442 (!(a->enc_flag & EC_PKEY_NO_PUBKEY) && a->pub_key == NULL)) {
1433 ECerror(ERR_R_PASSED_NULL_PARAMETER); 1443 ECerror(ERR_R_PASSED_NULL_PARAMETER);
1434 goto err; 1444 goto err;
1435 } 1445 }