Commit f0d774d4 authored by Sergei Golubchik's avatar Sergei Golubchik

MDEV-9212 ssl-validate-cert incorrect hostname check

Reimplement ssl_verify_server_cert() using the logic
from https://wiki.openssl.org/index.php/Hostname_validation

The bug was discovered by Alex Gaynor.
parent 544eeda3
...@@ -1885,8 +1885,11 @@ static int ssl_verify_server_cert(Vio *vio, const char* server_hostname, const c ...@@ -1885,8 +1885,11 @@ static int ssl_verify_server_cert(Vio *vio, const char* server_hostname, const c
{ {
SSL *ssl; SSL *ssl;
X509 *server_cert; X509 *server_cert;
char *cp1, *cp2; X509_NAME *x509sn;
char *buf; int cn_pos;
X509_NAME_ENTRY *cn_entry;
ASN1_STRING *cn_asn1;
const char *cn_str;
DBUG_ENTER("ssl_verify_server_cert"); DBUG_ENTER("ssl_verify_server_cert");
DBUG_PRINT("enter", ("server_hostname: %s", server_hostname)); DBUG_PRINT("enter", ("server_hostname: %s", server_hostname));
...@@ -1920,34 +1923,32 @@ static int ssl_verify_server_cert(Vio *vio, const char* server_hostname, const c ...@@ -1920,34 +1923,32 @@ static int ssl_verify_server_cert(Vio *vio, const char* server_hostname, const c
are what we expect. are what we expect.
*/ */
buf= X509_NAME_oneline(X509_get_subject_name(server_cert), 0, 0); x509sn= X509_get_subject_name(server_cert);
X509_free (server_cert);
if (!buf) if ((cn_pos= X509_NAME_get_index_by_NID(x509sn, NID_commonName, -1)) < 0)
{ goto err;
*errptr= "Out of memory";
DBUG_RETURN(1);
}
DBUG_PRINT("info", ("hostname in cert: %s", buf)); if (!(cn_entry= X509_NAME_get_entry(x509sn, cn_pos)))
cp1= strstr(buf, "/CN="); goto err;
if (cp1)
{ if (!(cn_asn1 = X509_NAME_ENTRY_get_data(cn_entry)))
cp1+= 4; /* Skip the "/CN=" that we found */ goto err;
/* Search for next / which might be the delimiter for email */
cp2= strchr(cp1, '/'); cn_str = (char *)ASN1_STRING_data(cn_asn1);
if (cp2)
*cp2= '\0'; /* Make sure there is no embedded \0 in the CN */
DBUG_PRINT("info", ("Server hostname in cert: %s", cp1)); if ((size_t)ASN1_STRING_length(cn_asn1) != strlen(cn_str))
if (!strcmp(cp1, server_hostname)) goto err;
{
free(buf); if (strcmp(cn_str, server_hostname))
/* Success */ goto err;
DBUG_RETURN(0);
} X509_free (server_cert);
} DBUG_RETURN(0);
err:
X509_free(server_cert);
*errptr= "SSL certificate validation failure"; *errptr= "SSL certificate validation failure";
free(buf);
DBUG_RETURN(1); DBUG_RETURN(1);
} }
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment