X-Git-Url: http://sjero.net/git/?p=wget;a=blobdiff_plain;f=src%2Fopenssl.c;h=dd3a62a4ee0cf594f97cc35655be548e259dd3c4;hp=f5239ede6e8f0b478a81625261a805165e13403c;hb=61a4b1f77a3412dbd9a3864d8422addf94459fd1;hpb=8e9648a972b88fa6eb2293383bd281c6021394d2 diff --git a/src/openssl.c b/src/openssl.c index f5239ede..dd3a62a4 100644 --- a/src/openssl.c +++ b/src/openssl.c @@ -390,7 +390,7 @@ static struct transport_implementation openssl_transport = { Returns true on success, false on failure. */ bool -ssl_connect (int fd) +ssl_connect_wget (int fd) { SSL *conn; struct openssl_transport_context *ctx; @@ -473,7 +473,7 @@ pattern_match (const char *pattern, const char *string) its certificate, corresponds to HOST. (HOST typically comes from the URL and is what the user thinks he's connecting to.) - This assumes that ssl_connect has successfully finished, i.e. that + This assumes that ssl_connect_wget has successfully finished, i.e. that the SSL handshake has been performed and that FD is connected to an SSL handle. @@ -569,9 +569,35 @@ ssl_check_certificate (int fd, const char *host) - Ensure that ASN1 strings from the certificate are encoded as UTF-8 which can be meaningfully compared to HOST. */ + X509_NAME *xname = X509_get_subject_name(cert); common_name[0] = '\0'; - X509_NAME_get_text_by_NID (X509_get_subject_name (cert), + X509_NAME_get_text_by_NID (xname, NID_commonName, common_name, sizeof (common_name)); + + /* We now determine the length of the ASN1 string. If it differs from + * common_name's length, then there is a \0 before the string terminates. + * This can be an instance of a null-prefix attack [0]. + * + * [0] https://www.blackhat.com/html/bh-usa-09/bh-usa-09-archives.html#Marlinspike + * */ + + int i=-1,j; + if(xname) { + for(;(j=X509_NAME_get_index_by_NID (xname, NID_commonName, i))!=-1;i=j); + } + + X509_NAME_ENTRY *xentry = X509_NAME_get_entry(xname,i); + ASN1_STRING *sdata = X509_NAME_ENTRY_get_data(xentry); + + if (strlen(common_name) != ASN1_STRING_length(sdata)) + { + logprintf (LOG_NOTQUIET, _("\ +%s: certificate common name is invalid. It is possible that someone is \ +eavesdropping on you (man-in-the-middle attack)!\n"), + severity); + success = false; + } + if (!pattern_match (common_name, host)) { logprintf (LOG_NOTQUIET, _("\