| // Copyright (c) 2016 The Chromium Embedded Framework Authors. All rights |
| // reserved. Use of this source code is governed by a BSD-style license that |
| // can be found in the LICENSE file. |
| |
| #include "libcef/browser/x509_certificate_impl.h" |
| |
| #include "libcef/browser/x509_cert_principal_impl.h" |
| #include "libcef/common/time_util.h" |
| |
| #include "net/cert/x509_util.h" |
| #include "net/ssl/ssl_private_key.h" |
| |
| namespace { |
| |
| CefRefPtr<CefBinaryValue> EncodeCertificate(const CRYPTO_BUFFER* cert_buffer, |
| bool der) { |
| std::string encoded; |
| if (der) { |
| encoded = |
| std::string(net::x509_util::CryptoBufferAsStringPiece(cert_buffer)); |
| } else if (!net::X509Certificate::GetPEMEncoded(cert_buffer, &encoded)) { |
| return nullptr; |
| } |
| if (encoded.empty()) |
| return nullptr; |
| return CefBinaryValue::Create(encoded.c_str(), encoded.size()); |
| } |
| |
| } // namespace |
| |
| CefX509CertificateImpl::CefX509CertificateImpl( |
| std::unique_ptr<net::ClientCertIdentity> identity) |
| : identity_(std::move(identity)), cert_(identity_->certificate()) {} |
| |
| CefX509CertificateImpl::CefX509CertificateImpl( |
| scoped_refptr<net::X509Certificate> cert) |
| : cert_(cert) {} |
| |
| CefRefPtr<CefX509CertPrincipal> CefX509CertificateImpl::GetSubject() { |
| if (cert_) |
| return new CefX509CertPrincipalImpl(cert_->subject()); |
| return nullptr; |
| } |
| |
| CefRefPtr<CefX509CertPrincipal> CefX509CertificateImpl::GetIssuer() { |
| if (cert_) |
| return new CefX509CertPrincipalImpl(cert_->issuer()); |
| return nullptr; |
| } |
| |
| CefRefPtr<CefBinaryValue> CefX509CertificateImpl::GetSerialNumber() { |
| if (cert_) { |
| const std::string& serial = cert_->serial_number(); |
| return CefBinaryValue::Create(serial.c_str(), serial.size()); |
| } |
| return nullptr; |
| } |
| |
| CefTime CefX509CertificateImpl::GetValidStart() { |
| CefTime validity; |
| if (cert_) { |
| const base::Time& valid_time = cert_->valid_start(); |
| if (!valid_time.is_null()) |
| cef_time_from_basetime(valid_time, validity); |
| } |
| return validity; |
| } |
| |
| CefTime CefX509CertificateImpl::GetValidExpiry() { |
| CefTime validity; |
| if (cert_) { |
| const base::Time& valid_time = cert_->valid_expiry(); |
| if (!valid_time.is_null()) |
| cef_time_from_basetime(valid_time, validity); |
| } |
| return validity; |
| } |
| |
| CefRefPtr<CefBinaryValue> CefX509CertificateImpl::GetDEREncoded() { |
| if (cert_) { |
| const CRYPTO_BUFFER* cert_buffer = cert_->cert_buffer(); |
| if (cert_buffer) |
| return EncodeCertificate(cert_buffer, true); |
| } |
| return nullptr; |
| } |
| |
| CefRefPtr<CefBinaryValue> CefX509CertificateImpl::GetPEMEncoded() { |
| if (cert_) { |
| const CRYPTO_BUFFER* cert_buffer = cert_->cert_buffer(); |
| if (cert_buffer) |
| return EncodeCertificate(cert_buffer, false); |
| } |
| return nullptr; |
| } |
| |
| size_t CefX509CertificateImpl::GetIssuerChainSize() { |
| if (cert_) |
| return cert_->intermediate_buffers().size(); |
| return 0; |
| } |
| |
| void CefX509CertificateImpl::AcquirePrivateKey( |
| base::OnceCallback<void(scoped_refptr<net::SSLPrivateKey>)> |
| private_key_callback) { |
| if (identity_) |
| identity_->AcquirePrivateKey(std::move(private_key_callback)); |
| else |
| std::move(private_key_callback).Run(nullptr); |
| } |
| |
| void CefX509CertificateImpl::GetEncodedIssuerChain( |
| CefX509Certificate::IssuerChainBinaryList& chain, |
| bool der) { |
| chain.clear(); |
| if (cert_) { |
| for (const auto& it : cert_->intermediate_buffers()) { |
| // Add each to the chain, even if one conversion unexpectedly failed. |
| // GetIssuerChainSize depends on these being the same length. |
| chain.push_back(EncodeCertificate(it.get(), der)); |
| } |
| } |
| } |
| |
| void CefX509CertificateImpl::GetDEREncodedIssuerChain( |
| CefX509Certificate::IssuerChainBinaryList& chain) { |
| if (der_encoded_issuer_chain_.empty()) |
| GetEncodedIssuerChain(der_encoded_issuer_chain_, true); |
| chain = der_encoded_issuer_chain_; |
| } |
| |
| void CefX509CertificateImpl::GetPEMEncodedIssuerChain( |
| CefX509Certificate::IssuerChainBinaryList& chain) { |
| if (pem_encoded_issuer_chain_.empty()) |
| GetEncodedIssuerChain(pem_encoded_issuer_chain_, false); |
| chain = pem_encoded_issuer_chain_; |
| } |