Software APIs
dif_edn.h
Go to the documentation of this file.
1 // Copyright lowRISC contributors (OpenTitan project).
2 // Licensed under the Apache License, Version 2.0, see LICENSE for details.
3 // SPDX-License-Identifier: Apache-2.0
4 
5 #ifndef OPENTITAN_SW_DEVICE_LIB_DIF_DIF_EDN_H_
6 #define OPENTITAN_SW_DEVICE_LIB_DIF_DIF_EDN_H_
7 
8 /**
9  * @file
10  * @brief <a href="/hw/ip/edn/doc/">Entropy Distribution Network</a> Device
11  * Interface Functions
12  *
13  * This API implements the interface for the Entropy Distribution Network (EDN)
14  * hardware.
15  *
16  * There are two main modes of operation:
17  *
18  * - boot-time: EDN configures the associated CSRNG instance to fetch pre-FIPS
19  * entropy immediately at boot-time or after reset.
20  * - auto refresh: EDN sends reseed and generate commands to the associated
21  * CSRNG instance. The API allows the user to set the CSRNG instantiate,
22  * reseed and generate para meters, as well as the reseed frequency.
23  */
24 
25 #include <stdint.h>
26 
30 
32 
33 #ifdef __cplusplus
34 extern "C" {
35 #endif // __cplusplus
36 
37 enum {
38  /**
39  * Maximum seed material number of uint32_t words supported in CSRNG
40  * instantiate and seed commands.
41  */
43 };
44 
45 enum {
46  /**
47  * Maximum generate length supported in CSRNG generate commands.
48  */
50 };
51 
52 enum {
53  /**
54  * Maximum number of generate commands between reseed commands in
55  * the EDN auto mode.
56  */
58 };
59 
60 enum {
61  /**
62  * Csrng commands
63  */
65  kDifEdnCmdReseed = 2,
66  kDifEdnCmdGenerate = 3
67 };
68 
69 /**
70  * CSRNG seed material for instantiate, reseed and generate commands.
71  */
72 typedef struct dif_edn_seed_material {
73  /**
74  * Number of uint32_t words in `data`. Up to
75  * `kDifEntropySeedMaterialMaxWordLen` words can be set to initialize or
76  * reseed the CSRNG. CSRNG will extend the `data` to zeros if the provided
77  * value is less than kDifEntropySeedMaterialMaxWordLen.
78  */
79  size_t len;
80  /**
81  * Seed material used in CSRNG instantiate, reseed or generate call.
82  */
85 
86 /**
87  * CSRNG command parameters for instantiate, reseed and generate commands.
88  */
89 typedef struct dif_edn_cmd {
90  /**
91  * The CSRNG application interface command header. For details, refer to the
92  * CSRNG documentation.
93  */
94  uint32_t cmd;
95  /**
96  * Optional seed material.
97  */
100 
101 /**
102  * Auto-generate EDN module configuration parameters.
103  */
104 typedef struct dif_edn_auto_params {
105  /**
106  * CSRNG instantiate command material.
107  */
109  /**
110  * CSRNG reseed command material.
111  */
113  /**
114  * CSRNG generate command material.
115  */
117  /**
118  * Number of generate calls that can be made before a reseed request is made.
119  */
120  uint32_t reseed_interval;
122 
123 /**
124  * EDN Status flags.
125  */
126 typedef enum dif_edn_status {
127  /**
128  * SW command register is ready to receive the next word of a command.
129  */
131  /**
132  * Device is ready to receive a command.
133  */
135  /**
136  * Device has received an error from the CSRNG block.
137  */
139  /**
140  * Device has recieved an ACK from the CSRNG block.
141  */
144 
145 /**
146  * EDN SM states as defined in the EDN state machine RTL.
147  */
148 typedef enum dif_edn_sm_state {
149  /**
150  * Device is idle.
151  */
153  /**
154  * Boot mode: load the instantiate command.
155  */
157  /**
158  * Boot mode: wait for instantiate command ack.
159  */
161  /**
162  * Boot mode: load the generate command.
163  */
165  /**
166  * Boot mode: wait for generate command ack.
167  */
169  /**
170  * Boot mode: signal a done pulse.
171  */
173  /**
174  * Boot mode: stay in done state until reset.
175  */
177  /**
178  * Boot mode: load the uninstantiate command.
179  */
181  /**
182  * Boot mode: wait for uninstantiate command ack.
183  */
185  /**
186  * Auto mode: load the instantiate command.
187  */
189  /**
190  * Auto mode: wait for first instantiate command ack.
191  */
193  /**
194  * Auto mode: wait for instantiate command ack.
195  */
197  /**
198  * Auto mode: determine next command to be sent.
199  */
201  /**
202  * Auto mode: capture the gen fifo count.
203  */
205  /**
206  * Auto mode: send the generate command.
207  */
209  /**
210  * Auto mode: capture the reseed fifo count.
211  */
213  /**
214  * Auto mode: send the reseed command.
215  */
217  /**
218  * Sw port: no hw request mode.
219  */
221  /**
222  * Stop accepting entropy from CSRNG.
223  */
225  /**
226  * Illegal state reached and hang.
227  */
230 
231 /**
232  * Enumeration of EDN FIFOs, which indicates which part of the hardware
233  * produced an error.
234  */
235 typedef enum dif_edn_fifo {
236  kDifEdnFifoReseedCmd,
237  kDifEdnFifoGenerateCmd,
239 
240 /**
241  * Enumeration of EDN FIFO errors.
242  */
243 typedef enum dif_edn_error {
244  /**
245  * Indicates an error in the command ack state machine.
246  */
248  /**
249  * Indicates an error in the main state machine.
250  */
252  /**
253  * Indicates an error in a hardened counter.
254  */
256  /**
257  * Indicates a write to a full FIFO occured.
258  */
260  /**
261  * Indicates a read from an empty FIFO occured.
262  */
264  /**
265  * Indicates a FIFO was somehow both full and empty.
266  */
269 
270 /**
271  * CSRNG consume seed from entropy source enable.
272  */
274  /**
275  * Seed material used as the only seed material.
276  *
277  * This configuration option will toggle the hardware state of the
278  * CSRNG to non-FIPS compliant until it is re-instantiated.
279  *
280  * Note: Software may opt to XOR the seed material with a seed to implement
281  * a software assisted FIPS mode of operation.
282  */
284  /**
285  * Entropy source XOR'ed with the provided seed material.
286  */
289 
290 /**
291  * Recoverable alerts emitted by the EDN.
292  */
294  /**
295  * Indicates a bad value was written to the EDN_ENABLE field of the control
296  * register.
297  */
299  /**
300  * Indicates a bad value was written to the BOOT_REQ_MODE field of the control
301  * register.
302  */
304  /**
305  * Indicates a bad value was written to the AUTO_REQ_MODE field of the
306  * control register.
307  */
309  /**
310  * Indicates a bad value was written to the CMD_FIFO_RST field of the
311  * control register.
312  */
314  /**
315  * Indicates the genbits bus saw two identical values, indicating a possible
316  * attack.
317  */
320 
321 /**
322  * Configures EDN with runtime information.
323  *
324  * This function should need to be called once for the lifetime of `handle`.
325  *
326  * @param edn An EDN handle.
327  * @return The result of the operation.
328  */
331 
332 /**
333  * Locks out EDN functionality.
334  *
335  * This function is reentrant: calling it while functionality is locked will
336  * have no effect and return `kDifEdnOk`.
337  *
338  * @param edn An EDN handle.
339  * @return The result of the operation.
340  */
343 
344 /**
345  * Checks whether this EDN is locked.
346  *
347  * @param edn An EDN handle.
348  * @param[out] is_locked Out-param for the locked state.
349  * @return The result of the operation.
350  */
352 dif_result_t dif_edn_is_locked(const dif_edn_t *edn, bool *is_locked);
353 
354 /**
355  * Enables the EDN in boot-time mode.
356  *
357  * Each call to this function should be sequenced with a call to
358  * `dif_edn_stop()`.
359  *
360  * @param edn An EDN handle.
361  * @return The result of the operation.
362  */
365 
366 /**
367  * Enables the EDN in auto refresh mode.
368  *
369  * Each call to this function should be sequenced with a call to
370  * `dif_edn_stop()`.
371  *
372  * @param edn An EDN handle.
373  * @param config Auto request configuration parameters.
374  * @return The result of the operation.
375  */
378  dif_edn_auto_params_t config);
379 
380 /**
381  * Queries the EDN status flags.
382  *
383  * @param edn An EDN handle.
384  * @param flag Status flag to query.
385  * @param set Flag state (set/unset).
386  * @return The result of the operation.
387  */
390  bool *set);
391 
392 /**
393  * Queries the EDN error flags.
394  *
395  * @param edn An EDN handle.
396  * @param[out] unhealthy_fifos Bitset of FIFOs in an unhealthy state; indices
397  * are `dif_edn_fifo_t`.
398  * @param[out] errors Bitset of errors relating to the above FIFOs; indices are
399  * `dif_edn_error_t`.
400  * @return The result of the operation.
401  */
403 dif_result_t dif_edn_get_errors(const dif_edn_t *edn, uint32_t *unhealthy_fifos,
404  uint32_t *errors);
405 
406 /**
407  * Forces the status registers to indicate `fifo` as being in an unhealthy
408  * state.
409  *
410  * @param edn An EDN handle
411  * @param fifo The FIFO to mark as unhealthy.
412  * @return The result of the operation.
413  */
416  dif_edn_fifo_t fifo);
417 
418 /**
419  * Forces the status registers to indicate a particular error cause.
420  *
421  * @param edn An EDN handle
422  * @param error The error to force.
423  * @return The result of the operation.
424  */
427  dif_edn_error_t error);
428 
429 /**
430  * Returns an opaque blob indicating the main state machine's current state.
431  *
432  * @param csrng An EDN handle
433  * @param state[out] The state machine state as an opaque blob.
434  * @return The result of the operation.
435  */
438  uint32_t *state);
439 
440 /**
441  * Initializes CSRNG instance with a new seed value.
442  *
443  * `seed_material` is used as specified in NIST SP 800-90Ar1 section
444  * 10.2.1.3.1.
445  *
446  * `seed_material` can be NULL, in which case CSRNG will use a zero
447  * vector instead.
448  *
449  * @param edn An EDN handle.
450  * @param entropy_src_enable Entropy source input enable.
451  * @param seed_material Seed initialization parameters.
452  * @return The result of the operation.
453  */
456  const dif_edn_t *edn, dif_edn_entropy_src_toggle_t entropy_src_enable,
457  const dif_edn_seed_material_t *seed_material);
458 
459 /**
460  * Reseeds CSRNG instance.
461  *
462  * When `seed_material.seed_material_len` is set to 0, only the entropy source
463  * seed is used to reseed the instance, otherwise it will be XOR'ed with the
464  * entropy source.
465  *
466  * @param edn An EDN handle.
467  * @param seed_material Reseed parameters.
468  * @return The result of the operation.
469  */
472  const dif_edn_seed_material_t *seed_material);
473 
474 /**
475  * Updates CSRNG state.
476  *
477  * This function is similar to `dif_edn_reseed()`, except:
478  *
479  * - Only `seed_material.seed_material` is used in the update operation.
480  * - The update operation does not reset the internal CSRNG reseed
481  * counter.
482  *
483  * @param edn An EDN handle.
484  * @param seed_material Update parameters.
485  * @return The result of the operation.
486  */
489  const dif_edn_seed_material_t *seed_material);
490 
491 /**
492  * Requests cryptographic entropy bits from the CSRNG.
493  *
494  * The prediction resistance flag as specified in SP 800-90Ar1 section
495  * 10.2.1.1 is not directly supported by the hardware. It is the
496  * responsibility of the caller to reseed as needed before calling
497  * this function.
498  *
499  * The CSRNG accepts generation requests with 128-bit granularity, with
500  * a minimum 128-bit request size. This function will increase the size
501  * of the request to align it to the nearest 128-bit boundary.
502  *
503  * @param edn An EDN handle.
504  * @param len Number of uint32_t words to generate.
505  * @return The result of the operation. KDifOutOfRange if the `len` parameter
506  * results in a 128bit block level size greater than 0x800.
507  */
509 dif_result_t dif_edn_generate_start(const dif_edn_t *edn, size_t len);
510 
511 /**
512  * Uninstantiates CSRNG.
513  *
514  * Resets the CSRNG instance. Values in the CSRNG are zeroed out. This
515  * command effectively resets the CSRNG, clearing any errors that it
516  * may have encountered due to processing or entropy source errors.
517  *
518  * @param edn An EDN handle.
519  * @return The result of the operation.
520  */
523 
524 /**
525  * Stops the current mode of operation and disables the entropy module.
526  *
527  * @param edn An EDN handle.
528  * @return The result of the operation.
529  */
532 
533 /**
534  * Gets the recoverable alerts currently recorded in the EDN block.
535  *
536  * This function returns the alerts in a bitset whose indices are given by
537  * `dif_edn_recoverable_alert_t`.
538  *
539  * @param edn An EDN handle.
540  * @param[out] alerts Bitset of alerts currently recorded.
541  * @return The result of the operation.
542  */
545  uint32_t *alerts);
546 
547 /**
548  * Clears all recoverable alerts currently recorded in the EDN block.
549  *
550  * @param edn An EDN handle.
551  * @return The result of the operation.
552  */
555 
556 #ifdef __cplusplus
557 } // extern "C"
558 #endif // __cplusplus
559 
560 #endif // OPENTITAN_SW_DEVICE_LIB_DIF_DIF_EDN_H_