mirror of
https://github.com/wolfSSL/wolfssl.git
synced 2026-07-05 14:00:48 +02:00
Merge pull request #10336 from julek-wolfssl/wolfSSL_PEM_read_bio_X509_CRL-multi-crl-fix
src/x509.c: refactor wolfSSL_PEM_read_bio_X509_CRL onto the per-block reader
This commit is contained in:
+33
-27
@@ -13494,36 +13494,35 @@ WOLFSSL_X509 *wolfSSL_PEM_read_bio_X509_REQ(WOLFSSL_BIO *bp, WOLFSSL_X509 **x,
|
||||
WOLFSSL_X509_CRL **x, wc_pem_password_cb *cb, void *u)
|
||||
{
|
||||
#if defined(WOLFSSL_PEM_TO_DER) && defined(HAVE_CRL)
|
||||
unsigned char* pem = NULL;
|
||||
int pemSz = 0;
|
||||
int derSz = 0;
|
||||
DerBuffer* der = NULL;
|
||||
WOLFSSL_X509_CRL* crl = NULL;
|
||||
|
||||
WOLFSSL_ENTER("wolfSSL_PEM_read_bio_X509_CRL");
|
||||
|
||||
if ((pem = ReadPemFromBioToBuffer(bp, &pemSz)) == NULL) {
|
||||
goto err;
|
||||
/* OpenSSL's PEM_read_bio_X509_CRL skips intervening cert/key blocks
|
||||
* and returns the next CRL in the stream (NULL only at EOF). Mirror
|
||||
* that by looping over the per-block reader until we get a CRL or
|
||||
* the BIO has nothing left to parse. */
|
||||
for (;;) {
|
||||
WOLFSSL_X509* x509 = NULL;
|
||||
WOLFSSL_X509_PKEY* x_pkey = NULL;
|
||||
if (wolfSSL_PEM_X509_X509_CRL_X509_PKEY_read_bio(bp, cb,
|
||||
&x509, &crl, &x_pkey) != WOLFSSL_SUCCESS) {
|
||||
break;
|
||||
}
|
||||
if (crl != NULL) {
|
||||
break;
|
||||
}
|
||||
wolfSSL_X509_free(x509);
|
||||
wolfSSL_X509_PKEY_free(x_pkey);
|
||||
}
|
||||
|
||||
if ((PemToDer(pem, pemSz, CRL_TYPE, &der, NULL, NULL, NULL)) < 0) {
|
||||
goto err;
|
||||
}
|
||||
derSz = (int)der->length;
|
||||
if ((crl = wolfSSL_d2i_X509_CRL(x, der->buffer, derSz)) == NULL) {
|
||||
goto err;
|
||||
if (x != NULL) {
|
||||
if (*x != NULL && *x != crl) {
|
||||
wolfSSL_X509_CRL_free(*x);
|
||||
}
|
||||
*x = crl;
|
||||
}
|
||||
|
||||
err:
|
||||
if (pemSz == 0) {
|
||||
WOLFSSL_ERROR(ASN_NO_PEM_HEADER);
|
||||
}
|
||||
XFREE(pem, 0, DYNAMIC_TYPE_PEM);
|
||||
if (der != NULL) {
|
||||
FreeDer(&der);
|
||||
}
|
||||
|
||||
(void)cb;
|
||||
(void)u;
|
||||
|
||||
return crl;
|
||||
@@ -13686,7 +13685,7 @@ int wolfSSL_write_X509_CRL(WOLFSSL_X509_CRL* crl, const char* path, int type)
|
||||
#endif /* !NO_FILESYSTEM */
|
||||
|
||||
#endif /* OPENSSL_EXTRA || OPENSSL_ALL */
|
||||
#ifdef OPENSSL_ALL
|
||||
#if defined(OPENSSL_EXTRA) || defined(OPENSSL_ALL)
|
||||
|
||||
#ifndef NO_BIO
|
||||
/* create and return a new WOLFSSL_X509_PKEY structure or NULL on failure */
|
||||
@@ -13706,7 +13705,7 @@ int wolfSSL_write_X509_CRL(WOLFSSL_X509_CRL* crl, const char* path, int type)
|
||||
|
||||
|
||||
/* free up all memory used by "xPkey" passed in */
|
||||
static void wolfSSL_X509_PKEY_free(WOLFSSL_X509_PKEY* xPkey)
|
||||
void wolfSSL_X509_PKEY_free(WOLFSSL_X509_PKEY* xPkey)
|
||||
{
|
||||
if (xPkey != NULL) {
|
||||
wolfSSL_EVP_PKEY_free(xPkey->dec_pkey);
|
||||
@@ -13732,7 +13731,7 @@ int wolfSSL_write_X509_CRL(WOLFSSL_X509_CRL* crl, const char* path, int type)
|
||||
* @param x_pkey Output
|
||||
* @return WOLFSSL_SUCCESS on success and WOLFSSL_FAILURE otherwise
|
||||
*/
|
||||
static int wolfSSL_PEM_X509_X509_CRL_X509_PKEY_read_bio(
|
||||
int wolfSSL_PEM_X509_X509_CRL_X509_PKEY_read_bio(
|
||||
WOLFSSL_BIO* bio, wc_pem_password_cb* cb, WOLFSSL_X509** x509,
|
||||
WOLFSSL_X509_CRL** crl, WOLFSSL_X509_PKEY** x_pkey)
|
||||
{
|
||||
@@ -13762,7 +13761,11 @@ int wolfSSL_write_X509_CRL(WOLFSSL_X509_CRL* crl, const char* path, int type)
|
||||
return WOLFSSL_FAILURE;
|
||||
}
|
||||
|
||||
if (l <= pem_struct_min_sz) {
|
||||
if (l == 0) {
|
||||
/* Streaming BIO (pipe/FIFO/socket): size unknown, use the cap. */
|
||||
l = MAX_BIO_READ_BUFFER;
|
||||
}
|
||||
else if (l <= pem_struct_min_sz) {
|
||||
/* No certificate in buffer */
|
||||
WOLFSSL_ERROR(ASN_NO_PEM_HEADER);
|
||||
return WOLFSSL_FAILURE;
|
||||
@@ -13916,6 +13919,9 @@ err:
|
||||
#endif /* WOLFSSL_PEM_TO_DER || WOLFSSL_DER_TO_PEM */
|
||||
}
|
||||
|
||||
#endif /* OPENSSL_EXTRA || OPENSSL_ALL */
|
||||
#ifdef OPENSSL_ALL
|
||||
|
||||
#ifndef NO_FILESYSTEM
|
||||
WOLF_STACK_OF(WOLFSSL_X509_INFO)* wolfSSL_PEM_X509_INFO_read(
|
||||
XFILE fp, WOLF_STACK_OF(WOLFSSL_X509_INFO)* sk,
|
||||
@@ -14053,7 +14059,7 @@ err:
|
||||
return localSk;
|
||||
}
|
||||
#endif /* !NO_BIO */
|
||||
#endif /* OPENSSL_ALL */
|
||||
#endif /* OPENSSL_EXTRA || OPENSSL_ALL */
|
||||
|
||||
void wolfSSL_X509_NAME_ENTRY_free(WOLFSSL_X509_NAME_ENTRY* ne)
|
||||
{
|
||||
|
||||
@@ -312,6 +312,17 @@ int test_wolfSSL_X509_load_crl_file(void)
|
||||
#endif
|
||||
""
|
||||
};
|
||||
int pemCount[] = {
|
||||
1,
|
||||
2,
|
||||
1,
|
||||
1,
|
||||
1,
|
||||
#ifdef WC_RSA_PSS
|
||||
1,
|
||||
#endif
|
||||
0
|
||||
};
|
||||
char der[][100] = {
|
||||
"./certs/crl/crl.der",
|
||||
"./certs/crl/crl2.der",
|
||||
@@ -342,7 +353,7 @@ int test_wolfSSL_X509_load_crl_file(void)
|
||||
ExpectIntEQ(X509_load_crl_file(lookup, pem[0], 0), 0);
|
||||
for (i = 0; pem[i][0] != '\0'; i++) {
|
||||
ExpectIntEQ(X509_load_crl_file(lookup, pem[i], WOLFSSL_FILETYPE_PEM),
|
||||
1);
|
||||
pemCount[i]);
|
||||
}
|
||||
|
||||
if (store) {
|
||||
@@ -394,6 +405,45 @@ int test_wolfSSL_X509_load_crl_file(void)
|
||||
|
||||
X509_STORE_free(store);
|
||||
store = NULL;
|
||||
|
||||
/* Combine crl.pem (1 CRL), a server cert, and crl2.pem (2 CRLs) into a
|
||||
* single memory BIO. wolfSSL_PEM_read_bio_X509_CRL must walk past the
|
||||
* intervening certificate and hand back all three CRLs before NULL,
|
||||
* matching OpenSSL's PEM_read_bio_X509_CRL behaviour. */
|
||||
{
|
||||
WOLFSSL_BIO* fileBio = NULL;
|
||||
WOLFSSL_BIO* memBio = NULL;
|
||||
WOLFSSL_X509_CRL* crl = NULL;
|
||||
unsigned char buf[4096];
|
||||
int n;
|
||||
int crlCount = 0;
|
||||
const char* sources[] = {
|
||||
"./certs/crl/crl.pem",
|
||||
"./certs/server-cert.pem",
|
||||
"./certs/crl/crl2.pem",
|
||||
NULL
|
||||
};
|
||||
|
||||
ExpectNotNull(memBio = wolfSSL_BIO_new(wolfSSL_BIO_s_mem()));
|
||||
for (i = 0; sources[i] != NULL; i++) {
|
||||
ExpectNotNull(fileBio = wolfSSL_BIO_new_file(sources[i], "rb"));
|
||||
while (fileBio != NULL &&
|
||||
(n = wolfSSL_BIO_read(fileBio, buf, sizeof(buf))) > 0) {
|
||||
ExpectIntEQ(wolfSSL_BIO_write(memBio, buf, n), n);
|
||||
}
|
||||
wolfSSL_BIO_free(fileBio);
|
||||
fileBio = NULL;
|
||||
}
|
||||
|
||||
while ((crl = wolfSSL_PEM_read_bio_X509_CRL(memBio, NULL, NULL, NULL))
|
||||
!= NULL) {
|
||||
crlCount++;
|
||||
wolfSSL_X509_CRL_free(crl);
|
||||
}
|
||||
ExpectIntEQ(crlCount, 3);
|
||||
|
||||
wolfSSL_BIO_free(memBio);
|
||||
}
|
||||
#endif
|
||||
return EXPECT_RESULT();
|
||||
}
|
||||
|
||||
@@ -34,7 +34,7 @@ int test_X509_LOOKUP_add_dir(void);
|
||||
TEST_DECL_GROUP("ossl_x509_lu", test_wolfSSL_X509_LOOKUP_load_file), \
|
||||
TEST_DECL_GROUP("ossl_x509_lu", test_wolfSSL_X509_LOOKUP_ctrl_file), \
|
||||
TEST_DECL_GROUP("ossl_x509_lu", test_wolfSSL_X509_LOOKUP_ctrl_hash_dir), \
|
||||
TEST_DECL_GROUP("ossl_x509_lu", test_wolfSSL_X509_LOOKUP_ctrl_hash_dir), \
|
||||
TEST_DECL_GROUP("ossl_x509_lu", test_wolfSSL_X509_load_crl_file), \
|
||||
TEST_DECL_GROUP("ossl_x509_lu", test_X509_LOOKUP_add_dir)
|
||||
|
||||
#endif /* WOLFCRYPT_TEST_OSSL_X509_LU_H */
|
||||
|
||||
@@ -7470,6 +7470,15 @@ WOLFSSL_LOCAL int pkcs8_encrypt(WOLFSSL_EVP_PKEY* pkey,
|
||||
word32* keySz);
|
||||
#endif /* OPENSSL_EXTRA || OPENSSL_EXTRA_X509_SMALL */
|
||||
|
||||
#if (defined(OPENSSL_EXTRA) || defined(OPENSSL_ALL)) && !defined(NO_BIO)
|
||||
WOLFSSL_LOCAL int wolfSSL_PEM_X509_X509_CRL_X509_PKEY_read_bio(
|
||||
WOLFSSL_BIO* bio, wc_pem_password_cb* cb, WOLFSSL_X509** x509,
|
||||
WOLFSSL_X509_CRL** crl, WOLFSSL_X509_PKEY** x_pkey);
|
||||
#endif
|
||||
#if defined(OPENSSL_EXTRA) || defined(OPENSSL_ALL)
|
||||
WOLFSSL_LOCAL void wolfSSL_X509_PKEY_free(WOLFSSL_X509_PKEY* xPkey);
|
||||
#endif
|
||||
|
||||
WOLFSSL_LOCAL void wolfssl_local_MaybeCheckAlertOnErr(WOLFSSL* ssl, int err);
|
||||
|
||||
#ifdef __cplusplus
|
||||
|
||||
Reference in New Issue
Block a user