1 // Copyright (c) 2012 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
5 #include "net/cert/x509_util_ios.h"
8 #include <CommonCrypto/CommonDigest.h>
12 #include "base/mac/scoped_cftyperef.h"
13 #include "crypto/nss_util.h"
14 #include "net/cert/x509_certificate.h"
15 #include "net/cert/x509_util_nss.h"
17 using base::ScopedCFTypeRef
;
20 namespace x509_util_ios
{
24 // Creates an NSS certificate handle from |data|, which is |length| bytes in
26 CERTCertificate
* CreateNSSCertHandleFromBytes(const char* data
,
31 crypto::EnsureNSSInit();
33 if (!NSS_IsInitialized())
37 der_cert
.data
= reinterpret_cast<unsigned char*>(const_cast<char*>(data
));
38 der_cert
.len
= length
;
39 der_cert
.type
= siDERCertBuffer
;
41 // Parse into a certificate structure.
42 return CERT_NewTempCertificate(CERT_GetDefaultCertDB(), &der_cert
, NULL
,
48 CERTCertificate
* CreateNSSCertHandleFromOSHandle(
49 SecCertificateRef cert_handle
) {
50 ScopedCFTypeRef
<CFDataRef
> cert_data(SecCertificateCopyData(cert_handle
));
51 return CreateNSSCertHandleFromBytes(
52 reinterpret_cast<const char*>(CFDataGetBytePtr(cert_data
)),
53 CFDataGetLength(cert_data
));
56 SecCertificateRef
CreateOSCertHandleFromNSSHandle(
57 CERTCertificate
* nss_cert_handle
) {
58 return X509Certificate::CreateOSCertHandleFromBytes(
59 reinterpret_cast<const char*>(nss_cert_handle
->derCert
.data
),
60 nss_cert_handle
->derCert
.len
);
63 X509Certificate
* CreateCertFromNSSHandles(
64 CERTCertificate
* cert_handle
,
65 const std::vector
<CERTCertificate
*>& intermediates
) {
66 ScopedCFTypeRef
<SecCertificateRef
> os_server_cert(
67 CreateOSCertHandleFromNSSHandle(cert_handle
));
70 std::vector
<SecCertificateRef
> os_intermediates
;
71 for (size_t i
= 0; i
< intermediates
.size(); ++i
) {
72 SecCertificateRef intermediate
=
73 CreateOSCertHandleFromNSSHandle(intermediates
[i
]);
76 os_intermediates
.push_back(intermediate
);
79 X509Certificate
* cert
= NULL
;
80 if (intermediates
.size() == os_intermediates
.size()) {
81 cert
= X509Certificate::CreateFromHandle(os_server_cert
,
85 for (size_t i
= 0; i
< os_intermediates
.size(); ++i
)
86 CFRelease(os_intermediates
[i
]);
90 SHA1HashValue
CalculateFingerprintNSS(CERTCertificate
* cert
) {
91 DCHECK(cert
->derCert
.data
);
92 DCHECK_NE(0U, cert
->derCert
.len
);
94 memset(sha1
.data
, 0, sizeof(sha1
.data
));
95 CC_SHA1(cert
->derCert
.data
, cert
->derCert
.len
, sha1
.data
);
99 // NSSCertificate implementation.
101 NSSCertificate::NSSCertificate(SecCertificateRef cert_handle
) {
102 nss_cert_handle_
= CreateNSSCertHandleFromOSHandle(cert_handle
);
103 DLOG_IF(INFO
, cert_handle
&& !nss_cert_handle_
)
104 << "Could not convert SecCertificateRef to CERTCertificate*";
107 NSSCertificate::~NSSCertificate() {
108 CERT_DestroyCertificate(nss_cert_handle_
);
111 CERTCertificate
* NSSCertificate::cert_handle() const {
112 return nss_cert_handle_
;
115 // NSSCertChain implementation
117 NSSCertChain::NSSCertChain(X509Certificate
* certificate
) {
119 certs_
.push_back(CreateNSSCertHandleFromOSHandle(
120 certificate
->os_cert_handle()));
121 const X509Certificate::OSCertHandles
& cert_intermediates
=
122 certificate
->GetIntermediateCertificates();
123 for (size_t i
= 0; i
< cert_intermediates
.size(); ++i
)
124 certs_
.push_back(CreateNSSCertHandleFromOSHandle(cert_intermediates
[i
]));
127 NSSCertChain::~NSSCertChain() {
128 for (size_t i
= 0; i
< certs_
.size(); ++i
)
129 CERT_DestroyCertificate(certs_
[i
]);
132 CERTCertificate
* NSSCertChain::cert_handle() const {
133 return certs_
.empty() ? NULL
: certs_
.front();
136 const std::vector
<CERTCertificate
*>& NSSCertChain::cert_chain() const {
140 } // namespace x509_util_ios