Software APIs
dif_hmac.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_HMAC_H_
6
#define OPENTITAN_SW_DEVICE_LIB_DIF_DIF_HMAC_H_
7
8
/**
9
* @file
10
* @brief <a href="/book/hw/ip/hmac/">HMAC</a> Device Interface Functions
11
*/
12
13
#include <stddef.h>
14
#include <stdint.h>
15
16
#include "
sw/device/lib/base/macros.h
"
17
#include "
sw/device/lib/base/mmio.h
"
18
#include "
sw/device/lib/dif/dif_base.h
"
19
20
#include "sw/device/lib/dif/autogen/dif_hmac_autogen.h"
21
22
#ifdef __cplusplus
23
extern
"C"
{
24
#endif
// __cplusplus
25
26
/**
27
* Supported HMAC modes of operation.
28
*/
29
typedef
enum
dif_hmac_mode
{
30
/** The HMAC mode. */
31
kDifHmacModeHmac
= 0,
32
/** The SHA256-only mode. */
33
kDifHmacModeSha256
,
34
}
dif_hmac_mode_t
;
35
36
/**
37
* Supported byte endienness options.
38
*/
39
typedef
enum
dif_hmac_endianness
{
40
/** Big endian byte ordering. */
41
kDifHmacEndiannessBig
= 0,
42
/** Little endian byte ordering. */
43
kDifHmacEndiannessLittle
,
44
}
dif_hmac_endianness_t
;
45
46
/**
47
* HMAC key length in bits.
48
*/
49
typedef
enum
dif_hmac_key_length
{
50
kDifHMACKey128 = 1,
51
kDifHMACKey256 = (1 << 1),
52
kDifHMACKey384 = (1 << 2),
53
kDifHMACKey512 = (1 << 3),
54
kDifHMACKey1024 = (1 << 4),
55
}
dif_hmac_key_length_t
;
56
57
/**
58
* SHA-2 digest size
59
*/
60
typedef
enum
dif_sha2_digest_size
{
61
kDifSHA256 = (1 << 1),
62
kDifSHA384 = (1 << 2),
63
kDifSHA512 = (1 << 3),
64
}
dif_sha2_digest_size_t
;
65
66
/**
67
* Configuration for a single HMAC Transaction
68
*/
69
typedef
struct
dif_hmac_transaction
{
70
/** Byte endianness for writes to the FIFO. */
71
dif_hmac_endianness_t
message_endianness
;
72
/** Byte endianness for reads from the digest. */
73
dif_hmac_endianness_t
digest_endianness
;
74
/** SHA-2 digest size. */
75
dif_sha2_digest_size_t
digest_size
;
76
/** HMAC key length. */
77
dif_hmac_key_length_t
key_length
;
78
/** Use the sideload key from the key manager. */
79
bool
sideload
;
80
}
dif_hmac_transaction_t
;
81
82
/**
83
* A typed representation of the HMAC digest.
84
*/
85
typedef
struct
dif_hmac_digest
{
86
uint32_t digest[8];
87
}
dif_hmac_digest_t
;
88
89
/**
90
* Resets the HMAC engine and readies it to receive a new message to process an
91
* HMAC digest.
92
*
93
* This function causes the HMAC engine to start its operation. After a
94
* successful call to this function, |dif_hmac_fifo_push()| can be called to
95
* write the message for HMAC processing.
96
*
97
* This function should be called with a valid `key` that references a 32-byte,
98
* contiguous, readable region where the key may be copied from. Passing a
99
* `NULL` `key` reference will skip loading of the key. This is only expected to
100
* be used to test scenarios where the key is not loaded.
101
*
102
* @param hmac The HMAC device to start HMAC operation for.
103
* @param key The 256-bit HMAC key. Ignored if `config.sideload` is set.
104
* @param config The per-transaction configuration.
105
* @return The result of the operation.
106
*/
107
OT_WARN_UNUSED_RESULT
108
dif_result_t
dif_hmac_mode_hmac_start
(
const
dif_hmac_t
*hmac,
109
const
uint8_t *key,
110
const
dif_hmac_transaction_t
config);
111
112
/**
113
* Resets the HMAC engine and readies it to receive a new message to process a
114
* SHA256 digest.
115
*
116
* This function causes the HMAC engine to start its operation. After a
117
* successful call to this function, |dif_hmac_fifo_push()| can be called to
118
* write the message for SHA256 processing.
119
*
120
* @param hmac The HMAC device to start SHA256 operation for.
121
* @param config The per-transaction configuration.
122
* @return The result of the operation.
123
*/
124
OT_WARN_UNUSED_RESULT
125
dif_result_t
dif_hmac_mode_sha256_start
(
const
dif_hmac_t
*hmac,
126
const
dif_hmac_transaction_t
config);
127
128
/**
129
* Attempts to send `len` bytes from the buffer pointed to by `data` to the
130
* device described by `hmac`. This function will send to the message FIFO until
131
* the FIFO fills up or `len` bytes have been sent.
132
*
133
* In the event that the FIFO fills up before `len` bytes have been sent this
134
* function will return a `kDifHmacFifoFull` error. In this case it is valid
135
* to call this function again by advancing `data` by `len` - |*bytes_sent|
136
* bytes. It may be desirable to wait for space to free up on the FIFO before
137
* issuing subsequent calls to this function, but it is not strictly
138
* necessary. The number of entries in the FIFO can be queried with
139
* `dif_hmac_fifo_count_entries()`.
140
*
141
* `data` *must* point to an allocated buffer of at least length `len`.
142
*
143
* @param hmac The HMAC device to send to.
144
* @param data A contiguous buffer to copy from.
145
* @param len The length of the buffer to copy from.
146
* @param[out] bytes_sent The number of bytes sent to the FIFO (optional).
147
* @return The result of the operation.
148
*/
149
OT_WARN_UNUSED_RESULT
150
dif_result_t
dif_hmac_fifo_push
(
const
dif_hmac_t
*hmac,
const
void
*data,
151
size_t
len,
size_t
*bytes_sent);
152
153
/**
154
* Retrieves the number of entries in the HMAC FIFO. These entries may be
155
* semi-arbitrary in length; this function should not be used to calculate
156
* message length.
157
*
158
* @param hmac The HMAC device to get the FIFO depth for.
159
* @param[out] num_entries The number of entries in the FIFO.
160
* @return The result of the operation.
161
*/
162
OT_WARN_UNUSED_RESULT
163
dif_result_t
dif_hmac_fifo_count_entries
(
const
dif_hmac_t
*hmac,
164
uint32_t *num_entries);
165
166
/**
167
* Retrieves the number of bits in the loaded HMAC device.
168
* `dif_hmac_fifo_count_entries()` should be called before this function to
169
* ensure the FIFO is empty, as any bits in the FIFO are not counted in
170
* `msg_len`.
171
*
172
* @param hmac The HMAC device to get the message length for.
173
* @param[out] msg_len The number of bits in the HMAC message.
174
* @return The result of the operation.
175
*/
176
OT_WARN_UNUSED_RESULT
177
dif_result_t
dif_hmac_get_message_length
(
const
dif_hmac_t
*hmac,
178
uint64_t *msg_len);
179
180
/**
181
* Attempts to run HMAC or SHA256 depending on the mode `hmac` was initialized
182
* in. Calls to this function always succeed and return without blocking. The
183
* caller can use `dif_hmac_check_state()` to check for errors and for the
184
* `DIF_HMAC_DONE` status before reading the digest with
185
* `dif_hmac_digest_read()`.
186
*
187
* @param hmac The HMAC device to initiate the run on.
188
* @return The result of the operation.
189
*/
190
OT_WARN_UNUSED_RESULT
191
dif_result_t
dif_hmac_process
(
const
dif_hmac_t
*hmac);
192
193
/**
194
* Attempts to finish a transaction started with `dif_hmac_mode_*_start`, and
195
* reads the final digest in the buffer referenced by `digest`.
196
*
197
* This queries the `INTR_STATE` register to check if the HMAC is finished, and
198
* will acknowledge a `hmac_done` interrupt. If that register is not pending,
199
* then this function assumes HMAC is still processing and will return
200
* `kDifHmacErrorDigestProcessing`.
201
*
202
* `digest` must reference an allocated, contiguous, 32-byte buffer. This buffer
203
* shall also be 4-byte aligned. This is all consistent with the platform
204
* requirements for size and alignment requirements of `dif_hmac_digest_t`.
205
*
206
* @param hmac The HMAC device to read the digest from.
207
* @param disable_after_done If true, the HMAC and SHA256 datapaths will be
208
* disabled after the digest is read, clearing the digest registers.
209
* @param[out] digest A contiguous 32-byte, 4-byte aligned buffer for the
210
* digest.
211
* @return The result of the operation.
212
*/
213
OT_WARN_UNUSED_RESULT
214
dif_result_t
dif_hmac_finish
(
const
dif_hmac_t
*hmac,
bool
disable_after_done,
215
dif_hmac_digest_t
*digest);
216
217
/**
218
* Randomizes internal secret registers on the HMAC device. This includes the
219
* key, hash value, and internal state machine. The value of `entropy` will be
220
* used to "randomize" the internal state of the HMAC device. See the HMAC IP
221
* documentation for more information: hw/ip/hmac/doc.
222
*
223
* @param hmac The HMAC device to clobber state on.
224
* @param entropy A source of randomness to write to the HMAC internal state.
225
* @param[out] digest The resulting digest from the wipe operation.
226
* @return The result of the operation.
227
*/
228
OT_WARN_UNUSED_RESULT
229
dif_result_t
dif_hmac_wipe_secret
(
const
dif_hmac_t
*hmac, uint32_t entropy,
230
dif_hmac_digest_t
*digest);
231
232
#ifdef __cplusplus
233
}
// extern "C"
234
#endif
// __cplusplus
235
236
#endif
// OPENTITAN_SW_DEVICE_LIB_DIF_DIF_HMAC_H_
sw
device
lib
dif
dif_hmac.h
Return to
OpenTitan Documentation