• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  *  Copyright (c) 2021, The OpenThread Authors.
3  *  All rights reserved.
4  *
5  *  Redistribution and use in source and binary forms, with or without
6  *  modification, are permitted provided that the following conditions are met:
7  *  1. Redistributions of source code must retain the above copyright
8  *     notice, this list of conditions and the following disclaimer.
9  *  2. Redistributions in binary form must reproduce the above copyright
10  *     notice, this list of conditions and the following disclaimer in the
11  *     documentation and/or other materials provided with the distribution.
12  *  3. Neither the name of the copyright holder nor the
13  *     names of its contributors may be used to endorse or promote products
14  *     derived from this software without specific prior written permission.
15  *
16  *  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
17  *  AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
18  *  IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
19  *  ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
20  *  LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
21  *  CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
22  *  SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
23  *  INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
24  *  CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
25  *  ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
26  *  POSSIBILITY OF SUCH DAMAGE.
27  */
28 
29 /**
30  * @file
31  * @brief
32  *   This file includes the platform abstraction for Crypto operations.
33  */
34 
35 #ifndef OPENTHREAD_PLATFORM_CRYPTO_H_
36 #define OPENTHREAD_PLATFORM_CRYPTO_H_
37 
38 #include <stdint.h>
39 #include <stdlib.h>
40 
41 #include <openthread/error.h>
42 
43 #ifdef __cplusplus
44 extern "C" {
45 #endif
46 
47 /**
48  * @addtogroup plat-crypto
49  *
50  * @brief
51  *   This module includes the platform abstraction for Crypto.
52  *
53  * @{
54  */
55 
56 /**
57  * Defines the key types.
58  */
59 typedef enum
60 {
61     OT_CRYPTO_KEY_TYPE_RAW,   ///< Key Type: Raw Data.
62     OT_CRYPTO_KEY_TYPE_AES,   ///< Key Type: AES.
63     OT_CRYPTO_KEY_TYPE_HMAC,  ///< Key Type: HMAC.
64     OT_CRYPTO_KEY_TYPE_ECDSA, ///< Key Type: ECDSA.
65 } otCryptoKeyType;
66 
67 /**
68  * Defines the key algorithms.
69  */
70 typedef enum
71 {
72     OT_CRYPTO_KEY_ALG_VENDOR,       ///< Key Algorithm: Vendor Defined.
73     OT_CRYPTO_KEY_ALG_AES_ECB,      ///< Key Algorithm: AES ECB.
74     OT_CRYPTO_KEY_ALG_HMAC_SHA_256, ///< Key Algorithm: HMAC SHA-256.
75     OT_CRYPTO_KEY_ALG_ECDSA,        ///< Key Algorithm: ECDSA.
76 } otCryptoKeyAlgorithm;
77 
78 /**
79  * Defines the key usage flags.
80  */
81 enum
82 {
83     OT_CRYPTO_KEY_USAGE_NONE        = 0,      ///< Key Usage: Key Usage is empty.
84     OT_CRYPTO_KEY_USAGE_EXPORT      = 1 << 0, ///< Key Usage: Key can be exported.
85     OT_CRYPTO_KEY_USAGE_ENCRYPT     = 1 << 1, ///< Key Usage: Encryption (vendor defined).
86     OT_CRYPTO_KEY_USAGE_DECRYPT     = 1 << 2, ///< Key Usage: AES ECB.
87     OT_CRYPTO_KEY_USAGE_SIGN_HASH   = 1 << 3, ///< Key Usage: Sign Hash.
88     OT_CRYPTO_KEY_USAGE_VERIFY_HASH = 1 << 4, ///< Key Usage: Verify Hash.
89 };
90 
91 /**
92  * Defines the key storage types.
93  */
94 typedef enum
95 {
96     OT_CRYPTO_KEY_STORAGE_VOLATILE,   ///< Key Persistence: Key is volatile.
97     OT_CRYPTO_KEY_STORAGE_PERSISTENT, ///< Key Persistence: Key is persistent.
98 } otCryptoKeyStorage;
99 
100 /**
101  * This datatype represents the key reference.
102  */
103 typedef uint32_t otCryptoKeyRef;
104 
105 /**
106  * @struct otCryptoKey
107  *
108  * Represents the Key Material required for Crypto operations.
109  */
110 typedef struct otCryptoKey
111 {
112     const uint8_t *mKey;       ///< Pointer to the buffer containing key. NULL indicates to use `mKeyRef`.
113     uint16_t       mKeyLength; ///< The key length in bytes (applicable when `mKey` is not NULL).
114     uint32_t       mKeyRef;    ///< The PSA key ref (requires `mKey` to be NULL).
115 } otCryptoKey;
116 
117 /**
118  * @struct otCryptoContext
119  *
120  * Stores the context object for platform APIs.
121  */
122 typedef struct otCryptoContext
123 {
124     void    *mContext;     ///< Pointer to the context.
125     uint16_t mContextSize; ///< The length of the context in bytes.
126 } otCryptoContext;
127 
128 /**
129  * Length of SHA256 hash (in bytes).
130  */
131 #define OT_CRYPTO_SHA256_HASH_SIZE 32
132 
133 /**
134  * @struct otPlatCryptoSha256Hash
135  *
136  * Represents a SHA-256 hash.
137  */
138 OT_TOOL_PACKED_BEGIN
139 struct otPlatCryptoSha256Hash
140 {
141     uint8_t m8[OT_CRYPTO_SHA256_HASH_SIZE]; ///< Hash bytes.
142 } OT_TOOL_PACKED_END;
143 
144 /**
145  * Represents a SHA-256 hash.
146  */
147 typedef struct otPlatCryptoSha256Hash otPlatCryptoSha256Hash;
148 
149 /**
150  * Max buffer size (in bytes) for representing the EDCSA key-pair in DER format.
151  */
152 #define OT_CRYPTO_ECDSA_MAX_DER_SIZE 125
153 
154 /**
155  * @struct otPlatCryptoEcdsaKeyPair
156  *
157  * Represents an ECDSA key pair (public and private keys).
158  *
159  * The key pair is stored using Distinguished Encoding Rules (DER) format (per RFC 5915).
160  */
161 typedef struct otPlatCryptoEcdsaKeyPair
162 {
163     uint8_t mDerBytes[OT_CRYPTO_ECDSA_MAX_DER_SIZE];
164     uint8_t mDerLength;
165 } otPlatCryptoEcdsaKeyPair;
166 
167 /**
168  * Buffer size (in bytes) for representing the EDCSA public key.
169  */
170 #define OT_CRYPTO_ECDSA_PUBLIC_KEY_SIZE 64
171 
172 /**
173  * @struct otPlatCryptoEcdsaPublicKey
174  *
175  * Represents a ECDSA public key.
176  *
177  * The public key is stored as a byte sequence representation of an uncompressed curve point (RFC 6605 - sec 4).
178  */
179 OT_TOOL_PACKED_BEGIN
180 struct otPlatCryptoEcdsaPublicKey
181 {
182     uint8_t m8[OT_CRYPTO_ECDSA_PUBLIC_KEY_SIZE];
183 } OT_TOOL_PACKED_END;
184 
185 typedef struct otPlatCryptoEcdsaPublicKey otPlatCryptoEcdsaPublicKey;
186 
187 /**
188  * Buffer size (in bytes) for representing the EDCSA signature.
189  */
190 #define OT_CRYPTO_ECDSA_SIGNATURE_SIZE 64
191 
192 /**
193  * @struct otPlatCryptoEcdsaSignature
194  *
195  * Represents an ECDSA signature.
196  *
197  * The signature is encoded as the concatenated binary representation of two MPIs `r` and `s` which are calculated
198  * during signing (RFC 6605 - section 4).
199  */
200 OT_TOOL_PACKED_BEGIN
201 struct otPlatCryptoEcdsaSignature
202 {
203     uint8_t m8[OT_CRYPTO_ECDSA_SIGNATURE_SIZE];
204 } OT_TOOL_PACKED_END;
205 
206 typedef struct otPlatCryptoEcdsaSignature otPlatCryptoEcdsaSignature;
207 
208 /**
209  * Max PBKDF2 SALT length: salt prefix (6) + extended panid (8) + network name (16)
210  */
211 #define OT_CRYPTO_PBDKF2_MAX_SALT_SIZE 30
212 
213 /**
214  * Initialize the Crypto module.
215  */
216 void otPlatCryptoInit(void);
217 
218 /**
219  * Import a key into PSA ITS.
220  *
221  * @param[in,out] aKeyRef           Pointer to the key ref to be used for crypto operations.
222  * @param[in]     aKeyType          Key Type encoding for the key.
223  * @param[in]     aKeyAlgorithm     Key algorithm encoding for the key.
224  * @param[in]     aKeyUsage         Key Usage encoding for the key (combinations of `OT_CRYPTO_KEY_USAGE_*`).
225  * @param[in]     aKeyPersistence   Key Persistence for this key
226  * @param[in]     aKey              Actual key to be imported.
227  * @param[in]     aKeyLen           Length of the key to be imported.
228  *
229  * @retval OT_ERROR_NONE          Successfully imported the key.
230  * @retval OT_ERROR_FAILED        Failed to import the key.
231  * @retval OT_ERROR_INVALID_ARGS  @p aKey was set to NULL.
232  *
233  * @note If OT_CRYPTO_KEY_STORAGE_PERSISTENT is passed for aKeyPersistence then @p aKeyRef is input and platform
234  *       should use the given aKeyRef and MUST not change it.
235  *
236  *       If OT_CRYPTO_KEY_STORAGE_VOLATILE is passed for aKeyPersistence then @p aKeyRef is output, the initial
237  *       value does not matter and platform API MUST update it to return the new key ref.
238  *
239  *       This API is only used by OT core when `OPENTHREAD_CONFIG_PLATFORM_KEY_REFERENCES_ENABLE` is enabled.
240  */
241 otError otPlatCryptoImportKey(otCryptoKeyRef      *aKeyRef,
242                               otCryptoKeyType      aKeyType,
243                               otCryptoKeyAlgorithm aKeyAlgorithm,
244                               int                  aKeyUsage,
245                               otCryptoKeyStorage   aKeyPersistence,
246                               const uint8_t       *aKey,
247                               size_t               aKeyLen);
248 
249 /**
250  * Export a key stored in PSA ITS.
251  *
252  * @param[in]   aKeyRef           The key ref to be used for crypto operations.
253  * @param[out]  aBuffer           Pointer to the buffer where key needs to be exported.
254  * @param[in]   aBufferLen        Length of the buffer passed to store the exported key.
255  * @param[out]  aKeyLen           Pointer to return the length of the exported key.
256  *
257  * @retval OT_ERROR_NONE          Successfully exported  @p aKeyRef.
258  * @retval OT_ERROR_FAILED        Failed to export @p aKeyRef.
259  * @retval OT_ERROR_INVALID_ARGS  @p aBuffer was NULL
260  *
261  * @note This API is only used by OT core when `OPENTHREAD_CONFIG_PLATFORM_KEY_REFERENCES_ENABLE` is enabled.
262  */
263 otError otPlatCryptoExportKey(otCryptoKeyRef aKeyRef, uint8_t *aBuffer, size_t aBufferLen, size_t *aKeyLen);
264 
265 /**
266  * Destroy a key stored in PSA ITS.
267  *
268  * @param[in]   aKeyRef          The key ref to be destroyed
269  *
270  * @retval OT_ERROR_NONE          Successfully destroyed the key.
271  * @retval OT_ERROR_FAILED        Failed to destroy the key.
272  *
273  * @note This API is only used by OT core when `OPENTHREAD_CONFIG_PLATFORM_KEY_REFERENCES_ENABLE` is enabled.
274  */
275 otError otPlatCryptoDestroyKey(otCryptoKeyRef aKeyRef);
276 
277 /**
278  * Check if the key ref passed has an associated key in PSA ITS.
279  *
280  * @param[in]  aKeyRef          The Key Ref to check.
281  *
282  * @retval TRUE                 There is an associated key with @p aKeyRef.
283  * @retval FALSE                There is no associated key with @p aKeyRef.
284  *
285  * @note This API is only used by OT core when `OPENTHREAD_CONFIG_PLATFORM_KEY_REFERENCES_ENABLE` is enabled.
286  */
287 bool otPlatCryptoHasKey(otCryptoKeyRef aKeyRef);
288 
289 /**
290  * Initialize the HMAC operation.
291  *
292  * @param[in]  aContext          Context for HMAC operation.
293  *
294  * @retval OT_ERROR_NONE          Successfully initialized HMAC operation.
295  * @retval OT_ERROR_FAILED        Failed to initialize HMAC operation.
296  * @retval OT_ERROR_INVALID_ARGS  @p aContext was NULL
297  *
298  * @note The platform driver shall point the context to the correct object such as psa_mac_operation_t or
299  *       mbedtls_md_context_t.
300  */
301 otError otPlatCryptoHmacSha256Init(otCryptoContext *aContext);
302 
303 /**
304  * Uninitialize the HMAC operation.
305  *
306  * @param[in]  aContext          Context for HMAC operation.
307  *
308  * @retval OT_ERROR_NONE          Successfully uninitialized HMAC operation.
309  * @retval OT_ERROR_FAILED        Failed to uninitialized HMAC operation.
310  * @retval OT_ERROR_INVALID_ARGS  @p aContext was NULL
311  */
312 otError otPlatCryptoHmacSha256Deinit(otCryptoContext *aContext);
313 
314 /**
315  * Start HMAC operation.
316  *
317  * @param[in]  aContext           Context for HMAC operation.
318  * @param[in]  aKey               Key material to be used for HMAC operation.
319  *
320  * @retval OT_ERROR_NONE          Successfully started HMAC operation.
321  * @retval OT_ERROR_FAILED        Failed to start HMAC operation.
322  * @retval OT_ERROR_INVALID_ARGS  @p aContext or @p aKey was NULL
323  */
324 otError otPlatCryptoHmacSha256Start(otCryptoContext *aContext, const otCryptoKey *aKey);
325 
326 /**
327  * Update the HMAC operation with new input.
328  *
329  * @param[in]  aContext           Context for HMAC operation.
330  * @param[in]  aBuf               A pointer to the input buffer.
331  * @param[in]  aBufLength         The length of @p aBuf in bytes.
332  *
333  * @retval OT_ERROR_NONE          Successfully updated HMAC with new input operation.
334  * @retval OT_ERROR_FAILED        Failed to update HMAC operation.
335  * @retval OT_ERROR_INVALID_ARGS  @p aContext or @p aBuf was NULL
336  */
337 otError otPlatCryptoHmacSha256Update(otCryptoContext *aContext, const void *aBuf, uint16_t aBufLength);
338 
339 /**
340  * Complete the HMAC operation.
341  *
342  * @param[in]  aContext           Context for HMAC operation.
343  * @param[out] aBuf               A pointer to the output buffer.
344  * @param[in]  aBufLength         The length of @p aBuf in bytes.
345  *
346  * @retval OT_ERROR_NONE          Successfully completed HMAC operation.
347  * @retval OT_ERROR_FAILED        Failed to complete HMAC operation.
348  * @retval OT_ERROR_INVALID_ARGS  @p aContext or @p aBuf was NULL
349  */
350 otError otPlatCryptoHmacSha256Finish(otCryptoContext *aContext, uint8_t *aBuf, size_t aBufLength);
351 
352 /**
353  * Initialise the AES operation.
354  *
355  * @param[in]  aContext           Context for AES operation.
356  *
357  * @retval OT_ERROR_NONE          Successfully Initialised AES operation.
358  * @retval OT_ERROR_FAILED        Failed to Initialise AES operation.
359  * @retval OT_ERROR_INVALID_ARGS  @p aContext was NULL
360  * @retval OT_ERROR_NO_BUFS       Cannot allocate the context.
361  *
362  * @note The platform driver shall point the context to the correct object such as psa_key_id
363  *       or mbedtls_aes_context_t.
364  */
365 otError otPlatCryptoAesInit(otCryptoContext *aContext);
366 
367 /**
368  * Set the key for AES operation.
369  *
370  * @param[in]  aContext           Context for AES operation.
371  * @param[out] aKey               Key to use for AES operation.
372  *
373  * @retval OT_ERROR_NONE          Successfully set the key for AES operation.
374  * @retval OT_ERROR_FAILED        Failed to set the key for AES operation.
375  * @retval OT_ERROR_INVALID_ARGS  @p aContext or @p aKey was NULL
376  */
377 otError otPlatCryptoAesSetKey(otCryptoContext *aContext, const otCryptoKey *aKey);
378 
379 /**
380  * Encrypt the given data.
381  *
382  * @param[in]  aContext           Context for AES operation.
383  * @param[in]  aInput             Pointer to the input buffer.
384  * @param[in]  aOutput            Pointer to the output buffer.
385  *
386  * @retval OT_ERROR_NONE          Successfully encrypted @p aInput.
387  * @retval OT_ERROR_FAILED        Failed to encrypt @p aInput.
388  * @retval OT_ERROR_INVALID_ARGS  @p aContext or @p aKey or @p aOutput were NULL
389  */
390 otError otPlatCryptoAesEncrypt(otCryptoContext *aContext, const uint8_t *aInput, uint8_t *aOutput);
391 
392 /**
393  * Free the AES context.
394  *
395  * @param[in]  aContext           Context for AES operation.
396  *
397  * @retval OT_ERROR_NONE          Successfully freed AES context.
398  * @retval OT_ERROR_FAILED        Failed to free AES context.
399  * @retval OT_ERROR_INVALID_ARGS  @p aContext was NULL
400  */
401 otError otPlatCryptoAesFree(otCryptoContext *aContext);
402 
403 /**
404  * Initialise the HKDF context.
405  *
406  * @param[in]  aContext           Context for HKDF operation.
407  *
408  * @retval OT_ERROR_NONE          Successfully Initialised AES operation.
409  * @retval OT_ERROR_FAILED        Failed to Initialise AES operation.
410  * @retval OT_ERROR_INVALID_ARGS  @p aContext was NULL
411  *
412  * @note The platform driver shall point the context to the correct object such as psa_key_derivation_operation_t
413  *       or HmacSha256::Hash
414  */
415 otError otPlatCryptoHkdfInit(otCryptoContext *aContext);
416 
417 /**
418  * Perform HKDF Expand step.
419  *
420  * @param[in]  aContext           Operation context for HKDF operation.
421  * @param[in]  aInfo              Pointer to the Info sequence.
422  * @param[in]  aInfoLength        Length of the Info sequence.
423  * @param[out] aOutputKey         Pointer to the output Key.
424  * @param[in]  aOutputKeyLength   Size of the output key buffer.
425  *
426  * @retval OT_ERROR_NONE          HKDF Expand was successful.
427  * @retval OT_ERROR_FAILED        HKDF Expand failed.
428  * @retval OT_ERROR_INVALID_ARGS  @p aContext was NULL
429  */
430 otError otPlatCryptoHkdfExpand(otCryptoContext *aContext,
431                                const uint8_t   *aInfo,
432                                uint16_t         aInfoLength,
433                                uint8_t         *aOutputKey,
434                                uint16_t         aOutputKeyLength);
435 
436 /**
437  * Perform HKDF Extract step.
438  *
439  * @param[in]  aContext           Operation context for HKDF operation.
440  * @param[in]  aSalt              Pointer to the Salt for HKDF.
441  * @param[in]  aSaltLength        Length of Salt.
442  * @param[in]  aInputKey          Pointer to the input key.
443  *
444  * @retval OT_ERROR_NONE          HKDF Extract was successful.
445  * @retval OT_ERROR_FAILED        HKDF Extract failed.
446  */
447 otError otPlatCryptoHkdfExtract(otCryptoContext   *aContext,
448                                 const uint8_t     *aSalt,
449                                 uint16_t           aSaltLength,
450                                 const otCryptoKey *aInputKey);
451 
452 /**
453  * Uninitialize the HKDF context.
454  *
455  * @param[in]  aContext           Context for HKDF operation.
456  *
457  * @retval OT_ERROR_NONE          Successfully un-initialised HKDF operation.
458  * @retval OT_ERROR_FAILED        Failed to un-initialised HKDF operation.
459  * @retval OT_ERROR_INVALID_ARGS  @p aContext was NULL
460  */
461 otError otPlatCryptoHkdfDeinit(otCryptoContext *aContext);
462 
463 /**
464  * Initialise the SHA-256 operation.
465  *
466  * @param[in]  aContext           Context for SHA-256 operation.
467  *
468  * @retval OT_ERROR_NONE          Successfully initialised SHA-256 operation.
469  * @retval OT_ERROR_FAILED        Failed to initialise SHA-256 operation.
470  * @retval OT_ERROR_INVALID_ARGS  @p aContext was NULL
471  *
472  *
473  * @note The platform driver shall point the context to the correct object such as psa_hash_operation_t
474  *       or mbedtls_sha256_context.
475  */
476 otError otPlatCryptoSha256Init(otCryptoContext *aContext);
477 
478 /**
479  * Uninitialize the SHA-256 operation.
480  *
481  * @param[in]  aContext           Context for SHA-256 operation.
482  *
483  * @retval OT_ERROR_NONE          Successfully un-initialised SHA-256 operation.
484  * @retval OT_ERROR_FAILED        Failed to un-initialised SHA-256 operation.
485  * @retval OT_ERROR_INVALID_ARGS  @p aContext was NULL
486  */
487 otError otPlatCryptoSha256Deinit(otCryptoContext *aContext);
488 
489 /**
490  * Start SHA-256 operation.
491  *
492  * @param[in]  aContext           Context for SHA-256 operation.
493  *
494  * @retval OT_ERROR_NONE          Successfully started SHA-256 operation.
495  * @retval OT_ERROR_FAILED        Failed to start SHA-256 operation.
496  * @retval OT_ERROR_INVALID_ARGS  @p aContext was NULL
497  */
498 otError otPlatCryptoSha256Start(otCryptoContext *aContext);
499 
500 /**
501  * Update SHA-256 operation with new input.
502  *
503  * @param[in]  aContext           Context for SHA-256 operation.
504  * @param[in]  aBuf               A pointer to the input buffer.
505  * @param[in]  aBufLength         The length of @p aBuf in bytes.
506  *
507  * @retval OT_ERROR_NONE          Successfully updated SHA-256 with new input operation.
508  * @retval OT_ERROR_FAILED        Failed to update SHA-256 operation.
509  * @retval OT_ERROR_INVALID_ARGS  @p aContext or @p aBuf was NULL
510  */
511 otError otPlatCryptoSha256Update(otCryptoContext *aContext, const void *aBuf, uint16_t aBufLength);
512 
513 /**
514  * Finish SHA-256 operation.
515  *
516  * @param[in]  aContext           Context for SHA-256 operation.
517  * @param[in]  aHash              A pointer to the output buffer, where hash needs to be stored.
518  * @param[in]  aHashSize          The length of @p aHash in bytes.
519  *
520  * @retval OT_ERROR_NONE          Successfully completed the SHA-256 operation.
521  * @retval OT_ERROR_FAILED        Failed to complete SHA-256 operation.
522  * @retval OT_ERROR_INVALID_ARGS  @p aContext or @p aHash was NULL
523  */
524 otError otPlatCryptoSha256Finish(otCryptoContext *aContext, uint8_t *aHash, uint16_t aHashSize);
525 
526 /**
527  * Initialize cryptographically-secure pseudorandom number generator (CSPRNG).
528  */
529 void otPlatCryptoRandomInit(void);
530 
531 /**
532  * Deinitialize cryptographically-secure pseudorandom number generator (CSPRNG).
533  */
534 void otPlatCryptoRandomDeinit(void);
535 
536 /**
537  * Fills a given buffer with cryptographically secure random bytes.
538  *
539  * @param[out] aBuffer            A pointer to a buffer to fill with the random bytes.
540  * @param[in]  aSize              Size of buffer (number of bytes to fill).
541  *
542  * @retval OT_ERROR_NONE          Successfully filled buffer with random values.
543  * @retval OT_ERROR_FAILED        Operation failed.
544  */
545 otError otPlatCryptoRandomGet(uint8_t *aBuffer, uint16_t aSize);
546 
547 /**
548  * Generate and populate the output buffer with a new ECDSA key-pair.
549  *
550  * @param[out] aKeyPair           A pointer to an ECDSA key-pair structure to store the generated key-pair.
551  *
552  * @retval OT_ERROR_NONE          A new key-pair was generated successfully.
553  * @retval OT_ERROR_NO_BUFS       Failed to allocate buffer for key generation.
554  * @retval OT_ERROR_NOT_CAPABLE   Feature not supported.
555  * @retval OT_ERROR_FAILED        Failed to generate key-pair.
556  */
557 otError otPlatCryptoEcdsaGenerateKey(otPlatCryptoEcdsaKeyPair *aKeyPair);
558 
559 /**
560  * Get the associated public key from the input context.
561  *
562  * @param[in]  aKeyPair           A pointer to an ECDSA key-pair structure where the key-pair is stored.
563  * @param[out] aPublicKey         A pointer to an ECDSA public key structure to store the public key.
564  *
565  * @retval OT_ERROR_NONE          Public key was retrieved successfully, and @p aBuffer is updated.
566  * @retval OT_ERROR_PARSE         The key-pair DER format could not be parsed (invalid format).
567  * @retval OT_ERROR_INVALID_ARGS  The @p aContext is NULL.
568  */
569 otError otPlatCryptoEcdsaGetPublicKey(const otPlatCryptoEcdsaKeyPair *aKeyPair, otPlatCryptoEcdsaPublicKey *aPublicKey);
570 
571 /**
572  * Calculate the ECDSA signature for a hashed message using the private key from the input context.
573  *
574  * Uses the deterministic digital signature generation procedure from RFC 6979.
575  *
576  * @param[in]  aKeyPair           A pointer to an ECDSA key-pair structure where the key-pair is stored.
577  * @param[in]  aHash              A pointer to a SHA-256 hash structure where the hash value for signature calculation
578  *                                is stored.
579  * @param[out] aSignature         A pointer to an ECDSA signature structure to output the calculated signature.
580  *
581  * @retval OT_ERROR_NONE          The signature was calculated successfully, @p aSignature was updated.
582  * @retval OT_ERROR_PARSE         The key-pair DER format could not be parsed (invalid format).
583  * @retval OT_ERROR_NO_BUFS       Failed to allocate buffer for signature calculation.
584  * @retval OT_ERROR_INVALID_ARGS  The @p aContext is NULL.
585  */
586 otError otPlatCryptoEcdsaSign(const otPlatCryptoEcdsaKeyPair *aKeyPair,
587                               const otPlatCryptoSha256Hash   *aHash,
588                               otPlatCryptoEcdsaSignature     *aSignature);
589 
590 /**
591  * Use the key from the input context to verify the ECDSA signature of a hashed message.
592  *
593  * @param[in]  aPublicKey         A pointer to an ECDSA public key structure where the public key for signature
594  *                                verification is stored.
595  * @param[in]  aHash              A pointer to a SHA-256 hash structure where the hash value for signature verification
596  *                                is stored.
597  * @param[in]  aSignature         A pointer to an ECDSA signature structure where the signature value to be verified is
598  *                                stored.
599  *
600  * @retval OT_ERROR_NONE          The signature was verified successfully.
601  * @retval OT_ERROR_SECURITY      The signature is invalid.
602  * @retval OT_ERROR_INVALID_ARGS  The key or hash is invalid.
603  * @retval OT_ERROR_NO_BUFS       Failed to allocate buffer for signature verification.
604  */
605 otError otPlatCryptoEcdsaVerify(const otPlatCryptoEcdsaPublicKey *aPublicKey,
606                                 const otPlatCryptoSha256Hash     *aHash,
607                                 const otPlatCryptoEcdsaSignature *aSignature);
608 
609 /**
610  * Calculate the ECDSA signature for a hashed message using the Key reference passed.
611  *
612  * Uses the deterministic digital signature generation procedure from RFC 6979.
613  *
614  * @param[in]  aKeyRef            Key Reference to the slot where the key-pair is stored.
615  * @param[in]  aHash              A pointer to a SHA-256 hash structure where the hash value for signature calculation
616  *                                is stored.
617  * @param[out] aSignature         A pointer to an ECDSA signature structure to output the calculated signature.
618  *
619  * @retval OT_ERROR_NONE          The signature was calculated successfully, @p aSignature was updated.
620  * @retval OT_ERROR_PARSE         The key-pair DER format could not be parsed (invalid format).
621  * @retval OT_ERROR_NO_BUFS       Failed to allocate buffer for signature calculation.
622  * @retval OT_ERROR_INVALID_ARGS  The @p aContext is NULL.
623  *
624  * @note This API is only used by OT core when `OPENTHREAD_CONFIG_PLATFORM_KEY_REFERENCES_ENABLE` is enabled.
625  */
626 otError otPlatCryptoEcdsaSignUsingKeyRef(otCryptoKeyRef                aKeyRef,
627                                          const otPlatCryptoSha256Hash *aHash,
628                                          otPlatCryptoEcdsaSignature   *aSignature);
629 
630 /**
631  * Get the associated public key from the key reference passed.
632  *
633  * The public key is stored differently depending on the crypto backend library being used
634  * (OPENTHREAD_CONFIG_CRYPTO_LIB).
635  *
636  * This API must make sure to return the public key as a byte sequence representation of an
637  * uncompressed curve point (RFC 6605 - sec 4)
638  *
639  * @param[in]  aKeyRef            Key Reference to the slot where the key-pair is stored.
640  * @param[out] aPublicKey         A pointer to an ECDSA public key structure to store the public key.
641  *
642  * @retval OT_ERROR_NONE          Public key was retrieved successfully, and @p aBuffer is updated.
643  * @retval OT_ERROR_PARSE         The key-pair DER format could not be parsed (invalid format).
644  * @retval OT_ERROR_INVALID_ARGS  The @p aContext is NULL.
645  *
646  * @note This API is only used by OT core when `OPENTHREAD_CONFIG_PLATFORM_KEY_REFERENCES_ENABLE` is enabled.
647  */
648 otError otPlatCryptoEcdsaExportPublicKey(otCryptoKeyRef aKeyRef, otPlatCryptoEcdsaPublicKey *aPublicKey);
649 
650 /**
651  * Generate and import a new ECDSA key-pair at reference passed.
652  *
653  * @param[in]  aKeyRef            Key Reference to the slot where the key-pair is stored.
654  *
655  * @retval OT_ERROR_NONE          A new key-pair was generated successfully.
656  * @retval OT_ERROR_NO_BUFS       Failed to allocate buffer for key generation.
657  * @retval OT_ERROR_NOT_CAPABLE   Feature not supported.
658  * @retval OT_ERROR_FAILED        Failed to generate key-pair.
659  *
660  * @note This API is only used by OT core when `OPENTHREAD_CONFIG_PLATFORM_KEY_REFERENCES_ENABLE` is enabled.
661  */
662 otError otPlatCryptoEcdsaGenerateAndImportKey(otCryptoKeyRef aKeyRef);
663 
664 /**
665  * Use the keyref to verify the ECDSA signature of a hashed message.
666  *
667  * @param[in]  aKeyRef            Key Reference to the slot where the key-pair is stored.
668  * @param[in]  aHash              A pointer to a SHA-256 hash structure where the hash value for signature verification
669  *                                is stored.
670  * @param[in]  aSignature         A pointer to an ECDSA signature structure where the signature value to be verified is
671  *                                stored.
672  *
673  * @retval OT_ERROR_NONE          The signature was verified successfully.
674  * @retval OT_ERROR_SECURITY      The signature is invalid.
675  * @retval OT_ERROR_INVALID_ARGS  The key or hash is invalid.
676  * @retval OT_ERROR_NO_BUFS       Failed to allocate buffer for signature verification.
677  *
678  * @note This API is only used by OT core when `OPENTHREAD_CONFIG_PLATFORM_KEY_REFERENCES_ENABLE` is enabled.
679  */
680 otError otPlatCryptoEcdsaVerifyUsingKeyRef(otCryptoKeyRef                    aKeyRef,
681                                            const otPlatCryptoSha256Hash     *aHash,
682                                            const otPlatCryptoEcdsaSignature *aSignature);
683 
684 /**
685  * Perform PKCS#5 PBKDF2 using CMAC (AES-CMAC-PRF-128).
686  *
687  * @param[in]     aPassword          Password to use when generating key.
688  * @param[in]     aPasswordLen       Length of password.
689  * @param[in]     aSalt              Salt to use when generating key.
690  * @param[in]     aSaltLen           Length of salt.
691  * @param[in]     aIterationCounter  Iteration count.
692  * @param[in]     aKeyLen            Length of generated key in bytes.
693  * @param[out]    aKey               A pointer to the generated key.
694  *
695  * @retval OT_ERROR_NONE          A new key-pair was generated successfully.
696  * @retval OT_ERROR_NO_BUFS       Failed to allocate buffer for key generation.
697  * @retval OT_ERROR_NOT_CAPABLE   Feature not supported.
698  * @retval OT_ERROR_FAILED        Failed to generate key.
699  */
700 otError otPlatCryptoPbkdf2GenerateKey(const uint8_t *aPassword,
701                                       uint16_t       aPasswordLen,
702                                       const uint8_t *aSalt,
703                                       uint16_t       aSaltLen,
704                                       uint32_t       aIterationCounter,
705                                       uint16_t       aKeyLen,
706                                       uint8_t       *aKey);
707 
708 /**
709  * @}
710  */
711 
712 #ifdef __cplusplus
713 } // end of extern "C"
714 #endif
715 #endif // OPENTHREAD_PLATFORM_CRYPTO_H_
716