Statistics
| Branch: | Tag: | Revision:

amiro-blt / Target / Demo / ARMCM4_STM32F405_Power_Management_GCC / Boot / lib / stdperiphlib / STM32F4xx_StdPeriph_Driver / src / stm32f4xx_cryp_aes.c @ 69661903

History | View | Annotate | Download (56.4 KB)

1
/**
2
  ******************************************************************************
3
  * @file    stm32f4xx_cryp_aes.c
4
  * @author  MCD Application Team
5
  * @version V1.1.0
6
  * @date    11-January-2013
7
  * @brief   This file provides high level functions to encrypt and decrypt an 
8
  *          input message using AES in ECB/CBC/CTR/GCM/CCM modes.
9
  *          It uses the stm32f4xx_cryp.c/.h drivers to access the STM32F4xx CRYP
10
  *          peripheral.
11
  *          AES-ECB/CBC/CTR/GCM/CCM modes are available on STM32F437x Devices.
12
  *          For STM32F41xx Devices, only AES-ECB/CBC/CTR modes are available.
13
  *
14
@verbatim
15
 ===================================================================
16
                  ##### How to use this driver #####
17
 ===================================================================
18
 [..]
19
   (#) Enable The CRYP controller clock using 
20
      RCC_AHB2PeriphClockCmd(RCC_AHB2Periph_CRYP, ENABLE); function.
21
  
22
   (#) Encrypt and decrypt using AES in ECB Mode using CRYP_AES_ECB() function.
23
  
24
   (#) Encrypt and decrypt using AES in CBC Mode using CRYP_AES_CBC() function.
25
  
26
   (#) Encrypt and decrypt using AES in CTR Mode using CRYP_AES_CTR() function.
27

28
   (#) Encrypt and decrypt using AES in GCM Mode using CRYP_AES_GCM() function.
29
   
30
   (#) Encrypt and decrypt using AES in CCM Mode using CRYP_AES_CCM() function.
31
     
32
@endverbatim
33
  *
34
  ******************************************************************************
35
  * @attention
36
  *
37
  * <h2><center>&copy; COPYRIGHT 2013 STMicroelectronics</center></h2>
38
  *
39
  * Licensed under MCD-ST Liberty SW License Agreement V2, (the "License");
40
  * You may not use this file except in compliance with the License.
41
  * You may obtain a copy of the License at:
42
  *
43
  *        http://www.st.com/software_license_agreement_liberty_v2
44
  *
45
  * Unless required by applicable law or agreed to in writing, software 
46
  * distributed under the License is distributed on an "AS IS" BASIS, 
47
  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
48
  * See the License for the specific language governing permissions and
49
  * limitations under the License.
50
  *
51
  ******************************************************************************  
52
  */
53

    
54
/* Includes ------------------------------------------------------------------*/
55
#include "stm32f4xx_cryp.h"
56

    
57
/** @addtogroup STM32F4xx_StdPeriph_Driver
58
  * @{
59
  */
60

    
61
/** @defgroup CRYP 
62
  * @brief CRYP driver modules
63
  * @{
64
  */
65

    
66
/* Private typedef -----------------------------------------------------------*/
67
/* Private define ------------------------------------------------------------*/
68
#define AESBUSY_TIMEOUT    ((uint32_t) 0x00010000)
69

    
70
/* Private macro -------------------------------------------------------------*/
71
/* Private variables ---------------------------------------------------------*/
72
/* Private function prototypes -----------------------------------------------*/
73
/* Private functions ---------------------------------------------------------*/
74

    
75
/** @defgroup CRYP_Private_Functions
76
  * @{
77
  */ 
78

    
79
/** @defgroup CRYP_Group6 High Level AES functions
80
 *  @brief   High Level AES functions 
81
 *
82
@verbatim   
83
 ===============================================================================
84
                       ##### High Level AES functions #####
85
 ===============================================================================
86

87
@endverbatim
88
  * @{
89
  */
