提交 9ee1c838 编写于 作者: R Richard Levitte

Memory leaks fix. There seems to be more in other parts of OpenSSL...

上级 88364bc2
...@@ -373,21 +373,22 @@ int MAIN(int argc, char **argv) ...@@ -373,21 +373,22 @@ int MAIN(int argc, char **argv)
} }
if (export_cert) { if (export_cert) {
EVP_PKEY *key; EVP_PKEY *key = NULL;
STACK_OF(PKCS12_SAFEBAG) *bags; STACK_OF(PKCS12_SAFEBAG) *bags = NULL;
STACK_OF(PKCS7) *safes; STACK_OF(PKCS7) *safes = NULL;
PKCS12_SAFEBAG *bag; PKCS12_SAFEBAG *bag = NULL;
PKCS8_PRIV_KEY_INFO *p8; PKCS8_PRIV_KEY_INFO *p8 = NULL;
PKCS7 *authsafe; PKCS7 *authsafe = NULL;
X509 *ucert = NULL; X509 *ucert = NULL;
STACK_OF(X509) *certs=NULL; STACK_OF(X509) *certs=NULL;
char *catmp; char *catmp = NULL;
int i; int i;
unsigned char keyid[EVP_MAX_MD_SIZE]; unsigned char keyid[EVP_MAX_MD_SIZE];
unsigned int keyidlen = 0; unsigned int keyidlen = 0;
#ifdef CRYPTO_MDEBUG #ifdef CRYPTO_MDEBUG
CRYPTO_push_info("process -export_cert"); CRYPTO_push_info("process -export_cert");
CRYPTO_push_info("reading private key");
#endif #endif
key = PEM_read_bio_PrivateKey(inkey ? inkey : in, NULL, NULL, passin); key = PEM_read_bio_PrivateKey(inkey ? inkey : in, NULL, NULL, passin);
if (!inkey) (void) BIO_reset(in); if (!inkey) (void) BIO_reset(in);
...@@ -395,18 +396,28 @@ int MAIN(int argc, char **argv) ...@@ -395,18 +396,28 @@ int MAIN(int argc, char **argv)
if (!key) { if (!key) {
BIO_printf (bio_err, "Error loading private key\n"); BIO_printf (bio_err, "Error loading private key\n");
ERR_print_errors(bio_err); ERR_print_errors(bio_err);
goto end; goto export_end;
} }
#ifdef CRYPTO_MDEBUG
CRYPTO_pop_info();
CRYPTO_push_info("reading certs from input");
#endif
certs = sk_X509_new(NULL); certs = sk_X509_new(NULL);
/* Load in all certs in input file */ /* Load in all certs in input file */
if(!cert_load(in, certs)) { if(!cert_load(in, certs)) {
BIO_printf(bio_err, "Error loading certificates from input\n"); BIO_printf(bio_err, "Error loading certificates from input\n");
ERR_print_errors(bio_err); ERR_print_errors(bio_err);
goto end; goto export_end;
} }
#ifdef CRYPTO_MDEBUG
CRYPTO_pop_info();
CRYPTO_push_info("reading certs from input 2");
#endif
for(i = 0; i < sk_X509_num(certs); i++) { for(i = 0; i < sk_X509_num(certs); i++) {
ucert = sk_X509_value(certs, i); ucert = sk_X509_value(certs, i);
if(X509_check_private_key(ucert, key)) { if(X509_check_private_key(ucert, key)) {
...@@ -414,12 +425,16 @@ int MAIN(int argc, char **argv) ...@@ -414,12 +425,16 @@ int MAIN(int argc, char **argv)
break; break;
} }
} }
if(!keyidlen) { if(!keyidlen) {
BIO_printf(bio_err, "No certificate matches private key\n"); BIO_printf(bio_err, "No certificate matches private key\n");
goto end; goto export_end;
} }
#ifdef CRYPTO_MDEBUG
CRYPTO_pop_info();
CRYPTO_push_info("reading certs from certfile");
#endif
bags = sk_PKCS12_SAFEBAG_new (NULL); bags = sk_PKCS12_SAFEBAG_new (NULL);
/* Add any more certificates asked for */ /* Add any more certificates asked for */
...@@ -427,11 +442,16 @@ int MAIN(int argc, char **argv) ...@@ -427,11 +442,16 @@ int MAIN(int argc, char **argv)
if(!cert_load(certsin, certs)) { if(!cert_load(certsin, certs)) {
BIO_printf(bio_err, "Error loading certificates from certfile\n"); BIO_printf(bio_err, "Error loading certificates from certfile\n");
ERR_print_errors(bio_err); ERR_print_errors(bio_err);
goto end; goto export_end;
} }
BIO_free(certsin); BIO_free(certsin);
} }
#ifdef CRYPTO_MDEBUG
CRYPTO_pop_info();
CRYPTO_push_info("building chain");
#endif
/* If chaining get chain from user cert */ /* If chaining get chain from user cert */
if (chain) { if (chain) {
int vret; int vret;
...@@ -440,24 +460,32 @@ int MAIN(int argc, char **argv) ...@@ -440,24 +460,32 @@ int MAIN(int argc, char **argv)
if (!store) if (!store)
{ {
BIO_printf (bio_err, "Memory allocation error\n"); BIO_printf (bio_err, "Memory allocation error\n");
goto end; goto export_end;
} }
if (!X509_STORE_load_locations(store, CAfile, CApath)) if (!X509_STORE_load_locations(store, CAfile, CApath))
X509_STORE_set_default_paths (store); X509_STORE_set_default_paths (store);
vret = get_cert_chain (ucert, store, &chain2); vret = get_cert_chain (ucert, store, &chain2);
X509_STORE_free(store);
if (!vret) {
/* Exclude verified certificate */
for (i = 1; i < sk_X509_num (chain2) ; i++)
sk_X509_push(certs, sk_X509_value (chain2, i));
}
sk_X509_free(chain2);
if (vret) { if (vret) {
BIO_printf (bio_err, "Error %s getting chain.\n", BIO_printf (bio_err, "Error %s getting chain.\n",
X509_verify_cert_error_string(vret)); X509_verify_cert_error_string(vret));
goto end; goto export_end;
} }
/* Exclude verified certificate */
for (i = 1; i < sk_X509_num (chain2) ; i++)
sk_X509_push(certs, sk_X509_value (chain2, i));
sk_X509_free(chain2);
} }
#ifdef CRYPTO_MDEBUG
CRYPTO_pop_info();
CRYPTO_push_info("building bags");
#endif
/* We now have loads of certificates: include them all */ /* We now have loads of certificates: include them all */
for(i = 0; i < sk_X509_num(certs); i++) { for(i = 0; i < sk_X509_num(certs); i++) {
X509 *cert = NULL; X509 *cert = NULL;
...@@ -472,54 +500,95 @@ int MAIN(int argc, char **argv) ...@@ -472,54 +500,95 @@ int MAIN(int argc, char **argv)
sk_PKCS12_SAFEBAG_push(bags, bag); sk_PKCS12_SAFEBAG_push(bags, bag);
} }
sk_X509_pop_free(certs, X509_free); sk_X509_pop_free(certs, X509_free);
if (canames) sk_free(canames); certs = NULL;
#ifdef CRYPTO_MDEBUG
CRYPTO_pop_info();
CRYPTO_push_info("encrypting bags");
#endif
if(!noprompt && if(!noprompt &&
EVP_read_pw_string(pass, 50, "Enter Export Password:", 1)) { EVP_read_pw_string(pass, 50, "Enter Export Password:", 1)) {
BIO_printf (bio_err, "Can't read Password\n"); BIO_printf (bio_err, "Can't read Password\n");
goto end; goto export_end;
} }
if (!twopass) strcpy(macpass, pass); if (!twopass) strcpy(macpass, pass);
/* Turn certbags into encrypted authsafe */ /* Turn certbags into encrypted authsafe */
authsafe = PKCS12_pack_p7encdata(cert_pbe, cpass, -1, NULL, 0, authsafe = PKCS12_pack_p7encdata(cert_pbe, cpass, -1, NULL, 0,
iter, bags); iter, bags);
sk_PKCS12_SAFEBAG_pop_free(bags, PKCS12_SAFEBAG_free); sk_PKCS12_SAFEBAG_pop_free(bags, PKCS12_SAFEBAG_free);
bags = NULL;
if (!authsafe) { if (!authsafe) {
ERR_print_errors (bio_err); ERR_print_errors (bio_err);
goto end; goto export_end;
} }
safes = sk_PKCS7_new (NULL); safes = sk_PKCS7_new (NULL);
sk_PKCS7_push (safes, authsafe); sk_PKCS7_push (safes, authsafe);
#ifdef CRYPTO_MDEBUG
CRYPTO_pop_info();
CRYPTO_push_info("building shrouded key bag");
#endif
/* Make a shrouded key bag */ /* Make a shrouded key bag */
p8 = EVP_PKEY2PKCS8 (key); p8 = EVP_PKEY2PKCS8 (key);
EVP_PKEY_free(key);
if(keytype) PKCS8_add_keyusage(p8, keytype); if(keytype) PKCS8_add_keyusage(p8, keytype);
bag = PKCS12_MAKE_SHKEYBAG(key_pbe, cpass, -1, NULL, 0, iter, p8); bag = PKCS12_MAKE_SHKEYBAG(key_pbe, cpass, -1, NULL, 0, iter, p8);
PKCS8_PRIV_KEY_INFO_free(p8); PKCS8_PRIV_KEY_INFO_free(p8);
p8 = NULL;
if (name) PKCS12_add_friendlyname (bag, name, -1); if (name) PKCS12_add_friendlyname (bag, name, -1);
PKCS12_add_localkeyid (bag, keyid, keyidlen); PKCS12_add_localkeyid (bag, keyid, keyidlen);
bags = sk_PKCS12_SAFEBAG_new(NULL); bags = sk_PKCS12_SAFEBAG_new(NULL);
sk_PKCS12_SAFEBAG_push (bags, bag); sk_PKCS12_SAFEBAG_push (bags, bag);
#ifdef CRYPTO_MDEBUG
CRYPTO_pop_info();
CRYPTO_push_info("encrypting shrouded key bag");
#endif
/* Turn it into unencrypted safe bag */ /* Turn it into unencrypted safe bag */
authsafe = PKCS12_pack_p7data (bags); authsafe = PKCS12_pack_p7data (bags);
sk_PKCS12_SAFEBAG_pop_free(bags, PKCS12_SAFEBAG_free); sk_PKCS12_SAFEBAG_pop_free(bags, PKCS12_SAFEBAG_free);
bags = NULL;
sk_PKCS7_push (safes, authsafe); sk_PKCS7_push (safes, authsafe);
#ifdef CRYPTO_MDEBUG
CRYPTO_pop_info();
CRYPTO_push_info("building pkcs12");
#endif
p12 = PKCS12_init (NID_pkcs7_data); p12 = PKCS12_init (NID_pkcs7_data);
M_PKCS12_pack_authsafes (p12, safes); M_PKCS12_pack_authsafes (p12, safes);
sk_PKCS7_pop_free(safes, PKCS7_free); sk_PKCS7_pop_free(safes, PKCS7_free);
safes = NULL;
PKCS12_set_mac (p12, mpass, -1, NULL, 0, maciter, NULL); PKCS12_set_mac (p12, mpass, -1, NULL, 0, maciter, NULL);
#ifdef CRYPTO_MDEBUG
CRYPTO_pop_info();
CRYPTO_push_info("writing pkcs12");
#endif
i2d_PKCS12_bio (out, p12); i2d_PKCS12_bio (out, p12);
ret = 0; ret = 0;
export_end:
#ifdef CRYPTO_MDEBUG
CRYPTO_pop_info();
CRYPTO_pop_info();
CRYPTO_push_info("process -export_cert: freeing");
#endif
if (key) EVP_PKEY_free(key);
if (certs) sk_X509_pop_free(certs, X509_free);
if (safes) sk_PKCS7_pop_free(safes, PKCS7_free);
if (bags) sk_PKCS12_SAFEBAG_pop_free(bags, PKCS12_SAFEBAG_free);
#ifdef CRYPTO_MDEBUG #ifdef CRYPTO_MDEBUG
CRYPTO_pop_info(); CRYPTO_pop_info();
#endif #endif
...@@ -585,6 +654,7 @@ int MAIN(int argc, char **argv) ...@@ -585,6 +654,7 @@ int MAIN(int argc, char **argv)
#endif #endif
BIO_free(in); BIO_free(in);
BIO_free(out); BIO_free(out);
if (canames) sk_free(canames);
if(passin) OPENSSL_free(passin); if(passin) OPENSSL_free(passin);
if(passout) OPENSSL_free(passout); if(passout) OPENSSL_free(passout);
EXIT(ret); EXIT(ret);
...@@ -726,7 +796,6 @@ int get_cert_chain (X509 *cert, X509_STORE *store, STACK_OF(X509) **chain) ...@@ -726,7 +796,6 @@ int get_cert_chain (X509 *cert, X509_STORE *store, STACK_OF(X509) **chain)
*chain = chn; *chain = chn;
err: err:
X509_STORE_CTX_cleanup(&store_ctx); X509_STORE_CTX_cleanup(&store_ctx);
X509_STORE_free(store);
return i; return i;
} }
...@@ -750,10 +819,22 @@ int cert_load(BIO *in, STACK_OF(X509) *sk) ...@@ -750,10 +819,22 @@ int cert_load(BIO *in, STACK_OF(X509) *sk)
int ret; int ret;
X509 *cert; X509 *cert;
ret = 0; ret = 0;
#ifdef CRYPTO_MDEBUG
CRYPTO_push_info("cert_load(): reading one cert");
#endif
while((cert = PEM_read_bio_X509(in, NULL, NULL, NULL))) { while((cert = PEM_read_bio_X509(in, NULL, NULL, NULL))) {
#ifdef CRYPTO_MDEBUG
CRYPTO_pop_info();
#endif
ret = 1; ret = 1;
sk_X509_push(sk, cert); sk_X509_push(sk, cert);
#ifdef CRYPTO_MDEBUG
CRYPTO_push_info("cert_load(): reading one cert");
#endif
} }
#ifdef CRYPTO_MDEBUG
CRYPTO_pop_info();
#endif
if(ret) ERR_clear_error(); if(ret) ERR_clear_error();
return ret; return ret;
} }
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册