Botan  2.4.0
Crypto and TLS for C++11
xmss_address.h
Go to the documentation of this file.
1 /*
2  * XMSS Address
3  * (C) 2016 Matthias Gierlings
4  *
5  * Botan is released under the Simplified BSD License (see license.txt)
6  **/
7 
8 #ifndef BOTAN_XMSS_ADDRESS_H_
9 #define BOTAN_XMSS_ADDRESS_H_
10 
11 #include <botan/xmss_tools.h>
12 
13 namespace Botan {
14 
15 /**
16  * Generic XMSS Address type holding 256 Bits of data. Properties
17  * of all three address formats L-Tree-Address, Hash-Tree-Address,
18  * OTS-Hash-Address can be called depending on the type currently
19  * assigned to the XMSS address using set_type().
20  **/
21 class XMSS_Address final
22  {
23  public:
24  /**
25  * Distinct types an XMSS_Address can represent. The available types
26  * are specified in [1] - 2.5 Hash Function Address Scheme.
27  **/
28  enum class Type : uint8_t
29  {
30  None = 255,
31  OTS_Hash_Address = 0,
32  LTree_Address = 1,
34  };
35 
36  /**
37  * The available modes for an XMSS Address:
38  * - Key_Mode: Used to generate the key.
39  * - Mask_Mode: Sets the n-byte bitmask (OTS-Hash-Address)
40  * - Mask_MSB_Mode: Used to generate the b most significant bytes of
41  * the 2n-byte bitmask (LTree Address and Hash Tree Address).
42  * - Mask_LSB_Mode: Used to generated the b least significant bytes
43  * of the 2n-byte bitmask. (LTree Address and Hash Tree Address).
44  **/
45  enum class Key_Mask : uint8_t
46  {
47  Key_Mode = 0,
48  Mask_Mode = 1,
49  Mask_MSB_Mode = 1,
50  Mask_LSB_Mode = 2
51  };
52 
53  /**
54  * Layer Address for XMSS is constantly zero and can not be changed this
55  * property is only of relevance to XMSS_MT.
56  *
57  * @return Layer address, which is constant 0 for XMSS.
58  **/
59  uint8_t get_layer_addr() const { return 0; }
60 
61  /**
62  * Layer Address for XMSS is constantly zero and can not be changed this
63  * property is only of relevance to XMSS_MT. Calling this method for
64  * XMSS will result in an error.
65  **/
67  {
68  BOTAN_ASSERT(false, "Only available in XMSS_MT.");
69  }
70 
71  /**
72  * Tree Address for XMSS is constantly zero and can not be changed this
73  * property is only of relevance to XMSS_MT.
74  *
75  * @return Tree address, which is constant 0 for XMSS.
76  **/
77  uint64_t get_tree_addr() const { return 0; }
78 
79  /**
80  * Tree Address for XMSS is constantly zero and can not be changed this
81  * property is only of relevance to XMSS_MT. Calling this method for
82  * XMSS will result in an error.
83  **/
85  {
86  BOTAN_ASSERT(false, "Only available in XMSS_MT.");
87  }
88 
89  /**
90  * retrieves the logical type currently assigned to the XMSS Address
91  * instance.
92  *
93  * @return Type of the address (OTS_Hash_Address, LTree_Address or
94  * Hash_Tree_Address)
95  **/
96  Type get_type() const
97  {
98  return static_cast<Type>(m_data[15]);
99  }
100 
101  /**
102  * Changes the logical type currently assigned to the XMSS Address
103  * instance. Please note that changing the type will automatically
104  * reset the 128 LSBs of the Address to zero. This affects the
105  * key_mask_mode property as well as all properties identified by
106  * XMSS_Address::Property.
107  *
108  * @param type Type that shall be assigned to the address
109  * (OTS_Hash_Address, LTree_Address or Hash_Tree_Address)
110  **/
112  {
113  m_data[15] = static_cast<uint8_t>(type);
114  std::fill(m_data.begin() + 16, m_data.end(), static_cast<uint8_t>(0));
115  }
116 
117  /**
118  * Retrieves the mode the address os currently set to. (See
119  * XMSS_Address::Key_Mask for details.)
120  *
121  * @return currently active mode
122  **/
124  {
125  return Key_Mask(m_data[31]);
126  }
127 
128  /**
129  * Changes the mode the address currently used address mode.
130  * (XMSS_Address::Key_Mask for details.)
131  *
132  * @param value Target mode.
133  **/
135  {
138  "Invalid Key_Mask for current XMSS_Address::Type.");
139  m_data[31] = static_cast<uint8_t>(value);
140  }
141 
142  /**
143  * Retrieve the index of the OTS key pair within the tree. A call to
144  * this method is only valid, if the address type is set to
145  * Type::OTS_Hash_Address.
146  *
147  * @return index of OTS key pair.
148  **/
149  uint32_t get_ots_address() const
150  {
152  "get_ots_address() requires XMSS_Address::Type::"
153  "OTS_Hash_Address.");
154  return get_hi32(2);
155  }
156 
157  /**
158  * Sets the index of the OTS key pair within the tree. A call to this
159  * method is only valid, if the address type is set to
160  * Type::OTS_Hash_Address.
161  *
162  * @param value index of OTS key pair.
163  **/
164  void set_ots_address(uint32_t value)
165  {
167  "set_ots_address() requires XMSS_Address::Type::"
168  "OTS_Hash_Address.");
169  set_hi32(2, value);
170  }
171 
172  /**
173  * Retrieves the index of the leaf computed with this LTree. A call to
174  * this method is only valid, if the address type is set to
175  * Type::LTree_Address.
176  *
177  * @return index of the leaf.
178  **/
179  uint32_t get_ltree_address() const
180  {
182  "set_ltree_address() requires XMSS_Address::Type::"
183  "LTree_Address.");
184  return get_hi32(2);
185  }
186 
187  /**
188  * Sets the index of the leaf computed with this LTree. A call to this
189  * method is only valid, if the address type is set to
190  * Type::LTree_Address.
191  *
192  * @param value index of the leaf.
193  **/
194  void set_ltree_address(uint32_t value)
195  {
197  "set_ltree_address() requires XMSS_Address::Type::"
198  "LTree_Address.");
199  set_hi32(2, value);
200  }
201 
202  /**
203  * Retrieve the chain address. A call to this method is only valid, if
204  * the address type is set to Type::OTS_Hash_Address.
205  *
206  * @return chain address.
207  **/
208  uint32_t get_chain_address() const
209  {
211  "get_chain_address() requires XMSS_Address::Type::"
212  "OTS_Hash_Address.");
213  return get_lo32(2);
214  }
215 
216  /**
217  * Set the chain address. A call to this method is only valid, if
218  * the address type is set to Type::OTS_Hash_Address.
219  **/
220  void set_chain_address(uint32_t value)
221  {
223  "set_chain_address() requires XMSS_Address::Type::"
224  "OTS_Hash_Address.");
225  set_lo32(2, value);
226  }
227 
228  /**
229  * Retrieves the height of the tree node to be computed within the
230  * tree. A call to this method is only valid, if the address type is
231  * set to Type::LTree_Address or Type::Hash_Tree_Address.
232  *
233  * @return height of the tree node.
234  **/
235  uint32_t get_tree_height() const
236  {
239  "get_tree_height() requires XMSS_Address::Type::"
240  "LTree_Address or XMSS_Address::Type::Hash_Tree_Address.");
241  return get_lo32(2);
242  }
243 
244  /**
245  * Sets the height of the tree node to be computed within the
246  * tree. A call to this method is only valid, if the address type is
247  * set to Type::LTree_Address or Type::Hash_Tree_Address.
248  *
249  * @param value height of the tree node.
250  **/
251  void set_tree_height(uint32_t value)
252  {
255  "set_tree_height() requires XMSS_Address::Type::"
256  "LTree_Address or XMSS_Address::Type::Hash_Tree_Address.");
257  set_lo32(2, value);
258  }
259 
260  /**
261  * Retrieves the address of the hash function call within the chain.
262  * A call to this method is only valid, if the address type is
263  * set to Type::OTS_Hash_Address.
264  *
265  * @return address of the hash function call within chain.
266  **/
267  uint32_t get_hash_address() const
268  {
270  "get_hash_address() requires XMSS_Address::Type::"
271  "OTS_Hash_Address.");
272  return get_hi32(3);
273  }
274 
275  /**
276  * Sets the address of the hash function call within the chain.
277  * A call to this method is only valid, if the address type is
278  * set to Type::OTS_Hash_Address.
279  *
280  * @param value address of the hash function call within chain.
281  **/
282  void set_hash_address(uint32_t value)
283  {
285  "set_hash_address() requires XMSS_Address::Type::"
286  "OTS_Hash_Address.");
287  set_hi32(3, value);
288  }
289 
290  /**
291  * Retrieves the index of the tree node at current tree height in the
292  * tree. A call to this method is only valid, if the address type is
293  * set to Type::LTree_Address or Type::Hash_Tree_Address.
294  *
295  * @return index of the tree node at current height.
296  **/
297  uint32_t get_tree_index() const
298  {
301  "get_tree_index() requires XMSS_Address::Type::"
302  "LTree_Address or XMSS_Address::Type::Hash_Tree_Address.");
303  return get_hi32(3);
304  }
305 
306  /**
307  * Sets the index of the tree node at current tree height in the
308  * tree. A call to this method is only valid, if the address type is
309  * set to Type::LTree_Address or Type::Hash_Tree_Address.
310  *
311  * @param value index of the tree node at current height.
312  **/
313  void set_tree_index(uint32_t value)
314  {
317  "set_tree_index() requires XMSS_Address::Type::"
318  "LTree_Address or XMSS_Address::Type::Hash_Tree_Address.");
319  set_hi32(3, value);
320  }
321 
323  {
324  return m_data;
325  }
326 
328  {
329  return m_data;
330  }
331 
332  /**
333  * @return the size of an XMSS_Address
334  **/
335  size_t size() const
336  {
337  return m_data.size();
338  }
339 
341  : m_data(m_address_size)
342  {
344  }
345 
347  : m_data(m_address_size)
348  {
349  set_type(type);
350  }
351 
353  {
354  BOTAN_ASSERT(m_data.size() == m_address_size,
355  "XMSS_Address must be of 256 bits size.");
356  }
357 
359  {
360  BOTAN_ASSERT(m_data.size() == m_address_size,
361  "XMSS_Address must be of 256 bits size.");
362  }
363 
364  protected:
366 
367  private:
368  static const size_t m_address_size = 32;
369 
370  inline uint32_t get_hi32(size_t offset) const
371  {
372  return ((0x000000FF & m_data[8 * offset + 3]) |
373  (0x000000FF & m_data[8 * offset + 2]) << 8 |
374  (0x000000FF & m_data[8 * offset + 1]) << 16 |
375  (0x000000FF & m_data[8 * offset ]) << 24);
376  }
377 
378  inline void set_hi32(size_t offset, uint32_t value)
379  {
380  m_data[offset * 8 ] = ((value >> 24) & 0xFF);
381  m_data[offset * 8 + 1] = ((value >> 16) & 0xFF);
382  m_data[offset * 8 + 2] = ((value >> 8) & 0xFF);
383  m_data[offset * 8 + 3] = ((value ) & 0xFF);
384  }
385 
386  inline uint32_t get_lo32(size_t offset) const
387  {
388  return ((0x000000FF & m_data[8 * offset + 7]) |
389  (0x000000FF & m_data[8 * offset + 6]) << 8 |
390  (0x000000FF & m_data[8 * offset + 5]) << 16 |
391  (0x000000FF & m_data[8 * offset + 4]) << 24);
392  }
393 
394  inline void set_lo32(size_t offset, uint32_t value)
395  {
396  m_data[offset * 8 + 4] = ((value >> 24) & 0xFF);
397  m_data[offset * 8 + 5] = ((value >> 16) & 0xFF);
398  m_data[offset * 8 + 6] = ((value >> 8) & 0xFF);
399  m_data[offset * 8 + 7] = ((value ) & 0xFF);
400  }
401  };
402 
403 }
404 
405 #endif
uint32_t get_ltree_address() const
Definition: xmss_address.h:179
uint32_t get_tree_index() const
Definition: xmss_address.h:297
Key_Mask get_key_mask_mode() const
Definition: xmss_address.h:123
void set_ots_address(uint32_t value)
Definition: xmss_address.h:164
void set_tree_height(uint32_t value)
Definition: xmss_address.h:251
uint32_t get_ots_address() const
Definition: xmss_address.h:149
secure_vector< uint8_t > & bytes()
Definition: xmss_address.h:327
void set_ltree_address(uint32_t value)
Definition: xmss_address.h:194
secure_vector< uint8_t > m_data
Definition: xmss_address.h:365
Definition: bigint.h:635
uint64_t get_tree_addr() const
Definition: xmss_address.h:77
MechanismType type
Type get_type() const
Definition: xmss_address.h:96
const secure_vector< uint8_t > & bytes() const
Definition: xmss_address.h:322
#define BOTAN_ASSERT(expr, assertion_made)
Definition: assert.h:29
uint32_t get_chain_address() const
Definition: xmss_address.h:208
uint32_t get_tree_height() const
Definition: xmss_address.h:235
void set_type(Type type)
Definition: xmss_address.h:111
uint32_t get_hash_address() const
Definition: xmss_address.h:267
Definition: alg_id.cpp:13
void set_chain_address(uint32_t value)
Definition: xmss_address.h:220
size_t size() const
Definition: xmss_address.h:335
XMSS_Address(secure_vector< uint8_t > &&data)
Definition: xmss_address.h:358
uint8_t get_layer_addr() const
Definition: xmss_address.h:59
void set_key_mask_mode(Key_Mask value)
Definition: xmss_address.h:134
std::vector< T, secure_allocator< T > > secure_vector
Definition: secmem.h:88
void set_tree_index(uint32_t value)
Definition: xmss_address.h:313
XMSS_Address(Type type)
Definition: xmss_address.h:346
void set_hash_address(uint32_t value)
Definition: xmss_address.h:282
XMSS_Address(const secure_vector< uint8_t > &data)
Definition: xmss_address.h:352