90

    
91
/**
92
  * @brief  Encrypt and decrypt using AES in ECB Mode
93
  * @param  Mode: encryption or decryption Mode.
94
  *          This parameter can be one of the following values:
95
  *            @arg MODE_ENCRYPT: Encryption
96
  *            @arg MODE_DECRYPT: Decryption
97
  * @param  Key: Key used for AES algorithm.
98
  * @param  Keysize: length of the Key, must be a 128, 192 or 256.
99
  * @param  Input: pointer to the Input buffer.
100
  * @param  Ilength: length of the Input buffer, must be a multiple of 16.
101
  * @param  Output: pointer to the returned buffer.
102
  * @retval An ErrorStatus enumeration value:
103
  *          - SUCCESS: Operation done
104
  *          - ERROR: Operation failed
105
  */
106
ErrorStatus CRYP_AES_ECB(uint8_t Mode, uint8_t* Key, uint16_t Keysize,
107
                         uint8_t* Input, uint32_t Ilength, uint8_t* Output)
108
{
109
  CRYP_InitTypeDef AES_CRYP_InitStructure;
110
  CRYP_KeyInitTypeDef AES_CRYP_KeyInitStructure;
111
  __IO uint32_t counter = 0;
112
  uint32_t busystatus = 0;
113
  ErrorStatus status = SUCCESS;
114
  uint32_t keyaddr    = (uint32_t)Key;
115
  uint32_t inputaddr  = (uint32_t)Input;
116
  uint32_t outputaddr = (uint32_t)Output;
117
  uint32_t i = 0;
118

    
119
  /* Crypto structures initialisation*/
120
  CRYP_KeyStructInit(&AES_CRYP_KeyInitStructure);
121

    
122
  switch(Keysize)
123
  {
124
    case 128:
125
    AES_CRYP_InitStructure.CRYP_KeySize = CRYP_KeySize_128b;
126
    AES_CRYP_KeyInitStructure.CRYP_Key2Left = __REV(*(uint32_t*)(keyaddr));
127
    keyaddr+=4;
128
    AES_CRYP_KeyInitStructure.CRYP_Key2Right= __REV(*(uint32_t*)(keyaddr));
129
    keyaddr+=4;
130
    AES_CRYP_KeyInitStructure.CRYP_Key3Left = __REV(*(uint32_t*)(keyaddr));
131
    keyaddr+=4;
132
    AES_CRYP_KeyInitStructure.CRYP_Key3Right= __REV(*(uint32_t*)(keyaddr));
133
    break;
134
    case 192:
135
    AES_CRYP_InitStructure.CRYP_KeySize  = CRYP_KeySize_192b;
136
    AES_CRYP_KeyInitStructure.CRYP_Key1Left = __REV(*(uint32_t*)(keyaddr));
137
    keyaddr+=4;
138
    AES_CRYP_KeyInitStructure.CRYP_Key1Right= __REV(*(uint32_t*)(keyaddr));
139
    keyaddr+=4;
140
    AES_CRYP_KeyInitStructure.CRYP_Key2Left = __REV(*(uint32_t*)(keyaddr));
141
    keyaddr+=4;
142
    AES_CRYP_KeyInitStructure.CRYP_Key2Right= __REV(*(uint32_t*)(keyaddr));
143
    keyaddr+=4;
144
    AES_CRYP_KeyInitStructure.CRYP_Key3Left = __REV(*(uint32_t*)(keyaddr));
145
    keyaddr+=4;
146
    AES_CRYP_KeyInitStructure.CRYP_Key3Right= __REV(*(uint32_t*)(keyaddr));
147
    break;
148
    case 256:
149
    AES_CRYP_InitStructure.CRYP_KeySize  = CRYP_KeySize_256b;
150
    AES_CRYP_KeyInitStructure.CRYP_Key0Left = __REV(*(uint32_t*)(keyaddr));
151
    keyaddr+=4;
152
    AES_CRYP_KeyInitStructure.CRYP_Key0Right= __REV(*(uint32_t*)(keyaddr));
153
    keyaddr+=4;
154
    AES_CRYP_KeyInitStructure.CRYP_Key1Left = __REV(*(uint32_t*)(keyaddr));
155
    keyaddr+=4;
156
    AES_CRYP_KeyInitStructure.CRYP_Key1Right= __REV(*(uint32_t*)(keyaddr));
157
    keyaddr+=4;
158
    AES_CRYP_KeyInitStructure.CRYP_Key2Left = __REV(*(uint32_t*)(keyaddr));
159
    keyaddr+=4;
160
    AES_CRYP_KeyInitStructure.CRYP_Key2Right= __REV(*(uint32_t*)(keyaddr));
161
    keyaddr+=4;
162
    AES_CRYP_KeyInitStructure.CRYP_Key3Left = __REV(*(uint32_t*)(keyaddr));
163
    keyaddr+=4;
164
    AES_CRYP_KeyInitStructure.CRYP_Key3Right= __REV(*(uint32_t*)(keyaddr));
165
    break;
166
    default:
167
    break;
168
  }
169

    
170
  /*------------------ AES Decryption ------------------*/
171
  if(Mode == MODE_DECRYPT) /* AES decryption */
172
  {
173
    /* Flush IN/OUT FIFOs */
174
    CRYP_FIFOFlush();
175

    
176
    /* Crypto Init for Key preparation for decryption process */
177
    AES_CRYP_InitStructure.CRYP_AlgoDir = CRYP_AlgoDir_Decrypt;
178
    AES_CRYP_InitStructure.CRYP_AlgoMode = CRYP_AlgoMode_AES_Key;
179
    AES_CRYP_InitStructure.CRYP_DataType = CRYP_DataType_32b;
180
    CRYP_Init(&AES_CRYP_InitStructure);
181

    
182
    /* Key Initialisation */
183
    CRYP_KeyInit(&AES_CRYP_KeyInitStructure);
184

    
185
    /* Enable Crypto processor */
186
    CRYP_Cmd(ENABLE);
187

    
188
    /* wait until the Busy flag is RESET */
189
    do
190
    {
191
      busystatus = CRYP_GetFlagStatus(CRYP_FLAG_BUSY);
192
      counter++;
193
    }while ((counter != AESBUSY_TIMEOUT) && (busystatus != RESET));
194

    
195
    if (busystatus != RESET)
196
   {
197
       status = ERROR;
198
    }
199
    else
200
    {
201
      /* Crypto Init for decryption process */  
202
      AES_CRYP_InitStructure.CRYP_AlgoDir = CRYP_AlgoDir_Decrypt;
203
    }
204
  }
205
  /*------------------ AES Encryption ------------------*/
206
  else /* AES encryption */
207
  {
208

    
209
    CRYP_KeyInit(&AES_CRYP_KeyInitStructure);
210

    
211
    /* Crypto Init for Encryption process */
212
    AES_CRYP_InitStructure.CRYP_AlgoDir  = CRYP_AlgoDir_Encrypt;
213
  }
214

    
215
  AES_CRYP_InitStructure.CRYP_AlgoMode = CRYP_AlgoMode_AES_ECB;
216
  AES_CRYP_InitStructure.CRYP_DataType = CRYP_DataType_8b;
217
  CRYP_Init(&AES_CRYP_InitStructure);
218

    
219
  /* Flush IN/OUT FIFOs */
220
  CRYP_FIFOFlush();
221

    
222
  /* Enable Crypto processor */
223
  CRYP_Cmd(ENABLE);
224

    
225
  if(CRYP_GetCmdStatus() == DISABLE)
226
  {
227
    /* The CRYP peripheral clock is not enabled or the device doesn't embedd 
228
       the CRYP peripheral (please check the device sales type. */
229
    return(ERROR);
230
  }
231
  
232
  for(i=0; ((i<Ilength) && (status != ERROR)); i+=16)
233
  {
234

    
235
    /* Write the Input block in the IN FIFO */
236
    CRYP_DataIn(*(uint32_t*)(inputaddr));
237
    inputaddr+=4;
238
    CRYP_DataIn(*(uint32_t*)(inputaddr));
239
    inputaddr+=4;
240
    CRYP_DataIn(*(uint32_t*)(inputaddr));
241
    inputaddr+=4;
242
    CRYP_DataIn(*(uint32_t*)(inputaddr));
243
    inputaddr+=4;
244

    
245
    /* Wait until the complete message has been processed */
246
    counter = 0;
247
    do
248
    {
249
      busystatus = CRYP_GetFlagStatus(CRYP_FLAG_BUSY);
250
      counter++;
251
    }while ((counter != AESBUSY_TIMEOUT) && (busystatus != RESET));
252

    
253
    if (busystatus != RESET)
254
   {
255
       status = ERROR;
256
    }
257
    else
258
    {
259

    
260
      /* Read the Output block from the Output FIFO */
261
      *(uint32_t*)(outputaddr) = CRYP_DataOut();
262
      outputaddr+=4;
263
      *(uint32_t*)(outputaddr) = CRYP_DataOut();
264
      outputaddr+=4;
265
      *(uint32_t*)(outputaddr) = CRYP_DataOut();
266
      outputaddr+=4;
267
      *(uint32_t*)(outputaddr) = CRYP_DataOut(); 
268
      outputaddr+=4;
269
    }
270
  }
271

    
272
  /* Disable Crypto */
273
  CRYP_Cmd(DISABLE);
274

    
275
  return status; 
276
}
277

    
278
/**
279
  * @brief  Encrypt and decrypt using AES in CBC Mode
280
  * @param  Mode: encryption or decryption Mode.
281
  *          This parameter can be one of the following values:
282
  *            @arg MODE_ENCRYPT: Encryption
283
  *            @arg MODE_DECRYPT: Decryption
284
  * @param  InitVectors: Initialisation Vectors used for AES algorithm.
285
  * @param  Key: Key used for AES algorithm.
286
  * @param  Keysize: length of the Key, must be a 128, 192 or 256.
287
  * @param  Input: pointer to the Input buffer.
288
  * @param  Ilength: length of the Input buffer, must be a multiple of 16.
289
  * @param  Output: pointer to the returned buffer.
290
  * @retval An ErrorStatus enumeration value:
291
  *          - SUCCESS: Operation done
292
  *          - ERROR: Operation failed
293
  */
