Index: chromeos/network/client_cert_util.cc |
diff --git a/chromeos/network/client_cert_util.cc b/chromeos/network/client_cert_util.cc |
index 4957e0e5c808d1eef1f55a3636bca0e402a9c38e..b831beaf53b99c7bdfb6ddd64817ece339f47e9e 100644 |
--- a/chromeos/network/client_cert_util.cc |
+++ b/chromeos/network/client_cert_util.cc |
@@ -11,6 +11,8 @@ |
#include <string> |
#include <vector> |
+#include "base/strings/string_number_conversions.h" |
+#include "base/strings/stringprintf.h" |
#include "base/values.h" |
#include "chromeos/network/certificate_pattern.h" |
#include "chromeos/network/network_event_log.h" |
@@ -29,71 +31,7 @@ namespace client_cert { |
namespace { |
-// Functor to filter out non-matching issuers. |
-class IssuerFilter { |
- public: |
- explicit IssuerFilter(const IssuerSubjectPattern& issuer) |
- : issuer_(issuer) {} |
- bool operator()(const scoped_refptr<net::X509Certificate>& cert) const { |
- return !CertPrincipalMatches(issuer_, cert.get()->issuer()); |
- } |
- private: |
- const IssuerSubjectPattern& issuer_; |
-}; |
- |
-// Functor to filter out non-matching subjects. |
-class SubjectFilter { |
- public: |
- explicit SubjectFilter(const IssuerSubjectPattern& subject) |
- : subject_(subject) {} |
- bool operator()(const scoped_refptr<net::X509Certificate>& cert) const { |
- return !CertPrincipalMatches(subject_, cert.get()->subject()); |
- } |
- private: |
- const IssuerSubjectPattern& subject_; |
-}; |
- |
-// Functor to filter out certs that don't have private keys, or are invalid. |
-class PrivateKeyFilter { |
- public: |
- explicit PrivateKeyFilter(net::CertDatabase* cert_db) : cert_db_(cert_db) {} |
- bool operator()(const scoped_refptr<net::X509Certificate>& cert) const { |
- return cert_db_->CheckUserCert(cert.get()) != net::OK; |
- } |
- private: |
- net::CertDatabase* cert_db_; |
-}; |
- |
-// Functor to filter out certs that don't have an issuer in the associated |
-// IssuerCAPEMs list. |
-class IssuerCaFilter { |
- public: |
- explicit IssuerCaFilter(const std::vector<std::string>& issuer_ca_pems) |
- : issuer_ca_pems_(issuer_ca_pems) {} |
- bool operator()(const scoped_refptr<net::X509Certificate>& cert) const { |
- // Find the certificate issuer for each certificate. |
- // TODO(gspencer): this functionality should be available from |
- // X509Certificate or NSSCertDatabase. |
- net::ScopedCERTCertificate issuer_cert(CERT_FindCertIssuer( |
- cert.get()->os_cert_handle(), PR_Now(), certUsageAnyCA)); |
- |
- if (!issuer_cert) |
- return true; |
- |
- std::string pem_encoded; |
- if (!net::X509Certificate::GetPEMEncoded(issuer_cert.get(), |
- &pem_encoded)) { |
- LOG(ERROR) << "Couldn't PEM-encode certificate."; |
- return true; |
- } |
- |
- return (std::find(issuer_ca_pems_.begin(), issuer_ca_pems_.end(), |
- pem_encoded) == |
- issuer_ca_pems_.end()); |
- } |
- private: |
- const std::vector<std::string>& issuer_ca_pems_; |
-}; |
+const char kDefaultTPMPin[] = "111111"; |
std::string GetStringFromDictionary(const base::DictionaryValue& dict, |
const std::string& key) { |
@@ -159,65 +97,6 @@ bool CertPrincipalMatches(const IssuerSubjectPattern& pattern, |
return true; |
} |
-scoped_refptr<net::X509Certificate> GetCertificateMatch( |
- const CertificatePattern& pattern, |
- const net::CertificateList& all_certs) { |
- typedef std::list<scoped_refptr<net::X509Certificate> > CertificateStlList; |
- |
- // Start with all the certs, and narrow it down from there. |
- CertificateStlList matching_certs; |
- |
- if (all_certs.empty()) |
- return NULL; |
- |
- for (net::CertificateList::const_iterator iter = all_certs.begin(); |
- iter != all_certs.end(); ++iter) { |
- matching_certs.push_back(*iter); |
- } |
- |
- // Strip off any certs that don't have the right issuer and/or subject. |
- if (!pattern.issuer().Empty()) { |
- matching_certs.remove_if(IssuerFilter(pattern.issuer())); |
- if (matching_certs.empty()) |
- return NULL; |
- } |
- |
- if (!pattern.subject().Empty()) { |
- matching_certs.remove_if(SubjectFilter(pattern.subject())); |
- if (matching_certs.empty()) |
- return NULL; |
- } |
- |
- if (!pattern.issuer_ca_pems().empty()) { |
- matching_certs.remove_if(IssuerCaFilter(pattern.issuer_ca_pems())); |
- if (matching_certs.empty()) |
- return NULL; |
- } |
- |
- // Eliminate any certs that don't have private keys associated with |
- // them. The CheckUserCert call in the filter is a little slow (because of |
- // underlying PKCS11 calls), so we do this last to reduce the number of times |
- // we have to call it. |
- PrivateKeyFilter private_filter(net::CertDatabase::GetInstance()); |
- matching_certs.remove_if(private_filter); |
- |
- if (matching_certs.empty()) |
- return NULL; |
- |
- // We now have a list of certificates that match the pattern we're |
- // looking for. Now we find the one with the latest start date. |
- scoped_refptr<net::X509Certificate> latest(NULL); |
- |
- // Iterate over the rest looking for the one that was issued latest. |
- for (CertificateStlList::iterator iter = matching_certs.begin(); |
- iter != matching_certs.end(); ++iter) { |
- if (!latest.get() || (*iter)->valid_start() > latest->valid_start()) |
- latest = *iter; |
- } |
- |
- return latest; |
-} |
- |
std::string GetPkcs11IdFromEapCertId(const std::string& cert_id) { |
if (cert_id.empty()) |
return std::string(); |
@@ -235,62 +114,82 @@ std::string GetPkcs11IdFromEapCertId(const std::string& cert_id) { |
} |
void SetShillProperties(const ConfigType cert_config_type, |
- const std::string& tpm_slot, |
- const std::string& tpm_pin, |
- const std::string* pkcs11_id, |
+ const int tpm_slot, |
+ const std::string& pkcs11_id, |
base::DictionaryValue* properties) { |
- const char* tpm_pin_property = NULL; |
switch (cert_config_type) { |
case CONFIG_TYPE_NONE: { |
return; |
} |
case CONFIG_TYPE_OPENVPN: { |
- tpm_pin_property = shill::kOpenVPNPinProperty; |
- if (pkcs11_id) { |
- properties->SetStringWithoutPathExpansion( |
- shill::kOpenVPNClientCertIdProperty, *pkcs11_id); |
- } |
+ properties->SetStringWithoutPathExpansion(shill::kOpenVPNPinProperty, |
+ kDefaultTPMPin); |
+ properties->SetStringWithoutPathExpansion( |
+ shill::kOpenVPNClientCertIdProperty, pkcs11_id); |
+ break; |
+ } |
+ case CONFIG_TYPE_IPSEC: { |
+ properties->SetStringWithoutPathExpansion(shill::kL2tpIpsecPinProperty, |
+ kDefaultTPMPin); |
+ properties->SetStringWithoutPathExpansion( |
+ shill::kL2tpIpsecClientCertSlotProperty, base::IntToString(tpm_slot)); |
+ properties->SetStringWithoutPathExpansion( |
+ shill::kL2tpIpsecClientCertIdProperty, pkcs11_id); |
+ break; |
+ } |
+ case CONFIG_TYPE_EAP: { |
+ properties->SetStringWithoutPathExpansion(shill::kEapPinProperty, |
+ kDefaultTPMPin); |
+ std::string key_id = |
+ base::StringPrintf("%i:%s", tpm_slot, pkcs11_id.c_str()); |
+ |
+ // Shill requires both CertID and KeyID for TLS connections, despite the |
+ // fact that by convention they are the same ID, because one identifies |
+ // the certificate and the other the private key. |
+ properties->SetStringWithoutPathExpansion(shill::kEapCertIdProperty, |
+ key_id); |
+ properties->SetStringWithoutPathExpansion(shill::kEapKeyIdProperty, |
+ key_id); |
+ break; |
+ } |
+ } |
+} |
+ |
+void SetEmptyShillProperties(const ConfigType cert_config_type, |
+ base::DictionaryValue* properties) { |
+ switch (cert_config_type) { |
+ case CONFIG_TYPE_NONE: { |
+ return; |
+ } |
+ case CONFIG_TYPE_OPENVPN: { |
+ properties->SetStringWithoutPathExpansion(shill::kOpenVPNPinProperty, |
+ std::string()); |
+ properties->SetStringWithoutPathExpansion( |
+ shill::kOpenVPNClientCertIdProperty, std::string()); |
break; |
} |
case CONFIG_TYPE_IPSEC: { |
- tpm_pin_property = shill::kL2tpIpsecPinProperty; |
- if (!tpm_slot.empty()) { |
- properties->SetStringWithoutPathExpansion( |
- shill::kL2tpIpsecClientCertSlotProperty, tpm_slot); |
- } |
- if (pkcs11_id) { |
- properties->SetStringWithoutPathExpansion( |
- shill::kL2tpIpsecClientCertIdProperty, *pkcs11_id); |
- } |
+ properties->SetStringWithoutPathExpansion(shill::kL2tpIpsecPinProperty, |
+ std::string()); |
+ properties->SetStringWithoutPathExpansion( |
+ shill::kL2tpIpsecClientCertSlotProperty, std::string()); |
+ properties->SetStringWithoutPathExpansion( |
+ shill::kL2tpIpsecClientCertIdProperty, std::string()); |
break; |
} |
case CONFIG_TYPE_EAP: { |
- tpm_pin_property = shill::kEapPinProperty; |
- if (pkcs11_id) { |
- std::string key_id; |
- if (pkcs11_id->empty()) { |
- // An empty pkcs11_id means that we should clear the properties. |
- } else { |
- if (tpm_slot.empty()) |
- NET_LOG_ERROR("Missing TPM slot id", ""); |
- else |
- key_id = tpm_slot + ":"; |
- key_id.append(*pkcs11_id); |
- } |
- // Shill requires both CertID and KeyID for TLS connections, despite the |
- // fact that by convention they are the same ID, because one identifies |
- // the certificate and the other the private key. |
- properties->SetStringWithoutPathExpansion(shill::kEapCertIdProperty, |
- key_id); |
- properties->SetStringWithoutPathExpansion(shill::kEapKeyIdProperty, |
- key_id); |
- } |
+ properties->SetStringWithoutPathExpansion(shill::kEapPinProperty, |
+ std::string()); |
+ // Shill requires both CertID and KeyID for TLS connections, despite the |
+ // fact that by convention they are the same ID, because one identifies |
+ // the certificate and the other the private key. |
+ properties->SetStringWithoutPathExpansion(shill::kEapCertIdProperty, |
+ std::string()); |
+ properties->SetStringWithoutPathExpansion(shill::kEapKeyIdProperty, |
+ std::string()); |
break; |
} |
} |
- DCHECK(tpm_pin_property); |
- if (!tpm_pin.empty()) |
- properties->SetStringWithoutPathExpansion(tpm_pin_property, tpm_pin); |
} |
ClientCertConfig::ClientCertConfig() |