Added check to enforce RFC 5280 Sec 4.2: "A certificate MUST NOT include more than one instance of a particular extension". Refactor of the DecodedCert struct to combine bit type options into bit-fields. Fix for wolfCrypt test for error codes to allow -161.

This commit is contained in:
David Garske
2018-02-06 14:33:03 -08:00
parent d9002bb072
commit d78e45dbb6
3 changed files with 88 additions and 42 deletions

View File

@ -6175,6 +6175,30 @@ int DecodePolicyOID(char *out, word32 outSz, byte *in, word32 inSz)
} }
#endif /* WOLFSSL_SEP */ #endif /* WOLFSSL_SEP */
/* Macro to check if bit is set, if not sets and return success.
Otherwise returns failure */
#ifndef WOLFSSL_NO_ASN_STRICT
#define VERIFY_AND_SET_OID(bit) \
({ \
int bitvalid; \
if (bit == 0) { \
bit = 1; \
bitvalid = 0; /* success */ \
} \
else { \
bitvalid = -1; /* fail */ \
} \
bitvalid; \
})
#else
/* With no strict defined, the verify is skipped */
#define VERIFY_AND_SET_OID(bit) \
({ \
bit = 1; \
0; /* success */ \
})
#endif
static int DecodeCertExtensions(DecodedCert* cert) static int DecodeCertExtensions(DecodedCert* cert)
/* /*
* Processing the Certificate Extensions. This does not modify the current * Processing the Certificate Extensions. This does not modify the current
@ -6243,8 +6267,9 @@ static int DecodeCertExtensions(DecodedCert* cert)
switch (oid) { switch (oid) {
case BASIC_CA_OID: case BASIC_CA_OID:
if (VERIFY_AND_SET_OID(cert->extBasicConstSet))
return ASN_OBJECT_ID_E;
#ifdef OPENSSL_EXTRA #ifdef OPENSSL_EXTRA
cert->extBasicConstSet = 1;
cert->extBasicConstCrit = critical; cert->extBasicConstCrit = critical;
#endif #endif
if (DecodeBasicCaConstraint(&input[idx], length, cert) < 0) if (DecodeBasicCaConstraint(&input[idx], length, cert) < 0)
@ -6252,8 +6277,9 @@ static int DecodeCertExtensions(DecodedCert* cert)
break; break;
case CRL_DIST_OID: case CRL_DIST_OID:
if (VERIFY_AND_SET_OID(cert->extCRLdistSet))
return ASN_OBJECT_ID_E;
#ifdef OPENSSL_EXTRA #ifdef OPENSSL_EXTRA
cert->extCRLdistSet = 1;
cert->extCRLdistCrit = critical; cert->extCRLdistCrit = critical;
#endif #endif
if (DecodeCrlDist(&input[idx], length, cert) < 0) if (DecodeCrlDist(&input[idx], length, cert) < 0)
@ -6261,8 +6287,9 @@ static int DecodeCertExtensions(DecodedCert* cert)
break; break;
case AUTH_INFO_OID: case AUTH_INFO_OID:
if (VERIFY_AND_SET_OID(cert->extAuthInfoSet))
return ASN_OBJECT_ID_E;
#ifdef OPENSSL_EXTRA #ifdef OPENSSL_EXTRA
cert->extAuthInfoSet = 1;
cert->extAuthInfoCrit = critical; cert->extAuthInfoCrit = critical;
#endif #endif
if (DecodeAuthInfo(&input[idx], length, cert) < 0) if (DecodeAuthInfo(&input[idx], length, cert) < 0)
@ -6270,8 +6297,9 @@ static int DecodeCertExtensions(DecodedCert* cert)
break; break;
case ALT_NAMES_OID: case ALT_NAMES_OID:
if (VERIFY_AND_SET_OID(cert->extSubjAltNameSet))
return ASN_OBJECT_ID_E;
#ifdef OPENSSL_EXTRA #ifdef OPENSSL_EXTRA
cert->extSubjAltNameSet = 1;
cert->extSubjAltNameCrit = critical; cert->extSubjAltNameCrit = critical;
#endif #endif
ret = DecodeAltNames(&input[idx], length, cert); ret = DecodeAltNames(&input[idx], length, cert);
@ -6280,7 +6308,8 @@ static int DecodeCertExtensions(DecodedCert* cert)
break; break;
case AUTH_KEY_OID: case AUTH_KEY_OID:
cert->extAuthKeyIdSet = 1; if (VERIFY_AND_SET_OID(cert->extAuthKeyIdSet))
return ASN_OBJECT_ID_E;
#ifdef OPENSSL_EXTRA #ifdef OPENSSL_EXTRA
cert->extAuthKeyIdCrit = critical; cert->extAuthKeyIdCrit = critical;
#endif #endif
@ -6289,7 +6318,8 @@ static int DecodeCertExtensions(DecodedCert* cert)
break; break;
case SUBJ_KEY_OID: case SUBJ_KEY_OID:
cert->extSubjKeyIdSet = 1; if (VERIFY_AND_SET_OID(cert->extSubjKeyIdSet))
return ASN_OBJECT_ID_E;
#ifdef OPENSSL_EXTRA #ifdef OPENSSL_EXTRA
cert->extSubjKeyIdCrit = critical; cert->extSubjKeyIdCrit = critical;
#endif #endif
@ -6311,8 +6341,9 @@ static int DecodeCertExtensions(DecodedCert* cert)
case CERT_POLICY_OID: case CERT_POLICY_OID:
#ifdef WOLFSSL_SEP #ifdef WOLFSSL_SEP
if (VERIFY_AND_SET_OID(cert->extCertPolicySet))
return ASN_OBJECT_ID_E;
#ifdef OPENSSL_EXTRA #ifdef OPENSSL_EXTRA
cert->extCertPolicySet = 1;
cert->extCertPolicyCrit = critical; cert->extCertPolicyCrit = critical;
#endif #endif
#endif #endif
@ -6326,7 +6357,8 @@ static int DecodeCertExtensions(DecodedCert* cert)
break; break;
case KEY_USAGE_OID: case KEY_USAGE_OID:
cert->extKeyUsageSet = 1; if (VERIFY_AND_SET_OID(cert->extKeyUsageSet))
return ASN_OBJECT_ID_E;
#ifdef OPENSSL_EXTRA #ifdef OPENSSL_EXTRA
cert->extKeyUsageCrit = critical; cert->extKeyUsageCrit = critical;
#endif #endif
@ -6335,7 +6367,8 @@ static int DecodeCertExtensions(DecodedCert* cert)
break; break;
case EXT_KEY_USAGE_OID: case EXT_KEY_USAGE_OID:
cert->extExtKeyUsageSet = 1; if (VERIFY_AND_SET_OID(cert->extExtKeyUsageSet))
return ASN_OBJECT_ID_E;
#ifdef OPENSSL_EXTRA #ifdef OPENSSL_EXTRA
cert->extExtKeyUsageCrit = critical; cert->extExtKeyUsageCrit = critical;
#endif #endif
@ -6354,7 +6387,8 @@ static int DecodeCertExtensions(DecodedCert* cert)
return ASN_NAME_INVALID_E; return ASN_NAME_INVALID_E;
} }
#endif #endif
cert->extNameConstraintSet = 1; if (VERIFY_AND_SET_OID(cert->extNameConstraintSet))
return ASN_OBJECT_ID_E;
#ifdef OPENSSL_EXTRA #ifdef OPENSSL_EXTRA
cert->extNameConstraintCrit = critical; cert->extNameConstraintCrit = critical;
#endif #endif
@ -6364,6 +6398,8 @@ static int DecodeCertExtensions(DecodedCert* cert)
#endif /* IGNORE_NAME_CONSTRAINTS */ #endif /* IGNORE_NAME_CONSTRAINTS */
case INHIBIT_ANY_OID: case INHIBIT_ANY_OID:
if (VERIFY_AND_SET_OID(cert->inhibitAnyOidSet))
return ASN_OBJECT_ID_E;
WOLFSSL_MSG("Inhibit anyPolicy extension not supported yet."); WOLFSSL_MSG("Inhibit anyPolicy extension not supported yet.");
break; break;

