summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorMatt Caswell <matt@openssl.org>2014-08-22 18:04:19 +0200
committerEmilia Kasper <emilia@openssl.org>2014-08-27 19:50:36 +0200
commit4e5f9f8a9a10d0a6a23552ce1a640beab0c0f547 (patch)
tree69e3438cc3d8335a684afe086f2bd1cbd3024e87
parent9446ecfb3a59b744185c4265909c5a99705b3134 (diff)
RT3065: automatically generate a missing EC public key
When d2i_ECPrivateKey reads a private key with a missing (optional) public key, generate one automatically from the group and private key. Reviewed-by: Dr Stephen Henson <steve@openssl.org> (cherry picked from commit ed383f847156940e93f256fed78599873a4a9b28) Conflicts: doc/crypto/EC_KEY_new.pod
-rw-r--r--crypto/ec/ec_asn1.c27
1 files changed, 19 insertions, 8 deletions
diff --git a/crypto/ec/ec_asn1.c b/crypto/ec/ec_asn1.c
index 510295ef2b..26d6360454 100644
--- a/crypto/ec/ec_asn1.c
+++ b/crypto/ec/ec_asn1.c
@@ -1183,19 +1183,20 @@ EC_KEY *d2i_ECPrivateKey(EC_KEY **a, const unsigned char **in, long len)
goto err;
}
+ if (ret->pub_key)
+ EC_POINT_clear_free(ret->pub_key);
+ ret->pub_key = EC_POINT_new(ret->group);
+ if (ret->pub_key == NULL)
+ {
+ ECerr(EC_F_D2I_ECPRIVATEKEY, ERR_R_EC_LIB);
+ goto err;
+ }
+
if (priv_key->publicKey)
{
const unsigned char *pub_oct;
size_t pub_oct_len;
- if (ret->pub_key)
- EC_POINT_clear_free(ret->pub_key);
- ret->pub_key = EC_POINT_new(ret->group);
- if (ret->pub_key == NULL)
- {
- ECerr(EC_F_D2I_ECPRIVATEKEY, ERR_R_EC_LIB);
- goto err;
- }
pub_oct = M_ASN1_STRING_data(priv_key->publicKey);
pub_oct_len = M_ASN1_STRING_length(priv_key->publicKey);
/* save the point conversion form */
@@ -1207,6 +1208,16 @@ EC_KEY *d2i_ECPrivateKey(EC_KEY **a, const unsigned char **in, long len)
goto err;
}
}
+ else
+ {
+ if (!EC_POINT_mul(ret->group, ret->pub_key, ret->priv_key, NULL, NULL, NULL))
+ {
+ ECerr(EC_F_D2I_ECPRIVATEKEY, ERR_R_EC_LIB);
+ goto err;
+ }
+ /* Remember the original private-key-only encoding. */
+ ret->enc_flag |= EC_PKEY_NO_PUBKEY;
+ }
ok = 1;
err: