mirror of
https://github.com/wolfSSL/wolfssl.git
synced 2025-07-31 19:24:42 +02:00
Merge pull request #1741 from dgarske/verify_cb
Refactor of the verify callback
This commit is contained in:
542
src/internal.c
542
src/internal.c
@@ -7921,6 +7921,8 @@ static void AddSessionCertToChain(WOLFSSL_X509_CHAIN* chain,
|
||||
#if defined(KEEP_PEER_CERT) || defined(SESSION_CERTS) || \
|
||||
defined(OPENSSL_EXTRA) || defined(OPENSSL_EXTRA_X509_SMALL)
|
||||
/* Copy parts X509 needs from Decoded cert, 0 on success */
|
||||
/* The same DecodedCert cannot be copied to WOLFSSL_X509 twice otherwise the
|
||||
* altNames pointers could be free'd by second x509 still active by first */
|
||||
int CopyDecodedToX509(WOLFSSL_X509* x509, DecodedCert* dCert)
|
||||
{
|
||||
int ret = 0;
|
||||
@@ -8335,7 +8337,6 @@ typedef struct ProcPeerCertArgs {
|
||||
buffer* exts; /* extentions */
|
||||
#endif
|
||||
DecodedCert* dCert;
|
||||
char* domain;
|
||||
word32 idx;
|
||||
word32 begin;
|
||||
int totalCerts; /* number of certs in certs buffer */
|
||||
@@ -8358,16 +8359,189 @@ typedef struct ProcPeerCertArgs {
|
||||
#endif
|
||||
} ProcPeerCertArgs;
|
||||
|
||||
/* WOLFSSL_ALWAYS_VERIFY_CB: Use verify callback for success or failure cases */
|
||||
/* WOLFSSL_VERIFY_CB_ALL_CERTS: Issue callback for all intermediate certificates */
|
||||
|
||||
/* Callback is issued for certificate presented in TLS Certificate (11) packet.
|
||||
* The intermediates are done first then peer leaf cert last. Use the
|
||||
* store->error_depth member to determine index (0=peer, >1 intermediates)
|
||||
*/
|
||||
|
||||
static int DoVerifyCallback(WOLFSSL* ssl, int ret, ProcPeerCertArgs* args)
|
||||
{
|
||||
int verify_ok = 0, alertWhy = 0, use_cb = 0;
|
||||
|
||||
/* Determine return code and alert reason */
|
||||
if (ret != 0) {
|
||||
alertWhy = bad_certificate;
|
||||
if (ret == ASN_AFTER_DATE_E ||
|
||||
ret == ASN_BEFORE_DATE_E) {
|
||||
alertWhy = certificate_expired;
|
||||
}
|
||||
}
|
||||
else {
|
||||
verify_ok = 1;
|
||||
}
|
||||
|
||||
/* Determine if verify callback should be used */
|
||||
if (ret != 0) {
|
||||
if (!ssl->options.verifyNone) {
|
||||
use_cb = 1; /* always report errors */
|
||||
}
|
||||
}
|
||||
#ifdef WOLFSSL_ALWAYS_VERIFY_CB
|
||||
/* always use verify callback on peer leaf cert */
|
||||
if (args->certIdx == 0) {
|
||||
use_cb = 1;
|
||||
}
|
||||
#endif
|
||||
#ifdef WOLFSSL_VERIFY_CB_ALL_CERTS
|
||||
/* perform verify callback on other intermediate certs (not just peer) */
|
||||
if (args->certIdx > 0) {
|
||||
use_cb = 1;
|
||||
}
|
||||
#endif
|
||||
|
||||
/* if verify callback has been set */
|
||||
if (use_cb && ssl->verifyCallback) {
|
||||
#ifdef WOLFSSL_SMALL_STACK
|
||||
WOLFSSL_X509_STORE_CTX* store;
|
||||
#ifdef OPENSSL_EXTRA
|
||||
WOLFSSL_X509* x509;
|
||||
#endif
|
||||
char* domain = NULL;
|
||||
#else
|
||||
WOLFSSL_X509_STORE_CTX store[1];
|
||||
#ifdef OPENSSL_EXTRA
|
||||
WOLFSSL_X509 x509[1];
|
||||
#endif
|
||||
char domain[ASN_NAME_MAX];
|
||||
#endif
|
||||
|
||||
#ifdef WOLFSSL_SMALL_STACK
|
||||
store = (WOLFSSL_X509_STORE_CTX*)XMALLOC(
|
||||
sizeof(WOLFSSL_X509_STORE_CTX), ssl->heap, DYNAMIC_TYPE_X509_STORE);
|
||||
if (store == NULL) {
|
||||
return MEMORY_E;
|
||||
}
|
||||
#ifdef OPENSSL_EXTRA
|
||||
x509 = (WOLFSSL_X509*)XMALLOC(sizeof(WOLFSSL_X509), ssl->heap,
|
||||
DYNAMIC_TYPE_X509);
|
||||
if (x509 == NULL) {
|
||||
XFREE(store, ssl->heap, DYNAMIC_TYPE_X509);
|
||||
return MEMORY_E;
|
||||
}
|
||||
#endif
|
||||
domain = (char*)XMALLOC(ASN_NAME_MAX, ssl->heap, DYNAMIC_TYPE_STRING);
|
||||
if (domain == NULL) {
|
||||
XFREE(store, ssl->heap, DYNAMIC_TYPE_X509);
|
||||
#ifdef OPENSSL_EXTRA
|
||||
XFREE(x509, ssl->heap, DYNAMIC_TYPE_X509);
|
||||
#endif
|
||||
return MEMORY_E;
|
||||
}
|
||||
#endif /* WOLFSSL_SMALL_STACK */
|
||||
|
||||
XMEMSET(store, 0, sizeof(WOLFSSL_X509_STORE_CTX));
|
||||
#ifdef OPENSSL_EXTRA
|
||||
XMEMSET(x509, 0, sizeof(WOLFSSL_X509));
|
||||
#endif
|
||||
domain[0] = '\0';
|
||||
|
||||
/* build subject CN as string to return in store */
|
||||
if (args->dCert && args->dCert->subjectCN) {
|
||||
int subjectCNLen = args->dCert->subjectCNLen;
|
||||
if (subjectCNLen > ASN_NAME_MAX-1)
|
||||
subjectCNLen = ASN_NAME_MAX-1;
|
||||
if (subjectCNLen > 0) {
|
||||
XMEMCPY(domain, args->dCert->subjectCN, subjectCNLen);
|
||||
domain[subjectCNLen] = '\0';
|
||||
}
|
||||
}
|
||||
|
||||
store->error = ret;
|
||||
store->error_depth = args->certIdx;
|
||||
store->discardSessionCerts = 0;
|
||||
store->domain = domain;
|
||||
store->userCtx = ssl->verifyCbCtx;
|
||||
store->certs = args->certs;
|
||||
store->totalCerts = args->totalCerts;
|
||||
store->ex_data = ssl;
|
||||
|
||||
#if defined(OPENSSL_EXTRA) || defined(HAVE_WEBSERVER)
|
||||
if (ssl->ctx->x509_store_pt != NULL) {
|
||||
store->store = ssl->ctx->x509_store_pt;
|
||||
}
|
||||
else {
|
||||
store->store = &ssl->ctx->x509_store;
|
||||
}
|
||||
#endif
|
||||
#ifdef OPENSSL_EXTRA
|
||||
if (args->certIdx == 0) {
|
||||
store->current_cert = &ssl->peerCert; /* use existing X509 */
|
||||
}
|
||||
else {
|
||||
InitX509(x509, 0, ssl->heap);
|
||||
if (CopyDecodedToX509(x509, args->dCert) == 0) {
|
||||
store->current_cert = x509;
|
||||
}
|
||||
}
|
||||
#endif
|
||||
#ifdef SESSION_CERTS
|
||||
store->sesChain = &ssl->session.chain;
|
||||
#endif
|
||||
/* non-zero return code indicates failure override */
|
||||
if (ssl->verifyCallback(verify_ok, store)) {
|
||||
WOLFSSL_MSG("Verify callback overriding error!");
|
||||
ret = 0;
|
||||
}
|
||||
#ifdef OPENSSL_EXTRA
|
||||
if (args->certIdx > 0)
|
||||
FreeX509(x509);
|
||||
#endif
|
||||
#if defined(SESSION_CERTS) && defined(OPENSSL_EXTRA)
|
||||
wolfSSL_sk_X509_free(store->chain);
|
||||
store->chain = NULL;
|
||||
#endif
|
||||
#ifdef WOLFSSL_SMALL_STACK
|
||||
XFREE(domain, ssl->heap, DYNAMIC_TYPE_STRING);
|
||||
#ifdef OPENSSL_EXTRA
|
||||
XFREE(x509, ssl->heap, DYNAMIC_TYPE_X509);
|
||||
#endif
|
||||
XFREE(store, ssl->heap, DYNAMIC_TYPE_X509_STORE);
|
||||
#endif
|
||||
|
||||
#ifdef SESSION_CERTS
|
||||
if (store->discardSessionCerts) {
|
||||
WOLFSSL_MSG("Verify callback requested discard sess certs");
|
||||
ssl->session.chain.count = 0;
|
||||
#ifdef WOLFSSL_ALT_CERT_CHAINS
|
||||
ssl->session.altChain.count = 0;
|
||||
#endif
|
||||
}
|
||||
#endif /* SESSION_CERTS */
|
||||
}
|
||||
|
||||
if (ret != 0) {
|
||||
if (!ssl->options.verifyNone) {
|
||||
/* handle failure */
|
||||
SendAlert(ssl, alert_fatal, alertWhy); /* try to send */
|
||||
ssl->options.isClosed = 1;
|
||||
}
|
||||
|
||||
/* Report SSL error */
|
||||
ssl->error = ret;
|
||||
}
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
static void FreeProcPeerCertArgs(WOLFSSL* ssl, void* pArgs)
|
||||
{
|
||||
ProcPeerCertArgs* args = (ProcPeerCertArgs*)pArgs;
|
||||
|
||||
(void)ssl;
|
||||
|
||||
if (args->domain) {
|
||||
XFREE(args->domain, ssl->heap, DYNAMIC_TYPE_STRING);
|
||||
args->domain = NULL;
|
||||
}
|
||||
if (args->certs) {
|
||||
XFREE(args->certs, ssl->heap, DYNAMIC_TYPE_DER);
|
||||
args->certs = NULL;
|
||||
@@ -8745,6 +8919,7 @@ int ProcessPeerCerts(WOLFSSL* ssl, byte* input, word32* inOutIdx,
|
||||
#endif
|
||||
if (!AlreadySigner(ssl->ctx->cm, subjectHash))
|
||||
args->untrustedDepth = 1;
|
||||
|
||||
FreeDecodedCert(args->dCert);
|
||||
args->dCertInit = 0;
|
||||
}
|
||||
@@ -8862,7 +9037,7 @@ int ProcessPeerCerts(WOLFSSL* ssl, byte* input, word32* inOutIdx,
|
||||
|
||||
#if defined(OPENSSL_ALL) || defined(WOLFSSL_NGINX)
|
||||
if (args->certIdx > args->untrustedDepth)
|
||||
args->untrustedDepth = (char) args->certIdx + 1;
|
||||
args->untrustedDepth = (char)args->certIdx + 1;
|
||||
#endif
|
||||
|
||||
/* already verified above */
|
||||
@@ -8965,192 +9140,10 @@ int ProcessPeerCerts(WOLFSSL* ssl, byte* input, word32* inOutIdx,
|
||||
}
|
||||
#endif /* HAVE_OCSP || HAVE_CRL */
|
||||
|
||||
#if defined(WOLFSSL_VERIFY_CB_ALL_CERTS)
|
||||
if (ret != 0) {
|
||||
if (!ssl->options.verifyNone) {
|
||||
int why = bad_certificate;
|
||||
|
||||
if (ret == ASN_AFTER_DATE_E || ret ==
|
||||
ASN_BEFORE_DATE_E) {
|
||||
why = certificate_expired;
|
||||
}
|
||||
if (ssl->verifyCallback) {
|
||||
int ok;
|
||||
|
||||
#ifdef WOLFSSL_SMALL_STACK
|
||||
WOLFSSL_X509_STORE_CTX* store;
|
||||
WOLFSSL_X509* x509 = (WOLFSSL_X509*)XMALLOC(
|
||||
sizeof(WOLFSSL_X509), ssl->heap,
|
||||
DYNAMIC_TYPE_X509);
|
||||
if (x509 == NULL) {
|
||||
ERROR_OUT(MEMORY_E, exit_ppc);
|
||||
}
|
||||
store = (WOLFSSL_X509_STORE_CTX*)XMALLOC(
|
||||
sizeof(WOLFSSL_X509_STORE_CTX), ssl->heap,
|
||||
DYNAMIC_TYPE_X509_STORE);
|
||||
if (store == NULL) {
|
||||
wolfSSL_X509_free(x509);
|
||||
ERROR_OUT(MEMORY_E, exit_ppc);
|
||||
}
|
||||
#else
|
||||
WOLFSSL_X509_STORE_CTX store[1];
|
||||
WOLFSSL_X509 x509[1];
|
||||
#endif
|
||||
|
||||
XMEMSET(store, 0, sizeof(WOLFSSL_X509_STORE_CTX));
|
||||
|
||||
store->error = ret;
|
||||
store->error_depth = args->certIdx;
|
||||
store->discardSessionCerts = 0;
|
||||
store->domain = args->domain;
|
||||
store->userCtx = ssl->verifyCbCtx;
|
||||
store->certs = args->certs;
|
||||
store->totalCerts = args->totalCerts;
|
||||
|
||||
#if defined(OPENSSL_EXTRA) || defined(HAVE_WEBSERVER)
|
||||
if (ssl->ctx->x509_store_pt != NULL) {
|
||||
store->store = ssl->ctx->x509_store_pt;
|
||||
}
|
||||
else {
|
||||
store->store = &ssl->ctx->x509_store;
|
||||
}
|
||||
#endif
|
||||
#if !defined(NO_CERTS)
|
||||
InitX509(x509, 1, ssl->heap);
|
||||
#if defined(KEEP_PEER_CERT) || \
|
||||
defined(SESSION_CERTS)
|
||||
if (CopyDecodedToX509(x509, args->dCert) == 0) {
|
||||
store->current_cert = x509;
|
||||
}
|
||||
#endif
|
||||
#endif
|
||||
#if defined(HAVE_EX_DATA) || defined(HAVE_FORTRESS)
|
||||
store->ex_data = ssl;
|
||||
#endif
|
||||
#ifdef SESSION_CERTS
|
||||
store->sesChain = &(ssl->session.chain);
|
||||
#endif
|
||||
ok = ssl->verifyCallback(0, store);
|
||||
if (ok) {
|
||||
WOLFSSL_MSG("Verify callback overriding error!");
|
||||
ret = 0;
|
||||
}
|
||||
#ifndef NO_CERTS
|
||||
FreeX509(x509);
|
||||
#endif
|
||||
#if defined(SESSION_CERTS) && defined(OPENSSL_EXTRA)
|
||||
wolfSSL_sk_X509_free(store->chain);
|
||||
store->chain = NULL;
|
||||
#endif
|
||||
#ifdef SESSION_CERTS
|
||||
if (store->discardSessionCerts) {
|
||||
WOLFSSL_MSG("Verify callback requested discard sess certs");
|
||||
ssl->session.chain.count = 0;
|
||||
#ifdef WOLFSSL_ALT_CERT_CHAINS
|
||||
ssl->session.altChain.count = 0;
|
||||
#endif
|
||||
}
|
||||
#endif /* SESSION_CERTS */
|
||||
#ifdef WOLFSSL_SMALL_STACK
|
||||
XFREE(x509, ssl->heap, DYNAMIC_TYPE_X509);
|
||||
XFREE(store, ssl->heap, DYNAMIC_TYPE_X509_STORE);
|
||||
#endif
|
||||
}
|
||||
if (ret != 0) {
|
||||
SendAlert(ssl, alert_fatal, why); /* try to send */
|
||||
ssl->options.isClosed = 1;
|
||||
}
|
||||
}
|
||||
|
||||
ssl->error = ret;
|
||||
}
|
||||
#ifdef WOLFSSL_ALWAYS_VERIFY_CB
|
||||
else {
|
||||
if (ssl->verifyCallback) {
|
||||
int ok;
|
||||
|
||||
#ifdef WOLFSSL_SMALL_STACK
|
||||
WOLFSSL_X509_STORE_CTX* store;
|
||||
WOLFSSL_X509* x509 = (WOLFSSL_X509*)XMALLOC(
|
||||
sizeof(WOLFSSL_X509), ssl->heap,
|
||||
DYNAMIC_TYPE_X509);
|
||||
if (x509 == NULL) {
|
||||
ERROR_OUT(MEMORY_E, exit_ppc);
|
||||
}
|
||||
store = (WOLFSSL_X509_STORE_CTX*)XMALLOC(
|
||||
sizeof(WOLFSSL_X509_STORE_CTX), ssl->heap,
|
||||
DYNAMIC_TYPE_X509_STORE);
|
||||
if (store == NULL) {
|
||||
wolfSSL_X509_free(x509);
|
||||
ERROR_OUT(MEMORY_E, exit_ppc);
|
||||
}
|
||||
#else
|
||||
WOLFSSL_X509_STORE_CTX store[1];
|
||||
WOLFSSL_X509 x509[1];
|
||||
#endif
|
||||
|
||||
XMEMSET(store, 0, sizeof(WOLFSSL_X509_STORE_CTX));
|
||||
|
||||
store->error = ret;
|
||||
store->error_depth = args->certIdx;
|
||||
store->discardSessionCerts = 0;
|
||||
store->domain = args->domain;
|
||||
store->userCtx = ssl->verifyCbCtx;
|
||||
store->certs = args->certs;
|
||||
store->totalCerts = args->totalCerts;
|
||||
|
||||
#if defined(OPENSSL_EXTRA) || defined(HAVE_WEBSERVER)
|
||||
if (ssl->ctx->x509_store_pt != NULL) {
|
||||
store->store = ssl->ctx->x509_store_pt;
|
||||
}
|
||||
else {
|
||||
store->store = &ssl->ctx->x509_store;
|
||||
}
|
||||
#endif
|
||||
#if !defined(NO_CERTS)
|
||||
InitX509(x509, 1, ssl->heap);
|
||||
#if defined(KEEP_PEER_CERT) || defined(SESSION_CERTS)
|
||||
if (CopyDecodedToX509(x509, args->dCert) == 0) {
|
||||
store->current_cert = x509;
|
||||
}
|
||||
#endif
|
||||
#endif
|
||||
#ifdef SESSION_CERTS
|
||||
store->sesChain = &(ssl->session.chain);
|
||||
#endif
|
||||
store->ex_data = ssl;
|
||||
|
||||
ok = ssl->verifyCallback(1, store);
|
||||
if (!ok) {
|
||||
WOLFSSL_MSG("Verify callback overriding valid certificate!");
|
||||
ret = -1;
|
||||
ssl->options.isClosed = 1;
|
||||
}
|
||||
#ifndef NO_CERTS
|
||||
FreeX509(x509);
|
||||
#endif
|
||||
#if defined(SESSION_CERTS) && defined(OPENSSL_EXTRA)
|
||||
wolfSSL_sk_X509_free(store->chain);
|
||||
store->chain = NULL;
|
||||
#endif
|
||||
#ifdef SESSION_CERTS
|
||||
if (store->discardSessionCerts) {
|
||||
WOLFSSL_MSG("Verify callback requested discard sess certs");
|
||||
ssl->session.chain.count = 0;
|
||||
#ifdef WOLFSSL_ALT_CERT_CHAINS
|
||||
ssl->session.altChain.count = 0;
|
||||
#endif
|
||||
}
|
||||
#endif /* SESSION_CERTS */
|
||||
#ifdef WOLFSSL_SMALL_STACK
|
||||
XFREE(store, ssl->heap, DYNAMIC_TYPE_X509_STORE);
|
||||
XFREE(x509, ssl->heap, DYNAMIC_TYPE_X509);
|
||||
#endif
|
||||
}
|
||||
}
|
||||
#endif /* WOLFSSL_ALWAYS_VERIFY_CB */
|
||||
#endif /* WOLFSSL_VERIFY_CB_ALL_CERTS */
|
||||
/* Do verify callback */
|
||||
ret = DoVerifyCallback(ssl, ret, args);
|
||||
|
||||
/* Handle error codes */
|
||||
if (ret != 0 && args->lastErr == 0) {
|
||||
args->lastErr = ret; /* save error from last time */
|
||||
ret = 0; /* reset error */
|
||||
@@ -9445,23 +9438,6 @@ int ProcessPeerCerts(WOLFSSL* ssl, byte* input, word32* inOutIdx,
|
||||
|
||||
ssl->options.havePeerCert = 1;
|
||||
|
||||
args->domain = (char*)XMALLOC(ASN_NAME_MAX, ssl->heap,
|
||||
DYNAMIC_TYPE_STRING);
|
||||
if (args->domain == NULL) {
|
||||
ERROR_OUT(MEMORY_E, exit_ppc);
|
||||
}
|
||||
|
||||
/* store for callback use */
|
||||
if (args->dCert->subjectCN &&
|
||||
args->dCert->subjectCNLen < ASN_NAME_MAX) {
|
||||
XMEMCPY(args->domain, args->dCert->subjectCN,
|
||||
args->dCert->subjectCNLen);
|
||||
args->domain[args->dCert->subjectCNLen] = '\0';
|
||||
}
|
||||
else {
|
||||
args->domain[0] = '\0';
|
||||
}
|
||||
|
||||
if (!ssl->options.verifyNone && ssl->buffers.domainName.buffer) {
|
||||
#ifndef WOLFSSL_ALLOW_NO_CN_IN_SAN
|
||||
/* Per RFC 5280 section 4.2.1.6, "Whenever such identities
|
||||
@@ -9677,14 +9653,7 @@ int ProcessPeerCerts(WOLFSSL* ssl, byte* input, word32* inOutIdx,
|
||||
break;
|
||||
}
|
||||
|
||||
FreeDecodedCert(args->dCert);
|
||||
args->dCertInit = 0;
|
||||
|
||||
/* release since we don't need it anymore */
|
||||
if (args->dCert) {
|
||||
XFREE(args->dCert, ssl->heap, DYNAMIC_TYPE_DCERT);
|
||||
args->dCert = NULL;
|
||||
}
|
||||
/* args->dCert free'd in function cleanup after callback */
|
||||
} /* if (count > 0) */
|
||||
|
||||
/* Check for error */
|
||||
@@ -9699,19 +9668,6 @@ int ProcessPeerCerts(WOLFSSL* ssl, byte* input, word32* inOutIdx,
|
||||
|
||||
case TLS_ASYNC_FINALIZE:
|
||||
{
|
||||
#ifdef WOLFSSL_SMALL_STACK
|
||||
WOLFSSL_X509_STORE_CTX* store = (WOLFSSL_X509_STORE_CTX*)XMALLOC(
|
||||
sizeof(WOLFSSL_X509_STORE_CTX), ssl->heap,
|
||||
DYNAMIC_TYPE_X509_STORE);
|
||||
if (store == NULL) {
|
||||
ERROR_OUT(MEMORY_E, exit_ppc);
|
||||
}
|
||||
#else
|
||||
WOLFSSL_X509_STORE_CTX store[1];
|
||||
#endif
|
||||
|
||||
XMEMSET(store, 0, sizeof(WOLFSSL_X509_STORE_CTX));
|
||||
|
||||
/* load last error */
|
||||
if (args->lastErr != 0 && ret == 0) {
|
||||
ret = args->lastErr;
|
||||
@@ -9723,127 +9679,12 @@ int ProcessPeerCerts(WOLFSSL* ssl, byte* input, word32* inOutIdx,
|
||||
ret = MAX_CHAIN_ERROR;
|
||||
}
|
||||
#endif
|
||||
if (ret != 0) {
|
||||
if (!ssl->options.verifyNone) {
|
||||
int why = bad_certificate;
|
||||
|
||||
if (ret == ASN_AFTER_DATE_E || ret == ASN_BEFORE_DATE_E) {
|
||||
why = certificate_expired;
|
||||
}
|
||||
if (ssl->verifyCallback) {
|
||||
int ok;
|
||||
|
||||
store->error = ret;
|
||||
store->error_depth = args->certIdx;
|
||||
store->discardSessionCerts = 0;
|
||||
store->domain = args->domain;
|
||||
store->userCtx = ssl->verifyCbCtx;
|
||||
store->certs = args->certs;
|
||||
store->totalCerts = args->totalCerts;
|
||||
|
||||
#if defined(OPENSSL_EXTRA) || defined(HAVE_WEBSERVER)
|
||||
if (ssl->ctx->x509_store_pt != NULL) {
|
||||
store->store = ssl->ctx->x509_store_pt;
|
||||
}
|
||||
else {
|
||||
store->store = &ssl->ctx->x509_store;
|
||||
}
|
||||
#endif
|
||||
#ifdef KEEP_PEER_CERT
|
||||
if (ssl->peerCert.subject.sz > 0)
|
||||
store->current_cert = &ssl->peerCert;
|
||||
else
|
||||
store->current_cert = NULL;
|
||||
#else
|
||||
store->current_cert = NULL;
|
||||
#endif /* KEEP_PEER_CERT */
|
||||
#if defined(HAVE_EX_DATA) || defined(HAVE_FORTRESS)
|
||||
store->ex_data = ssl;
|
||||
#endif
|
||||
#ifdef SESSION_CERTS
|
||||
store->sesChain = &(ssl->session.chain);
|
||||
#endif
|
||||
ok = ssl->verifyCallback(0, store);
|
||||
if (ok) {
|
||||
WOLFSSL_MSG("Verify callback overriding error!");
|
||||
ret = 0;
|
||||
}
|
||||
#ifdef SESSION_CERTS
|
||||
if (store->discardSessionCerts) {
|
||||
WOLFSSL_MSG("Verify callback requested discard sess certs");
|
||||
ssl->session.chain.count = 0;
|
||||
#ifdef WOLFSSL_ALT_CERT_CHAINS
|
||||
ssl->session.altChain.count = 0;
|
||||
#endif
|
||||
}
|
||||
#endif /* SESSION_CERTS */
|
||||
}
|
||||
if (ret != 0) {
|
||||
SendAlert(ssl, alert_fatal, why); /* try to send */
|
||||
ssl->options.isClosed = 1;
|
||||
}
|
||||
}
|
||||
|
||||
ssl->error = ret;
|
||||
}
|
||||
#ifdef WOLFSSL_ALWAYS_VERIFY_CB
|
||||
else {
|
||||
if (ssl->verifyCallback) {
|
||||
int ok;
|
||||
|
||||
store->error = ret;
|
||||
#ifdef WOLFSSL_WPAS
|
||||
store->error_depth = 0;
|
||||
#else
|
||||
store->error_depth = args->certIdx;
|
||||
#endif
|
||||
store->discardSessionCerts = 0;
|
||||
store->domain = args->domain;
|
||||
store->userCtx = ssl->verifyCbCtx;
|
||||
store->certs = args->certs;
|
||||
store->totalCerts = args->totalCerts;
|
||||
|
||||
#if defined(OPENSSL_EXTRA) || defined(HAVE_WEBSERVER)
|
||||
if (ssl->ctx->x509_store_pt != NULL) {
|
||||
store->store = ssl->ctx->x509_store_pt;
|
||||
}
|
||||
else {
|
||||
store->store = &ssl->ctx->x509_store;
|
||||
}
|
||||
#endif
|
||||
#ifdef KEEP_PEER_CERT
|
||||
if (ssl->peerCert.subject.sz > 0)
|
||||
store->current_cert = &ssl->peerCert;
|
||||
else
|
||||
store->current_cert = NULL;
|
||||
#endif
|
||||
store->ex_data = ssl;
|
||||
#ifdef SESSION_CERTS
|
||||
store->sesChain = &(ssl->session.chain);
|
||||
#endif
|
||||
|
||||
ok = ssl->verifyCallback(1, store);
|
||||
if (!ok) {
|
||||
WOLFSSL_MSG("Verify callback overriding valid certificate!");
|
||||
ret = -1;
|
||||
SendAlert(ssl, alert_fatal, bad_certificate);
|
||||
ssl->options.isClosed = 1;
|
||||
}
|
||||
#ifdef SESSION_CERTS
|
||||
if (store->discardSessionCerts) {
|
||||
WOLFSSL_MSG("Verify callback requested discard sess certs");
|
||||
ssl->session.chain.count = 0;
|
||||
#ifdef WOLFSSL_ALT_CERT_CHAINS
|
||||
ssl->session.altChain.count = 0;
|
||||
#endif
|
||||
}
|
||||
#endif /* SESSION_CERTS */
|
||||
}
|
||||
}
|
||||
#endif /* WOLFSSL_ALWAYS_VERIFY_CB */
|
||||
/* Do verify callback */
|
||||
ret = DoVerifyCallback(ssl, ret, args);
|
||||
|
||||
if (ssl->options.verifyNone &&
|
||||
(ret == CRL_MISSING || ret == CRL_CERT_REVOKED)) {
|
||||
(ret == CRL_MISSING || ret == CRL_CERT_REVOKED)) {
|
||||
WOLFSSL_MSG("Ignoring CRL problem based on verify setting");
|
||||
ret = ssl->error = 0;
|
||||
}
|
||||
@@ -9856,13 +9697,6 @@ int ProcessPeerCerts(WOLFSSL* ssl, byte* input, word32* inOutIdx,
|
||||
args->idx += ssl->keys.padSz;
|
||||
}
|
||||
|
||||
#if defined(SESSION_CERTS) && defined(OPENSSL_EXTRA)
|
||||
wolfSSL_sk_X509_free(store->chain);
|
||||
store->chain = NULL;
|
||||
#endif
|
||||
#ifdef WOLFSSL_SMALL_STACK
|
||||
XFREE(store, ssl->heap, DYNAMIC_TYPE_X509_STORE);
|
||||
#endif
|
||||
/* Advance state and proceed */
|
||||
ssl->options.asyncState = TLS_ASYNC_END;
|
||||
} /* case TLS_ASYNC_FINALIZE */
|
||||
|
@@ -14439,6 +14439,9 @@ int wolfSSL_EVP_MD_type(const WOLFSSL_EVP_MD *md)
|
||||
WOLFSSL_X509* wolfSSL_get_peer_certificate(WOLFSSL* ssl)
|
||||
{
|
||||
WOLFSSL_ENTER("SSL_get_peer_certificate");
|
||||
if (ssl == NULL)
|
||||
return NULL;
|
||||
|
||||
if (ssl->peerCert.issuer.sz)
|
||||
return &ssl->peerCert;
|
||||
#ifdef SESSION_CERTS
|
||||
|
@@ -349,8 +349,10 @@ typedef struct WOLFSSL_BUFFER_INFO {
|
||||
|
||||
typedef struct WOLFSSL_X509_STORE_CTX {
|
||||
WOLFSSL_X509_STORE* store; /* Store full of a CA cert chain */
|
||||
WOLFSSL_X509* current_cert; /* stunnel dereference */
|
||||
WOLFSSL_X509* current_cert; /* current X509 (OPENSSL_EXTRA) */
|
||||
#ifdef WOLFSSL_ASIO
|
||||
WOLFSSL_X509* current_issuer; /* asio dereference */
|
||||
#endif
|
||||
WOLFSSL_X509_CHAIN* sesChain; /* pointer to WOLFSSL_SESSION peer chain */
|
||||
WOLFSSL_STACK* chain;
|
||||
#ifdef OPENSSL_EXTRA
|
||||
|
@@ -1408,6 +1408,18 @@ static WC_INLINE int myVerify(int preverify, WOLFSSL_X509_STORE_CTX* store)
|
||||
#endif
|
||||
(void)preverify;
|
||||
|
||||
/* Verify Callback Arguments:
|
||||
* preverify: 1=Verify Okay, 0=Failure
|
||||
* store->current_cert: Current WOLFSSL_X509 object (only with OPENSSL_EXTRA)
|
||||
* store->error_depth: Current Index
|
||||
* store->domain: Subject CN as string (null term)
|
||||
* store->totalCerts: Number of certs presented by peer
|
||||
* store->certs[i]: A `WOLFSSL_BUFFER_INFO` with plain DER for each cert
|
||||
* store->store: WOLFSSL_X509_STORE with CA cert chain
|
||||
* store->store->cm: WOLFSSL_CERT_MANAGER
|
||||
* store->ex_data: The WOLFSSL object pointer
|
||||
*/
|
||||
|
||||
printf("In verification callback, error = %d, %s\n", store->error,
|
||||
wolfSSL_ERR_error_string(store->error, buffer));
|
||||
#ifdef OPENSSL_EXTRA
|
||||
@@ -1436,9 +1448,11 @@ static WC_INLINE int myVerify(int preverify, WOLFSSL_X509_STORE_CTX* store)
|
||||
#endif
|
||||
#endif
|
||||
|
||||
printf("\tSubject's domain name is %s\n", store->domain);
|
||||
printf("\tSubject's domain name at %d is %s\n", store->error_depth, store->domain);
|
||||
|
||||
printf("\tAllowing to continue anyway (shouldn't do this, EVER!!!)\n");
|
||||
printf("\tAllowing to continue anyway (shouldn't do this)\n");
|
||||
|
||||
/* A non-zero return code indicates failure override */
|
||||
return 1;
|
||||
}
|
||||
|
||||
|
Reference in New Issue
Block a user