|
@@ -58,6 +58,18 @@ FILE_LICENCE ( GPL2_OR_LATER );
|
58
|
58
|
__einfo_error ( EINFO_EINVAL_ASN1_TIME )
|
59
|
59
|
#define EINFO_EINVAL_ASN1_TIME \
|
60
|
60
|
__einfo_uniqify ( EINFO_EINVAL, 0x05, "Invalid time" )
|
|
61
|
+#define EINVAL_ASN1_ALGORITHM \
|
|
62
|
+ __einfo_error ( EINFO_EINVAL_ASN1_ALGORITHM )
|
|
63
|
+#define EINFO_EINVAL_ASN1_ALGORITHM \
|
|
64
|
+ __einfo_uniqify ( EINFO_EINVAL, 0x06, "Invalid algorithm" )
|
|
65
|
+#define ENOTSUP_ALGORITHM \
|
|
66
|
+ __einfo_error ( EINFO_ENOTSUP_ALGORITHM )
|
|
67
|
+#define EINFO_ENOTSUP_ALGORITHM \
|
|
68
|
+ __einfo_uniqify ( EINFO_ENOTSUP, 0x01, "Unsupported algorithm" )
|
|
69
|
+#define ENOTTY_ALGORITHM \
|
|
70
|
+ __einfo_error ( EINFO_ENOTTY_ALGORITHM )
|
|
71
|
+#define EINFO_ENOTTY_ALGORITHM \
|
|
72
|
+ __einfo_uniqify ( EINFO_ENOTTY, 0x01, "Inappropriate algorithm" )
|
61
|
73
|
|
62
|
74
|
/**
|
63
|
75
|
* Invalidate ASN.1 object cursor
|
|
@@ -377,11 +389,12 @@ asn1_find_algorithm ( const struct asn1_cursor *cursor ) {
|
377
|
389
|
* Parse ASN.1 OID-identified algorithm
|
378
|
390
|
*
|
379
|
391
|
* @v cursor ASN.1 object cursor
|
380
|
|
- * @ret algorithm Algorithm, or NULL
|
|
392
|
+ * @ret algorithm Algorithm
|
|
393
|
+ * @ret rc Return status code
|
381
|
394
|
*/
|
382
|
|
-struct asn1_algorithm * asn1_algorithm ( const struct asn1_cursor *cursor ) {
|
|
395
|
+int asn1_algorithm ( const struct asn1_cursor *cursor,
|
|
396
|
+ struct asn1_algorithm **algorithm ) {
|
383
|
397
|
struct asn1_cursor contents;
|
384
|
|
- struct asn1_algorithm *algorithm;
|
385
|
398
|
int rc;
|
386
|
399
|
|
387
|
400
|
/* Enter signatureAlgorithm */
|
|
@@ -393,18 +406,104 @@ struct asn1_algorithm * asn1_algorithm ( const struct asn1_cursor *cursor ) {
|
393
|
406
|
DBGC ( cursor, "ASN1 %p cannot locate algorithm OID:\n",
|
394
|
407
|
cursor );
|
395
|
408
|
DBGC_HDA ( cursor, 0, cursor->data, cursor->len );
|
396
|
|
- return NULL;
|
|
409
|
+ return -EINVAL_ASN1_ALGORITHM;
|
397
|
410
|
}
|
398
|
411
|
|
399
|
412
|
/* Identify algorithm */
|
400
|
|
- algorithm = asn1_find_algorithm ( &contents );
|
401
|
|
- if ( ! algorithm ) {
|
|
413
|
+ *algorithm = asn1_find_algorithm ( &contents );
|
|
414
|
+ if ( ! *algorithm ) {
|
402
|
415
|
DBGC ( cursor, "ASN1 %p unrecognised algorithm:\n", cursor );
|
403
|
416
|
DBGC_HDA ( cursor, 0, cursor->data, cursor->len );
|
404
|
|
- return NULL;
|
|
417
|
+ return -ENOTSUP_ALGORITHM;
|
|
418
|
+ }
|
|
419
|
+
|
|
420
|
+ return 0;
|
|
421
|
+}
|
|
422
|
+
|
|
423
|
+/**
|
|
424
|
+ * Parse ASN.1 OID-identified public-key algorithm
|
|
425
|
+ *
|
|
426
|
+ * @v cursor ASN.1 object cursor
|
|
427
|
+ * @ret algorithm Algorithm
|
|
428
|
+ * @ret rc Return status code
|
|
429
|
+ */
|
|
430
|
+int asn1_pubkey_algorithm ( const struct asn1_cursor *cursor,
|
|
431
|
+ struct asn1_algorithm **algorithm ) {
|
|
432
|
+ int rc;
|
|
433
|
+
|
|
434
|
+ /* Parse algorithm */
|
|
435
|
+ if ( ( rc = asn1_algorithm ( cursor, algorithm ) ) != 0 )
|
|
436
|
+ return rc;
|
|
437
|
+
|
|
438
|
+ /* Check algorithm has a public key */
|
|
439
|
+ if ( ! (*algorithm)->pubkey ) {
|
|
440
|
+ DBGC ( cursor, "ASN1 %p algorithm %s is not a public-key "
|
|
441
|
+ "algorithm:\n", cursor, (*algorithm)->name );
|
|
442
|
+ DBGC_HDA ( cursor, 0, cursor->data, cursor->len );
|
|
443
|
+ return -ENOTTY_ALGORITHM;
|
|
444
|
+ }
|
|
445
|
+
|
|
446
|
+ return 0;
|
|
447
|
+}
|
|
448
|
+
|
|
449
|
+/**
|
|
450
|
+ * Parse ASN.1 OID-identified digest algorithm
|
|
451
|
+ *
|
|
452
|
+ * @v cursor ASN.1 object cursor
|
|
453
|
+ * @ret algorithm Algorithm
|
|
454
|
+ * @ret rc Return status code
|
|
455
|
+ */
|
|
456
|
+int asn1_digest_algorithm ( const struct asn1_cursor *cursor,
|
|
457
|
+ struct asn1_algorithm **algorithm ) {
|
|
458
|
+ int rc;
|
|
459
|
+
|
|
460
|
+ /* Parse algorithm */
|
|
461
|
+ if ( ( rc = asn1_algorithm ( cursor, algorithm ) ) != 0 )
|
|
462
|
+ return rc;
|
|
463
|
+
|
|
464
|
+ /* Check algorithm has a digest */
|
|
465
|
+ if ( ! (*algorithm)->digest ) {
|
|
466
|
+ DBGC ( cursor, "ASN1 %p algorithm %s is not a digest "
|
|
467
|
+ "algorithm:\n", cursor, (*algorithm)->name );
|
|
468
|
+ DBGC_HDA ( cursor, 0, cursor->data, cursor->len );
|
|
469
|
+ return -ENOTTY_ALGORITHM;
|
|
470
|
+ }
|
|
471
|
+
|
|
472
|
+ return 0;
|
|
473
|
+}
|
|
474
|
+
|
|
475
|
+/**
|
|
476
|
+ * Parse ASN.1 OID-identified signature algorithm
|
|
477
|
+ *
|
|
478
|
+ * @v cursor ASN.1 object cursor
|
|
479
|
+ * @ret algorithm Algorithm
|
|
480
|
+ * @ret rc Return status code
|
|
481
|
+ */
|
|
482
|
+int asn1_signature_algorithm ( const struct asn1_cursor *cursor,
|
|
483
|
+ struct asn1_algorithm **algorithm ) {
|
|
484
|
+ int rc;
|
|
485
|
+
|
|
486
|
+ /* Parse algorithm */
|
|
487
|
+ if ( ( rc = asn1_algorithm ( cursor, algorithm ) ) != 0 )
|
|
488
|
+ return rc;
|
|
489
|
+
|
|
490
|
+ /* Check algorithm has a public key */
|
|
491
|
+ if ( ! (*algorithm)->pubkey ) {
|
|
492
|
+ DBGC ( cursor, "ASN1 %p algorithm %s is not a signature "
|
|
493
|
+ "algorithm:\n", cursor, (*algorithm)->name );
|
|
494
|
+ DBGC_HDA ( cursor, 0, cursor->data, cursor->len );
|
|
495
|
+ return -ENOTTY_ALGORITHM;
|
|
496
|
+ }
|
|
497
|
+
|
|
498
|
+ /* Check algorithm has a digest */
|
|
499
|
+ if ( ! (*algorithm)->digest ) {
|
|
500
|
+ DBGC ( cursor, "ASN1 %p algorithm %s is not a signature "
|
|
501
|
+ "algorithm:\n", cursor, (*algorithm)->name );
|
|
502
|
+ DBGC_HDA ( cursor, 0, cursor->data, cursor->len );
|
|
503
|
+ return -ENOTTY_ALGORITHM;
|
405
|
504
|
}
|
406
|
505
|
|
407
|
|
- return algorithm;
|
|
506
|
+ return 0;
|
408
|
507
|
}
|
409
|
508
|
|
410
|
509
|
/**
|