diff --git a/src/internal.c b/src/internal.c index f7b60d590..5065746ed 100644 --- a/src/internal.c +++ b/src/internal.c @@ -2648,6 +2648,12 @@ void FreeX509(WOLFSSL_X509* x509) #ifdef OPENSSL_EXTRA XFREE(x509->authKeyId, x509->heap, DYNAMIC_TYPE_X509_EXT); XFREE(x509->subjKeyId, x509->heap, DYNAMIC_TYPE_X509_EXT); + if (x509->authInfo != NULL) { + XFREE(x509->authInfo, x509->heap, DYNAMIC_TYPE_X509_EXT); + } + if (x509->extKeyUsageSrc != NULL) { + XFREE(x509->extKeyUsageSrc, x509->heap, DYNAMIC_TYPE_X509_EXT); + } #endif /* OPENSSL_EXTRA */ if (x509->altNames) FreeAltNames(x509->altNames, NULL); @@ -6313,6 +6319,23 @@ int CopyDecodedToX509(WOLFSSL_X509* x509, DecodedCert* dCert) x509->pathLength = dCert->pathLength; x509->keyUsage = dCert->extKeyUsage; + x509->CRLdistSet = dCert->extCRLdistSet; + x509->CRLdistCrit = dCert->extCRLdistCrit; + x509->CRLInfo = dCert->extCrlInfo; + x509->CRLInfoSz = dCert->extCrlInfoSz; + x509->authInfoSet = dCert->extAuthInfoSet; + x509->authInfoCrit = dCert->extAuthInfoCrit; + if (dCert->extAuthInfo != NULL && dCert->extAuthInfoSz > 0) { + x509->authInfo = (byte*)XMALLOC(dCert->extAuthInfoSz, x509->heap, + DYNAMIC_TYPE_X509_EXT); + if (x509->authInfo != NULL) { + XMEMCPY(x509->authInfo, dCert->extAuthInfo, dCert->extAuthInfoSz); + x509->authInfoSz = dCert->extAuthInfoSz; + } + else { + ret = MEMORY_E; + } + } x509->basicConstSet = dCert->extBasicConstSet; x509->basicConstCrit = dCert->extBasicConstCrit; x509->basicConstPlSet = dCert->pathLengthSet; @@ -6346,10 +6369,33 @@ int CopyDecodedToX509(WOLFSSL_X509* x509, DecodedCert* dCert) } x509->keyUsageSet = dCert->extKeyUsageSet; x509->keyUsageCrit = dCert->extKeyUsageCrit; + if (dCert->extExtKeyUsageSrc != NULL && dCert->extExtKeyUsageSz > 0) { + x509->extKeyUsageSrc = (byte*)XMALLOC(dCert->extExtKeyUsageSz, + x509->heap, DYNAMIC_TYPE_X509_EXT); + if (x509->extKeyUsageSrc != NULL) { + XMEMCPY(x509->extKeyUsageSrc, dCert->extExtKeyUsageSrc, + dCert->extExtKeyUsageSz); + x509->extKeyUsageSz = dCert->extExtKeyUsageSz; + x509->extKeyUsageCrit = dCert->extExtKeyUsageCrit; + x509->extKeyUsageCount = dCert->extExtKeyUsageCount; + } + else { + ret = MEMORY_E; + } + } #ifdef WOLFSSL_SEP x509->certPolicySet = dCert->extCertPolicySet; x509->certPolicyCrit = dCert->extCertPolicyCrit; #endif /* WOLFSSL_SEP */ + #ifdef WOLFSSL_CERT_EXT + { + int i; + for (i = 0; i < dCert->extCertPoliciesNb && i < MAX_CERTPOL_NB; i++) + XMEMCPY(x509->certPolicies[i], dCert->extCertPolicies[i], + MAX_CERTPOL_SZ); + x509->certPoliciesNb = dCert->extCertPoliciesNb; + } + #endif /* WOLFSSL_CERT_EXT */ #endif /* OPENSSL_EXTRA */ #ifdef HAVE_ECC x509->pkCurveOID = dCert->pkCurveOID; diff --git a/src/ssl.c b/src/ssl.c index b0d6eaaff..9aeede590 100644 --- a/src/ssl.c +++ b/src/ssl.c @@ -5733,15 +5733,298 @@ int wolfSSL_check_private_key(const WOLFSSL* ssl) } +/* Looks for the extension matching the passed in nid + * + * c : if not null then is set to status value -2 if multiple occurances + * of the extension are found, -1 if not found, 0 if found and not + * critical, and 1 if found and critical. + * nid : Extension OID to be found. + * idx : if NULL return first extension found match, otherwise start search at + * idx location and set idx to the location of extension returned. + * returns NULL or a pointer to an WOLFSSL_STACK holding extension structure + * + * NOTE code for decoding extensions is in asn.c DecodeCertExtensions -- + * use already decoded extension in this function to avoid decoding twice. + * Currently we do not make use of idx since getting pre decoded extensions. + */ void* wolfSSL_X509_get_ext_d2i(const WOLFSSL_X509* x509, int nid, int* c, int* idx) { - WOLFSSL_STUB("wolfSSL_X509_get_ext_d2i"); - (void)x509; - (void)nid; - (void)c; + WOLFSSL_STACK* sk = NULL; + WOLFSSL_ASN1_OBJECT* obj = NULL; + + WOLFSSL_ENTER("wolfSSL_X509_get_ext_d2i"); + + if (x509 == NULL) { + return NULL; + } + + if (c != NULL) { + *c = -1; /* default to not found */ + } + + sk = (STACK_OF(WOLFSSL_ASN1_OBJECT)*)XMALLOC( + sizeof(STACK_OF(WOLFSSL_ASN1_OBJECT)), NULL, DYNAMIC_TYPE_ASN1); + if (sk == NULL) { + return NULL; + } + XMEMSET(sk, 0, sizeof(STACK_OF(WOLFSSL_ASN1_OBJECT))); + + switch (nid) { + case BASIC_CA_OID: + if (x509->basicConstSet) { + obj = wolfSSL_ASN1_OBJECT_new(); + if (c != NULL) { + *c = x509->basicConstCrit; + } + obj->type = BASIC_CA_OID; + } + else { + WOLFSSL_MSG("No Basic Constraint set"); + } + break; + + case ALT_NAMES_OID: + { + DNS_entry* dns; + + if (x509->subjAltNameSet && x509->altNames != NULL) { + /* alt names are DNS_entry structs */ + if (c != NULL) { + if (x509->altNames->next != NULL) { + *c = -2; /* more then one found */ + } + else { + *c = x509->subjAltNameCrit; + } + } + + dns = x509->altNames; + while (dns != NULL) { + obj = wolfSSL_ASN1_OBJECT_new(); + obj->type = ALT_NAMES_OID; + obj->obj = (byte*)dns->name; + dns = dns->next; + /* last dns in list add at end of function */ + if (dns != NULL) { + if (wolfSSL_sk_ASN1_OBJECT_push(sk, obj) != + SSL_SUCCESS) { + WOLFSSL_MSG("Error pushing ASN1 object onto stack"); + wolfSSL_ASN1_OBJECT_free(obj); + wolfSSL_sk_ASN1_OBJECT_free(sk); + sk = NULL; + } + } + } + } + else { + WOLFSSL_MSG("No Alt Names set"); + } + } + break; + + case CRL_DIST_OID: + if (x509->CRLdistSet && x509->CRLInfo != NULL) { + if (c != NULL) { + *c = x509->CRLdistCrit; + } + obj = wolfSSL_ASN1_OBJECT_new(); + obj->type = CRL_DIST_OID; + obj->obj = x509->CRLInfo; + obj->objSz = x509->CRLInfoSz; + } + else { + WOLFSSL_MSG("No CRL dist set"); + } + break; + + case AUTH_INFO_OID: + if (x509->authInfoSet && x509->authInfo != NULL) { + if (c != NULL) { + *c = x509->authInfoCrit; + } + obj = wolfSSL_ASN1_OBJECT_new(); + obj->type = AUTH_INFO_OID; + obj->obj = x509->authInfo; + obj->objSz = x509->authInfoSz; + } + else { + WOLFSSL_MSG("No Auth Info set"); + } + break; + + case AUTH_KEY_OID: + if (x509->authKeyIdSet) { + if (c != NULL) { + *c = x509->authKeyIdCrit; + } + obj = wolfSSL_ASN1_OBJECT_new(); + obj->type = AUTH_KEY_OID; + obj->obj = x509->authKeyId; + obj->objSz = x509->authKeyIdSz; + } + else { + WOLFSSL_MSG("No Auth Key set"); + } + break; + + case SUBJ_KEY_OID: + if (x509->subjKeyIdSet) { + if (c != NULL) { + *c = x509->subjKeyIdCrit; + } + obj = wolfSSL_ASN1_OBJECT_new(); + obj->type = SUBJ_KEY_OID; + obj->obj = x509->subjKeyId; + obj->objSz = x509->subjKeyIdSz; + } + else { + WOLFSSL_MSG("No Subject Key set"); + } + break; + + case CERT_POLICY_OID: + #ifdef WOLFSSL_CERT_EXT + { + int i; + + if (x509->certPoliciesNb > 0) { + if (c != NULL) { + if (x509->certPoliciesNb > 1) { + *c = -2; + } + else { + *c = 0; + } + } + + for (i = 0; i < x509->certPoliciesNb - 1; i++) { + obj = wolfSSL_ASN1_OBJECT_new(); + obj->type = CERT_POLICY_OID; + obj->obj = (byte*)(x509->certPolicies[i]); + obj->objSz = MAX_CERTPOL_SZ; + if (wolfSSL_sk_ASN1_OBJECT_push(sk, obj) + != SSL_SUCCESS) { + WOLFSSL_MSG("Error pushing ASN1 object onto stack"); + wolfSSL_ASN1_OBJECT_free(obj); + wolfSSL_sk_ASN1_OBJECT_free(sk); + sk = NULL; + } + } + obj = wolfSSL_ASN1_OBJECT_new(); + obj->type = CERT_POLICY_OID; + obj->obj = (byte*)(x509->certPolicies[i]); + obj->objSz = MAX_CERTPOL_SZ; + } + else { + WOLFSSL_MSG("No Cert Policy set"); + } + } + #else + #ifdef WOLFSSL_SEP + if (x509->certPolicySet) { + if (c != NULL) { + *c = x509->certPolicyCrit; + } + obj = wolfSSL_ASN1_OBJECT_new(); + obj->type = CERT_POLICY_OID; + } + else { + WOLFSSL_MSG("No Cert Policy set"); + } + #else + WOLFSSL_MSG("wolfSSL not built with WOLFSSL_SEP or WOLFSSL_CERT_EXT"); + #endif /* WOLFSSL_SEP */ + #endif /* WOLFSSL_CERT_EXT */ + break; + + case KEY_USAGE_OID: + if (x509->keyUsageSet) { + if (c != NULL) { + *c = x509->keyUsageCrit; + } + obj = wolfSSL_ASN1_OBJECT_new(); + obj->type = KEY_USAGE_OID; + obj->obj = (byte*)&(x509->keyUsage); + obj->objSz = sizeof(word16); + } + else { + WOLFSSL_MSG("No Key Usage set"); + } + break; + + case INHIBIT_ANY_OID: + WOLFSSL_MSG("INHIBIT ANY extension not supported"); + break; + + case EXT_KEY_USAGE_OID: + if (x509->extKeyUsageSrc != NULL) { + if (c != NULL) { + if (x509->extKeyUsageCount > 1) { + *c = -2; + } + else { + *c = x509->extKeyUsageCrit; + } + } + obj = wolfSSL_ASN1_OBJECT_new(); + obj->type = EXT_KEY_USAGE_OID; + obj->obj = x509->extKeyUsageSrc; + obj->objSz = x509->extKeyUsageSz; + } + else { + WOLFSSL_MSG("No Extended Key Usage set"); + } + break; + + case NAME_CONS_OID: + WOLFSSL_MSG("Name Constraint OID extension not supported"); + break; + + case PRIV_KEY_USAGE_PERIOD_OID: + WOLFSSL_MSG("Private Key Usage Period extension not supported"); + break; + + case SUBJECT_INFO_ACCESS: + WOLFSSL_MSG("Subject Info Access extension not supported"); + break; + + case POLICY_MAP_OID: + WOLFSSL_MSG("Policy Map extension not supported"); + break; + + case POLICY_CONST_OID: + WOLFSSL_MSG("Policy Constraint extension not supported"); + break; + + case ISSUE_ALT_NAMES_OID: + WOLFSSL_MSG("Issue Alt Names extension not supported"); + break; + + case TLS_FEATURE_OID: + WOLFSSL_MSG("TLS Feature extension not supported"); + break; + + default: + WOLFSSL_MSG("Unsupported/Unknown extension OID"); + } + + if (obj != NULL) { + if (wolfSSL_sk_ASN1_OBJECT_push(sk, obj) != SSL_SUCCESS) { + WOLFSSL_MSG("Error pushing ASN1 object onto stack"); + wolfSSL_ASN1_OBJECT_free(obj); + wolfSSL_sk_ASN1_OBJECT_free(sk); + sk = NULL; + } + } + else { /* no ASN1 object found for extension, free stack */ + wolfSSL_sk_ASN1_OBJECT_free(sk); + sk = NULL; + } + (void)idx; - return NULL; + + return sk; } @@ -12333,6 +12616,101 @@ WOLFSSL_X509* wolfSSL_get_certificate(WOLFSSL* ssl) #ifdef OPENSSL_EXTRA +/* return 1 on success 0 on fail */ +int wolfSSL_sk_ASN1_OBJECT_push(STACK_OF(WOLFSSL_ASN1_OBJEXT)* sk, + WOLFSSL_ASN1_OBJECT* obj) +{ + WOLFSSL_STACK* node; + + if (sk == NULL || obj == NULL) { + return SSL_FAILURE; + } + + /* no previous values in stack */ + if (sk->data.obj == NULL) { + sk->data.obj = obj; + sk->num += 1; + return SSL_SUCCESS; + } + + /* stack already has value(s) create a new node and add more */ + node = (WOLFSSL_STACK*)XMALLOC(sizeof(WOLFSSL_STACK), NULL, + DYNAMIC_TYPE_ASN1); + if (node == NULL) { + WOLFSSL_MSG("Memory error"); + return SSL_FAILURE; + } + XMEMSET(node, 0, sizeof(WOLFSSL_STACK)); + + /* push new obj onto head of stack */ + node->data.obj = sk->data.obj; + node->next = sk->next; + sk->next = node; + sk->data.obj = obj; + sk->num += 1; + + return SSL_SUCCESS; +} + + +WOLFSSL_ASN1_OBJECT* wolfSSL_sk_ASN1_OBJCET_pop( + STACK_OF(WOLFSSL_ASN1_OBJECT)* sk) +{ + WOLFSSL_STACK* node; + WOLFSSL_ASN1_OBJECT* obj; + + if (sk == NULL) { + return NULL; + } + + node = sk->next; + obj = sk->data.obj; + + if (node != NULL) { /* update sk and remove node from stack */ + sk->data.obj = node->data.obj; + sk->next = node->next; + XFREE(node, NULL, DYNAMIC_TYPE_ASN1); + } + else { /* last obj in stack */ + sk->data.obj = NULL; + } + + if (sk->num > 0) { + sk->num -= 1; + } + + return obj; +} + + +/* free structure for x509 stack */ +void wolfSSL_sk_ASN1_OBJECT_free(STACK_OF(WOLFSSL_ASN1_OBJECT)* sk) +{ + WOLFSSL_STACK* node; + + if (sk == NULL) { + return; + } + + /* parse through stack freeing each node */ + node = sk->next; + while (sk->num > 1) { + WOLFSSL_STACK* tmp = node; + node = node->next; + + wolfSSL_ASN1_OBJECT_free(tmp->data.obj); + XFREE(tmp, NULL, DYNAMIC_TYPE_ASN1); + sk->num -= 1; + } + + /* free head of stack */ + if (sk->num == 1) { + wolfSSL_ASN1_OBJECT_free(sk->data.obj); + } + XFREE(sk, NULL, DYNAMIC_TYPE_ASN1); +} + + int wolfSSL_set_session_id_context(WOLFSSL* ssl, const unsigned char* id, unsigned int len) { diff --git a/tests/api.c b/tests/api.c index 86db69b24..ff3b72d72 100644 --- a/tests/api.c +++ b/tests/api.c @@ -2253,6 +2253,8 @@ static void test_wolfSSL_certs(void) X509* x509; WOLFSSL* ssl; WOLFSSL_CTX* ctx; + STACK_OF(ASN1_OBJECT)* sk; + int crit; printf(testingFmt, "wolfSSL_certs()"); @@ -2285,12 +2287,94 @@ static void test_wolfSSL_certs(void) SSL_use_PrivateKey_ASN1 SSL_use_RSAPrivateKey_ASN1 SSL_X509_digest - SSL_X509_get_ext_d2i */ - SSL_free(ssl); + /* test and checkout X509 extensions */ + sk = X509_get_ext_d2i(x509, NID_basic_constraints, &crit, NULL); + AssertNotNull(sk); + AssertIntEQ(crit, 0); + wolfSSL_sk_ASN1_OBJECT_free(sk); + + sk = X509_get_ext_d2i(x509, NID_key_usage, &crit, NULL); + /* AssertNotNull(sk); NID not yet supported */ + AssertIntEQ(crit, -1); + wolfSSL_sk_ASN1_OBJECT_free(sk); + + sk = X509_get_ext_d2i(x509, NID_ext_key_usage, &crit, NULL); + AssertNotNull(sk); + AssertIntEQ(crit, -2); /* multiple cases */ + wolfSSL_sk_ASN1_OBJECT_free(sk); + + sk = X509_get_ext_d2i(x509, NID_authority_key_identifier, &crit, NULL); + AssertNotNull(sk); + wolfSSL_sk_ASN1_OBJECT_free(sk); + + sk = X509_get_ext_d2i(x509, NID_private_key_usage_period, &crit, NULL); + /* AssertNotNull(sk); NID not yet supported */ + AssertIntEQ(crit, -1); + wolfSSL_sk_ASN1_OBJECT_free(sk); + + sk = X509_get_ext_d2i(x509, NID_subject_alt_name, &crit, NULL); + /* AssertNotNull(sk); no alt names set */ + wolfSSL_sk_ASN1_OBJECT_free(sk); + + sk = X509_get_ext_d2i(x509, NID_issuer_alt_name, &crit, NULL); + /* AssertNotNull(sk); NID not yet supported */ + AssertIntEQ(crit, -1); + wolfSSL_sk_ASN1_OBJECT_free(sk); + + sk = X509_get_ext_d2i(x509, NID_info_access, &crit, NULL); + /* AssertNotNull(sk); no auth info set */ + wolfSSL_sk_ASN1_OBJECT_free(sk); + + sk = X509_get_ext_d2i(x509, NID_sinfo_access, &crit, NULL); + /* AssertNotNull(sk); NID not yet supported */ + AssertIntEQ(crit, -1); + wolfSSL_sk_ASN1_OBJECT_free(sk); + + sk = X509_get_ext_d2i(x509, NID_name_constraints, &crit, NULL); + /* AssertNotNull(sk); NID not yet supported */ + AssertIntEQ(crit, -1); + wolfSSL_sk_ASN1_OBJECT_free(sk); + + sk = X509_get_ext_d2i(x509, NID_certificate_policies, &crit, NULL); + #if !defined(WOLFSSL_SEP) && !defined(WOLFSSL_CERT_EXT) + AssertNull(sk); + #else + /* AssertNotNull(sk); no cert policy set */ + #endif + wolfSSL_sk_ASN1_OBJECT_free(sk); + + sk = X509_get_ext_d2i(x509, NID_policy_mappings, &crit, NULL); + /* AssertNotNull(sk); NID not yet supported */ + AssertIntEQ(crit, -1); + wolfSSL_sk_ASN1_OBJECT_free(sk); + + sk = X509_get_ext_d2i(x509, NID_policy_constraints, &crit, NULL); + /* AssertNotNull(sk); NID not yet supported */ + AssertIntEQ(crit, -1); + wolfSSL_sk_ASN1_OBJECT_free(sk); + + sk = X509_get_ext_d2i(x509, NID_inhibit_any_policy, &crit, NULL); + /* AssertNotNull(sk); NID not yet supported */ + AssertIntEQ(crit, -1); + wolfSSL_sk_ASN1_OBJECT_free(sk); + + sk = X509_get_ext_d2i(x509, NID_tlsfeature, &crit, NULL); + /* AssertNotNull(sk); NID not yet supported */ + AssertIntEQ(crit, -1); + wolfSSL_sk_ASN1_OBJECT_free(sk); + + /* test invalid cases */ + crit = 0; + sk = X509_get_ext_d2i(x509, -1, &crit, NULL); + AssertNull(sk); + AssertIntEQ(crit, -1); + sk = X509_get_ext_d2i(NULL, NID_tlsfeature, NULL, NULL); + AssertNull(sk); + + SSL_free(ssl); /* frees x509 also since loaded into ssl */ SSL_CTX_free(ctx); - X509_free(x509); printf(resultFmt, passed); #endif /* defined(OPENSSL_EXTRA) && !defined(NO_CERTS) */ diff --git a/wolfcrypt/src/asn.c b/wolfcrypt/src/asn.c index 665199aeb..7c6cc171f 100755 --- a/wolfcrypt/src/asn.c +++ b/wolfcrypt/src/asn.c @@ -1398,6 +1398,38 @@ int GetObjectId(const byte* input, word32* inOutIdx, word32* oid, } +WOLFSSL_ASN1_OBJECT* wolfSSL_ASN1_OBJECT_new(void) +{ + WOLFSSL_ASN1_OBJECT* obj; + + obj = (WOLFSSL_ASN1_OBJECT*)XMALLOC(sizeof(WOLFSSL_ASN1_OBJECT), NULL, + DYNAMIC_TYPE_ASN1); + if (obj == NULL) { + return NULL; + } + + XMEMSET(obj, 0, sizeof(WOLFSSL_ASN1_OBJECT)); + return obj; +} + + +void wolfSSL_ASN1_OBJECT_free(WOLFSSL_ASN1_OBJECT* obj) +{ + if (obj == NULL) { + return; + } + + if (obj->dynamic == 1) { + if (obj->obj != NULL) { + WOLFSSL_MSG("Freeing ASN1 OBJECT data"); + XFREE(obj->obj, obj->heap, DYNAMIC_TYPE_ASN1); + } + } + + XFREE(obj, NULL, DYNAMIC_TYPE_ASN1); +} + + #ifndef NO_RSA #ifndef HAVE_USER_RSA #if defined(OPENSSL_EXTRA) || defined(RSA_DECODE_EXTRA) @@ -2560,6 +2592,10 @@ void InitDecodedCert(DecodedCert* cert, byte* source, word32 inSz, void* heap) #ifdef OPENSSL_EXTRA XMEMSET(&cert->issuerName, 0, sizeof(DecodedName)); XMEMSET(&cert->subjectName, 0, sizeof(DecodedName)); + cert->extCRLdistSet = 0; + cert->extCRLdistCrit = 0; + cert->extAuthInfoSet = 0; + cert->extAuthInfoCrit = 0; cert->extBasicConstSet = 0; cert->extBasicConstCrit = 0; cert->extSubjAltNameSet = 0; @@ -5206,11 +5242,19 @@ static int DecodeCertExtensions(DecodedCert* cert) break; case CRL_DIST_OID: + #ifdef OPENSSL_EXTRA + cert->extCRLdistSet = 1; + cert->extCRLdistCrit = critical; + #endif if (DecodeCrlDist(&input[idx], length, cert) < 0) return ASN_PARSE_E; break; case AUTH_INFO_OID: + #ifdef OPENSSL_EXTRA + cert->extAuthInfoSet = 1; + cert->extAuthInfoCrit = critical; + #endif if (DecodeAuthInfo(&input[idx], length, cert) < 0) return ASN_PARSE_E; break; diff --git a/wolfssl/internal.h b/wolfssl/internal.h index 92d09f570..62e6bb58c 100644 --- a/wolfssl/internal.h +++ b/wolfssl/internal.h @@ -2503,6 +2503,7 @@ struct WOLFSSL_STACK { union { WOLFSSL_X509* x509; WOLFSSL_BIO* bio; + WOLFSSL_ASN1_OBJECT* obj; } data; WOLFSSL_STACK* next; }; @@ -2566,9 +2567,21 @@ struct WOLFSSL_X509 { void* heap; /* heap hint */ byte dynamicMemory; /* dynamic memory flag */ byte isCa; +#ifdef WOLFSSL_CERT_EXT + char certPolicies[MAX_CERTPOL_NB][MAX_CERTPOL_SZ]; + int certPoliciesNb; +#endif /* WOLFSSL_CERT_EXT */ #ifdef OPENSSL_EXTRA word32 pathLength; word16 keyUsage; + byte CRLdistSet; + byte CRLdistCrit; + byte* CRLInfo; + int CRLInfoSz; + byte authInfoSet; + byte authInfoCrit; + byte* authInfo; + int authInfoSz; byte basicConstSet; byte basicConstCrit; byte basicConstPlSet; @@ -2584,6 +2597,10 @@ struct WOLFSSL_X509 { word32 subjKeyIdSz; byte keyUsageSet; byte keyUsageCrit; + byte extKeyUsageCrit; + byte* extKeyUsageSrc; + word32 extKeyUsageSz; + word32 extKeyUsageCount; #endif /* OPENSSL_EXTRA */ }; diff --git a/wolfssl/openssl/ssl.h b/wolfssl/openssl/ssl.h index 1776e4f53..e6d2a8d28 100644 --- a/wolfssl/openssl/ssl.h +++ b/wolfssl/openssl/ssl.h @@ -81,6 +81,11 @@ typedef WOLFSSL_ASN1_OBJECT ASN1_OBJECT; typedef WOLFSSL_ASN1_STRING ASN1_STRING; typedef WOLFSSL_dynlock_value CRYPTO_dynlock_value; +/* GENERAL_NAME and BASIC_CONSTRAINTS structs may need implemented as + * compatibility layer expands. For now treating them as an ASN1_OBJECT */ +typedef WOLFSSL_ASN1_OBJECT GENERAL_NAME; +typedef WOLFSSL_ASN1_OBJECT BASIC_CONSTRAINTS; + #define ASN1_UTCTIME WOLFSSL_ASN1_TIME typedef WOLFSSL_MD4_CTX MD4_CTX; @@ -213,8 +218,8 @@ typedef WOLFSSL_X509_STORE_CTX X509_STORE_CTX; #define SSL_SESSION_get_master_key_length wolfSSL_SESSION_get_master_key_length #define SSL_X509_NAME_get_text_by_NID wolfSSL_X509_NAME_get_text_by_NID -#define SSL_X509_get_ext_d2i wolfSSL_X509_get_ext_d2i -#define SSL_X509_digest wolfSSL_X509_digest +#define X509_get_ext_d2i wolfSSL_X509_get_ext_d2i +#define X509_digest wolfSSL_X509_digest #define X509_free wolfSSL_X509_free #define OPENSSL_free wolfSSL_OPENSSL_free @@ -640,6 +645,24 @@ typedef WOLFSSL_ASN1_BIT_STRING ASN1_BIT_STRING; #endif /* HAVE_STUNNEL */ +/* certificate extension NIDs */ +#define NID_basic_constraints 133 +#define NID_key_usage 129 /* 2.5.29.15 */ +#define NID_ext_key_usage 151 /* 2.5.29.37 */ +#define NID_subject_key_identifier 128 +#define NID_authority_key_identifier 149 +#define NID_private_key_usage_period 130 /* 2.5.29.16 */ +#define NID_subject_alt_name 131 +#define NID_issuer_alt_name 132 +#define NID_info_access 69 +#define NID_sinfo_access 79 /* id-pe 11 */ +#define NID_name_constraints 144 /* 2.5.29.30 */ +#define NID_certificate_policies 146 +#define NID_policy_mappings 147 +#define NID_policy_constraints 150 +#define NID_inhibit_any_policy 168 /* 2.5.29.54 */ +#define NID_tlsfeature 92 /* id-pe 24 */ + #ifdef __cplusplus } /* extern "C" */ #endif diff --git a/wolfssl/ssl.h b/wolfssl/ssl.h index b90718a12..d9cf756df 100644 --- a/wolfssl/ssl.h +++ b/wolfssl/ssl.h @@ -444,6 +444,12 @@ WOLFSSL_API int wolfSSL_sk_X509_push(STACK_OF(WOLFSSL_X509_NAME)* sk, WOLFSSL_API WOLFSSL_X509* wolfSSL_sk_X509_pop(STACK_OF(WOLFSSL_X509_NAME)* sk); WOLFSSL_API void wolfSSL_sk_X509_free(STACK_OF(WOLFSSL_X509_NAME)* sk); +WOLFSSL_API int wolfSSL_sk_ASN1_OBJECT_push(STACK_OF(WOLFSSL_ASN1_OBJEXT)* sk, + WOLFSSL_ASN1_OBJECT* obj); +WOLFSSL_API WOLFSSL_ASN1_OBJECT* wolfSSL_sk_ASN1_OBJCET_pop( + STACK_OF(WOLFSSL_ASN1_OBJECT)* sk); +WOLFSSL_API void wolfSSL_sk_ASN1_OBJECT_free(STACK_OF(WOLFSSL_ASN1_OBJECT)* sk); + WOLFSSL_API int wolfSSL_set_ex_data(WOLFSSL*, int, void*); WOLFSSL_API int wolfSSL_get_shutdown(const WOLFSSL*); WOLFSSL_API int wolfSSL_set_rfd(WOLFSSL*, int); diff --git a/wolfssl/wolfcrypt/asn.h b/wolfssl/wolfcrypt/asn.h index fdb8dc7dc..2499cf42f 100644 --- a/wolfssl/wolfcrypt/asn.h +++ b/wolfssl/wolfcrypt/asn.h @@ -303,14 +303,20 @@ enum Extensions_Sum { BASIC_CA_OID = 133, ALT_NAMES_OID = 131, CRL_DIST_OID = 145, - AUTH_INFO_OID = 69, + AUTH_INFO_OID = 69, /* id-pe 1 */ AUTH_KEY_OID = 149, SUBJ_KEY_OID = 128, CERT_POLICY_OID = 146, KEY_USAGE_OID = 129, /* 2.5.29.15 */ INHIBIT_ANY_OID = 168, /* 2.5.29.54 */ - EXT_KEY_USAGE_OID = 151, /* 2.5.29.37 */ - NAME_CONS_OID = 144 /* 2.5.29.30 */ + EXT_KEY_USAGE_OID = 151, /* 2.5.29.37 */ + NAME_CONS_OID = 144, /* 2.5.29.30 */ + PRIV_KEY_USAGE_PERIOD_OID = 130, /* 2.5.29.16 */ + SUBJECT_INFO_ACCESS = 79, /* id-pe 11 */ + POLICY_MAP_OID = 147, + POLICY_CONST_OID = 150, + ISSUE_ALT_NAMES_OID = 132, + TLS_FEATURE_OID = 92 /* id-pe 24 */ }; enum CertificatePolicy_Sum { @@ -475,6 +481,10 @@ struct DecodedCert { byte extExtKeyUsageSet; /* Extended Key Usage */ byte extExtKeyUsage; /* Extended Key usage bitfield */ #ifdef OPENSSL_EXTRA + byte extCRLdistSet; + byte extCRLdistCrit; + byte extAuthInfoSet; + byte extAuthInfoCrit; byte extBasicConstSet; byte extBasicConstCrit; byte extSubjAltNameSet; @@ -554,6 +564,16 @@ struct DecodedCert { #endif /* WOLFSSL_CERT_EXT */ }; + +struct WOLFSSL_ASN1_OBJECT { + void* heap; + byte* obj; + int type; /* oid */ + word32 objSz; + byte dynamic; /* if 1 then obj was dynamiclly created, 0 otherwise */ +}; + + extern const char* BEGIN_CERT; extern const char* END_CERT; extern const char* BEGIN_CERT_REQ; diff --git a/wolfssl/wolfcrypt/asn_public.h b/wolfssl/wolfcrypt/asn_public.h index c9d95459d..f0f9eaf5a 100644 --- a/wolfssl/wolfcrypt/asn_public.h +++ b/wolfssl/wolfcrypt/asn_public.h @@ -159,6 +159,7 @@ typedef struct Cert { } Cert; #endif /* WOLFSSL_CERT_GEN */ +typedef struct WOLFSSL_ASN1_OBJECT WOLFSSL_ASN1_OBJECT; #ifdef WOLFSSL_CERT_GEN @@ -280,6 +281,9 @@ WOLFSSL_API int wc_GetCTC_HashOID(int type); */ WOLFSSL_API int wc_GetTime(void* timePtr, word32 timeSize); +WOLFSSL_API WOLFSSL_ASN1_OBJECT* wolfSSL_ASN1_OBJECT_new(void); +WOLFSSL_API void wolfSSL_ASN1_OBJECT_free(WOLFSSL_ASN1_OBJECT* obj); + #ifdef __cplusplus } /* extern "C" */ #endif diff --git a/wolfssl/wolfcrypt/types.h b/wolfssl/wolfcrypt/types.h index ac20cae99..53687bf7d 100644 --- a/wolfssl/wolfcrypt/types.h +++ b/wolfssl/wolfcrypt/types.h @@ -339,7 +339,8 @@ DYNAMIC_TYPE_SESSION_TICK = 57, DYNAMIC_TYPE_PKCS = 58, DYNAMIC_TYPE_MUTEX = 59, - DYNAMIC_TYPE_PKCS7 = 60 + DYNAMIC_TYPE_PKCS7 = 60, + DYNAMIC_TYPE_ASN1 = 61 }; /* max error buffer string size */