summaryrefslogtreecommitdiffstats
path: root/chromeos/network/cert_loader.h
blob: f3b69aefe7c2292986e83d6abb923c7959cf5d83 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
// Copyright (c) 2013 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#ifndef CHROMEOS_NETWORK_CERT_LOADER_H_
#define CHROMEOS_NETWORK_CERT_LOADER_H_

#include <string>

#include "base/memory/ref_counted.h"
#include "base/memory/scoped_ptr.h"
#include "base/memory/weak_ptr.h"
#include "base/observer_list_threadsafe.h"
#include "base/threading/thread_checker.h"
#include "chromeos/chromeos_export.h"
#include "chromeos/dbus/dbus_method_call_status.h"
#include "chromeos/login/login_state.h"
#include "net/cert/cert_database.h"
#include "net/cert/x509_certificate.h"

namespace crypto {
class SymmetricKey;
}

namespace chromeos {

// This class is responsible for initializing the TPM token and loading
// certificates once the TPM is initialized. It is expected to be constructed
// on the UI thread and public methods should all be called from the UI thread.
// When certificates have been loaded (after login completes), or the cert
// database changes, observers are called with OnCertificatesLoaded().
class CHROMEOS_EXPORT CertLoader : public net::CertDatabase::Observer,
                                   public LoginState::Observer {
 public:
  class Observer {
   public:
    virtual ~Observer() {}

    // Called when the certificates, passed for convenience as |cert_list|,
    // have completed loading. |initial_load| is true the first time this
    // is called.
    virtual void OnCertificatesLoaded(const net::CertificateList& cert_list,
                                      bool initial_load) = 0;

   protected:
    Observer() {}

   private:
    DISALLOW_COPY_AND_ASSIGN(Observer);
  };

  // Manage the global instance.
  static void Initialize();
  static void Shutdown();
  static CertLoader* Get();
  static bool IsInitialized();

  void AddObserver(CertLoader::Observer* observer);
  void RemoveObserver(CertLoader::Observer* observer);

  // Returns true when the certificate list has been requested but not loaded.
  bool CertificatesLoading() const;

  // Returns true if the TPM is available for hardware-backed certificates.
  bool IsHardwareBacked() const;

  bool certificates_loaded() const { return certificates_loaded_; }

  // 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_; }
  const std::string& tpm_user_pin() const { return tpm_user_pin_; }

  // This will be empty until certificates_loaded() is true.
  const net::CertificateList& cert_list() const { return cert_list_; }

 private:
  CertLoader();
  virtual ~CertLoader();

  void RequestCertificates();

  void OnTpmIsEnabled(DBusMethodCallStatus call_status,
                      bool tpm_is_enabled);
  void OnPkcs11IsTpmTokenReady(DBusMethodCallStatus call_status,
                               bool is_tpm_token_ready);
  void OnPkcs11GetTpmTokenInfo(DBusMethodCallStatus call_status,
                               const std::string& token_name,
                               const std::string& user_pin);
  void InitializeTPMToken();
  void StartLoadCertificates();
  void UpdateCertificates(net::CertificateList* cert_list);
  void MaybeRetryRequestCertificates();
  void RequestCertificatesTask();

  void NotifyCertificatesLoaded(bool initial_load);

  // net::CertDatabase::Observer
  virtual void OnCertTrustChanged(const net::X509Certificate* cert) OVERRIDE;
  virtual void OnCertAdded(const net::X509Certificate* cert) OVERRIDE;
  virtual void OnCertRemoved(const net::X509Certificate* cert) OVERRIDE;

  // LoginState::Observer
  virtual void LoggedInStateChanged(LoginState::LoggedInState state) OVERRIDE;

  ObserverList<Observer> observers_;

  // Active request task for re-requests while waiting for TPM init.
  base::Closure request_task_;

  // Local state.
  bool tpm_token_ready_;
  bool certificates_requested_;
  bool certificates_loaded_;
  // The key store for the current user has been loaded. This flag is needed to
  // ensure that the key store will not be loaded twice in the policy recovery
  // "safe-mode".
  bool key_store_loaded_;

  // Cached TPM token info.
  std::string tpm_token_name_;
  std::string tpm_token_slot_;
  std::string tpm_user_pin_;

  // Cached Certificates.
  net::CertificateList cert_list_;

  base::ThreadChecker thread_checker_;

  // TODO(stevenjb): Use multiple factories to track callback chains.
  base::WeakPtrFactory<CertLoader> weak_ptr_factory_;

  DISALLOW_COPY_AND_ASSIGN(CertLoader);
};

}  // namespace chromeos

#endif  // CHROMEOS_NETWORK_CERT_LOADER_H_