1 // Copyright 2014 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. 4 5 #ifndef CHROMEOS_TPM_TOKEN_LOADER_H_ 6 #define CHROMEOS_TPM_TOKEN_LOADER_H_ 7 8 #include <string> 9 10 #include "base/basictypes.h" 11 #include "base/memory/ref_counted.h" 12 #include "base/memory/weak_ptr.h" 13 #include "base/observer_list.h" 14 #include "base/threading/thread_checker.h" 15 #include "base/time/time.h" 16 #include "chromeos/chromeos_export.h" 17 #include "chromeos/dbus/dbus_method_call_status.h" 18 #include "chromeos/login/login_state.h" 19 20 namespace base { 21 class SequencedTaskRunner; 22 } 23 24 namespace chromeos { 25 26 // This class is responsible for loading the TPM token when the user logs 27 // in. It is expected to be constructed on the UI thread and public methods 28 // should all be called from the UI thread. When the TPM token is loaded, 29 // or if the TPM should stay disabled for the session, the observers are 30 // notified using |OnTPMTokenReady|. 31 class CHROMEOS_EXPORT TPMTokenLoader : public LoginState::Observer { 32 public: 33 class Observer { 34 public: 35 // Called when the TPM token initialization is done or the case where TPM 36 // should stay disabled is detected (e.g. on guest login). 37 virtual void OnTPMTokenReady() = 0; 38 39 protected: 40 virtual ~Observer() {} 41 }; 42 43 // Sets the global instance. Must be called before any calls to Get(). 44 // The global instance will immediately start observing |LoginState|. 45 static void Initialize(); 46 47 // Sets the global. stubbed out, instance. To be used in tests. 48 static void InitializeForTest(); 49 50 // Destroys the global instance. 51 static void Shutdown(); 52 53 // Gets the global instance. Initialize() must be called before this. 54 static TPMTokenLoader* Get(); 55 56 // Returns true if the global instance has been initialized. 57 static bool IsInitialized(); 58 59 // |crypto_task_runner| is the task runner that any synchronous crypto calls 60 // should be made from, e.g. in Chrome this is the IO thread. Must be called 61 // after the thread is started. When called, this will attempt to start TPM 62 // token loading. 63 void SetCryptoTaskRunner( 64 const scoped_refptr<base::SequencedTaskRunner>& crypto_task_runner); 65 66 void AddObserver(TPMTokenLoader::Observer* observer); 67 void RemoveObserver(TPMTokenLoader::Observer* observer); 68 69 // Checks if the TPM token in ready to be used. 70 bool IsTPMTokenReady() const; 71 72 std::string tpm_user_pin() const { return tpm_user_pin_; } 73 74 private: 75 explicit TPMTokenLoader(bool for_test); 76 virtual ~TPMTokenLoader(); 77 78 // Starts tpm token initialization if the user is logged in and the crypto 79 // task runner is set. 80 void MaybeStartTokenInitialization(); 81 82 // This is the cyclic chain of callbacks to initialize the TPM token. 83 void ContinueTokenInitialization(); 84 void OnPersistentNSSDBOpened(); 85 void OnTpmIsEnabled(DBusMethodCallStatus call_status, 86 bool tpm_is_enabled); 87 void OnPkcs11IsTpmTokenReady(DBusMethodCallStatus call_status, 88 bool is_tpm_token_ready); 89 void OnPkcs11GetTpmTokenInfo(DBusMethodCallStatus call_status, 90 const std::string& token_name, 91 const std::string& user_pin, 92 int token_slot_id); 93 void OnTPMTokenInitialized(bool success); 94 95 // If token initialization step fails (e.g. if tpm token is not yet ready) 96 // schedules the initialization step retry attempt after a timeout. 97 void RetryTokenInitializationLater(); 98 99 // Notifies observers that the TPM token is ready. 100 void NotifyTPMTokenReady(); 101 102 // LoginState::Observer 103 virtual void LoggedInStateChanged() OVERRIDE; 104 105 bool initialized_for_test_; 106 107 ObserverList<Observer> observers_; 108 109 // The states are traversed in this order but some might get omitted or never 110 // be left. 111 enum TPMTokenState { 112 TPM_STATE_UNKNOWN, 113 TPM_INITIALIZATION_STARTED, 114 TPM_DB_OPENED, 115 TPM_DISABLED, 116 TPM_ENABLED, 117 TPM_TOKEN_READY, 118 TPM_TOKEN_INFO_RECEIVED, 119 TPM_TOKEN_INITIALIZED, 120 }; 121 TPMTokenState tpm_token_state_; 122 123 // The current request delay before the next attempt to initialize the 124 // TPM. Will be adapted after each attempt. 125 base::TimeDelta tpm_request_delay_; 126 127 // Cached TPM token info. 128 std::string tpm_token_name_; 129 int tpm_token_slot_id_; 130 std::string tpm_user_pin_; 131 132 base::ThreadChecker thread_checker_; 133 134 // TaskRunner for crypto calls. 135 scoped_refptr<base::SequencedTaskRunner> crypto_task_runner_; 136 137 base::WeakPtrFactory<TPMTokenLoader> weak_factory_; 138 139 DISALLOW_COPY_AND_ASSIGN(TPMTokenLoader); 140 }; 141 142 } // namespace chromeos 143 144 #endif // CHROMEOS_TPM_TOKEN_LOADER_H_ 145