sam4e_crypto_cipher.c
Go to the documentation of this file.
1 /**
2  * @file sam4e_crypto_cipher.c
3  * @brief SAM4E cipher hardware accelerator
4  *
5  * @section License
6  *
7  * SPDX-License-Identifier: GPL-2.0-or-later
8  *
9  * Copyright (C) 2010-2024 Oryx Embedded SARL. All rights reserved.
10  *
11  * This file is part of CycloneCRYPTO Open.
12  *
13  * This program is free software; you can redistribute it and/or
14  * modify it under the terms of the GNU General Public License
15  * as published by the Free Software Foundation; either version 2
16  * of the License, or (at your option) any later version.
17  *
18  * This program is distributed in the hope that it will be useful,
19  * but WITHOUT ANY WARRANTY; without even the implied warranty of
20  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
21  * GNU General Public License for more details.
22  *
23  * You should have received a copy of the GNU General Public License
24  * along with this program; if not, write to the Free Software Foundation,
25  * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
26  *
27  * @author Oryx Embedded SARL (www.oryx-embedded.com)
28  * @version 2.4.0
29  **/
30 
31 //Switch to the appropriate trace level
32 #define TRACE_LEVEL CRYPTO_TRACE_LEVEL
33 
34 //Dependencies
35 #include "sam4e.h"
36 #include "core/crypto.h"
41 #include "debug.h"
42 
43 //Check crypto library configuration
44 #if (SAM4E_CRYPTO_CIPHER_SUPPORT == ENABLED && AES_SUPPORT == ENABLED)
45 
46 
47 /**
48  * @brief Load AES key
49  * @param[in] context AES algorithm context
50  **/
51 
52 void aesLoadKey(AesContext *context)
53 {
54  uint32_t temp;
55 
56  //Read mode register
57  temp = AES->AES_MR & ~AES_MR_KEYSIZE_Msk;
58 
59  //Check the length of the key
60  if(context->nr == 10)
61  {
62  //10 rounds are required for 128-bit key
63  AES->AES_MR = temp | AES_MR_KEYSIZE_AES128;
64 
65  //Set the 128-bit encryption key
66  AES->AES_KEYWR[0] = context->ek[0];
67  AES->AES_KEYWR[1] = context->ek[1];
68  AES->AES_KEYWR[2] = context->ek[2];
69  AES->AES_KEYWR[3] = context->ek[3];
70  }
71  else if(context->nr == 12)
72  {
73  //12 rounds are required for 192-bit key
74  AES->AES_MR = temp | AES_MR_KEYSIZE_AES192;
75 
76  //Set the 192-bit encryption key
77  AES->AES_KEYWR[0] = context->ek[0];
78  AES->AES_KEYWR[1] = context->ek[1];
79  AES->AES_KEYWR[2] = context->ek[2];
80  AES->AES_KEYWR[3] = context->ek[3];
81  AES->AES_KEYWR[4] = context->ek[4];
82  AES->AES_KEYWR[5] = context->ek[5];
83  }
84  else
85  {
86  //14 rounds are required for 256-bit key
87  AES->AES_MR = temp | AES_MR_KEYSIZE_AES256;
88 
89  //Set the 256-bit encryption key
90  AES->AES_KEYWR[0] = context->ek[0];
91  AES->AES_KEYWR[1] = context->ek[1];
92  AES->AES_KEYWR[2] = context->ek[2];
93  AES->AES_KEYWR[3] = context->ek[3];
94  AES->AES_KEYWR[4] = context->ek[4];
95  AES->AES_KEYWR[5] = context->ek[5];
96  AES->AES_KEYWR[6] = context->ek[6];
97  AES->AES_KEYWR[7] = context->ek[7];
98  }
99 }
100 
101 
102 /**
103  * @brief Encrypt/decrypt a 16-byte block using AES algorithm
104  * @param[in] input Input block to be encrypted/decrypted
105  * @param[out] output Resulting block
106  **/
107 
108 void aesProcessDataBlock(const uint8_t *input, uint8_t *output)
109 {
110  uint32_t *p;
111 
112  //Write input block
113  p = (uint32_t *) input;
114  AES->AES_IDATAR[0] = p[0];
115  AES->AES_IDATAR[1] = p[1];
116  AES->AES_IDATAR[2] = p[2];
117  AES->AES_IDATAR[3] = p[3];
118 
119  //Start encryption/decryption
120  AES->AES_CR = AES_CR_START;
121 
122  //When processing completes, the DATRDY flag is raised
123  while((AES->AES_ISR & AES_ISR_DATRDY) == 0)
124  {
125  }
126 
127  //Read output block
128  p = (uint32_t *) output;
129  p[0] = AES->AES_ODATAR[0];
130  p[1] = AES->AES_ODATAR[1];
131  p[2] = AES->AES_ODATAR[2];
132  p[3] = AES->AES_ODATAR[3];
133 }
134 
135 
136 /**
137  * @brief Perform AES encryption or decryption
138  * @param[in] context AES algorithm context
139  * @param[in] iv Initialization vector
140  * @param[in] input Data to be encrypted/decrypted
141  * @param[out] output Data resulting from the encryption/decryption process
142  * @param[in] length Total number of data bytes to be processed
143  * @param[in] mode Operation mode
144  **/
145 
146 void aesProcessData(AesContext *context, uint8_t *iv, const uint8_t *input,
147  uint8_t *output, size_t length, uint32_t mode)
148 {
149  uint32_t *p;
150 
151  //Acquire exclusive access to the AES module
153 
154  //Perform software reset
155  AES->AES_CR = AES_CR_SWRST;
156 
157  //Set operation mode
158  AES->AES_MR = AES_MR_SMOD_MANUAL_START | mode;
159  //Set encryption key
160  aesLoadKey(context);
161 
162  //Valid initialization vector?
163  if(iv != NULL)
164  {
165  //Set initialization vector
166  p = (uint32_t *) iv;
167  AES->AES_IVR[0] = p[0];
168  AES->AES_IVR[1] = p[1];
169  AES->AES_IVR[2] = p[2];
170  AES->AES_IVR[3] = p[3];
171  }
172 
173  //Process data
174  while(length >= AES_BLOCK_SIZE)
175  {
176  //The data is encrypted block by block
177  aesProcessDataBlock(input, output);
178 
179  //Next block
180  input += AES_BLOCK_SIZE;
181  output += AES_BLOCK_SIZE;
183  }
184 
185  //Process final block of data
186  if(length > 0)
187  {
188  uint8_t buffer[AES_BLOCK_SIZE];
189 
190  //Copy input data
191  osMemset(buffer, 0, AES_BLOCK_SIZE);
192  osMemcpy(buffer, input, length);
193 
194  //Encrypt the final block of data
195  aesProcessDataBlock(buffer, buffer);
196 
197  //Copy output data
198  osMemcpy(output, buffer, length);
199  }
200 
201  //Release exclusive access to the AES module
203 }
204 
205 
206 /**
207  * @brief Key expansion
208  * @param[in] context Pointer to the AES context to initialize
209  * @param[in] key Pointer to the key
210  * @param[in] keyLen Length of the key
211  * @return Error code
212  **/
213 
214 error_t aesInit(AesContext *context, const uint8_t *key, size_t keyLen)
215 {
216  //Check parameters
217  if(context == NULL || key == NULL)
219 
220  //Check the length of the key
221  if(keyLen == 16)
222  {
223  //10 rounds are required for 128-bit key
224  context->nr = 10;
225  }
226  else if(keyLen == 24)
227  {
228  //12 rounds are required for 192-bit key
229  context->nr = 12;
230  }
231  else if(keyLen == 32)
232  {
233  //14 rounds are required for 256-bit key
234  context->nr = 14;
235  }
236  else
237  {
238  //Report an error
240  }
241 
242  //Copy the original key
243  osMemcpy(context->ek, key, keyLen);
244 
245  //No error to report
246  return NO_ERROR;
247 }
248 
249 
250 /**
251  * @brief Encrypt a 16-byte block using AES algorithm
252  * @param[in] context Pointer to the AES context
253  * @param[in] input Plaintext block to encrypt
254  * @param[out] output Ciphertext block resulting from encryption
255  **/
256 
257 void aesEncryptBlock(AesContext *context, const uint8_t *input, uint8_t *output)
258 {
259  //Perform AES encryption
260  aesProcessData(context, NULL, input, output, AES_BLOCK_SIZE, AES_MR_CIPHER |
261  AES_MR_OPMOD_ECB);
262 }
263 
264 
265 /**
266  * @brief Decrypt a 16-byte block using AES algorithm
267  * @param[in] context Pointer to the AES context
268  * @param[in] input Ciphertext block to decrypt
269  * @param[out] output Plaintext block resulting from decryption
270  **/
271 
272 void aesDecryptBlock(AesContext *context, const uint8_t *input, uint8_t *output)
273 {
274  //Perform AES decryption
275  aesProcessData(context, NULL, input, output, AES_BLOCK_SIZE,
276  AES_MR_OPMOD_ECB);
277 }
278 
279 
280 #if (ECB_SUPPORT == ENABLED)
281 
282 /**
283  * @brief ECB encryption
284  * @param[in] cipher Cipher algorithm
285  * @param[in] context Cipher algorithm context
286  * @param[in] p Plaintext to be encrypted
287  * @param[out] c Ciphertext resulting from the encryption
288  * @param[in] length Total number of data bytes to be encrypted
289  * @return Error code
290  **/
291 
292 error_t ecbEncrypt(const CipherAlgo *cipher, void *context,
293  const uint8_t *p, uint8_t *c, size_t length)
294 {
295  error_t error;
296 
297  //Initialize status code
298  error = NO_ERROR;
299 
300  //AES cipher algorithm?
301  if(cipher == AES_CIPHER_ALGO)
302  {
303  //Check the length of the payload
304  if(length == 0)
305  {
306  //No data to process
307  }
308  else if((length % AES_BLOCK_SIZE) == 0)
309  {
310  //Encrypt payload data
311  aesProcessData(context, NULL, p, c, length, AES_MR_CIPHER |
312  AES_MR_OPMOD_ECB);
313  }
314  else
315  {
316  //The length of the payload must be a multiple of the block size
317  error = ERROR_INVALID_LENGTH;
318  }
319  }
320  else
321  {
322  //ECB mode operates in a block-by-block fashion
323  while(length >= cipher->blockSize)
324  {
325  //Encrypt current block
326  cipher->encryptBlock(context, p, c);
327 
328  //Next block
329  p += cipher->blockSize;
330  c += cipher->blockSize;
331  length -= cipher->blockSize;
332  }
333 
334  //The length of the payload must be a multiple of the block size
335  if(length != 0)
336  {
337  error = ERROR_INVALID_LENGTH;
338  }
339  }
340 
341  //Return status code
342  return error;
343 }
344 
345 
346 /**
347  * @brief ECB decryption
348  * @param[in] cipher Cipher algorithm
349  * @param[in] context Cipher algorithm context
350  * @param[in] c Ciphertext to be decrypted
351  * @param[out] p Plaintext resulting from the decryption
352  * @param[in] length Total number of data bytes to be decrypted
353  * @return Error code
354  **/
355 
356 error_t ecbDecrypt(const CipherAlgo *cipher, void *context,
357  const uint8_t *c, uint8_t *p, size_t length)
358 {
359  error_t error;
360 
361  //Initialize status code
362  error = NO_ERROR;
363 
364  //AES cipher algorithm?
365  if(cipher == AES_CIPHER_ALGO)
366  {
367  //Check the length of the payload
368  if(length == 0)
369  {
370  //No data to process
371  }
372  else if((length % AES_BLOCK_SIZE) == 0)
373  {
374  //Decrypt payload data
375  aesProcessData(context, NULL, c, p, length, AES_MR_OPMOD_ECB);
376  }
377  else
378  {
379  //The length of the payload must be a multiple of the block size
380  error = ERROR_INVALID_LENGTH;
381  }
382  }
383  else
384  {
385  //ECB mode operates in a block-by-block fashion
386  while(length >= cipher->blockSize)
387  {
388  //Decrypt current block
389  cipher->decryptBlock(context, c, p);
390 
391  //Next block
392  c += cipher->blockSize;
393  p += cipher->blockSize;
394  length -= cipher->blockSize;
395  }
396 
397  //The length of the payload must be a multiple of the block size
398  if(length != 0)
399  {
400  error = ERROR_INVALID_LENGTH;
401  }
402  }
403 
404  //Return status code
405  return error;
406 }
407 
408 #endif
409 #if (CBC_SUPPORT == ENABLED)
410 
411 /**
412  * @brief CBC encryption
413  * @param[in] cipher Cipher algorithm
414  * @param[in] context Cipher algorithm context
415  * @param[in,out] iv Initialization vector
416  * @param[in] p Plaintext to be encrypted
417  * @param[out] c Ciphertext resulting from the encryption
418  * @param[in] length Total number of data bytes to be encrypted
419  * @return Error code
420  **/
421 
422 error_t cbcEncrypt(const CipherAlgo *cipher, void *context,
423  uint8_t *iv, const uint8_t *p, uint8_t *c, size_t length)
424 {
425  error_t error;
426 
427  //Initialize status code
428  error = NO_ERROR;
429 
430  //AES cipher algorithm?
431  if(cipher == AES_CIPHER_ALGO)
432  {
433  //Check the length of the payload
434  if(length == 0)
435  {
436  //No data to process
437  }
438  else if((length % AES_BLOCK_SIZE) == 0)
439  {
440  //Encrypt payload data
441  aesProcessData(context, iv, p, c, length, AES_MR_CIPHER |
442  AES_MR_OPMOD_CBC);
443 
444  //Update the value of the initialization vector
446  }
447  else
448  {
449  //The length of the payload must be a multiple of the block size
450  error = ERROR_INVALID_LENGTH;
451  }
452  }
453  else
454  {
455  size_t i;
456 
457  //CBC mode operates in a block-by-block fashion
458  while(length >= cipher->blockSize)
459  {
460  //XOR input block with IV contents
461  for(i = 0; i < cipher->blockSize; i++)
462  {
463  c[i] = p[i] ^ iv[i];
464  }
465 
466  //Encrypt the current block based upon the output of the previous
467  //encryption
468  cipher->encryptBlock(context, c, c);
469 
470  //Update IV with output block contents
471  osMemcpy(iv, c, cipher->blockSize);
472 
473  //Next block
474  p += cipher->blockSize;
475  c += cipher->blockSize;
476  length -= cipher->blockSize;
477  }
478 
479  //The length of the payload must be a multiple of the block size
480  if(length != 0)
481  {
482  error = ERROR_INVALID_LENGTH;
483  }
484  }
485 
486  //Return status code
487  return error;
488 }
489 
490 
491 /**
492  * @brief CBC decryption
493  * @param[in] cipher Cipher algorithm
494  * @param[in] context Cipher algorithm context
495  * @param[in,out] iv Initialization vector
496  * @param[in] c Ciphertext to be decrypted
497  * @param[out] p Plaintext resulting from the decryption
498  * @param[in] length Total number of data bytes to be decrypted
499  * @return Error code
500  **/
501 
502 error_t cbcDecrypt(const CipherAlgo *cipher, void *context,
503  uint8_t *iv, const uint8_t *c, uint8_t *p, size_t length)
504 {
505  error_t error;
506 
507  //Initialize status code
508  error = NO_ERROR;
509 
510  //AES cipher algorithm?
511  if(cipher == AES_CIPHER_ALGO)
512  {
513  //Check the length of the payload
514  if(length == 0)
515  {
516  //No data to process
517  }
518  else if((length % AES_BLOCK_SIZE) == 0)
519  {
520  uint8_t block[AES_BLOCK_SIZE];
521 
522  //Save the last input block
524 
525  //Decrypt payload data
526  aesProcessData(context, iv, c, p, length, AES_MR_OPMOD_CBC);
527 
528  //Update the value of the initialization vector
530  }
531  else
532  {
533  //The length of the payload must be a multiple of the block size
534  error = ERROR_INVALID_LENGTH;
535  }
536  }
537  else
538  {
539  size_t i;
540  uint8_t t[16];
541 
542  //CBC mode operates in a block-by-block fashion
543  while(length >= cipher->blockSize)
544  {
545  //Save input block
546  osMemcpy(t, c, cipher->blockSize);
547 
548  //Decrypt the current block
549  cipher->decryptBlock(context, c, p);
550 
551  //XOR output block with IV contents
552  for(i = 0; i < cipher->blockSize; i++)
553  {
554  p[i] ^= iv[i];
555  }
556 
557  //Update IV with input block contents
558  osMemcpy(iv, t, cipher->blockSize);
559 
560  //Next block
561  c += cipher->blockSize;
562  p += cipher->blockSize;
563  length -= cipher->blockSize;
564  }
565 
566  //The length of the payload must be a multiple of the block size
567  if(length != 0)
568  {
569  error = ERROR_INVALID_LENGTH;
570  }
571  }
572 
573  //Return status code
574  return error;
575 }
576 
577 #endif
578 #if (CFB_SUPPORT == ENABLED)
579 
580 /**
581  * @brief CFB encryption
582  * @param[in] cipher Cipher algorithm
583  * @param[in] context Cipher algorithm context
584  * @param[in] s Size of the plaintext and ciphertext segments
585  * @param[in,out] iv Initialization vector
586  * @param[in] p Plaintext to be encrypted
587  * @param[out] c Ciphertext resulting from the encryption
588  * @param[in] length Total number of data bytes to be encrypted
589  * @return Error code
590  **/
591 
592 error_t cfbEncrypt(const CipherAlgo *cipher, void *context, uint_t s,
593  uint8_t *iv, const uint8_t *p, uint8_t *c, size_t length)
594 {
595  error_t error;
596 
597  //Initialize status code
598  error = NO_ERROR;
599 
600  //AES cipher algorithm?
601  if(cipher == AES_CIPHER_ALGO)
602  {
603  //Check the value of the parameter
604  if(s == (AES_BLOCK_SIZE * 8))
605  {
606  //Check the length of the payload
607  if(length > 0)
608  {
609  //Encrypt payload data
610  aesProcessData(context, iv, p, c, length, AES_MR_CIPHER |
611  AES_MR_OPMOD_CFB | AES_MR_CFBS_SIZE_128BIT);
612  }
613  else
614  {
615  //No data to process
616  }
617  }
618  else
619  {
620  //The value of the parameter is not valid
621  error = ERROR_INVALID_PARAMETER;
622  }
623  }
624  else
625  {
626  //Check the value of the parameter
627  if((s % 8) == 0 && s >= 1 && s <= (cipher->blockSize * 8))
628  {
629  size_t i;
630  size_t n;
631  uint8_t o[16];
632 
633  //Determine the size, in bytes, of the plaintext and ciphertext segments
634  s = s / 8;
635 
636  //Process each plaintext segment
637  while(length > 0)
638  {
639  //Compute the number of bytes to process at a time
640  n = MIN(length, s);
641 
642  //Compute O(j) = CIPH(I(j))
643  cipher->encryptBlock(context, iv, o);
644 
645  //Compute C(j) = P(j) XOR MSB(O(j))
646  for(i = 0; i < n; i++)
647  {
648  c[i] = p[i] ^ o[i];
649  }
650 
651  //Compute I(j+1) = LSB(I(j)) | C(j)
652  osMemmove(iv, iv + s, cipher->blockSize - s);
653  osMemcpy(iv + cipher->blockSize - s, c, s);
654 
655  //Next block
656  p += n;
657  c += n;
658  length -= n;
659  }
660  }
661  else
662  {
663  //The value of the parameter is not valid
664  error = ERROR_INVALID_PARAMETER;
665  }
666  }
667 
668  //Return status code
669  return error;
670 }
671 
672 
673 /**
674  * @brief CFB decryption
675  * @param[in] cipher Cipher algorithm
676  * @param[in] context Cipher algorithm context
677  * @param[in] s Size of the plaintext and ciphertext segments
678  * @param[in,out] iv Initialization vector
679  * @param[in] c Ciphertext to be decrypted
680  * @param[out] p Plaintext resulting from the decryption
681  * @param[in] length Total number of data bytes to be decrypted
682  * @return Error code
683  **/
684 
685 error_t cfbDecrypt(const CipherAlgo *cipher, void *context, uint_t s,
686  uint8_t *iv, const uint8_t *c, uint8_t *p, size_t length)
687 {
688  error_t error;
689 
690  //Initialize status code
691  error = NO_ERROR;
692 
693  //AES cipher algorithm?
694  if(cipher == AES_CIPHER_ALGO)
695  {
696  //Check the value of the parameter
697  if(s == (AES_BLOCK_SIZE * 8))
698  {
699  //Check the length of the payload
700  if(length > 0)
701  {
702  //Decrypt payload data
703  aesProcessData(context, iv, c, p, length, AES_MR_OPMOD_CFB |
704  AES_MR_CFBS_SIZE_128BIT);
705  }
706  else
707  {
708  //No data to process
709  }
710  }
711  else
712  {
713  //The value of the parameter is not valid
714  error = ERROR_INVALID_PARAMETER;
715  }
716  }
717  else
718  {
719  //Check the value of the parameter
720  if((s % 8) == 0 && s >= 1 && s <= (cipher->blockSize * 8))
721  {
722  size_t i;
723  size_t n;
724  uint8_t o[16];
725 
726  //Determine the size, in bytes, of the plaintext and ciphertext segments
727  s = s / 8;
728 
729  //Process each ciphertext segment
730  while(length > 0)
731  {
732  //Compute the number of bytes to process at a time
733  n = MIN(length, s);
734 
735  //Compute O(j) = CIPH(I(j))
736  cipher->encryptBlock(context, iv, o);
737 
738  //Compute I(j+1) = LSB(I(j)) | C(j)
739  osMemmove(iv, iv + s, cipher->blockSize - s);
740  osMemcpy(iv + cipher->blockSize - s, c, s);
741 
742  //Compute P(j) = C(j) XOR MSB(O(j))
743  for(i = 0; i < n; i++)
744  {
745  p[i] = c[i] ^ o[i];
746  }
747 
748  //Next block
749  c += n;
750  p += n;
751  length -= n;
752  }
753  }
754  else
755  {
756  //The value of the parameter is not valid
757  error = ERROR_INVALID_PARAMETER;
758  }
759  }
760 
761  //Return status code
762  return error;
763 }
764 
765 #endif
766 #if (OFB_SUPPORT == ENABLED)
767 
768 /**
769  * @brief OFB encryption
770  * @param[in] cipher Cipher algorithm
771  * @param[in] context Cipher algorithm context
772  * @param[in] s Size of the plaintext and ciphertext segments
773  * @param[in,out] iv Initialization vector
774  * @param[in] p Plaintext to be encrypted
775  * @param[out] c Ciphertext resulting from the encryption
776  * @param[in] length Total number of data bytes to be encrypted
777  * @return Error code
778  **/
779 
780 error_t ofbEncrypt(const CipherAlgo *cipher, void *context, uint_t s,
781  uint8_t *iv, const uint8_t *p, uint8_t *c, size_t length)
782 {
783  error_t error;
784 
785  //Initialize status code
786  error = NO_ERROR;
787 
788  //AES cipher algorithm?
789  if(cipher == AES_CIPHER_ALGO)
790  {
791  //Check the value of the parameter
792  if(s == (AES_BLOCK_SIZE * 8))
793  {
794  //Check the length of the payload
795  if(length > 0)
796  {
797  //Encrypt payload data
798  aesProcessData(context, iv, p, c, length, AES_MR_CIPHER |
799  AES_MR_OPMOD_OFB);
800  }
801  else
802  {
803  //No data to process
804  }
805  }
806  else
807  {
808  //The value of the parameter is not valid
809  error = ERROR_INVALID_PARAMETER;
810  }
811  }
812  else
813  {
814  //Check the value of the parameter
815  if((s % 8) == 0 && s >= 1 && s <= (cipher->blockSize * 8))
816  {
817  size_t i;
818  size_t n;
819  uint8_t o[16];
820 
821  //Determine the size, in bytes, of the plaintext and ciphertext segments
822  s = s / 8;
823 
824  //Process each plaintext segment
825  while(length > 0)
826  {
827  //Compute the number of bytes to process at a time
828  n = MIN(length, s);
829 
830  //Compute O(j) = CIPH(I(j))
831  cipher->encryptBlock(context, iv, o);
832 
833  //Compute C(j) = P(j) XOR MSB(O(j))
834  for(i = 0; i < n; i++)
835  {
836  c[i] = p[i] ^ o[i];
837  }
838 
839  //Compute I(j+1) = LSB(I(j)) | O(j)
840  osMemmove(iv, iv + s, cipher->blockSize - s);
841  osMemcpy(iv + cipher->blockSize - s, o, s);
842 
843  //Next block
844  p += n;
845  c += n;
846  length -= n;
847  }
848  }
849  else
850  {
851  //The value of the parameter is not valid
852  error = ERROR_INVALID_PARAMETER;
853  }
854  }
855 
856  //Return status code
857  return error;
858 }
859 
860 #endif
861 #endif
#define AES_CIPHER_ALGO
Definition: aes.h:45
#define AES_BLOCK_SIZE
Definition: aes.h:43
Collection of AEAD algorithms.
Block cipher modes of operation.
unsigned int uint_t
Definition: compiler_port.h:50
General definitions for cryptographic algorithms.
Debugging facilities.
uint8_t n
uint8_t o
error_t
Error codes.
Definition: error.h:43
@ ERROR_INVALID_KEY_LENGTH
Definition: error.h:107
@ NO_ERROR
Success.
Definition: error.h:44
@ ERROR_INVALID_LENGTH
Definition: error.h:111
@ ERROR_INVALID_PARAMETER
Invalid parameter.
Definition: error.h:47
uint8_t iv[]
Definition: ike.h:1502
uint8_t t
Definition: lldp_ext_med.h:212
uint8_t c
Definition: ndp.h:514
uint8_t s
Definition: ndp.h:345
uint8_t p
Definition: ndp.h:300
#define osMemset(p, value, length)
Definition: os_port.h:135
#define osMemmove(dest, src, length)
Definition: os_port.h:147
#define osMemcpy(dest, src, length)
Definition: os_port.h:141
#define MIN(a, b)
Definition: os_port.h:63
void osAcquireMutex(OsMutex *mutex)
Acquire ownership of the specified mutex object.
void osReleaseMutex(OsMutex *mutex)
Release ownership of the specified mutex object.
OsMutex sam4eCryptoMutex
Definition: sam4e_crypto.c:42
SAM4E hardware cryptographic accelerator.
error_t aesInit(AesContext *context, const uint8_t *key, size_t keyLen)
Key expansion.
void aesLoadKey(AesContext *context)
Load AES key.
void aesProcessData(AesContext *context, uint8_t *iv, const uint8_t *input, uint8_t *output, size_t length, uint32_t mode)
Perform AES encryption or decryption.
error_t cbcEncrypt(const CipherAlgo *cipher, void *context, uint8_t *iv, const uint8_t *p, uint8_t *c, size_t length)
CBC encryption.
error_t cbcDecrypt(const CipherAlgo *cipher, void *context, uint8_t *iv, const uint8_t *c, uint8_t *p, size_t length)
CBC decryption.
void aesDecryptBlock(AesContext *context, const uint8_t *input, uint8_t *output)
Decrypt a 16-byte block using AES algorithm.
error_t cfbDecrypt(const CipherAlgo *cipher, void *context, uint_t s, uint8_t *iv, const uint8_t *c, uint8_t *p, size_t length)
CFB decryption.
void aesEncryptBlock(AesContext *context, const uint8_t *input, uint8_t *output)
Encrypt a 16-byte block using AES algorithm.
error_t ecbEncrypt(const CipherAlgo *cipher, void *context, const uint8_t *p, uint8_t *c, size_t length)
ECB encryption.
error_t cfbEncrypt(const CipherAlgo *cipher, void *context, uint_t s, uint8_t *iv, const uint8_t *p, uint8_t *c, size_t length)
CFB encryption.
void aesProcessDataBlock(const uint8_t *input, uint8_t *output)
Encrypt/decrypt a 16-byte block using AES algorithm.
error_t ofbEncrypt(const CipherAlgo *cipher, void *context, uint_t s, uint8_t *iv, const uint8_t *p, uint8_t *c, size_t length)
OFB encryption.
error_t ecbDecrypt(const CipherAlgo *cipher, void *context, const uint8_t *c, uint8_t *p, size_t length)
ECB decryption.
SAM4E cipher hardware accelerator.
AES algorithm context.
Definition: aes.h:58
uint_t nr
Definition: aes.h:59
uint32_t ek[60]
Definition: aes.h:60
Common interface for encryption algorithms.
Definition: crypto.h:1036
CipherAlgoEncryptBlock encryptBlock
Definition: crypto.h:1044
CipherAlgoDecryptBlock decryptBlock
Definition: crypto.h:1045
size_t blockSize
Definition: crypto.h:1040
uint8_t length
Definition: tcp.h:368
uint16_t block
Definition: tftp_common.h:115