1 /**
2   ******************************************************************************
3   * @file    stm32h7xx_hal_cryp.c
4   * @author  MCD Application Team
5   * @brief   CRYP HAL module driver.
6   *          This file provides firmware functions to manage the following
7   *          functionalities of the Cryptography (CRYP) peripheral:
8   *           + Initialization and de-initialization functions
9   *           + AES processing functions
10   *           + DES processing functions
11   *           + TDES processing functions
12   *           + DMA callback functions
13   *           + CRYP IRQ handler management
14   *           + Peripheral State functions
15   *
16   ******************************************************************************
17   * @attention
18   *
19   * Copyright (c) 2017 STMicroelectronics.
20   * All rights reserved.
21   *
22   * This software is licensed under terms that can be found in the LICENSE file
23   * in the root directory of this software component.
24   * If no LICENSE file comes with this software, it is provided AS-IS.
25   *
26   ******************************************************************************
27   @verbatim
28   ==============================================================================
29                      ##### How to use this driver #####
30   ==============================================================================
31     [..]
32       The CRYP HAL driver can be used in CRYP IP as follows:
33 
34       (#)Initialize the CRYP low level resources by implementing the HAL_CRYP_MspInit():
35          (##) Enable the CRYP interface clock using __HAL_RCC_CRYP_CLK_ENABLE()
36          (##) In case of using interrupts (e.g. HAL_CRYP_Encrypt_IT())
37              (+++) Configure the CRYP interrupt priority using HAL_NVIC_SetPriority()
38              (+++) Enable the CRYP IRQ handler using HAL_NVIC_EnableIRQ()
39              (+++) In CRYP IRQ handler, call HAL_CRYP_IRQHandler()
40          (##) In case of using DMA to control data transfer (e.g. HAL_CRYP_Encrypt_DMA())
41              (+++) Enable the DMAx interface clock using __RCC_DMAx_CLK_ENABLE()
42              (+++) Configure and enable two DMA streams one for managing data transfer from
43                  memory to peripheral (input stream) and another stream for managing data
44                  transfer from peripheral to memory (output stream)
45              (+++) Associate the initialized DMA handle to the CRYP DMA handle
46                  using  __HAL_LINKDMA()
47              (+++) Configure the priority and enable the NVIC for the transfer complete
48                  interrupt on the two DMA Streams. The output stream should have higher
49                  priority than the input stream HAL_NVIC_SetPriority() and HAL_NVIC_EnableIRQ()
50 
51       (#)Initialize the CRYP according to the specified parameters :
52          (##) The data type: bit swap(1-bit data), byte swap(8-bit data), half word swap(16-bit data)
53             or no swap(32-bit data).
54          (##) The key size: 128, 192 or 256.
55          (##) The AlgoMode DES/ TDES Algorithm ECB/CBC or AES Algorithm ECB/CBC/CTR/GCM or CCM.
56          (##) The initialization vector (counter). It is not used in ECB mode.
57          (##) The key buffer used for encryption/decryption.
58          (##) The Header used only in AES GCM and CCM Algorithm for authentication.
59          (##) The HeaderSize The size of header buffer in word.
60          (##) The B0 block is the first authentication block used only  in AES CCM mode.
61 
62       (#)Three processing (encryption/decryption) functions are available:
63          (##) Polling mode: encryption and decryption APIs are blocking functions
64               i.e. they process the data and wait till the processing is finished,
65               e.g. HAL_CRYP_Encrypt & HAL_CRYP_Decrypt
66          (##) Interrupt mode: encryption and decryption APIs are not blocking functions
67               i.e. they process the data under interrupt,
68               e.g. HAL_CRYP_Encrypt_IT & HAL_CRYP_Decrypt_IT
69          (##) DMA mode: encryption and decryption APIs are not blocking functions
70               i.e. the data transfer is ensured by DMA,
71               e.g. HAL_CRYP_Encrypt_DMA & HAL_CRYP_Decrypt_DMA
72 
73       (#)When the processing function is called at first time after HAL_CRYP_Init()
74          the CRYP peripheral is configured and processes the buffer in input.
75          At second call, no need to Initialize the CRYP, user have to get current configuration via
76          HAL_CRYP_GetConfig() API, then only  HAL_CRYP_SetConfig() is requested to set
77          new parametres, finally user can  start encryption/decryption.
78 
79        (#)Call HAL_CRYP_DeInit() to deinitialize the CRYP peripheral.
80 
81        (#)To process a single message with consecutive calls to HAL_CRYP_Encrypt() or HAL_CRYP_Decrypt()
82           without having to configure again the Key or the Initialization Vector between each API call,
83           the field KeyIVConfigSkip of the initialization structure must be set to CRYP_KEYIVCONFIG_ONCE.
84           Same is true for consecutive calls of HAL_CRYP_Encrypt_IT(), HAL_CRYP_Decrypt_IT(), HAL_CRYP_Encrypt_DMA()
85           or HAL_CRYP_Decrypt_DMA().
86 
87     [..]
88       The cryptographic processor supports following standards:
89       (#) The data encryption standard (DES) and Triple-DES (TDES) supported only by CRYP1 IP:
90          (##)64-bit data block processing
91          (##) chaining modes supported :
92              (+++)  Electronic Code Book(ECB)
93              (+++)  Cipher Block Chaining (CBC)
94          (##) keys length supported :64-bit, 128-bit and 192-bit.
95       (#) The advanced encryption standard (AES) supported  by CRYP1:
96          (##)128-bit data block processing
97          (##) chaining modes supported :
98              (+++)  Electronic Code Book(ECB)
99              (+++)  Cipher Block Chaining (CBC)
100              (+++)  Counter mode (CTR)
101              (+++)  Galois/counter mode (GCM/GMAC)
102              (+++)  Counter with Cipher Block Chaining-Message(CCM)
103          (##) keys length Supported :
104              (+++) for CRYP1 IP: 128-bit, 192-bit and 256-bit.
105 
106     [..]  This section describes the AES Galois/counter mode (GCM) supported by both CRYP1 IP:
107       (#)  Algorithm supported :
108          (##) Galois/counter mode (GCM)
109          (##) Galois message authentication code (GMAC) :is exactly the same as
110               GCM algorithm composed only by an header.
111       (#)  Four phases are performed in GCM :
112          (##) Init phase: IP prepares the GCM hash subkey (H) and do the IV processing
113          (##) Header phase: IP processes the Additional Authenticated Data (AAD), with hash
114           computation only.
115          (##) Payload phase: IP processes the plaintext (P) with hash computation + keystream
116           encryption + data XORing. It works in a similar way for ciphertext (C).
117          (##) Final phase: IP generates the authenticated tag (T) using the last block of data.
118           HAL_CRYPEx_AESGCM_GenerateAuthTAG API used in this phase to generate 4 words which correspond
119           to the Tag. user should consider only part of this 4 words, if Tag length is less than 128 bits.
120       (#)  structure of message construction in GCM is defined as below  :
121          (##) 16 bytes Initial Counter Block (ICB)composed of IV and counter
122          (##) The authenticated header A (also knows as Additional Authentication Data AAD)
123           this part of the message is only authenticated, not encrypted.
124          (##) The plaintext message P is both authenticated and encrypted as ciphertext.
125           GCM standard specifies that ciphertext has same bit length as the plaintext.
126          (##) The last block is composed of the length of A (on 64 bits) and the length of ciphertext
127           (on 64 bits)
128 
129     [..]  This section describe The AES Counter with Cipher Block Chaining-Message
130           Authentication Code (CCM) supported by both CRYP1 IP:
131       (#)  Specific parameters for CCM  :
132 
133          (##) B0 block  : According to NIST Special Publication 800-38C,
134             The first block B0 is formatted as follows, where l(m) is encoded in
135             most-significant-byte first order(see below table 3)
136 
137               (+++)  Q: a bit string representation of the octet length of P (plaintext)
138               (+++)  q The octet length of the binary representation of the octet length of the payload
139               (+++)  A nonce (N), n The octet length of the where n+q=15.
140               (+++)  Flags: most significant octet containing four flags for control information,
141               (+++)  t The octet length of the MAC.
142          (##) B1 block (header) : associated data length(a) concatenated with Associated Data (A)
143               the associated data length expressed in bytes (a) defined as below:
144             (+++)  If 0 < a < 216-28, then it is encoded as [a]16, i.e. two octets
145             (+++)  If 216-28 < a < 232, then it is encoded as 0xff || 0xfe || [a]32, i.e. six octets
146             (+++)  If 232 < a < 264, then it is encoded as 0xff || 0xff || [a]64, i.e. ten octets
147          (##) CTRx block  : control blocks
148             (+++) Generation of CTR1 from first block B0 information :
149               equal to B0 with first 5 bits zeroed and most significant bits storing octet
150               length of P also zeroed, then incremented by one ( see below Table 4)
151             (+++) Generation of CTR0: same as CTR1 with bit[0] set to zero.
152 
153       (#)  Four phases are performed in CCM for CRYP1 IP:
154          (##) Init phase: IP prepares the GCM hash subkey (H) and do the IV processing
155          (##) Header phase: IP processes the Additional Authenticated Data (AAD), with hash
156           computation only.
157          (##) Payload phase: IP processes the plaintext (P) with hash computation + keystream
158           encryption + data XORing. It works in a similar way for ciphertext (C).
159          (##) Final phase: IP generates the authenticated tag (T) using the last block of data.
160          HAL_CRYPEx_AESCCM_GenerateAuthTAG API used in this phase to generate 4 words which correspond to the Tag.
161          user should consider only part of this 4 words, if Tag length is less than 128 bits
162 
163   *** Callback registration ***
164   =============================
165 
166   [..]
167   The compilation define  USE_HAL_CRYP_REGISTER_CALLBACKS when set to 1
168   allows the user to configure dynamically the driver callbacks.
169   Use Functions @ref HAL_CRYP_RegisterCallback() or HAL_CRYP_RegisterXXXCallback()
170   to register an interrupt callback.
171 
172   [..]
173   Function @ref HAL_CRYP_RegisterCallback() allows to register following callbacks:
174     (+) InCpltCallback     :  Input FIFO transfer completed callback.
175     (+) OutCpltCallback    : Output FIFO transfer completed callback.
176     (+) ErrorCallback      : callback for error detection.
177     (+) MspInitCallback    : CRYP MspInit.
178     (+) MspDeInitCallback  : CRYP MspDeInit.
179   This function takes as parameters the HAL peripheral handle, the Callback ID
180   and a pointer to the user callback function.
181 
182   [..]
183   Use function @ref HAL_CRYP_UnRegisterCallback() to reset a callback to the default
184   weak function.
185   @ref HAL_CRYP_UnRegisterCallback() takes as parameters the HAL peripheral handle,
186   and the Callback ID.
187   This function allows to reset following callbacks:
188     (+) InCpltCallback     :  Input FIFO transfer completed callback.
189     (+) OutCpltCallback    : Output FIFO transfer completed callback.
190     (+) ErrorCallback      : callback for error detection.
191     (+) MspInitCallback    : CRYP MspInit.
192     (+) MspDeInitCallback  : CRYP MspDeInit.
193 
194   [..]
195   By default, after the @ref HAL_CRYP_Init() and when the state is HAL_CRYP_STATE_RESET
196   all callbacks are set to the corresponding weak functions :
197   examples @ref HAL_CRYP_InCpltCallback() , @ref HAL_CRYP_OutCpltCallback().
198   Exception done for MspInit and MspDeInit functions that are
199   reset to the legacy weak function in the @ref HAL_CRYP_Init()/ @ref HAL_CRYP_DeInit() only when
200   these callbacks are null (not registered beforehand).
201   if not, MspInit or MspDeInit are not null, the @ref HAL_CRYP_Init() / @ref HAL_CRYP_DeInit()
202   keep and use the user MspInit/MspDeInit functions (registered beforehand)
203 
204   [..]
205   Callbacks can be registered/unregistered in HAL_CRYP_STATE_READY state only.
206   Exception done MspInit/MspDeInit callbacks that can be registered/unregistered
207   in HAL_CRYP_STATE_READY or HAL_CRYP_STATE_RESET state,
208   thus registered (user) MspInit/DeInit callbacks can be used during the Init/DeInit.
209   In that case first register the MspInit/MspDeInit user callbacks
210   using @ref HAL_CRYP_RegisterCallback() before calling @ref HAL_CRYP_DeInit()
211   or @ref HAL_CRYP_Init() function.
212 
213   [..]
214   When The compilation define USE_HAL_CRYP_REGISTER_CALLBACKS is set to 0 or
215   not defined, the callback registration feature is not available and all callbacks
216   are set to the corresponding weak functions.
217 
218   @endverbatim
219 
220   Table 1. Initial Counter Block (ICB)
221           +-------------------------------------------------------+
222           |       Initialization vector (IV)      |  Counter      |
223           |----------------|----------------|-----------|---------|
224          127              95                63            31       0
225 
226 
227               Bit Number    Register           Contents
228               ----------   ---------------       -----------
229               127 ...96    CRYP_IV1R[31:0]     ICB[127:96]
230               95  ...64    CRYP_IV1L[31:0]     B0[95:64]
231               63 ... 32    CRYP_IV0R[31:0]     ICB[63:32]
232               31 ... 0     CRYP_IV0L[31:0]     ICB[31:0], where 32-bit counter= 0x2
233 
234   Table 2.  GCM last block definition
235 
236           +-------------------------------------------------------------------+
237           |  Bit[0]   |  Bit[32]           |  Bit[64]  | Bit[96]              |
238           |-----------|--------------------|-----------|----------------------|
239           |   0x0     | Header length[31:0]|     0x0   | Payload length[31:0] |
240           |-----------|--------------------|-----------|----------------------|
241 
242   Table 3. B0 block
243                 Octet Number   Contents
244                 ------------   ---------
245                 0              Flags
246                 1 ... 15-q     Nonce N
247                 16-q ... 15    Q
248 
249             the Flags field is formatted as follows:
250 
251                 Bit Number   Contents
252                 ----------   ----------------------
253                 7            Reserved (always zero)
254                 6            Adata
255                 5 ... 3      (t-2)/2
256                 2 ... 0      [q-1]3
257 
258  Table 4. CTRx block
259                 Bit Number    Register           Contents
260                 ----------   ---------------       -----------
261                 127 ...96    CRYP_IV1R[31:0]     B0[127:96], where Q length bits are set to 0, except for
262                                                  bit 0 that is set to 1
263                 95  ...64    CRYP_IV1L[31:0]     B0[95:64]
264                 63 ... 32    CRYP_IV0R[31:0]     B0[63:32]
265                 31 ... 0     CRYP_IV0L[31:0]     B0[31:0], where flag bits set to 0
266   */
267 
268 /* Includes ------------------------------------------------------------------*/
269 #include "stm32h7xx_hal.h"
270 
271 /** @addtogroup STM32H7xx_HAL_Driver
272   * @{
273   */
274 
275 #if defined (CRYP)
276 
277 /** @defgroup CRYP CRYP
278   * @brief CRYP HAL module driver.
279   * @{
280   */
281 
282 
283 #ifdef HAL_CRYP_MODULE_ENABLED
284 
285 /* Private typedef -----------------------------------------------------------*/
286 /* Private define ------------------------------------------------------------*/
287 /** @addtogroup CRYP_Private_Defines
288   * @{
289   */
290 #define CRYP_TIMEOUT_KEYPREPARATION      82U         /*!<  The latency of key preparation operation is 82 clock cycles.*/
291 #define CRYP_TIMEOUT_GCMCCMINITPHASE     299U        /*!<  The latency of  GCM/CCM init phase to prepare hash subkey is 299 clock cycles.*/
292 #define CRYP_TIMEOUT_GCMCCMHEADERPHASE   290U        /*!<  The latency of  GCM/CCM header phase is 290 clock cycles.*/
293 
294 #define  CRYP_PHASE_READY                0x00000001U /*!< CRYP peripheral is ready for initialization. */
295 #define  CRYP_PHASE_PROCESS              0x00000002U /*!< CRYP peripheral is in processing phase */
296 
297 #define CRYP_PHASE_INIT                  0x00000000U             /*!< GCM/GMAC (or CCM) init phase */
298 #define CRYP_PHASE_HEADER                CRYP_CR_GCM_CCMPH_0     /*!< GCM/GMAC or CCM header phase */
299 #define CRYP_PHASE_PAYLOAD               CRYP_CR_GCM_CCMPH_1     /*!< GCM(/CCM) payload phase      */
300 #define CRYP_PHASE_FINAL                 CRYP_CR_GCM_CCMPH       /*!< GCM/GMAC or CCM  final phase */
301 #define CRYP_OPERATINGMODE_ENCRYPT       0x00000000U             /*!< Encryption mode   */
302 #define CRYP_OPERATINGMODE_DECRYPT       CRYP_CR_ALGODIR         /*!< Decryption        */
303 
304 
305 /*  CTR1 information to use in CCM algorithm */
306 #define CRYP_CCM_CTR1_0                  0x07FFFFFFU
307 #define CRYP_CCM_CTR1_1                  0xFFFFFF00U
308 #define CRYP_CCM_CTR1_2                  0x00000001U
309 
310 /**
311   * @}
312   */
313 
314 
315 /* Private macro -------------------------------------------------------------*/
316 /** @addtogroup CRYP_Private_Macros
317   * @{
318   */
319 
320 #define CRYP_SET_PHASE(__HANDLE__, __PHASE__)  do{(__HANDLE__)->Instance->CR &= (uint32_t)(~CRYP_CR_GCM_CCMPH);\
321                                                         (__HANDLE__)->Instance->CR |= (uint32_t)(__PHASE__);\
322                                                        }while(0)
323 
324 #define HAL_CRYP_FIFO_FLUSH(__HANDLE__) ((__HANDLE__)->Instance->CR |=  CRYP_CR_FFLUSH)
325 
326 
327 /**
328   * @}
329   */
330 
331 /* Private struct -------------------------------------------------------------*/
332 /* Private variables ---------------------------------------------------------*/
333 /* Private function prototypes -----------------------------------------------*/
334 /** @addtogroup CRYP_Private_Functions_prototypes
335   * @{
336   */
337 
338 static void CRYP_SetDMAConfig(CRYP_HandleTypeDef *hcryp, uint32_t inputaddr, uint16_t Size, uint32_t outputaddr);
339 static void CRYP_DMAInCplt(DMA_HandleTypeDef *hdma);
340 static void CRYP_DMAOutCplt(DMA_HandleTypeDef *hdma);
341 static void CRYP_DMAError(DMA_HandleTypeDef *hdma);
342 static void CRYP_SetKey(CRYP_HandleTypeDef *hcryp, uint32_t KeySize);
343 static void CRYP_AES_IT(CRYP_HandleTypeDef *hcryp);
344 static HAL_StatusTypeDef CRYP_GCMCCM_SetHeaderPhase(CRYP_HandleTypeDef *hcryp, uint32_t Timeout);
345 static void CRYP_GCMCCM_SetPayloadPhase_IT(CRYP_HandleTypeDef *hcryp);
346 static void CRYP_GCMCCM_SetHeaderPhase_IT(CRYP_HandleTypeDef *hcryp);
347 static HAL_StatusTypeDef CRYP_GCMCCM_SetHeaderPhase_DMA(CRYP_HandleTypeDef *hcryp);
348 #if !defined (CRYP_VER_2_2)
349 static void CRYP_Workaround(CRYP_HandleTypeDef *hcryp, uint32_t Timeout);
350 #endif /*End of not defined CRYP_VER_2_2*/
351 static HAL_StatusTypeDef CRYP_AESGCM_Process_DMA(CRYP_HandleTypeDef *hcryp);
352 static HAL_StatusTypeDef CRYP_AESGCM_Process_IT(CRYP_HandleTypeDef *hcryp);
353 static HAL_StatusTypeDef CRYP_AESGCM_Process(CRYP_HandleTypeDef *hcryp, uint32_t Timeout);
354 static HAL_StatusTypeDef CRYP_AESCCM_Process(CRYP_HandleTypeDef *hcryp, uint32_t Timeout);
355 static HAL_StatusTypeDef CRYP_AESCCM_Process_IT(CRYP_HandleTypeDef *hcryp);
356 static HAL_StatusTypeDef CRYP_AESCCM_Process_DMA(CRYP_HandleTypeDef *hcryp);
357 static void CRYP_AES_ProcessData(CRYP_HandleTypeDef *hcrypt, uint32_t Timeout);
358 static HAL_StatusTypeDef CRYP_AES_Encrypt(CRYP_HandleTypeDef *hcryp, uint32_t Timeout);
359 static HAL_StatusTypeDef CRYP_AES_Decrypt(CRYP_HandleTypeDef *hcryp, uint32_t Timeout);
360 static HAL_StatusTypeDef CRYP_AES_Decrypt_IT(CRYP_HandleTypeDef *hcryp);
361 static HAL_StatusTypeDef CRYP_AES_Encrypt_IT(CRYP_HandleTypeDef *hcryp);
362 static HAL_StatusTypeDef CRYP_AES_Decrypt_DMA(CRYP_HandleTypeDef *hcryp);
363 static void CRYP_TDES_IT(CRYP_HandleTypeDef *hcryp);
364 static HAL_StatusTypeDef CRYP_WaitOnIFEMFlag(const CRYP_HandleTypeDef *hcryp, uint32_t Timeout);
365 static HAL_StatusTypeDef CRYP_WaitOnBUSYFlag(const CRYP_HandleTypeDef *hcryp, uint32_t Timeout);
366 static HAL_StatusTypeDef CRYP_WaitOnOFNEFlag(const CRYP_HandleTypeDef *hcryp, uint32_t Timeout);
367 static HAL_StatusTypeDef CRYP_TDES_Process(CRYP_HandleTypeDef *hcryp, uint32_t Timeout);
368 
369 /**
370   * @}
371   */
372 
373 /* Exported functions ---------------------------------------------------------*/
374 
375 /** @defgroup CRYP_Exported_Functions CRYP Exported Functions
376   * @{
377   */
378 
379 
380 /** @defgroup CRYP_Exported_Functions_Group1 Initialization and de-initialization functions
381   *  @brief    CRYP  Initialization and Configuration functions.
382   *
383 @verbatim
384   ========================================================================================
385      ##### Initialization, de-initialization and Set and Get configuration functions #####
386   ========================================================================================
387     [..]  This section provides functions allowing to:
388       (+) Initialize the CRYP
389       (+) DeInitialize the CRYP
390       (+) Initialize the CRYP MSP
391       (+) DeInitialize the CRYP MSP
392       (+) configure CRYP (HAL_CRYP_SetConfig) with the specified parameters in the CRYP_ConfigTypeDef
393           Parameters which are configured in This section are :
394           (++) Key size
395           (++) Data Type : 32,16, 8 or 1bit
396           (++) AlgoMode : for CRYP1 IP
397                  ECB and CBC in DES/TDES Standard
398                  ECB,CBC,CTR,GCM/GMAC and CCM in AES Standard.
399       (+) Get CRYP configuration (HAL_CRYP_GetConfig) from the specified parameters in the CRYP_HandleTypeDef
400 
401 
402 @endverbatim
403   * @{
404   */
405 
406 
407 /**
408   * @brief  Initializes the CRYP according to the specified
409   *         parameters in the CRYP_ConfigTypeDef and creates the associated handle.
410   * @param  hcryp: pointer to a CRYP_HandleTypeDef structure that contains
411   *         the configuration information for CRYP module
412   * @retval HAL status
413   */
HAL_CRYP_Init(CRYP_HandleTypeDef * hcryp)414 HAL_StatusTypeDef HAL_CRYP_Init(CRYP_HandleTypeDef *hcryp)
415 {
416   /* Check the CRYP handle allocation */
417   if (hcryp == NULL)
418   {
419     return HAL_ERROR;
420   }
421 
422   /* Check parameters */
423   assert_param(IS_CRYP_KEYSIZE(hcryp->Init.KeySize));
424   assert_param(IS_CRYP_DATATYPE(hcryp->Init.DataType));
425   assert_param(IS_CRYP_ALGORITHM(hcryp->Init.Algorithm));
426   assert_param(IS_CRYP_INIT(hcryp->Init.KeyIVConfigSkip));
427 
428 #if (USE_HAL_CRYP_REGISTER_CALLBACKS == 1)
429   if (hcryp->State == HAL_CRYP_STATE_RESET)
430   {
431     /* Allocate lock resource and initialize it */
432     hcryp->Lock = HAL_UNLOCKED;
433 
434     hcryp->InCpltCallback  = HAL_CRYP_InCpltCallback;  /* Legacy weak  InCpltCallback  */
435     hcryp->OutCpltCallback = HAL_CRYP_OutCpltCallback; /* Legacy weak OutCpltCallback  */
436     hcryp->ErrorCallback   = HAL_CRYP_ErrorCallback;   /* Legacy weak ErrorCallback    */
437 
438     if (hcryp->MspInitCallback == NULL)
439     {
440       hcryp->MspInitCallback = HAL_CRYP_MspInit; /* Legacy weak MspInit  */
441     }
442 
443     /* Init the low level hardware */
444     hcryp->MspInitCallback(hcryp);
445   }
446 #else
447   if (hcryp->State == HAL_CRYP_STATE_RESET)
448   {
449     /* Allocate lock resource and initialize it */
450     hcryp->Lock = HAL_UNLOCKED;
451 
452     /* Init the low level hardware */
453     HAL_CRYP_MspInit(hcryp);
454   }
455 #endif /* (USE_HAL_CRYP_REGISTER_CALLBACKS) */
456 
457   /* Set the key size(This bit field is don't care in the DES or TDES modes) data type and Algorithm */
458   MODIFY_REG(hcryp->Instance->CR, CRYP_CR_DATATYPE | CRYP_CR_KEYSIZE | CRYP_CR_ALGOMODE,
459              hcryp->Init.DataType | hcryp->Init.KeySize | hcryp->Init.Algorithm);
460 #if !defined (CRYP_VER_2_2)
461   /* Read Device ID to indicate CRYP1 IP Version */
462   hcryp->Version = HAL_GetREVID();
463 #endif /*End of not defined CRYP_VER_2_2*/
464   /* Reset Error Code field */
465   hcryp->ErrorCode = HAL_CRYP_ERROR_NONE;
466 
467   /* Reset peripheral Key and IV configuration flag */
468   hcryp->KeyIVConfig = 0U;
469 
470   /* Change the CRYP state */
471   hcryp->State = HAL_CRYP_STATE_READY;
472 
473   /* Set the default CRYP phase */
474   hcryp->Phase = CRYP_PHASE_READY;
475 
476   /* Return function status */
477   return HAL_OK;
478 }
479 
480 /**
481   * @brief  De-Initializes the CRYP peripheral.
482   * @param  hcryp: pointer to a CRYP_HandleTypeDef structure that contains
483   *         the configuration information for CRYP module
484   * @retval HAL status
485   */
HAL_CRYP_DeInit(CRYP_HandleTypeDef * hcryp)486 HAL_StatusTypeDef HAL_CRYP_DeInit(CRYP_HandleTypeDef *hcryp)
487 {
488   /* Check the CRYP handle allocation */
489   if (hcryp == NULL)
490   {
491     return HAL_ERROR;
492   }
493 
494   /* Set the default CRYP phase */
495   hcryp->Phase = CRYP_PHASE_READY;
496 
497   /* Reset CrypInCount and CrypOutCount */
498   hcryp->CrypInCount = 0;
499   hcryp->CrypOutCount = 0;
500   hcryp->CrypHeaderCount = 0;
501 
502   /* Disable the CRYP peripheral clock */
503   __HAL_CRYP_DISABLE(hcryp);
504 
505 #if (USE_HAL_CRYP_REGISTER_CALLBACKS == 1)
506   if (hcryp->MspDeInitCallback == NULL)
507   {
508     hcryp->MspDeInitCallback = HAL_CRYP_MspDeInit; /* Legacy weak MspDeInit  */
509   }
510   /* DeInit the low level hardware */
511   hcryp->MspDeInitCallback(hcryp);
512 
513 #else
514   /* DeInit the low level hardware: CLOCK, NVIC.*/
515   HAL_CRYP_MspDeInit(hcryp);
516 #endif /* USE_HAL_CRYP_REGISTER_CALLBACKS */
517 
518   /* Change the CRYP state */
519   hcryp->State = HAL_CRYP_STATE_RESET;
520 
521   /* Release Lock */
522   __HAL_UNLOCK(hcryp);
523 
524   /* Return function status */
525   return HAL_OK;
526 }
527 
528 /**
529   * @brief  Configure the CRYP according to the specified
530   *         parameters in the CRYP_ConfigTypeDef
531   * @param  hcryp: pointer to a CRYP_HandleTypeDef structure
532   * @param  pConf: pointer to a CRYP_ConfigTypeDef structure that contains
533   *         the configuration information for CRYP module
534   * @retval HAL status
535   */
HAL_CRYP_SetConfig(CRYP_HandleTypeDef * hcryp,CRYP_ConfigTypeDef * pConf)536 HAL_StatusTypeDef HAL_CRYP_SetConfig(CRYP_HandleTypeDef *hcryp, CRYP_ConfigTypeDef *pConf)
537 {
538   /* Check the CRYP handle allocation */
539   if ((hcryp == NULL) || (pConf == NULL))
540   {
541     return HAL_ERROR;
542   }
543 
544   /* Check parameters */
545   assert_param(IS_CRYP_KEYSIZE(pConf->KeySize));
546   assert_param(IS_CRYP_DATATYPE(pConf->DataType));
547   assert_param(IS_CRYP_ALGORITHM(pConf->Algorithm));
548 
549   if (hcryp->State == HAL_CRYP_STATE_READY)
550   {
551     /* Change the CRYP state */
552     hcryp->State = HAL_CRYP_STATE_BUSY;
553 
554     /* Process locked */
555     __HAL_LOCK(hcryp);
556 
557     /* Set  CRYP parameters  */
558     hcryp->Init.DataType        = pConf->DataType;
559     hcryp->Init.pKey            = pConf->pKey;
560     hcryp->Init.Algorithm       = pConf->Algorithm;
561     hcryp->Init.KeySize         = pConf->KeySize;
562     hcryp->Init.pInitVect       = pConf->pInitVect;
563     hcryp->Init.Header          = pConf->Header;
564     hcryp->Init.HeaderSize      = pConf->HeaderSize;
565     hcryp->Init.B0              = pConf->B0;
566     hcryp->Init.DataWidthUnit   = pConf->DataWidthUnit;
567     hcryp->Init.HeaderWidthUnit = pConf->HeaderWidthUnit;
568     hcryp->Init.KeyIVConfigSkip = pConf->KeyIVConfigSkip;
569 
570     /* Set the key size(This bit field is don't care in the DES or TDES modes) data type, AlgoMode and operating mode*/
571     MODIFY_REG(hcryp->Instance->CR, CRYP_CR_DATATYPE | CRYP_CR_KEYSIZE | CRYP_CR_ALGOMODE,
572                hcryp->Init.DataType | hcryp->Init.KeySize | hcryp->Init.Algorithm);
573 
574     /* Process Unlocked */
575     __HAL_UNLOCK(hcryp);
576 
577     /* Reset Error Code field */
578     hcryp->ErrorCode = HAL_CRYP_ERROR_NONE;
579 
580     /* Change the CRYP state */
581     hcryp->State = HAL_CRYP_STATE_READY;
582 
583     /* Set the default CRYP phase */
584     hcryp->Phase = CRYP_PHASE_READY;
585 
586     /* Return function status */
587     return HAL_OK;
588   }
589   else
590   {
591     /* Process Unlocked */
592     __HAL_UNLOCK(hcryp);
593 
594     /* Busy error code field */
595     hcryp->ErrorCode |= HAL_CRYP_ERROR_BUSY;
596     return HAL_ERROR;
597   }
598 }
599 
600 /**
601   * @brief  Get CRYP Configuration parameters in associated handle.
602   * @param  pConf: pointer to a CRYP_ConfigTypeDef structure
603   * @param  hcryp: pointer to a CRYP_HandleTypeDef structure that contains
604   *         the configuration information for CRYP module
605   * @retval HAL status
606   */
HAL_CRYP_GetConfig(CRYP_HandleTypeDef * hcryp,CRYP_ConfigTypeDef * pConf)607 HAL_StatusTypeDef HAL_CRYP_GetConfig(CRYP_HandleTypeDef *hcryp, CRYP_ConfigTypeDef *pConf)
608 {
609   /* Check the CRYP handle allocation */
610   if ((hcryp == NULL) || (pConf == NULL))
611   {
612     return HAL_ERROR;
613   }
614 
615   if (hcryp->State == HAL_CRYP_STATE_READY)
616   {
617     /* Change the CRYP state */
618     hcryp->State = HAL_CRYP_STATE_BUSY;
619 
620     /* Process locked */
621     __HAL_LOCK(hcryp);
622 
623     /* Get  CRYP parameters  */
624     pConf->DataType        = hcryp->Init.DataType;
625     pConf->pKey            = hcryp->Init.pKey;
626     pConf->Algorithm       = hcryp->Init.Algorithm;
627     pConf->KeySize         = hcryp->Init.KeySize ;
628     pConf->pInitVect       = hcryp->Init.pInitVect;
629     pConf->Header          = hcryp->Init.Header ;
630     pConf->HeaderSize      = hcryp->Init.HeaderSize;
631     pConf->B0              = hcryp->Init.B0;
632     pConf->DataWidthUnit   = hcryp->Init.DataWidthUnit;
633     pConf->HeaderWidthUnit = hcryp->Init.HeaderWidthUnit;
634     pConf->KeyIVConfigSkip = hcryp->Init.KeyIVConfigSkip;
635 
636     /* Process Unlocked */
637     __HAL_UNLOCK(hcryp);
638 
639     /* Change the CRYP state */
640     hcryp->State = HAL_CRYP_STATE_READY;
641 
642     /* Return function status */
643     return HAL_OK;
644   }
645   else
646   {
647     /* Process Unlocked */
648     __HAL_UNLOCK(hcryp);
649 
650     /* Busy error code field */
651     hcryp->ErrorCode |= HAL_CRYP_ERROR_BUSY;
652     return HAL_ERROR;
653   }
654 }
655 /**
656   * @brief  Initializes the CRYP MSP.
657   * @param  hcryp: pointer to a CRYP_HandleTypeDef structure that contains
658   *         the configuration information for CRYP module
659   * @retval None
660   */
HAL_CRYP_MspInit(CRYP_HandleTypeDef * hcryp)661 __weak void HAL_CRYP_MspInit(CRYP_HandleTypeDef *hcryp)
662 {
663   /* Prevent unused argument(s) compilation warning */
664   UNUSED(hcryp);
665 
666   /* NOTE : This function Should not be modified, when the callback is needed,
667             the HAL_CRYP_MspInit could be implemented in the user file
668    */
669 }
670 
671 /**
672   * @brief  DeInitializes CRYP MSP.
673   * @param  hcryp: pointer to a CRYP_HandleTypeDef structure that contains
674   *         the configuration information for CRYP module
675   * @retval None
676   */
HAL_CRYP_MspDeInit(CRYP_HandleTypeDef * hcryp)677 __weak void HAL_CRYP_MspDeInit(CRYP_HandleTypeDef *hcryp)
678 {
679   /* Prevent unused argument(s) compilation warning */
680   UNUSED(hcryp);
681 
682   /* NOTE : This function Should not be modified, when the callback is needed,
683             the HAL_CRYP_MspDeInit could be implemented in the user file
684    */
685 }
686 
687 #if (USE_HAL_CRYP_REGISTER_CALLBACKS == 1)
688 /**
689   * @brief  Register a User CRYP Callback
690   *         To be used instead of the weak predefined callback
691   * @param hcryp cryp handle
692   * @param CallbackID ID of the callback to be registered
693   *        This parameter can be one of the following values:
694   *          @arg @ref HAL_CRYP_INPUT_COMPLETE_CB_ID Input FIFO transfer completed callback ID
695   *          @arg @ref HAL_CRYP_OUTPUT_COMPLETE_CB_ID Output FIFO transfer completed callback ID
696   *          @arg @ref HAL_CRYP_ERROR_CB_ID Rx Half Error callback ID
697   *          @arg @ref HAL_CRYP_MSPINIT_CB_ID MspInit callback ID
698   *          @arg @ref HAL_CRYP_MSPDEINIT_CB_ID MspDeInit callback ID
699   * @param pCallback pointer to the Callback function
700   * @retval status
701   */
HAL_CRYP_RegisterCallback(CRYP_HandleTypeDef * hcryp,HAL_CRYP_CallbackIDTypeDef CallbackID,pCRYP_CallbackTypeDef pCallback)702 HAL_StatusTypeDef HAL_CRYP_RegisterCallback(CRYP_HandleTypeDef *hcryp, HAL_CRYP_CallbackIDTypeDef CallbackID,
703                                             pCRYP_CallbackTypeDef pCallback)
704 {
705   HAL_StatusTypeDef status = HAL_OK;
706 
707   if (pCallback == NULL)
708   {
709     /* Update the error code */
710     hcryp->ErrorCode |= HAL_CRYP_ERROR_INVALID_CALLBACK;
711 
712     return HAL_ERROR;
713   }
714   /* Process locked */
715   __HAL_LOCK(hcryp);
716 
717   if (hcryp->State == HAL_CRYP_STATE_READY)
718   {
719     switch (CallbackID)
720     {
721       case HAL_CRYP_INPUT_COMPLETE_CB_ID :
722         hcryp->InCpltCallback = pCallback;
723         break;
724 
725       case HAL_CRYP_OUTPUT_COMPLETE_CB_ID :
726         hcryp->OutCpltCallback = pCallback;
727         break;
728 
729       case HAL_CRYP_ERROR_CB_ID :
730         hcryp->ErrorCallback = pCallback;
731         break;
732 
733       case HAL_CRYP_MSPINIT_CB_ID :
734         hcryp->MspInitCallback = pCallback;
735         break;
736 
737       case HAL_CRYP_MSPDEINIT_CB_ID :
738         hcryp->MspDeInitCallback = pCallback;
739         break;
740 
741       default :
742         /* Update the error code */
743         hcryp->ErrorCode |= HAL_CRYP_ERROR_INVALID_CALLBACK;
744         /* Return error status */
745         status =  HAL_ERROR;
746         break;
747     }
748   }
749   else if (hcryp->State == HAL_CRYP_STATE_RESET)
750   {
751     switch (CallbackID)
752     {
753       case HAL_CRYP_MSPINIT_CB_ID :
754         hcryp->MspInitCallback = pCallback;
755         break;
756 
757       case HAL_CRYP_MSPDEINIT_CB_ID :
758         hcryp->MspDeInitCallback = pCallback;
759         break;
760 
761       default :
762         /* Update the error code */
763         hcryp->ErrorCode |= HAL_CRYP_ERROR_INVALID_CALLBACK;
764         /* Return error status */
765         status =  HAL_ERROR;
766         break;
767     }
768   }
769   else
770   {
771     /* Update the error code */
772     hcryp->ErrorCode |= HAL_CRYP_ERROR_INVALID_CALLBACK;
773     /* Return error status */
774     status =  HAL_ERROR;
775   }
776 
777   /* Release Lock */
778   __HAL_UNLOCK(hcryp);
779 
780   return status;
781 }
782 
783 /**
784   * @brief  Unregister an CRYP Callback
785   *         CRYP callabck is redirected to the weak predefined callback
786   * @param hcryp cryp handle
787   * @param CallbackID ID of the callback to be unregistered
788   *        This parameter can be one of the following values:
789   *          @arg @ref HAL_CRYP_INPUT_COMPLETE_CB_ID Input FIFO transfer completed callback ID
790   *          @arg @ref HAL_CRYP_OUTPUT_COMPLETE_CB_ID Output FIFO transfer completed callback ID
791   *          @arg @ref HAL_CRYP_ERROR_CB_ID Rx Half Error callback ID
792   *          @arg @ref HAL_CRYP_MSPINIT_CB_ID MspInit callback ID
793   *          @arg @ref HAL_CRYP_MSPDEINIT_CB_ID MspDeInit callback ID
794   * @retval status
795   */
HAL_CRYP_UnRegisterCallback(CRYP_HandleTypeDef * hcryp,HAL_CRYP_CallbackIDTypeDef CallbackID)796 HAL_StatusTypeDef HAL_CRYP_UnRegisterCallback(CRYP_HandleTypeDef *hcryp, HAL_CRYP_CallbackIDTypeDef CallbackID)
797 {
798   HAL_StatusTypeDef status = HAL_OK;
799 
800   /* Process locked */
801   __HAL_LOCK(hcryp);
802 
803   if (hcryp->State == HAL_CRYP_STATE_READY)
804   {
805     switch (CallbackID)
806     {
807       case HAL_CRYP_INPUT_COMPLETE_CB_ID :
808         hcryp->InCpltCallback = HAL_CRYP_InCpltCallback;  /* Legacy weak  InCpltCallback  */
809         break;
810 
811       case HAL_CRYP_OUTPUT_COMPLETE_CB_ID :
812         hcryp->OutCpltCallback = HAL_CRYP_OutCpltCallback;         /* Legacy weak OutCpltCallback       */
813         break;
814 
815       case HAL_CRYP_ERROR_CB_ID :
816         hcryp->ErrorCallback = HAL_CRYP_ErrorCallback;           /* Legacy weak ErrorCallback        */
817         break;
818 
819       case HAL_CRYP_MSPINIT_CB_ID :
820         hcryp->MspInitCallback = HAL_CRYP_MspInit;
821         break;
822 
823       case HAL_CRYP_MSPDEINIT_CB_ID :
824         hcryp->MspDeInitCallback = HAL_CRYP_MspDeInit;
825         break;
826 
827       default :
828         /* Update the error code */
829         hcryp->ErrorCode |= HAL_CRYP_ERROR_INVALID_CALLBACK;
830         /* Return error status */
831         status =  HAL_ERROR;
832         break;
833     }
834   }
835   else if (hcryp->State == HAL_CRYP_STATE_RESET)
836   {
837     switch (CallbackID)
838     {
839       case HAL_CRYP_MSPINIT_CB_ID :
840         hcryp->MspInitCallback = HAL_CRYP_MspInit;
841         break;
842 
843       case HAL_CRYP_MSPDEINIT_CB_ID :
844         hcryp->MspDeInitCallback = HAL_CRYP_MspDeInit;
845         break;
846 
847       default :
848         /* Update the error code */
849         hcryp->ErrorCode |= HAL_CRYP_ERROR_INVALID_CALLBACK;
850         /* Return error status */
851         status =  HAL_ERROR;
852         break;
853     }
854   }
855   else
856   {
857     /* Update the error code */
858     hcryp->ErrorCode |= HAL_CRYP_ERROR_INVALID_CALLBACK;;
859     /* Return error status */
860     status =  HAL_ERROR;
861   }
862 
863   /* Release Lock */
864   __HAL_UNLOCK(hcryp);
865 
866   return status;
867 }
868 #endif /* USE_HAL_UART_REGISTER_CALLBACKS */
869 
870 /**
871   * @}
872   */
873 
874 /** @defgroup CRYP_Exported_Functions_Group2  Encrypt Decrypt functions
875   *  @brief   CRYP processing functions.
876   *
877 @verbatim
878   ==============================================================================
879                       ##### Encrypt Decrypt  functions #####
880   ==============================================================================
881     [..]  This section provides API allowing to Encrypt/Decrypt Data following
882           Standard DES/TDES or AES, and Algorithm configured by the user:
883       (+) Standard DES/TDES only supported by CRYP1 IP, below list of Algorithm supported :
884            (++)  Electronic Code Book(ECB)
885            (++) Cipher Block Chaining (CBC)
886       (+) Standard AES  supported by CRYP1 IP , list of Algorithm supported:
887            (++) Electronic Code Book(ECB)
888            (++) Cipher Block Chaining (CBC)
889            (++) Counter mode (CTR)
890            (++) Cipher Block Chaining (CBC)
891            (++) Counter mode (CTR)
892            (++) Galois/counter mode (GCM)
893            (++) Counter with Cipher Block Chaining-Message(CCM)
894     [..]  Three processing functions are available:
895       (+) Polling mode : HAL_CRYP_Encrypt & HAL_CRYP_Decrypt
896       (+) Interrupt mode : HAL_CRYP_Encrypt_IT & HAL_CRYP_Decrypt_IT
897       (+) DMA mode : HAL_CRYP_Encrypt_DMA & HAL_CRYP_Decrypt_DMA
898 
899 @endverbatim
900   * @{
901   */
902 
903 
904 /**
905   * @brief  Encryption mode.
906   * @param  hcryp: pointer to a CRYP_HandleTypeDef structure that contains
907   *         the configuration information for CRYP module
908   * @param  Input: Pointer to the input buffer (plaintext)
909   * @param  Size: Length of the plaintext buffer either in word or in byte, according to DataWidthUnit.
910   * @param  Output: Pointer to the output buffer(ciphertext)
911   * @param  Timeout: Specify Timeout value
912   * @retval HAL status
913   */
HAL_CRYP_Encrypt(CRYP_HandleTypeDef * hcryp,uint32_t * Input,uint16_t Size,uint32_t * Output,uint32_t Timeout)914 HAL_StatusTypeDef HAL_CRYP_Encrypt(CRYP_HandleTypeDef *hcryp, uint32_t *Input, uint16_t Size, uint32_t *Output,
915                                    uint32_t Timeout)
916 {
917   uint32_t algo;
918   HAL_StatusTypeDef status;
919 
920   if (hcryp->State == HAL_CRYP_STATE_READY)
921   {
922     /* Change state Busy */
923     hcryp->State = HAL_CRYP_STATE_BUSY;
924 
925     /* Process locked */
926     __HAL_LOCK(hcryp);
927 
928     /*  Reset CrypInCount, CrypOutCount and Initialize pCrypInBuffPtr, pCrypOutBuffPtr and Size parameters*/
929     hcryp->CrypInCount = 0U;
930     hcryp->CrypOutCount = 0U;
931     hcryp->pCrypInBuffPtr = Input;
932     hcryp->pCrypOutBuffPtr = Output;
933 
934     /*  Calculate Size parameter in Byte*/
935     if (hcryp->Init.DataWidthUnit == CRYP_DATAWIDTHUNIT_WORD)
936     {
937       hcryp->Size = Size * 4U;
938     }
939     else
940     {
941       hcryp->Size = Size;
942     }
943 
944     /* Set Encryption operating mode*/
945     MODIFY_REG(hcryp->Instance->CR, CRYP_CR_ALGODIR, CRYP_OPERATINGMODE_ENCRYPT);
946 
947     /* algo get algorithm selected */
948     algo = hcryp->Instance->CR & CRYP_CR_ALGOMODE;
949 
950     switch (algo)
951     {
952       case CRYP_DES_ECB:
953       case CRYP_DES_CBC:
954       case CRYP_TDES_ECB:
955       case CRYP_TDES_CBC:
956 
957         /*Set Key */
958         hcryp->Instance->K1LR = *(uint32_t *)(hcryp->Init.pKey);
959         hcryp->Instance->K1RR = *(uint32_t *)(hcryp->Init.pKey + 1);
960         if ((hcryp->Init.Algorithm == CRYP_TDES_ECB) || (hcryp->Init.Algorithm == CRYP_TDES_CBC))
961         {
962           hcryp->Instance->K2LR = *(uint32_t *)(hcryp->Init.pKey + 2);
963           hcryp->Instance->K2RR = *(uint32_t *)(hcryp->Init.pKey + 3);
964           hcryp->Instance->K3LR = *(uint32_t *)(hcryp->Init.pKey + 4);
965           hcryp->Instance->K3RR = *(uint32_t *)(hcryp->Init.pKey + 5);
966         }
967 
968         /*Set Initialization Vector (IV)*/
969         if ((hcryp->Init.Algorithm == CRYP_DES_CBC) || (hcryp->Init.Algorithm == CRYP_TDES_CBC))
970         {
971           hcryp->Instance->IV0LR = *(uint32_t *)(hcryp->Init.pInitVect);
972           hcryp->Instance->IV0RR = *(uint32_t *)(hcryp->Init.pInitVect + 1);
973         }
974 
975         /* Flush FIFO */
976         HAL_CRYP_FIFO_FLUSH(hcryp);
977 
978         /* Set the phase */
979         hcryp->Phase = CRYP_PHASE_PROCESS;
980 
981         /* Start DES/TDES encryption process */
982         status = CRYP_TDES_Process(hcryp, Timeout);
983         break;
984 
985       case CRYP_AES_ECB:
986       case CRYP_AES_CBC:
987       case CRYP_AES_CTR:
988 
989         /* AES encryption */
990         status = CRYP_AES_Encrypt(hcryp, Timeout);
991         break;
992 
993       case CRYP_AES_GCM:
994 
995         /* AES GCM encryption */
996         status = CRYP_AESGCM_Process(hcryp, Timeout);
997         break;
998 
999       case CRYP_AES_CCM:
1000 
1001         /* AES CCM encryption */
1002         status = CRYP_AESCCM_Process(hcryp, Timeout);
1003         break;
1004 
1005       default:
1006         hcryp->ErrorCode |= HAL_CRYP_ERROR_NOT_SUPPORTED;
1007         status = HAL_ERROR;
1008         break;
1009     }
1010 
1011     if (status == HAL_OK)
1012     {
1013       /* Change the CRYP peripheral state */
1014       hcryp->State = HAL_CRYP_STATE_READY;
1015 
1016       /* Process unlocked */
1017       __HAL_UNLOCK(hcryp);
1018     }
1019   }
1020   else
1021   {
1022     /* Process unlocked */
1023     __HAL_UNLOCK(hcryp);
1024 
1025     /* Busy error code field */
1026     hcryp->ErrorCode |= HAL_CRYP_ERROR_BUSY;
1027     status = HAL_ERROR;
1028   }
1029 
1030   /* Return function status */
1031   return status ;
1032 }
1033 
1034 /**
1035   * @brief  Decryption mode.
1036   * @param  hcryp: pointer to a CRYP_HandleTypeDef structure that contains
1037   *         the configuration information for CRYP module
1038   * @param  Input: Pointer to the input buffer (ciphertext )
1039   * @param  Size: Length of the plaintext buffer either in word or in byte, according to DataWidthUnit
1040   * @param  Output: Pointer to the output buffer(plaintext)
1041   * @param  Timeout: Specify Timeout value
1042   * @retval HAL status
1043   */
HAL_CRYP_Decrypt(CRYP_HandleTypeDef * hcryp,uint32_t * Input,uint16_t Size,uint32_t * Output,uint32_t Timeout)1044 HAL_StatusTypeDef HAL_CRYP_Decrypt(CRYP_HandleTypeDef *hcryp, uint32_t *Input, uint16_t Size, uint32_t *Output,
1045                                    uint32_t Timeout)
1046 {
1047   HAL_StatusTypeDef status;
1048   uint32_t algo;
1049 
1050   if (hcryp->State == HAL_CRYP_STATE_READY)
1051   {
1052     /* Change state Busy */
1053     hcryp->State = HAL_CRYP_STATE_BUSY;
1054 
1055     /* Process locked */
1056     __HAL_LOCK(hcryp);
1057 
1058     /*  Reset CrypInCount, CrypOutCount and Initialize pCrypInBuffPtr, pCrypOutBuffPtr and Size parameters*/
1059     hcryp->CrypInCount = 0U;
1060     hcryp->CrypOutCount = 0U;
1061     hcryp->pCrypInBuffPtr = Input;
1062     hcryp->pCrypOutBuffPtr = Output;
1063 
1064     /*  Calculate Size parameter in Byte*/
1065     if (hcryp->Init.DataWidthUnit == CRYP_DATAWIDTHUNIT_WORD)
1066     {
1067       hcryp->Size = Size * 4U;
1068     }
1069     else
1070     {
1071       hcryp->Size = Size;
1072     }
1073 
1074     /* Set Decryption operating mode*/
1075     MODIFY_REG(hcryp->Instance->CR, CRYP_CR_ALGODIR, CRYP_OPERATINGMODE_DECRYPT);
1076 
1077     /* algo get algorithm selected */
1078     algo = hcryp->Instance->CR & CRYP_CR_ALGOMODE;
1079 
1080     switch (algo)
1081     {
1082       case CRYP_DES_ECB:
1083       case CRYP_DES_CBC:
1084       case CRYP_TDES_ECB:
1085       case CRYP_TDES_CBC:
1086 
1087         /*Set Key */
1088         hcryp->Instance->K1LR = *(uint32_t *)(hcryp->Init.pKey);
1089         hcryp->Instance->K1RR = *(uint32_t *)(hcryp->Init.pKey + 1);
1090         if ((hcryp->Init.Algorithm == CRYP_TDES_ECB) || (hcryp->Init.Algorithm == CRYP_TDES_CBC))
1091         {
1092           hcryp->Instance->K2LR = *(uint32_t *)(hcryp->Init.pKey + 2);
1093           hcryp->Instance->K2RR = *(uint32_t *)(hcryp->Init.pKey + 3);
1094           hcryp->Instance->K3LR = *(uint32_t *)(hcryp->Init.pKey + 4);
1095           hcryp->Instance->K3RR = *(uint32_t *)(hcryp->Init.pKey + 5);
1096         }
1097 
1098         /*Set Initialization Vector (IV)*/
1099         if ((hcryp->Init.Algorithm == CRYP_DES_CBC) || (hcryp->Init.Algorithm == CRYP_TDES_CBC))
1100         {
1101           hcryp->Instance->IV0LR = *(uint32_t *)(hcryp->Init.pInitVect);
1102           hcryp->Instance->IV0RR = *(uint32_t *)(hcryp->Init.pInitVect + 1);
1103         }
1104 
1105         /* Flush FIFO */
1106         HAL_CRYP_FIFO_FLUSH(hcryp);
1107 
1108         /* Set the phase */
1109         hcryp->Phase = CRYP_PHASE_PROCESS;
1110 
1111         /* Start DES/TDES decryption process */
1112         status = CRYP_TDES_Process(hcryp, Timeout);
1113 
1114         break;
1115 
1116       case CRYP_AES_ECB:
1117       case CRYP_AES_CBC:
1118       case CRYP_AES_CTR:
1119 
1120         /* AES decryption */
1121         status = CRYP_AES_Decrypt(hcryp, Timeout);
1122         break;
1123 
1124       case CRYP_AES_GCM:
1125 
1126         /* AES GCM decryption */
1127         status = CRYP_AESGCM_Process(hcryp, Timeout) ;
1128         break;
1129 
1130       case CRYP_AES_CCM:
1131 
1132         /* AES CCM decryption */
1133         status = CRYP_AESCCM_Process(hcryp, Timeout);
1134         break;
1135 
1136       default:
1137         hcryp->ErrorCode |= HAL_CRYP_ERROR_NOT_SUPPORTED;
1138         status = HAL_ERROR;
1139         break;
1140     }
1141 
1142     if (status == HAL_OK)
1143     {
1144       /* Change the CRYP peripheral state */
1145       hcryp->State = HAL_CRYP_STATE_READY;
1146 
1147       /* Process unlocked */
1148       __HAL_UNLOCK(hcryp);
1149     }
1150   }
1151   else
1152   {
1153     /* Process unlocked */
1154     __HAL_UNLOCK(hcryp);
1155 
1156     /* Busy error code field */
1157     hcryp->ErrorCode |= HAL_CRYP_ERROR_BUSY;
1158     status = HAL_ERROR;
1159   }
1160 
1161   /* Return function status */
1162   return status;
1163 }
1164 
1165 /**
1166   * @brief  Encryption in interrupt mode.
1167   * @param  hcryp: pointer to a CRYP_HandleTypeDef structure that contains
1168   *         the configuration information for CRYP module
1169   * @param  Input: Pointer to the input buffer (plaintext)
1170   * @param  Size: Length of the plaintext buffer either in word or in byte, according to DataWidthUnit
1171   * @param  Output: Pointer to the output buffer(ciphertext)
1172   * @retval HAL status
1173   */
HAL_CRYP_Encrypt_IT(CRYP_HandleTypeDef * hcryp,uint32_t * Input,uint16_t Size,uint32_t * Output)1174 HAL_StatusTypeDef HAL_CRYP_Encrypt_IT(CRYP_HandleTypeDef *hcryp, uint32_t *Input, uint16_t Size, uint32_t *Output)
1175 {
1176   uint32_t algo;
1177   HAL_StatusTypeDef status;
1178 
1179   if (hcryp->State == HAL_CRYP_STATE_READY)
1180   {
1181     /* Change state Busy */
1182     hcryp->State = HAL_CRYP_STATE_BUSY;
1183 
1184     /* Process locked */
1185     __HAL_LOCK(hcryp);
1186 
1187     /*  Reset CrypInCount, CrypOutCount and Initialize pCrypInBuffPtr, pCrypOutBuffPtr and Size parameters*/
1188     hcryp->CrypInCount = 0U;
1189     hcryp->CrypOutCount = 0U;
1190     hcryp->pCrypInBuffPtr = Input;
1191     hcryp->pCrypOutBuffPtr = Output;
1192 
1193     /*  Calculate Size parameter in Byte*/
1194     if (hcryp->Init.DataWidthUnit == CRYP_DATAWIDTHUNIT_WORD)
1195     {
1196       hcryp->Size = Size * 4U;
1197     }
1198     else
1199     {
1200       hcryp->Size = Size;
1201     }
1202 
1203     /* Set encryption operating mode*/
1204     MODIFY_REG(hcryp->Instance->CR, CRYP_CR_ALGODIR, CRYP_OPERATINGMODE_ENCRYPT);
1205 
1206     /* algo get algorithm selected */
1207     algo = (hcryp->Instance->CR & CRYP_CR_ALGOMODE);
1208 
1209     switch (algo)
1210     {
1211       case CRYP_DES_ECB:
1212       case CRYP_DES_CBC:
1213       case CRYP_TDES_ECB:
1214       case CRYP_TDES_CBC:
1215 
1216         /*Set Key */
1217         hcryp->Instance->K1LR = *(uint32_t *)(hcryp->Init.pKey);
1218         hcryp->Instance->K1RR = *(uint32_t *)(hcryp->Init.pKey + 1);
1219         if ((hcryp->Init.Algorithm == CRYP_TDES_ECB) || (hcryp->Init.Algorithm == CRYP_TDES_CBC))
1220         {
1221           hcryp->Instance->K2LR = *(uint32_t *)(hcryp->Init.pKey + 2);
1222           hcryp->Instance->K2RR = *(uint32_t *)(hcryp->Init.pKey + 3);
1223           hcryp->Instance->K3LR = *(uint32_t *)(hcryp->Init.pKey + 4);
1224           hcryp->Instance->K3RR = *(uint32_t *)(hcryp->Init.pKey + 5);
1225         }
1226         /* Set the Initialization Vector*/
1227         if ((hcryp->Init.Algorithm == CRYP_DES_CBC) || (hcryp->Init.Algorithm == CRYP_TDES_CBC))
1228         {
1229           hcryp->Instance->IV0LR = *(uint32_t *)(hcryp->Init.pInitVect);
1230           hcryp->Instance->IV0RR = *(uint32_t *)(hcryp->Init.pInitVect + 1);
1231         }
1232 
1233         /* Flush FIFO */
1234         HAL_CRYP_FIFO_FLUSH(hcryp);
1235 
1236         /* Set the phase */
1237         hcryp->Phase = CRYP_PHASE_PROCESS;
1238 
1239         /* Enable interrupts */
1240         __HAL_CRYP_ENABLE_IT(hcryp, CRYP_IT_INI | CRYP_IT_OUTI);
1241 
1242         /* Enable CRYP to start DES/TDES process*/
1243         __HAL_CRYP_ENABLE(hcryp);
1244 
1245         status = HAL_OK;
1246         break;
1247 
1248       case CRYP_AES_ECB:
1249       case CRYP_AES_CBC:
1250       case CRYP_AES_CTR:
1251 
1252         status = CRYP_AES_Encrypt_IT(hcryp);
1253         break;
1254 
1255       case CRYP_AES_GCM:
1256 
1257         status = CRYP_AESGCM_Process_IT(hcryp) ;
1258         break;
1259 
1260       case CRYP_AES_CCM:
1261 
1262         status = CRYP_AESCCM_Process_IT(hcryp);
1263         break;
1264 
1265       default:
1266         hcryp->ErrorCode |= HAL_CRYP_ERROR_NOT_SUPPORTED;
1267         status =  HAL_ERROR;
1268         break;
1269     }
1270   }
1271   else
1272   {
1273     /* Busy error code field */
1274     hcryp->ErrorCode |= HAL_CRYP_ERROR_BUSY;
1275     status =  HAL_ERROR;
1276   }
1277 
1278   /* Return function status */
1279   return status ;
1280 }
1281 
1282 /**
1283   * @brief  Decryption in itnterrupt mode.
1284   * @param  hcryp: pointer to a CRYP_HandleTypeDef structure that contains
1285   *         the configuration information for CRYP module
1286   * @param  Input: Pointer to the input buffer (ciphertext )
1287   * @param  Size: Length of the plaintext buffer either in word or in byte, according to DataWidthUnit
1288   * @param  Output: Pointer to the output buffer(plaintext)
1289   * @retval HAL status
1290   */
HAL_CRYP_Decrypt_IT(CRYP_HandleTypeDef * hcryp,uint32_t * Input,uint16_t Size,uint32_t * Output)1291 HAL_StatusTypeDef HAL_CRYP_Decrypt_IT(CRYP_HandleTypeDef *hcryp, uint32_t *Input, uint16_t Size, uint32_t *Output)
1292 {
1293   uint32_t algo;
1294   HAL_StatusTypeDef status = HAL_OK;
1295 
1296   if (hcryp->State == HAL_CRYP_STATE_READY)
1297   {
1298     /* Change state Busy */
1299     hcryp->State = HAL_CRYP_STATE_BUSY;
1300 
1301     /* Process locked */
1302     __HAL_LOCK(hcryp);
1303 
1304     /*  Reset CrypInCount, CrypOutCount and Initialize pCrypInBuffPtr, pCrypOutBuffPtr and Size parameters*/
1305     hcryp->CrypInCount = 0U;
1306     hcryp->CrypOutCount = 0U;
1307     hcryp->pCrypInBuffPtr = Input;
1308     hcryp->pCrypOutBuffPtr = Output;
1309 
1310     /*  Calculate Size parameter in Byte*/
1311     if (hcryp->Init.DataWidthUnit == CRYP_DATAWIDTHUNIT_WORD)
1312     {
1313       hcryp->Size = Size * 4U;
1314     }
1315     else
1316     {
1317       hcryp->Size = Size;
1318     }
1319 
1320     /* Set decryption operating mode*/
1321     MODIFY_REG(hcryp->Instance->CR, CRYP_CR_ALGODIR, CRYP_OPERATINGMODE_DECRYPT);
1322 
1323     /* algo get algorithm selected */
1324     algo = hcryp->Instance->CR & CRYP_CR_ALGOMODE;
1325 
1326     switch (algo)
1327     {
1328       case CRYP_DES_ECB:
1329       case CRYP_DES_CBC:
1330       case CRYP_TDES_ECB:
1331       case CRYP_TDES_CBC:
1332 
1333         /*Set Key */
1334         hcryp->Instance->K1LR = *(uint32_t *)(hcryp->Init.pKey);
1335         hcryp->Instance->K1RR = *(uint32_t *)(hcryp->Init.pKey + 1);
1336         if ((hcryp->Init.Algorithm == CRYP_TDES_ECB) || (hcryp->Init.Algorithm == CRYP_TDES_CBC))
1337         {
1338           hcryp->Instance->K2LR = *(uint32_t *)(hcryp->Init.pKey + 2);
1339           hcryp->Instance->K2RR = *(uint32_t *)(hcryp->Init.pKey + 3);
1340           hcryp->Instance->K3LR = *(uint32_t *)(hcryp->Init.pKey + 4);
1341           hcryp->Instance->K3RR = *(uint32_t *)(hcryp->Init.pKey + 5);
1342         }
1343 
1344         /* Set the Initialization Vector*/
1345         if ((hcryp->Init.Algorithm == CRYP_DES_CBC) || (hcryp->Init.Algorithm == CRYP_TDES_CBC))
1346         {
1347           hcryp->Instance->IV0LR = *(uint32_t *)(hcryp->Init.pInitVect);
1348           hcryp->Instance->IV0RR = *(uint32_t *)(hcryp->Init.pInitVect + 1);
1349         }
1350         /* Flush FIFO */
1351         HAL_CRYP_FIFO_FLUSH(hcryp);
1352 
1353         /* Set the phase */
1354         hcryp->Phase = CRYP_PHASE_PROCESS;
1355 
1356         /* Enable interrupts */
1357         __HAL_CRYP_ENABLE_IT(hcryp, CRYP_IT_INI | CRYP_IT_OUTI);
1358 
1359         /* Enable CRYP and start DES/TDES process*/
1360         __HAL_CRYP_ENABLE(hcryp);
1361 
1362         break;
1363 
1364       case CRYP_AES_ECB:
1365       case CRYP_AES_CBC:
1366       case CRYP_AES_CTR:
1367 
1368         /* AES decryption */
1369         status = CRYP_AES_Decrypt_IT(hcryp);
1370         break;
1371 
1372       case CRYP_AES_GCM:
1373 
1374         /* AES GCM decryption */
1375         status = CRYP_AESGCM_Process_IT(hcryp) ;
1376         break;
1377 
1378       case CRYP_AES_CCM:
1379 
1380         /* AES CCMdecryption */
1381         status = CRYP_AESCCM_Process_IT(hcryp);
1382         break;
1383 
1384       default:
1385         hcryp->ErrorCode |= HAL_CRYP_ERROR_NOT_SUPPORTED;
1386         status = HAL_ERROR;
1387         break;
1388     }
1389   }
1390   else
1391   {
1392     /* Busy error code field */
1393     hcryp->ErrorCode |= HAL_CRYP_ERROR_BUSY;
1394     status = HAL_ERROR;
1395   }
1396 
1397   /* Return function status */
1398   return status;
1399 }
1400 
1401 /**
1402   * @brief  Encryption in DMA mode.
1403   * @param  hcryp: pointer to a CRYP_HandleTypeDef structure that contains
1404   *         the configuration information for CRYP module
1405   * @param  Input: Pointer to the input buffer (plaintext)
1406   * @param  Size: Length of the plaintext buffer either in word or in byte, according to DataWidthUnit
1407   * @param  Output: Pointer to the output buffer(ciphertext)
1408   * @retval HAL status
1409   */
HAL_CRYP_Encrypt_DMA(CRYP_HandleTypeDef * hcryp,uint32_t * Input,uint16_t Size,uint32_t * Output)1410 HAL_StatusTypeDef HAL_CRYP_Encrypt_DMA(CRYP_HandleTypeDef *hcryp, uint32_t *Input, uint16_t Size, uint32_t *Output)
1411 {
1412   HAL_StatusTypeDef status = HAL_OK;
1413   uint32_t algo;
1414   uint32_t DoKeyIVConfig = 1U; /* By default, carry out peripheral Key and IV configuration */
1415 
1416   if (hcryp->State == HAL_CRYP_STATE_READY)
1417   {
1418     /* Change state Busy */
1419     hcryp->State = HAL_CRYP_STATE_BUSY;
1420 
1421     /* Process locked */
1422     __HAL_LOCK(hcryp);
1423 
1424     /*  Reset CrypInCount, CrypOutCount and Initialize pCrypInBuffPtr, pCrypOutBuffPtr and Size parameters*/
1425     hcryp->CrypInCount = 0U;
1426     hcryp->CrypOutCount = 0U;
1427     hcryp->pCrypInBuffPtr = Input;
1428     hcryp->pCrypOutBuffPtr = Output;
1429 
1430     /*  Calculate Size parameter in Byte*/
1431     if (hcryp->Init.DataWidthUnit == CRYP_DATAWIDTHUNIT_WORD)
1432     {
1433       hcryp->Size = Size * 4U;
1434     }
1435     else
1436     {
1437       hcryp->Size = Size;
1438     }
1439 
1440     /* Set encryption operating mode*/
1441     MODIFY_REG(hcryp->Instance->CR, CRYP_CR_ALGODIR, CRYP_OPERATINGMODE_ENCRYPT);
1442 
1443     /* algo get algorithm selected */
1444     algo = hcryp->Instance->CR & CRYP_CR_ALGOMODE;
1445 
1446     switch (algo)
1447     {
1448       case CRYP_DES_ECB:
1449       case CRYP_DES_CBC:
1450       case CRYP_TDES_ECB:
1451       case CRYP_TDES_CBC:
1452 
1453         /*Set Key */
1454         hcryp->Instance->K1LR = *(uint32_t *)(hcryp->Init.pKey);
1455         hcryp->Instance->K1RR = *(uint32_t *)(hcryp->Init.pKey + 1);
1456         if ((hcryp->Init.Algorithm == CRYP_TDES_ECB) || (hcryp->Init.Algorithm == CRYP_TDES_CBC))
1457         {
1458           hcryp->Instance->K2LR = *(uint32_t *)(hcryp->Init.pKey + 2);
1459           hcryp->Instance->K2RR = *(uint32_t *)(hcryp->Init.pKey + 3);
1460           hcryp->Instance->K3LR = *(uint32_t *)(hcryp->Init.pKey + 4);
1461           hcryp->Instance->K3RR = *(uint32_t *)(hcryp->Init.pKey + 5);
1462         }
1463 
1464         /* Set the Initialization Vector*/
1465         if ((hcryp->Init.Algorithm == CRYP_DES_CBC) || (hcryp->Init.Algorithm == CRYP_TDES_CBC))
1466         {
1467           hcryp->Instance->IV0LR = *(uint32_t *)(hcryp->Init.pInitVect);
1468           hcryp->Instance->IV0RR = *(uint32_t *)(hcryp->Init.pInitVect + 1);
1469         }
1470 
1471         /* Flush FIFO */
1472         HAL_CRYP_FIFO_FLUSH(hcryp);
1473 
1474         /* Set the phase */
1475         hcryp->Phase = CRYP_PHASE_PROCESS;
1476 
1477         /* Start DMA process transfer for DES/TDES */
1478         CRYP_SetDMAConfig(hcryp, (uint32_t)(hcryp->pCrypInBuffPtr), (hcryp->Size / 4U),
1479                           (uint32_t)(hcryp->pCrypOutBuffPtr));
1480 
1481         break;
1482 
1483       case CRYP_AES_ECB:
1484       case CRYP_AES_CBC:
1485       case CRYP_AES_CTR:
1486 
1487         if (hcryp->Init.KeyIVConfigSkip == CRYP_KEYIVCONFIG_ONCE)
1488         {
1489           if (hcryp->KeyIVConfig == 1U)
1490           {
1491             /* If the Key and IV configuration has to be done only once
1492                and if it has already been done, skip it */
1493             DoKeyIVConfig = 0U;
1494           }
1495           else
1496           {
1497             /* If the Key and IV configuration has to be done only once
1498                and if it has not been done already, do it and set KeyIVConfig
1499                to keep track it won't have to be done again next time */
1500             hcryp->KeyIVConfig = 1U;
1501           }
1502         }
1503 
1504         if (DoKeyIVConfig == 1U)
1505         {
1506           /*  Set the Key*/
1507           CRYP_SetKey(hcryp, hcryp->Init.KeySize);
1508 
1509           /* Set the Initialization Vector*/
1510           if (hcryp->Init.Algorithm != CRYP_AES_ECB)
1511           {
1512             hcryp->Instance->IV0LR = *(uint32_t *)(hcryp->Init.pInitVect);
1513             hcryp->Instance->IV0RR = *(uint32_t *)(hcryp->Init.pInitVect + 1U);
1514             hcryp->Instance->IV1LR = *(uint32_t *)(hcryp->Init.pInitVect + 2U);
1515             hcryp->Instance->IV1RR = *(uint32_t *)(hcryp->Init.pInitVect + 3U);
1516           }
1517         } /* if (DoKeyIVConfig == 1U) */
1518 
1519         /* Set the phase */
1520         hcryp->Phase = CRYP_PHASE_PROCESS;
1521 
1522         /* Start DMA process transfer for AES */
1523         CRYP_SetDMAConfig(hcryp, (uint32_t)(hcryp->pCrypInBuffPtr), (hcryp->Size / 4U),
1524                           (uint32_t)(hcryp->pCrypOutBuffPtr));
1525         break;
1526 
1527       case CRYP_AES_GCM:
1528 
1529         /* AES GCM encryption */
1530         status = CRYP_AESGCM_Process_DMA(hcryp) ;
1531         break;
1532 
1533       case CRYP_AES_CCM:
1534 
1535         /* AES CCM encryption */
1536         status = CRYP_AESCCM_Process_DMA(hcryp);
1537         break;
1538 
1539       default:
1540         hcryp->ErrorCode |= HAL_CRYP_ERROR_NOT_SUPPORTED;
1541         status =  HAL_ERROR;
1542         break;
1543     }
1544   }
1545   else
1546   {
1547     /* Busy error code field */
1548     hcryp->ErrorCode |= HAL_CRYP_ERROR_BUSY;
1549     status =  HAL_ERROR;
1550   }
1551 
1552   /* Return function status */
1553   return status;
1554 }
1555 
1556 /**
1557   * @brief  Decryption in DMA mode.
1558   * @param  hcryp: pointer to a CRYP_HandleTypeDef structure that contains
1559   *         the configuration information for CRYP module
1560   * @param  Input: Pointer to the input buffer (ciphertext )
1561   * @param  Size: Length of the plaintext buffer either in word or in byte, according to DataWidthUnit
1562   * @param  Output: Pointer to the output buffer(plaintext)
1563   * @retval HAL status
1564   */
HAL_CRYP_Decrypt_DMA(CRYP_HandleTypeDef * hcryp,uint32_t * Input,uint16_t Size,uint32_t * Output)1565 HAL_StatusTypeDef HAL_CRYP_Decrypt_DMA(CRYP_HandleTypeDef *hcryp, uint32_t *Input, uint16_t Size, uint32_t *Output)
1566 {
1567   uint32_t algo;
1568   HAL_StatusTypeDef status = HAL_OK;
1569 
1570   if (hcryp->State == HAL_CRYP_STATE_READY)
1571   {
1572     /* Change state Busy */
1573     hcryp->State = HAL_CRYP_STATE_BUSY;
1574 
1575     /* Process locked */
1576     __HAL_LOCK(hcryp);
1577 
1578     /*  Reset CrypInCount, CrypOutCount and Initialize pCrypInBuffPtr, pCrypOutBuffPtr and Size parameters*/
1579     hcryp->CrypInCount = 0U;
1580     hcryp->CrypOutCount = 0U;
1581     hcryp->pCrypInBuffPtr = Input;
1582     hcryp->pCrypOutBuffPtr = Output;
1583 
1584     /*  Calculate Size parameter in Byte*/
1585     if (hcryp->Init.DataWidthUnit == CRYP_DATAWIDTHUNIT_WORD)
1586     {
1587       hcryp->Size = Size * 4U;
1588     }
1589     else
1590     {
1591       hcryp->Size = Size;
1592     }
1593 
1594     /* Set decryption operating mode*/
1595     MODIFY_REG(hcryp->Instance->CR, CRYP_CR_ALGODIR, CRYP_OPERATINGMODE_DECRYPT);
1596 
1597     /* algo get algorithm selected */
1598     algo = hcryp->Instance->CR & CRYP_CR_ALGOMODE;
1599 
1600     switch (algo)
1601     {
1602       case CRYP_DES_ECB:
1603       case CRYP_DES_CBC:
1604       case CRYP_TDES_ECB:
1605       case CRYP_TDES_CBC:
1606 
1607         /*Set Key */
1608         hcryp->Instance->K1LR = *(uint32_t *)(hcryp->Init.pKey);
1609         hcryp->Instance->K1RR = *(uint32_t *)(hcryp->Init.pKey + 1);
1610         if ((hcryp->Init.Algorithm == CRYP_TDES_ECB) || (hcryp->Init.Algorithm == CRYP_TDES_CBC))
1611         {
1612           hcryp->Instance->K2LR = *(uint32_t *)(hcryp->Init.pKey + 2);
1613           hcryp->Instance->K2RR = *(uint32_t *)(hcryp->Init.pKey + 3);
1614           hcryp->Instance->K3LR = *(uint32_t *)(hcryp->Init.pKey + 4);
1615           hcryp->Instance->K3RR = *(uint32_t *)(hcryp->Init.pKey + 5);
1616         }
1617 
1618         /* Set the Initialization Vector*/
1619         if ((hcryp->Init.Algorithm == CRYP_DES_CBC) || (hcryp->Init.Algorithm == CRYP_TDES_CBC))
1620         {
1621           hcryp->Instance->IV0LR = *(uint32_t *)(hcryp->Init.pInitVect);
1622           hcryp->Instance->IV0RR = *(uint32_t *)(hcryp->Init.pInitVect + 1);
1623         }
1624 
1625         /* Flush FIFO */
1626         HAL_CRYP_FIFO_FLUSH(hcryp);
1627 
1628         /* Set the phase */
1629         hcryp->Phase = CRYP_PHASE_PROCESS;
1630 
1631         /* Start DMA process transfer for DES/TDES */
1632         CRYP_SetDMAConfig(hcryp, (uint32_t)(hcryp->pCrypInBuffPtr), (hcryp->Size / 4U),
1633                           (uint32_t)(hcryp->pCrypOutBuffPtr));
1634         break;
1635 
1636       case CRYP_AES_ECB:
1637       case CRYP_AES_CBC:
1638       case CRYP_AES_CTR:
1639 
1640         /* AES decryption */
1641         status = CRYP_AES_Decrypt_DMA(hcryp);
1642         break;
1643 
1644       case CRYP_AES_GCM:
1645 
1646         /* AES GCM decryption */
1647         status = CRYP_AESGCM_Process_DMA(hcryp) ;
1648 
1649         break;
1650 
1651       case CRYP_AES_CCM:
1652 
1653         /* AES CCM decryption */
1654         status = CRYP_AESCCM_Process_DMA(hcryp);
1655         break;
1656 
1657       default:
1658         hcryp->ErrorCode |= HAL_CRYP_ERROR_NOT_SUPPORTED;
1659         status =  HAL_ERROR;
1660         break;
1661     }
1662   }
1663   else
1664   {
1665     /* Busy error code field */
1666     hcryp->ErrorCode |= HAL_CRYP_ERROR_BUSY;
1667     status = HAL_ERROR;
1668   }
1669 
1670   /* Return function status */
1671   return status;
1672 }
1673 
1674 /**
1675   * @}
1676   */
1677 
1678 /** @defgroup CRYP_Exported_Functions_Group3 CRYP IRQ handler management
1679   *  @brief    CRYP IRQ handler.
1680   *
1681 @verbatim
1682   ==============================================================================
1683                 ##### CRYP IRQ handler management #####
1684   ==============================================================================
1685 [..]  This section provides CRYP IRQ handler and callback functions.
1686       (+) HAL_CRYP_IRQHandler CRYP interrupt request
1687       (+) HAL_CRYP_InCpltCallback input data transfer complete callback
1688       (+) HAL_CRYP_OutCpltCallback output data transfer complete callback
1689       (+) HAL_CRYP_ErrorCallback  CRYP error callback
1690       (+) HAL_CRYP_GetState return the CRYP state
1691       (+) HAL_CRYP_GetError return the CRYP error code
1692 @endverbatim
1693   * @{
1694   */
1695 
1696 /**
1697   * @brief  This function handles cryptographic interrupt request.
1698   * @param  hcryp: pointer to a CRYP_HandleTypeDef structure that contains
1699   *         the configuration information for CRYP module
1700   * @retval None
1701   */
HAL_CRYP_IRQHandler(CRYP_HandleTypeDef * hcryp)1702 void HAL_CRYP_IRQHandler(CRYP_HandleTypeDef *hcryp)
1703 {
1704   uint32_t itstatus = hcryp->Instance->MISR;
1705 
1706   if ((itstatus & (CRYP_IT_INI | CRYP_IT_OUTI)) != 0U)
1707   {
1708     if ((hcryp->Init.Algorithm == CRYP_DES_ECB) || (hcryp->Init.Algorithm == CRYP_DES_CBC) ||
1709         (hcryp->Init.Algorithm == CRYP_TDES_ECB) || (hcryp->Init.Algorithm == CRYP_TDES_CBC))
1710     {
1711       CRYP_TDES_IT(hcryp); /* DES or TDES*/
1712     }
1713     else if ((hcryp->Init.Algorithm == CRYP_AES_ECB) || (hcryp->Init.Algorithm == CRYP_AES_CBC) ||
1714              (hcryp->Init.Algorithm == CRYP_AES_CTR))
1715     {
1716       CRYP_AES_IT(hcryp); /*AES*/
1717     }
1718 
1719     else if ((hcryp->Init.Algorithm == CRYP_AES_GCM) || (hcryp->Init.Algorithm == CRYP_CR_ALGOMODE_AES_CCM))
1720     {
1721       /* if header phase */
1722       if ((hcryp->Instance->CR & CRYP_PHASE_HEADER) == CRYP_PHASE_HEADER)
1723       {
1724         CRYP_GCMCCM_SetHeaderPhase_IT(hcryp);
1725       }
1726       else  /* if payload phase */
1727       {
1728         CRYP_GCMCCM_SetPayloadPhase_IT(hcryp);
1729       }
1730     }
1731     else
1732     {
1733       /* Nothing to do */
1734     }
1735   }
1736 }
1737 
1738 /**
1739   * @brief  Return the CRYP error code.
1740   * @param  hcryp : pointer to a CRYP_HandleTypeDef structure that contains
1741   *                 the configuration information for the  CRYP IP
1742   * @retval CRYP error code
1743   */
HAL_CRYP_GetError(CRYP_HandleTypeDef * hcryp)1744 uint32_t HAL_CRYP_GetError(CRYP_HandleTypeDef *hcryp)
1745 {
1746   return hcryp->ErrorCode;
1747 }
1748 
1749 /**
1750   * @brief  Returns the CRYP state.
1751   * @param  hcryp: pointer to a CRYP_HandleTypeDef structure that contains
1752   *         the configuration information for CRYP module.
1753   * @retval HAL state
1754   */
HAL_CRYP_GetState(CRYP_HandleTypeDef * hcryp)1755 HAL_CRYP_STATETypeDef HAL_CRYP_GetState(CRYP_HandleTypeDef *hcryp)
1756 {
1757   return hcryp->State;
1758 }
1759 
1760 /**
1761   * @brief  Input FIFO transfer completed callback.
1762   * @param  hcryp: pointer to a CRYP_HandleTypeDef structure that contains
1763   *         the configuration information for CRYP module.
1764   * @retval None
1765   */
HAL_CRYP_InCpltCallback(CRYP_HandleTypeDef * hcryp)1766 __weak void HAL_CRYP_InCpltCallback(CRYP_HandleTypeDef *hcryp)
1767 {
1768   /* Prevent unused argument(s) compilation warning */
1769   UNUSED(hcryp);
1770 
1771   /* NOTE : This function Should not be modified, when the callback is needed,
1772             the HAL_CRYP_InCpltCallback could be implemented in the user file
1773    */
1774 }
1775 
1776 /**
1777   * @brief  Output FIFO transfer completed callback.
1778   * @param  hcryp: pointer to a CRYP_HandleTypeDef structure that contains
1779   *         the configuration information for CRYP module.
1780   * @retval None
1781   */
HAL_CRYP_OutCpltCallback(CRYP_HandleTypeDef * hcryp)1782 __weak void HAL_CRYP_OutCpltCallback(CRYP_HandleTypeDef *hcryp)
1783 {
1784   /* Prevent unused argument(s) compilation warning */
1785   UNUSED(hcryp);
1786 
1787   /* NOTE : This function Should not be modified, when the callback is needed,
1788             the HAL_CRYP_OutCpltCallback could be implemented in the user file
1789    */
1790 }
1791 
1792 /**
1793   * @brief  CRYP error callback.
1794   * @param  hcryp: pointer to a CRYP_HandleTypeDef structure that contains
1795   *         the configuration information for CRYP module.
1796   * @retval None
1797   */
HAL_CRYP_ErrorCallback(CRYP_HandleTypeDef * hcryp)1798 __weak void HAL_CRYP_ErrorCallback(CRYP_HandleTypeDef *hcryp)
1799 {
1800   /* Prevent unused argument(s) compilation warning */
1801   UNUSED(hcryp);
1802 
1803   /* NOTE : This function Should not be modified, when the callback is needed,
1804             the HAL_CRYP_ErrorCallback could be implemented in the user file
1805    */
1806 }
1807 /**
1808   * @}
1809   */
1810 
1811 /* Private functions ---------------------------------------------------------*/
1812 /** @addtogroup CRYP_Private_Functions
1813   * @{
1814   */
1815 
1816 /**
1817   * @brief  Encryption in ECB/CBC Algorithm with DES/TDES standard.
1818   * @param  hcryp: pointer to a CRYP_HandleTypeDef structure that contains
1819   *         the configuration information for CRYP module
1820   * @param  Timeout: Timeout value
1821   * @retval HAL status
1822   */
CRYP_TDES_Process(CRYP_HandleTypeDef * hcryp,uint32_t Timeout)1823 static HAL_StatusTypeDef CRYP_TDES_Process(CRYP_HandleTypeDef *hcryp, uint32_t Timeout)
1824 {
1825 
1826   uint32_t temp;  /* Temporary CrypOutBuff */
1827   uint16_t incount; /* Temporary CrypInCount Value */
1828   uint16_t outcount;  /* Temporary CrypOutCount Value */
1829 
1830   /* Enable CRYP */
1831   __HAL_CRYP_ENABLE(hcryp);
1832   /*Temporary CrypOutCount Value*/
1833   outcount = hcryp->CrypOutCount;
1834 
1835   /*Start processing*/
1836   while ((hcryp->CrypInCount < (hcryp->Size / 4U)) && (outcount < (hcryp->Size / 4U)))
1837   {
1838     /* Temporary CrypInCount Value */
1839     incount = hcryp->CrypInCount;
1840     /* Write plain data and get cipher data */
1841     if (((hcryp->Instance->SR & CRYP_FLAG_IFNF) != 0x0U) && (incount < (hcryp->Size / 4U)))
1842     {
1843       /* Write the input block in the IN FIFO */
1844       hcryp->Instance->DIN  = *(uint32_t *)(hcryp->pCrypInBuffPtr + hcryp->CrypInCount);
1845       hcryp->CrypInCount++;
1846       hcryp->Instance->DIN  = *(uint32_t *)(hcryp->pCrypInBuffPtr + hcryp->CrypInCount);
1847       hcryp->CrypInCount++;
1848     }
1849 
1850     /* Wait for OFNE flag to be raised */
1851     if (CRYP_WaitOnOFNEFlag(hcryp, Timeout) != HAL_OK)
1852     {
1853       /* Disable the CRYP peripheral clock */
1854       __HAL_CRYP_DISABLE(hcryp);
1855 
1856       /* Change state & errorCode*/
1857       hcryp->ErrorCode |= HAL_CRYP_ERROR_TIMEOUT;
1858       hcryp->State = HAL_CRYP_STATE_READY;
1859 
1860       /* Process unlocked */
1861       __HAL_UNLOCK(hcryp);
1862 #if (USE_HAL_CRYP_REGISTER_CALLBACKS == 1)
1863       /*Call registered error callback*/
1864       hcryp->ErrorCallback(hcryp);
1865 #else
1866       /*Call legacy weak error callback*/
1867       HAL_CRYP_ErrorCallback(hcryp);
1868 #endif /* USE_HAL_CRYP_REGISTER_CALLBACKS */
1869     }
1870 
1871     /*Temporary CrypOutCount Value*/
1872     outcount = hcryp->CrypOutCount;
1873 
1874     if (((hcryp->Instance->SR & CRYP_FLAG_OFNE) != 0x0U) && (outcount < (hcryp->Size / 4U)))
1875     {
1876       /* Read the output block from the Output FIFO and put them in temporary Buffer
1877        then get CrypOutBuff from temporary buffer  */
1878       temp = hcryp->Instance->DOUT;
1879       *(uint32_t *)(hcryp->pCrypOutBuffPtr + (hcryp->CrypOutCount)) = temp;
1880       hcryp->CrypOutCount++;
1881       temp = hcryp->Instance->DOUT;
1882       *(uint32_t *)(hcryp->pCrypOutBuffPtr + (hcryp->CrypOutCount)) = temp;
1883       hcryp->CrypOutCount++;
1884     }
1885     /*Temporary CrypOutCount Value*/
1886     outcount = hcryp->CrypOutCount;
1887   }
1888   /* Disable CRYP */
1889   __HAL_CRYP_DISABLE(hcryp);
1890   /* Change the CRYP state */
1891   hcryp->State = HAL_CRYP_STATE_READY;
1892 
1893   /* Return function status */
1894   return HAL_OK;
1895 }
1896 
1897 /**
1898   * @brief  CRYP block input/output data handling under interruption with DES/TDES standard.
1899   * @note   The function is called under interruption only, once
1900   *         interruptions have been enabled by CRYP_Decrypt_IT() and CRYP_Encrypt_IT().
1901   * @param  hcryp: pointer to a CRYP_HandleTypeDef structure that contains
1902   *         the configuration information for CRYP module.
1903   * @retval HAL status
1904   */
CRYP_TDES_IT(CRYP_HandleTypeDef * hcryp)1905 static void CRYP_TDES_IT(CRYP_HandleTypeDef *hcryp)
1906 {
1907   uint32_t temp;  /* Temporary CrypOutBuff */
1908 
1909   if (hcryp->State == HAL_CRYP_STATE_BUSY)
1910   {
1911     if (__HAL_CRYP_GET_IT(hcryp, CRYP_IT_INI) != 0x0U)
1912     {
1913       if (__HAL_CRYP_GET_FLAG(hcryp, CRYP_FLAG_INRIS) != 0x0U)
1914       {
1915         /* Write input block in the IN FIFO */
1916         hcryp->Instance->DIN = *(uint32_t *)(hcryp->pCrypInBuffPtr + hcryp->CrypInCount);
1917         hcryp->CrypInCount++;
1918         hcryp->Instance->DIN = *(uint32_t *)(hcryp->pCrypInBuffPtr + hcryp->CrypInCount);
1919         hcryp->CrypInCount++;
1920 
1921         if (hcryp->CrypInCount == (hcryp->Size / 4U))
1922         {
1923           /* Disable interruption */
1924           __HAL_CRYP_DISABLE_IT(hcryp, CRYP_IT_INI);
1925 
1926           /* Call the input data transfer complete callback */
1927 #if (USE_HAL_CRYP_REGISTER_CALLBACKS == 1)
1928           /*Call registered Input complete callback*/
1929           hcryp->InCpltCallback(hcryp);
1930 #else
1931           /*Call legacy weak Input complete callback*/
1932           HAL_CRYP_InCpltCallback(hcryp);
1933 #endif /* USE_HAL_CRYP_REGISTER_CALLBACKS */
1934         }
1935       }
1936     }
1937 
1938     if (__HAL_CRYP_GET_IT(hcryp, CRYP_IT_OUTI) != 0x0U)
1939     {
1940       if (__HAL_CRYP_GET_FLAG(hcryp, CRYP_FLAG_OUTRIS) != 0x0U)
1941       {
1942         /* Read the output block from the Output FIFO and put them in temporary Buffer
1943          then get CrypOutBuff from temporary buffer  */
1944         temp = hcryp->Instance->DOUT;
1945         *(uint32_t *)(hcryp->pCrypOutBuffPtr + (hcryp->CrypOutCount)) = temp;
1946         hcryp->CrypOutCount++;
1947         temp = hcryp->Instance->DOUT;
1948         *(uint32_t *)(hcryp->pCrypOutBuffPtr + (hcryp->CrypOutCount)) = temp;
1949         hcryp->CrypOutCount++;
1950         if (hcryp->CrypOutCount == (hcryp->Size / 4U))
1951         {
1952           /* Disable interruption */
1953           __HAL_CRYP_DISABLE_IT(hcryp, CRYP_IT_OUTI);
1954 
1955           /* Disable CRYP */
1956           __HAL_CRYP_DISABLE(hcryp);
1957 
1958           /* Process unlocked */
1959           __HAL_UNLOCK(hcryp);
1960 
1961           /* Change the CRYP state */
1962           hcryp->State = HAL_CRYP_STATE_READY;
1963 
1964           /* Call output transfer complete callback */
1965 #if (USE_HAL_CRYP_REGISTER_CALLBACKS == 1)
1966           /*Call registered Output complete callback*/
1967           hcryp->OutCpltCallback(hcryp);
1968 #else
1969           /*Call legacy weak Output complete callback*/
1970           HAL_CRYP_OutCpltCallback(hcryp);
1971 #endif /* USE_HAL_CRYP_REGISTER_CALLBACKS */
1972 
1973         }
1974       }
1975     }
1976   }
1977   else
1978   {
1979     /* Process unlocked */
1980     __HAL_UNLOCK(hcryp);
1981     /* Busy error code field */
1982     hcryp->ErrorCode |= HAL_CRYP_ERROR_BUSY;
1983 #if (USE_HAL_CRYP_REGISTER_CALLBACKS == 1)
1984     /*Call registered error callback*/
1985     hcryp->ErrorCallback(hcryp);
1986 #else
1987     /*Call legacy weak error callback*/
1988     HAL_CRYP_ErrorCallback(hcryp);
1989 #endif /* USE_HAL_CRYP_REGISTER_CALLBACKS */
1990   }
1991 }
1992 
1993 /**
1994   * @brief  Encryption in ECB/CBC & CTR Algorithm with AES Standard
1995   * @param  hcryp: pointer to a CRYP_HandleTypeDef structure
1996   * @param  Timeout: specify Timeout value
1997   * @retval HAL status
1998   */
CRYP_AES_Encrypt(CRYP_HandleTypeDef * hcryp,uint32_t Timeout)1999 static HAL_StatusTypeDef CRYP_AES_Encrypt(CRYP_HandleTypeDef *hcryp, uint32_t Timeout)
2000 {
2001   uint16_t outcount;  /* Temporary CrypOutCount Value */
2002   uint32_t DoKeyIVConfig = 1U; /* By default, carry out peripheral Key and IV configuration */
2003 
2004   if (hcryp->Init.KeyIVConfigSkip == CRYP_KEYIVCONFIG_ONCE)
2005   {
2006     if (hcryp->KeyIVConfig == 1U)
2007     {
2008       /* If the Key and IV configuration has to be done only once
2009          and if it has already been done, skip it */
2010       DoKeyIVConfig = 0U;
2011     }
2012     else
2013     {
2014       /* If the Key and IV configuration has to be done only once
2015          and if it has not been done already, do it and set KeyIVConfig
2016          to keep track it won't have to be done again next time */
2017       hcryp->KeyIVConfig = 1U;
2018     }
2019   }
2020 
2021   if (DoKeyIVConfig == 1U)
2022   {
2023     /*  Set the Key*/
2024     CRYP_SetKey(hcryp, hcryp->Init.KeySize);
2025 
2026     if (hcryp->Init.Algorithm != CRYP_AES_ECB)
2027     {
2028       /* Set the Initialization Vector*/
2029       hcryp->Instance->IV0LR = *(uint32_t *)(hcryp->Init.pInitVect);
2030       hcryp->Instance->IV0RR = *(uint32_t *)(hcryp->Init.pInitVect + 1U);
2031       hcryp->Instance->IV1LR = *(uint32_t *)(hcryp->Init.pInitVect + 2U);
2032       hcryp->Instance->IV1RR = *(uint32_t *)(hcryp->Init.pInitVect + 3U);
2033     }
2034   } /* if (DoKeyIVConfig == 1U) */
2035 
2036   /* Set the phase */
2037   hcryp->Phase = CRYP_PHASE_PROCESS;
2038 
2039   /* Enable CRYP */
2040   __HAL_CRYP_ENABLE(hcryp);
2041   /*Temporary CrypOutCount Value*/
2042   outcount = hcryp->CrypOutCount;
2043 
2044   while ((hcryp->CrypInCount < (hcryp->Size / 4U)) && (outcount < (hcryp->Size / 4U)))
2045   {
2046     /* Write plain Ddta and get cipher data */
2047     CRYP_AES_ProcessData(hcryp, Timeout);
2048     /*Temporary CrypOutCount Value*/
2049     outcount = hcryp->CrypOutCount;
2050   }
2051 
2052   /* Disable CRYP */
2053   __HAL_CRYP_DISABLE(hcryp);
2054 
2055   /* Change the CRYP state */
2056   hcryp->State = HAL_CRYP_STATE_READY;
2057 
2058   /* Return function status */
2059   return HAL_OK;
2060 }
2061 
2062 /**
2063   * @brief  Encryption in ECB/CBC & CTR mode with AES Standard using interrupt mode
2064   * @param  hcryp: pointer to a CRYP_HandleTypeDef structure that contains
2065   *         the configuration information for CRYP module
2066   * @retval HAL status
2067   */
CRYP_AES_Encrypt_IT(CRYP_HandleTypeDef * hcryp)2068 static HAL_StatusTypeDef CRYP_AES_Encrypt_IT(CRYP_HandleTypeDef *hcryp)
2069 {
2070   uint32_t DoKeyIVConfig = 1U; /* By default, carry out peripheral Key and IV configuration */
2071 
2072   if (hcryp->Init.KeyIVConfigSkip == CRYP_KEYIVCONFIG_ONCE)
2073   {
2074     if (hcryp->KeyIVConfig == 1U)
2075     {
2076       /* If the Key and IV configuration has to be done only once
2077          and if it has already been done, skip it */
2078       DoKeyIVConfig = 0U;
2079     }
2080     else
2081     {
2082       /* If the Key and IV configuration has to be done only once
2083          and if it has not been done already, do it and set KeyIVConfig
2084          to keep track it won't have to be done again next time */
2085       hcryp->KeyIVConfig = 1U;
2086     }
2087   }
2088 
2089   if (DoKeyIVConfig == 1U)
2090   {
2091     /*  Set the Key*/
2092     CRYP_SetKey(hcryp, hcryp->Init.KeySize);
2093 
2094     if (hcryp->Init.Algorithm != CRYP_AES_ECB)
2095     {
2096       /* Set the Initialization Vector*/
2097       hcryp->Instance->IV0LR = *(uint32_t *)(hcryp->Init.pInitVect);
2098       hcryp->Instance->IV0RR = *(uint32_t *)(hcryp->Init.pInitVect + 1U);
2099       hcryp->Instance->IV1LR = *(uint32_t *)(hcryp->Init.pInitVect + 2U);
2100       hcryp->Instance->IV1RR = *(uint32_t *)(hcryp->Init.pInitVect + 3U);
2101     }
2102   } /* if (DoKeyIVConfig == 1U) */
2103 
2104   /* Set the phase */
2105   hcryp->Phase = CRYP_PHASE_PROCESS;
2106 
2107   if (hcryp->Size != 0U)
2108   {
2109     /* Enable interrupts */
2110     __HAL_CRYP_ENABLE_IT(hcryp, CRYP_IT_INI | CRYP_IT_OUTI);
2111 
2112     /* Enable CRYP */
2113     __HAL_CRYP_ENABLE(hcryp);
2114   }
2115   else
2116   {
2117     /* Change the CRYP state */
2118     hcryp->State = HAL_CRYP_STATE_READY;
2119 
2120     /* Process unlocked */
2121     __HAL_UNLOCK(hcryp);
2122   }
2123 
2124   /* Return function status */
2125   return HAL_OK;
2126 }
2127 
2128 /**
2129   * @brief  Decryption in ECB/CBC & CTR mode with AES Standard
2130   * @param  hcryp: pointer to a CRYP_HandleTypeDef structure
2131   * @param  Timeout: Specify Timeout value
2132   * @retval HAL status
2133   */
CRYP_AES_Decrypt(CRYP_HandleTypeDef * hcryp,uint32_t Timeout)2134 static HAL_StatusTypeDef CRYP_AES_Decrypt(CRYP_HandleTypeDef *hcryp, uint32_t Timeout)
2135 {
2136   uint16_t outcount;  /* Temporary CrypOutCount Value */
2137   uint32_t DoKeyIVConfig = 1U; /* By default, carry out peripheral Key and IV configuration */
2138 
2139   if (hcryp->Init.KeyIVConfigSkip == CRYP_KEYIVCONFIG_ONCE)
2140   {
2141     if (hcryp->KeyIVConfig == 1U)
2142     {
2143       /* If the Key and IV configuration has to be done only once
2144          and if it has already been done, skip it */
2145       DoKeyIVConfig = 0U;
2146     }
2147     else
2148     {
2149       /* If the Key and IV configuration has to be done only once
2150          and if it has not been done already, do it and set KeyIVConfig
2151          to keep track it won't have to be done again next time */
2152       hcryp->KeyIVConfig = 1U;
2153     }
2154   }
2155 
2156   if (DoKeyIVConfig == 1U)
2157   {
2158     /*  Key preparation for ECB/CBC */
2159     if (hcryp->Init.Algorithm != CRYP_AES_CTR)   /*ECB or CBC*/
2160     {
2161       /* change ALGOMODE to key preparation for decryption*/
2162       MODIFY_REG(hcryp->Instance->CR, CRYP_CR_ALGOMODE, CRYP_CR_ALGOMODE_AES_KEY);
2163 
2164       /*  Set the Key*/
2165       CRYP_SetKey(hcryp, hcryp->Init.KeySize);
2166 
2167       /* Enable CRYP */
2168       __HAL_CRYP_ENABLE(hcryp);
2169 
2170       /* Wait for BUSY flag to be raised */
2171       if (CRYP_WaitOnBUSYFlag(hcryp, Timeout) != HAL_OK)
2172       {
2173         /* Disable the CRYP peripheral clock */
2174         __HAL_CRYP_DISABLE(hcryp);
2175 
2176         /* Change state */
2177         hcryp->ErrorCode |= HAL_CRYP_ERROR_TIMEOUT;
2178         hcryp->State = HAL_CRYP_STATE_READY;
2179 
2180         /* Process unlocked */
2181         __HAL_UNLOCK(hcryp);
2182         return HAL_ERROR;
2183       }
2184       /* Turn back to ALGOMODE of the configuration */
2185       MODIFY_REG(hcryp->Instance->CR, CRYP_CR_ALGOMODE, hcryp->Init.Algorithm);
2186     }
2187     else  /*Algorithm CTR */
2188     {
2189       /*  Set the Key*/
2190       CRYP_SetKey(hcryp, hcryp->Init.KeySize);
2191     }
2192 
2193     /* Set IV */
2194     if (hcryp->Init.Algorithm != CRYP_AES_ECB)
2195     {
2196       /* Set the Initialization Vector*/
2197       hcryp->Instance->IV0LR = *(uint32_t *)(hcryp->Init.pInitVect);
2198       hcryp->Instance->IV0RR = *(uint32_t *)(hcryp->Init.pInitVect + 1);
2199       hcryp->Instance->IV1LR = *(uint32_t *)(hcryp->Init.pInitVect + 2);
2200       hcryp->Instance->IV1RR = *(uint32_t *)(hcryp->Init.pInitVect + 3);
2201     }
2202   } /* if (DoKeyIVConfig == 1U) */
2203 
2204   /* Set the phase */
2205   hcryp->Phase = CRYP_PHASE_PROCESS;
2206 
2207   /* Enable CRYP */
2208   __HAL_CRYP_ENABLE(hcryp);
2209 
2210   /*Temporary CrypOutCount Value*/
2211   outcount = hcryp->CrypOutCount;
2212 
2213   while ((hcryp->CrypInCount < (hcryp->Size / 4U)) && (outcount < (hcryp->Size / 4U)))
2214   {
2215     /* Write plain data and get cipher data */
2216     CRYP_AES_ProcessData(hcryp, Timeout);
2217     /*Temporary CrypOutCount Value*/
2218     outcount = hcryp->CrypOutCount;
2219   }
2220 
2221   /* Disable CRYP */
2222   __HAL_CRYP_DISABLE(hcryp);
2223 
2224   /* Change the CRYP state */
2225   hcryp->State = HAL_CRYP_STATE_READY;
2226 
2227   /* Return function status */
2228   return HAL_OK;
2229 }
2230 /**
2231   * @brief  Decryption in ECB/CBC & CTR mode with AES Standard using interrupt mode
2232   * @param  hcryp: pointer to a CRYP_HandleTypeDef structure that contains
2233   *         the configuration information for CRYP module
2234   * @retval HAL status
2235   */
CRYP_AES_Decrypt_IT(CRYP_HandleTypeDef * hcryp)2236 static HAL_StatusTypeDef CRYP_AES_Decrypt_IT(CRYP_HandleTypeDef *hcryp)
2237 {
2238   __IO uint32_t count = 0U;
2239   uint32_t DoKeyIVConfig = 1U; /* By default, carry out peripheral Key and IV configuration */
2240 
2241   if (hcryp->Init.KeyIVConfigSkip == CRYP_KEYIVCONFIG_ONCE)
2242   {
2243     if (hcryp->KeyIVConfig == 1U)
2244     {
2245       /* If the Key and IV configuration has to be done only once
2246          and if it has already been done, skip it */
2247       DoKeyIVConfig = 0U;
2248     }
2249     else
2250     {
2251       /* If the Key and IV configuration has to be done only once
2252          and if it has not been done already, do it and set KeyIVConfig
2253          to keep track it won't have to be done again next time */
2254       hcryp->KeyIVConfig = 1U;
2255     }
2256   }
2257 
2258   if (DoKeyIVConfig == 1U)
2259   {
2260     /*  Key preparation for ECB/CBC */
2261     if (hcryp->Init.Algorithm != CRYP_AES_CTR)
2262     {
2263       /* change ALGOMODE to key preparation for decryption*/
2264       MODIFY_REG(hcryp->Instance->CR, CRYP_CR_ALGOMODE, CRYP_CR_ALGOMODE_AES_KEY);
2265 
2266       /*  Set the Key*/
2267       CRYP_SetKey(hcryp, hcryp->Init.KeySize);
2268 
2269       /* Enable CRYP */
2270       __HAL_CRYP_ENABLE(hcryp);
2271 
2272       /* Wait for BUSY flag to be raised */
2273       count = CRYP_TIMEOUT_KEYPREPARATION;
2274       do
2275       {
2276         count-- ;
2277         if (count == 0U)
2278         {
2279           /* Change state */
2280           hcryp->ErrorCode |= HAL_CRYP_ERROR_TIMEOUT;
2281           hcryp->State = HAL_CRYP_STATE_READY;
2282 
2283           /* Process unlocked */
2284           __HAL_UNLOCK(hcryp);
2285           return HAL_ERROR;
2286         }
2287       } while (HAL_IS_BIT_SET(hcryp->Instance->SR, CRYP_FLAG_BUSY));
2288 
2289       /* Turn back to ALGOMODE of the configuration */
2290       MODIFY_REG(hcryp->Instance->CR, CRYP_CR_ALGOMODE, hcryp->Init.Algorithm);
2291     }
2292     else  /*Algorithm CTR */
2293     {
2294       /*  Set the Key*/
2295       CRYP_SetKey(hcryp, hcryp->Init.KeySize);
2296     }
2297 
2298     /* Set IV */
2299     if (hcryp->Init.Algorithm != CRYP_AES_ECB)
2300     {
2301       /* Set the Initialization Vector*/
2302       hcryp->Instance->IV0LR = *(uint32_t *)(hcryp->Init.pInitVect);
2303       hcryp->Instance->IV0RR = *(uint32_t *)(hcryp->Init.pInitVect + 1);
2304       hcryp->Instance->IV1LR = *(uint32_t *)(hcryp->Init.pInitVect + 2);
2305       hcryp->Instance->IV1RR = *(uint32_t *)(hcryp->Init.pInitVect + 3);
2306     }
2307   } /* if (DoKeyIVConfig == 1U) */
2308 
2309   /* Set the phase */
2310   hcryp->Phase = CRYP_PHASE_PROCESS;
2311   if (hcryp->Size != 0U)
2312   {
2313     /* Enable interrupts */
2314     __HAL_CRYP_ENABLE_IT(hcryp, CRYP_IT_INI | CRYP_IT_OUTI);
2315 
2316     /* Enable CRYP */
2317     __HAL_CRYP_ENABLE(hcryp);
2318   }
2319   else
2320   {
2321     /* Process locked */
2322     __HAL_UNLOCK(hcryp);
2323 
2324     /* Change the CRYP state */
2325     hcryp->State = HAL_CRYP_STATE_READY;
2326   }
2327   /* Return function status */
2328   return HAL_OK;
2329 }
2330 /**
2331   * @brief  Decryption in ECB/CBC & CTR mode with AES Standard using DMA mode
2332   * @param  hcryp: pointer to a CRYP_HandleTypeDef structure that contains
2333   *         the configuration information for CRYP module
2334   * @retval HAL status
2335   */
CRYP_AES_Decrypt_DMA(CRYP_HandleTypeDef * hcryp)2336 static HAL_StatusTypeDef CRYP_AES_Decrypt_DMA(CRYP_HandleTypeDef *hcryp)
2337 {
2338   __IO uint32_t count = 0U;
2339   uint32_t DoKeyIVConfig = 1U; /* By default, carry out peripheral Key and IV configuration */
2340 
2341   if (hcryp->Init.KeyIVConfigSkip == CRYP_KEYIVCONFIG_ONCE)
2342   {
2343     if (hcryp->KeyIVConfig == 1U)
2344     {
2345       /* If the Key and IV configuration has to be done only once
2346          and if it has already been done, skip it */
2347       DoKeyIVConfig = 0U;
2348     }
2349     else
2350     {
2351       /* If the Key and IV configuration has to be done only once
2352          and if it has not been done already, do it and set KeyIVConfig
2353          to keep track it won't have to be done again next time */
2354       hcryp->KeyIVConfig = 1U;
2355     }
2356   }
2357 
2358   if (DoKeyIVConfig == 1U)
2359   {
2360     /*  Key preparation for ECB/CBC */
2361     if (hcryp->Init.Algorithm != CRYP_AES_CTR)
2362     {
2363       /* change ALGOMODE to key preparation for decryption*/
2364       MODIFY_REG(hcryp->Instance->CR, CRYP_CR_ALGOMODE, CRYP_CR_ALGOMODE_AES_KEY);
2365 
2366       /*  Set the Key*/
2367       CRYP_SetKey(hcryp, hcryp->Init.KeySize);
2368 
2369       /* Enable CRYP */
2370       __HAL_CRYP_ENABLE(hcryp);
2371 
2372       /* Wait for BUSY flag to be raised */
2373       count = CRYP_TIMEOUT_KEYPREPARATION;
2374       do
2375       {
2376         count-- ;
2377         if (count == 0U)
2378         {
2379           /* Disable the CRYP peripheral clock */
2380           __HAL_CRYP_DISABLE(hcryp);
2381 
2382           /* Change state */
2383           hcryp->ErrorCode |= HAL_CRYP_ERROR_TIMEOUT;
2384           hcryp->State = HAL_CRYP_STATE_READY;
2385 
2386           /* Process unlocked */
2387           __HAL_UNLOCK(hcryp);
2388           return HAL_ERROR;
2389         }
2390       } while (HAL_IS_BIT_SET(hcryp->Instance->SR, CRYP_FLAG_BUSY));
2391 
2392       /* Turn back to ALGOMODE of the configuration */
2393       MODIFY_REG(hcryp->Instance->CR, CRYP_CR_ALGOMODE, hcryp->Init.Algorithm);
2394     }
2395     else  /*Algorithm CTR */
2396     {
2397       /*  Set the Key*/
2398       CRYP_SetKey(hcryp, hcryp->Init.KeySize);
2399     }
2400 
2401     if (hcryp->Init.Algorithm != CRYP_AES_ECB)
2402     {
2403       /* Set the Initialization Vector*/
2404       hcryp->Instance->IV0LR = *(uint32_t *)(hcryp->Init.pInitVect);
2405       hcryp->Instance->IV0RR = *(uint32_t *)(hcryp->Init.pInitVect + 1);
2406       hcryp->Instance->IV1LR = *(uint32_t *)(hcryp->Init.pInitVect + 2);
2407       hcryp->Instance->IV1RR = *(uint32_t *)(hcryp->Init.pInitVect + 3);
2408     }
2409   } /* if (DoKeyIVConfig == 1U) */
2410 
2411   /* Set the phase */
2412   hcryp->Phase = CRYP_PHASE_PROCESS;
2413 
2414   if (hcryp->Size != 0U)
2415   {
2416     /* Set the input and output addresses and start DMA transfer */
2417     CRYP_SetDMAConfig(hcryp, (uint32_t)(hcryp->pCrypInBuffPtr), (hcryp->Size / 4U),
2418                       (uint32_t)(hcryp->pCrypOutBuffPtr));
2419   }
2420   else
2421   {
2422     /* Process unlocked */
2423     __HAL_UNLOCK(hcryp);
2424 
2425     /* Change the CRYP state */
2426     hcryp->State = HAL_CRYP_STATE_READY;
2427   }
2428 
2429   /* Return function status */
2430   return HAL_OK;
2431 }
2432 
2433 
2434 /**
2435   * @brief  DMA CRYP input data process complete callback.
2436   * @param  hdma: DMA handle
2437   * @retval None
2438   */
CRYP_DMAInCplt(DMA_HandleTypeDef * hdma)2439 static void CRYP_DMAInCplt(DMA_HandleTypeDef *hdma)
2440 {
2441   CRYP_HandleTypeDef *hcryp = (CRYP_HandleTypeDef *)((DMA_HandleTypeDef *)hdma)->Parent;
2442 
2443   /* Disable the DMA transfer for input FIFO request by resetting the DIEN bit
2444   in the DMACR register */
2445   hcryp->Instance->DMACR &= (uint32_t)(~CRYP_DMACR_DIEN);
2446 
2447   /* Call input data transfer complete callback */
2448 #if (USE_HAL_CRYP_REGISTER_CALLBACKS == 1)
2449   /*Call registered Input complete callback*/
2450   hcryp->InCpltCallback(hcryp);
2451 #else
2452   /*Call legacy weak Input complete callback*/
2453   HAL_CRYP_InCpltCallback(hcryp);
2454 #endif /* USE_HAL_CRYP_REGISTER_CALLBACKS */
2455 }
2456 
2457 /**
2458   * @brief  DMA CRYP output data process complete callback.
2459   * @param  hdma: DMA handle
2460   * @retval None
2461   */
CRYP_DMAOutCplt(DMA_HandleTypeDef * hdma)2462 static void CRYP_DMAOutCplt(DMA_HandleTypeDef *hdma)
2463 {
2464   uint32_t count;
2465   uint32_t npblb;
2466   uint32_t lastwordsize;
2467   uint32_t temp;  /* Temporary CrypOutBuff */
2468   uint32_t temp_cr_algodir;
2469   CRYP_HandleTypeDef *hcryp = (CRYP_HandleTypeDef *)((DMA_HandleTypeDef *)hdma)->Parent;
2470 
2471 
2472   /* Disable the DMA transfer for output FIFO */
2473   hcryp->Instance->DMACR &= (uint32_t)(~CRYP_DMACR_DOEN);
2474 
2475   /* Last block transfer in case of GCM or CCM with Size not %16*/
2476   if (((hcryp->Size) % 16U) != 0U)
2477   {
2478     /* set CrypInCount and CrypOutCount to exact number of word already computed via DMA  */
2479     hcryp->CrypInCount = (hcryp->Size / 16U) * 4U ;
2480     hcryp->CrypOutCount = hcryp->CrypInCount;
2481 
2482     /* Compute the number of padding bytes in last block of payload */
2483     npblb = ((((uint32_t)(hcryp->Size) / 16U) + 1U) * 16U) - (uint32_t)(hcryp->Size);
2484 
2485 #if !defined (CRYP_VER_2_2)
2486     if (hcryp->Version >= REV_ID_B)
2487 #endif /*End of not defined CRYP_VER_2_2*/
2488     {
2489       /* Case of AES GCM payload encryption or AES CCM payload decryption to get right tag */
2490       temp_cr_algodir = hcryp->Instance->CR & CRYP_CR_ALGODIR;
2491       if (((temp_cr_algodir == CRYP_OPERATINGMODE_ENCRYPT) && (hcryp->Init.Algorithm == CRYP_AES_GCM)) ||
2492           ((temp_cr_algodir == CRYP_OPERATINGMODE_DECRYPT) && (hcryp->Init.Algorithm == CRYP_AES_CCM)))
2493       {
2494         /* Disable the CRYP */
2495         __HAL_CRYP_DISABLE(hcryp);
2496 
2497         /* Specify the number of non-valid bytes using NPBLB register*/
2498         MODIFY_REG(hcryp->Instance->CR, CRYP_CR_NPBLB, npblb << 20);
2499 
2500         /* Enable CRYP to start the final phase */
2501         __HAL_CRYP_ENABLE(hcryp);
2502       }
2503     }
2504 
2505     /* Number of valid words (lastwordsize) in last block */
2506     if ((npblb % 4U) == 0U)
2507     {
2508       lastwordsize = (16U - npblb) / 4U;
2509     }
2510     else
2511     {
2512       lastwordsize = ((16U - npblb) / 4U) + 1U;
2513     }
2514     /* Write the last input block in the IN FIFO */
2515     for (count = 0U; count < lastwordsize; count ++)
2516     {
2517       hcryp->Instance->DIN  = *(uint32_t *)(hcryp->pCrypInBuffPtr + hcryp->CrypInCount);
2518       hcryp->CrypInCount++;
2519     }
2520     /* Pad the data with zeros to have a complete block */
2521     while (count < 4U)
2522     {
2523       hcryp->Instance->DIN  = 0U;
2524       count++;
2525     }
2526     /* Wait for OFNE flag to be raised */
2527     count = CRYP_TIMEOUT_GCMCCMHEADERPHASE;
2528     do
2529     {
2530       count-- ;
2531       if (count == 0U)
2532       {
2533         /* Disable the CRYP peripheral clock */
2534         __HAL_CRYP_DISABLE(hcryp);
2535 
2536         /* Change state */
2537         hcryp->ErrorCode |= HAL_CRYP_ERROR_TIMEOUT;
2538         hcryp->State = HAL_CRYP_STATE_READY;
2539 
2540         /* Process unlocked */
2541         __HAL_UNLOCK(hcryp);
2542 #if (USE_HAL_CRYP_REGISTER_CALLBACKS == 1)
2543         /*Call registered error callback*/
2544         hcryp->ErrorCallback(hcryp);
2545 #else
2546         /*Call legacy weak error callback*/
2547         HAL_CRYP_ErrorCallback(hcryp);
2548 #endif /* USE_HAL_CRYP_REGISTER_CALLBACKS */
2549       }
2550     } while (HAL_IS_BIT_CLR(hcryp->Instance->SR, CRYP_FLAG_OFNE));
2551 
2552     /*Read the output block from the output FIFO */
2553     for (count = 0U; count < 4U; count++)
2554     {
2555       /* Read the output block from the output FIFO and put them in temporary buffer
2556          then get CrypOutBuff from temporary buffer */
2557       temp = hcryp->Instance->DOUT;
2558 
2559       *(uint32_t *)(hcryp->pCrypOutBuffPtr + (hcryp->CrypOutCount)) = temp;
2560       hcryp->CrypOutCount++;
2561     }
2562   } /*End of last block transfer in case of GCM or CCM */
2563 
2564   if ((hcryp->Init.Algorithm & CRYP_AES_GCM) != CRYP_AES_GCM)
2565   {
2566     /* Disable CRYP  (not allowed in  GCM)*/
2567     __HAL_CRYP_DISABLE(hcryp);
2568   }
2569 
2570   /* Change the CRYP state to ready */
2571   hcryp->State = HAL_CRYP_STATE_READY;
2572 
2573   /* Process unlocked */
2574   __HAL_UNLOCK(hcryp);
2575 
2576   /* Call output data transfer complete callback */
2577 #if (USE_HAL_CRYP_REGISTER_CALLBACKS == 1)
2578   /*Call registered Output complete callback*/
2579   hcryp->OutCpltCallback(hcryp);
2580 #else
2581   /*Call legacy weak Output complete callback*/
2582   HAL_CRYP_OutCpltCallback(hcryp);
2583 #endif /* USE_HAL_CRYP_REGISTER_CALLBACKS */
2584 }
2585 
2586 /**
2587   * @brief  DMA CRYP communication error callback.
2588   * @param  hdma: DMA handle
2589   * @retval None
2590   */
CRYP_DMAError(DMA_HandleTypeDef * hdma)2591 static void CRYP_DMAError(DMA_HandleTypeDef *hdma)
2592 {
2593   CRYP_HandleTypeDef *hcryp = (CRYP_HandleTypeDef *)((DMA_HandleTypeDef *)hdma)->Parent;
2594 
2595   /* Change the CRYP peripheral state */
2596   hcryp->State = HAL_CRYP_STATE_READY;
2597 
2598   /* DMA error code field */
2599   hcryp->ErrorCode |= HAL_CRYP_ERROR_DMA;
2600 
2601   /* Call error callback */
2602 #if (USE_HAL_CRYP_REGISTER_CALLBACKS == 1)
2603   /*Call registered error callback*/
2604   hcryp->ErrorCallback(hcryp);
2605 #else
2606   /*Call legacy weak error callback*/
2607   HAL_CRYP_ErrorCallback(hcryp);
2608 #endif /* USE_HAL_CRYP_REGISTER_CALLBACKS */
2609 }
2610 
2611 /**
2612   * @brief  Set the DMA configuration and start the DMA transfer
2613   * @param  hcryp: pointer to a CRYP_HandleTypeDef structure that contains
2614   *         the configuration information for CRYP module
2615   * @param  inputaddr: address of the input buffer
2616   * @param  Size: size of the input buffer, must be a multiple of 16.
2617   * @param  outputaddr: address of the output buffer
2618   * @retval None
2619   */
CRYP_SetDMAConfig(CRYP_HandleTypeDef * hcryp,uint32_t inputaddr,uint16_t Size,uint32_t outputaddr)2620 static void CRYP_SetDMAConfig(CRYP_HandleTypeDef *hcryp, uint32_t inputaddr, uint16_t Size, uint32_t outputaddr)
2621 {
2622   /* Set the CRYP DMA transfer complete callback */
2623   hcryp->hdmain->XferCpltCallback = CRYP_DMAInCplt;
2624 
2625   /* Set the DMA input error callback */
2626   hcryp->hdmain->XferErrorCallback = CRYP_DMAError;
2627 
2628   /* Set the CRYP DMA transfer complete callback */
2629   hcryp->hdmaout->XferCpltCallback = CRYP_DMAOutCplt;
2630 
2631   /* Set the DMA output error callback */
2632   hcryp->hdmaout->XferErrorCallback = CRYP_DMAError;
2633 
2634   /* Enable CRYP */
2635   __HAL_CRYP_ENABLE(hcryp);
2636 
2637   /* Enable the input DMA Stream */
2638   if (HAL_DMA_Start_IT(hcryp->hdmain, inputaddr, (uint32_t)&hcryp->Instance->DIN, Size) != HAL_OK)
2639   {
2640     /* DMA error code field */
2641     hcryp->ErrorCode |= HAL_CRYP_ERROR_DMA;
2642 
2643     /* Call error callback */
2644 #if (USE_HAL_CRYP_REGISTER_CALLBACKS == 1)
2645     /*Call registered error callback*/
2646     hcryp->ErrorCallback(hcryp);
2647 #else
2648     /*Call legacy weak error callback*/
2649     HAL_CRYP_ErrorCallback(hcryp);
2650 #endif /* USE_HAL_CRYP_REGISTER_CALLBACKS */
2651   }
2652 
2653   /* Enable the output DMA Stream */
2654   if (HAL_DMA_Start_IT(hcryp->hdmaout, (uint32_t)&hcryp->Instance->DOUT, outputaddr, Size) != HAL_OK)
2655   {
2656     /* DMA error code field */
2657     hcryp->ErrorCode |= HAL_CRYP_ERROR_DMA;
2658 
2659     /* Call error callback */
2660 #if (USE_HAL_CRYP_REGISTER_CALLBACKS == 1)
2661     /*Call registered error callback*/
2662     hcryp->ErrorCallback(hcryp);
2663 #else
2664     /*Call legacy weak error callback*/
2665     HAL_CRYP_ErrorCallback(hcryp);
2666 #endif /* USE_HAL_CRYP_REGISTER_CALLBACKS */
2667   }
2668   /* Enable In/Out DMA request */
2669   hcryp->Instance->DMACR = CRYP_DMACR_DOEN | CRYP_DMACR_DIEN;
2670 }
2671 
2672 /**
2673   * @brief  Process Data: Write Input data in polling mode and used in AES functions.
2674   * @param  hcryp: pointer to a CRYP_HandleTypeDef structure that contains
2675   *         the configuration information for CRYP module
2676   * @param  Timeout: Specify Timeout value
2677   * @retval None
2678   */
CRYP_AES_ProcessData(CRYP_HandleTypeDef * hcryp,uint32_t Timeout)2679 static void CRYP_AES_ProcessData(CRYP_HandleTypeDef *hcryp, uint32_t Timeout)
2680 {
2681 
2682   uint32_t temp[4];  /* Temporary CrypOutBuff */
2683   uint16_t incount;  /* Temporary CrypInCount Value */
2684   uint16_t outcount;  /* Temporary CrypOutCount Value */
2685   uint32_t i;
2686 
2687   /*Temporary CrypOutCount Value*/
2688   incount = hcryp->CrypInCount;
2689 
2690   if (((hcryp->Instance->SR & CRYP_FLAG_IFNF) != 0x0U) && (incount < ((hcryp->Size) / 4U)))
2691   {
2692     /* Write the input block in the IN FIFO */
2693     hcryp->Instance->DIN  = *(uint32_t *)(hcryp->pCrypInBuffPtr + hcryp->CrypInCount);
2694     hcryp->CrypInCount++;
2695     hcryp->Instance->DIN  = *(uint32_t *)(hcryp->pCrypInBuffPtr + hcryp->CrypInCount);
2696     hcryp->CrypInCount++;
2697     hcryp->Instance->DIN  = *(uint32_t *)(hcryp->pCrypInBuffPtr + hcryp->CrypInCount);
2698     hcryp->CrypInCount++;
2699     hcryp->Instance->DIN  = *(uint32_t *)(hcryp->pCrypInBuffPtr + hcryp->CrypInCount);
2700     hcryp->CrypInCount++;
2701   }
2702 
2703   /* Wait for OFNE flag to be raised */
2704   if (CRYP_WaitOnOFNEFlag(hcryp, Timeout) != HAL_OK)
2705   {
2706     /* Disable the CRYP peripheral clock */
2707     __HAL_CRYP_DISABLE(hcryp);
2708 
2709     /* Change state & error code*/
2710     hcryp->ErrorCode |= HAL_CRYP_ERROR_TIMEOUT;
2711     hcryp->State = HAL_CRYP_STATE_READY;
2712 
2713     /* Process unlocked */
2714     __HAL_UNLOCK(hcryp);
2715 #if (USE_HAL_CRYP_REGISTER_CALLBACKS == 1)
2716     /*Call registered error callback*/
2717     hcryp->ErrorCallback(hcryp);
2718 #else
2719     /*Call legacy weak error callback*/
2720     HAL_CRYP_ErrorCallback(hcryp);
2721 #endif /* USE_HAL_CRYP_REGISTER_CALLBACKS */
2722   }
2723   /*Temporary CrypOutCount Value*/
2724   outcount = hcryp->CrypOutCount;
2725 
2726   if (((hcryp->Instance->SR & CRYP_FLAG_OFNE) != 0x0U) && (outcount < ((hcryp->Size) / 4U)))
2727   {
2728     /* Read the output block from the Output FIFO and put them in temporary buffer
2729        then get CrypOutBuff from temporary buffer  */
2730     for (i = 0U; i < 4U; i++)
2731     {
2732       temp[i] = hcryp->Instance->DOUT;
2733     }
2734     i = 0U;
2735     while (((hcryp->CrypOutCount < ((hcryp->Size) / 4U))) && (i < 4U))
2736     {
2737       *(uint32_t *)(hcryp->pCrypOutBuffPtr + hcryp->CrypOutCount) = temp[i];
2738       hcryp->CrypOutCount++;
2739       i++;
2740     }
2741   }
2742 }
2743 
2744 /**
2745   * @brief  Handle CRYP block input/output data handling under interruption.
2746   * @note   The function is called under interruption only, once
2747   *         interruptions have been enabled by HAL_CRYP_Encrypt_IT or HAL_CRYP_Decrypt_IT.
2748   * @param  hcryp: pointer to a CRYP_HandleTypeDef structure that contains
2749   *         the configuration information for CRYP module.
2750   * @retval HAL status
2751   */
CRYP_AES_IT(CRYP_HandleTypeDef * hcryp)2752 static void CRYP_AES_IT(CRYP_HandleTypeDef *hcryp)
2753 {
2754   uint32_t temp[4];  /* Temporary CrypOutBuff */
2755   uint16_t incount; /* Temporary CrypInCount Value */
2756   uint16_t outcount;  /* Temporary CrypOutCount Value */
2757   uint32_t i;
2758 
2759   if (hcryp->State == HAL_CRYP_STATE_BUSY)
2760   {
2761     /*Temporary CrypOutCount Value*/
2762     incount = hcryp->CrypInCount;
2763 
2764     if (((hcryp->Instance->SR & CRYP_FLAG_IFNF) != 0x0U) && (incount < (hcryp->Size / 4U)))
2765     {
2766       /* Write the input block in the IN FIFO */
2767       hcryp->Instance->DIN  = *(uint32_t *)(hcryp->pCrypInBuffPtr + hcryp->CrypInCount);
2768       hcryp->CrypInCount++;
2769       hcryp->Instance->DIN  = *(uint32_t *)(hcryp->pCrypInBuffPtr + hcryp->CrypInCount);
2770       hcryp->CrypInCount++;
2771       hcryp->Instance->DIN  = *(uint32_t *)(hcryp->pCrypInBuffPtr + hcryp->CrypInCount);
2772       hcryp->CrypInCount++;
2773       hcryp->Instance->DIN  = *(uint32_t *)(hcryp->pCrypInBuffPtr + hcryp->CrypInCount);
2774       hcryp->CrypInCount++;
2775       if (hcryp->CrypInCount == (hcryp->Size / 4U))
2776       {
2777         /* Disable interrupts */
2778         __HAL_CRYP_DISABLE_IT(hcryp, CRYP_IT_INI);
2779 
2780         /* Call the input data transfer complete callback */
2781 #if (USE_HAL_CRYP_REGISTER_CALLBACKS == 1)
2782         /*Call registered Input complete callback*/
2783         hcryp->InCpltCallback(hcryp);
2784 #else
2785         /*Call legacy weak Input complete callback*/
2786         HAL_CRYP_InCpltCallback(hcryp);
2787 #endif /* USE_HAL_CRYP_REGISTER_CALLBACKS */
2788       }
2789     }
2790 
2791     /*Temporary CrypOutCount Value*/
2792     outcount = hcryp->CrypOutCount;
2793 
2794     if (((hcryp->Instance->SR & CRYP_FLAG_OFNE) != 0x0U) && (outcount < (hcryp->Size / 4U)))
2795     {
2796       /* Read the output block from the output FIFO and put them in temporary buffer
2797          then get CrypOutBuff from temporary buffer  */
2798       for (i = 0U; i < 4U; i++)
2799       {
2800         temp[i] = hcryp->Instance->DOUT;
2801       }
2802       i = 0U;
2803       while (((hcryp->CrypOutCount < ((hcryp->Size) / 4U))) && (i < 4U))
2804       {
2805         *(uint32_t *)(hcryp->pCrypOutBuffPtr + hcryp->CrypOutCount) = temp[i];
2806         hcryp->CrypOutCount++;
2807         i++;
2808       }
2809       if (hcryp->CrypOutCount == (hcryp->Size / 4U))
2810       {
2811         /* Disable interrupts */
2812         __HAL_CRYP_DISABLE_IT(hcryp, CRYP_IT_OUTI);
2813 
2814         /* Change the CRYP state */
2815         hcryp->State = HAL_CRYP_STATE_READY;
2816 
2817         /* Disable CRYP */
2818         __HAL_CRYP_DISABLE(hcryp);
2819 
2820         /* Process unlocked */
2821         __HAL_UNLOCK(hcryp);
2822 
2823         /* Call output transfer complete callback */
2824 #if (USE_HAL_CRYP_REGISTER_CALLBACKS == 1)
2825         /*Call registered Output complete callback*/
2826         hcryp->OutCpltCallback(hcryp);
2827 #else
2828         /*Call legacy weak Output complete callback*/
2829         HAL_CRYP_OutCpltCallback(hcryp);
2830 #endif /* USE_HAL_CRYP_REGISTER_CALLBACKS */
2831       }
2832     }
2833   }
2834   else
2835   {
2836     /* Process unlocked */
2837     __HAL_UNLOCK(hcryp);
2838     /* Busy error code field */
2839     hcryp->ErrorCode |= HAL_CRYP_ERROR_BUSY;
2840 #if (USE_HAL_CRYP_REGISTER_CALLBACKS == 1)
2841     /*Call registered error callback*/
2842     hcryp->ErrorCallback(hcryp);
2843 #else
2844     /*Call legacy weak error callback*/
2845     HAL_CRYP_ErrorCallback(hcryp);
2846 #endif /* USE_HAL_CRYP_REGISTER_CALLBACKS */
2847   }
2848 }
2849 
2850 /**
2851   * @brief  Writes Key in Key registers.
2852   * @param  hcryp: pointer to a CRYP_HandleTypeDef structure that contains
2853   *         the configuration information for CRYP module
2854   * @param  KeySize: Size of Key
2855   * @retval None
2856   */
CRYP_SetKey(CRYP_HandleTypeDef * hcryp,uint32_t KeySize)2857 static void CRYP_SetKey(CRYP_HandleTypeDef *hcryp, uint32_t KeySize)
2858 {
2859   switch (KeySize)
2860   {
2861     case CRYP_KEYSIZE_256B:
2862       hcryp->Instance->K0LR = *(uint32_t *)(hcryp->Init.pKey);
2863       hcryp->Instance->K0RR = *(uint32_t *)(hcryp->Init.pKey + 1);
2864       hcryp->Instance->K1LR = *(uint32_t *)(hcryp->Init.pKey + 2);
2865       hcryp->Instance->K1RR = *(uint32_t *)(hcryp->Init.pKey + 3);
2866       hcryp->Instance->K2LR = *(uint32_t *)(hcryp->Init.pKey + 4);
2867       hcryp->Instance->K2RR = *(uint32_t *)(hcryp->Init.pKey + 5);
2868       hcryp->Instance->K3LR = *(uint32_t *)(hcryp->Init.pKey + 6);
2869       hcryp->Instance->K3RR = *(uint32_t *)(hcryp->Init.pKey + 7);
2870       break;
2871     case CRYP_KEYSIZE_192B:
2872       hcryp->Instance->K1LR = *(uint32_t *)(hcryp->Init.pKey);
2873       hcryp->Instance->K1RR = *(uint32_t *)(hcryp->Init.pKey + 1);
2874       hcryp->Instance->K2LR = *(uint32_t *)(hcryp->Init.pKey + 2);
2875       hcryp->Instance->K2RR = *(uint32_t *)(hcryp->Init.pKey + 3);
2876       hcryp->Instance->K3LR = *(uint32_t *)(hcryp->Init.pKey + 4);
2877       hcryp->Instance->K3RR = *(uint32_t *)(hcryp->Init.pKey + 5);
2878       break;
2879     case CRYP_KEYSIZE_128B:
2880       hcryp->Instance->K2LR = *(uint32_t *)(hcryp->Init.pKey);
2881       hcryp->Instance->K2RR = *(uint32_t *)(hcryp->Init.pKey + 1);
2882       hcryp->Instance->K3LR = *(uint32_t *)(hcryp->Init.pKey + 2);
2883       hcryp->Instance->K3RR = *(uint32_t *)(hcryp->Init.pKey + 3);
2884 
2885       break;
2886     default:
2887       break;
2888   }
2889 }
2890 
2891 /**
2892   * @brief  Encryption/Decryption process in AES GCM mode and prepare the authentication TAG
2893   * @param  hcryp: pointer to a CRYP_HandleTypeDef structure that contains
2894   *         the configuration information for CRYP module
2895   * @param  Timeout: Timeout duration
2896   * @retval HAL status
2897   */
CRYP_AESGCM_Process(CRYP_HandleTypeDef * hcryp,uint32_t Timeout)2898 static HAL_StatusTypeDef CRYP_AESGCM_Process(CRYP_HandleTypeDef *hcryp, uint32_t Timeout)
2899 {
2900   uint32_t tickstart;
2901   uint32_t wordsize = (uint32_t)(hcryp->Size) / 4U;
2902   uint32_t npblb ;
2903   uint32_t temp[4];  /* Temporary CrypOutBuff */
2904   uint32_t index ;
2905   uint32_t lastwordsize ;
2906   uint16_t outcount;  /* Temporary CrypOutCount Value */
2907   uint32_t DoKeyIVConfig = 1U; /* By default, carry out peripheral Key and IV configuration */
2908 
2909   if (hcryp->Init.KeyIVConfigSkip == CRYP_KEYIVCONFIG_ONCE)
2910   {
2911     if (hcryp->KeyIVConfig == 1U)
2912     {
2913       /* If the Key and IV configuration has to be done only once
2914          and if it has already been done, skip it */
2915       DoKeyIVConfig = 0U;
2916       hcryp->SizesSum += hcryp->Size; /* Compute message total payload length */
2917     }
2918     else
2919     {
2920       /* If the Key and IV configuration has to be done only once
2921          and if it has not been done already, do it and set KeyIVConfig
2922          to keep track it won't have to be done again next time */
2923       hcryp->KeyIVConfig = 1U;
2924       hcryp->SizesSum = hcryp->Size; /* Merely store payload length */
2925     }
2926   }
2927   else
2928   {
2929     hcryp->SizesSum = hcryp->Size;
2930   }
2931 
2932   if (DoKeyIVConfig == 1U)
2933   {
2934     /*  Reset CrypHeaderCount */
2935     hcryp->CrypHeaderCount = 0U;
2936 
2937     /****************************** Init phase **********************************/
2938 
2939     CRYP_SET_PHASE(hcryp, CRYP_PHASE_INIT);
2940 
2941     /* Set the key */
2942     CRYP_SetKey(hcryp, hcryp->Init.KeySize);
2943 
2944     /* Set the initialization vector and the counter : Initial Counter Block (ICB)*/
2945     hcryp->Instance->IV0LR = *(uint32_t *)(hcryp->Init.pInitVect);
2946     hcryp->Instance->IV0RR = *(uint32_t *)(hcryp->Init.pInitVect + 1);
2947     hcryp->Instance->IV1LR = *(uint32_t *)(hcryp->Init.pInitVect + 2);
2948     hcryp->Instance->IV1RR = *(uint32_t *)(hcryp->Init.pInitVect + 3);
2949 
2950     /* Enable the CRYP peripheral */
2951     __HAL_CRYP_ENABLE(hcryp);
2952 
2953     /* Get tick */
2954     tickstart = HAL_GetTick();
2955 
2956     /*Wait for the CRYPEN bit to be cleared*/
2957     while ((hcryp->Instance->CR & CRYP_CR_CRYPEN) == CRYP_CR_CRYPEN)
2958     {
2959       /* Check for the Timeout */
2960       if (Timeout != HAL_MAX_DELAY)
2961       {
2962         if (((HAL_GetTick() - tickstart) > Timeout) || (Timeout == 0U))
2963         {
2964           /* Disable the CRYP peripheral clock */
2965           __HAL_CRYP_DISABLE(hcryp);
2966 
2967           /* Change state */
2968           hcryp->ErrorCode |= HAL_CRYP_ERROR_TIMEOUT;
2969           hcryp->State = HAL_CRYP_STATE_READY;
2970 
2971           /* Process unlocked */
2972           __HAL_UNLOCK(hcryp);
2973           return HAL_ERROR;
2974         }
2975       }
2976     }
2977 
2978     /************************ Header phase *************************************/
2979 
2980     if (CRYP_GCMCCM_SetHeaderPhase(hcryp,  Timeout) != HAL_OK)
2981     {
2982       return HAL_ERROR;
2983     }
2984 
2985     /*************************Payload phase ************************************/
2986 
2987     /* Set the phase */
2988     hcryp->Phase = CRYP_PHASE_PROCESS;
2989 
2990     /* Disable the CRYP peripheral */
2991     __HAL_CRYP_DISABLE(hcryp);
2992 
2993 #if !defined (CRYP_VER_2_2)
2994     if (hcryp->Version >= REV_ID_B)
2995 #endif /*End of not defined CRYP_VER_2_2*/
2996     {
2997       /* Set to 0 the number of non-valid bytes using NPBLB register*/
2998       MODIFY_REG(hcryp->Instance->CR, CRYP_CR_NPBLB, 0U);
2999     }
3000 
3001     /* Select payload phase once the header phase is performed */
3002     CRYP_SET_PHASE(hcryp, CRYP_PHASE_PAYLOAD);
3003 
3004     /* Enable the CRYP peripheral */
3005     __HAL_CRYP_ENABLE(hcryp);
3006   } /* if (DoKeyIVConfig == 1U) */
3007 
3008   if ((hcryp->Size % 16U) != 0U)
3009   {
3010     /* recalculate  wordsize */
3011     wordsize = ((wordsize / 4U) * 4U) ;
3012   }
3013 
3014   /* Get tick */
3015   tickstart = HAL_GetTick();
3016   /*Temporary CrypOutCount Value*/
3017   outcount = hcryp->CrypOutCount;
3018 
3019   /* Write input data and get output Data */
3020   while ((hcryp->CrypInCount < wordsize) && (outcount < wordsize))
3021   {
3022     /* Write plain data and get cipher data */
3023     CRYP_AES_ProcessData(hcryp, Timeout);
3024 
3025     /*Temporary CrypOutCount Value*/
3026     outcount = hcryp->CrypOutCount;
3027 
3028     /* Check for the Timeout */
3029     if (Timeout != HAL_MAX_DELAY)
3030     {
3031       if (((HAL_GetTick() - tickstart) > Timeout) || (Timeout == 0U))
3032       {
3033         /* Disable the CRYP peripheral clock */
3034         __HAL_CRYP_DISABLE(hcryp);
3035 
3036         /* Change state & error code */
3037         hcryp->ErrorCode |= HAL_CRYP_ERROR_TIMEOUT;
3038         hcryp->State = HAL_CRYP_STATE_READY;
3039 
3040         /* Process unlocked */
3041         __HAL_UNLOCK(hcryp);
3042         return HAL_ERROR;
3043       }
3044     }
3045   }
3046 
3047   if ((hcryp->Size % 16U) != 0U)
3048   {
3049 
3050 #if !defined (CRYP_VER_2_2)
3051     if (hcryp->Version >= REV_ID_B)
3052 #endif /*End of not defined CRYP_VER_2_2*/
3053     {
3054       /* Compute the number of padding bytes in last block of payload */
3055       npblb = ((((uint32_t)(hcryp->Size) / 16U) + 1U) * 16U) - (uint32_t)(hcryp->Size);
3056 
3057       /*  Set Npblb in case of AES GCM payload encryption to get right tag*/
3058       if ((hcryp->Instance->CR & CRYP_CR_ALGODIR) == CRYP_OPERATINGMODE_ENCRYPT)
3059       {
3060         /* Disable the CRYP */
3061         __HAL_CRYP_DISABLE(hcryp);
3062 
3063         /* Specify the number of non-valid bytes using NPBLB register*/
3064         MODIFY_REG(hcryp->Instance->CR, CRYP_CR_NPBLB, npblb << 20);
3065 
3066         /* Enable CRYP to start the final phase */
3067         __HAL_CRYP_ENABLE(hcryp);
3068       }
3069       /* Number of valid words (lastwordsize) in last block */
3070       if ((npblb % 4U) == 0U)
3071       {
3072         lastwordsize = (16U - npblb) / 4U;
3073       }
3074       else
3075       {
3076         lastwordsize = ((16U - npblb) / 4U) + 1U;
3077       }
3078 
3079       /* Write the last input block in the IN FIFO */
3080       for (index = 0U; index < lastwordsize; index ++)
3081       {
3082         hcryp->Instance->DIN  = *(uint32_t *)(hcryp->pCrypInBuffPtr + hcryp->CrypInCount);
3083         hcryp->CrypInCount++;
3084       }
3085 
3086       /* Pad the data with zeros to have a complete block */
3087       while (index < 4U)
3088       {
3089         hcryp->Instance->DIN  = 0U;
3090         index++;
3091       }
3092 
3093       /* Wait for OFNE flag to be raised */
3094       if (CRYP_WaitOnOFNEFlag(hcryp, Timeout) != HAL_OK)
3095       {
3096         /* Disable the CRYP peripheral clock */
3097         __HAL_CRYP_DISABLE(hcryp);
3098 
3099         /* Change state */
3100         hcryp->ErrorCode |= HAL_CRYP_ERROR_TIMEOUT;
3101         hcryp->State = HAL_CRYP_STATE_READY;
3102 
3103         /* Process Unlocked */
3104         __HAL_UNLOCK(hcryp);
3105 #if (USE_HAL_CRYP_REGISTER_CALLBACKS == 1)
3106         /*Call registered error callback*/
3107         hcryp->ErrorCallback(hcryp);
3108 #else
3109         /*Call legacy weak error callback*/
3110         HAL_CRYP_ErrorCallback(hcryp);
3111 #endif /* USE_HAL_CRYP_REGISTER_CALLBACKS */
3112       }
3113 
3114       /*Read the output block from the output FIFO */
3115       if ((hcryp->Instance->SR & CRYP_FLAG_OFNE) != 0x0U)
3116       {
3117         for (index = 0U; index < 4U; index++)
3118         {
3119           /* Read the output block from the output FIFO and put them in temporary buffer
3120           then get CrypOutBuff from temporary buffer */
3121           temp[index] = hcryp->Instance->DOUT;
3122         }
3123         for (index = 0; index < lastwordsize; index++)
3124         {
3125           *(uint32_t *)(hcryp->pCrypOutBuffPtr + (hcryp->CrypOutCount)) = temp[index];
3126           hcryp->CrypOutCount++;
3127         }
3128       }
3129     }
3130 #if !defined (CRYP_VER_2_2)
3131     else /*  Workaround to be used */
3132     {
3133       /*  Workaround 2 for STM32H7 below rev.B To generate correct TAG only when size of the last block of
3134       payload is inferior to 128 bits, in case of GCM encryption or CCM decryption*/
3135       CRYP_Workaround(hcryp, Timeout);
3136     } /* end of NPBLB or Workaround*/
3137 #endif /*End of not defined CRYP_VER_2_2*/
3138   }
3139 
3140   /* Return function status */
3141   return HAL_OK;
3142 }
3143 
3144 /**
3145   * @brief  Encryption/Decryption process in AES GCM mode and prepare the authentication TAG in interrupt mode
3146   * @param  hcryp: pointer to a CRYP_HandleTypeDef structure that contains
3147   *         the configuration information for CRYP module
3148   * @retval HAL status
3149   */
CRYP_AESGCM_Process_IT(CRYP_HandleTypeDef * hcryp)3150 static HAL_StatusTypeDef CRYP_AESGCM_Process_IT(CRYP_HandleTypeDef *hcryp)
3151 {
3152   __IO uint32_t count = 0U;
3153   uint32_t DoKeyIVConfig = 1U; /* By default, carry out peripheral Key and IV configuration */
3154 
3155   if (hcryp->Init.KeyIVConfigSkip == CRYP_KEYIVCONFIG_ONCE)
3156   {
3157     if (hcryp->KeyIVConfig == 1U)
3158     {
3159       /* If the Key and IV configuration has to be done only once
3160       and if it has already been done, skip it */
3161       DoKeyIVConfig = 0U;
3162       hcryp->SizesSum += hcryp->Size; /* Compute message total payload length */
3163     }
3164     else
3165     {
3166       /* If the Key and IV configuration has to be done only once
3167       and if it has not been done already, do it and set KeyIVConfig
3168       to keep track it won't have to be done again next time */
3169       hcryp->KeyIVConfig = 1U;
3170       hcryp->SizesSum = hcryp->Size; /* Merely store payload length */
3171     }
3172   }
3173   else
3174   {
3175     hcryp->SizesSum = hcryp->Size;
3176   }
3177 
3178   /* Configure Key, IV and process message (header and payload) */
3179   if (DoKeyIVConfig == 1U)
3180   {
3181     /*  Reset CrypHeaderCount */
3182     hcryp->CrypHeaderCount = 0U;
3183 
3184     /******************************* Init phase *********************************/
3185 
3186     CRYP_SET_PHASE(hcryp, CRYP_PHASE_INIT);
3187 
3188     /* Set the key */
3189     CRYP_SetKey(hcryp, hcryp->Init.KeySize);
3190 
3191     /* Set the initialization vector and the counter : Initial Counter Block (ICB)*/
3192     hcryp->Instance->IV0LR = *(uint32_t *)(hcryp->Init.pInitVect);
3193     hcryp->Instance->IV0RR = *(uint32_t *)(hcryp->Init.pInitVect + 1);
3194     hcryp->Instance->IV1LR = *(uint32_t *)(hcryp->Init.pInitVect + 2);
3195     hcryp->Instance->IV1RR = *(uint32_t *)(hcryp->Init.pInitVect + 3);
3196 
3197     /* Enable the CRYP peripheral */
3198     __HAL_CRYP_ENABLE(hcryp);
3199 
3200     /*Wait for the CRYPEN bit to be cleared*/
3201     count = CRYP_TIMEOUT_GCMCCMINITPHASE;
3202     do
3203     {
3204       count-- ;
3205       if (count == 0U)
3206       {
3207         /* Disable the CRYP peripheral clock */
3208         __HAL_CRYP_DISABLE(hcryp);
3209 
3210         /* Change state */
3211         hcryp->ErrorCode |= HAL_CRYP_ERROR_TIMEOUT;
3212         hcryp->State = HAL_CRYP_STATE_READY;
3213 
3214         /* Process unlocked */
3215         __HAL_UNLOCK(hcryp);
3216         return HAL_ERROR;
3217       }
3218     } while ((hcryp->Instance->CR & CRYP_CR_CRYPEN) == CRYP_CR_CRYPEN);
3219 
3220     /***************************** Header phase *********************************/
3221 
3222     /* Select header phase */
3223     CRYP_SET_PHASE(hcryp, CRYP_PHASE_HEADER);
3224   } /* end of if (DoKeyIVConfig == 1U) */
3225   /* Enable interrupts */
3226   __HAL_CRYP_ENABLE_IT(hcryp, CRYP_IT_INI);
3227 
3228   /* Enable CRYP */
3229   __HAL_CRYP_ENABLE(hcryp);
3230 
3231   /* Return function status */
3232   return HAL_OK;
3233 }
3234 
3235 
3236 /**
3237   * @brief  Encryption/Decryption process in AES GCM mode and prepare the authentication TAG using DMA
3238   * @param  hcryp: pointer to a CRYP_HandleTypeDef structure that contains
3239   *         the configuration information for CRYP module
3240   * @retval HAL status
3241   */
CRYP_AESGCM_Process_DMA(CRYP_HandleTypeDef * hcryp)3242 static HAL_StatusTypeDef CRYP_AESGCM_Process_DMA(CRYP_HandleTypeDef *hcryp)
3243 {
3244   __IO uint32_t count = 0U;
3245   uint32_t wordsize = (uint32_t)(hcryp->Size) / 4U ;
3246   uint32_t index;
3247   uint32_t npblb;
3248   uint32_t lastwordsize;
3249   uint32_t temp[4];  /* Temporary CrypOutBuff */
3250   uint32_t DoKeyIVConfig = 1U; /* By default, carry out peripheral Key and IV configuration */
3251 
3252   if (hcryp->Init.KeyIVConfigSkip == CRYP_KEYIVCONFIG_ONCE)
3253   {
3254     if (hcryp->KeyIVConfig == 1U)
3255     {
3256       /* If the Key and IV configuration has to be done only once
3257          and if it has already been done, skip it */
3258       DoKeyIVConfig = 0U;
3259       hcryp->SizesSum += hcryp->Size; /* Compute message total payload length */
3260     }
3261     else
3262     {
3263       /* If the Key and IV configuration has to be done only once
3264          and if it has not been done already, do it and set KeyIVConfig
3265          to keep track it won't have to be done again next time */
3266       hcryp->KeyIVConfig = 1U;
3267       hcryp->SizesSum = hcryp->Size; /* Merely store payload length */
3268     }
3269   }
3270   else
3271   {
3272     hcryp->SizesSum = hcryp->Size;
3273   }
3274 
3275   if (DoKeyIVConfig == 1U)
3276   {
3277     /*  Reset CrypHeaderCount */
3278     hcryp->CrypHeaderCount = 0U;
3279 
3280     /*************************** Init phase ************************************/
3281 
3282     CRYP_SET_PHASE(hcryp, CRYP_PHASE_INIT);
3283 
3284     /* Set the key */
3285     CRYP_SetKey(hcryp, hcryp->Init.KeySize);
3286 
3287     /* Set the initialization vector and the counter : Initial Counter Block (ICB)*/
3288     hcryp->Instance->IV0LR = *(uint32_t *)(hcryp->Init.pInitVect);
3289     hcryp->Instance->IV0RR = *(uint32_t *)(hcryp->Init.pInitVect + 1);
3290     hcryp->Instance->IV1LR = *(uint32_t *)(hcryp->Init.pInitVect + 2);
3291     hcryp->Instance->IV1RR = *(uint32_t *)(hcryp->Init.pInitVect + 3);
3292 
3293     /* Enable the CRYP peripheral */
3294     __HAL_CRYP_ENABLE(hcryp);
3295 
3296     /*Wait for the CRYPEN bit to be cleared*/
3297     count = CRYP_TIMEOUT_GCMCCMINITPHASE;
3298     do
3299     {
3300       count-- ;
3301       if (count == 0U)
3302       {
3303         /* Disable the CRYP peripheral clock */
3304         __HAL_CRYP_DISABLE(hcryp);
3305 
3306         /* Change state */
3307         hcryp->ErrorCode |= HAL_CRYP_ERROR_TIMEOUT;
3308         hcryp->State = HAL_CRYP_STATE_READY;
3309 
3310         /* Process unlocked */
3311         __HAL_UNLOCK(hcryp);
3312         return HAL_ERROR;
3313       }
3314     } while ((hcryp->Instance->CR & CRYP_CR_CRYPEN) == CRYP_CR_CRYPEN);
3315 
3316     /************************ Header phase *************************************/
3317 
3318     if (CRYP_GCMCCM_SetHeaderPhase_DMA(hcryp) != HAL_OK)
3319     {
3320       return HAL_ERROR;
3321     }
3322 
3323     /************************ Payload phase ************************************/
3324 
3325     /* Set the phase */
3326     hcryp->Phase = CRYP_PHASE_PROCESS;
3327 
3328     /* Disable the CRYP peripheral */
3329     __HAL_CRYP_DISABLE(hcryp);
3330 
3331 #if !defined (CRYP_VER_2_2)
3332     if (hcryp->Version >= REV_ID_B)
3333 #endif /*End of not defined CRYP_VER_2_2*/
3334     {
3335       /* Set to 0 the number of non-valid bytes using NPBLB register*/
3336       MODIFY_REG(hcryp->Instance->CR, CRYP_CR_NPBLB, 0U);
3337     }
3338 
3339     /* Select payload phase once the header phase is performed */
3340     CRYP_SET_PHASE(hcryp, CRYP_PHASE_PAYLOAD);
3341 
3342   } /* if (DoKeyIVConfig == 1U) */
3343 
3344   if (hcryp->Size == 0U)
3345   {
3346     /* Process unLocked */
3347     __HAL_UNLOCK(hcryp);
3348 
3349     /* Change the CRYP state and phase */
3350     hcryp->State = HAL_CRYP_STATE_READY;
3351   }
3352   else if (hcryp->Size >= 16U)
3353   {
3354     /* for STM32H7 below rev.B : Size should be %4  otherwise Tag will  be incorrectly generated for GCM Encryption:
3355     Workaround is implemented in polling mode, so if last block of payload <128bit don't use DMA mode otherwise
3356     TAG is incorrectly generated */
3357 
3358     /*DMA transfer must not include the last block in case of Size is not %16 */
3359     wordsize = wordsize - (wordsize % 4U);
3360 
3361     /*DMA transfer */
3362     CRYP_SetDMAConfig(hcryp, (uint32_t)(hcryp->pCrypInBuffPtr), (uint16_t)wordsize,
3363                       (uint32_t)(hcryp->pCrypOutBuffPtr));
3364   }
3365   else /* length of input data is < 16 */
3366   {
3367     /* Compute the number of padding bytes in last block of payload */
3368     npblb = 16U - (uint32_t)hcryp->Size;
3369 
3370 #if !defined (CRYP_VER_2_2)
3371     if (hcryp->Version >= REV_ID_B)
3372 #endif /*End of not defined CRYP_VER_2_2*/
3373     {
3374       /* Set Npblb in case of AES GCM payload encryption to get right tag*/
3375       if ((hcryp->Instance->CR & CRYP_CR_ALGODIR) == CRYP_OPERATINGMODE_ENCRYPT)
3376       {
3377         /* Specify the number of non-valid bytes using NPBLB register*/
3378         MODIFY_REG(hcryp->Instance->CR, CRYP_CR_NPBLB, npblb << 20);
3379       }
3380     }
3381     /* Enable CRYP to start the final phase */
3382     __HAL_CRYP_ENABLE(hcryp);
3383 
3384     /* Number of valid words (lastwordsize) in last block */
3385     if ((npblb % 4U) == 0U)
3386     {
3387       lastwordsize = (16U - npblb) / 4U;
3388     }
3389     else
3390     {
3391       lastwordsize = ((16U - npblb) / 4U) + 1U;
3392     }
3393 
3394     /* Write the last input block in the IN FIFO */
3395     for (index = 0; index < lastwordsize; index ++)
3396     {
3397       hcryp->Instance->DIN  = *(uint32_t *)(hcryp->pCrypInBuffPtr + hcryp->CrypInCount);
3398       hcryp->CrypInCount++;
3399     }
3400 
3401     /* Pad the data with zeros to have a complete block */
3402     while (index < 4U)
3403     {
3404       hcryp->Instance->DIN  = 0U;
3405       index++;
3406     }
3407 
3408     /* Wait for OFNE flag to be raised */
3409     count = CRYP_TIMEOUT_GCMCCMHEADERPHASE;
3410     do
3411     {
3412       count-- ;
3413       if (count == 0U)
3414       {
3415         /* Disable the CRYP peripheral clock */
3416         __HAL_CRYP_DISABLE(hcryp);
3417 
3418         /* Change state */
3419         hcryp->ErrorCode |= HAL_CRYP_ERROR_TIMEOUT;
3420         hcryp->State = HAL_CRYP_STATE_READY;
3421 
3422         /* Process unlocked */
3423         __HAL_UNLOCK(hcryp);
3424 #if (USE_HAL_CRYP_REGISTER_CALLBACKS == 1)
3425         /*Call registered error callback*/
3426         hcryp->ErrorCallback(hcryp);
3427 #else
3428         /*Call legacy weak error callback*/
3429         HAL_CRYP_ErrorCallback(hcryp);
3430 #endif /* USE_HAL_CRYP_REGISTER_CALLBACKS */
3431       }
3432     } while (HAL_IS_BIT_CLR(hcryp->Instance->SR, CRYP_FLAG_OFNE));
3433 
3434     /*Read the output block from the output FIFO */
3435     for (index = 0U; index < 4U; index++)
3436     {
3437       /* Read the output block from the output FIFO and put them in temporary buffer
3438       then get CrypOutBuff from temporary buffer */
3439       temp[index] = hcryp->Instance->DOUT;
3440     }
3441     for (index = 0; index < lastwordsize; index++)
3442     {
3443       *(uint32_t *)(hcryp->pCrypOutBuffPtr + hcryp->CrypOutCount) = temp[index];
3444       hcryp->CrypOutCount++;
3445     }
3446 
3447     /* Change the CRYP state to ready */
3448     hcryp->State = HAL_CRYP_STATE_READY;
3449 
3450     /* Process unlocked */
3451     __HAL_UNLOCK(hcryp);
3452   }
3453 
3454   /* Return function status */
3455   return HAL_OK;
3456 }
3457 
3458 
3459 /**
3460   * @brief  AES CCM encryption/decryption processing in polling mode
3461   * @param  hcryp: pointer to a CRYP_HandleTypeDef structure that contains
3462   *         the configuration information for CRYP module
3463   * @param  Timeout: Timeout duration
3464   * @retval HAL status
3465   */
CRYP_AESCCM_Process(CRYP_HandleTypeDef * hcryp,uint32_t Timeout)3466 static HAL_StatusTypeDef CRYP_AESCCM_Process(CRYP_HandleTypeDef *hcryp, uint32_t Timeout)
3467 {
3468   uint32_t tickstart;
3469   uint32_t wordsize = (uint32_t)(hcryp->Size) / 4U;
3470   uint32_t npblb ;
3471   uint32_t lastwordsize ;
3472   uint32_t temp[4] ;  /* Temporary CrypOutBuff */
3473   uint32_t index ;
3474   uint16_t outcount;  /* Temporary CrypOutCount Value */
3475   uint32_t DoKeyIVConfig = 1U; /* By default, carry out peripheral Key and IV configuration */
3476 
3477   if (hcryp->Init.KeyIVConfigSkip == CRYP_KEYIVCONFIG_ONCE)
3478   {
3479     if (hcryp->KeyIVConfig == 1U)
3480     {
3481       /* If the Key and IV configuration has to be done only once
3482       and if it has already been done, skip it */
3483       DoKeyIVConfig = 0U;
3484       hcryp->SizesSum += hcryp->Size; /* Compute message total payload length */
3485     }
3486     else
3487     {
3488       /* If the Key and IV configuration has to be done only once
3489       and if it has not been done already, do it and set KeyIVConfig
3490       to keep track it won't have to be done again next time */
3491       hcryp->KeyIVConfig = 1U;
3492       hcryp->SizesSum = hcryp->Size; /* Merely store payload length */
3493     }
3494   }
3495   else
3496   {
3497     hcryp->SizesSum = hcryp->Size;
3498   }
3499 
3500   if (DoKeyIVConfig == 1U)
3501   {
3502     /*  Reset CrypHeaderCount */
3503     hcryp->CrypHeaderCount = 0U;
3504 
3505     /********************** Init phase ******************************************/
3506 
3507     CRYP_SET_PHASE(hcryp, CRYP_PHASE_INIT);
3508 
3509     /* Set the key */
3510     CRYP_SetKey(hcryp, hcryp->Init.KeySize);
3511 
3512     /* Set the initialization vector (IV) with CTR1 information */
3513     hcryp->Instance->IV0LR = (hcryp->Init.B0[0]) & CRYP_CCM_CTR1_0;
3514     hcryp->Instance->IV0RR = hcryp->Init.B0[1];
3515     hcryp->Instance->IV1LR = hcryp->Init.B0[2];
3516     hcryp->Instance->IV1RR = (hcryp->Init.B0[3] & CRYP_CCM_CTR1_1) |  CRYP_CCM_CTR1_2;
3517 
3518     /* Enable the CRYP peripheral */
3519     __HAL_CRYP_ENABLE(hcryp);
3520 
3521 #if defined (CRYP_VER_2_2)
3522     {
3523       /* for STM32H7 rev.B and above Write  B0 packet into CRYP_DR*/
3524       hcryp->Instance->DIN = *(uint32_t *)(hcryp->Init.B0);
3525       hcryp->Instance->DIN = *(uint32_t *)(hcryp->Init.B0 + 1);
3526       hcryp->Instance->DIN = *(uint32_t *)(hcryp->Init.B0 + 2);
3527       hcryp->Instance->DIN = *(uint32_t *)(hcryp->Init.B0 + 3);
3528     }
3529 #else
3530     if (hcryp->Version >= REV_ID_B)
3531     {
3532       /* for STM32H7 rev.B and above Write  B0 packet into CRYP_DR*/
3533       hcryp->Instance->DIN = *(uint32_t *)(hcryp->Init.B0);
3534       hcryp->Instance->DIN = *(uint32_t *)(hcryp->Init.B0 + 1);
3535       hcryp->Instance->DIN = *(uint32_t *)(hcryp->Init.B0 + 2);
3536       hcryp->Instance->DIN = *(uint32_t *)(hcryp->Init.B0 + 3);
3537     }
3538     else /* data has to be swapped according to the DATATYPE */
3539     {
3540       if (hcryp->Init.DataType == CRYP_BYTE_SWAP)
3541       {
3542         hcryp->Instance->DIN = __REV(*(uint32_t *)(hcryp->Init.B0));
3543         hcryp->Instance->DIN = __REV(*(uint32_t *)(hcryp->Init.B0 + 1));
3544         hcryp->Instance->DIN = __REV(*(uint32_t *)(hcryp->Init.B0 + 2));
3545         hcryp->Instance->DIN = __REV(*(uint32_t *)(hcryp->Init.B0 + 3));
3546       }
3547       else if (hcryp->Init.DataType == CRYP_HALFWORD_SWAP)
3548       {
3549         hcryp->Instance->DIN = __ROR(*(uint32_t *)(hcryp->Init.B0), 16);
3550         hcryp->Instance->DIN = __ROR(*(uint32_t *)(hcryp->Init.B0 + 1), 16);
3551         hcryp->Instance->DIN = __ROR(*(uint32_t *)(hcryp->Init.B0 + 2), 16);
3552         hcryp->Instance->DIN = __ROR(*(uint32_t *)(hcryp->Init.B0 + 3), 16);
3553       }
3554       else if (hcryp->Init.DataType == CRYP_BIT_SWAP)
3555       {
3556         hcryp->Instance->DIN = __RBIT(*(uint32_t *)(hcryp->Init.B0));
3557         hcryp->Instance->DIN = __RBIT(*(uint32_t *)(hcryp->Init.B0 + 1));
3558         hcryp->Instance->DIN = __RBIT(*(uint32_t *)(hcryp->Init.B0 + 2));
3559         hcryp->Instance->DIN = __RBIT(*(uint32_t *)(hcryp->Init.B0 + 3));
3560       }
3561       else
3562       {
3563         hcryp->Instance->DIN = *(uint32_t *)(hcryp->Init.B0);
3564         hcryp->Instance->DIN = *(uint32_t *)(hcryp->Init.B0 + 1);
3565         hcryp->Instance->DIN = *(uint32_t *)(hcryp->Init.B0 + 2);
3566         hcryp->Instance->DIN = *(uint32_t *)(hcryp->Init.B0 + 3);
3567       }
3568     }
3569 #endif /* CRYP_VER_2_2 */
3570     /* Get tick */
3571     tickstart = HAL_GetTick();
3572 
3573     /*Wait for the CRYPEN bit to be cleared*/
3574     while ((hcryp->Instance->CR & CRYP_CR_CRYPEN) == CRYP_CR_CRYPEN)
3575     {
3576       /* Check for the Timeout */
3577       if (Timeout != HAL_MAX_DELAY)
3578       {
3579         if (((HAL_GetTick() - tickstart) > Timeout) || (Timeout == 0U))
3580         {
3581           /* Disable the CRYP peripheral clock */
3582           __HAL_CRYP_DISABLE(hcryp);
3583 
3584           /* Change state */
3585           hcryp->ErrorCode |= HAL_CRYP_ERROR_TIMEOUT;
3586           hcryp->State = HAL_CRYP_STATE_READY;
3587 
3588           /* Process unlocked */
3589           __HAL_UNLOCK(hcryp);
3590           return HAL_ERROR;
3591         }
3592       }
3593     }
3594 
3595     /************************* Header phase *************************************/
3596     /* Header block(B1) : associated data length expressed in bytes concatenated
3597     with Associated Data (A)*/
3598 
3599     if (CRYP_GCMCCM_SetHeaderPhase(hcryp, Timeout) != HAL_OK)
3600     {
3601       return HAL_ERROR;
3602     }
3603     /********************** Payload phase ***************************************/
3604 
3605     /* Set the phase */
3606     hcryp->Phase = CRYP_PHASE_PROCESS;
3607 
3608     /* Disable the CRYP peripheral */
3609     __HAL_CRYP_DISABLE(hcryp);
3610 #if !defined (CRYP_VER_2_2)
3611     if (hcryp->Version >= REV_ID_B)
3612 #endif /*End of not defined CRYP_VER_2_2*/
3613     {
3614       /* Set to 0 the number of non-valid bytes using NPBLB register*/
3615       MODIFY_REG(hcryp->Instance->CR, CRYP_CR_NPBLB, 0U);
3616     }
3617 
3618     /* Select payload phase once the header phase is performed */
3619     CRYP_SET_PHASE(hcryp, CRYP_PHASE_PAYLOAD);
3620 
3621     /* Enable the CRYP peripheral */
3622     __HAL_CRYP_ENABLE(hcryp);
3623 
3624   } /* if (DoKeyIVConfig == 1U) */
3625 
3626   if ((hcryp->Size % 16U) != 0U)
3627   {
3628     /* recalculate  wordsize */
3629     wordsize = ((wordsize / 4U) * 4U) ;
3630   }
3631   /* Get tick */
3632   tickstart = HAL_GetTick();
3633 
3634   /*Temporary CrypOutCount Value*/
3635   outcount = hcryp->CrypOutCount;
3636 
3637   /* Write input data and get output data */
3638   while ((hcryp->CrypInCount < wordsize) && (outcount < wordsize))
3639   {
3640     /* Write plain data and get cipher data */
3641     CRYP_AES_ProcessData(hcryp, Timeout);
3642 
3643     /*Temporary CrypOutCount Value*/
3644     outcount = hcryp->CrypOutCount;
3645 
3646     /* Check for the Timeout */
3647     if (Timeout != HAL_MAX_DELAY)
3648     {
3649       if (((HAL_GetTick() - tickstart) > Timeout) || (Timeout == 0U))
3650       {
3651         /* Disable the CRYP peripheral clock */
3652         __HAL_CRYP_DISABLE(hcryp);
3653 
3654         /* Change state */
3655         hcryp->ErrorCode |= HAL_CRYP_ERROR_TIMEOUT;
3656         hcryp->State = HAL_CRYP_STATE_READY;
3657 
3658         /* Process unlocked */
3659         __HAL_UNLOCK(hcryp);
3660         return HAL_ERROR;
3661       }
3662     }
3663   }
3664 
3665   if ((hcryp->Size % 16U) != 0U)
3666   {
3667 #if !defined (CRYP_VER_2_2)
3668     if (hcryp->Version >= REV_ID_B)
3669 #endif /*End of not defined CRYP_VER_2_2*/
3670     {
3671       /* Compute the number of padding bytes in last block of payload */
3672       npblb = ((((uint32_t)(hcryp->Size) / 16U) + 1U) * 16U) - (uint32_t)(hcryp->Size);
3673 
3674       if ((hcryp->Instance->CR & CRYP_CR_ALGODIR) == CRYP_OPERATINGMODE_DECRYPT)
3675       {
3676         /* Disable the CRYP */
3677         __HAL_CRYP_DISABLE(hcryp);
3678 
3679         /* Set Npblb in case of AES CCM payload decryption to get right tag  */
3680         MODIFY_REG(hcryp->Instance->CR, CRYP_CR_NPBLB, npblb << 20);
3681 
3682         /* Enable CRYP to start the final phase */
3683         __HAL_CRYP_ENABLE(hcryp);
3684       }
3685 
3686       /* Number of valid words (lastwordsize) in last block */
3687       if ((npblb % 4U) == 0U)
3688       {
3689         lastwordsize = (16U - npblb) / 4U;
3690       }
3691       else
3692       {
3693         lastwordsize = ((16U - npblb) / 4U) + 1U;
3694       }
3695 
3696       /* Write the last input block in the IN FIFO */
3697       for (index = 0U; index < lastwordsize; index ++)
3698       {
3699         hcryp->Instance->DIN  = *(uint32_t *)(hcryp->pCrypInBuffPtr + hcryp->CrypInCount);
3700         hcryp->CrypInCount++;
3701       }
3702 
3703       /* Pad the data with zeros to have a complete block */
3704       while (index < 4U)
3705       {
3706         hcryp->Instance->DIN  = 0U;
3707         index++;
3708       }
3709 
3710       /* Wait for OFNE flag to be raised */
3711       if (CRYP_WaitOnOFNEFlag(hcryp, Timeout) != HAL_OK)
3712       {
3713         /* Disable the CRYP peripheral clock */
3714         __HAL_CRYP_DISABLE(hcryp);
3715 
3716         /* Change state */
3717         hcryp->ErrorCode |= HAL_CRYP_ERROR_TIMEOUT;
3718         hcryp->State = HAL_CRYP_STATE_READY;
3719 
3720         /* Process Unlocked */
3721         __HAL_UNLOCK(hcryp);
3722 #if (USE_HAL_CRYP_REGISTER_CALLBACKS == 1)
3723         /*Call registered error callback*/
3724         hcryp->ErrorCallback(hcryp);
3725 #else
3726         /*Call legacy weak error callback*/
3727         HAL_CRYP_ErrorCallback(hcryp);
3728 #endif /* USE_HAL_CRYP_REGISTER_CALLBACKS */
3729       }
3730 
3731       /*Read the output block from the output FIFO */
3732       if ((hcryp->Instance->SR & CRYP_FLAG_OFNE) != 0x0U)
3733       {
3734         for (index = 0U; index < 4U; index++)
3735         {
3736           /* Read the output block from the output FIFO and put them in temporary buffer
3737           then get CrypOutBuff from temporary buffer */
3738           temp[index] = hcryp->Instance->DOUT;
3739         }
3740         for (index = 0; index < lastwordsize; index++)
3741         {
3742           *(uint32_t *)(hcryp->pCrypOutBuffPtr + hcryp->CrypOutCount) = temp[index];
3743           hcryp->CrypOutCount++;
3744         }
3745       }
3746     }
3747 #if !defined (CRYP_VER_2_2)
3748     else /* No NPBLB, Workaround to be used */
3749     {
3750       /* CRYP Workaround :  CRYP1 generates correct TAG  during CCM decryption only when ciphertext
3751       blocks size is multiple of 128 bits. If lthe size of the last block of payload is inferior to 128 bits,
3752       when CCM decryption is selected, then the TAG message will be wrong.*/
3753       CRYP_Workaround(hcryp, Timeout);
3754     }
3755 #endif /*End of not defined CRYP_VER_2_2*/
3756   }
3757 
3758   /* Return function status */
3759   return HAL_OK;
3760 }
3761 
3762 /**
3763   * @brief  AES CCM encryption/decryption process in interrupt mode
3764   * @param  hcryp: pointer to a CRYP_HandleTypeDef structure that contains
3765   *         the configuration information for CRYP module
3766   * @retval HAL status
3767   */
CRYP_AESCCM_Process_IT(CRYP_HandleTypeDef * hcryp)3768 static HAL_StatusTypeDef CRYP_AESCCM_Process_IT(CRYP_HandleTypeDef *hcryp)
3769 {
3770   __IO uint32_t count = 0U;
3771   uint32_t DoKeyIVConfig = 1U; /* By default, carry out peripheral Key and IV configuration */
3772 
3773   if (hcryp->Init.KeyIVConfigSkip == CRYP_KEYIVCONFIG_ONCE)
3774   {
3775     if (hcryp->KeyIVConfig == 1U)
3776     {
3777       /* If the Key and IV configuration has to be done only once
3778       and if it has already been done, skip it */
3779       DoKeyIVConfig = 0U;
3780       hcryp->SizesSum += hcryp->Size; /* Compute message total payload length */
3781     }
3782     else
3783     {
3784       /* If the Key and IV configuration has to be done only once
3785       and if it has not been done already, do it and set KeyIVConfig
3786       to keep track it won't have to be done again next time */
3787       hcryp->KeyIVConfig = 1U;
3788       hcryp->SizesSum = hcryp->Size; /* Merely store payload length */
3789     }
3790   }
3791   else
3792   {
3793     hcryp->SizesSum = hcryp->Size;
3794   }
3795 
3796   /* Configure Key, IV and process message (header and payload) */
3797   if (DoKeyIVConfig == 1U)
3798   {
3799     /*  Reset CrypHeaderCount */
3800     hcryp->CrypHeaderCount = 0U;
3801 
3802     /************ Init phase ************/
3803 
3804     CRYP_SET_PHASE(hcryp, CRYP_PHASE_INIT);
3805 
3806     /* Set the key */
3807     CRYP_SetKey(hcryp, hcryp->Init.KeySize);
3808 
3809     /* Set the initialization vector (IV) with CTR1 information */
3810     hcryp->Instance->IV0LR = (hcryp->Init.B0[0]) & CRYP_CCM_CTR1_0;
3811     hcryp->Instance->IV0RR = hcryp->Init.B0[1];
3812     hcryp->Instance->IV1LR = hcryp->Init.B0[2];
3813     hcryp->Instance->IV1RR = (hcryp->Init.B0[3] & CRYP_CCM_CTR1_1) |  CRYP_CCM_CTR1_2;
3814 
3815     /* Enable the CRYP peripheral */
3816     __HAL_CRYP_ENABLE(hcryp);
3817 
3818     /*Write the B0 packet into CRYP_DR*/
3819 #if !defined (CRYP_VER_2_2)
3820     if (hcryp->Version >= REV_ID_B)
3821 #endif /*End of not defined CRYP_VER_2_2*/
3822     {
3823       /* for STM32H7 rev.B and above data has not to be swapped */
3824       hcryp->Instance->DIN = *(uint32_t *)(hcryp->Init.B0);
3825       hcryp->Instance->DIN = *(uint32_t *)(hcryp->Init.B0 + 1);
3826       hcryp->Instance->DIN = *(uint32_t *)(hcryp->Init.B0 + 2);
3827       hcryp->Instance->DIN = *(uint32_t *)(hcryp->Init.B0 + 3);
3828     }
3829 #if !defined (CRYP_VER_2_2)
3830     else /* data has to be swapped according to the DATATYPE */
3831     {
3832       if (hcryp->Init.DataType == CRYP_BYTE_SWAP)
3833       {
3834         hcryp->Instance->DIN = __REV(*(uint32_t *)(hcryp->Init.B0));
3835         hcryp->Instance->DIN = __REV(*(uint32_t *)(hcryp->Init.B0 + 1));
3836         hcryp->Instance->DIN = __REV(*(uint32_t *)(hcryp->Init.B0 + 2));
3837         hcryp->Instance->DIN = __REV(*(uint32_t *)(hcryp->Init.B0 + 3));
3838       }
3839       else if (hcryp->Init.DataType == CRYP_HALFWORD_SWAP)
3840       {
3841         hcryp->Instance->DIN = __ROR(*(uint32_t *)(hcryp->Init.B0), 16);
3842         hcryp->Instance->DIN = __ROR(*(uint32_t *)(hcryp->Init.B0 + 1), 16);
3843         hcryp->Instance->DIN = __ROR(*(uint32_t *)(hcryp->Init.B0 + 2), 16);
3844         hcryp->Instance->DIN = __ROR(*(uint32_t *)(hcryp->Init.B0 + 3), 16);
3845       }
3846       else if (hcryp->Init.DataType == CRYP_BIT_SWAP)
3847       {
3848         hcryp->Instance->DIN = __RBIT(*(uint32_t *)(hcryp->Init.B0));
3849         hcryp->Instance->DIN = __RBIT(*(uint32_t *)(hcryp->Init.B0 + 1));
3850         hcryp->Instance->DIN = __RBIT(*(uint32_t *)(hcryp->Init.B0 + 2));
3851         hcryp->Instance->DIN = __RBIT(*(uint32_t *)(hcryp->Init.B0 + 3));
3852       }
3853       else
3854       {
3855         hcryp->Instance->DIN = *(uint32_t *)(hcryp->Init.B0);
3856         hcryp->Instance->DIN = *(uint32_t *)(hcryp->Init.B0 + 1);
3857         hcryp->Instance->DIN = *(uint32_t *)(hcryp->Init.B0 + 2);
3858         hcryp->Instance->DIN = *(uint32_t *)(hcryp->Init.B0 + 3);
3859       }
3860     }
3861 #endif /*End of not defined CRYP_VER_2_2*/
3862     /*Wait for the CRYPEN bit to be cleared*/
3863     count = CRYP_TIMEOUT_GCMCCMINITPHASE;
3864     do
3865     {
3866       count-- ;
3867       if (count == 0U)
3868       {
3869         /* Disable the CRYP peripheral clock */
3870         __HAL_CRYP_DISABLE(hcryp);
3871 
3872         /* Change state */
3873         hcryp->ErrorCode |= HAL_CRYP_ERROR_TIMEOUT;
3874         hcryp->State = HAL_CRYP_STATE_READY;
3875 
3876         /* Process unlocked */
3877         __HAL_UNLOCK(hcryp);
3878         return HAL_ERROR;
3879       }
3880     } while ((hcryp->Instance->CR & CRYP_CR_CRYPEN) == CRYP_CR_CRYPEN);
3881 
3882     /* Select header phase */
3883     CRYP_SET_PHASE(hcryp, CRYP_PHASE_HEADER);
3884   } /* end of if (DoKeyIVConfig == 1U) */
3885   /* Enable interrupts */
3886   __HAL_CRYP_ENABLE_IT(hcryp, CRYP_IT_INI);
3887 
3888   /* Enable CRYP */
3889   __HAL_CRYP_ENABLE(hcryp);
3890 
3891   /* Return function status */
3892   return HAL_OK;
3893 }
3894 /**
3895   * @brief  AES CCM encryption/decryption process in DMA mode
3896   * @param  hcryp: pointer to a CRYP_HandleTypeDef structure that contains
3897   *         the configuration information for CRYP module
3898   * @retval HAL status
3899   */
CRYP_AESCCM_Process_DMA(CRYP_HandleTypeDef * hcryp)3900 static HAL_StatusTypeDef CRYP_AESCCM_Process_DMA(CRYP_HandleTypeDef *hcryp)
3901 {
3902   __IO uint32_t count    = 0U;
3903   uint32_t wordsize = (uint32_t)(hcryp->Size) / 4U ;
3904   uint32_t index;
3905   uint32_t npblb;
3906   uint32_t lastwordsize;
3907   uint32_t temp[4];  /* Temporary CrypOutBuff */
3908   uint32_t DoKeyIVConfig = 1U; /* By default, carry out peripheral Key and IV configuration */
3909 
3910   if (hcryp->Init.KeyIVConfigSkip == CRYP_KEYIVCONFIG_ONCE)
3911   {
3912     if (hcryp->KeyIVConfig == 1U)
3913     {
3914       /* If the Key and IV configuration has to be done only once
3915       and if it has already been done, skip it */
3916       DoKeyIVConfig = 0U;
3917       hcryp->SizesSum += hcryp->Size; /* Compute message total payload length */
3918     }
3919     else
3920     {
3921       /* If the Key and IV configuration has to be done only once
3922       and if it has not been done already, do it and set KeyIVConfig
3923       to keep track it won't have to be done again next time */
3924       hcryp->KeyIVConfig = 1U;
3925       hcryp->SizesSum = hcryp->Size; /* Merely store payload length */
3926     }
3927   }
3928   else
3929   {
3930     hcryp->SizesSum = hcryp->Size;
3931   }
3932 
3933   if (DoKeyIVConfig == 1U)
3934   {
3935     /*  Reset CrypHeaderCount */
3936     hcryp->CrypHeaderCount = 0U;
3937 
3938     /************************** Init phase **************************************/
3939 
3940     CRYP_SET_PHASE(hcryp, CRYP_PHASE_INIT);
3941 
3942     /* Set the key */
3943     CRYP_SetKey(hcryp, hcryp->Init.KeySize);
3944 
3945     /* Set the initialization vector (IV) with CTR1 information */
3946     hcryp->Instance->IV0LR = (hcryp->Init.B0[0]) & CRYP_CCM_CTR1_0;
3947     hcryp->Instance->IV0RR = hcryp->Init.B0[1];
3948     hcryp->Instance->IV1LR = hcryp->Init.B0[2];
3949     hcryp->Instance->IV1RR = (hcryp->Init.B0[3] & CRYP_CCM_CTR1_1) |  CRYP_CCM_CTR1_2;
3950 
3951     /* Enable the CRYP peripheral */
3952     __HAL_CRYP_ENABLE(hcryp);
3953 
3954     /*Write the B0 packet into CRYP_DR*/
3955 #if !defined (CRYP_VER_2_2)
3956     if (hcryp->Version >= REV_ID_B)
3957 #endif /*End of not defined CRYP_VER_2_2*/
3958     {
3959       /* for STM32H7 rev.B and above data has not to be swapped */
3960       hcryp->Instance->DIN = *(uint32_t *)(hcryp->Init.B0);
3961       hcryp->Instance->DIN = *(uint32_t *)(hcryp->Init.B0 + 1);
3962       hcryp->Instance->DIN = *(uint32_t *)(hcryp->Init.B0 + 2);
3963       hcryp->Instance->DIN = *(uint32_t *)(hcryp->Init.B0 + 3);
3964     }
3965 #if !defined (CRYP_VER_2_2)
3966     else /* data has to be swapped according to the DATATYPE */
3967     {
3968       if (hcryp->Init.DataType == CRYP_BYTE_SWAP)
3969       {
3970         hcryp->Instance->DIN = __REV(*(uint32_t *)(hcryp->Init.B0));
3971         hcryp->Instance->DIN = __REV(*(uint32_t *)(hcryp->Init.B0 + 1));
3972         hcryp->Instance->DIN = __REV(*(uint32_t *)(hcryp->Init.B0 + 2));
3973         hcryp->Instance->DIN = __REV(*(uint32_t *)(hcryp->Init.B0 + 3));
3974       }
3975       else if (hcryp->Init.DataType == CRYP_HALFWORD_SWAP)
3976       {
3977         hcryp->Instance->DIN = __ROR(*(uint32_t *)(hcryp->Init.B0), 16);
3978         hcryp->Instance->DIN = __ROR(*(uint32_t *)(hcryp->Init.B0 + 1), 16);
3979         hcryp->Instance->DIN = __ROR(*(uint32_t *)(hcryp->Init.B0 + 2), 16);
3980         hcryp->Instance->DIN = __ROR(*(uint32_t *)(hcryp->Init.B0 + 3), 16);
3981       }
3982       else if (hcryp->Init.DataType == CRYP_BIT_SWAP)
3983       {
3984         hcryp->Instance->DIN = __RBIT(*(uint32_t *)(hcryp->Init.B0));
3985         hcryp->Instance->DIN = __RBIT(*(uint32_t *)(hcryp->Init.B0 + 1));
3986         hcryp->Instance->DIN = __RBIT(*(uint32_t *)(hcryp->Init.B0 + 2));
3987         hcryp->Instance->DIN = __RBIT(*(uint32_t *)(hcryp->Init.B0 + 3));
3988       }
3989       else
3990       {
3991         hcryp->Instance->DIN = *(uint32_t *)(hcryp->Init.B0);
3992         hcryp->Instance->DIN = *(uint32_t *)(hcryp->Init.B0 + 1);
3993         hcryp->Instance->DIN = *(uint32_t *)(hcryp->Init.B0 + 2);
3994         hcryp->Instance->DIN = *(uint32_t *)(hcryp->Init.B0 + 3);
3995       }
3996     }
3997 #endif /*End of not defined CRYP_VER_2_2*/
3998     /*Wait for the CRYPEN bit to be cleared*/
3999     count = CRYP_TIMEOUT_GCMCCMINITPHASE;
4000     do
4001     {
4002       count-- ;
4003       if (count == 0U)
4004       {
4005         /* Disable the CRYP peripheral clock */
4006         __HAL_CRYP_DISABLE(hcryp);
4007 
4008         /* Change state */
4009         hcryp->ErrorCode |= HAL_CRYP_ERROR_TIMEOUT;
4010         hcryp->State = HAL_CRYP_STATE_READY;
4011 
4012         /* Process unlocked */
4013         __HAL_UNLOCK(hcryp);
4014         return HAL_ERROR;
4015       }
4016     } while ((hcryp->Instance->CR & CRYP_CR_CRYPEN) == CRYP_CR_CRYPEN);
4017 
4018     /********************* Header phase *****************************************/
4019 
4020     if (CRYP_GCMCCM_SetHeaderPhase_DMA(hcryp) != HAL_OK)
4021     {
4022       return HAL_ERROR;
4023     }
4024 
4025     /******************** Payload phase *****************************************/
4026 
4027     /* Set the phase */
4028     hcryp->Phase = CRYP_PHASE_PROCESS;
4029 
4030     /* Disable the CRYP peripheral */
4031     __HAL_CRYP_DISABLE(hcryp);
4032 #if !defined (CRYP_VER_2_2)
4033     if (hcryp->Version >= REV_ID_B)
4034 #endif /*End of not defined CRYP_VER_2_2*/
4035     {
4036       /* Set to 0 the number of non-valid bytes using NPBLB register*/
4037       MODIFY_REG(hcryp->Instance->CR, CRYP_CR_NPBLB, 0U);
4038     }
4039 
4040     /* Select payload phase once the header phase is performed */
4041     CRYP_SET_PHASE(hcryp, CRYP_PHASE_PAYLOAD);
4042   } /* if (DoKeyIVConfig == 1U) */
4043 
4044   if (hcryp->Size == 0U)
4045   {
4046     /* Process unLocked */
4047     __HAL_UNLOCK(hcryp);
4048 
4049     /* Change the CRYP state and phase */
4050     hcryp->State = HAL_CRYP_STATE_READY;
4051   }
4052   else if (hcryp->Size >= 16U)
4053   {
4054     /* for STM32H7 below rev.B ::  Size should be %4  otherwise Tag will  be incorrectly generated for CCM Decryption,
4055     Workaround is implemented in polling mode*/
4056     /*DMA transfer must not include the last block in case of Size is not %16 */
4057     wordsize = wordsize - (wordsize % 4U);
4058 
4059     /*DMA transfer */
4060     CRYP_SetDMAConfig(hcryp, (uint32_t)(hcryp->pCrypInBuffPtr), (uint16_t) wordsize,
4061                       (uint32_t)(hcryp->pCrypOutBuffPtr));
4062   }
4063   else /* length of input data is  < 16U */
4064   {
4065     /* Compute the number of padding bytes in last block of payload */
4066     npblb = 16U - (uint32_t)(hcryp->Size);
4067 
4068 #if !defined (CRYP_VER_2_2)
4069     if (hcryp->Version >= REV_ID_B)
4070 #endif /*End of not defined CRYP_VER_2_2*/
4071     {
4072       /* Set Npblb in case of AES CCM payload decryption to get right tag*/
4073       if ((hcryp->Instance->CR & CRYP_CR_ALGODIR) == CRYP_OPERATINGMODE_DECRYPT)
4074       {
4075         /* Specify the number of non-valid bytes using NPBLB register*/
4076         MODIFY_REG(hcryp->Instance->CR, CRYP_CR_NPBLB, npblb << 20);
4077       }
4078     }
4079     /* Enable CRYP to start the final phase */
4080     __HAL_CRYP_ENABLE(hcryp);
4081 
4082     /* Number of valid words (lastwordsize) in last block */
4083     if ((npblb % 4U) == 0U)
4084     {
4085       lastwordsize = (16U - npblb) / 4U;
4086     }
4087     else
4088     {
4089       lastwordsize = ((16U - npblb) / 4U) + 1U;
4090     }
4091 
4092     /* Write the last input block in the IN FIFO */
4093     for (index = 0U; index < lastwordsize; index ++)
4094     {
4095       hcryp->Instance->DIN  = *(uint32_t *)(hcryp->pCrypInBuffPtr + hcryp->CrypInCount);
4096       hcryp->CrypInCount++;
4097     }
4098 
4099     /* Pad the data with zeros to have a complete block */
4100     while (index < 4U)
4101     {
4102       hcryp->Instance->DIN  = 0U;
4103       index++;
4104     }
4105 
4106     /* Wait for OFNE flag to be raised */
4107     count = CRYP_TIMEOUT_GCMCCMHEADERPHASE;
4108     do
4109     {
4110       count-- ;
4111       if (count == 0U)
4112       {
4113         /* Disable the CRYP peripheral clock */
4114         __HAL_CRYP_DISABLE(hcryp);
4115 
4116         /* Change state */
4117         hcryp->ErrorCode |= HAL_CRYP_ERROR_TIMEOUT;
4118         hcryp->State = HAL_CRYP_STATE_READY;
4119 
4120         /* Process unlocked */
4121         __HAL_UNLOCK(hcryp);
4122 #if (USE_HAL_CRYP_REGISTER_CALLBACKS == 1)
4123         /*Call registered error callback*/
4124         hcryp->ErrorCallback(hcryp);
4125 #else
4126         /*Call legacy weak error callback*/
4127         HAL_CRYP_ErrorCallback(hcryp);
4128 #endif /* USE_HAL_CRYP_REGISTER_CALLBACKS */
4129       }
4130     } while (HAL_IS_BIT_CLR(hcryp->Instance->SR, CRYP_FLAG_OFNE));
4131 
4132     /*Read the output block from the output FIFO */
4133     for (index = 0U; index < 4U; index++)
4134     {
4135       /* Read the output block from the output FIFO and put them in temporary buffer
4136       then get CrypOutBuff from temporary buffer */
4137       temp[index] = hcryp->Instance->DOUT;
4138     }
4139     for (index = 0; index < lastwordsize; index++)
4140     {
4141       *(uint32_t *)(hcryp->pCrypOutBuffPtr + hcryp->CrypOutCount) = temp[index];
4142       hcryp->CrypOutCount++;
4143     }
4144 
4145     /* Change the CRYP state to ready */
4146     hcryp->State = HAL_CRYP_STATE_READY;
4147 
4148     /* Process unlocked */
4149     __HAL_UNLOCK(hcryp);
4150   }
4151 
4152   /* Return function status */
4153   return HAL_OK;
4154 }
4155 
4156 /**
4157   * @brief  Sets the payload phase in interrupt mode
4158   * @param  hcryp: pointer to a CRYP_HandleTypeDef structure that contains
4159   *         the configuration information for CRYP module
4160   * @retval state
4161   */
CRYP_GCMCCM_SetPayloadPhase_IT(CRYP_HandleTypeDef * hcryp)4162 static void CRYP_GCMCCM_SetPayloadPhase_IT(CRYP_HandleTypeDef *hcryp)
4163 {
4164   uint32_t loopcounter;
4165   uint32_t temp[4];  /* Temporary CrypOutBuff */
4166   uint32_t lastwordsize;
4167   uint32_t npblb;
4168   uint32_t temp_cr_algodir;
4169   uint8_t negative = 0U;
4170   uint32_t i;
4171 
4172   /***************************** Payload phase *******************************/
4173 
4174   if ((hcryp->Size / 4U) < hcryp->CrypInCount)
4175   {
4176     negative = 1U;
4177   }
4178 
4179   if (hcryp->Size == 0U)
4180   {
4181     /* Disable interrupts */
4182     __HAL_CRYP_DISABLE_IT(hcryp, CRYP_IT_INI | CRYP_IT_OUTI);
4183 
4184     /* Process unlocked */
4185     __HAL_UNLOCK(hcryp);
4186 
4187     /* Change the CRYP state */
4188     hcryp->State = HAL_CRYP_STATE_READY;
4189   }
4190 
4191   else if ((((hcryp->Size / 4U) - (hcryp->CrypInCount)) >= 4U) &&
4192            (negative == 0U))
4193   {
4194     if ((hcryp->Instance->IMSCR & CRYP_IMSCR_INIM) != 0x0U)
4195     {
4196       /* Write the input block in the IN FIFO */
4197       hcryp->Instance->DIN  = *(uint32_t *)(hcryp->pCrypInBuffPtr + hcryp->CrypInCount);
4198       hcryp->CrypInCount++;
4199       hcryp->Instance->DIN  = *(uint32_t *)(hcryp->pCrypInBuffPtr + hcryp->CrypInCount);
4200       hcryp->CrypInCount++;
4201       hcryp->Instance->DIN  = *(uint32_t *)(hcryp->pCrypInBuffPtr + hcryp->CrypInCount);
4202       hcryp->CrypInCount++;
4203       hcryp->Instance->DIN  = *(uint32_t *)(hcryp->pCrypInBuffPtr + hcryp->CrypInCount);
4204       hcryp->CrypInCount++;
4205       if (((hcryp->Size / 4U) == hcryp->CrypInCount) && ((hcryp->Size % 16U) == 0U))
4206       {
4207         /* Disable interrupts */
4208         __HAL_CRYP_DISABLE_IT(hcryp, CRYP_IT_INI);
4209         /* Call the input data transfer complete callback */
4210 #if (USE_HAL_CRYP_REGISTER_CALLBACKS == 1U)
4211         /*Call registered Input complete callback*/
4212         hcryp->InCpltCallback(hcryp);
4213 #else
4214         /*Call legacy weak Input complete callback*/
4215         HAL_CRYP_InCpltCallback(hcryp);
4216 #endif /* USE_HAL_CRYP_REGISTER_CALLBACKS */
4217       }
4218 
4219       if (hcryp->CrypOutCount < (hcryp->Size / 4U))
4220       {
4221         if ((hcryp->Instance->SR & CRYP_FLAG_OFNE) != 0x0U)
4222         {
4223           /* Read the output block from the Output FIFO and put them in temporary buffer
4224           then get CrypOutBuff from temporary buffer  */
4225           for (i = 0U; i < 4U; i++)
4226           {
4227             temp[i] = hcryp->Instance->DOUT;
4228           }
4229           i = 0U;
4230           while (((hcryp->CrypOutCount < ((hcryp->Size) / 4U))) && (i < 4U))
4231           {
4232             *(uint32_t *)(hcryp->pCrypOutBuffPtr + hcryp->CrypOutCount) = temp[i];
4233             hcryp->CrypOutCount++;
4234             i++;
4235           }
4236           if (((hcryp->Size / 4U) == hcryp->CrypOutCount) && ((hcryp->Size % 16U) == 0U))
4237           {
4238             /* Disable interrupts */
4239             __HAL_CRYP_DISABLE_IT(hcryp, CRYP_IT_OUTI);
4240 
4241             /* Change the CRYP state */
4242             hcryp->State = HAL_CRYP_STATE_READY;
4243 
4244             /* Disable CRYP */
4245             __HAL_CRYP_DISABLE(hcryp);
4246 
4247             /* Process unlocked */
4248             __HAL_UNLOCK(hcryp);
4249 
4250             /* Call output transfer complete callback */
4251 #if (USE_HAL_CRYP_REGISTER_CALLBACKS == 1U)
4252             /*Call registered Output complete callback*/
4253             hcryp->OutCpltCallback(hcryp);
4254 #else
4255             /*Call legacy weak Output complete callback*/
4256             HAL_CRYP_OutCpltCallback(hcryp);
4257 #endif /* USE_HAL_CRYP_REGISTER_CALLBACKS */
4258           }
4259         }
4260       }
4261     }
4262   }
4263   else if ((hcryp->Size % 16U) != 0U)
4264   {
4265     /* Set padding only in case of input fifo interrupt */
4266     if ((hcryp->Instance->IMSCR & CRYP_IMSCR_INIM) != 0x0U)
4267     {
4268       /* Compute the number of padding bytes in last block of payload */
4269       npblb = ((((uint32_t)hcryp->Size / 16U) + 1U) * 16U) - (uint32_t)(hcryp->Size);
4270 
4271 #if !defined (CRYP_VER_2_2)
4272       if (hcryp->Version >= REV_ID_B)
4273 #endif /*End of not defined CRYP_VER_2_2*/
4274       {
4275         /* Set Npblb in case of AES GCM payload encryption and CCM decryption to get right tag */
4276         temp_cr_algodir = hcryp->Instance->CR & CRYP_CR_ALGODIR;
4277 
4278         if (((temp_cr_algodir == CRYP_OPERATINGMODE_ENCRYPT) && (hcryp->Init.Algorithm == CRYP_AES_GCM)) ||
4279             ((temp_cr_algodir == CRYP_OPERATINGMODE_DECRYPT) && (hcryp->Init.Algorithm == CRYP_AES_CCM)))
4280         {
4281           /* Disable the CRYP */
4282           __HAL_CRYP_DISABLE(hcryp);
4283 
4284           /* Specify the number of non-valid bytes using NPBLB register*/
4285           MODIFY_REG(hcryp->Instance->CR, CRYP_CR_NPBLB, npblb << 20);
4286 
4287           /* Enable CRYP to start the final phase */
4288           __HAL_CRYP_ENABLE(hcryp);
4289         }
4290       }
4291 
4292       /* Number of valid words (lastwordsize) in last block */
4293       if ((npblb % 4U) == 0U)
4294       {
4295         lastwordsize = (16U - npblb) / 4U;
4296       }
4297       else
4298       {
4299         lastwordsize = ((16U - npblb) / 4U) + 1U;
4300       }
4301 
4302       /* Write the last input block in the IN FIFO */
4303       for (loopcounter = 0U; loopcounter < lastwordsize; loopcounter++)
4304       {
4305         hcryp->Instance->DIN  = *(uint32_t *)(hcryp->pCrypInBuffPtr + hcryp->CrypInCount);
4306         hcryp->CrypInCount++;
4307       }
4308       /* Pad the data with zeros to have a complete block */
4309       while (loopcounter < 4U)
4310       {
4311         hcryp->Instance->DIN  = 0U;
4312         loopcounter++;
4313       }
4314 
4315       /* Disable the input FIFO Interrupt */
4316       __HAL_CRYP_DISABLE_IT(hcryp, CRYP_IT_INI);
4317     }
4318 
4319     /*Read the output block from the output FIFO */
4320     if ((hcryp->Instance->SR & CRYP_FLAG_OFNE) != 0x0U)
4321     {
4322       for (i = 0U; i < 4U; i++)
4323       {
4324         temp[i] = hcryp->Instance->DOUT;
4325       }
4326       if (((hcryp->Size) / 4U) == 0U)
4327       {
4328         for (i = 0U; (uint16_t)i < ((hcryp->Size) % 4U); i++)
4329         {
4330           *(uint32_t *)(hcryp->pCrypOutBuffPtr + hcryp->CrypOutCount) = temp[i];
4331           hcryp->CrypOutCount++;
4332         }
4333       }
4334       i = 0U;
4335       while (((hcryp->CrypOutCount < ((hcryp->Size) / 4U))) && (i < 4U))
4336       {
4337         *(uint32_t *)(hcryp->pCrypOutBuffPtr + hcryp->CrypOutCount) = temp[i];
4338         hcryp->CrypOutCount++;
4339         i++;
4340       }
4341     }
4342 
4343     /* Disable the output FIFO Interrupt */
4344     if (hcryp->CrypOutCount >= ((hcryp->Size) / 4U))
4345     {
4346       /* Disable interrupts */
4347       __HAL_CRYP_DISABLE_IT(hcryp, CRYP_IT_OUTI | CRYP_IT_INI);
4348 
4349       /* Change the CRYP peripheral state */
4350       hcryp->State = HAL_CRYP_STATE_READY;
4351 
4352       /* Process unlocked */
4353       __HAL_UNLOCK(hcryp);
4354 
4355       /* Call output transfer complete callback */
4356 #if (USE_HAL_CRYP_REGISTER_CALLBACKS == 1U)
4357       /*Call registered Output complete callback*/
4358       hcryp->OutCpltCallback(hcryp);
4359 #else
4360       /*Call legacy weak Output complete callback*/
4361       HAL_CRYP_OutCpltCallback(hcryp);
4362 #endif /* USE_HAL_CRYP_REGISTER_CALLBACKS */
4363     }
4364   }
4365   else
4366   {
4367     /* Nothing to do */
4368   }
4369 }
4370 
4371 
4372 /**
4373   * @brief  Sets the header phase in polling mode
4374   * @param  hcryp: pointer to a CRYP_HandleTypeDef structure that contains
4375   *         the configuration information for CRYP module(Header & HeaderSize)
4376   * @param  Timeout: Timeout value
4377   * @retval state
4378   */
CRYP_GCMCCM_SetHeaderPhase(CRYP_HandleTypeDef * hcryp,uint32_t Timeout)4379 static HAL_StatusTypeDef CRYP_GCMCCM_SetHeaderPhase(CRYP_HandleTypeDef *hcryp, uint32_t Timeout)
4380 {
4381   uint32_t loopcounter;
4382   uint32_t size_in_bytes;
4383   uint32_t tmp;
4384   uint32_t mask[4] = {0x0U, 0x0FFU, 0x0FFFFU, 0x0FFFFFFU};
4385 
4386   /***************************** Header phase for GCM/GMAC or CCM *********************************/
4387 
4388 
4389   if (hcryp->Init.HeaderWidthUnit == CRYP_HEADERWIDTHUNIT_WORD)
4390   {
4391     size_in_bytes = hcryp->Init.HeaderSize * 4U;
4392   }
4393   else
4394   {
4395     size_in_bytes = hcryp->Init.HeaderSize;
4396   }
4397 
4398   if ((size_in_bytes != 0U))
4399   {
4400     /* Select header phase */
4401     CRYP_SET_PHASE(hcryp, CRYP_PHASE_HEADER);
4402 
4403     /* Enable the CRYP peripheral */
4404     __HAL_CRYP_ENABLE(hcryp);
4405 
4406     /* If size_in_bytes is a multiple of blocks (a multiple of four 32-bits words ) */
4407     if ((size_in_bytes % 16U) == 0U)
4408     {
4409       /*  No padding */
4410       for (loopcounter = 0U; (loopcounter < (size_in_bytes / 4U)); loopcounter += 4U)
4411 
4412       {
4413         hcryp->Instance->DIN = *(uint32_t *)(hcryp->Init.Header + hcryp->CrypHeaderCount);
4414         hcryp->CrypHeaderCount++ ;
4415         hcryp->Instance->DIN = *(uint32_t *)(hcryp->Init.Header + hcryp->CrypHeaderCount);
4416         hcryp->CrypHeaderCount++ ;
4417         hcryp->Instance->DIN = *(uint32_t *)(hcryp->Init.Header + hcryp->CrypHeaderCount);
4418         hcryp->CrypHeaderCount++ ;
4419         hcryp->Instance->DIN = *(uint32_t *)(hcryp->Init.Header + hcryp->CrypHeaderCount);
4420         hcryp->CrypHeaderCount++ ;
4421 
4422         /* Wait for IFEM to be raised */
4423         if (CRYP_WaitOnIFEMFlag(hcryp, Timeout) != HAL_OK)
4424         {
4425           /* Disable the CRYP peripheral clock */
4426           __HAL_CRYP_DISABLE(hcryp);
4427 
4428           /* Change state */
4429           hcryp->ErrorCode |= HAL_CRYP_ERROR_TIMEOUT;
4430           hcryp->State = HAL_CRYP_STATE_READY;
4431 
4432           /* Process unlocked */
4433           __HAL_UNLOCK(hcryp);
4434           return HAL_ERROR;
4435         }
4436       }
4437     }
4438     else
4439     {
4440       /* Write header block in the IN FIFO without last block */
4441       for (loopcounter = 0U; (loopcounter < ((size_in_bytes / 16U) * 4U)); loopcounter += 4U)
4442       {
4443         hcryp->Instance->DIN = *(uint32_t *)(hcryp->Init.Header + hcryp->CrypHeaderCount);
4444         hcryp->CrypHeaderCount++ ;
4445         hcryp->Instance->DIN = *(uint32_t *)(hcryp->Init.Header + hcryp->CrypHeaderCount);
4446         hcryp->CrypHeaderCount++ ;
4447         hcryp->Instance->DIN = *(uint32_t *)(hcryp->Init.Header + hcryp->CrypHeaderCount);
4448         hcryp->CrypHeaderCount++ ;
4449         hcryp->Instance->DIN = *(uint32_t *)(hcryp->Init.Header + hcryp->CrypHeaderCount);
4450         hcryp->CrypHeaderCount++ ;
4451 
4452         /* Wait for IFEM to be raised */
4453         if (CRYP_WaitOnIFEMFlag(hcryp, Timeout) != HAL_OK)
4454         {
4455           /* Disable the CRYP peripheral clock */
4456           __HAL_CRYP_DISABLE(hcryp);
4457 
4458           /* Change state */
4459           hcryp->ErrorCode |= HAL_CRYP_ERROR_TIMEOUT;
4460           hcryp->State = HAL_CRYP_STATE_READY;
4461 
4462           /* Process unlocked */
4463           __HAL_UNLOCK(hcryp);
4464           return HAL_ERROR;
4465         }
4466       }
4467       /*  Last block optionally pad the data with zeros*/
4468       for (loopcounter = 0U; (loopcounter < ((size_in_bytes / 4U) % 4U)); loopcounter++)
4469       {
4470         hcryp->Instance->DIN = *(uint32_t *)(hcryp->Init.Header + hcryp->CrypHeaderCount);
4471         hcryp->CrypHeaderCount++ ;
4472       }
4473       /* If the header size is a multiple of words */
4474       if ((size_in_bytes % 4U) == 0U)
4475       {
4476         /* Pad the data with zeros to have a complete block */
4477         while (loopcounter < 4U)
4478         {
4479           hcryp->Instance->DIN = 0x0U;
4480           loopcounter++;
4481         }
4482       }
4483       else
4484       {
4485         /* Enter last bytes, padded with zeroes */
4486         tmp =  *(uint32_t *)(hcryp->Init.Header + hcryp->CrypHeaderCount);
4487         tmp &= mask[size_in_bytes % 4U];
4488         hcryp->Instance->DIN = tmp;
4489         loopcounter++;
4490         /* Pad the data with zeros to have a complete block */
4491         while (loopcounter < 4U)
4492         {
4493           hcryp->Instance->DIN = 0x0U;
4494           loopcounter++;
4495         }
4496       }
4497       /* Wait for CCF IFEM to be raised */
4498       if (CRYP_WaitOnIFEMFlag(hcryp, Timeout) != HAL_OK)
4499       {
4500         /* Disable the CRYP peripheral clock */
4501         __HAL_CRYP_DISABLE(hcryp);
4502 
4503         /* Change state */
4504         hcryp->ErrorCode |= HAL_CRYP_ERROR_TIMEOUT;
4505         hcryp->State = HAL_CRYP_STATE_READY;
4506 
4507         /* Process unlocked */
4508         __HAL_UNLOCK(hcryp);
4509         return HAL_ERROR;
4510       }
4511     }
4512     /* Wait until the complete message has been processed */
4513     if (CRYP_WaitOnBUSYFlag(hcryp, Timeout) != HAL_OK)
4514     {
4515       /* Disable the CRYP peripheral clock */
4516       __HAL_CRYP_DISABLE(hcryp);
4517 
4518       /* Change state */
4519       hcryp->ErrorCode |= HAL_CRYP_ERROR_TIMEOUT;
4520       hcryp->State = HAL_CRYP_STATE_READY;
4521 
4522       /* Process unlocked & return error */
4523       __HAL_UNLOCK(hcryp);
4524       return HAL_ERROR;
4525     }
4526   }
4527   /* Return function status */
4528   return HAL_OK;
4529 }
4530 
4531 /**
4532   * @brief  Sets the header phase when using DMA in process
4533   * @param  hcryp: pointer to a CRYP_HandleTypeDef structure that contains
4534   *         the configuration information for CRYP module(Header & HeaderSize)
4535   * @retval None
4536   */
CRYP_GCMCCM_SetHeaderPhase_DMA(CRYP_HandleTypeDef * hcryp)4537 static HAL_StatusTypeDef CRYP_GCMCCM_SetHeaderPhase_DMA(CRYP_HandleTypeDef *hcryp)
4538 {
4539   __IO uint32_t count  = 0U;
4540   uint32_t loopcounter;
4541 
4542   /***************************** Header phase for GCM/GMAC or CCM *********************************/
4543   if ((hcryp->Init.HeaderSize != 0U))
4544   {
4545     /* Select header phase */
4546     CRYP_SET_PHASE(hcryp, CRYP_PHASE_HEADER);
4547 
4548     /* Enable the CRYP peripheral */
4549     __HAL_CRYP_ENABLE(hcryp);
4550 
4551     if ((hcryp->Init.HeaderSize % 4U) == 0U)
4552     {
4553       /* HeaderSize %4, no padding */
4554       for (loopcounter = 0U; (loopcounter < hcryp->Init.HeaderSize); loopcounter += 4U)
4555       {
4556         hcryp->Instance->DIN = *(uint32_t *)(hcryp->Init.Header + hcryp->CrypHeaderCount);
4557         hcryp->CrypHeaderCount++ ;
4558         hcryp->Instance->DIN = *(uint32_t *)(hcryp->Init.Header + hcryp->CrypHeaderCount);
4559         hcryp->CrypHeaderCount++ ;
4560         hcryp->Instance->DIN = *(uint32_t *)(hcryp->Init.Header + hcryp->CrypHeaderCount);
4561         hcryp->CrypHeaderCount++ ;
4562         hcryp->Instance->DIN = *(uint32_t *)(hcryp->Init.Header + hcryp->CrypHeaderCount);
4563         hcryp->CrypHeaderCount++ ;
4564 
4565         /* Wait for IFEM to be raised */
4566         count = CRYP_TIMEOUT_GCMCCMHEADERPHASE;
4567         do
4568         {
4569           count-- ;
4570           if (count == 0U)
4571           {
4572             /* Disable the CRYP peripheral clock */
4573             __HAL_CRYP_DISABLE(hcryp);
4574 
4575             /* Change state */
4576             hcryp->ErrorCode |= HAL_CRYP_ERROR_TIMEOUT;
4577             hcryp->State = HAL_CRYP_STATE_READY;
4578 
4579             /* Process unlocked */
4580             __HAL_UNLOCK(hcryp);
4581             return HAL_ERROR;
4582           }
4583         } while (HAL_IS_BIT_CLR(hcryp->Instance->SR, CRYP_FLAG_IFEM));
4584       }
4585     }
4586     else
4587     {
4588       /*Write header block in the IN FIFO without last block */
4589       for (loopcounter = 0U; (loopcounter < ((hcryp->Init.HeaderSize) - (hcryp->Init.HeaderSize % 4U)));
4590            loopcounter += 4U)
4591       {
4592         hcryp->Instance->DIN = *(uint32_t *)(hcryp->Init.Header + hcryp->CrypHeaderCount);
4593         hcryp->CrypHeaderCount++ ;
4594         hcryp->Instance->DIN = *(uint32_t *)(hcryp->Init.Header + hcryp->CrypHeaderCount);
4595         hcryp->CrypHeaderCount++ ;
4596         hcryp->Instance->DIN = *(uint32_t *)(hcryp->Init.Header + hcryp->CrypHeaderCount);
4597         hcryp->CrypHeaderCount++ ;
4598         hcryp->Instance->DIN = *(uint32_t *)(hcryp->Init.Header + hcryp->CrypHeaderCount);
4599         hcryp->CrypHeaderCount++ ;
4600 
4601         /* Wait for IFEM to be raised */
4602         count = CRYP_TIMEOUT_GCMCCMHEADERPHASE;
4603         do
4604         {
4605           count-- ;
4606           if (count == 0U)
4607           {
4608             /* Disable the CRYP peripheral clock */
4609             __HAL_CRYP_DISABLE(hcryp);
4610 
4611             /* Change state */
4612             hcryp->ErrorCode |= HAL_CRYP_ERROR_TIMEOUT;
4613             hcryp->State = HAL_CRYP_STATE_READY;
4614 
4615             /* Process unlocked */
4616             __HAL_UNLOCK(hcryp);
4617             return HAL_ERROR;
4618           }
4619         } while (HAL_IS_BIT_CLR(hcryp->Instance->SR, CRYP_FLAG_IFEM));
4620       }
4621       /*  Last block optionally pad the data with zeros*/
4622       for (loopcounter = 0U; (loopcounter < (hcryp->Init.HeaderSize % 4U)); loopcounter++)
4623       {
4624         hcryp->Instance->DIN = *(uint32_t *)(hcryp->Init.Header + hcryp->CrypHeaderCount);
4625         hcryp->CrypHeaderCount++ ;
4626       }
4627       while (loopcounter < 4U)
4628       {
4629         /* Pad the data with zeros to have a complete block */
4630         hcryp->Instance->DIN = 0x0U;
4631         loopcounter++;
4632       }
4633       /* Wait for IFEM to be raised */
4634       count = CRYP_TIMEOUT_GCMCCMHEADERPHASE;
4635       do
4636       {
4637         count-- ;
4638         if (count == 0U)
4639         {
4640           /* Disable the CRYP peripheral clock */
4641           __HAL_CRYP_DISABLE(hcryp);
4642           /* Change state */
4643           hcryp->ErrorCode |= HAL_CRYP_ERROR_TIMEOUT;
4644           hcryp->State = HAL_CRYP_STATE_READY;
4645           /* Process unlocked */
4646           __HAL_UNLOCK(hcryp);
4647           return HAL_ERROR;
4648         }
4649       } while (HAL_IS_BIT_CLR(hcryp->Instance->SR, CRYP_FLAG_IFEM));
4650     }
4651     /* Wait until the complete message has been processed */
4652     count = CRYP_TIMEOUT_GCMCCMHEADERPHASE;
4653     do
4654     {
4655       count-- ;
4656       if (count == 0U)
4657       {
4658         /* Disable the CRYP peripheral clock */
4659         __HAL_CRYP_DISABLE(hcryp);
4660         /* Change state */
4661         hcryp->ErrorCode |= HAL_CRYP_ERROR_TIMEOUT;
4662         hcryp->State = HAL_CRYP_STATE_READY;
4663         /* Process unlocked */
4664         __HAL_UNLOCK(hcryp);
4665         return HAL_ERROR;
4666       }
4667     } while (HAL_IS_BIT_SET(hcryp->Instance->SR, CRYP_FLAG_BUSY));
4668   }
4669 
4670   /* Return function status */
4671   return HAL_OK;
4672 }
4673 
4674 /**
4675   * @brief  Sets the header phase in interrupt mode
4676   * @param  hcryp: pointer to a CRYP_HandleTypeDef structure that contains
4677   *         the configuration information for CRYP module(Header & HeaderSize)
4678   * @retval None
4679   */
CRYP_GCMCCM_SetHeaderPhase_IT(CRYP_HandleTypeDef * hcryp)4680 static void CRYP_GCMCCM_SetHeaderPhase_IT(CRYP_HandleTypeDef *hcryp)
4681 {
4682   uint32_t loopcounter;
4683 
4684   /***************************** Header phase *********************************/
4685 
4686   if (hcryp->Init.HeaderSize ==  hcryp->CrypHeaderCount)
4687   {
4688     /* Disable interrupts */
4689     __HAL_CRYP_DISABLE_IT(hcryp, CRYP_IT_INI);
4690 
4691     /* Disable the CRYP peripheral */
4692     __HAL_CRYP_DISABLE(hcryp);
4693 
4694 #if !defined (CRYP_VER_2_2)
4695     if (hcryp->Version >= REV_ID_B)
4696 #endif /*End of not defined CRYP_VER_2_2*/
4697     {
4698       /* Set to 0 the number of non-valid bytes using NPBLB register*/
4699       MODIFY_REG(hcryp->Instance->CR, CRYP_CR_NPBLB, 0U);
4700     }
4701 
4702     /* Set the phase */
4703     hcryp->Phase = CRYP_PHASE_PROCESS;
4704 
4705     /* Select payload phase once the header phase is performed */
4706     CRYP_SET_PHASE(hcryp, CRYP_PHASE_PAYLOAD);
4707 
4708     /* Enable Interrupts */
4709     __HAL_CRYP_ENABLE_IT(hcryp, CRYP_IT_INI | CRYP_IT_OUTI);
4710 
4711     /* Enable the CRYP peripheral */
4712     __HAL_CRYP_ENABLE(hcryp);
4713   }
4714   else if (((hcryp->Init.HeaderSize) - (hcryp->CrypHeaderCount)) >= 4U)
4715 
4716   {
4717     /* HeaderSize %4, no padding */
4718     hcryp->Instance->DIN = *(uint32_t *)(hcryp->Init.Header + hcryp->CrypHeaderCount);
4719     hcryp->CrypHeaderCount++ ;
4720     hcryp->Instance->DIN = *(uint32_t *)(hcryp->Init.Header + hcryp->CrypHeaderCount);
4721     hcryp->CrypHeaderCount++  ;
4722     hcryp->Instance->DIN = *(uint32_t *)(hcryp->Init.Header + hcryp->CrypHeaderCount);
4723     hcryp->CrypHeaderCount++ ;
4724     hcryp->Instance->DIN = *(uint32_t *)(hcryp->Init.Header + hcryp->CrypHeaderCount);
4725     hcryp->CrypHeaderCount++ ;
4726   }
4727   else
4728   {
4729     /*  Last block optionally pad the data with zeros*/
4730     for (loopcounter = 0U; loopcounter < (hcryp->Init.HeaderSize % 4U); loopcounter++)
4731     {
4732       hcryp->Instance->DIN = *(uint32_t *)(hcryp->Init.Header + hcryp->CrypHeaderCount);
4733       hcryp->CrypHeaderCount++ ;
4734     }
4735     while (loopcounter < 4U)
4736     {
4737       /* Pad the data with zeros to have a complete block */
4738       hcryp->Instance->DIN = 0x0U;
4739       loopcounter++;
4740     }
4741   }
4742 }
4743 
4744 #if !defined (CRYP_VER_2_2)
4745 /**
4746   * @brief  Workaround used for GCM/CCM mode.
4747   * @param  hcryp: pointer to a CRYP_HandleTypeDef structure that contains
4748   *         the configuration information for CRYP module
4749   * @param  Timeout: Timeout value
4750   * @retval None
4751   */
CRYP_Workaround(CRYP_HandleTypeDef * hcryp,uint32_t Timeout)4752 static void CRYP_Workaround(CRYP_HandleTypeDef *hcryp, uint32_t Timeout)
4753 {
4754   uint32_t  iv1temp;
4755   uint32_t  temp[4] = {0};
4756   uint32_t  temp2[4] = {0};
4757   uint32_t intermediate_data[4] = {0};
4758   uint32_t index;
4759   uint32_t lastwordsize;
4760   uint32_t npblb;
4761 
4762   /* Compute the number of padding bytes in last block of payload */
4763   npblb = ((((uint32_t)(hcryp->Size) / 16U) + 1U) * 16U) - (uint32_t)(hcryp->Size);
4764 
4765   /* Number of valid words (lastwordsize) in last block */
4766   if ((npblb % 4U) == 0U)
4767   {
4768     lastwordsize = (16U - npblb) / 4U;
4769   }
4770   else
4771   {
4772     lastwordsize = ((16U - npblb) / 4U) + 1U;
4773   }
4774 
4775   /* Workaround 2, case GCM encryption */
4776   if (hcryp->Init.Algorithm == CRYP_AES_GCM)
4777   {
4778     if ((hcryp->Instance->CR & CRYP_CR_ALGODIR) == CRYP_OPERATINGMODE_ENCRYPT)
4779     {
4780       /*Workaround in order to properly compute authentication tags while doing
4781        a GCM encryption with the last block of payload size inferior to 128 bits*/
4782       /* Disable CRYP to start the final phase */
4783       __HAL_CRYP_DISABLE(hcryp);
4784 
4785       /*Update CRYP_IV1R register and ALGOMODE*/
4786       hcryp->Instance->IV1RR = ((hcryp->Instance->CSGCMCCM7R) - 1U);
4787       MODIFY_REG(hcryp->Instance->CR, CRYP_CR_ALGOMODE, CRYP_AES_CTR);
4788 
4789       /* Enable CRYP to start the final phase */
4790       __HAL_CRYP_ENABLE(hcryp);
4791     }
4792 
4793     for (index = 0; index < lastwordsize ; index ++)
4794     {
4795       /* Write the last input block in the IN FIFO */
4796       hcryp->Instance->DIN  = *(uint32_t *)(hcryp->pCrypInBuffPtr + hcryp->CrypInCount);
4797       hcryp->CrypInCount++;
4798     }
4799     while (index < 4U)
4800     {
4801       /* Pad the data with zeros to have a complete block */
4802       hcryp->Instance->DIN  = 0U;
4803       index++;
4804     }
4805     /* Wait for OFNE flag to be raised */
4806     if (CRYP_WaitOnOFNEFlag(hcryp, Timeout) != HAL_OK)
4807     {
4808       /* Disable the CRYP peripheral clock */
4809       __HAL_CRYP_DISABLE(hcryp);
4810 
4811       /* Change state */
4812       hcryp->ErrorCode |= HAL_CRYP_ERROR_TIMEOUT;
4813       hcryp->State = HAL_CRYP_STATE_READY;
4814 
4815       /* Process Unlocked */
4816       __HAL_UNLOCK(hcryp);
4817 #if (USE_HAL_CRYP_REGISTER_CALLBACKS == 1)
4818       /*Call registered error callback*/
4819       hcryp->ErrorCallback(hcryp);
4820 #else
4821       /*Call legacy weak error callback*/
4822       HAL_CRYP_ErrorCallback(hcryp);
4823 #endif /* USE_HAL_CRYP_REGISTER_CALLBACKS */
4824     }
4825     if ((hcryp->Instance->SR & CRYP_FLAG_OFNE) != 0x0U)
4826     {
4827       for (index = 0U; index < 4U; index++)
4828       {
4829         /* Read the output block from the output FIFO */
4830         intermediate_data[index] = hcryp->Instance->DOUT;
4831 
4832         /* Intermediate data buffer to be used in for the workaround*/
4833         *(uint32_t *)(hcryp->pCrypOutBuffPtr + (hcryp->CrypOutCount)) = intermediate_data[index];
4834         hcryp->CrypOutCount++;
4835       }
4836     }
4837 
4838     if ((hcryp->Instance->CR & CRYP_CR_ALGODIR) == CRYP_OPERATINGMODE_ENCRYPT)
4839     {
4840       /*workaround in order to properly compute authentication tags while doing
4841       a GCM encryption with the last block of payload size inferior to 128 bits*/
4842       /* Change the AES mode to GCM mode and Select Final phase */
4843       /* configured  CHMOD GCM   */
4844       MODIFY_REG(hcryp->Instance->CR, CRYP_CR_ALGOMODE, CRYP_AES_GCM);
4845 
4846       /* configured  final phase  */
4847       MODIFY_REG(hcryp->Instance->CR, CRYP_CR_GCM_CCMPH, CRYP_PHASE_FINAL);
4848 
4849       if ((hcryp->Instance->CR & CRYP_CR_DATATYPE) == CRYP_NO_SWAP)
4850       {
4851         if ((npblb % 4U) == 1U)
4852         {
4853           intermediate_data[lastwordsize - 1U] &= 0xFFFFFF00U;
4854         }
4855         if ((npblb % 4U) == 2U)
4856         {
4857           intermediate_data[lastwordsize - 1U] &= 0xFFFF0000U;
4858         }
4859         if ((npblb % 4U) == 3U)
4860         {
4861           intermediate_data[lastwordsize - 1U] &= 0xFF000000U;
4862         }
4863       }
4864       else if ((hcryp->Instance->CR & CRYP_CR_DATATYPE) == CRYP_BYTE_SWAP)
4865       {
4866         if ((npblb % 4U) == 1U)
4867         {
4868           intermediate_data[lastwordsize - 1U] &= __REV(0xFFFFFF00U);
4869         }
4870         if ((npblb % 4U) == 2U)
4871         {
4872           intermediate_data[lastwordsize - 1U] &= __REV(0xFFFF0000U);
4873         }
4874         if ((npblb % 4U) == 3U)
4875         {
4876           intermediate_data[lastwordsize - 1U] &= __REV(0xFF000000U);
4877         }
4878       }
4879       else if ((hcryp->Instance->CR & CRYP_CR_DATATYPE) == CRYP_HALFWORD_SWAP)
4880       {
4881         if ((npblb % 4U) == 1U)
4882         {
4883           intermediate_data[lastwordsize - 1U] &= __ROR((0xFFFFFF00U), 16);
4884         }
4885         if ((npblb % 4U) == 2U)
4886         {
4887           intermediate_data[lastwordsize - 1U] &= __ROR((0xFFFF0000U), 16);
4888         }
4889         if ((npblb % 4U) == 3U)
4890         {
4891           intermediate_data[lastwordsize - 1U] &= __ROR((0xFF000000U), 16);
4892         }
4893       }
4894       else /*CRYP_BIT_SWAP*/
4895       {
4896         if ((npblb % 4U) == 1U)
4897         {
4898           intermediate_data[lastwordsize - 1U] &= __RBIT(0xFFFFFF00U);
4899         }
4900         if ((npblb % 4U) == 2U)
4901         {
4902           intermediate_data[lastwordsize - 1U] &= __RBIT(0xFFFF0000U);
4903         }
4904         if ((npblb % 4U) == 3U)
4905         {
4906           intermediate_data[lastwordsize - 1U] &= __RBIT(0xFF000000U);
4907         }
4908       }
4909 
4910       for (index = 0U; index < lastwordsize ; index ++)
4911       {
4912         /*Write the intermediate_data in the IN FIFO */
4913         hcryp->Instance->DIN = intermediate_data[index];
4914       }
4915       while (index < 4U)
4916       {
4917         /* Pad the data with zeros to have a complete block */
4918         hcryp->Instance->DIN  = 0x0U;
4919         index++;
4920       }
4921       /* Wait for OFNE flag to be raised */
4922       if (CRYP_WaitOnOFNEFlag(hcryp, Timeout) != HAL_OK)
4923       {
4924         /* Disable the CRYP peripheral clock */
4925         __HAL_CRYP_DISABLE(hcryp);
4926 
4927         /* Change state */
4928         hcryp->ErrorCode |= HAL_CRYP_ERROR_TIMEOUT;
4929         hcryp->State = HAL_CRYP_STATE_READY;
4930 
4931         /* Process unlocked */
4932         __HAL_UNLOCK(hcryp);
4933 #if (USE_HAL_CRYP_REGISTER_CALLBACKS == 1U)
4934         /*Call registered error callback*/
4935         hcryp->ErrorCallback(hcryp);
4936 #else
4937         /*Call legacy weak error callback*/
4938         HAL_CRYP_ErrorCallback(hcryp);
4939 #endif /* USE_HAL_CRYP_REGISTER_CALLBACKS */
4940       }
4941 
4942       if ((hcryp->Instance->SR & CRYP_FLAG_OFNE) != 0x0U)
4943       {
4944         for (index = 0U; index < 4U; index++)
4945         {
4946           intermediate_data[index] = hcryp->Instance->DOUT;
4947         }
4948       }
4949     }
4950   } /* End of GCM encryption */
4951   else
4952   {
4953     /* Workaround 2, case CCM decryption, in order to properly compute
4954       authentication tags while doing a CCM decryption with the last block
4955       of payload size inferior to 128 bits*/
4956 
4957     if ((hcryp->Instance->CR & CRYP_CR_ALGODIR) == CRYP_OPERATINGMODE_DECRYPT)
4958     {
4959       iv1temp = hcryp->Instance->CSGCMCCM7R;
4960 
4961       /* Disable CRYP to start the final phase */
4962       __HAL_CRYP_DISABLE(hcryp);
4963 
4964       temp[0] =  hcryp->Instance->CSGCMCCM0R;
4965       temp[1] =  hcryp->Instance->CSGCMCCM1R;
4966       temp[2] =  hcryp->Instance->CSGCMCCM2R;
4967       temp[3] =  hcryp->Instance->CSGCMCCM3R;
4968 
4969       hcryp->Instance->IV1RR = iv1temp;
4970 
4971       /* Configured  CHMOD CTR   */
4972       MODIFY_REG(hcryp->Instance->CR, CRYP_CR_ALGOMODE, CRYP_AES_CTR);
4973 
4974       /* Enable CRYP to start the final phase */
4975       __HAL_CRYP_ENABLE(hcryp);
4976     }
4977     /*  Last block optionally pad the data with zeros*/
4978     for (index = 0U; index < lastwordsize; index ++)
4979     {
4980       /* Write the last Input block in the IN FIFO */
4981       hcryp->Instance->DIN  = *(uint32_t *)(hcryp->pCrypInBuffPtr + hcryp->CrypInCount);
4982       hcryp->CrypInCount++;
4983     }
4984     while (index < 4U)
4985     {
4986       /* Pad the data with zeros to have a complete block */
4987       hcryp->Instance->DIN  = 0U;
4988       index++;
4989     }
4990     /* Wait for OFNE flag to be raised */
4991     if (CRYP_WaitOnOFNEFlag(hcryp, Timeout) != HAL_OK)
4992     {
4993       /* Disable the CRYP peripheral clock */
4994       __HAL_CRYP_DISABLE(hcryp);
4995 
4996       /* Change state */
4997       hcryp->ErrorCode |= HAL_CRYP_ERROR_TIMEOUT;
4998       hcryp->State = HAL_CRYP_STATE_READY;
4999 
5000       /* Process Unlocked */
5001       __HAL_UNLOCK(hcryp);
5002 #if (USE_HAL_CRYP_REGISTER_CALLBACKS == 1)
5003       /*Call registered error callback*/
5004       hcryp->ErrorCallback(hcryp);
5005 #else
5006       /*Call legacy weak error callback*/
5007       HAL_CRYP_ErrorCallback(hcryp);
5008 #endif /* USE_HAL_CRYP_REGISTER_CALLBACKS */
5009     }
5010 
5011     if ((hcryp->Instance->SR & CRYP_FLAG_OFNE) != 0x0U)
5012     {
5013       for (index = 0U; index < 4U; index++)
5014       {
5015         /* Read the Output block from the Output FIFO */
5016         intermediate_data[index] = hcryp->Instance->DOUT;
5017 
5018         /*intermediate data buffer to be used in for the workaround*/
5019         *(uint32_t *)(hcryp->pCrypOutBuffPtr + (hcryp->CrypOutCount)) = intermediate_data[index];
5020         hcryp->CrypOutCount++;
5021       }
5022     }
5023 
5024     if ((hcryp->Instance->CR & CRYP_CR_ALGODIR) == CRYP_OPERATINGMODE_DECRYPT)
5025     {
5026       temp2[0] =  hcryp->Instance->CSGCMCCM0R;
5027       temp2[1] =  hcryp->Instance->CSGCMCCM1R;
5028       temp2[2] =  hcryp->Instance->CSGCMCCM2R;
5029       temp2[3] =  hcryp->Instance->CSGCMCCM3R;
5030 
5031       /* configured  CHMOD CCM   */
5032       MODIFY_REG(hcryp->Instance->CR, CRYP_CR_ALGOMODE, CRYP_AES_CCM);
5033 
5034       /* configured  Header phase  */
5035       MODIFY_REG(hcryp->Instance->CR, CRYP_CR_GCM_CCMPH, CRYP_PHASE_HEADER);
5036 
5037       /*set to zero the bits corresponding to the padded bits*/
5038       for (index = lastwordsize; index < 4U; index ++)
5039       {
5040         intermediate_data[index] = 0U;
5041       }
5042 
5043       if ((npblb % 4U) == 1U)
5044       {
5045         intermediate_data[lastwordsize - 1U] &= 0xFFFFFF00U;
5046       }
5047       if ((npblb % 4U) == 2U)
5048       {
5049         intermediate_data[lastwordsize - 1U] &= 0xFFFF0000U;
5050       }
5051       if ((npblb % 4U) == 3U)
5052       {
5053         intermediate_data[lastwordsize - 1U] &= 0xFF000000U;
5054       }
5055 
5056       for (index = 0U; index < 4U ; index ++)
5057       {
5058         intermediate_data[index] ^=  temp[index];
5059         intermediate_data[index] ^=  temp2[index];
5060       }
5061       for (index = 0U; index < 4U; index ++)
5062       {
5063         /* Write the last Input block in the IN FIFO */
5064         hcryp->Instance->DIN  = intermediate_data[index] ;
5065       }
5066 
5067       /* Wait for BUSY flag to be raised */
5068       if (CRYP_WaitOnBUSYFlag(hcryp, Timeout) != HAL_OK)
5069       {
5070         /* Disable the CRYP peripheral clock */
5071         __HAL_CRYP_DISABLE(hcryp);
5072 
5073         /* Change state */
5074         hcryp->ErrorCode |= HAL_CRYP_ERROR_TIMEOUT;
5075         hcryp->State = HAL_CRYP_STATE_READY;
5076 
5077         /* Process Unlocked */
5078         __HAL_UNLOCK(hcryp);
5079 #if (USE_HAL_CRYP_REGISTER_CALLBACKS == 1)
5080         /*Call registered error callback*/
5081         hcryp->ErrorCallback(hcryp);
5082 #else
5083         /*Call legacy weak error callback*/
5084         HAL_CRYP_ErrorCallback(hcryp);
5085 #endif /* USE_HAL_CRYP_REGISTER_CALLBACKS */
5086       }
5087     }
5088   } /* End of CCM WKA*/
5089 
5090   /* Process Unlocked */
5091   __HAL_UNLOCK(hcryp);
5092 }
5093 #endif /*End of not defined CRYP_VER_2_2*/
5094 
5095 /**
5096   * @brief  Handle CRYP hardware block Timeout when waiting for IFEM flag to be raised.
5097   * @param  hcryp: pointer to a CRYP_HandleTypeDef structure that contains
5098   *         the configuration information for CRYP module.
5099   * @param  Timeout: Timeout duration.
5100   * @retval HAL status
5101   */
CRYP_WaitOnIFEMFlag(const CRYP_HandleTypeDef * hcryp,uint32_t Timeout)5102 static HAL_StatusTypeDef CRYP_WaitOnIFEMFlag(const CRYP_HandleTypeDef *hcryp, uint32_t Timeout)
5103 {
5104   uint32_t tickstart;
5105 
5106   /* Get timeout */
5107   tickstart = HAL_GetTick();
5108 
5109   while (HAL_IS_BIT_CLR(hcryp->Instance->SR, CRYP_FLAG_IFEM))
5110   {
5111     /* Check for the Timeout */
5112     if (Timeout != HAL_MAX_DELAY)
5113     {
5114       if (((HAL_GetTick() - tickstart) > Timeout) || (Timeout == 0U))
5115       {
5116         return HAL_ERROR;
5117       }
5118     }
5119   }
5120   return HAL_OK;
5121 }
5122 /**
5123   * @brief  Handle CRYP hardware block Timeout when waiting for BUSY flag to be raised.
5124   * @param  hcryp: pointer to a CRYP_HandleTypeDef structure that contains
5125   *         the configuration information for CRYP module.
5126   * @param  Timeout: Timeout duration.
5127   * @retval HAL status
5128   */
CRYP_WaitOnBUSYFlag(const CRYP_HandleTypeDef * hcryp,uint32_t Timeout)5129 static HAL_StatusTypeDef CRYP_WaitOnBUSYFlag(const CRYP_HandleTypeDef *hcryp, uint32_t Timeout)
5130 {
5131   uint32_t tickstart;
5132 
5133   /* Get timeout */
5134   tickstart = HAL_GetTick();
5135 
5136   while (HAL_IS_BIT_SET(hcryp->Instance->SR, CRYP_FLAG_BUSY))
5137   {
5138     /* Check for the Timeout */
5139     if (Timeout != HAL_MAX_DELAY)
5140     {
5141       if (((HAL_GetTick() - tickstart) > Timeout) || (Timeout == 0U))
5142       {
5143         return HAL_ERROR;
5144       }
5145     }
5146   }
5147   return HAL_OK;
5148 }
5149 
5150 
5151 /**
5152   * @brief  Handle CRYP hardware block Timeout when waiting for OFNE flag to be raised.
5153   * @param  hcryp: pointer to a CRYP_HandleTypeDef structure that contains
5154   *         the configuration information for CRYP module.
5155   * @param  Timeout: Timeout duration.
5156   * @retval HAL status
5157   */
CRYP_WaitOnOFNEFlag(const CRYP_HandleTypeDef * hcryp,uint32_t Timeout)5158 static HAL_StatusTypeDef CRYP_WaitOnOFNEFlag(const CRYP_HandleTypeDef  *hcryp, uint32_t Timeout)
5159 {
5160   uint32_t tickstart;
5161 
5162   /* Get timeout */
5163   tickstart = HAL_GetTick();
5164 
5165   while (HAL_IS_BIT_CLR(hcryp->Instance->SR, CRYP_FLAG_OFNE))
5166   {
5167     /* Check for the Timeout */
5168     if (Timeout != HAL_MAX_DELAY)
5169     {
5170       if (((HAL_GetTick() - tickstart) > Timeout) || (Timeout == 0U))
5171       {
5172         return HAL_ERROR;
5173       }
5174     }
5175   }
5176   return HAL_OK;
5177 }
5178 
5179 
5180 /**
5181   * @}
5182   */
5183 
5184 
5185 
5186 /**
5187   * @}
5188   */
5189 
5190 /**
5191   * @}
5192   */
5193 
5194 #endif /* HAL_CRYP_MODULE_ENABLED */
5195 
5196 
5197 /**
5198   * @}
5199   */
5200 #endif /* CRYP */
5201 /**
5202   * @}
5203   */
5204 
5205