in wangle/ssl/SSLContextManager.cpp [940:1014]
void SSLContextManager::SslContexts::insert(
shared_ptr<ServerSSLContext> sslCtx,
bool defaultFallback) {
X509* x509 = getX509(sslCtx->getSSLCtx());
if (!x509) {
throw std::runtime_error("SSLCtx is invalid");
}
auto guard = folly::makeGuard([x509] { X509_free(x509); });
auto identityResult = getCertIdentity(*x509);
auto& identity = identityResult.first;
auto identitySource = identityResult.second;
if (!identity) {
throw std::runtime_error("Cannot get certificate identity");
}
/**
* Some notes from RFC 2818. Only for future quick references in case of bugs
*
* RFC 2818 section 3.1:
* "......
* If a subjectAltName extension of type dNSName is present, that MUST
* be used as the identity. Otherwise, the (most specific) Common Name
* field in the Subject field of the certificate MUST be used. Although
* the use of the Common Name is existing practice, it is deprecated and
* Certification Authorities are encouraged to use the dNSName instead.
* ......
* In some cases, the URI is specified as an IP address rather than a
* hostname. In this case, the iPAddress subjectAltName must be present
* in the certificate and must exactly match the IP in the URI.
* ......"
*/
// Not sure if we ever get this kind of X509...
// If we do, assume '*' is always in the CN and ignore all subject alternative
// names.
if (identitySource == CertIdentitySource::CommonName &&
identity->length() == 1 && (*identity)[0] == '*') {
if (!defaultFallback) {
throw std::runtime_error("STAR X509 is not the default");
}
return;
}
CertCrypto certCrypto;
int sigAlg = X509_get_signature_nid(x509);
if (sigAlg == NID_sha1WithRSAEncryption || sigAlg == NID_ecdsa_with_SHA1) {
certCrypto = CertCrypto::SHA1_SIGNATURE;
VLOG(4) << "Adding SSLContext with SHA1 Signature";
} else {
certCrypto = CertCrypto::BEST_AVAILABLE;
VLOG(4) << "Adding SSLContext with best available crypto";
}
// Insert by identity.
//
// This will be used as the lookup key if this SSLContext is marked as
// the default.
insertSSLCtxByDomainName(*identity, sslCtx, certCrypto, defaultFallback);
// Insert by subject alternative name(s)
auto altNames = SSLUtil::getSubjectAltName(x509);
if (altNames) {
for (auto& name : *altNames) {
insertSSLCtxByDomainName(name, sslCtx, certCrypto, defaultFallback);
}
}
if (defaultFallback) {
defaultCtxDomainName_ = *identity;
} else {
addServerContext(sslCtx);
}
}