1 /**
2 ******************************************************************************
3 * @file stm32wbaxx_hal_cryp_ex.c
4 * @author MCD Application Team
5 * @brief CRYPEx HAL module driver.
6 * This file provides firmware functions to manage the extended
7 * functionalities of the Cryptography (CRYP) peripheral.
8 *
9 ******************************************************************************
10 * @attention
11 *
12 * Copyright (c) 2022 STMicroelectronics.
13 * All rights reserved.
14 *
15 * This software is licensed under terms that can be found in the LICENSE file
16 * in the root directory of this software component.
17 * If no LICENSE file comes with this software, it is provided AS-IS.
18 *
19 ******************************************************************************
20 */
21
22 /* Includes ------------------------------------------------------------------*/
23 #include "stm32wbaxx_hal.h"
24
25 /** @addtogroup STM32WBAxx_HAL_Driver
26 * @{
27 */
28
29 /** @addtogroup CRYPEx
30 * @{
31 */
32
33 #if defined(AES)
34
35 #ifdef HAL_CRYP_MODULE_ENABLED
36
37 /* Private typedef -----------------------------------------------------------*/
38 /* Private define ------------------------------------------------------------*/
39 /** @addtogroup CRYPEx_Private_Defines
40 * @{
41 */
42
43 #define CRYP_PHASE_INIT 0x00000000U /*!< GCM/GMAC (or CCM) init phase */
44 #define CRYP_PHASE_HEADER AES_CR_GCMPH_0 /*!< GCM/GMAC or CCM header phase */
45 #define CRYP_PHASE_PAYLOAD AES_CR_GCMPH_1 /*!< GCM(/CCM) payload phase */
46 #define CRYP_PHASE_FINAL AES_CR_GCMPH /*!< GCM/GMAC or CCM final phase */
47
48 #define CRYP_OPERATINGMODE_ENCRYPT 0x00000000U /*!< Encryption mode */
49 #define CRYP_OPERATINGMODE_KEYDERIVATION AES_CR_MODE_0 /*!< Key derivation mode only used when performing ECB and CBC decryptions */
50 #define CRYP_OPERATINGMODE_DECRYPT AES_CR_MODE_1 /*!< Decryption */
51 #define CRYP_OPERATINGMODE_KEYDERIVATION_DECRYPT AES_CR_MODE /*!< Key derivation and decryption only used when performing ECB and CBC decryptions */
52
53 #define CRYPEx_PHASE_PROCESS 0x02U /*!< CRYP peripheral is in processing phase */
54 #define CRYPEx_PHASE_FINAL 0x03U /*!< CRYP peripheral is in final phase this is relevant only with CCM and GCM modes */
55
56 /* CTR0 information to use in CCM algorithm */
57 #define CRYP_CCM_CTR0_0 0x07FFFFFFU
58 #define CRYP_CCM_CTR0_3 0xFFFFFF00U
59
60 /**
61 * @}
62 */
63
64 /* Private macro -------------------------------------------------------------*/
65 /* Private variables ---------------------------------------------------------*/
66 /* Private function prototypes -----------------------------------------------*/
67 #if defined(SAES)
68 static HAL_StatusTypeDef CRYPEx_KeyDecrypt(CRYP_HandleTypeDef *hcryp, uint32_t Timeout);
69 static HAL_StatusTypeDef CRYPEx_KeyEncrypt(CRYP_HandleTypeDef *hcryp, uint32_t Timeout);
70 static HAL_StatusTypeDef CRYPEx_KeyGeneration(CRYP_HandleTypeDef *hcryp, uint32_t Timeout);
71 #endif /* defined(SAES) */
72 /* Exported functions---------------------------------------------------------*/
73 /** @addtogroup CRYPEx_Exported_Functions
74 * @{
75 */
76
77 /** @defgroup CRYPEx_Exported_Functions_Group1 Extended AES processing functions
78 * @brief Extended processing functions.
79 *
80 @verbatim
81 ==============================================================================
82 ##### Extended AES processing functions #####
83 ==============================================================================
84 [..] This section provides functions allowing to generate the authentication
85 TAG in Polling mode
86 (#)HAL_CRYPEx_AESGCM_GenerateAuthTAG
87 (#)HAL_CRYPEx_AESCCM_GenerateAuthTAG
88 they should be used after Encrypt/Decrypt operation.
89
90 @endverbatim
91 * @{
92 */
93
94 /**
95 * @brief generate the GCM authentication TAG.
96 * @param hcryp pointer to a CRYP_HandleTypeDef structure that contains
97 * the configuration information for CRYP module
98 * @param pAuthTag Pointer to the authentication buffer
99 * the pAuthTag generated here is 128bits length, if the TAG length is
100 * less than 128bits, user should consider only the valid part of pAuthTag
101 * buffer which correspond exactly to TAG length.
102 * @param Timeout Timeout duration
103 * @retval HAL status
104 */
HAL_CRYPEx_AESGCM_GenerateAuthTAG(CRYP_HandleTypeDef * hcryp,const uint32_t * pAuthTag,uint32_t Timeout)105 HAL_StatusTypeDef HAL_CRYPEx_AESGCM_GenerateAuthTAG(CRYP_HandleTypeDef *hcryp, const uint32_t *pAuthTag,
106 uint32_t Timeout)
107 {
108 /* Assume first Init.HeaderSize is in words */
109 uint64_t headerlength = (uint64_t)hcryp->Init.HeaderSize * 32U; /* Header length in bits */
110 uint64_t inputlength = (uint64_t)hcryp->SizesSum * 8U; /* Input length in bits */
111 uint32_t tagaddr = (uint32_t)pAuthTag;
112 uint32_t i;
113 uint32_t tickstart;
114
115 /* Correct headerlength if Init.HeaderSize is actually in bytes */
116 if (hcryp->Init.HeaderWidthUnit == CRYP_HEADERWIDTHUNIT_BYTE)
117 {
118 headerlength /= 4U;
119 }
120
121 if (hcryp->State == HAL_CRYP_STATE_READY)
122 {
123 __HAL_LOCK(hcryp);
124
125 /* Change the CRYP peripheral state */
126 hcryp->State = HAL_CRYP_STATE_BUSY;
127
128 /* Check if initialization phase has already been performed */
129 if (hcryp->Phase == CRYPEx_PHASE_PROCESS)
130 {
131 /* Change the CRYP phase */
132 hcryp->Phase = CRYPEx_PHASE_FINAL;
133
134 /* Select final phase */
135 MODIFY_REG(hcryp->Instance->CR, AES_CR_GCMPH, CRYP_PHASE_FINAL);
136
137 /* Write into the AES_DINR register the number of bits in header (64 bits)
138 followed by the number of bits in the payload */
139 hcryp->Instance->DINR = 0U;
140 hcryp->Instance->DINR = (uint32_t)(headerlength);
141 hcryp->Instance->DINR = 0U;
142 hcryp->Instance->DINR = (uint32_t)(inputlength);
143
144 /* Wait for CCF flag to be raised */
145 tickstart = HAL_GetTick();
146 while (HAL_IS_BIT_CLR(hcryp->Instance->ISR, AES_ISR_CCF))
147 {
148 /* Check for the Timeout */
149 if (Timeout != HAL_MAX_DELAY)
150 {
151 if (((HAL_GetTick() - tickstart) > Timeout) || (Timeout == 0U))
152 {
153 /* Disable the CRYP peripheral clock */
154 __HAL_CRYP_DISABLE(hcryp);
155
156 /* Change state */
157 hcryp->ErrorCode |= HAL_CRYP_ERROR_TIMEOUT;
158 hcryp->State = HAL_CRYP_STATE_READY;
159 __HAL_UNLOCK(hcryp);
160 return HAL_ERROR;
161 }
162 }
163 }
164
165 /* Read the authentication TAG in the output FIFO */
166 for (i = 0U; i < 4U; i++)
167 {
168 *(uint32_t *)(tagaddr) = hcryp->Instance->DOUTR;
169 tagaddr += 4U;
170 }
171
172 /* Clear CCF flag */
173 __HAL_CRYP_CLEAR_FLAG(hcryp, CRYP_CLEAR_CCF);
174
175 /* Disable the peripheral */
176 __HAL_CRYP_DISABLE(hcryp);
177
178 /* Change the CRYP peripheral state */
179 hcryp->State = HAL_CRYP_STATE_READY;
180 __HAL_UNLOCK(hcryp);
181 }
182 else /* Initialization phase has not been performed */
183 {
184 /* Disable the Peripheral */
185 __HAL_CRYP_DISABLE(hcryp);
186
187 /* Sequence error code field */
188 hcryp->ErrorCode |= HAL_CRYP_ERROR_AUTH_TAG_SEQUENCE;
189
190 /* Change the CRYP peripheral state */
191 hcryp->State = HAL_CRYP_STATE_READY;
192 __HAL_UNLOCK(hcryp);
193 return HAL_ERROR;
194 }
195 }
196 else
197 {
198 /* Busy error code field */
199 hcryp->ErrorCode |= HAL_CRYP_ERROR_BUSY;
200 return HAL_ERROR;
201 }
202 /* Return function status */
203 return HAL_OK;
204 }
205
206 /**
207 * @brief AES CCM Authentication TAG generation.
208 * @param hcryp pointer to a CRYP_HandleTypeDef structure that contains
209 * the configuration information for CRYP module
210 * @param pAuthTag Pointer to the authentication buffer
211 * the pAuthTag generated here is 128bits length, if the TAG length is
212 * less than 128bits, user should consider only the valid part of pAuthTag
213 * buffer which correspond exactly to TAG length.
214 * @param Timeout Timeout duration
215 * @retval HAL status
216 */
HAL_CRYPEx_AESCCM_GenerateAuthTAG(CRYP_HandleTypeDef * hcryp,const uint32_t * pAuthTag,uint32_t Timeout)217 HAL_StatusTypeDef HAL_CRYPEx_AESCCM_GenerateAuthTAG(CRYP_HandleTypeDef *hcryp, const uint32_t *pAuthTag,
218 uint32_t Timeout)
219 {
220 uint32_t tagaddr = (uint32_t)pAuthTag;
221 uint32_t i;
222 uint32_t tickstart;
223
224 if (hcryp->State == HAL_CRYP_STATE_READY)
225 {
226 __HAL_LOCK(hcryp);
227
228 /* Disable interrupts in case they were kept enabled to proceed
229 a single message in several iterations */
230 __HAL_CRYP_DISABLE_IT(hcryp, CRYP_IT_CCFIE | CRYP_IT_RWEIE | CRYP_IT_KEIE);
231
232 /* Change the CRYP peripheral state */
233 hcryp->State = HAL_CRYP_STATE_BUSY;
234
235 /* Check if initialization phase has already been performed */
236 if (hcryp->Phase == CRYPEx_PHASE_PROCESS)
237 {
238 /* Change the CRYP phase */
239 hcryp->Phase = CRYPEx_PHASE_FINAL;
240 /* Select final phase */
241 MODIFY_REG(hcryp->Instance->CR, AES_CR_GCMPH, CRYP_PHASE_FINAL);
242
243 /* Wait for CCF flag to be raised */
244 tickstart = HAL_GetTick();
245 while (HAL_IS_BIT_CLR(hcryp->Instance->ISR, AES_ISR_CCF))
246 {
247 /* Check for the Timeout */
248 if (Timeout != HAL_MAX_DELAY)
249 {
250 if (((HAL_GetTick() - tickstart) > Timeout) || (Timeout == 0U))
251 {
252 /* Disable the CRYP peripheral Clock */
253 __HAL_CRYP_DISABLE(hcryp);
254
255 /* Change state */
256 hcryp->ErrorCode |= HAL_CRYP_ERROR_TIMEOUT;
257 hcryp->State = HAL_CRYP_STATE_READY;
258 __HAL_UNLOCK(hcryp);
259 return HAL_ERROR;
260 }
261 }
262 }
263
264 /* Read the authentication TAG in the output FIFO */
265 for (i = 0U; i < 4U; i++)
266 {
267 *(uint32_t *)(tagaddr) = hcryp->Instance->DOUTR;
268 tagaddr += 4U;
269 }
270
271 /* Clear CCF Flag */
272 __HAL_CRYP_CLEAR_FLAG(hcryp, CRYP_CLEAR_CCF);
273
274 /* Change the CRYP peripheral state */
275 hcryp->State = HAL_CRYP_STATE_READY;
276 __HAL_UNLOCK(hcryp);
277
278 /* Disable CRYP */
279 __HAL_CRYP_DISABLE(hcryp);
280 }
281 else /* Initialization phase has not been performed */
282 {
283 /* Disable the peripheral */
284 __HAL_CRYP_DISABLE(hcryp);
285
286 /* Sequence error code field */
287 hcryp->ErrorCode |= HAL_CRYP_ERROR_AUTH_TAG_SEQUENCE;
288
289 /* Change the CRYP peripheral state */
290 hcryp->State = HAL_CRYP_STATE_READY;
291 __HAL_UNLOCK(hcryp);
292 return HAL_ERROR;
293 }
294 }
295 else
296 {
297 /* Busy error code field */
298 hcryp->ErrorCode = HAL_CRYP_ERROR_BUSY;
299 return HAL_ERROR;
300 }
301 /* Return function status */
302 return HAL_OK;
303 }
304
305 /**
306 * @}
307 */
308
309 #if defined(SAES)
310
311 /** @defgroup CRYPEx_Exported_Functions_Group2 Wrap and Unwrap key functions
312 * @brief Wrap and Unwrap key functions.
313 *
314 @verbatim
315 ==============================================================================
316 ##### Wrap and Unwrap key #####
317 ==============================================================================
318 [..] This section provides API allowing to wrap (encrypt) and unwrap (decrypt)
319 key using one of the following keys, and AES Algorithm.
320 Key selection :
321 - Derived hardware unique key (DHUK)
322 - XOR of DHUK and BHK
323 - Boot hardware key (BHK)
324
325 @endverbatim
326 * @{
327 */
328
329 /**
330 * @brief Wrap (encrypt) application keys.
331 * @param hcryp pointer to a CRYP_HandleTypeDef structure that contains
332 * the configuration information for CRYP module
333 * @param pInput Pointer to the Key buffer to encrypt in case of ECB or CBC
334 * @param pOutput Pointer to the Key buffer encrypted in case of ECB or CBC
335 * @param Timeout Specify Timeout value
336 * @retval HAL status
337 */
HAL_CRYPEx_WrapKey(CRYP_HandleTypeDef * hcryp,uint32_t * pInput,uint32_t * pOutput,uint32_t Timeout)338 HAL_StatusTypeDef HAL_CRYPEx_WrapKey(CRYP_HandleTypeDef *hcryp, uint32_t *pInput, uint32_t *pOutput, uint32_t Timeout)
339 {
340 HAL_StatusTypeDef status;
341 uint32_t algo;
342
343 if (hcryp->State == HAL_CRYP_STATE_READY)
344 {
345 /* Change state Busy */
346 hcryp->State = HAL_CRYP_STATE_BUSY;
347 __HAL_LOCK(hcryp);
348
349 /* Reset CrypInCount, CrypOutCount and Initialize pCrypInBuffPtr and pCrypOutBuffPtr parameters*/
350 hcryp->CrypInCount = 0U;
351 hcryp->CrypOutCount = 0U;
352 hcryp->pCrypInBuffPtr = pInput;
353 hcryp->pCrypOutBuffPtr = pOutput;
354
355 /* Disable the CRYP peripheral clock */
356 __HAL_CRYP_DISABLE(hcryp);
357
358 /* Set the operating mode*/
359 MODIFY_REG(hcryp->Instance->CR, AES_CR_KMOD, CRYP_KEYMODE_WRAPPED);
360
361 /* Encryption operating mode(Mode 0)*/
362 MODIFY_REG(hcryp->Instance->CR, AES_CR_MODE, CRYP_OPERATINGMODE_ENCRYPT);
363
364
365 /* algo get algorithm selected */
366 algo = hcryp->Instance->CR & AES_CR_CHMOD;
367
368 switch (algo)
369 {
370 case CRYP_AES_ECB:
371 case CRYP_AES_CBC:
372 /* AES decryption */
373 status = CRYPEx_KeyEncrypt(hcryp, Timeout);
374 break;
375 case CRYP_AES_CTR:
376 /* AES Key generation */
377 status = CRYPEx_KeyGeneration(hcryp, Timeout);
378 break;
379 default:
380 hcryp->ErrorCode |= HAL_CRYP_ERROR_NOT_SUPPORTED;
381 status = HAL_ERROR;
382 break;
383 }
384 }
385 else
386 {
387 /* Busy error code field */
388 hcryp->ErrorCode |= HAL_CRYP_ERROR_BUSY;
389 status = HAL_ERROR;
390 }
391 /* Return function status */
392 return status;
393 }
394
395 /**
396 * @brief Unwrap (Decrypt) application keys.
397 * @param hcryp pointer to a CRYP_HandleTypeDef structure that contains
398 * the configuration information for CRYP module
399 * @param pInput Pointer to the Key buffer to decrypt or generated key in case of CTR.
400 * @param Timeout Specify Timeout value
401 * @retval HAL status
402 */
HAL_CRYPEx_UnwrapKey(CRYP_HandleTypeDef * hcryp,uint32_t * pInput,uint32_t Timeout)403 HAL_StatusTypeDef HAL_CRYPEx_UnwrapKey(CRYP_HandleTypeDef *hcryp, uint32_t *pInput, uint32_t Timeout)
404 {
405 HAL_StatusTypeDef status;
406 uint32_t algo;
407
408 if (hcryp->State == HAL_CRYP_STATE_READY)
409 {
410 /* Change state Busy */
411 hcryp->State = HAL_CRYP_STATE_BUSY;
412
413 __HAL_LOCK(hcryp);
414
415 /* Reset CrypInCount, CrypOutCount and Initialize pCrypInBuffPtr and pCrypOutBuffPtr parameters */
416 hcryp->CrypInCount = 0U;
417 hcryp->CrypOutCount = 0U;
418 hcryp->pCrypInBuffPtr = pInput;
419
420 /* Disable the CRYP peripheral clock */
421 __HAL_CRYP_DISABLE(hcryp);
422
423 /* Set the operating mode*/
424 MODIFY_REG(hcryp->Instance->CR, AES_CR_KMOD, CRYP_KEYMODE_WRAPPED);
425
426 /* Decryption operating mode(Mode 3)*/
427 MODIFY_REG(hcryp->Instance->CR, AES_CR_MODE, CRYP_OPERATINGMODE_DECRYPT);
428
429 /* algo get algorithm selected */
430 algo = hcryp->Instance->CR & AES_CR_CHMOD;
431
432 switch (algo)
433 {
434 case CRYP_AES_ECB:
435 case CRYP_AES_CBC:
436 /* AES decryption */
437 status = CRYPEx_KeyDecrypt(hcryp, Timeout);
438 break;
439
440 case CRYP_AES_CTR:
441 /* AES Key generation */
442 status = CRYPEx_KeyGeneration(hcryp, Timeout);
443 break;
444 default:
445 hcryp->ErrorCode |= HAL_CRYP_ERROR_NOT_SUPPORTED;
446 status = HAL_ERROR;
447 break;
448 }
449 }
450 else
451 {
452 /* Busy error code field */
453 hcryp->ErrorCode |= HAL_CRYP_ERROR_BUSY;
454 status = HAL_ERROR;
455 }
456 /* Return function status */
457 return status;
458 }
459
460 /**
461 * @}
462 */
463
464 /** @defgroup CRYPEx_Exported_Functions_Group3 Encrypt and Decrypt Shared key functions
465 * @brief Encrypt and Decrypt Shared key functions.
466 *
467 @verbatim
468 ==============================================================================
469 ##### Encrypt and Decrypt Shared key functions #####
470 ==============================================================================
471 [..] This section provides API allowing to Encrypt and Decrypt Shared key
472
473 @endverbatim
474 * @{
475 */
476
477 /**
478 * @brief Encrypt Shared key.
479 * @param hcryp pointer to a CRYP_HandleTypeDef structure that contains
480 * the configuration information for CRYP module
481 * @param pKey Pointer to the Key buffer to share
482 * @param pOutput Pointer to the Key buffer encrypted
483 * @param ID Key share identification
484 * @param Timeout Specify Timeout value
485 * @retval HAL status
486 */
HAL_CRYPEx_EncryptSharedKey(CRYP_HandleTypeDef * hcryp,uint32_t * pKey,uint32_t * pOutput,uint32_t ID,uint32_t Timeout)487 HAL_StatusTypeDef HAL_CRYPEx_EncryptSharedKey(CRYP_HandleTypeDef *hcryp, uint32_t *pKey, uint32_t *pOutput, uint32_t ID,
488 uint32_t Timeout)
489 {
490 HAL_StatusTypeDef status;
491 uint32_t algo;
492
493 if (hcryp->State == HAL_CRYP_STATE_READY)
494 {
495 /* Change state Busy */
496 hcryp->State = HAL_CRYP_STATE_BUSY;
497 __HAL_LOCK(hcryp);
498
499 /* Reset CrypInCount, CrypOutCount and Initialize pCrypInBuffPtr and pCrypOutBuffPtr parameters */
500 hcryp->CrypInCount = 0U;
501 hcryp->CrypOutCount = 0U;
502 hcryp->pCrypInBuffPtr = pKey;
503 hcryp->pCrypOutBuffPtr = pOutput;
504
505 /* Disable the CRYP peripheral clock */
506 __HAL_CRYP_DISABLE(hcryp);
507
508 /* Set the operating mode */
509 MODIFY_REG(hcryp->Instance->CR, AES_CR_KMOD | AES_CR_KSHAREID, CRYP_KEYMODE_SHARED | ID);
510
511 /* Encryption operating mode(Mode 0)*/
512 MODIFY_REG(hcryp->Instance->CR, AES_CR_MODE, CRYP_OPERATINGMODE_ENCRYPT);
513
514 /* algo get algorithm selected */
515 algo = hcryp->Instance->CR & AES_CR_CHMOD;
516
517 switch (algo)
518 {
519 case CRYP_AES_ECB:
520 case CRYP_AES_CBC:
521 /* AES decryption */
522 status = CRYPEx_KeyEncrypt(hcryp, Timeout);
523 break;
524 case CRYP_AES_CTR:
525 /* AES CTR key generation */
526 status = CRYPEx_KeyGeneration(hcryp, Timeout);
527 break;
528 default:
529 hcryp->ErrorCode |= HAL_CRYP_ERROR_NOT_SUPPORTED;
530 status = HAL_ERROR;
531 break;
532 }
533 }
534 else
535 {
536 /* Busy error code field */
537 hcryp->ErrorCode |= HAL_CRYP_ERROR_BUSY;
538 status = HAL_ERROR;
539 }
540 /* Return function status */
541 return status;
542 }
543
544 /**
545 * @brief Decrypt Shared key.
546 * @param hcryp pointer to a CRYP_HandleTypeDef structure that contains
547 * the configuration information for CRYP module
548 * @param pKey Pointer to the Key buffer to share
549 * @param ID Key share identification
550 * @param Timeout Specify Timeout value
551 * @retval HAL status
552 */
HAL_CRYPEx_DecryptSharedKey(CRYP_HandleTypeDef * hcryp,uint32_t * pKey,uint32_t ID,uint32_t Timeout)553 HAL_StatusTypeDef HAL_CRYPEx_DecryptSharedKey(CRYP_HandleTypeDef *hcryp, uint32_t *pKey, uint32_t ID, uint32_t Timeout)
554 {
555 HAL_StatusTypeDef status;
556 uint32_t algo;
557
558 if (hcryp->State == HAL_CRYP_STATE_READY)
559 {
560 /* Change state Busy */
561 hcryp->State = HAL_CRYP_STATE_BUSY;
562 __HAL_LOCK(hcryp);
563
564 /* Reset CrypInCount, CrypOutCount and Initialize pCrypInBuffPtr and pCrypOutBuffPtr parameters */
565 hcryp->CrypInCount = 0U;
566 hcryp->CrypOutCount = 0U;
567 hcryp->pCrypInBuffPtr = pKey;
568
569 /* Disable the CRYP peripheral clock */
570 __HAL_CRYP_DISABLE(hcryp);
571
572 /* Set the operating mode */
573 MODIFY_REG(hcryp->Instance->CR, AES_CR_KMOD | AES_CR_KSHAREID, CRYP_KEYMODE_SHARED | ID);
574
575 /* Decryption operating mode(Mode 3)*/
576 MODIFY_REG(hcryp->Instance->CR, AES_CR_MODE, CRYP_OPERATINGMODE_DECRYPT);
577
578 /* algo get algorithm selected */
579 algo = hcryp->Instance->CR & AES_CR_CHMOD;
580
581 switch (algo)
582 {
583 case CRYP_AES_ECB:
584 case CRYP_AES_CBC:
585 /* AES decryption */
586 status = CRYPEx_KeyDecrypt(hcryp, Timeout);
587 break;
588 case CRYP_AES_CTR:
589 /* AES CTR key generation */
590 status = CRYPEx_KeyGeneration(hcryp, Timeout);
591 break;
592 default:
593 hcryp->ErrorCode |= HAL_CRYP_ERROR_NOT_SUPPORTED;
594 status = HAL_ERROR;
595 break;
596 }
597 }
598 else
599 {
600 /* Busy error code field */
601 hcryp->ErrorCode |= HAL_CRYP_ERROR_BUSY;
602 status = HAL_ERROR;
603 }
604 /* Return function status */
605 return status;
606 }
607
608 /**
609 * @}
610 */
611
612 /**
613 * @}
614 */
615
616 /* Private functions ---------------------------------------------------------*/
617 /** @addtogroup CRYP_Private_Functions
618 * @{
619 */
620 /**
621 * @brief Key Decryption
622 * @param hcryp pointer to a CRYP_HandleTypeDef structure
623 * @param Timeout specify Timeout value
624 * @note It is strongly recommended to select hardware secret keys
625 * @retval HAL status
626 */
CRYPEx_KeyDecrypt(CRYP_HandleTypeDef * hcryp,uint32_t Timeout)627 static HAL_StatusTypeDef CRYPEx_KeyDecrypt(CRYP_HandleTypeDef *hcryp, uint32_t Timeout)
628 {
629 uint32_t incount; /* Temporary CrypInCount Value */
630 uint32_t i;
631 uint32_t tickstart;
632
633 /* key preparation for decryption, operating mode 2*/
634 MODIFY_REG(hcryp->Instance->CR, AES_CR_MODE, CRYP_OPERATINGMODE_KEYDERIVATION);
635
636 /* Enable CRYP */
637 __HAL_CRYP_ENABLE(hcryp);
638
639 /* Wait for CCF flag to be raised */
640 tickstart = HAL_GetTick();
641 while (HAL_IS_BIT_CLR(hcryp->Instance->ISR, AES_ISR_CCF))
642 {
643 /* Check for the Timeout */
644 if (Timeout != HAL_MAX_DELAY)
645 {
646 if (((HAL_GetTick() - tickstart) > Timeout) || (Timeout == 0U))
647 {
648 /* Disable the CRYP peripheral clock */
649 __HAL_CRYP_DISABLE(hcryp);
650
651 /* Change state */
652 hcryp->ErrorCode |= HAL_CRYP_ERROR_TIMEOUT;
653 hcryp->State = HAL_CRYP_STATE_READY;
654 __HAL_UNLOCK(hcryp);
655 return HAL_ERROR;
656 }
657 }
658 }
659 /* Clear CCF Flag */
660 __HAL_CRYP_CLEAR_FLAG(hcryp, CRYP_CLEAR_CCF);
661
662 /* End of Key preparation for ECB/CBC */
663 /* Return to decryption operating mode(Mode 3)*/
664 MODIFY_REG(hcryp->Instance->CR, AES_CR_MODE, CRYP_OPERATINGMODE_DECRYPT);
665
666 if (hcryp->Init.Algorithm != CRYP_AES_ECB)
667 {
668 /* Set the Initialization Vector */
669 hcryp->Instance->IVR3 = *(uint32_t *)(hcryp->Init.pInitVect);
670 hcryp->Instance->IVR2 = *(uint32_t *)(hcryp->Init.pInitVect + 1U);
671 hcryp->Instance->IVR1 = *(uint32_t *)(hcryp->Init.pInitVect + 2U);
672 hcryp->Instance->IVR0 = *(uint32_t *)(hcryp->Init.pInitVect + 3U);
673 }
674 /* Enable CRYP */
675 __HAL_CRYP_ENABLE(hcryp);
676
677 /* Set the phase */
678 hcryp->Phase = CRYPEx_PHASE_PROCESS;
679
680 if (hcryp->Init.KeySize == CRYP_KEYSIZE_128B)
681 {
682 incount = 4U;
683 }
684 else
685 {
686 incount = 8U;
687 }
688 while (hcryp->CrypInCount < incount)
689 {
690 /* Write four times to input the key to encrypt */
691 for (i = 0U; i < 4U; i++)
692 {
693 hcryp->Instance->DINR = *(uint32_t *)(hcryp->pCrypInBuffPtr + hcryp->CrypInCount);
694 hcryp->CrypInCount++;
695 }
696 /* Wait for CCF flag to be raised */
697 tickstart = HAL_GetTick();
698 while (HAL_IS_BIT_CLR(hcryp->Instance->ISR, AES_ISR_CCF))
699 {
700 /* Check for the Timeout */
701 if (Timeout != HAL_MAX_DELAY)
702 {
703 if (((HAL_GetTick() - tickstart) > Timeout) || (Timeout == 0U))
704 {
705 /* Disable the CRYP peripheral clock */
706 __HAL_CRYP_DISABLE(hcryp);
707
708 /* Change state */
709 hcryp->ErrorCode |= HAL_CRYP_ERROR_TIMEOUT;
710 hcryp->State = HAL_CRYP_STATE_READY;
711 __HAL_UNLOCK(hcryp);
712 return HAL_ERROR;
713 }
714 }
715 }
716
717 /* Clear CCF Flag */
718 __HAL_CRYP_CLEAR_FLAG(hcryp, CRYP_CLEAR_CCF);
719 }
720
721 /* Disable the CRYP peripheral clock */
722 __HAL_CRYP_DISABLE(hcryp);
723
724 /* Change the CRYP peripheral state */
725 hcryp->State = HAL_CRYP_STATE_READY;
726 __HAL_UNLOCK(hcryp);
727 return HAL_OK;
728 }
729
730 /**
731 * @brief Key Encryption
732 * @param hcryp pointer to a CRYP_HandleTypeDef structure
733 * @param Timeout specify Timeout value
734 * @retval HAL status
735 */
CRYPEx_KeyEncrypt(CRYP_HandleTypeDef * hcryp,uint32_t Timeout)736 static HAL_StatusTypeDef CRYPEx_KeyEncrypt(CRYP_HandleTypeDef *hcryp, uint32_t Timeout)
737 {
738 uint32_t incount; /* Temporary CrypInCount Value */
739 uint32_t i;
740 uint32_t tickstart;
741 uint32_t temp; /* Temporary CrypOutBuff */
742
743 if (hcryp->Init.Algorithm != CRYP_AES_ECB)
744 {
745 /* Set the Initialization Vector */
746 hcryp->Instance->IVR3 = *(uint32_t *)(hcryp->Init.pInitVect);
747 hcryp->Instance->IVR2 = *(uint32_t *)(hcryp->Init.pInitVect + 1U);
748 hcryp->Instance->IVR1 = *(uint32_t *)(hcryp->Init.pInitVect + 2U);
749 hcryp->Instance->IVR0 = *(uint32_t *)(hcryp->Init.pInitVect + 3U);
750 }
751
752 /* Enable CRYP */
753 __HAL_CRYP_ENABLE(hcryp);
754
755 /* Set the phase */
756 hcryp->Phase = CRYPEx_PHASE_PROCESS;
757
758 if (hcryp->Init.KeySize == CRYP_KEYSIZE_128B)
759 {
760 incount = 4U;
761 }
762 else
763 {
764 incount = 8U;
765 }
766 while (hcryp->CrypInCount < incount)
767 {
768 for (i = 0U; i < 4U; i++)
769 {
770 hcryp->Instance->DINR = *(uint32_t *)(hcryp->pCrypInBuffPtr + hcryp->CrypInCount);
771 hcryp->CrypInCount++;
772 }
773 /* Wait for CCF flag to be raised */
774 tickstart = HAL_GetTick();
775 while (HAL_IS_BIT_CLR(hcryp->Instance->ISR, AES_ISR_CCF))
776 {
777 /* Check for the Timeout */
778 if (Timeout != HAL_MAX_DELAY)
779 {
780 if (((HAL_GetTick() - tickstart) > Timeout) || (Timeout == 0U))
781 {
782 /* Disable the CRYP peripheral clock */
783 __HAL_CRYP_DISABLE(hcryp);
784
785 /* Change state */
786 hcryp->ErrorCode |= HAL_CRYP_ERROR_TIMEOUT;
787 hcryp->State = HAL_CRYP_STATE_READY;
788 __HAL_UNLOCK(hcryp);
789 return HAL_ERROR;
790 }
791 }
792 }
793
794 /* Clear CCF Flag */
795 __HAL_CRYP_CLEAR_FLAG(hcryp, CRYP_CLEAR_CCF);
796
797 /* Read the output block from the output FIFO and put them in temporary buffer then
798 get CrypOutBuff from temporary buffer */
799 for (i = 0U; i < 4U; i++)
800 {
801 temp = hcryp->Instance->DOUTR;
802 *(uint32_t *)(hcryp->pCrypOutBuffPtr + hcryp->CrypOutCount) = temp;
803 hcryp->CrypOutCount++;
804 }
805 }
806
807 /* Disable the CRYP peripheral clock */
808 __HAL_CRYP_DISABLE(hcryp);
809
810 /* Change the CRYP peripheral state */
811 hcryp->State = HAL_CRYP_STATE_READY;
812 __HAL_UNLOCK(hcryp);
813 return HAL_OK;
814 }
815 /**
816 * @brief Key Generation
817 * @param hcryp pointer to a CRYP_HandleTypeDef structure
818 * @param Timeout specify Timeout value
819 * @retval HAL status
820 */
CRYPEx_KeyGeneration(CRYP_HandleTypeDef * hcryp,uint32_t Timeout)821 static HAL_StatusTypeDef CRYPEx_KeyGeneration(CRYP_HandleTypeDef *hcryp, uint32_t Timeout)
822 {
823 uint32_t tickstart;
824
825 /* No swap, DATATYPE must be kept to 0x0.*/
826 MODIFY_REG(hcryp->Instance->CR, AES_CR_DATATYPE, CRYP_NO_SWAP);
827
828 /*Writes initialization vector in IV registers*/
829 if (hcryp->Init.pInitVect != NULL)
830 {
831 /* Set the Initialization Vector*/
832 hcryp->Instance->IVR3 = *(uint32_t *)(hcryp->Init.pInitVect);
833 hcryp->Instance->IVR2 = *(uint32_t *)(hcryp->Init.pInitVect + 1U);
834 hcryp->Instance->IVR1 = *(uint32_t *)(hcryp->Init.pInitVect + 2U);
835 /* Keeping the two least significant bit of SAES_IVR0 to 00 */
836 hcryp->Instance->IVR0 = *(uint32_t *)(hcryp->Init.pInitVect + 3U);
837 hcryp->Instance->IVR0 &= 0xFFFFFFFCU ;
838 }
839 else
840 {
841 return HAL_ERROR;
842 }
843
844 /* Enable CRYP */
845 __HAL_CRYP_ENABLE(hcryp);
846
847 /* Wait for CCF flag to be raised */
848 tickstart = HAL_GetTick();
849 while (HAL_IS_BIT_CLR(hcryp->Instance->ISR, AES_ISR_CCF))
850 {
851 /* Check for the Timeout */
852 if (Timeout != HAL_MAX_DELAY)
853 {
854 if (((HAL_GetTick() - tickstart) > Timeout) || (Timeout == 0U))
855 {
856 /* Disable the CRYP peripheral clock */
857 __HAL_CRYP_DISABLE(hcryp);
858
859 /* Change state */
860 hcryp->ErrorCode |= HAL_CRYP_ERROR_TIMEOUT;
861 hcryp->State = HAL_CRYP_STATE_READY;
862 __HAL_UNLOCK(hcryp);
863 return HAL_ERROR;
864 }
865 }
866 }
867 /* Clear CCF Flag */
868 __HAL_CRYP_CLEAR_FLAG(hcryp, CRYP_CLEAR_CCF);
869
870 /* Disable the CRYP peripheral clock */
871 __HAL_CRYP_DISABLE(hcryp);
872
873 /* Change the CRYP peripheral state */
874 hcryp->State = HAL_CRYP_STATE_READY;
875 __HAL_UNLOCK(hcryp);
876
877 return HAL_OK;
878 }
879 #endif /* defined(SAES)*/
880
881 /**
882 * @}
883 */
884
885 /**
886 * @}
887 */
888
889 /**
890 * @}
891 */
892
893 #endif /* HAL_CRYP_MODULE_ENABLED */
894
895 #endif /* AES */
896 /**
897 * @}
898 */
899
900 /**
901 * @}
902 */
903