x509.c File Reference

X.509 certificates. More...

#include <stdlib.h>
#include <string.h>
#include <errno.h>
#include <gpxe/asn1.h>
#include <gpxe/x509.h>

Go to the source code of this file.

Functions

 FILE_LICENCE (GPL2_OR_LATER)
static int x509_public_key (const struct asn1_cursor *certificate, struct asn1_cursor *algorithm, struct asn1_cursor *pubkey)
 Identify X.509 certificate public key.
int x509_rsa_public_key (const struct asn1_cursor *certificate, struct x509_rsa_public_key *rsa_pubkey)
 Identify X.509 certificate RSA modulus and public exponent.

Variables

static const uint8_t oid_rsa_encryption []
 Object Identifier for "rsaEncryption" (1.2.840.113549.1.1.1).


Detailed Description

X.509 certificates.

The structure of X.509v3 certificates is concisely documented in RFC5280 section 4.1. The structure of RSA public keys is documented in RFC2313.

Definition in file x509.c.


Function Documentation

FILE_LICENCE ( GPL2_OR_LATER   ) 

static int x509_public_key ( const struct asn1_cursor certificate,
struct asn1_cursor algorithm,
struct asn1_cursor pubkey 
) [static]

Identify X.509 certificate public key.

Parameters:
certificate Certificate
algorithm Public key algorithm to fill in
pubkey Public key value to fill in
Return values:
rc Return status code

Definition at line 48 of file x509.c.

References ASN1_BIT_STRING, asn1_enter(), ASN1_EXPLICIT_TAG, ASN1_INTEGER, ASN1_SEQUENCE, asn1_skip(), asn1_cursor::data, DBG, DBG_HDA, asn1_cursor::len, and memcpy.

Referenced by x509_rsa_public_key().

00050                                                           {
00051         struct asn1_cursor cursor;
00052         int rc;
00053 
00054         /* Locate subjectPublicKeyInfo */
00055         memcpy ( &cursor, certificate, sizeof ( cursor ) );
00056         rc = ( asn1_enter ( &cursor, ASN1_SEQUENCE ), /* Certificate */
00057                asn1_enter ( &cursor, ASN1_SEQUENCE ), /* tbsCertificate */
00058                asn1_skip ( &cursor, ASN1_EXPLICIT_TAG ), /* version */
00059                asn1_skip ( &cursor, ASN1_INTEGER ), /* serialNumber */
00060                asn1_skip ( &cursor, ASN1_SEQUENCE ), /* signature */
00061                asn1_skip ( &cursor, ASN1_SEQUENCE ), /* issuer */
00062                asn1_skip ( &cursor, ASN1_SEQUENCE ), /* validity */
00063                asn1_skip ( &cursor, ASN1_SEQUENCE ), /* name */
00064                asn1_enter ( &cursor, ASN1_SEQUENCE )/* subjectPublicKeyInfo*/);
00065         if ( rc != 0 ) {
00066                 DBG ( "Cannot locate subjectPublicKeyInfo in:\n" );
00067                 DBG_HDA ( 0, certificate->data, certificate->len );
00068                 return rc;
00069         }
00070 
00071         /* Locate algorithm */
00072         memcpy ( algorithm, &cursor, sizeof ( *algorithm ) );
00073         rc = ( asn1_enter ( algorithm, ASN1_SEQUENCE ) /* algorithm */ );
00074         if ( rc != 0 ) {
00075                 DBG ( "Cannot locate algorithm in:\n" );
00076                 DBG_HDA ( 0, certificate->data, certificate->len );
00077                 return rc;
00078         }
00079 
00080         /* Locate subjectPublicKey */
00081         memcpy ( pubkey, &cursor, sizeof ( *pubkey ) );
00082         rc = ( asn1_skip ( pubkey, ASN1_SEQUENCE ), /* algorithm */
00083                asn1_enter ( pubkey, ASN1_BIT_STRING ) /* subjectPublicKey*/ );
00084         if ( rc != 0 ) {
00085                 DBG ( "Cannot locate subjectPublicKey in:\n" );
00086                 DBG_HDA ( 0, certificate->data, certificate->len );
00087                 return rc;
00088         }
00089 
00090         return 0;
00091 }

int x509_rsa_public_key ( const struct asn1_cursor certificate,
struct x509_rsa_public_key rsa_pubkey 
)

Identify X.509 certificate RSA modulus and public exponent.

Parameters:
certificate Certificate
rsa RSA public key to fill in
Return values:
rc Return status code
The caller is responsible for eventually calling x509_free_rsa_public_key() to free the storage allocated to hold the RSA modulus and exponent.

Definition at line 104 of file x509.c.

References asn1_enter(), ASN1_INTEGER, ASN1_OID, ASN1_SEQUENCE, asn1_skip(), asn1_cursor::data, DBG, DBG2, DBG2_HDA, DBG_HDA, ENOMEM, ENOTSUP, x509_rsa_public_key::exponent, x509_rsa_public_key::exponent_len, asn1_cursor::len, malloc(), memcmp(), memcpy, x509_rsa_public_key::modulus, x509_rsa_public_key::modulus_len, oid_rsa_encryption, and x509_public_key().

