diff --git a/ChangeLog.d/8799.txt b/ChangeLog.d/8799.txt index b44bb99919..50e7c118c8 100644 --- a/ChangeLog.d/8799.txt +++ b/ChangeLog.d/8799.txt @@ -1,4 +1,3 @@ Bugfix * mbedtls_pem_read_buffer() now performs a check on the padding data of - decrypted keys and it rejects invalid ones. It also parses and validates - the main ASN.1 SEQUENCE header. + decrypted keys and it rejects invalid ones. diff --git a/include/mbedtls/asn1.h b/include/mbedtls/asn1.h index d8ee469308..ff019f432a 100644 --- a/include/mbedtls/asn1.h +++ b/include/mbedtls/asn1.h @@ -198,7 +198,7 @@ typedef struct mbedtls_asn1_named_data { mbedtls_asn1_named_data; #if defined(MBEDTLS_ASN1_PARSE_C) || defined(MBEDTLS_X509_CREATE_C) || \ - defined(MBEDTLS_PSA_UTIL_HAVE_ECDSA) || defined(MBEDTLS_PEM_PARSE_C) + defined(MBEDTLS_PSA_UTIL_HAVE_ECDSA) /** * \brief Get the length of an ASN.1 element. * Updates the pointer to immediately behind the length. @@ -245,8 +245,7 @@ int mbedtls_asn1_get_len(unsigned char **p, int mbedtls_asn1_get_tag(unsigned char **p, const unsigned char *end, size_t *len, int tag); -#endif /* MBEDTLS_ASN1_PARSE_C || MBEDTLS_X509_CREATE_C || - MBEDTLS_PSA_UTIL_HAVE_ECDSA || MBEDTLS_PEM_PARSE_C */ +#endif /* MBEDTLS_ASN1_PARSE_C || MBEDTLS_X509_CREATE_C || MBEDTLS_PSA_UTIL_HAVE_ECDSA */ #if defined(MBEDTLS_ASN1_PARSE_C) /** diff --git a/library/asn1parse.c b/library/asn1parse.c index 644b43ba96..e33fdf71da 100644 --- a/library/asn1parse.c +++ b/library/asn1parse.c @@ -8,7 +8,7 @@ #include "common.h" #if defined(MBEDTLS_ASN1_PARSE_C) || defined(MBEDTLS_X509_CREATE_C) || \ - defined(MBEDTLS_PSA_UTIL_HAVE_ECDSA) || defined(MBEDTLS_PEM_PARSE_C) + defined(MBEDTLS_PSA_UTIL_HAVE_ECDSA) #include "mbedtls/asn1.h" #include "mbedtls/platform_util.h" @@ -74,8 +74,7 @@ int mbedtls_asn1_get_tag(unsigned char **p, return mbedtls_asn1_get_len(p, end, len); } -#endif /* MBEDTLS_ASN1_PARSE_C || MBEDTLS_X509_CREATE_C || - MBEDTLS_PSA_UTIL_HAVE_ECDSA || MBEDTLS_PEM_PARSE_C */ +#endif /* MBEDTLS_ASN1_PARSE_C || MBEDTLS_X509_CREATE_C || MBEDTLS_PSA_UTIL_HAVE_ECDSA */ #if defined(MBEDTLS_ASN1_PARSE_C) int mbedtls_asn1_get_bool(unsigned char **p, diff --git a/library/pem.c b/library/pem.c index 3f01d3bdd3..48180eed48 100644 --- a/library/pem.c +++ b/library/pem.c @@ -17,7 +17,6 @@ #include "mbedtls/cipher.h" #include "mbedtls/platform_util.h" #include "mbedtls/error.h" -#include "mbedtls/asn1.h" #include @@ -466,28 +465,6 @@ int mbedtls_pem_read_buffer(mbedtls_pem_context *ctx, const char *header, const mbedtls_zeroize_and_free(buf, len); return ret; } - - /* - * In RFC1421 PEM is used as container for DER (ASN.1) content so we - * can use ASN.1 functions to parse the main SEQUENCE tag and to get its - * length. - */ - unsigned char *p = buf; - size_t sequence_len; - ret = mbedtls_asn1_get_tag(&p, buf + len, &sequence_len, - MBEDTLS_ASN1_SEQUENCE | MBEDTLS_ASN1_CONSTRUCTED); - if (ret != 0) { - mbedtls_free(buf); - return MBEDTLS_ERROR_ADD(MBEDTLS_ERR_PEM_INVALID_DATA, ret); - } - /* Add also the sequence block (tag + len) to the total amount of valid data. */ - sequence_len += (p - buf); - - /* Ensure that the reported SEQUENCE length matches the data len (i.e. no - * trailing garbage data). */ - if (len != sequence_len) { - return MBEDTLS_ERR_PEM_BAD_INPUT_DATA; - } #else mbedtls_zeroize_and_free(buf, len); return MBEDTLS_ERR_PEM_FEATURE_UNAVAILABLE; diff --git a/tests/suites/test_suite_pem.data b/tests/suites/test_suite_pem.data index e3bb7e4da1..6f8af6c31d 100644 --- a/tests/suites/test_suite_pem.data +++ b/tests/suites/test_suite_pem.data @@ -61,21 +61,14 @@ PEM read (valid EC key encoded with AES-128-CBC) depends_on:MBEDTLS_MD_CAN_MD5:MBEDTLS_AES_C:MBEDTLS_CIPHER_MODE_CBC mbedtls_pem_read_buffer:"-----BEGIN EC PRIVATE KEY-----":"-----END EC PRIVATE KEY-----":"-----BEGIN EC PRIVATE KEY-----\nProc-Type\: 4,ENCRYPTED\nDEK-Info\: AES-128-CBC,151F851B6A7F3FBDAA5B7173117D0127\n\nLw+0OM+0Bwcl+ls/vxQbLrVshGc7bsNPvvtj2sJeMFFEq3V1mj/IO++0KK/CDhMH\nh6CZPsmgVOeM5uFpqYaq0fJbUduN2eDMWszWRm0SFkY=\n-----END EC PRIVATE KEY-----":"pwdpwd":0:"3041020101040f00d8023c809afd45e426d1a4dbe0ffa00706052b81040004a1220320000400da1ecfa53d528237625e119e2e0500d2eb671724f16deb6a63749516b7" -# The text "hello world" (which is clearly not a valid ASN.1 SEQUENCE) is encoded -# with AES-128-CBC to prove that ASN.1 parsing after decoding fails. +# The text "hello world" together with some invalid padding data is encoded +# with AES-128-CBC in order to test padding validation. # Since PBKDF1 isn't supported in OpenSSL, here's the steps: # 1. generate the key (password="password"; IV=0x3132333435363738 in hex or "12345678" as string) # echo -n "password12345678" | openssl md5 # 2. encode data -# echo -n "hello world" | openssl aes-128-cbc -e -base64 -p -K "bbb0ddff1b944b3cc68eaaeb7ac20099" -iv "3132333435363738" -PEM read (Invalid SEQUENCE encoded with AES-128-CBC) -depends_on:MBEDTLS_MD_CAN_MD5:MBEDTLS_AES_C:MBEDTLS_CIPHER_MODE_CBC -mbedtls_pem_read_buffer:"-----BEGIN EC PRIVATE KEY-----":"-----END EC PRIVATE KEY-----":"-----BEGIN EC PRIVATE KEY-----\nProc-Type\: 4,ENCRYPTED\nDEK-Info\: AES-128-CBC,31323334353637380000000000000000\n\nDfRGkwS+VjvR0IYsjZwW6Q==\n-----END EC PRIVATE KEY-----":"password":MBEDTLS_ERR_PEM_INVALID_DATA + MBEDTLS_ERR_ASN1_UNEXPECTED_TAG:"" - -# Same as above, but with invalid padding data. -# Generated with: # echo -n -e "\x68\x65\x6c\x6c\x6f\x20\x77\x6f\x72\x6c\x64\x01\x02\x03\x04\x05" | openssl aes-128-cbc -e -base64 -p -K "bbb0ddff1b944b3cc68eaaeb7ac20099" -iv "3132333435363738" -nopad -PEM read (Invalid padding data for AES-128-CBC) +PEM read (AES-128-CBC, invalid padding data) depends_on:MBEDTLS_MD_CAN_MD5:MBEDTLS_AES_C:MBEDTLS_CIPHER_MODE_CBC mbedtls_pem_read_buffer:"-----BEGIN EC PRIVATE KEY-----":"-----END EC PRIVATE KEY-----":"-----BEGIN EC PRIVATE KEY-----\nProc-Type\: 4,ENCRYPTED\nDEK-Info\: AES-128-CBC,31323334353637380000000000000000\n\n333hxynfxEdXrSHQfIabxQ==\n-----END EC PRIVATE KEY-----":"password":MBEDTLS_ERR_PEM_BAD_INPUT_DATA:"" diff --git a/tests/suites/test_suite_pem.function b/tests/suites/test_suite_pem.function index 2acc16e9f3..413dc551c3 100644 --- a/tests/suites/test_suite_pem.function +++ b/tests/suites/test_suite_pem.function @@ -3,7 +3,6 @@ #include "mbedtls/pem.h" #include "mbedtls/des.h" #include "mbedtls/aes.h" -#include "mbedtls/asn1.h" /* END_HEADER */ /* BEGIN_CASE depends_on:MBEDTLS_PEM_WRITE_C */