Chromium Code Reviews| Index: net/cert/x509_util_nss_certs.cc |
| diff --git a/net/cert/x509_util_nss_certs.cc b/net/cert/x509_util_nss_certs.cc |
| index 1ec360d31e6d81d013a6ae56154826cd72840160..7a5b966595790fce68a9ea4cfcd391568425d3b0 100644 |
| --- a/net/cert/x509_util_nss_certs.cc |
| +++ b/net/cert/x509_util_nss_certs.cc |
| @@ -33,6 +33,10 @@ namespace net { |
| namespace { |
| +// Microsoft User Principal Name: 1.3.6.1.4.1.311.20.2.3 |
| +const uint8_t kUpnOid[] = {0x2b, 0x6, 0x1, 0x4, 0x1, |
| + 0x82, 0x37, 0x14, 0x2, 0x3}; |
| + |
| // Callback for CERT_DecodeCertPackage(), used in |
| // CreateOSCertHandlesFromBytes(). |
| SECStatus PR_CALLBACK |
| @@ -200,6 +204,73 @@ void GetSubjectAltName(CERTCertificate* cert_handle, |
| PORT_FreeArena(arena, PR_FALSE); |
| } |
| +CERTGeneralNameTypeEnum SANTypeToGeneralNameType(SubjectAltNameType type) { |
| + switch (type) { |
| + case SAN_RFC822_NAME: |
| + return certRFC822Name; |
| + case SAN_DNS_NAME: |
| + return certDNSName; |
| + case SAN_URI: |
| + return certURI; |
| + case SAN_IP_ADDRESS: |
| + return certIPAddress; |
| + case SAN_UPN: |
| + return certOtherName; |
| + } |
| + NOTREACHED(); |
| + return certOtherName; |
| +} |
| + |
| +void GetSubjectAltNameByType(CERTCertificate* cert_handle, |
| + SubjectAltNameType type, |
| + std::vector<std::string>* names) { |
| + crypto::ScopedSECItem alt_name(SECITEM_AllocItem(NULL, NULL, 0)); |
| + DCHECK(alt_name.get()); |
| + |
| + SECStatus rv = CERT_FindCertExtension( |
| + cert_handle, SEC_OID_X509_SUBJECT_ALT_NAME, alt_name.get()); |
| + if (rv != SECSuccess) |
| + return; |
| + |
| + crypto::ScopedPLArenaPool arena(PORT_NewArena(DER_DEFAULT_CHUNKSIZE)); |
| + DCHECK(arena.get()); |
| + |
| + CERTGeneralName* alt_name_list; |
| + alt_name_list = CERT_DecodeAltNameExtension(arena.get(), alt_name.get()); |
| + |
| + CERTGeneralName* name = alt_name_list; |
| + while (name) { |
| + if (name->type == SANTypeToGeneralNameType(type)) { |
| + switch (type) { |
| + case SAN_RFC822_NAME: |
| + case SAN_DNS_NAME: |
| + case SAN_URI: |
| + case SAN_IP_ADDRESS: |
| + names->push_back( |
| + std::string(reinterpret_cast<char*>(name->name.other.data), |
| + name->name.other.len)); |
| + break; |
| + case SAN_UPN: |
| + OtherName* on = &name->name.OthName; |
| + if (on->oid.len == sizeof(kUpnOid) && |
| + !memcmp(on->oid.data, kUpnOid, sizeof(kUpnOid))) { |
|
Ryan Sleevi
2016/03/01 00:28:29
The use of ! for values that return <0,0,>0 has be
Kevin Cernekee
2016/03/01 19:28:01
Done.
|
| + SECItem decoded; |
| + if (SEC_ASN1DecodeItem(arena.get(), &decoded, |
|
Ryan Sleevi
2016/03/01 00:28:28
SECURITY: DO *not* use this function in any way wh
Kevin Cernekee
2016/03/01 19:28:01
Done.
|
| + SEC_ASN1_GET(SEC_UTF8StringTemplate), |
| + &name->name.OthName.name) == SECSuccess) { |
| + names->push_back(std::string( |
| + reinterpret_cast<char*>(decoded.data), decoded.len)); |
| + } |
| + } |
| + break; |
| + } |
| + } |
| + name = CERT_GetNextGeneralName(name); |
| + if (name == alt_name_list) |
| + break; |
| + } |
| +} |
| + |
| X509Certificate::OSCertHandles CreateOSCertHandlesFromBytes( |
| const char* data, |
| size_t length, |