diff options
author | mattm@chromium.org <mattm@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2013-10-25 22:03:26 +0000 |
---|---|---|
committer | mattm@chromium.org <mattm@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2013-10-25 22:03:26 +0000 |
commit | 3f3b9b18150a554f25266ea128c00e7099b44dab (patch) | |
tree | 0a09cff50617d47ee2c331f1f9b1eeb230548b10 | |
parent | e5d506af10531be07634ff375e0aea4bd975dbce (diff) | |
download | chromium_src-3f3b9b18150a554f25266ea128c00e7099b44dab.zip chromium_src-3f3b9b18150a554f25266ea128c00e7099b44dab.tar.gz chromium_src-3f3b9b18150a554f25266ea128c00e7099b44dab.tar.bz2 |
crypto/nss_util: Get TPM slot id, do lookup by id instead of by name.
chromeos/cert_loader: store slot id as int.
BUG=302124
Review URL: https://codereview.chromium.org/36593002
git-svn-id: svn://svn.chromium.org/chrome/trunk/src@231126 0039d316-1c4b-4281-b951-d872f2087c98
-rw-r--r-- | chromeos/cert_loader.cc | 11 | ||||
-rw-r--r-- | chromeos/cert_loader.h | 6 | ||||
-rw-r--r-- | chromeos/network/client_cert_resolver.cc | 12 | ||||
-rw-r--r-- | chromeos/network/network_connection_handler.cc | 12 | ||||
-rw-r--r-- | crypto/nss_util.cc | 61 | ||||
-rw-r--r-- | crypto/nss_util.h | 1 |
6 files changed, 62 insertions, 41 deletions
diff --git a/chromeos/cert_loader.cc b/chromeos/cert_loader.cc index 5674117..ea8895f 100644 --- a/chromeos/cert_loader.cc +++ b/chromeos/cert_loader.cc @@ -94,6 +94,7 @@ CertLoader::CertLoader() tpm_token_state_(TPM_STATE_UNKNOWN), tpm_request_delay_( base::TimeDelta::FromMilliseconds(kInitialRequestDelayMs)), + tpm_token_slot_id_(-1), initialize_token_factory_(this), update_certificates_factory_(this) { if (LoginState::IsInitialized()) @@ -211,8 +212,10 @@ void CertLoader::InitializeTokenAndLoadCertificates() { base::PostTaskAndReplyWithResult( crypto_task_runner_.get(), FROM_HERE, - base::Bind( - &crypto::InitializeTPMToken, tpm_token_name_, tpm_user_pin_), + base::Bind(&crypto::InitializeTPMToken, + tpm_token_name_, + tpm_token_slot_id_, + tpm_user_pin_), base::Bind(&CertLoader::OnTPMTokenInitialized, initialize_token_factory_.GetWeakPtr())); return; @@ -298,7 +301,7 @@ void CertLoader::OnPkcs11IsTpmTokenReady(DBusMethodCallStatus call_status, void CertLoader::OnPkcs11GetTpmTokenInfo(DBusMethodCallStatus call_status, const std::string& token_name, const std::string& user_pin, - int token_slot) { + int token_slot_id) { VLOG(1) << "OnPkcs11GetTpmTokenInfo: " << token_name; if (call_status == DBUS_METHOD_CALL_FAILURE) { @@ -307,7 +310,7 @@ void CertLoader::OnPkcs11GetTpmTokenInfo(DBusMethodCallStatus call_status, } tpm_token_name_ = token_name; - tpm_token_slot_ = base::IntToString(token_slot); + tpm_token_slot_id_ = token_slot_id; tpm_user_pin_ = user_pin; tpm_token_state_ = TPM_TOKEN_INFO_RECEIVED; diff --git a/chromeos/cert_loader.h b/chromeos/cert_loader.h index f9c2de0..226bf30 100644 --- a/chromeos/cert_loader.h +++ b/chromeos/cert_loader.h @@ -100,7 +100,7 @@ class CHROMEOS_EXPORT CertLoader : public net::CertDatabase::Observer, // TPM info is only valid once the TPM is available (IsHardwareBacked is // true). Otherwise empty strings will be returned. const std::string& tpm_token_name() const { return tpm_token_name_; } - const std::string& tpm_token_slot() const { return tpm_token_slot_; } + int tpm_token_slot_id() const { return tpm_token_slot_id_; } const std::string& tpm_user_pin() const { return tpm_user_pin_; } // This will be empty until certificates_loaded() is true. @@ -124,7 +124,7 @@ class CHROMEOS_EXPORT CertLoader : public net::CertDatabase::Observer, void OnPkcs11GetTpmTokenInfo(DBusMethodCallStatus call_status, const std::string& token_name, const std::string& user_pin, - int token_slot); + int token_slot_id); void OnTPMTokenInitialized(bool success); // These calls handle the updating of the certificate list after the TPM token @@ -178,7 +178,7 @@ class CHROMEOS_EXPORT CertLoader : public net::CertDatabase::Observer, // Cached TPM token info. std::string tpm_token_name_; - std::string tpm_token_slot_; + int tpm_token_slot_id_; std::string tpm_user_pin_; // Cached Certificates. diff --git a/chromeos/network/client_cert_resolver.cc b/chromeos/network/client_cert_resolver.cc index 72c97c5..9a48ec4 100644 --- a/chromeos/network/client_cert_resolver.cc +++ b/chromeos/network/client_cert_resolver.cc @@ -12,6 +12,7 @@ #include <string> #include "base/stl_util.h" +#include "base/strings/string_number_conversions.h" #include "base/task_runner.h" #include "base/threading/worker_pool.h" #include "base/time/time.h" @@ -431,11 +432,12 @@ void ClientCertResolver::ConfigureCertificates(NetworkCertMatches* matches) { VLOG(1) << "Configuring certificate of network " << it->service_path; CertLoader* cert_loader = CertLoader::Get(); base::DictionaryValue shill_properties; - client_cert::SetShillProperties(it->cert_config_type, - cert_loader->tpm_token_slot(), - cert_loader->tpm_user_pin(), - &it->pkcs11_id, - &shill_properties); + client_cert::SetShillProperties( + it->cert_config_type, + base::IntToString(cert_loader->tpm_token_slot_id()), + cert_loader->tpm_user_pin(), + &it->pkcs11_id, + &shill_properties); DBusThreadManager::Get()->GetShillServiceClient()-> SetProperties(dbus::ObjectPath(it->service_path), shill_properties, diff --git a/chromeos/network/network_connection_handler.cc b/chromeos/network/network_connection_handler.cc index 1418bfa..9649f51 100644 --- a/chromeos/network/network_connection_handler.cc +++ b/chromeos/network/network_connection_handler.cc @@ -7,6 +7,7 @@ #include "base/bind.h" #include "base/command_line.h" #include "base/json/json_reader.h" +#include "base/strings/string_number_conversions.h" #include "chromeos/chromeos_switches.h" #include "chromeos/dbus/dbus_thread_manager.h" #include "chromeos/dbus/shill_manager_client.h" @@ -441,11 +442,12 @@ void NetworkConnectionHandler::VerifyConfiguredAndConnect( if (cert_loader_ && cert_loader_->IsHardwareBacked()) { // Pass NULL if pkcs11_id is empty, so that it doesn't clear any // previously configured client cert. - client_cert::SetShillProperties(client_cert_type, - cert_loader_->tpm_token_slot(), - cert_loader_->tpm_user_pin(), - pkcs11_id.empty() ? NULL : &pkcs11_id, - &config_properties); + client_cert::SetShillProperties( + client_cert_type, + base::IntToString(cert_loader_->tpm_token_slot_id()), + cert_loader_->tpm_user_pin(), + pkcs11_id.empty() ? NULL : &pkcs11_id, + &config_properties); } } diff --git a/crypto/nss_util.cc b/crypto/nss_util.cc index 80191b3..04080ed 100644 --- a/crypto/nss_util.cc +++ b/crypto/nss_util.cc @@ -168,20 +168,6 @@ void UseLocalCacheOfNSSDatabaseIfNFS(const base::FilePath& database_dir) { #endif // defined(OS_LINUX) || defined(OS_OPENBSD) } -PK11SlotInfo* FindSlotWithTokenName(const std::string& token_name) { - AutoSECMODListReadLock auto_lock; - SECMODModuleList* head = SECMOD_GetDefaultModuleList(); - for (SECMODModuleList* item = head; item != NULL; item = item->next) { - int slot_count = item->module->loaded ? item->module->slotCount : 0; - for (int i = 0; i < slot_count; i++) { - PK11SlotInfo* slot = item->module->slots[i]; - if (PK11_GetTokenName(slot) == token_name) - return PK11_ReferenceSlot(slot); - } - } - return NULL; -} - #endif // defined(USE_NSS) // A singleton to initialize/deinitialize NSPR. @@ -247,10 +233,14 @@ class NSSInitSingleton { } void EnableTPMTokenForNSS() { + // If this gets set, then we'll use the TPM for certs with + // private keys, otherwise we'll fall back to the software + // implementation. tpm_token_enabled_for_nss_ = true; } bool InitializeTPMToken(const std::string& token_name, + int token_slot_id, const std::string& user_pin) { // If EnableTPMTokenForNSS hasn't been called, return false. if (!tpm_token_enabled_for_nss_) @@ -275,12 +265,15 @@ class NSSInitSingleton { // read from this slot without requiring a call to C_Login. // askpw=only -- Only authenticate to the token when necessary. "NSS=\"slotParams=(0={slotFlags=[PublicCerts] askpw=only})\""); + if (!chaps_module_ && test_slot_) { + // chromeos_unittests try to test the TPM initialization process. If we + // have a test DB open, pretend that it is the TPM slot. + tpm_slot_ = PK11_ReferenceSlot(test_slot_); + return true; + } } if (chaps_module_){ - // If this gets set, then we'll use the TPM for certs with - // private keys, otherwise we'll fall back to the software - // implementation. - tpm_slot_ = GetTPMSlot(); + tpm_slot_ = GetTPMSlotForId(token_slot_id); return tpm_slot_ != NULL; } @@ -302,10 +295,22 @@ class NSSInitSingleton { return tpm_slot_ != NULL; } - PK11SlotInfo* GetTPMSlot() { - std::string token_name; - GetTPMTokenInfo(&token_name, NULL); - return FindSlotWithTokenName(token_name); + // Note that CK_SLOT_ID is an unsigned long, but cryptohome gives us the slot + // id as an int. This should be safe since this is only used with chaps, which + // we also control. + PK11SlotInfo* GetTPMSlotForId(CK_SLOT_ID slot_id) { + if (!chaps_module_) + return NULL; + + VLOG(1) << "Poking chaps module."; + SECStatus rv = SECMOD_UpdateSlotList(chaps_module_); + if (rv != SECSuccess) + PLOG(ERROR) << "SECMOD_UpdateSlotList failed: " << PORT_GetError(); + + PK11SlotInfo* slot = SECMOD_LookupSlot(chaps_module_->moduleID, slot_id); + if (!slot) + LOG(ERROR) << "TPM slot " << slot_id << " not found."; + return slot; } #endif // defined(OS_CHROMEOS) @@ -526,7 +531,7 @@ class NSSInitSingleton { // Aw, snap. Can't find/load root cert shared library. // This will make it hard to talk to anybody via https. - NOTREACHED(); + // TODO(mattm): Re-add the NOTREACHED here when crbug.com/310972 is fixed. return NULL; } @@ -549,6 +554,12 @@ class NSSInitSingleton { << GetNSSErrorMessage(); return NULL; } + if (!module->loaded) { + LOG(ERROR) << "After loading " << name << ", loaded==false: " + << GetNSSErrorMessage(); + SECMOD_DestroyModule(module); + return NULL; + } return module; } #endif @@ -752,8 +763,10 @@ bool IsTPMTokenReady() { } bool InitializeTPMToken(const std::string& token_name, + int token_slot_id, const std::string& user_pin) { - return g_nss_singleton.Get().InitializeTPMToken(token_name, user_pin); + return g_nss_singleton.Get().InitializeTPMToken( + token_name, token_slot_id, user_pin); } #endif // defined(OS_CHROMEOS) diff --git a/crypto/nss_util.h b/crypto/nss_util.h index 1d7503d..2c825a0 100644 --- a/crypto/nss_util.h +++ b/crypto/nss_util.h @@ -116,6 +116,7 @@ CRYPTO_EXPORT bool IsTPMTokenReady(); // Initialize the TPM token. Does nothing if it is already initialized. CRYPTO_EXPORT bool InitializeTPMToken(const std::string& token_name, + int token_slot_id, const std::string& user_pin); #endif |