iPXE
rsa.c
Go to the documentation of this file.
1 /*
2  * Copyright (C) 2012 Michael Brown <mbrown@fensystems.co.uk>.
3  *
4  * This program is free software; you can redistribute it and/or
5  * modify it under the terms of the GNU General Public License as
6  * published by the Free Software Foundation; either version 2 of the
7  * License, or any later version.
8  *
9  * This program is distributed in the hope that it will be useful, but
10  * WITHOUT ANY WARRANTY; without even the implied warranty of
11  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
12  * General Public License for more details.
13  *
14  * You should have received a copy of the GNU General Public License
15  * along with this program; if not, write to the Free Software
16  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
17  * 02110-1301, USA.
18  *
19  * You can also choose to distribute this program under the terms of
20  * the Unmodified Binary Distribution Licence (as given in the file
21  * COPYING.UBDL), provided that you have satisfied its requirements.
22  */
23 
24 FILE_LICENCE ( GPL2_OR_LATER_OR_UBDL );
25 FILE_SECBOOT ( PERMITTED );
26 
27 #include <stdint.h>
28 #include <stdlib.h>
29 #include <stdarg.h>
30 #include <string.h>
31 #include <errno.h>
32 #include <ipxe/asn1.h>
33 #include <ipxe/crypto.h>
34 #include <ipxe/bigint.h>
35 #include <ipxe/random_nz.h>
36 #include <ipxe/rsa.h>
37 
38 /** @file
39  *
40  * RSA public-key cryptography
41  *
42  * RSA is documented in RFC 3447.
43  */
44 
45 /* Disambiguate the various error causes */
46 #define EACCES_VERIFY \
47  __einfo_error ( EINFO_EACCES_VERIFY )
48 #define EINFO_EACCES_VERIFY \
49  __einfo_uniqify ( EINFO_EACCES, 0x01, "RSA signature incorrect" )
50 
51 /** An RSA context */
52 struct rsa_context {
53  /** Allocated memory */
54  void *dynamic;
55  /** Modulus */
57  /** Modulus size */
58  unsigned int size;
59  /** Modulus length */
60  size_t max_len;
61  /** Exponent */
63  /** Exponent size */
64  unsigned int exponent_size;
65  /** Input buffer */
67  /** Output buffer */
69  /** Temporary working space for modular exponentiation */
70  void *tmp;
71 };
72 
73 /**
74  * Identify RSA prefix
75  *
76  * @v digest Digest algorithm
77  * @ret prefix RSA prefix, or NULL
78  */
79 static struct rsa_digestinfo_prefix *
82 
84  if ( prefix->digest == digest )
85  return prefix;
86  }
87  return NULL;
88 }
89 
90 /**
91  * Free RSA dynamic storage
92  *
93  * @v context RSA context
94  */
95 static inline void rsa_free ( struct rsa_context *context ) {
96 
97  free ( context->dynamic );
98 }
99 
100 /**
101  * Allocate RSA dynamic storage
102  *
103  * @v context RSA context
104  * @v modulus_len Modulus length
105  * @v exponent_len Exponent length
106  * @ret rc Return status code
107  */
108 static int rsa_alloc ( struct rsa_context *context, size_t modulus_len,
109  size_t exponent_len ) {
110  unsigned int size = bigint_required_size ( modulus_len );
111  unsigned int exponent_size = bigint_required_size ( exponent_len );
112  bigint_t ( size ) *modulus;
113  size_t tmp_len = bigint_mod_exp_tmp_len ( modulus );
114  struct {
115  bigint_t ( size ) modulus;
116  bigint_t ( exponent_size ) exponent;
117  bigint_t ( size ) input;
118  bigint_t ( size ) output;
119  uint8_t tmp[tmp_len];
120  } __attribute__ (( packed )) *dynamic;
121 
122  /* Allocate dynamic storage */
123  dynamic = malloc ( sizeof ( *dynamic ) );
124  if ( ! dynamic )
125  return -ENOMEM;
126 
127  /* Assign dynamic storage */
128  context->dynamic = dynamic;
129  context->modulus0 = &dynamic->modulus.element[0];
130  context->size = size;
131  context->max_len = modulus_len;
132  context->exponent0 = &dynamic->exponent.element[0];
133  context->exponent_size = exponent_size;
134  context->input0 = &dynamic->input.element[0];
135  context->output0 = &dynamic->output.element[0];
136  context->tmp = &dynamic->tmp;
137 
138  return 0;
139 }
140 
141 /**
142  * Parse RSA modulus and exponent
143  *
144  * @v modulus Modulus to fill in
145  * @v exponent Exponent to fill in
146  * @v raw ASN.1 cursor
147  * @ret rc Return status code
148  */
149 static int rsa_parse_mod_exp ( struct asn1_cursor *modulus,
150  struct asn1_cursor *exponent,
151  const struct asn1_cursor *raw ) {
152  struct asn1_cursor cursor;
153  int is_private;
154  int rc;
155 
156  /* Enter subjectPublicKeyInfo/privateKeyInfo/RSAPrivateKey */
157  memcpy ( &cursor, raw, sizeof ( cursor ) );
158  asn1_enter ( &cursor, ASN1_SEQUENCE );
159 
160  /* Determine key format */
161  if ( asn1_type ( &cursor ) == ASN1_INTEGER ) {
162 
163  /* Private key */
164  is_private = 1;
165 
166  /* Skip version */
167  asn1_skip_any ( &cursor );
168 
169  /* Enter privateKey, if present */
170  if ( asn1_check_algorithm ( &cursor, &rsa_encryption_algorithm,
171  NULL ) == 0 ) {
172 
173  /* Skip privateKeyAlgorithm */
174  asn1_skip_any ( &cursor );
175 
176  /* Enter privateKey */
177  asn1_enter ( &cursor, ASN1_OCTET_STRING );
178 
179  /* Enter RSAPrivateKey */
180  asn1_enter ( &cursor, ASN1_SEQUENCE );
181 
182  /* Skip version */
183  asn1_skip ( &cursor, ASN1_INTEGER );
184  }
185 
186  } else {
187 
188  /* Public key */
189  is_private = 0;
190 
191  /* Skip algorithm */
192  asn1_skip ( &cursor, ASN1_SEQUENCE );
193 
194  /* Enter subjectPublicKey */
195  asn1_enter_bits ( &cursor, NULL );
196 
197  /* Enter RSAPublicKey */
198  asn1_enter ( &cursor, ASN1_SEQUENCE );
199  }
200 
201  /* Extract modulus */
202  memcpy ( modulus, &cursor, sizeof ( *modulus ) );
203  if ( ( rc = asn1_enter_unsigned ( modulus ) ) != 0 )
204  return rc;
205  asn1_skip_any ( &cursor );
206 
207  /* Skip public exponent, if applicable */
208  if ( is_private )
209  asn1_skip ( &cursor, ASN1_INTEGER );
210 
211  /* Extract publicExponent/privateExponent */
212  memcpy ( exponent, &cursor, sizeof ( *exponent ) );
213  if ( ( rc = asn1_enter_unsigned ( exponent ) ) != 0 )
214  return rc;
215 
216  return 0;
217 }
218 
219 /**
220  * Initialise RSA cipher
221  *
222  * @v context RSA context
223  * @v key Key
224  * @ret rc Return status code
225  */
226 static int rsa_init ( struct rsa_context *context,
227  const struct asn1_cursor *key ) {
228  struct asn1_cursor modulus;
229  struct asn1_cursor exponent;
230  int rc;
231 
232  /* Initialise context */
233  memset ( context, 0, sizeof ( *context ) );
234 
235  /* Parse modulus and exponent */
236  if ( ( rc = rsa_parse_mod_exp ( &modulus, &exponent, key ) ) != 0 ){
237  DBGC ( context, "RSA %p invalid modulus/exponent:\n", context );
238  DBGC_HDA ( context, 0, key->data, key->len );
239  goto err_parse;
240  }
241 
242  DBGC ( context, "RSA %p modulus:\n", context );
243  DBGC_HDA ( context, 0, modulus.data, modulus.len );
244  DBGC ( context, "RSA %p exponent:\n", context );
245  DBGC_HDA ( context, 0, exponent.data, exponent.len );
246 
247  /* Allocate dynamic storage */
248  if ( ( rc = rsa_alloc ( context, modulus.len, exponent.len ) ) != 0 )
249  goto err_alloc;
250 
251  /* Construct big integers */
252  bigint_init ( ( ( bigint_t ( context->size ) * ) context->modulus0 ),
253  modulus.data, modulus.len );
254  bigint_init ( ( ( bigint_t ( context->exponent_size ) * )
255  context->exponent0 ), exponent.data, exponent.len );
256 
257  return 0;
258 
259  rsa_free ( context );
260  err_alloc:
261  err_parse:
262  return rc;
263 }
264 
265 /**
266  * Perform RSA cipher operation
267  *
268  * @v context RSA context
269  * @v in Input buffer
270  * @v out Output buffer
271  */
272 static void rsa_cipher ( struct rsa_context *context,
273  const void *in, void *out ) {
274  bigint_t ( context->size ) *input = ( ( void * ) context->input0 );
275  bigint_t ( context->size ) *output = ( ( void * ) context->output0 );
276  bigint_t ( context->size ) *modulus = ( ( void * ) context->modulus0 );
277  bigint_t ( context->exponent_size ) *exponent =
278  ( ( void * ) context->exponent0 );
279 
280  /* Initialise big integer */
281  bigint_init ( input, in, context->max_len );
282 
283  /* Perform modular exponentiation */
284  bigint_mod_exp ( input, modulus, exponent, output, context->tmp );
285 
286  /* Copy out result */
287  bigint_done ( output, out, context->max_len );
288 }
289 
290 /**
291  * Encrypt using RSA
292  *
293  * @v key Key
294  * @v plaintext Plaintext
295  * @v ciphertext Ciphertext
296  * @ret ciphertext_len Length of ciphertext, or negative error
297  */
298 static int rsa_encrypt ( const struct asn1_cursor *key,
299  const struct asn1_cursor *plaintext,
300  struct asn1_builder *ciphertext ) {
301  struct rsa_context context;
302  void *temp;
303  uint8_t *encoded;
304  size_t max_len;
305  size_t random_nz_len;
306  int rc;
307 
308  DBGC ( &context, "RSA %p encrypting:\n", &context );
309  DBGC_HDA ( &context, 0, plaintext->data, plaintext->len );
310 
311  /* Initialise context */
312  if ( ( rc = rsa_init ( &context, key ) ) != 0 )
313  goto err_init;
314 
315  /* Calculate lengths */
316  max_len = ( context.max_len - 11 );
317  random_nz_len = ( max_len - plaintext->len + 8 );
318 
319  /* Sanity check */
320  if ( plaintext->len > max_len ) {
321  DBGC ( &context, "RSA %p plaintext too long (%zd bytes, max "
322  "%zd)\n", &context, plaintext->len, max_len );
323  rc = -ERANGE;
324  goto err_sanity;
325  }
326 
327  /* Construct encoded message (using the big integer output
328  * buffer as temporary storage)
329  */
330  temp = context.output0;
331  encoded = temp;
332  encoded[0] = 0x00;
333  encoded[1] = 0x02;
334  if ( ( rc = get_random_nz ( &encoded[2], random_nz_len ) ) != 0 ) {
335  DBGC ( &context, "RSA %p could not generate random data: %s\n",
336  &context, strerror ( rc ) );
337  goto err_random;
338  }
339  encoded[ 2 + random_nz_len ] = 0x00;
340  memcpy ( &encoded[ context.max_len - plaintext->len ],
341  plaintext->data, plaintext->len );
342 
343  /* Create space for ciphertext */
344  if ( ( rc = asn1_grow ( ciphertext, context.max_len ) ) != 0 )
345  goto err_grow;
346 
347  /* Encipher the encoded message */
348  rsa_cipher ( &context, encoded, ciphertext->data );
349  DBGC ( &context, "RSA %p encrypted:\n", &context );
350  DBGC_HDA ( &context, 0, ciphertext->data, context.max_len );
351 
352  /* Free context */
353  rsa_free ( &context );
354 
355  return 0;
356 
357  err_grow:
358  err_random:
359  err_sanity:
360  rsa_free ( &context );
361  err_init:
362  return rc;
363 }
364 
365 /**
366  * Decrypt using RSA
367  *
368  * @v key Key
369  * @v ciphertext Ciphertext
370  * @v plaintext Plaintext
371  * @ret rc Return status code
372  */
373 static int rsa_decrypt ( const struct asn1_cursor *key,
374  const struct asn1_cursor *ciphertext,
375  struct asn1_builder *plaintext ) {
376  struct rsa_context context;
377  void *temp;
378  uint8_t *encoded;
379  uint8_t *end;
380  uint8_t *zero;
381  uint8_t *start;
382  size_t len;
383  int rc;
384 
385  DBGC ( &context, "RSA %p decrypting:\n", &context );
386  DBGC_HDA ( &context, 0, ciphertext->data, ciphertext->len );
387 
388  /* Initialise context */
389  if ( ( rc = rsa_init ( &context, key ) ) != 0 )
390  goto err_init;
391 
392  /* Sanity check */
393  if ( ciphertext->len != context.max_len ) {
394  DBGC ( &context, "RSA %p ciphertext incorrect length (%zd "
395  "bytes, should be %zd)\n",
396  &context, ciphertext->len, context.max_len );
397  rc = -ERANGE;
398  goto err_sanity;
399  }
400 
401  /* Decipher the message (using the big integer input buffer as
402  * temporary storage)
403  */
404  temp = context.input0;
405  encoded = temp;
406  rsa_cipher ( &context, ciphertext->data, encoded );
407 
408  /* Parse the message */
409  end = ( encoded + context.max_len );
410  if ( ( encoded[0] != 0x00 ) || ( encoded[1] != 0x02 ) ) {
411  rc = -EINVAL;
412  goto err_invalid;
413  }
414  zero = memchr ( &encoded[2], 0, ( end - &encoded[2] ) );
415  if ( ! zero ) {
416  DBGC ( &context, "RSA %p invalid decrypted message:\n",
417  &context );
418  DBGC_HDA ( &context, 0, encoded, context.max_len );
419  rc = -EINVAL;
420  goto err_invalid;
421  }
422  start = ( zero + 1 );
423  len = ( end - start );
424 
425  /* Create space for plaintext */
426  if ( ( rc = asn1_grow ( plaintext, len ) ) != 0 )
427  goto err_grow;
428 
429  /* Copy out message */
430  memcpy ( plaintext->data, start, len );
431  DBGC ( &context, "RSA %p decrypted:\n", &context );
432  DBGC_HDA ( &context, 0, plaintext->data, len );
433 
434  /* Free context */
435  rsa_free ( &context );
436 
437  return 0;
438 
439  err_grow:
440  err_invalid:
441  err_sanity:
442  rsa_free ( &context );
443  err_init:
444  return rc;
445 }
446 
447 /**
448  * Encode RSA digest
449  *
450  * @v context RSA context
451  * @v digest Digest algorithm
452  * @v value Digest value
453  * @v encoded Encoded digest
454  * @ret rc Return status code
455  */
456 static int rsa_encode_digest ( struct rsa_context *context,
457  struct digest_algorithm *digest,
458  const void *value, void *encoded ) {
460  size_t digest_len = digest->digestsize;
461  uint8_t *temp = encoded;
462  size_t digestinfo_len;
463  size_t max_len;
464  size_t pad_len;
465 
466  /* Identify prefix */
468  if ( ! prefix ) {
469  DBGC ( context, "RSA %p has no prefix for %s\n",
470  context, digest->name );
471  return -ENOTSUP;
472  }
473  digestinfo_len = ( prefix->len + digest_len );
474 
475  /* Sanity check */
476  max_len = ( context->max_len - 11 );
477  if ( digestinfo_len > max_len ) {
478  DBGC ( context, "RSA %p %s digestInfo too long (%zd bytes, "
479  "max %zd)\n", context, digest->name, digestinfo_len,
480  max_len );
481  return -ERANGE;
482  }
483  DBGC ( context, "RSA %p encoding %s digest:\n",
484  context, digest->name );
485  DBGC_HDA ( context, 0, value, digest_len );
486 
487  /* Construct encoded message */
488  *(temp++) = 0x00;
489  *(temp++) = 0x01;
490  pad_len = ( max_len - digestinfo_len + 8 );
491  memset ( temp, 0xff, pad_len );
492  temp += pad_len;
493  *(temp++) = 0x00;
494  memcpy ( temp, prefix->data, prefix->len );
495  temp += prefix->len;
496  memcpy ( temp, value, digest_len );
497  temp += digest_len;
498  assert ( temp == ( encoded + context->max_len ) );
499  DBGC ( context, "RSA %p encoded %s digest:\n", context, digest->name );
500  DBGC_HDA ( context, 0, encoded, context->max_len );
501 
502  return 0;
503 }
504 
505 /**
506  * Sign digest value using RSA
507  *
508  * @v key Key
509  * @v digest Digest algorithm
510  * @v value Digest value
511  * @v signature Signature
512  * @ret rc Return status code
513  */
514 static int rsa_sign ( const struct asn1_cursor *key,
515  struct digest_algorithm *digest, const void *value,
516  struct asn1_builder *signature ) {
517  struct rsa_context context;
518  int rc;
519 
520  DBGC ( &context, "RSA %p signing %s digest:\n",
521  &context, digest->name );
522  DBGC_HDA ( &context, 0, value, digest->digestsize );
523 
524  /* Initialise context */
525  if ( ( rc = rsa_init ( &context, key ) ) != 0 )
526  goto err_init;
527 
528  /* Create space for encoded digest and signature */
529  if ( ( rc = asn1_grow ( signature, context.max_len ) ) != 0 )
530  goto err_grow;
531 
532  /* Encode digest */
533  if ( ( rc = rsa_encode_digest ( &context, digest, value,
534  signature->data ) ) != 0 )
535  goto err_encode;
536 
537  /* Encipher the encoded digest */
538  rsa_cipher ( &context, signature->data, signature->data );
539  DBGC ( &context, "RSA %p signed %s digest:\n", &context, digest->name );
540  DBGC_HDA ( &context, 0, signature->data, signature->len );
541 
542  /* Free context */
543  rsa_free ( &context );
544 
545  return 0;
546 
547  err_encode:
548  err_grow:
549  rsa_free ( &context );
550  err_init:
551  return rc;
552 }
553 
554 /**
555  * Verify signed digest value using RSA
556  *
557  * @v key Key
558  * @v digest Digest algorithm
559  * @v value Digest value
560  * @v signature Signature
561  * @ret rc Return status code
562  */
563 static int rsa_verify ( const struct asn1_cursor *key,
564  struct digest_algorithm *digest, const void *value,
565  const struct asn1_cursor *signature ) {
566  struct rsa_context context;
567  void *temp;
568  void *expected;
569  void *actual;
570  int rc;
571 
572  DBGC ( &context, "RSA %p verifying %s digest:\n",
573  &context, digest->name );
574  DBGC_HDA ( &context, 0, value, digest->digestsize );
575  DBGC_HDA ( &context, 0, signature->data, signature->len );
576 
577  /* Initialise context */
578  if ( ( rc = rsa_init ( &context, key ) ) != 0 )
579  goto err_init;
580 
581  /* Sanity check */
582  if ( signature->len != context.max_len ) {
583  DBGC ( &context, "RSA %p signature incorrect length (%zd "
584  "bytes, should be %zd)\n",
585  &context, signature->len, context.max_len );
586  rc = -ERANGE;
587  goto err_sanity;
588  }
589 
590  /* Decipher the signature (using the big integer input buffer
591  * as temporary storage)
592  */
593  temp = context.input0;
594  expected = temp;
595  rsa_cipher ( &context, signature->data, expected );
596  DBGC ( &context, "RSA %p deciphered signature:\n", &context );
597  DBGC_HDA ( &context, 0, expected, context.max_len );
598 
599  /* Encode digest (using the big integer output buffer as
600  * temporary storage)
601  */
602  temp = context.output0;
603  actual = temp;
604  if ( ( rc = rsa_encode_digest ( &context, digest, value,
605  actual ) ) != 0 )
606  goto err_encode;
607 
608  /* Verify the signature */
609  if ( memcmp ( actual, expected, context.max_len ) != 0 ) {
610  DBGC ( &context, "RSA %p signature verification failed\n",
611  &context );
612  rc = -EACCES_VERIFY;
613  goto err_verify;
614  }
615 
616  /* Free context */
617  rsa_free ( &context );
618 
619  DBGC ( &context, "RSA %p signature verified successfully\n", &context );
620  return 0;
621 
622  err_verify:
623  err_encode:
624  err_sanity:
625  rsa_free ( &context );
626  err_init:
627  return rc;
628 }
629 
630 /**
631  * Check for matching RSA public/private key pair
632  *
633  * @v private_key Private key
634  * @v public_key Public key
635  * @ret rc Return status code
636  */
637 static int rsa_match ( const struct asn1_cursor *private_key,
638  const struct asn1_cursor *public_key ) {
639  struct asn1_cursor private_modulus;
640  struct asn1_cursor private_exponent;
641  struct asn1_cursor public_modulus;
642  struct asn1_cursor public_exponent;
643  int rc;
644 
645  /* Parse moduli and exponents */
646  if ( ( rc = rsa_parse_mod_exp ( &private_modulus, &private_exponent,
647  private_key ) ) != 0 )
648  return rc;
649  if ( ( rc = rsa_parse_mod_exp ( &public_modulus, &public_exponent,
650  public_key ) ) != 0 )
651  return rc;
652 
653  /* Compare moduli */
654  if ( asn1_compare ( &private_modulus, &public_modulus ) != 0 )
655  return -ENOTTY;
656 
657  return 0;
658 }
659 
660 /** RSA public-key algorithm */
662  .name = "rsa",
663  .encrypt = rsa_encrypt,
664  .decrypt = rsa_decrypt,
665  .sign = rsa_sign,
666  .verify = rsa_verify,
667  .match = rsa_match,
668 };
669 
670 /* Drag in objects via rsa_algorithm */
672 
673 /* Drag in crypto configuration */
674 REQUIRE_OBJECT ( config_crypto );
static int rsa_encrypt(const struct asn1_cursor *key, const struct asn1_cursor *plaintext, struct asn1_builder *ciphertext)
Encrypt using RSA.
Definition: rsa.c:298
static int rsa_parse_mod_exp(struct asn1_cursor *modulus, struct asn1_cursor *exponent, const struct asn1_cursor *raw)
Parse RSA modulus and exponent.
Definition: rsa.c:149
#define __attribute__(x)
Definition: compiler.h:10
void * tmp
Temporary working space for modular exponentiation.
Definition: rsa.c:70
#define EINVAL
Invalid argument.
Definition: errno.h:429
int asn1_enter_unsigned(struct asn1_cursor *cursor)
Enter ASN.1 unsigned integer.
Definition: asn1.c:369
struct arbelprm_rc_send_wqe rc
Definition: arbel.h:14
bigint_element_t * output0
Output buffer.
Definition: rsa.c:68
static int rsa_verify(const struct asn1_cursor *key, struct digest_algorithm *digest, const void *value, const struct asn1_cursor *signature)
Verify signed digest value using RSA.
Definition: rsa.c:563
void * data
Data.
Definition: asn1.h:36
int asn1_compare(const struct asn1_cursor *cursor1, const struct asn1_cursor *cursor2)
Compare two ASN.1 objects.
Definition: asn1.c:458
#define bigint_mod_exp(base, modulus, exponent, result, tmp)
Perform modular exponentiation of big integers.
Definition: bigint.h:347
FILE_SECBOOT(PERMITTED)
__be32 in[4]
Definition: CIB_PRM.h:35
int asn1_enter(struct asn1_cursor *cursor, unsigned int type)
Enter ASN.1 object.
Definition: asn1.c:169
Error codes.
int asn1_enter_bits(struct asn1_cursor *cursor, unsigned int *unused)
Enter ASN.1 bit string.
Definition: asn1.c:311
uint16_t size
Buffer size.
Definition: dwmac.h:14
static int rsa_encode_digest(struct rsa_context *context, struct digest_algorithm *digest, const void *value, void *encoded)
Encode RSA digest.
Definition: rsa.c:456
const void * data
Start of data.
Definition: asn1.h:23
#define DBGC(...)
Definition: compiler.h:505
unsigned int exponent_size
Exponent size.
Definition: rsa.c:64
int get_random_nz(void *data, size_t len)
Get random non-zero bytes.
Definition: random_nz.c:63
Definition: bnxt_hsi.h:68
static void rsa_cipher(struct rsa_context *context, const void *in, void *out)
Perform RSA cipher operation.
Definition: rsa.c:272
#define bigint_init(value, data, len)
Initialise big integer.
Definition: bigint.h:62
char prefix[4]
Definition: vmconsole.c:53
FILE_LICENCE(GPL2_OR_LATER_OR_UBDL)
Cryptographic API.
static unsigned int asn1_type(const struct asn1_cursor *cursor)
Extract ASN.1 type.
Definition: asn1.h:479
static struct rsa_digestinfo_prefix * rsa_find_prefix(struct digest_algorithm *digest)
Identify RSA prefix.
Definition: rsa.c:80
REQUIRING_SYMBOL(rsa_algorithm)
int asn1_skip_any(struct asn1_cursor *cursor)
Skip ASN.1 object of any type.
Definition: asn1.c:290
__be32 out[4]
Definition: CIB_PRM.h:36
#define EACCES_VERIFY
Definition: rsa.c:46
Big integer support.
bigint_element_t * modulus0
Modulus.
Definition: rsa.c:56
#define ENOTSUP
Operation not supported.
Definition: errno.h:590
static int rsa_sign(const struct asn1_cursor *key, struct digest_algorithm *digest, const void *value, struct asn1_builder *signature)
Sign digest value using RSA.
Definition: rsa.c:514
void * memchr(const void *src, int character, size_t len)
Find character within a memory region.
Definition: string.c:136
size_t len
Length of data.
Definition: asn1.h:25
uint32_t start
Starting offset.
Definition: netvsc.h:12
unsigned long tmp
Definition: linux_pci.h:65
#define ENOMEM
Not enough space.
Definition: errno.h:535
HMAC_DRBG algorithm.
void * memcpy(void *dest, const void *src, size_t len) __nonnull
assert((readw(&hdr->flags) &(GTF_reading|GTF_writing))==0)
An RSA context.
Definition: rsa.c:52
ASN.1 encoding.
static int rsa_match(const struct asn1_cursor *private_key, const struct asn1_cursor *public_key)
Check for matching RSA public/private key pair.
Definition: rsa.c:637
pseudo_bit_t value[0x00020]
Definition: arbel.h:13
#define DBGC_HDA(...)
Definition: compiler.h:506
unsigned int size
Modulus size.
Definition: rsa.c:58
size_t max_len
Modulus length.
Definition: rsa.c:60
void * dynamic
Allocated memory.
Definition: rsa.c:54
uint32_t bigint_element_t
Element of a big integer.
Definition: bigint.h:16
bigint_element_t * input0
Input buffer.
Definition: rsa.c:66
ring len
Length.
Definition: dwmac.h:231
#define bigint_done(value, out, len)
Finalise big integer.
Definition: bigint.h:75
int asn1_grow(struct asn1_builder *builder, size_t extra)
Grow ASN.1 builder.
Definition: asn1.c:916
static void rsa_free(struct rsa_context *context)
Free RSA dynamic storage.
Definition: rsa.c:95
#define ERANGE
Result too large.
Definition: errno.h:640
char * strerror(int errno)
Retrieve string representation of error number.
Definition: strerror.c:79
static void(* free)(struct refcnt *refcnt))
Definition: refcnt.h:55
#define bigint_required_size(len)
Determine number of elements required for a big-integer type.
Definition: bigint.h:31
An ASN.1 object builder.
Definition: asn1.h:29
#define for_each_table_entry(pointer, table)
Iterate through all entries within a linker table.
Definition: tables.h:386
An RSA digestInfo prefix.
Definition: rsa.h:43
unsigned char uint8_t
Definition: stdint.h:10
static int rsa_decrypt(const struct asn1_cursor *key, const struct asn1_cursor *ciphertext, struct asn1_builder *plaintext)
Decrypt using RSA.
Definition: rsa.c:373
#define ASN1_SEQUENCE
ASN.1 sequence.
Definition: asn1.h:90
void * malloc(size_t size)
Allocate memory.
Definition: malloc.c:621
#define ASN1_INTEGER
ASN.1 integer.
Definition: asn1.h:63
bigint_element_t * exponent0
Exponent.
Definition: rsa.c:62
long pad_len
Definition: bigint.h:31
RSA public-key cryptography.
#define ENOTTY
Inappropriate I/O control operation.
Definition: errno.h:595
size_t digestsize
Digest size.
Definition: crypto.h:27
const char * name
Algorithm name.
Definition: crypto.h:21
int asn1_skip(struct asn1_cursor *cursor, unsigned int type)
Skip ASN.1 object.
Definition: asn1.c:231
struct pubkey_algorithm rsa_algorithm
RSA public-key algorithm.
Definition: rsa.c:661
int asn1_check_algorithm(const struct asn1_cursor *cursor, struct asn1_algorithm *expected, struct asn1_cursor *params)
Check ASN.1 OID-identified algorithm.
Definition: asn1.c:705
A message digest algorithm.
Definition: crypto.h:19
uint32_t end
Ending offset.
Definition: netvsc.h:18
A private key.
Definition: privkey.h:17
struct digest_algorithm * digest
Digest algorithm.
Definition: rsa.h:45
__be32 raw[7]
Definition: CIB_PRM.h:28
REQUIRE_OBJECT(config_crypto)
static int rsa_init(struct rsa_context *context, const struct asn1_cursor *key)
Initialise RSA cipher.
Definition: rsa.c:226
#define bigint_mod_exp_tmp_len(modulus)
Calculate temporary working space required for moduluar exponentiation.
Definition: bigint.h:361
#define ASN1_OCTET_STRING
ASN.1 octet string.
Definition: asn1.h:69
u8 signature
CPU signature.
Definition: CIB_PRM.h:35
int memcmp(const void *first, const void *second, size_t len)
Compare memory regions.
Definition: string.c:115
#define NULL
NULL pointer (VOID *)
Definition: Base.h:322
String functions.
An ASN.1 object cursor.
Definition: asn1.h:21
A public key algorithm.
Definition: crypto.h:122
static int rsa_alloc(struct rsa_context *context, size_t modulus_len, size_t exponent_len)
Allocate RSA dynamic storage.
Definition: rsa.c:108
union @391 key
Sense key.
Definition: scsi.h:18
const char * name
Algorithm name.
Definition: crypto.h:124
typedef bigint_t(X25519_SIZE) x25519_t
An X25519 unsigned big integer used in internal calculations.
void * memset(void *dest, int character, size_t len) __nonnull
#define RSA_DIGESTINFO_PREFIXES
RSA digestInfo prefix table.
Definition: rsa.h:53