View File

@ -1026,7 +1026,7 @@ int error_test(void)
int j = 0; int j = 0;
/* Values that are not or no longer error codes. */ /* Values that are not or no longer error codes. */
int missing[] = { -122, -123, -124, -127, -128, -129, int missing[] = { -122, -123, -124, -127, -128, -129,
-161, -162, -163, -164, -165, -166, -167, -168, -169, -162, -163, -164, -165, -166, -167, -168, -169,
-179, -233, -179, -233,
0 }; 0 };

View File

@ -549,7 +549,6 @@ struct DecodedCert {
char* subjectCN; /* CommonName */ char* subjectCN; /* CommonName */
int subjectCNLen; /* CommonName Length */ int subjectCNLen; /* CommonName Length */
char subjectCNEnc; /* CommonName Encoding */ char subjectCNEnc; /* CommonName Encoding */
int subjectCNStored; /* have we saved a copy we own */
char issuer[ASN_NAME_MAX]; /* full name including common name */ char issuer[ASN_NAME_MAX]; /* full name including common name */
char subject[ASN_NAME_MAX]; /* full name including common name */ char subject[ASN_NAME_MAX]; /* full name including common name */
int verify; /* Default to yes, but could be off */ int verify; /* Default to yes, but could be off */
@ -567,36 +566,12 @@ struct DecodedCert {
byte* extCrlInfo; /* CRL Distribution Points */ byte* extCrlInfo; /* CRL Distribution Points */
int extCrlInfoSz; /* length of the URI */ int extCrlInfoSz; /* length of the URI */
byte extSubjKeyId[KEYID_SIZE]; /* Subject Key ID */ byte extSubjKeyId[KEYID_SIZE]; /* Subject Key ID */
byte extSubjKeyIdSet; /* Set when the SKID was read from cert */
byte extAuthKeyId[KEYID_SIZE]; /* Authority Key ID */ byte extAuthKeyId[KEYID_SIZE]; /* Authority Key ID */
byte extAuthKeyIdSet; /* Set when the AKID was read from cert */
#ifndef IGNORE_NAME_CONSTRAINTS
byte extNameConstraintSet;
#endif /* IGNORE_NAME_CONSTRAINTS */
byte isCA; /* CA basic constraint true */
byte pathLengthSet; /* CA basic const path length set */
byte pathLength; /* CA basic constraint path length */ byte pathLength; /* CA basic constraint path length */
byte weOwnAltNames; /* altNames haven't been given to copy */
byte extKeyUsageSet;
word16 extKeyUsage; /* Key usage bitfield */ word16 extKeyUsage; /* Key usage bitfield */
byte extExtKeyUsageSet; /* Extended Key Usage */
byte extExtKeyUsage; /* Extended Key usage bitfield */ byte extExtKeyUsage; /* Extended Key usage bitfield */
#ifdef OPENSSL_EXTRA #ifdef OPENSSL_EXTRA
byte extCRLdistSet;
byte extCRLdistCrit;
byte extAuthInfoSet;
byte extAuthInfoCrit;
byte extBasicConstSet;
byte extBasicConstCrit;
byte extSubjAltNameSet;
byte extSubjAltNameCrit;
byte extAuthKeyIdCrit;
#ifndef IGNORE_NAME_CONSTRAINTS
byte extNameConstraintCrit;
#endif /* IGNORE_NAME_CONSTRAINTS */
byte extSubjKeyIdCrit;
byte extKeyUsageCrit;
byte extExtKeyUsageCrit;
byte* extExtKeyUsageSrc; byte* extExtKeyUsageSrc;
word32 extExtKeyUsageSz; word32 extExtKeyUsageSz;
word32 extExtKeyUsageCount; word32 extExtKeyUsageCount;
@ -605,6 +580,7 @@ struct DecodedCert {
byte* extSubjKeyIdSrc; byte* extSubjKeyIdSrc;
word32 extSubjKeyIdSz; word32 extSubjKeyIdSz;
#endif #endif
#if defined(HAVE_ECC) || defined(HAVE_ED25519) #if defined(HAVE_ECC) || defined(HAVE_ED25519)
word32 pkCurveOID; /* Public Key's curve OID */ word32 pkCurveOID; /* Public Key's curve OID */
#endif /* HAVE_ECC */ #endif /* HAVE_ECC */
@ -620,7 +596,7 @@ struct DecodedCert {
byte* subjectRaw; /* pointer to subject inside source */ byte* subjectRaw; /* pointer to subject inside source */
int subjectRawLen; int subjectRawLen;
#endif #endif
#if defined(WOLFSSL_CERT_GEN) #ifdef WOLFSSL_CERT_GEN
/* easy access to subject info for other sign */ /* easy access to subject info for other sign */
char* subjectSN; char* subjectSN;
int subjectSNLen; int subjectSNLen;
@ -654,10 +630,6 @@ struct DecodedCert {
byte* hwType; byte* hwType;
int hwSerialNumSz; int hwSerialNumSz;
byte* hwSerialNum; byte* hwSerialNum;
#ifdef OPENSSL_EXTRA
byte extCertPolicySet;
byte extCertPolicyCrit;
#endif /* OPENSSL_EXTRA */
#endif /* WOLFSSL_SEP */ #endif /* WOLFSSL_SEP */
#ifdef WOLFSSL_CERT_EXT #ifdef WOLFSSL_CERT_EXT
char extCertPolicies[MAX_CERTPOL_NB][MAX_CERTPOL_SZ]; char extCertPolicies[MAX_CERTPOL_NB][MAX_CERTPOL_SZ];
@ -666,6 +638,44 @@ struct DecodedCert {
Signer* ca; Signer* ca;
SignatureCtx sigCtx; SignatureCtx sigCtx;
/* Option Bits */
byte subjectCNStored : 1; /* have we saved a copy we own */
byte extSubjKeyIdSet : 1; /* Set when the SKID was read from cert */
byte extAuthKeyIdSet : 1; /* Set when the AKID was read from cert */
#ifndef IGNORE_NAME_CONSTRAINTS
byte extNameConstraintSet : 1;
#endif
byte isCA : 1; /* CA basic constraint true */
byte pathLengthSet : 1; /* CA basic const path length set */
byte weOwnAltNames : 1; /* altNames haven't been given to copy */
byte extKeyUsageSet : 1;
byte extExtKeyUsageSet : 1; /* Extended Key Usage set */
byte extCRLdistSet : 1;
byte extAuthInfoSet : 1;
byte extBasicConstSet : 1;
byte extSubjAltNameSet : 1;
byte inhibitAnyOidSet : 1;
#ifdef WOLFSSL_SEP
byte extCertPolicySet : 1;
#endif
#ifdef OPENSSL_EXTRA
byte extCRLdistCrit : 1;
byte extAuthInfoCrit : 1;
byte extBasicConstCrit : 1;
byte extSubjAltNameCrit : 1;
byte extAuthKeyIdCrit : 1;
#ifndef IGNORE_NAME_CONSTRAINTS
byte extNameConstraintCrit : 1;
#endif
byte extSubjKeyIdCrit : 1;
byte extKeyUsageCrit : 1;
byte extExtKeyUsageCrit : 1;
#endif /* OPENSSL_EXTRA */
#ifdef WOLFSSL_SEP
byte extCertPolicyCrit : 1;
#endif
}; };