sectransp: check for client certs by name first, then file 11/278511/2
authorSeonah Moon <seonah1.moon@samsung.com>
Thu, 21 Jul 2022 10:06:48 +0000 (19:06 +0900)
committerseonah moon <seonah1.moon@samsung.com>
Thu, 21 Jul 2022 11:48:47 +0000 (11:48 +0000)
CVE-2021-22926

Bug: https://curl.se/docs/CVE-2021-22926.html

Assisted-by: Daniel Gustafsson
Reported-by: Harry Sintonen
backport of mainline commit: https://github.com/curl/curl/commit/fd9b40bf8dfd43edcbc0d254d613d95a11061c05

Change-Id: I66fac22afb269646b0872fdc5aa4df1aeaf0a427

lib/vtls/sectransp.c

index 1345323b590b5eb48515958141ef28c66d7f927b..7d772752a72b09787c69d7ba5498174224b8d299 100644 (file)
@@ -32,6 +32,7 @@
 #include "curl_base64.h"
 #include "strtok.h"
 #include "multiif.h"
+#include "strcase.h"
 
 #ifdef USE_SECTRANSP
 
@@ -1648,24 +1649,26 @@ static CURLcode sectransp_connect_step1(struct connectdata *conn,
     bool is_cert_file = (!is_cert_data) && is_file(ssl_cert);
     SecIdentityRef cert_and_key = NULL;
 
-    /* User wants to authenticate with a client cert. Look for it:
-       If we detect that this is a file on disk, then let's load it.
-       Otherwise, assume that the user wants to use an identity loaded
-       from the Keychain. */
-    if(is_cert_file || is_cert_data) {
+    /* User wants to authenticate with a client cert. Look for it. Assume that
+       the user wants to use an identity loaded from the Keychain. If not, try
+       it as a file on disk */
+    if(!is_cert_data)
+      err = CopyIdentityWithLabel(ssl_cert, &cert_and_key);
+    else
+      err = !noErr;
+    if((err != noErr) && (is_cert_file || is_cert_data)) {
       if(!SSL_SET_OPTION(cert_type))
-        infof(data, "WARNING: SSL: Certificate type not set, assuming "
-                    "PKCS#12 format.\n");
-      else if(strncmp(SSL_SET_OPTION(cert_type), "P12",
-        strlen(SSL_SET_OPTION(cert_type))) != 0)
-        infof(data, "WARNING: SSL: The Security framework only supports "
-                    "loading identities that are in PKCS#12 format.\n");
-
+        infof(data, "SSL: Certificate type not set, assuming "
+              "PKCS#12 format.");
+      else if(!strcasecompare(SSL_SET_OPTION(cert_type), "P12")) {
+        failf(data, "SSL: The Security framework only supports "
+              "loading identities that are in PKCS#12 format.");
+        return CURLE_SSL_CERTPROBLEM;
+      }
       err = CopyIdentityFromPKCS12File(ssl_cert, ssl_cert_blob,
-        SSL_SET_OPTION(key_passwd), &cert_and_key);
+                                       SSL_SET_OPTION(key_passwd),
+                                       &cert_and_key);
     }
-    else
-      err = CopyIdentityWithLabel(ssl_cert, &cert_and_key);
 
     if(err == noErr && cert_and_key) {
       SecCertificateRef cert = NULL;