summaryrefslogtreecommitdiffstats
path: root/crypto
diff options
context:
space:
mode:
authorDr. David von Oheimb <David.von.Oheimb@siemens.com>2020-05-05 11:31:05 +0200
committerDr. David von Oheimb <David.von.Oheimb@siemens.com>2020-06-08 05:37:48 +0200
commitc29ba6a92ea9c2c9616e044c1dd0efedafa0aeef (patch)
tree670390868d2b809c27b1bf00669bd213a0d58104 /crypto
parent4ca015555b97f00101c5f7274e99302ffe2db500 (diff)
Fix mem leaks and allow missing pkey and/or cert in try_decode_PKCS12()
Reviewed-by: Richard Levitte <levitte@openssl.org> (Merged from https://github.com/openssl/openssl/pull/11733)
Diffstat (limited to 'crypto')
-rw-r--r--crypto/store/loader_file.c67
1 files changed, 36 insertions, 31 deletions
diff --git a/crypto/store/loader_file.c b/crypto/store/loader_file.c
index 65672d4a9a..ed74e55834 100644
--- a/crypto/store/loader_file.c
+++ b/crypto/store/loader_file.c
@@ -219,7 +219,6 @@ static OSSL_STORE_INFO *try_decode_PKCS12(const char *pem_name,
if (ctx == NULL) {
/* Initial parsing */
PKCS12 *p12;
- int ok = 0;
if (pem_name != NULL)
/* No match, there is no PEM PKCS12 tag */
@@ -256,37 +255,46 @@ static OSSL_STORE_INFO *try_decode_PKCS12(const char *pem_name,
OSSL_STORE_INFO *osi_pkey = NULL;
OSSL_STORE_INFO *osi_cert = NULL;
OSSL_STORE_INFO *osi_ca = NULL;
-
- if ((ctx = sk_OSSL_STORE_INFO_new_null()) != NULL
- && (osi_pkey = OSSL_STORE_INFO_new_PKEY(pkey)) != NULL
- && sk_OSSL_STORE_INFO_push(ctx, osi_pkey) != 0
- && (osi_cert = OSSL_STORE_INFO_new_CERT(cert)) != NULL
- && sk_OSSL_STORE_INFO_push(ctx, osi_cert) != 0) {
- ok = 1;
- osi_pkey = NULL;
- osi_cert = NULL;
-
- while (sk_X509_num(chain) > 0) {
+ int ok = 1;
+
+ if ((ctx = sk_OSSL_STORE_INFO_new_null()) != NULL) {
+ if (pkey != NULL) {
+ if ((osi_pkey = OSSL_STORE_INFO_new_PKEY(pkey)) != NULL
+ /* clearing pkey here avoids case distinctions */
+ && (pkey = NULL) == NULL
+ && sk_OSSL_STORE_INFO_push(ctx, osi_pkey) != 0)
+ osi_pkey = NULL;
+ else
+ ok = 0;
+ }
+ if (ok && cert != NULL) {
+ if ((osi_cert = OSSL_STORE_INFO_new_CERT(cert)) != NULL
+ /* clearing cert here avoids case distinctions */
+ && (cert = NULL) == NULL
+ && sk_OSSL_STORE_INFO_push(ctx, osi_cert) != 0)
+ osi_cert = NULL;
+ else
+ ok = 0;
+ }
+ while (ok && sk_X509_num(chain) > 0) {
X509 *ca = sk_X509_value(chain, 0);
- if ((osi_ca = OSSL_STORE_INFO_new_CERT(ca)) == NULL
- || sk_OSSL_STORE_INFO_push(ctx, osi_ca) == 0) {
+ if ((osi_ca = OSSL_STORE_INFO_new_CERT(ca)) != NULL
+ && sk_X509_shift(chain) != NULL
+ && sk_OSSL_STORE_INFO_push(ctx, osi_ca) != 0)
+ osi_ca = NULL;
+ else
ok = 0;
- break;
- }
- osi_ca = NULL;
- (void)sk_X509_shift(chain);
}
}
- sk_X509_free(chain);
+ EVP_PKEY_free(pkey);
+ X509_free(cert);
+ sk_X509_pop_free(chain, X509_free);
+ OSSL_STORE_INFO_free(osi_pkey);
+ OSSL_STORE_INFO_free(osi_cert);
+ OSSL_STORE_INFO_free(osi_ca);
if (!ok) {
- OSSL_STORE_INFO_free(osi_ca);
- OSSL_STORE_INFO_free(osi_cert);
- OSSL_STORE_INFO_free(osi_pkey);
sk_OSSL_STORE_INFO_pop_free(ctx, OSSL_STORE_INFO_free);
- EVP_PKEY_free(pkey);
- X509_free(cert);
- sk_X509_pop_free(chain, X509_free);
ctx = NULL;
}
*pctx = ctx;
@@ -294,15 +302,12 @@ static OSSL_STORE_INFO *try_decode_PKCS12(const char *pem_name,
}
p12_end:
PKCS12_free(p12);
- if (!ok)
+ if (ctx == NULL)
return NULL;
}
- if (ctx != NULL) {
- *matchcount = 1;
- store_info = sk_OSSL_STORE_INFO_shift(ctx);
- }
-
+ *matchcount = 1;
+ store_info = sk_OSSL_STORE_INFO_shift(ctx);
return store_info;
}