294
ErrorStatus CRYP_AES_CBC(uint8_t Mode, uint8_t InitVectors[16], uint8_t *Key,
295
                         uint16_t Keysize, uint8_t *Input, uint32_t Ilength,
296
                         uint8_t *Output)
297
{
298
  CRYP_InitTypeDef AES_CRYP_InitStructure;
299
  CRYP_KeyInitTypeDef AES_CRYP_KeyInitStructure;
300
  CRYP_IVInitTypeDef AES_CRYP_IVInitStructure;
301
  __IO uint32_t counter = 0;
302
  uint32_t busystatus = 0;
303
  ErrorStatus status = SUCCESS;
304
  uint32_t keyaddr    = (uint32_t)Key;
305
  uint32_t inputaddr  = (uint32_t)Input;
306
  uint32_t outputaddr = (uint32_t)Output;
307
  uint32_t ivaddr = (uint32_t)InitVectors;
308
  uint32_t i = 0;
309

    
310
  /* Crypto structures initialisation*/
311
  CRYP_KeyStructInit(&AES_CRYP_KeyInitStructure);
312

    
313
  switch(Keysize)
314
  {
315
    case 128:
316
    AES_CRYP_InitStructure.CRYP_KeySize = CRYP_KeySize_128b;
317
    AES_CRYP_KeyInitStructure.CRYP_Key2Left = __REV(*(uint32_t*)(keyaddr));
318
    keyaddr+=4;
319
    AES_CRYP_KeyInitStructure.CRYP_Key2Right= __REV(*(uint32_t*)(keyaddr));
320
    keyaddr+=4;
321
    AES_CRYP_KeyInitStructure.CRYP_Key3Left = __REV(*(uint32_t*)(keyaddr));
322
    keyaddr+=4;
323
    AES_CRYP_KeyInitStructure.CRYP_Key3Right= __REV(*(uint32_t*)(keyaddr));
324
    break;
325
    case 192:
326
    AES_CRYP_InitStructure.CRYP_KeySize  = CRYP_KeySize_192b;
327
    AES_CRYP_KeyInitStructure.CRYP_Key1Left = __REV(*(uint32_t*)(keyaddr));
328
    keyaddr+=4;
329
    AES_CRYP_KeyInitStructure.CRYP_Key1Right= __REV(*(uint32_t*)(keyaddr));
330
    keyaddr+=4;
331
    AES_CRYP_KeyInitStructure.CRYP_Key2Left = __REV(*(uint32_t*)(keyaddr));
332
    keyaddr+=4;
333
    AES_CRYP_KeyInitStructure.CRYP_Key2Right= __REV(*(uint32_t*)(keyaddr));
334
    keyaddr+=4;
335
    AES_CRYP_KeyInitStructure.CRYP_Key3Left = __REV(*(uint32_t*)(keyaddr));
336
    keyaddr+=4;
337
    AES_CRYP_KeyInitStructure.CRYP_Key3Right= __REV(*(uint32_t*)(keyaddr));
338
    break;
339
    case 256:
340
    AES_CRYP_InitStructure.CRYP_KeySize  = CRYP_KeySize_256b;
341
    AES_CRYP_KeyInitStructure.CRYP_Key0Left = __REV(*(uint32_t*)(keyaddr));
342
    keyaddr+=4;
343
    AES_CRYP_KeyInitStructure.CRYP_Key0Right= __REV(*(uint32_t*)(keyaddr));
344
    keyaddr+=4;
345
    AES_CRYP_KeyInitStructure.CRYP_Key1Left = __REV(*(uint32_t*)(keyaddr));
346
    keyaddr+=4;
347
    AES_CRYP_KeyInitStructure.CRYP_Key1Right= __REV(*(uint32_t*)(keyaddr));
348
    keyaddr+=4;
349
    AES_CRYP_KeyInitStructure.CRYP_Key2Left = __REV(*(uint32_t*)(keyaddr));
350
    keyaddr+=4;
351
    AES_CRYP_KeyInitStructure.CRYP_Key2Right= __REV(*(uint32_t*)(keyaddr));
352
    keyaddr+=4;
353
    AES_CRYP_KeyInitStructure.CRYP_Key3Left = __REV(*(uint32_t*)(keyaddr));
354
    keyaddr+=4;
355
    AES_CRYP_KeyInitStructure.CRYP_Key3Right= __REV(*(uint32_t*)(keyaddr));
356
    break;
357
    default:
358
    break;
359
  }
360

    
361
  /* CRYP Initialization Vectors */
362
  AES_CRYP_IVInitStructure.CRYP_IV0Left = __REV(*(uint32_t*)(ivaddr));
363
  ivaddr+=4;
364
  AES_CRYP_IVInitStructure.CRYP_IV0Right= __REV(*(uint32_t*)(ivaddr));
365
  ivaddr+=4;
366
  AES_CRYP_IVInitStructure.CRYP_IV1Left = __REV(*(uint32_t*)(ivaddr));
367
  ivaddr+=4;
368
  AES_CRYP_IVInitStructure.CRYP_IV1Right= __REV(*(uint32_t*)(ivaddr)