gcm.c
Go to the documentation of this file.
1 /**
2  * @file gcm.c
3  * @brief Galois/Counter Mode (GCM)
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  * @section Description
28  *
29  * The Galois/Counter Mode (GCM) is an authenticated encryption algorithm
30  * designed to provide both data authenticity (integrity) and confidentiality.
31  * Refer to SP 800-38D for more details
32  *
33  * @author Oryx Embedded SARL (www.oryx-embedded.com)
34  * @version 2.4.0
35  **/
36 
37 //Switch to the appropriate trace level
38 #define TRACE_LEVEL CRYPTO_TRACE_LEVEL
39 
40 //Dependencies
41 #include "core/crypto.h"
42 #include "aead/gcm.h"
43 #include "debug.h"
44 
45 //Check crypto library configuration
46 #if (GCM_SUPPORT == ENABLED)
47 
48 //Reduction table
49 static const uint32_t r[GCM_TABLE_N] =
50 {
51 #if (GCM_TABLE_W == 4)
52  0x00000000, 0x1C200000, 0x38400000, 0x24600000, 0x70800000, 0x6CA00000, 0x48C00000, 0x54E00000,
53  0xE1000000, 0xFD200000, 0xD9400000, 0xC5600000, 0x91800000, 0x8DA00000, 0xA9C00000, 0xB5E00000
54 #else
55  0x00000000, 0x01C20000, 0x03840000, 0x02460000, 0x07080000, 0x06CA0000, 0x048C0000, 0x054E0000,
56  0x0E100000, 0x0FD20000, 0x0D940000, 0x0C560000, 0x09180000, 0x08DA0000, 0x0A9C0000, 0x0B5E0000,
57  0x1C200000, 0x1DE20000, 0x1FA40000, 0x1E660000, 0x1B280000, 0x1AEA0000, 0x18AC0000, 0x196E0000,
58  0x12300000, 0x13F20000, 0x11B40000, 0x10760000, 0x15380000, 0x14FA0000, 0x16BC0000, 0x177E0000,
59  0x38400000, 0x39820000, 0x3BC40000, 0x3A060000, 0x3F480000, 0x3E8A0000, 0x3CCC0000, 0x3D0E0000,
60  0x36500000, 0x37920000, 0x35D40000, 0x34160000, 0x31580000, 0x309A0000, 0x32DC0000, 0x331E0000,
61  0x24600000, 0x25A20000, 0x27E40000, 0x26260000, 0x23680000, 0x22AA0000, 0x20EC0000, 0x212E0000,
62  0x2A700000, 0x2BB20000, 0x29F40000, 0x28360000, 0x2D780000, 0x2CBA0000, 0x2EFC0000, 0x2F3E0000,
63  0x70800000, 0x71420000, 0x73040000, 0x72C60000, 0x77880000, 0x764A0000, 0x740C0000, 0x75CE0000,
64  0x7E900000, 0x7F520000, 0x7D140000, 0x7CD60000, 0x79980000, 0x785A0000, 0x7A1C0000, 0x7BDE0000,
65  0x6CA00000, 0x6D620000, 0x6F240000, 0x6EE60000, 0x6BA80000, 0x6A6A0000, 0x682C0000, 0x69EE0000,
66  0x62B00000, 0x63720000, 0x61340000, 0x60F60000, 0x65B80000, 0x647A0000, 0x663C0000, 0x67FE0000,
67  0x48C00000, 0x49020000, 0x4B440000, 0x4A860000, 0x4FC80000, 0x4E0A0000, 0x4C4C0000, 0x4D8E0000,
68  0x46D00000, 0x47120000, 0x45540000, 0x44960000, 0x41D80000, 0x401A0000, 0x425C0000, 0x439E0000,
69  0x54E00000, 0x55220000, 0x57640000, 0x56A60000, 0x53E80000, 0x522A0000, 0x506C0000, 0x51AE0000,
70  0x5AF00000, 0x5B320000, 0x59740000, 0x58B60000, 0x5DF80000, 0x5C3A0000, 0x5E7C0000, 0x5FBE0000,
71  0xE1000000, 0xE0C20000, 0xE2840000, 0xE3460000, 0xE6080000, 0xE7CA0000, 0xE58C0000, 0xE44E0000,
72  0xEF100000, 0xEED20000, 0xEC940000, 0xED560000, 0xE8180000, 0xE9DA0000, 0xEB9C0000, 0xEA5E0000,
73  0xFD200000, 0xFCE20000, 0xFEA40000, 0xFF660000, 0xFA280000, 0xFBEA0000, 0xF9AC0000, 0xF86E0000,
74  0xF3300000, 0xF2F20000, 0xF0B40000, 0xF1760000, 0xF4380000, 0xF5FA0000, 0xF7BC0000, 0xF67E0000,
75  0xD9400000, 0xD8820000, 0xDAC40000, 0xDB060000, 0xDE480000, 0xDF8A0000, 0xDDCC0000, 0xDC0E0000,
76  0xD7500000, 0xD6920000, 0xD4D40000, 0xD5160000, 0xD0580000, 0xD19A0000, 0xD3DC0000, 0xD21E0000,
77  0xC5600000, 0xC4A20000, 0xC6E40000, 0xC7260000, 0xC2680000, 0xC3AA0000, 0xC1EC0000, 0xC02E0000,
78  0xCB700000, 0xCAB20000, 0xC8F40000, 0xC9360000, 0xCC780000, 0xCDBA0000, 0xCFFC0000, 0xCE3E0000,
79  0x91800000, 0x90420000, 0x92040000, 0x93C60000, 0x96880000, 0x974A0000, 0x950C0000, 0x94CE0000,
80  0x9F900000, 0x9E520000, 0x9C140000, 0x9DD60000, 0x98980000, 0x995A0000, 0x9B1C0000, 0x9ADE0000,
81  0x8DA00000, 0x8C620000, 0x8E240000, 0x8FE60000, 0x8AA80000, 0x8B6A0000, 0x892C0000, 0x88EE0000,
82  0x83B00000, 0x82720000, 0x80340000, 0x81F60000, 0x84B80000, 0x857A0000, 0x873C0000, 0x86FE0000,
83  0xA9C00000, 0xA8020000, 0xAA440000, 0xAB860000, 0xAEC80000, 0xAF0A0000, 0xAD4C0000, 0xAC8E0000,
84  0xA7D00000, 0xA6120000, 0xA4540000, 0xA5960000, 0xA0D80000, 0xA11A0000, 0xA35C0000, 0xA29E0000,
85  0xB5E00000, 0xB4220000, 0xB6640000, 0xB7A60000, 0xB2E80000, 0xB32A0000, 0xB16C0000, 0xB0AE0000,
86  0xBBF00000, 0xBA320000, 0xB8740000, 0xB9B60000, 0xBCF80000, 0xBD3A0000, 0xBF7C0000, 0xBEBE0000
87 #endif
88 };
89 
90 
91 /**
92  * @brief Initialize GCM context
93  * @param[in] context Pointer to the GCM context
94  * @param[in] cipherAlgo Cipher algorithm
95  * @param[in] cipherContext Pointer to the cipher algorithm context
96  * @return Error code
97  **/
98 
99 __weak_func error_t gcmInit(GcmContext *context, const CipherAlgo *cipherAlgo,
100  void *cipherContext)
101 {
102  uint_t i;
103  uint_t j;
104  uint32_t c;
105  uint32_t h[4];
106 
107  //Check parameters
108  if(context == NULL || cipherAlgo == NULL || cipherContext == NULL)
110 
111  //GCM supports only symmetric block ciphers whose block size is 128 bits
112  if(cipherAlgo->type != CIPHER_ALGO_TYPE_BLOCK || cipherAlgo->blockSize != 16)
114 
115  //Save cipher algorithm context
116  context->cipherAlgo = cipherAlgo;
117  context->cipherContext = cipherContext;
118 
119  //Let H = 0
120  h[0] = 0;
121  h[1] = 0;
122  h[2] = 0;
123  h[3] = 0;
124 
125  //Generate the hash subkey H
126  context->cipherAlgo->encryptBlock(context->cipherContext, (uint8_t *) h,
127  (uint8_t *) h);
128 
129  //Pre-compute M(0) = H * 0
130  j = GCM_REVERSE_BITS(0);
131  context->m[j][0] = 0;
132  context->m[j][1] = 0;
133  context->m[j][2] = 0;
134  context->m[j][3] = 0;
135 
136  //Pre-compute M(1) = H * 1
137  j = GCM_REVERSE_BITS(1);
138  context->m[j][0] = betoh32(h[3]);
139  context->m[j][1] = betoh32(h[2]);
140  context->m[j][2] = betoh32(h[1]);
141  context->m[j][3] = betoh32(h[0]);
142 
143  //Pre-compute all multiples of H (Shoup's method)
144  for(i = 2; i < GCM_TABLE_N; i++)
145  {
146  //Odd value?
147  if((i & 1) != 0)
148  {
149  //Compute M(i) = M(i - 1) + H
150  j = GCM_REVERSE_BITS(i - 1);
151  h[0] = context->m[j][0];
152  h[1] = context->m[j][1];
153  h[2] = context->m[j][2];
154  h[3] = context->m[j][3];
155 
156  //An addition in GF(2^128) is identical to a bitwise exclusive-OR
157  //operation
158  j = GCM_REVERSE_BITS(1);
159  h[0] ^= context->m[j][0];
160  h[1] ^= context->m[j][1];
161  h[2] ^= context->m[j][2];
162  h[3] ^= context->m[j][3];
163  }
164  else
165  {
166  //Compute M(i) = M(i / 2) * x
167  j = GCM_REVERSE_BITS(i / 2);
168  h[0] = context->m[j][0];
169  h[1] = context->m[j][1];
170  h[2] = context->m[j][2];
171  h[3] = context->m[j][3];
172 
173  //The multiplication of a polynomial by x in GF(2^128) corresponds
174  //to a shift of indices
175  c = h[0] & 0x01;
176  h[0] = (h[0] >> 1) | (h[1] << 31);
177  h[1] = (h[1] >> 1) | (h[2] << 31);
178  h[2] = (h[2] >> 1) | (h[3] << 31);
179  h[3] >>= 1;
180 
181  //If the highest term of the result is equal to one, then perform
182  //reduction
183  h[3] ^= r[GCM_REVERSE_BITS(1)] & ~(c - 1);
184  }
185 
186  //Save M(i)
187  j = GCM_REVERSE_BITS(i);
188  context->m[j][0] = h[0];
189  context->m[j][1] = h[1];
190  context->m[j][2] = h[2];
191  context->m[j][3] = h[3];
192  }
193 
194  //Successful initialization
195  return NO_ERROR;
196 }
197 
198 
199 /**
200  * @brief Authenticated encryption using GCM
201  * @param[in] context Pointer to the GCM context
202  * @param[in] iv Initialization vector
203  * @param[in] ivLen Length of the initialization vector
204  * @param[in] a Additional authenticated data
205  * @param[in] aLen Length of the additional data
206  * @param[in] p Plaintext to be encrypted
207  * @param[out] c Ciphertext resulting from the encryption
208  * @param[in] length Total number of data bytes to be encrypted
209  * @param[out] t Authentication tag
210  * @param[in] tLen Length of the authentication tag
211  * @return Error code
212  **/
213 
214 __weak_func error_t gcmEncrypt(GcmContext *context, const uint8_t *iv,
215  size_t ivLen, const uint8_t *a, size_t aLen, const uint8_t *p,
216  uint8_t *c, size_t length, uint8_t *t, size_t tLen)
217 {
218  size_t k;
219  size_t n;
220  uint8_t b[16];
221  uint8_t j[16];
222  uint8_t s[16];
223 
224  //Make sure the GCM context is valid
225  if(context == NULL)
227 
228  //The length of the IV shall meet SP 800-38D requirements
229  if(ivLen < 1)
230  return ERROR_INVALID_LENGTH;
231 
232  //Check the length of the authentication tag
233  if(tLen < 4 || tLen > 16)
234  return ERROR_INVALID_LENGTH;
235 
236  //Check whether the length of the IV is 96 bits
237  if(ivLen == 12)
238  {
239  //When the length of the IV is 96 bits, the padding string is appended
240  //to the IV to form the pre-counter block
241  osMemcpy(j, iv, 12);
242  STORE32BE(1, j + 12);
243  }
244  else
245  {
246  //Initialize GHASH calculation
247  osMemset(j, 0, 16);
248 
249  //Length of the IV
250  n = ivLen;
251 
252  //Process the initialization vector
253  while(n > 0)
254  {
255  //The IV processed in a block-by-block fashion
256  k = MIN(n, 16);
257 
258  //Apply GHASH function
259  gcmXorBlock(j, j, iv, k);
260  gcmMul(context, j);
261 
262  //Next block
263  iv += k;
264  n -= k;
265  }
266 
267  //The string is appended with 64 additional 0 bits, followed by the
268  //64-bit representation of the length of the IV
269  osMemset(b, 0, 8);
270  STORE64BE(ivLen * 8, b + 8);
271 
272  //The GHASH function is applied to the resulting string to form the
273  //pre-counter block
274  gcmXorBlock(j, j, b, 16);
275  gcmMul(context, j);
276  }
277 
278  //Compute MSB(CIPH(J(0)))
279  context->cipherAlgo->encryptBlock(context->cipherContext, j, b);
280  osMemcpy(t, b, tLen);
281 
282  //Initialize GHASH calculation
283  osMemset(s, 0, 16);
284  //Length of the AAD
285  n = aLen;
286 
287  //Process AAD
288  while(n > 0)
289  {
290  //Additional data are processed in a block-by-block fashion
291  k = MIN(n, 16);
292 
293  //Apply GHASH function
294  gcmXorBlock(s, s, a, k);
295  gcmMul(context, s);
296 
297  //Next block
298  a += k;
299  n -= k;
300  }
301 
302  //Length of the plaintext
303  n = length;
304 
305  //Process plaintext
306  while(n > 0)
307  {
308  //The encryption operates in a block-by-block fashion
309  k = MIN(n, 16);
310 
311  //Increment counter
312  gcmIncCounter(j);
313 
314  //Encrypt plaintext
315  context->cipherAlgo->encryptBlock(context->cipherContext, j, b);
316  gcmXorBlock(c, p, b, k);
317 
318  //Apply GHASH function
319  gcmXorBlock(s, s, c, k);
320  gcmMul(context, s);
321 
322  //Next block
323  p += k;
324  c += k;
325  n -= k;
326  }
327 
328  //Append the 64-bit representation of the length of the AAD and the
329  //ciphertext
330  STORE64BE(aLen * 8, b);
331  STORE64BE(length * 8, b + 8);
332 
333  //The GHASH function is applied to the result to produce a single output
334  //block S
335  gcmXorBlock(s, s, b, 16);
336  gcmMul(context, s);
337 
338  //Let T = MSB(GCTR(J(0), S)
339  gcmXorBlock(t, t, s, tLen);
340 
341  //Successful encryption
342  return NO_ERROR;
343 }
344 
345 
346 /**
347  * @brief Authenticated decryption using GCM
348  * @param[in] context Pointer to the GCM context
349  * @param[in] iv Initialization vector
350  * @param[in] ivLen Length of the initialization vector
351  * @param[in] a Additional authenticated data
352  * @param[in] aLen Length of the additional data
353  * @param[in] c Ciphertext to be decrypted
354  * @param[out] p Plaintext resulting from the decryption
355  * @param[in] length Total number of data bytes to be decrypted
356  * @param[in] t Authentication tag
357  * @param[in] tLen Length of the authentication tag
358  * @return Error code
359  **/
360 
361 __weak_func error_t gcmDecrypt(GcmContext *context, const uint8_t *iv,
362  size_t ivLen, const uint8_t *a, size_t aLen, const uint8_t *c,
363  uint8_t *p, size_t length, const uint8_t *t, size_t tLen)
364 {
365  uint8_t mask;
366  size_t k;
367  size_t n;
368  uint8_t b[16];
369  uint8_t j[16];
370  uint8_t r[16];
371  uint8_t s[16];
372 
373  //Make sure the GCM context is valid
374  if(context == NULL)
376 
377  //The length of the IV shall meet SP 800-38D requirements
378  if(ivLen < 1)
379  return ERROR_INVALID_LENGTH;
380 
381  //Check the length of the authentication tag
382  if(tLen < 4 || tLen > 16)
383  return ERROR_INVALID_LENGTH;
384 
385  //Check whether the length of the IV is 96 bits
386  if(ivLen == 12)
387  {
388  //When the length of the IV is 96 bits, the padding string is appended
389  //to the IV to form the pre-counter block
390  osMemcpy(j, iv, 12);
391  STORE32BE(1, j + 12);
392  }
393  else
394  {
395  //Initialize GHASH calculation
396  osMemset(j, 0, 16);
397 
398  //Length of the IV
399  n = ivLen;
400 
401  //Process the initialization vector
402  while(n > 0)
403  {
404  //The IV processed in a block-by-block fashion
405  k = MIN(n, 16);
406 
407  //Apply GHASH function
408  gcmXorBlock(j, j, iv, k);
409  gcmMul(context, j);
410 
411  //Next block
412  iv += k;
413  n -= k;
414  }
415 
416  //The string is appended with 64 additional 0 bits, followed by the
417  //64-bit representation of the length of the IV
418  osMemset(b, 0, 8);
419  STORE64BE(ivLen * 8, b + 8);
420 
421  //The GHASH function is applied to the resulting string to form the
422  //pre-counter block
423  gcmXorBlock(j, j, b, 16);
424  gcmMul(context, j);
425  }
426 
427  //Compute MSB(CIPH(J(0)))
428  context->cipherAlgo->encryptBlock(context->cipherContext, j, b);
429  osMemcpy(r, b, tLen);
430 
431  //Initialize GHASH calculation
432  osMemset(s, 0, 16);
433  //Length of the AAD
434  n = aLen;
435 
436  //Process AAD
437  while(n > 0)
438  {
439  //Additional data are processed in a block-by-block fashion
440  k = MIN(n, 16);
441 
442  //Apply GHASH function
443  gcmXorBlock(s, s, a, k);
444  gcmMul(context, s);
445 
446  //Next block
447  a += k;
448  n -= k;
449  }
450 
451  //Length of the ciphertext
452  n = length;
453 
454  //Process ciphertext
455  while(n > 0)
456  {
457  //The decryption operates in a block-by-block fashion
458  k = MIN(n, 16);
459 
460  //Apply GHASH function
461  gcmXorBlock(s, s, c, k);
462  gcmMul(context, s);
463 
464  //Increment counter
465  gcmIncCounter(j);
466 
467  //Decrypt ciphertext
468  context->cipherAlgo->encryptBlock(context->cipherContext, j, b);
469  gcmXorBlock(p, c, b, k);
470 
471  //Next block
472  c += k;
473  p += k;
474  n -= k;
475  }
476 
477  //Append the 64-bit representation of the length of the AAD and the
478  //ciphertext
479  STORE64BE(aLen * 8, b);
480  STORE64BE(length * 8, b + 8);
481 
482  //The GHASH function is applied to the result to produce a single output
483  //block S
484  gcmXorBlock(s, s, b, 16);
485  gcmMul(context, s);
486 
487  //Let R = MSB(GCTR(J(0), S))
488  gcmXorBlock(r, r, s, tLen);
489 
490  //The calculated tag is bitwise compared to the received tag. The message
491  //is authenticated if and only if the tags match
492  for(mask = 0, n = 0; n < tLen; n++)
493  {
494  mask |= r[n] ^ t[n];
495  }
496 
497  //Return status code
498  return (mask == 0) ? NO_ERROR : ERROR_FAILURE;
499 }
500 
501 
502 /**
503  * @brief Multiplication operation in GF(2^128)
504  * @param[in] context Pointer to the GCM context
505  * @param[in, out] x 16-byte block to be multiplied by H
506  **/
507 
508 __weak_func void gcmMul(GcmContext *context, uint8_t *x)
509 {
510  int_t i;
511  uint8_t b;
512  uint8_t c;
513  uint32_t z[4];
514 
515  //Let Z = 0
516  z[0] = 0;
517  z[1] = 0;
518  z[2] = 0;
519  z[3] = 0;
520 
521  //Fast table-driven implementation (Shoup's method)
522  for(i = 15; i >= 0; i--)
523  {
524 #if (GCM_TABLE_W == 4)
525  //Get the lower nibble
526  b = x[i] & 0x0F;
527 
528  //Multiply 4 bits at a time
529  c = z[0] & 0x0F;
530  z[0] = (z[0] >> 4) | (z[1] << 28);
531  z[1] = (z[1] >> 4) | (z[2] << 28);
532  z[2] = (z[2] >> 4) | (z[3] << 28);
533  z[3] >>= 4;
534 
535  z[0] ^= context->m[b][0];
536  z[1] ^= context->m[b][1];
537  z[2] ^= context->m[b][2];
538  z[3] ^= context->m[b][3];
539 
540  //Perform reduction
541  z[3] ^= r[c];
542 
543  //Get the upper nibble
544  b = (x[i] >> 4) & 0x0F;
545 
546  //Multiply 4 bits at a time
547  c = z[0] & 0x0F;
548  z[0] = (z[0] >> 4) | (z[1] << 28);
549  z[1] = (z[1] >> 4) | (z[2] << 28);
550  z[2] = (z[2] >> 4) | (z[3] << 28);
551  z[3] >>= 4;
552 
553  z[0] ^= context->m[b][0];
554  z[1] ^= context->m[b][1];
555  z[2] ^= context->m[b][2];
556  z[3] ^= context->m[b][3];
557 
558  //Perform reduction
559  z[3] ^= r[c];
560 #else
561  //Get current byte
562  b = x[i];
563 
564  //Multiply 8 bits at a time
565  c = z[0] & 0xFF;
566  z[0] = (z[0] >> 8) | (z[1] << 24);
567  z[1] = (z[1] >> 8) | (z[2] << 24);
568  z[2] = (z[2] >> 8) | (z[3] << 24);
569  z[3] >>= 8;
570 
571  z[0] ^= context->m[b][0];
572  z[1] ^= context->m[b][1];
573  z[2] ^= context->m[b][2];
574  z[3] ^= context->m[b][3];
575 
576  //Perform reduction
577  z[3] ^= r[c];
578 #endif
579  }
580 
581  //Save the result
582  STORE32BE(z[3], x);
583  STORE32BE(z[2], x + 4);
584  STORE32BE(z[1], x + 8);
585  STORE32BE(z[0], x + 12);
586 }
587 
588 
589 /**
590  * @brief XOR operation
591  * @param[out] x Block resulting from the XOR operation
592  * @param[in] a First block
593  * @param[in] b Second block
594  * @param[in] n Size of the block
595  **/
596 
597 void gcmXorBlock(uint8_t *x, const uint8_t *a, const uint8_t *b, size_t n)
598 {
599  size_t i;
600 
601  //Perform XOR operation
602  for(i = 0; i < n; i++)
603  {
604  x[i] = a[i] ^ b[i];
605  }
606 }
607 
608 
609 /**
610  * @brief Increment counter block
611  * @param[in,out] ctr Pointer to the counter block
612  **/
613 
614 void gcmIncCounter(uint8_t *ctr)
615 {
616  uint16_t temp;
617 
618  //The function increments the right-most 32 bits of the block. The remaining
619  //left-most 96 bits remain unchanged
620  temp = ctr[15] + 1;
621  ctr[15] = temp & 0xFF;
622  temp = (temp >> 8) + ctr[14];
623  ctr[14] = temp & 0xFF;
624  temp = (temp >> 8) + ctr[13];
625  ctr[13] = temp & 0xFF;
626  temp = (temp >> 8) + ctr[12];
627  ctr[12] = temp & 0xFF;
628 }
629 
630 #endif
signed int int_t
Definition: compiler_port.h:49
unsigned int uint_t
Definition: compiler_port.h:50
#define betoh32(value)
Definition: cpu_endian.h:454
#define STORE32BE(a, p)
Definition: cpu_endian.h:286
#define STORE64BE(a, p)
Definition: cpu_endian.h:322
General definitions for cryptographic algorithms.
@ CIPHER_ALGO_TYPE_BLOCK
Definition: crypto.h:932
Debugging facilities.
uint8_t n
uint8_t z
Definition: dns_common.h:191
error_t
Error codes.
Definition: error.h:43
@ NO_ERROR
Success.
Definition: error.h:44
@ ERROR_INVALID_LENGTH
Definition: error.h:111
@ ERROR_FAILURE
Generic error code.
Definition: error.h:45
@ ERROR_INVALID_PARAMETER
Invalid parameter.
Definition: error.h:47
__weak_func error_t gcmInit(GcmContext *context, const CipherAlgo *cipherAlgo, void *cipherContext)
Initialize GCM context.
Definition: gcm.c:99
__weak_func void gcmMul(GcmContext *context, uint8_t *x)
Multiplication operation in GF(2^128)
Definition: gcm.c:508
__weak_func error_t gcmDecrypt(GcmContext *context, const uint8_t *iv, size_t ivLen, const uint8_t *a, size_t aLen, const uint8_t *c, uint8_t *p, size_t length, const uint8_t *t, size_t tLen)
Authenticated decryption using GCM.
Definition: gcm.c:361
void gcmIncCounter(uint8_t *ctr)
Increment counter block.
Definition: gcm.c:614
__weak_func error_t gcmEncrypt(GcmContext *context, const uint8_t *iv, size_t ivLen, const uint8_t *a, size_t aLen, const uint8_t *p, uint8_t *c, size_t length, uint8_t *t, size_t tLen)
Authenticated encryption using GCM.
Definition: gcm.c:214
void gcmXorBlock(uint8_t *x, const uint8_t *a, const uint8_t *b, size_t n)
XOR operation.
Definition: gcm.c:597
Galois/Counter Mode (GCM)
#define GCM_TABLE_N
Definition: gcm.h:46
#define GCM_REVERSE_BITS(n)
Definition: gcm.h:47
uint8_t iv[]
Definition: ike.h:1502
uint8_t x
Definition: lldp_ext_med.h:211
uint8_t t
Definition: lldp_ext_med.h:212
uint8_t b
Definition: nbns_common.h:104
uint8_t h
Definition: ndp.h:302
uint8_t c
Definition: ndp.h:514
uint8_t r
Definition: ndp.h:346
uint8_t s
Definition: ndp.h:345
uint8_t p
Definition: ndp.h:300
uint8_t a
Definition: ndp.h:411
#define osMemset(p, value, length)
Definition: os_port.h:135
#define osMemcpy(dest, src, length)
Definition: os_port.h:141
#define MIN(a, b)
Definition: os_port.h:63
Common interface for encryption algorithms.
Definition: crypto.h:1036
CipherAlgoEncryptBlock encryptBlock
Definition: crypto.h:1044
size_t blockSize
Definition: crypto.h:1040
CipherAlgoType type
Definition: crypto.h:1039
GCM context.
Definition: gcm.h:64
const CipherAlgo * cipherAlgo
Cipher algorithm.
Definition: gcm.h:65
void * cipherContext
Cipher algorithm context.
Definition: gcm.h:66
uint32_t m[GCM_TABLE_N][4]
Precalculated table.
Definition: gcm.h:67
uint8_t length
Definition: tcp.h:368
uint8_t mask
Definition: web_socket.h:319