00105                                                                    {
00106         struct asn1_cursor algorithm;
00107         struct asn1_cursor pubkey;
00108         struct asn1_cursor modulus;
00109         struct asn1_cursor exponent;
00110         int rc;
00111 
00112         /* First, extract the public key algorithm and key data */
00113         if ( ( rc = x509_public_key ( certificate, &algorithm,
00114                                       &pubkey ) ) != 0 )
00115                 return rc;
00116 
00117         /* Check that algorithm is RSA */
00118         rc = ( asn1_enter ( &algorithm, ASN1_OID ) /* algorithm */ );
00119         if ( rc != 0 ) {
00120                 DBG ( "Cannot locate algorithm:\n" );
00121                 DBG_HDA ( 0, certificate->data, certificate->len );
00122         return rc;
00123         }
00124         if ( ( algorithm.len != sizeof ( oid_rsa_encryption ) ) ||
00125              ( memcmp ( algorithm.data, &oid_rsa_encryption,
00126                         sizeof ( oid_rsa_encryption ) ) != 0 ) ) {
00127                 DBG ( "algorithm is not rsaEncryption in:\n" );
00128                 DBG_HDA ( 0, certificate->data, certificate->len );
00129                 return -ENOTSUP;
00130         }
00131 
00132         /* Check that public key is a byte string, i.e. that the
00133          * "unused bits" byte contains zero.
00134          */
00135         if ( ( pubkey.len < 1 ) ||
00136              ( ( *( uint8_t * ) pubkey.data ) != 0 ) ) {
00137                 DBG ( "subjectPublicKey is not a byte string in:\n" );
00138                 DBG_HDA ( 0, certificate->data, certificate->len );
00139                 return -ENOTSUP;
00140         }
00141         pubkey.data++;
00142         pubkey.len--;
00143 
00144         /* Pick out the modulus and exponent */
00145         rc = ( asn1_enter ( &pubkey, ASN1_SEQUENCE ) /* RSAPublicKey */ );
00146         if ( rc != 0 ) {
00147                 DBG ( "Cannot locate RSAPublicKey in:\n" );
00148                 DBG_HDA ( 0, certificate->data, certificate->len );
00149                 return -ENOTSUP;
00150         }
00151         memcpy ( &modulus, &pubkey, sizeof ( modulus ) );
00152         rc = ( asn1_enter ( &modulus, ASN1_INTEGER ) /* modulus */ );
00153         if ( rc != 0 ) {
00154                 DBG ( "Cannot locate modulus in:\n" );
00155                 DBG_HDA ( 0, certificate->data, certificate->len );
00156                 return -ENOTSUP;
00157         }
00158         memcpy ( &exponent, &pubkey, sizeof ( exponent ) );
00159         rc = ( asn1_skip ( &exponent, ASN1_INTEGER ), /* modulus */
00160                asn1_enter ( &exponent, ASN1_INTEGER ) /* publicExponent */ );
00161         if ( rc != 0 ) {
00162                 DBG ( "Cannot locate publicExponent in:\n" );
00163                 DBG_HDA ( 0, certificate->data, certificate->len );
00164                 return -ENOTSUP;
00165         }
00166 
00167         /* Allocate space and copy out modulus and exponent */
00168         rsa_pubkey->modulus = malloc ( modulus.len + exponent.len );
00169         if ( ! rsa_pubkey->modulus )
00170                 return -ENOMEM;
00171         rsa_pubkey->exponent = ( rsa_pubkey->modulus + modulus.len );
00172         memcpy ( rsa_pubkey->modulus, modulus.data, modulus.len );
00173         rsa_pubkey->modulus_len = modulus.len;
00174         memcpy ( rsa_pubkey->exponent, exponent.data, exponent.len );
00175         rsa_pubkey->exponent_len = exponent.len;
00176 
00177         DBG2 ( "RSA modulus:\n" );
00178         DBG2_HDA ( 0, rsa_pubkey->modulus, rsa_pubkey->modulus_len );
00179         DBG2 ( "RSA exponent:\n" );
00180         DBG2_HDA ( 0, rsa_pubkey->exponent, rsa_pubkey->exponent_len );
00181 
00182         return 0;
00183 }


Variable Documentation

const uint8_t oid_rsa_encryption[] [static]

Initial value:

 { 0x2a, 0x86, 0x48, 0x86, 0xf7,
                                              0x0d, 0x01, 0x01, 0x01 }
Object Identifier for "rsaEncryption" (1.2.840.113549.1.1.1).

Definition at line 37 of file x509.c.

Referenced by x509_rsa_public_key().


Generated on Tue Apr 6 20:01:15 2010 for gPXE by  doxygen 1.5.7.1