]> git.baikalelectronics.ru Git - arm-tf.git/commitdiff
fix(auth): require at least one extension to be present
authorDemi Marie Obenour <demiobenour@gmail.com>
Thu, 8 Dec 2022 20:23:58 +0000 (15:23 -0500)
committerDemi Marie Obenour <demiobenour@gmail.com>
Thu, 29 Dec 2022 23:41:10 +0000 (18:41 -0500)
X.509 and RFC5280 allow omitting the extensions entirely, but require
that if the extensions field is present at all, it must contain at least
one certificate.  TF-A already requires the extensions to be present,
but allows them to be empty.  However, a certificate with an empty
extensions field will always fail later on, as the extensions contain
the information needed to validate the next stage in the boot chain.
Therefore, it is simpler to require the extension field to be present
and contain at least one extension.  Also add a comment explaining why
the extensions field is required, even though it is OPTIONAL in the
ASN.1 syntax.

Change-Id: Ie26eed8a7924bf50937a6b27ccdf7cc9a390588d
Signed-off-by: Demi Marie Obenour <demiobenour@gmail.com>
drivers/auth/mbedtls/mbedtls_x509_parser.c

index 8c78003bb2399a06887a026160d67ac026598aaf..9cccd964d41e90aaa86e69420e3f137048afc95f 100644 (file)
@@ -304,7 +304,18 @@ static int cert_parse(void *img, unsigned int img_len)
 
        /*
         * extensions      [3]  EXPLICIT Extensions OPTIONAL
-        * -- must use all remaining bytes in TBSCertificate
+        * }
+        *
+        * X.509 and RFC5280 allow omitting the extensions entirely.
+        * However, in TF-A, a certificate with no extensions would
+        * always fail later on, as the extensions contain the
+        * information needed to authenticate the next stage in the
+        * boot chain.  Furthermore, get_ext() assumes that the
+        * extensions have been parsed into v3_ext, and allowing
+        * there to be no extensions would pointlessly complicate
+        * the code.  Therefore, just reject certificates without
+        * extensions.  This is also why version 1 and 2 certificates
+        * are rejected above.
         */
        ret = mbedtls_asn1_get_tag(&p, end, &len,
                                   MBEDTLS_ASN1_CONTEXT_SPECIFIC |
@@ -326,9 +337,12 @@ static int cert_parse(void *img, unsigned int img_len)
        v3_ext.len = end - v3_ext.p;
 
        /*
-        * Check extensions integrity
+        * Check extensions integrity.  At least one extension is
+        * required: the ASN.1 specifies a minimum size of 1, and at
+        * least one extension is needed to authenticate the next stage
+        * in the boot chain.
         */
-       while (p < end) {
+       do {
                ret = mbedtls_asn1_get_tag(&p, end, &len,
                                           MBEDTLS_ASN1_CONSTRUCTED |
                                           MBEDTLS_ASN1_SEQUENCE);
@@ -356,7 +370,7 @@ static int cert_parse(void *img, unsigned int img_len)
                        return IMG_PARSER_ERR_FORMAT;
                }
                p += len;
-       }
+       } while (p < end);
 
        if (p != end) {
                return IMG_PARSER_ERR_FORMAT;