mirror of
https://github.com/Mbed-TLS/mbedtls.git
synced 2026-10-28 18:07:34 +08:00
x509: Accept basicConstraints with omitted cA
RFC 5280 defines cA as BOOLEAN DEFAULT FALSE, so a basicConstraints
extension containing only pathLenConstraint (SEQUENCE { INTEGER n })
is syntactically valid and must be interpreted as cA=FALSE. The fix
for CVE-2026-49300 rejected this encoding outright, breaking
compatibility with certificates emitted by devices such as
Eaton/CODESYS PLCs.
Tolerate MBEDTLS_ERR_ASN1_UNEXPECTED_TAG from the cA BOOLEAN parse,
keeping cA FALSE and letting the existing INTEGER parser validate
pathLenConstraint. The INTEGER value is never used to determine cA,
so the CVE fix is preserved.
Fixes #11006
Signed-off-by: v1rtu3x <149050962+v1rtu3x@users.noreply.github.com>
(cherry picked from commit 62dd8a556c01cc289d4fb3f19352a78ede90dac2)
This commit is contained in:
parent
8a04fc0861
commit
5af05a964a
5
ChangeLog.d/x509-basic-constraints-integer-first.txt
Normal file
5
ChangeLog.d/x509-basic-constraints-integer-first.txt
Normal file
@ -0,0 +1,5 @@
|
||||
Bugfix
|
||||
* Accept a basicConstraints extension that omits cA and contains only
|
||||
pathLenConstraint, interpreting it as cA=FALSE as specified by RFC 5280.
|
||||
This restores compatibility with certificates emitted by some devices
|
||||
without accepting them as CA certificates. Fixes #11006.
|
||||
@ -519,17 +519,19 @@ static int x509_get_basic_constraints(unsigned char **p,
|
||||
}
|
||||
|
||||
if ((ret = mbedtls_asn1_get_bool(p, end, ca_istrue)) != 0) {
|
||||
/* If the SEQUENCE starts with an INTEGER and not a BOOLEAN,
|
||||
* according to RFC 5280, it's syntactically valid, but it's
|
||||
* something that a CA MUST NOT produce. So we reject it.
|
||||
/* cA is DEFAULT FALSE. If it is absent, the first element must
|
||||
* be pathLenConstraint. Keep cA false and let the INTEGER parser
|
||||
* below validate the element.
|
||||
*
|
||||
* Note: historically, from XySSL 0.9 to Mbed TLS 3.6.6/4.1.0,
|
||||
* `SEQUENCE { INTEGER n }` was interpreted as cA=FALSE if n == 0
|
||||
* and cA=TRUE if n != 0. This was dangerous since
|
||||
* `SEQUENCE { INTEGER n }` should be parsed as cA=FALSE
|
||||
* according to RFC 5280, so we stopped doing it.
|
||||
* according to RFC 5280.
|
||||
*/
|
||||
return MBEDTLS_ERROR_ADD(MBEDTLS_ERR_X509_INVALID_EXTENSIONS, ret);
|
||||
if (ret != MBEDTLS_ERR_ASN1_UNEXPECTED_TAG) {
|
||||
return MBEDTLS_ERROR_ADD(MBEDTLS_ERR_X509_INVALID_EXTENSIONS, ret);
|
||||
}
|
||||
}
|
||||
/* `SEQUENCE { BOOLEAN FALSE }` is not DER since default-value fields
|
||||
* must be omitted in DER. But it seems harmless, and Mbed TLS has
|
||||
|
||||
@ -2070,11 +2070,27 @@ mbedtls_x509_crt_parse_file:"../framework/data_files/parse_input/server5.basic-c
|
||||
|
||||
X509 CRT ASN1: basicConstraints: no cA but pathLenConstraint (bad signature)
|
||||
depends_on:MBEDTLS_PK_CAN_ECDSA_SOME:MBEDTLS_ECP_HAVE_SECP256R1:MBEDTLS_MD_CAN_SHA256
|
||||
mbedtls_x509_crt_parse_file:"../framework/data_files/parse_input/server5.basic-constraints-integer-first.badsign.crt":MBEDTLS_ERROR_ADD(MBEDTLS_ERR_X509_INVALID_EXTENSIONS, MBEDTLS_ERR_ASN1_UNEXPECTED_TAG):0
|
||||
mbedtls_x509_crt_parse_file:"../framework/data_files/parse_input/server5.basic-constraints-integer-first.badsign.crt":0:1
|
||||
|
||||
X509 CRT ASN1: basicConstraints: no cA, pathLen only: not a CA
|
||||
depends_on:MBEDTLS_PK_CAN_ECDSA_SOME:MBEDTLS_ECP_HAVE_SECP256R1:MBEDTLS_MD_CAN_SHA256
|
||||
mbedtls_x509_get_ca_istrue:"../framework/data_files/parse_input/server5.basic-constraints-integer-first.badsign.crt":0
|
||||
|
||||
X509 CRT ASN1: basicConstraints: no cA but pathLenConstraint (good self signature)
|
||||
depends_on:MBEDTLS_PK_CAN_ECDSA_SOME:MBEDTLS_ECP_HAVE_SECP256R1:MBEDTLS_MD_CAN_SHA256
|
||||
mbedtls_x509_crt_parse_file:"../framework/data_files/parse_input/server5.basic-constraints-integer-first.selfsigned.crt":MBEDTLS_ERROR_ADD(MBEDTLS_ERR_X509_INVALID_EXTENSIONS, MBEDTLS_ERR_ASN1_UNEXPECTED_TAG):0
|
||||
mbedtls_x509_crt_parse_file:"../framework/data_files/parse_input/server5.basic-constraints-integer-first.selfsigned.crt":0:1
|
||||
|
||||
X509 CRT ASN1: basicConstraints: no cA but zero pathLenConstraint
|
||||
depends_on:MBEDTLS_PK_CAN_ECDSA_SOME:MBEDTLS_ECP_HAVE_SECP256R1:MBEDTLS_MD_CAN_SHA256
|
||||
x509_crt_parse_basic_constraints:"308201573081fea003020102020c53a2cb4b124ead837da894b2300a06082a8648ce3d040302300e310c300a06035504030c03457665301e170d3236303531323039353330345a170d3336303531323039353330345a300e310c300a06035504030c034576653059301306072a8648ce3d020106082a8648ce3d0301070342000437cc56d976091e5a723ec7592dff206eee7cf9069174d0ad14b5f768225962924ee500d82311ffea2fd2345d5d16bd8a88c26b770d55cd8a2a0efa01c8b4edffa3423040300f0603551d130101ff04053003020100300e0603551d0f0101ff040403020780301d0603551d0e041604145061a58fd407d9d782010ce5657f8c6346a713be300a06082a8648ce3d0403020348003045022100d67d572af0aa540cd0f9d86d43788c178ca9501d8c0f4f6690c773f4b82c4b9a022011620feee62aca3944b8321636849030014ef80604550031312bb707b7f2bf04":0:0:0
|
||||
|
||||
X509 CRT ASN1: basicConstraints: invalid cA BOOLEAN length
|
||||
depends_on:MBEDTLS_PK_CAN_ECDSA_SOME:MBEDTLS_ECP_HAVE_SECP256R1:MBEDTLS_MD_CAN_SHA256
|
||||
x509_crt_parse_basic_constraints:"308201573081fea003020102020c53a2cb4b124ead837da894b2300a06082a8648ce3d040302300e310c300a06035504030c03457665301e170d3236303531323039353330345a170d3336303531323039353330345a300e310c300a06035504030c034576653059301306072a8648ce3d020106082a8648ce3d0301070342000437cc56d976091e5a723ec7592dff206eee7cf9069174d0ad14b5f768225962924ee500d82311ffea2fd2345d5d16bd8a88c26b770d55cd8a2a0efa01c8b4edffa3423040300f0603551d130101ff040530030100ff300e0603551d0f0101ff040403020780301d0603551d0e041604145061a58fd407d9d782010ce5657f8c6346a713be300a06082a8648ce3d0403020348003045022100d67d572af0aa540cd0f9d86d43788c178ca9501d8c0f4f6690c773f4b82c4b9a022011620feee62aca3944b8321636849030014ef80604550031312bb707b7f2bf04":MBEDTLS_ERROR_ADD(MBEDTLS_ERR_X509_INVALID_EXTENSIONS, MBEDTLS_ERR_ASN1_INVALID_LENGTH):0:0
|
||||
|
||||
X509 CRT ASN1: basicConstraints: neither cA nor pathLenConstraint
|
||||
depends_on:MBEDTLS_PK_CAN_ECDSA_SOME:MBEDTLS_ECP_HAVE_SECP256R1:MBEDTLS_MD_CAN_SHA256
|
||||
x509_crt_parse_basic_constraints:"308201573081fea003020102020c53a2cb4b124ead837da894b2300a06082a8648ce3d040302300e310c300a06035504030c03457665301e170d3236303531323039353330345a170d3336303531323039353330345a300e310c300a06035504030c034576653059301306072a8648ce3d020106082a8648ce3d0301070342000437cc56d976091e5a723ec7592dff206eee7cf9069174d0ad14b5f768225962924ee500d82311ffea2fd2345d5d16bd8a88c26b770d55cd8a2a0efa01c8b4edffa3423040300f0603551d130101ff04053003050100300e0603551d0f0101ff040403020780301d0603551d0e041604145061a58fd407d9d782010ce5657f8c6346a713be300a06082a8648ce3d0403020348003045022100d67d572af0aa540cd0f9d86d43788c178ca9501d8c0f4f6690c773f4b82c4b9a022011620feee62aca3944b8321636849030014ef80604550031312bb707b7f2bf04":MBEDTLS_ERROR_ADD(MBEDTLS_ERR_X509_INVALID_EXTENSIONS, MBEDTLS_ERR_ASN1_UNEXPECTED_TAG):0:0
|
||||
|
||||
X509 CRT ASN1 (TBS, inv extBasicConstraint, no pathlen length)
|
||||
depends_on:MBEDTLS_RSA_C:MBEDTLS_MD_CAN_SHA256
|
||||
|
||||
@ -1121,6 +1121,28 @@ exit:
|
||||
}
|
||||
/* END_CASE */
|
||||
|
||||
/* BEGIN_CASE depends_on:MBEDTLS_X509_CRT_PARSE_C */
|
||||
void x509_crt_parse_basic_constraints(data_t *buf, int result,
|
||||
int ca_istrue, int path_len_constraint)
|
||||
{
|
||||
mbedtls_x509_crt crt;
|
||||
|
||||
mbedtls_x509_crt_init(&crt);
|
||||
USE_PSA_INIT();
|
||||
|
||||
TEST_EQUAL(mbedtls_x509_crt_parse_der(&crt, buf->x, buf->len), result);
|
||||
if (result == 0) {
|
||||
TEST_EQUAL(mbedtls_x509_crt_get_ca_istrue(&crt), ca_istrue);
|
||||
/* max_pathlen is 1 higher than pathLenConstraint. */
|
||||
TEST_EQUAL(crt.max_pathlen, path_len_constraint + 1);
|
||||
}
|
||||
|
||||
exit:
|
||||
mbedtls_x509_crt_free(&crt);
|
||||
USE_PSA_DONE();
|
||||
}
|
||||
/* END_CASE */
|
||||
|
||||
/* BEGIN_CASE depends_on:MBEDTLS_X509_CRT_PARSE_C */
|
||||
void x509parse_crt(data_t *buf, char *result_str, int result)
|
||||
{
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user