Fixed issue #124: access violation when checking subjectAltName extension of X509 certificate.
This commit is contained in:
parent
7e36a74645
commit
894b1d18a6
@ -396,57 +396,45 @@ bool X509Certificate_OpenSSL::verifyHostName
|
|||||||
}
|
}
|
||||||
|
|
||||||
// Now, look in subject alternative names
|
// Now, look in subject alternative names
|
||||||
for (int i = 0, extCount = X509_get_ext_count(m_data->cert) ; i < extCount ; ++i)
|
bool verify = false;
|
||||||
|
|
||||||
|
STACK_OF(GENERAL_NAME)* altNames = static_cast <GENERAL_NAMES*>
|
||||||
|
(X509_get_ext_d2i(m_data->cert, NID_subject_alt_name, NULL, NULL));
|
||||||
|
|
||||||
|
if (altNames == NULL)
|
||||||
|
return false;
|
||||||
|
|
||||||
|
// Check each name within the extension
|
||||||
|
for (int i = 0, n = sk_GENERAL_NAME_num(altNames) ; i < n ; ++i)
|
||||||
{
|
{
|
||||||
X509_EXTENSION* ext = X509_get_ext(m_data->cert, i);
|
const GENERAL_NAME* currentName = sk_GENERAL_NAME_value(altNames, i);
|
||||||
const char* extStr = OBJ_nid2sn(OBJ_obj2nid(X509_EXTENSION_get_object(ext)));
|
|
||||||
|
|
||||||
if (strcmp(extStr, "subjectAltName") == 0)
|
if (currentName->type == GEN_DNS)
|
||||||
{
|
{
|
||||||
const X509V3_EXT_METHOD* method;
|
// Current name is a DNS name, let's check it
|
||||||
|
char *DNSName = (char *) ASN1_STRING_data(currentName->d.dNSName);
|
||||||
|
|
||||||
if ((method = X509V3_EXT_get(ext)) != NULL)
|
// Make sure there isn't an embedded NUL character in the DNS name
|
||||||
|
if (ASN1_STRING_length(currentName->d.dNSName) != strlen(DNSName))
|
||||||
{
|
{
|
||||||
const unsigned char* extVal = ext->value->data;
|
// Malformed certificate
|
||||||
void *extValStr;
|
break;
|
||||||
|
|
||||||
if (method->it)
|
|
||||||
{
|
|
||||||
extValStr = ASN1_item_d2i
|
|
||||||
(NULL, &extVal, ext->value->length, ASN1_ITEM_ptr(method->it));
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
extValStr = method->d2i
|
|
||||||
(NULL, &extVal, ext->value->length);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (extValStr && method->i2v)
|
|
||||||
{
|
|
||||||
STACK_OF(CONF_VALUE)* val = call_i2v(method, extValStr, 0);
|
|
||||||
|
|
||||||
for (int j = 0 ; j < sk_CONF_VALUE_num(val) ; ++j)
|
|
||||||
{
|
|
||||||
CONF_VALUE* cnf = sk_CONF_VALUE_value(val, j);
|
|
||||||
|
|
||||||
if ((strcasecmp(cnf->name, "DNS") == 0 &&
|
|
||||||
cnMatch(cnf->value, hostname.c_str()))
|
|
||||||
||
|
|
||||||
(strncasecmp(cnf->name, "IP", 2) == 0 &&
|
|
||||||
cnMatch(cnf->value, hostname.c_str())))
|
|
||||||
{
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (nonMatchingNames)
|
|
||||||
nonMatchingNames->push_back(cnf->value);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (cnMatch(DNSName, hostname.c_str()))
|
||||||
|
{
|
||||||
|
verify = true;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (nonMatchingNames)
|
||||||
|
nonMatchingNames->push_back(DNSName);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return false;
|
sk_GENERAL_NAME_pop_free(altNames, GENERAL_NAME_free);
|
||||||
|
|
||||||
|
return verify;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user