mirror of
https://github.com/ipxe/ipxe
synced 2025-12-06 17:30:26 +03:00
[crypto] Allow for OID-identified elliptic curve algorithms
Elliptic curves in X.509 certificates are identified via the id-ecPublicKey object identifier (1.2.840.10045.2.1), with the specific elliptic curve identified via a second OID in the algorithm parameters. Signed-off-by: Michael Brown <mcb30@ipxe.org>
This commit is contained in:
@@ -83,6 +83,19 @@ FILE_LICENCE ( GPL2_OR_LATER_OR_UBDL );
|
||||
#define EINFO_ENOTTY_ALGORITHM \
|
||||
__einfo_uniqify ( EINFO_ENOTTY, 0x01, "Inappropriate algorithm" )
|
||||
|
||||
/** "ecPublicKey" object identifier */
|
||||
static uint8_t oid_ecpublickey[] = { ASN1_OID_ECPUBLICKEY };
|
||||
|
||||
/** Generic elliptic curve container algorithm
|
||||
*
|
||||
* The actual curve to be used is identified via the algorithm
|
||||
* parameters, rather than the top-level OID.
|
||||
*/
|
||||
struct asn1_algorithm ecpubkey_algorithm __asn1_algorithm = {
|
||||
.name = "ecPublicKey",
|
||||
.oid = ASN1_CURSOR ( oid_ecpublickey ),
|
||||
};
|
||||
|
||||
/**
|
||||
* Start parsing ASN.1 object
|
||||
*
|
||||
@@ -624,20 +637,66 @@ int asn1_signature_algorithm ( const struct asn1_cursor *cursor,
|
||||
return 0;
|
||||
}
|
||||
|
||||
/**
|
||||
* Parse ASN.1 OID-identified elliptic curve algorithm
|
||||
*
|
||||
* @v cursor ASN.1 object cursor
|
||||
* @ret algorithm Algorithm
|
||||
* @ret rc Return status code
|
||||
*/
|
||||
int asn1_curve_algorithm ( const struct asn1_cursor *cursor,
|
||||
struct asn1_algorithm **algorithm ) {
|
||||
struct asn1_cursor curve;
|
||||
|
||||
/* Elliptic curves are identified as either:
|
||||
*
|
||||
* - the algorithm "id-ecPublicKey" with the actual curve
|
||||
* specified in the algorithm parameters, or
|
||||
*
|
||||
* - a standalone object identifier for the curve
|
||||
*/
|
||||
if ( asn1_check_algorithm ( cursor, &ecpubkey_algorithm,
|
||||
&curve ) != 0 ) {
|
||||
memcpy ( &curve, cursor, sizeof ( curve ) );
|
||||
}
|
||||
|
||||
/* Identify curve */
|
||||
asn1_enter ( &curve, ASN1_OID );
|
||||
*algorithm = asn1_find_algorithm ( &curve );
|
||||
if ( ! *algorithm ) {
|
||||
DBGC ( cursor, "ASN1 %p unrecognised EC algorithm:\n",
|
||||
cursor );
|
||||
DBGC_HDA ( cursor, 0, cursor->data, cursor->len );
|
||||
return -ENOTSUP_ALGORITHM;
|
||||
}
|
||||
|
||||
/* Check algorithm has an elliptic curve */
|
||||
if ( ! (*algorithm)->curve ) {
|
||||
DBGC ( cursor, "ASN1 %p algorithm %s is not an elliptic curve "
|
||||
"algorithm:\n", cursor, (*algorithm)->name );
|
||||
DBGC_HDA ( cursor, 0, cursor->data, cursor->len );
|
||||
return -ENOTTY_ALGORITHM;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/**
|
||||
* Check ASN.1 OID-identified algorithm
|
||||
*
|
||||
* @v cursor ASN.1 object cursor
|
||||
* @v expected Expected algorithm
|
||||
* @ret params Algorithm parameters, or NULL
|
||||
* @ret rc Return status code
|
||||
*/
|
||||
int asn1_check_algorithm ( const struct asn1_cursor *cursor,
|
||||
struct asn1_algorithm *expected ) {
|
||||
struct asn1_algorithm *expected,
|
||||
struct asn1_cursor *params ) {
|
||||
struct asn1_algorithm *actual;
|
||||
int rc;
|
||||
|
||||
/* Parse algorithm */
|
||||
if ( ( rc = asn1_algorithm ( cursor, &actual, NULL ) ) != 0 )
|
||||
if ( ( rc = asn1_algorithm ( cursor, &actual, params ) ) != 0 )
|
||||
return rc;
|
||||
|
||||
/* Check algorithm matches */
|
||||
|
||||
@@ -194,8 +194,8 @@ static int rsa_parse_mod_exp ( struct asn1_cursor *modulus,
|
||||
asn1_skip_any ( &cursor );
|
||||
|
||||
/* Enter privateKey, if present */
|
||||
if ( asn1_check_algorithm ( &cursor,
|
||||
&rsa_encryption_algorithm ) == 0 ) {
|
||||
if ( asn1_check_algorithm ( &cursor, &rsa_encryption_algorithm,
|
||||
NULL ) == 0 ) {
|
||||
|
||||
/* Skip privateKeyAlgorithm */
|
||||
asn1_skip_any ( &cursor );
|
||||
|
||||
@@ -127,9 +127,15 @@ struct asn1_builder_header {
|
||||
#define ASN1_OID_TRIPLE( value ) \
|
||||
( 0x80 | ( ( (value) >> 14 ) & 0x7f ) ), ASN1_OID_DOUBLE ( (value) )
|
||||
|
||||
/** ASN.1 OID for ecPublicKey (1.2.840.10045.2.1) */
|
||||
#define ASN1_OID_ECPUBLICKEY \
|
||||
ASN1_OID_INITIAL ( 1, 2 ), ASN1_OID_DOUBLE ( 840 ), \
|
||||
ASN1_OID_DOUBLE ( 10045 ), ASN1_OID_SINGLE ( 2 ), \
|
||||
ASN1_OID_SINGLE ( 1 )
|
||||
|
||||
/** ASN.1 OID for prime256v1 (1.2.840.10045.3.1.7) */
|
||||
#define ASN1_OID_PRIME256V1 \
|
||||
ASN1_OID_INITIAL ( 1, 1 ), ASN1_OID_DOUBLE ( 840 ), \
|
||||
ASN1_OID_INITIAL ( 1, 2 ), ASN1_OID_DOUBLE ( 840 ), \
|
||||
ASN1_OID_DOUBLE ( 10045 ), ASN1_OID_SINGLE ( 3 ), \
|
||||
ASN1_OID_SINGLE ( 1 ), ASN1_OID_SINGLE ( 7 )
|
||||
|
||||
@@ -426,6 +432,7 @@ extern struct asn1_algorithm oid_sha512_algorithm __asn1_algorithm;
|
||||
extern struct asn1_algorithm oid_sha224_algorithm __asn1_algorithm;
|
||||
extern struct asn1_algorithm oid_sha512_224_algorithm __asn1_algorithm;
|
||||
extern struct asn1_algorithm oid_sha512_256_algorithm __asn1_algorithm;
|
||||
extern struct asn1_algorithm ecpubkey_algorithm __asn1_algorithm;
|
||||
|
||||
/**
|
||||
* Invalidate ASN.1 object cursor
|
||||
@@ -497,8 +504,11 @@ extern int asn1_cipher_algorithm ( const struct asn1_cursor *cursor,
|
||||
struct asn1_cursor *params );
|
||||
extern int asn1_signature_algorithm ( const struct asn1_cursor *cursor,
|
||||
struct asn1_algorithm **algorithm );
|
||||
extern int asn1_curve_algorithm ( const struct asn1_cursor *cursor,
|
||||
struct asn1_algorithm **algorithm );
|
||||
extern int asn1_check_algorithm ( const struct asn1_cursor *cursor,
|
||||
struct asn1_algorithm *expected );
|
||||
struct asn1_algorithm *expected,
|
||||
struct asn1_cursor *params );
|
||||
extern int asn1_parse_cbc ( struct asn1_algorithm *algorithm,
|
||||
struct asn1_cursor *params );
|
||||
extern int asn1_parse_gcm ( struct asn1_algorithm *algorithm,
|
||||
|
||||
Reference in New Issue
Block a user