Botan  2.1.0
Crypto and TLS for C++11
tpm.h
Go to the documentation of this file.
1 
2 /*
3 * TPM 1.2 interface
4 * (C) 2015 Jack Lloyd
5 *
6 * Botan is released under the Simplified BSD License (see license.txt)
7 */
8 
9 #ifndef BOTAN_TPM_H__
10 #define BOTAN_TPM_H__
11 
12 #include <botan/exceptn.h>
13 #include <botan/pk_keys.h>
14 #include <botan/bigint.h>
15 #include <botan/rng.h>
16 #include <botan/uuid.h>
17 
18 //TODO remove this
19 #include <tss/tspi.h>
20 
21 namespace Botan {
22 
23 class TPM_Error : public Exception
24  {
25  public:
26  TPM_Error(const std::string& err) : Exception(err) {}
27  };
28 
29 /**
30 * Creates a connection to the TPM. All other TPM types take and hold
31 * a TPM_Context reference, so all other objects must be deallocated
32 * before ~TPM_Context runs.
33 *
34 * Use nullptr for the srk_password to indicate the well known secret
35 * (ie, an unencrypted SRK). This is usually what you want.
36 *
37 * TODO: handling owner password?
38 */
39 class BOTAN_DLL TPM_Context
40  {
41  public:
42  /**
43  * User callback for getting the PIN. Will be passed the best available
44  * description of what we are attempting to load.
45  */
46  typedef std::function<std::string (std::string)> pin_cb;
47 
48  TPM_Context(pin_cb cb, const char* srk_password);
49 
50  ~TPM_Context();
51 
52  // Get data from the TPM's RNG, whatever that is
53  void gen_random(uint8_t out[], size_t out_len);
54 
55  // Uses Tspi_TPM_StirRandom to add data to TPM's internal pool
56  void stir_random(const uint8_t in[], size_t in_len);
57 
58  std::string get_user_pin(const std::string& who)
59  {
60  return m_pin_cb(who);
61  }
62 
63  uint32_t current_counter();
64 
65  TSS_HCONTEXT handle() const { return m_ctx; }
66  TSS_HKEY srk() const { return m_srk; }
67 
68  private:
69  std::function<std::string (std::string)> m_pin_cb;
70  TSS_HCONTEXT m_ctx;
71  TSS_HKEY m_srk;
72  TSS_HTPM m_tpm;
73  };
74 
75 class BOTAN_DLL TPM_RNG : public Hardware_RNG
76  {
77  public:
78  TPM_RNG(TPM_Context& ctx) : m_ctx(ctx) {}
79 
80  void add_entropy(const uint8_t in[], size_t in_len) override
81  {
82  m_ctx.stir_random(in, in_len);
83  }
84 
85  void randomize(uint8_t out[], size_t out_len) override
86  {
87  m_ctx.gen_random(out, out_len);
88  }
89 
90  std::string name() const override { return "TPM_RNG"; }
91 
92  bool is_seeded() const override { return true; }
93 
94  void clear() override {}
95 
96  private:
97  TPM_Context& m_ctx;
98 };
99 
100 enum class TPM_Storage_Type { User, System };
101 
102 /*
103 * Also implements the public interface, but does not have usable
104 * TODO: derive from RSA_PublicKey???
105 */
106 class BOTAN_DLL TPM_PrivateKey : public Private_Key
107  {
108  public:
109  // TODO: key import?
110 
111  /*
112  * Create a new key on the TPM parented to the SRK
113  * @param bits must be 1024 or 2048
114  */
115  TPM_PrivateKey(TPM_Context& ctx, size_t bits, const char* key_password);
116 
117  // reference an existing TPM key using URL syntax from GnuTLS
118  // "tpmkey:uuid=79f07ca9-73ac-478a-9093-11ca6702e774;storage=user"
119  //TPM_PrivateKey(TPM_Context& ctx, const std::string& tpm_url);
120 
122  const std::string& uuid,
123  TPM_Storage_Type storage_type);
124 
126  const std::vector<uint8_t>& blob);
127 
128  /**
129  * If the key is not currently registered under a known UUID,
130  * generates a new random UUID and registers the key.
131  * Returns the access URL.
132  */
133  std::string register_key(TPM_Storage_Type storage_type);
134 
135  /**
136  * Returns a copy of the public key
137  */
138  std::unique_ptr<Public_Key> public_key() const;
139 
140  std::vector<uint8_t> export_blob() const;
141 
142  TPM_Context& ctx() const { return m_ctx; }
143 
144  TSS_HKEY handle() const { return m_key; }
145 
146  /*
147  * Returns the list of all keys (in URL format) registered with the system
148  */
149  static std::vector<std::string> registered_keys(TPM_Context& ctx);
150 
151  size_t estimated_strength() const override;
152 
153  size_t key_length() const override;
154 
155  AlgorithmIdentifier algorithm_identifier() const override;
156 
157  std::vector<uint8_t> public_key_bits() const override;
158 
159  secure_vector<uint8_t> private_key_bits() const override;
160 
161  bool check_key(RandomNumberGenerator& rng, bool) const override;
162 
163  std::string algo_name() const override { return "RSA"; } // ???
164 
165  std::unique_ptr<PK_Ops::Signature>
166  create_signature_op(RandomNumberGenerator& rng,
167  const std::string& params,
168  const std::string& provider) const override;
169 
170  private:
171  BigInt get_n() const;
172  BigInt get_e() const;
173 
174  TPM_Context& m_ctx;
175  TSS_HKEY m_key;
176 
177  // Only set for registered keys
178  UUID m_uuid;
179  TPM_Storage_Type m_storage;
180 
181  // Lazily computed in get_n, get_e
182  mutable BigInt m_n, m_e;
183  };
184 
185 // TODO: NVRAM interface
186 // TODO: PCR measurement, writing, key locking
187 
188 }
189 
190 #endif
TSS_HKEY srk() const
Definition: tpm.h:66
TPM_Storage_Type
Definition: tpm.h:100
bool is_seeded() const override
Definition: tpm.h:92
TSS_HCONTEXT handle() const
Definition: tpm.h:65
std::string name() const override
Definition: tpm.h:90
TSS_HKEY handle() const
Definition: tpm.h:144
void clear() override
Definition: tpm.h:94
std::vector< T, secure_allocator< T >> secure_vector
Definition: secmem.h:121
void randomize(uint8_t out[], size_t out_len) override
Definition: tpm.h:85
void add_entropy(const uint8_t in[], size_t in_len) override
Definition: tpm.h:80
std::string algo_name() const override
Definition: tpm.h:163
std::function< std::string(std::string)> pin_cb
Definition: tpm.h:46
Definition: alg_id.cpp:13
TPM_RNG(TPM_Context &ctx)
Definition: tpm.h:78
std::string get_user_pin(const std::string &who)
Definition: tpm.h:58
TPM_Error(const std::string &err)
Definition: tpm.h:26
const TPM_PrivateKey & m_key
Definition: tpm.cpp:438
const BigInt & m_n
Definition: rsa.cpp:234
TPM_Context & ctx() const
Definition: tpm.h:142