iPXE
Macros | Functions | Variables
x509.c File Reference

X.509 certificates. More...

#include <stdlib.h>
#include <string.h>
#include <errno.h>
#include <assert.h>
#include <ipxe/list.h>
#include <ipxe/base16.h>
#include <ipxe/asn1.h>
#include <ipxe/crypto.h>
#include <ipxe/md5.h>
#include <ipxe/sha1.h>
#include <ipxe/sha256.h>
#include <ipxe/rsa.h>
#include <ipxe/rootcert.h>
#include <ipxe/certstore.h>
#include <ipxe/socket.h>
#include <ipxe/in.h>
#include <ipxe/image.h>
#include <ipxe/ocsp.h>
#include <ipxe/x509.h>
#include <config/crypto.h>

Go to the source code of this file.

Macros

#define ENOTSUP_ALGORITHM   __einfo_error ( EINFO_ENOTSUP_ALGORITHM )
 
#define EINFO_ENOTSUP_ALGORITHM   __einfo_uniqify ( EINFO_ENOTSUP, 0x01, "Unsupported algorithm" )
 
#define ENOTSUP_EXTENSION   __einfo_error ( EINFO_ENOTSUP_EXTENSION )
 
#define EINFO_ENOTSUP_EXTENSION   __einfo_uniqify ( EINFO_ENOTSUP, 0x02, "Unsupported extension" )
 
#define EINVAL_ALGORITHM   __einfo_error ( EINFO_EINVAL_ALGORITHM )
 
#define EINFO_EINVAL_ALGORITHM   __einfo_uniqify ( EINFO_EINVAL, 0x01, "Invalid algorithm type" )
 
#define EINVAL_ALGORITHM_MISMATCH   __einfo_error ( EINFO_EINVAL_ALGORITHM_MISMATCH )
 
#define EINFO_EINVAL_ALGORITHM_MISMATCH   __einfo_uniqify ( EINFO_EINVAL, 0x04, "Signature algorithm mismatch" )
 
#define EINVAL_PATH_LEN   __einfo_error ( EINFO_EINVAL_PATH_LEN )
 
#define EINFO_EINVAL_PATH_LEN   __einfo_uniqify ( EINFO_EINVAL, 0x05, "Invalid pathLenConstraint" )
 
#define EINVAL_VERSION   __einfo_error ( EINFO_EINVAL_VERSION )
 
#define EINFO_EINVAL_VERSION   __einfo_uniqify ( EINFO_EINVAL, 0x06, "Invalid version" )
 
#define EACCES_WRONG_ISSUER   __einfo_error ( EINFO_EACCES_WRONG_ISSUER )
 
#define EINFO_EACCES_WRONG_ISSUER   __einfo_uniqify ( EINFO_EACCES, 0x01, "Wrong issuer" )
 
#define EACCES_NOT_CA   __einfo_error ( EINFO_EACCES_NOT_CA )
 
#define EINFO_EACCES_NOT_CA   __einfo_uniqify ( EINFO_EACCES, 0x02, "Not a CA certificate" )
 
#define EACCES_KEY_USAGE   __einfo_error ( EINFO_EACCES_KEY_USAGE )
 
#define EINFO_EACCES_KEY_USAGE   __einfo_uniqify ( EINFO_EACCES, 0x03, "Incorrect key usage" )
 
#define EACCES_EXPIRED   __einfo_error ( EINFO_EACCES_EXPIRED )
 
#define EINFO_EACCES_EXPIRED   __einfo_uniqify ( EINFO_EACCES, 0x04, "Expired (or not yet valid)" )
 
#define EACCES_PATH_LEN   __einfo_error ( EINFO_EACCES_PATH_LEN )
 
#define EINFO_EACCES_PATH_LEN   __einfo_uniqify ( EINFO_EACCES, 0x05, "Maximum path length exceeded" )
 
#define EACCES_UNTRUSTED   __einfo_error ( EINFO_EACCES_UNTRUSTED )
 
#define EINFO_EACCES_UNTRUSTED   __einfo_uniqify ( EINFO_EACCES, 0x06, "Untrusted root certificate" )
 
#define EACCES_OUT_OF_ORDER   __einfo_error ( EINFO_EACCES_OUT_OF_ORDER )
 
#define EINFO_EACCES_OUT_OF_ORDER   __einfo_uniqify ( EINFO_EACCES, 0x07, "Validation out of order" )
 
#define EACCES_EMPTY   __einfo_error ( EINFO_EACCES_EMPTY )
 
#define EINFO_EACCES_EMPTY   __einfo_uniqify ( EINFO_EACCES, 0x08, "Empty certificate chain" )
 
#define EACCES_OCSP_REQUIRED   __einfo_error ( EINFO_EACCES_OCSP_REQUIRED )
 
#define EINFO_EACCES_OCSP_REQUIRED   __einfo_uniqify ( EINFO_EACCES, 0x09, "OCSP check required" )
 
#define EACCES_WRONG_NAME   __einfo_error ( EINFO_EACCES_WRONG_NAME )
 
#define EINFO_EACCES_WRONG_NAME   __einfo_uniqify ( EINFO_EACCES, 0x0a, "Incorrect certificate name" )
 
#define EACCES_USELESS   __einfo_error ( EINFO_EACCES_USELESS )
 
#define EINFO_EACCES_USELESS   __einfo_uniqify ( EINFO_EACCES, 0x0b, "No usable certificates" )
 

Functions

 FILE_LICENCE (GPL2_OR_LATER_OR_UBDL)
 
const char * x509_name (struct x509_certificate *cert)
 Get X.509 certificate display name. More...
 
static int x509_parse_version (struct x509_certificate *cert, const struct asn1_cursor *raw)
 Parse X.509 certificate version. More...
 
static int x509_parse_serial (struct x509_certificate *cert, const struct asn1_cursor *raw)
 Parse X.509 certificate serial number. More...
 
static int x509_parse_issuer (struct x509_certificate *cert, const struct asn1_cursor *raw)
 Parse X.509 certificate issuer. More...
 
static int x509_parse_validity (struct x509_certificate *cert, const struct asn1_cursor *raw)
 Parse X.509 certificate validity. More...
 
static int x509_parse_common_name (struct x509_certificate *cert, const struct asn1_cursor *raw)
 Parse X.509 certificate common name. More...
 
static int x509_parse_subject (struct x509_certificate *cert, const struct asn1_cursor *raw)
 Parse X.509 certificate subject. More...
 
static int x509_parse_public_key (struct x509_certificate *cert, const struct asn1_cursor *raw)
 Parse X.509 certificate public key information. More...
 
static int x509_parse_basic_constraints (struct x509_certificate *cert, const struct asn1_cursor *raw)
 Parse X.509 certificate basic constraints. More...
 
static int x509_parse_key_usage (struct x509_certificate *cert, const struct asn1_cursor *raw)
 Parse X.509 certificate key usage. More...
 
static int x509_parse_key_purpose (struct x509_certificate *cert, const struct asn1_cursor *raw)
 Parse X.509 certificate key purpose identifier. More...
 
static int x509_parse_extended_key_usage (struct x509_certificate *cert, const struct asn1_cursor *raw)
 Parse X.509 certificate extended key usage. More...
 
static int x509_parse_ocsp (struct x509_certificate *cert, const struct asn1_cursor *raw)
 Parse X.509 certificate OCSP access method. More...
 
static struct x509_access_methodx509_find_access_method (const struct asn1_cursor *oid)
 Identify X.509 access method by OID. More...
 
static int x509_parse_access_description (struct x509_certificate *cert, const struct asn1_cursor *raw)
 Parse X.509 certificate access description. More...
 
static int x509_parse_authority_info_access (struct x509_certificate *cert, const struct asn1_cursor *raw)
 Parse X.509 certificate authority information access. More...
 
static int x509_parse_subject_alt_name (struct x509_certificate *cert, const struct asn1_cursor *raw)
 Parse X.509 certificate subject alternative name. More...
 
static struct x509_extensionx509_find_extension (const struct asn1_cursor *oid)
 Identify X.509 extension by OID. More...
 
static int x509_parse_extension (struct x509_certificate *cert, const struct asn1_cursor *raw)
 Parse X.509 certificate extension. More...
 
static int x509_parse_extensions (struct x509_certificate *cert, const struct asn1_cursor *raw)
 Parse X.509 certificate extensions, if present. More...
 
static int x509_parse_tbscertificate (struct x509_certificate *cert, const struct asn1_cursor *raw)
 Parse X.509 certificate tbsCertificate. More...
 
int x509_parse (struct x509_certificate *cert, const struct asn1_cursor *raw)
 Parse X.509 certificate from ASN.1 data. More...
 
int x509_certificate (const void *data, size_t len, struct x509_certificate **cert)
 Create X.509 certificate. More...
 
static int x509_check_signature (struct x509_certificate *cert, struct x509_public_key *public_key)
 Check X.509 certificate signature. More...
 
int x509_check_issuer (struct x509_certificate *cert, struct x509_certificate *issuer)
 Check X.509 certificate against issuer certificate. More...
 
void x509_fingerprint (struct x509_certificate *cert, struct digest_algorithm *digest, void *fingerprint)
 Calculate X.509 certificate fingerprint. More...
 
int x509_check_root (struct x509_certificate *cert, struct x509_root *root)
 Check X.509 root certificate. More...
 
int x509_check_time (struct x509_certificate *cert, time_t time)
 Check X.509 certificate validity period. More...
 
int x509_validate (struct x509_certificate *cert, struct x509_certificate *issuer, time_t time, struct x509_root *root)
 Validate X.509 certificate. More...
 
static int x509_check_dnsname (struct x509_certificate *cert, const struct asn1_cursor *raw, const char *name)
 Check X.509 certificate alternative dNSName. More...
 
static int x509_check_ipaddress (struct x509_certificate *cert, const struct asn1_cursor *raw, const char *name)
 Check X.509 certificate alternative iPAddress. More...
 
static int x509_check_alt_name (struct x509_certificate *cert, const struct asn1_cursor *raw, const char *name)
 Check X.509 certificate alternative name. More...
 
int x509_check_name (struct x509_certificate *cert, const char *name)
 Check X.509 certificate name. More...
 
static void x509_free_chain (struct refcnt *refcnt)
 Free X.509 certificate chain. More...
 
struct x509_chainx509_alloc_chain (void)
 Allocate X.509 certificate chain. More...
 
int x509_append (struct x509_chain *chain, struct x509_certificate *cert)
 Append X.509 certificate to X.509 certificate chain. More...
 
int x509_append_raw (struct x509_chain *chain, const void *data, size_t len)
 Append X.509 certificate to X.509 certificate chain. More...
 
static struct x509_certificatex509_find_subject (struct x509_chain *certs, const struct asn1_cursor *subject)
 Identify X.509 certificate by subject. More...
 
int x509_auto_append (struct x509_chain *chain, struct x509_chain *certs)
 Append X.509 certificates to X.509 certificate chain. More...
 
int x509_validate_chain (struct x509_chain *chain, time_t time, struct x509_chain *store, struct x509_root *root)
 Validate X.509 certificate chain. More...
 
int image_x509 (struct image *image, size_t offset, struct x509_certificate **cert)
 Extract X.509 certificate object from image. More...
 
 REQUIRING_SYMBOL (x509_validate)
 
 REQUIRE_OBJECT (certstore)
 
 REQUIRE_OBJECT (config_crypto)
 

Variables

static uint8_t oid_common_name [] = { ASN1_OID_COMMON_NAME }
 "commonName" object identifier More...
 
static struct asn1_cursor oid_common_name_cursor
 "commonName" object identifier cursor More...
 
static uint8_t oid_code_signing [] = { ASN1_OID_CODESIGNING }
 "id-kp-codeSigning" object identifier More...
 
static uint8_t oid_ocsp_signing [] = { ASN1_OID_OCSPSIGNING }
 "id-kp-OCSPSigning" object identifier More...
 
static struct x509_key_purpose x509_key_purposes []
 Supported key purposes. More...
 
static uint8_t oid_ad_ocsp [] = { ASN1_OID_OCSP }
 "id-ad-ocsp" object identifier More...
 
static struct x509_access_method x509_access_methods []
 Supported access methods. More...
 
static uint8_t oid_ce_basic_constraints []
 "id-ce-basicConstraints" object identifier More...
 
static uint8_t oid_ce_key_usage []
 "id-ce-keyUsage" object identifier More...
 
static uint8_t oid_ce_ext_key_usage []
 "id-ce-extKeyUsage" object identifier More...
 
static uint8_t oid_pe_authority_info_access []
 "id-pe-authorityInfoAccess" object identifier More...
 
static uint8_t oid_ce_subject_alt_name []
 "id-ce-subjectAltName" object identifier More...
 
static struct x509_extension x509_extensions []
 Supported certificate extensions. More...
 

Detailed Description

X.509 certificates.

The structure of X.509v3 certificates is documented in RFC 5280 section 4.1.

Definition in file x509.c.

Macro Definition Documentation

◆ ENOTSUP_ALGORITHM

#define ENOTSUP_ALGORITHM   __einfo_error ( EINFO_ENOTSUP_ALGORITHM )

Definition at line 56 of file x509.c.

◆ EINFO_ENOTSUP_ALGORITHM

#define EINFO_ENOTSUP_ALGORITHM   __einfo_uniqify ( EINFO_ENOTSUP, 0x01, "Unsupported algorithm" )

Definition at line 58 of file x509.c.

◆ ENOTSUP_EXTENSION

#define ENOTSUP_EXTENSION   __einfo_error ( EINFO_ENOTSUP_EXTENSION )

Definition at line 60 of file x509.c.

◆ EINFO_ENOTSUP_EXTENSION

#define EINFO_ENOTSUP_EXTENSION   __einfo_uniqify ( EINFO_ENOTSUP, 0x02, "Unsupported extension" )

Definition at line 62 of file x509.c.

◆ EINVAL_ALGORITHM

#define EINVAL_ALGORITHM   __einfo_error ( EINFO_EINVAL_ALGORITHM )

Definition at line 64 of file x509.c.

◆ EINFO_EINVAL_ALGORITHM

#define EINFO_EINVAL_ALGORITHM   __einfo_uniqify ( EINFO_EINVAL, 0x01, "Invalid algorithm type" )

Definition at line 66 of file x509.c.

◆ EINVAL_ALGORITHM_MISMATCH

#define EINVAL_ALGORITHM_MISMATCH   __einfo_error ( EINFO_EINVAL_ALGORITHM_MISMATCH )

Definition at line 68 of file x509.c.

◆ EINFO_EINVAL_ALGORITHM_MISMATCH

#define EINFO_EINVAL_ALGORITHM_MISMATCH   __einfo_uniqify ( EINFO_EINVAL, 0x04, "Signature algorithm mismatch" )

Definition at line 70 of file x509.c.

◆ EINVAL_PATH_LEN

#define EINVAL_PATH_LEN   __einfo_error ( EINFO_EINVAL_PATH_LEN )

Definition at line 72 of file x509.c.

◆ EINFO_EINVAL_PATH_LEN

#define EINFO_EINVAL_PATH_LEN   __einfo_uniqify ( EINFO_EINVAL, 0x05, "Invalid pathLenConstraint" )

Definition at line 74 of file x509.c.

◆ EINVAL_VERSION

#define EINVAL_VERSION   __einfo_error ( EINFO_EINVAL_VERSION )

Definition at line 76 of file x509.c.

◆ EINFO_EINVAL_VERSION

#define EINFO_EINVAL_VERSION   __einfo_uniqify ( EINFO_EINVAL, 0x06, "Invalid version" )

Definition at line 78 of file x509.c.

◆ EACCES_WRONG_ISSUER

#define EACCES_WRONG_ISSUER   __einfo_error ( EINFO_EACCES_WRONG_ISSUER )

Definition at line 80 of file x509.c.

◆ EINFO_EACCES_WRONG_ISSUER

#define EINFO_EACCES_WRONG_ISSUER   __einfo_uniqify ( EINFO_EACCES, 0x01, "Wrong issuer" )

Definition at line 82 of file x509.c.

◆ EACCES_NOT_CA

#define EACCES_NOT_CA   __einfo_error ( EINFO_EACCES_NOT_CA )

Definition at line 84 of file x509.c.

◆ EINFO_EACCES_NOT_CA

#define EINFO_EACCES_NOT_CA   __einfo_uniqify ( EINFO_EACCES, 0x02, "Not a CA certificate" )

Definition at line 86 of file x509.c.

◆ EACCES_KEY_USAGE

#define EACCES_KEY_USAGE   __einfo_error ( EINFO_EACCES_KEY_USAGE )

Definition at line 88 of file x509.c.

◆ EINFO_EACCES_KEY_USAGE

#define EINFO_EACCES_KEY_USAGE   __einfo_uniqify ( EINFO_EACCES, 0x03, "Incorrect key usage" )

Definition at line 90 of file x509.c.

◆ EACCES_EXPIRED

#define EACCES_EXPIRED   __einfo_error ( EINFO_EACCES_EXPIRED )

Definition at line 92 of file x509.c.

◆ EINFO_EACCES_EXPIRED

#define EINFO_EACCES_EXPIRED   __einfo_uniqify ( EINFO_EACCES, 0x04, "Expired (or not yet valid)" )

Definition at line 94 of file x509.c.

◆ EACCES_PATH_LEN

#define EACCES_PATH_LEN   __einfo_error ( EINFO_EACCES_PATH_LEN )

Definition at line 96 of file x509.c.

◆ EINFO_EACCES_PATH_LEN

#define EINFO_EACCES_PATH_LEN   __einfo_uniqify ( EINFO_EACCES, 0x05, "Maximum path length exceeded" )

Definition at line 98 of file x509.c.

◆ EACCES_UNTRUSTED

#define EACCES_UNTRUSTED   __einfo_error ( EINFO_EACCES_UNTRUSTED )

Definition at line 100 of file x509.c.

◆ EINFO_EACCES_UNTRUSTED

#define EINFO_EACCES_UNTRUSTED   __einfo_uniqify ( EINFO_EACCES, 0x06, "Untrusted root certificate" )

Definition at line 102 of file x509.c.

◆ EACCES_OUT_OF_ORDER

#define EACCES_OUT_OF_ORDER   __einfo_error ( EINFO_EACCES_OUT_OF_ORDER )

Definition at line 104 of file x509.c.

◆ EINFO_EACCES_OUT_OF_ORDER

#define EINFO_EACCES_OUT_OF_ORDER   __einfo_uniqify ( EINFO_EACCES, 0x07, "Validation out of order" )

Definition at line 106 of file x509.c.

◆ EACCES_EMPTY

#define EACCES_EMPTY   __einfo_error ( EINFO_EACCES_EMPTY )

Definition at line 108 of file x509.c.

◆ EINFO_EACCES_EMPTY

#define EINFO_EACCES_EMPTY   __einfo_uniqify ( EINFO_EACCES, 0x08, "Empty certificate chain" )

Definition at line 110 of file x509.c.

◆ EACCES_OCSP_REQUIRED

#define EACCES_OCSP_REQUIRED   __einfo_error ( EINFO_EACCES_OCSP_REQUIRED )

Definition at line 112 of file x509.c.

◆ EINFO_EACCES_OCSP_REQUIRED

#define EINFO_EACCES_OCSP_REQUIRED   __einfo_uniqify ( EINFO_EACCES, 0x09, "OCSP check required" )

Definition at line 114 of file x509.c.

◆ EACCES_WRONG_NAME

#define EACCES_WRONG_NAME   __einfo_error ( EINFO_EACCES_WRONG_NAME )

Definition at line 116 of file x509.c.

◆ EINFO_EACCES_WRONG_NAME

#define EINFO_EACCES_WRONG_NAME   __einfo_uniqify ( EINFO_EACCES, 0x0a, "Incorrect certificate name" )

Definition at line 118 of file x509.c.

◆ EACCES_USELESS

#define EACCES_USELESS   __einfo_error ( EINFO_EACCES_USELESS )

Definition at line 120 of file x509.c.

◆ EINFO_EACCES_USELESS

#define EINFO_EACCES_USELESS   __einfo_uniqify ( EINFO_EACCES, 0x0b, "No usable certificates" )

Definition at line 122 of file x509.c.

Function Documentation

◆ FILE_LICENCE()

FILE_LICENCE ( GPL2_OR_LATER_OR_UBDL  )

◆ x509_name()

const char* x509_name ( struct x509_certificate cert)

Get X.509 certificate display name.

Parameters
certX.509 certificate
Return values
nameDisplay name

Definition at line 131 of file x509.c.

131  {
132  struct asn1_cursor *common_name = &cert->subject.common_name;
134  static char buf[64];
135  uint8_t fingerprint[ digest->digestsize ];
136  size_t len;
137 
138  len = common_name->len;
139  if ( len ) {
140  /* Certificate has a commonName: use that */
141  if ( len > ( sizeof ( buf ) - 1 /* NUL */ ) )
142  len = ( sizeof ( buf ) - 1 /* NUL */ );
143  memcpy ( buf, common_name->data, len );
144  buf[len] = '\0';
145  } else {
146  /* Certificate has no commonName: use SHA-1 fingerprint */
147  x509_fingerprint ( cert, digest, fingerprint );
148  base16_encode ( fingerprint, sizeof ( fingerprint ),
149  buf, sizeof ( buf ) );
150  }
151  return buf;
152 }
const void * data
Start of data.
Definition: asn1.h:21
struct md4_digest digest
Digest of data already processed.
Definition: md4.h:12
size_t len
Length of data.
Definition: asn1.h:23
void * memcpy(void *dest, const void *src, size_t len) __nonnull
struct x509_subject subject
Subject.
Definition: x509.h:212
unsigned char uint8_t
Definition: stdint.h:10
void x509_fingerprint(struct x509_certificate *cert, struct digest_algorithm *digest, void *fingerprint)
Calculate X.509 certificate fingerprint.
Definition: x509.c:1228
struct asn1_cursor common_name
Common name.
Definition: x509.h:62
uint32_t len
Length.
Definition: ena.h:14
A message digest algorithm.
Definition: crypto.h:16
An ASN.1 object cursor.
Definition: asn1.h:19
struct digest_algorithm sha1_algorithm
SHA-1 algorithm.
Definition: sha1.c:258

References x509_subject::common_name, asn1_cursor::data, digest, len, asn1_cursor::len, memcpy(), sha1_algorithm, x509_certificate::subject, and x509_fingerprint().

Referenced by certstat(), certstore_add(), certstore_apply_settings(), certstore_del(), certstore_found(), certstore_init(), cms_parse_certificates(), ocsp_check_signature(), ocsp_parse_basic_response(), ocsp_parse_cert_id(), ocsp_parse_certs(), ocsp_parse_responder_id(), ocsp_parse_response_status(), ocsp_parse_response_type(), ocsp_parse_responses(), ocsp_request(), ocsp_uri_string(), ocsp_validate(), tls_new_certificate_request(), tls_parse_chain(), validator_append(), validator_name(), validator_progress(), validator_start_download(), validator_start_ocsp(), x509_append(), x509_check_alt_name(), x509_check_dnsname(), x509_check_ipaddress(), x509_check_issuer(), x509_check_name(), x509_check_root(), x509_check_signature(), x509_check_time(), x509_parse_subject(), and x509_validate().

◆ x509_parse_version()

static int x509_parse_version ( struct x509_certificate cert,
const struct asn1_cursor raw 
)
static

Parse X.509 certificate version.

Parameters
certX.509 certificate
rawASN.1 cursor
Return values
rcReturn status code

Definition at line 168 of file x509.c.

169  {
170  struct asn1_cursor cursor;
171  int version;
172  int rc;
173 
174  /* Enter version */
175  memcpy ( &cursor, raw, sizeof ( cursor ) );
176  asn1_enter ( &cursor, ASN1_EXPLICIT_TAG ( 0 ) );
177 
178  /* Parse integer */
179  if ( ( rc = asn1_integer ( &cursor, &version ) ) != 0 ) {
180  DBGC ( cert, "X509 %p cannot parse version: %s\n",
181  cert, strerror ( rc ) );
182  DBGC_HDA ( cert, 0, raw->data, raw->len );
183  return rc;
184  }
185 
186  /* Sanity check */
187  if ( version < 0 ) {
188  DBGC ( cert, "X509 %p invalid version %d\n", cert, version );
189  DBGC_HDA ( cert, 0, raw->data, raw->len );
190  return -EINVAL_VERSION;
191  }
192 
193  /* Record version */
194  cert->version = version;
195  DBGC2 ( cert, "X509 %p is a version %d certificate\n",
196  cert, ( cert->version + 1 ) );
197 
198  return 0;
199 }
struct arbelprm_rc_send_wqe rc
Definition: arbel.h:14
int asn1_enter(struct asn1_cursor *cursor, unsigned int type)
Enter ASN.1 object.
Definition: asn1.c:160
#define DBGC(...)
Definition: compiler.h:505
void * memcpy(void *dest, const void *src, size_t len) __nonnull
u32 version
Version number.
Definition: ath9k_hw.c:1983
#define EINVAL_VERSION
Definition: x509.c:76
#define DBGC_HDA(...)
Definition: compiler.h:506
char * strerror(int errno)
Retrieve string representation of error number.
Definition: strerror.c:78
#define DBGC2(...)
Definition: compiler.h:522
unsigned int version
Version.
Definition: x509.h:200
int asn1_integer(const struct asn1_cursor *cursor, int *value)
Parse value of ASN.1 integer.
Definition: asn1.c:320
__be32 raw[7]
Definition: CIB_PRM.h:28
#define ASN1_EXPLICIT_TAG(number)
ASN.1 explicit tag.
Definition: asn1.h:94
An ASN.1 object cursor.
Definition: asn1.h:19

References asn1_enter(), ASN1_EXPLICIT_TAG, asn1_integer(), DBGC, DBGC2, DBGC_HDA, EINVAL_VERSION, memcpy(), raw, rc, strerror(), x509_certificate::version, and version.

Referenced by x509_parse_tbscertificate().

◆ x509_parse_serial()

static int x509_parse_serial ( struct x509_certificate cert,
const struct asn1_cursor raw 
)
static

Parse X.509 certificate serial number.

Parameters
certX.509 certificate
rawASN.1 cursor
Return values
rcReturn status code

Definition at line 208 of file x509.c.

209  {
210  struct x509_serial *serial = &cert->serial;
211  int rc;
212 
213  /* Record raw serial number */
214  memcpy ( &serial->raw, raw, sizeof ( serial->raw ) );
215  if ( ( rc = asn1_shrink ( &serial->raw, ASN1_INTEGER ) ) != 0 ) {
216  DBGC ( cert, "X509 %p cannot shrink serialNumber: %s\n",
217  cert, strerror ( rc ) );
218  return rc;
219  }
220  DBGC2 ( cert, "X509 %p issuer is:\n", cert );
221  DBGC2_HDA ( cert, 0, serial->raw.data, serial->raw.len );
222 
223  return 0;
224 }
struct arbelprm_rc_send_wqe rc
Definition: arbel.h:14
#define DBGC(...)
Definition: compiler.h:505
int asn1_shrink(struct asn1_cursor *cursor, unsigned int type)
Shrink ASN.1 cursor to fit object.
Definition: asn1.c:240
void * memcpy(void *dest, const void *src, size_t len) __nonnull
#define DBGC2_HDA(...)
Definition: compiler.h:523
char * strerror(int errno)
Retrieve string representation of error number.
Definition: strerror.c:78
struct x509_serial serial
Serial number.
Definition: x509.h:202
uint64_t serial
Serial number.
Definition: edd.h:30
#define ASN1_INTEGER
ASN.1 integer.
Definition: asn1.h:61
An X.509 serial number.
Definition: x509.h:22
#define DBGC2(...)
Definition: compiler.h:522
__be32 raw[7]
Definition: CIB_PRM.h:28

References ASN1_INTEGER, asn1_shrink(), DBGC, DBGC2, DBGC2_HDA, memcpy(), raw, rc, serial, x509_certificate::serial, and strerror().

Referenced by x509_parse_tbscertificate().

◆ x509_parse_issuer()

static int x509_parse_issuer ( struct x509_certificate cert,
const struct asn1_cursor raw 
)
static

Parse X.509 certificate issuer.

Parameters
certX.509 certificate
rawASN.1 cursor
Return values
rcReturn status code

Definition at line 233 of file x509.c.

234  {
235  struct x509_issuer *issuer = &cert->issuer;
236  int rc;
237 
238  /* Record raw issuer */
239  memcpy ( &issuer->raw, raw, sizeof ( issuer->raw ) );
240  if ( ( rc = asn1_shrink ( &issuer->raw, ASN1_SEQUENCE ) ) != 0 ) {
241  DBGC ( cert, "X509 %p cannot shrink issuer: %s\n",
242  cert, strerror ( rc ) );
243  return rc;
244  }
245  DBGC2 ( cert, "X509 %p issuer is:\n", cert );
246  DBGC2_HDA ( cert, 0, issuer->raw.data, issuer->raw.len );
247 
248  return 0;
249 }
struct arbelprm_rc_send_wqe rc
Definition: arbel.h:14
struct asn1_cursor raw
Raw issuer.
Definition: x509.h:30
struct x509_issuer issuer
Issuer.
Definition: x509.h:208
const void * data
Start of data.
Definition: asn1.h:21
#define DBGC(...)
Definition: compiler.h:505
size_t len
Length of data.
Definition: asn1.h:23
int asn1_shrink(struct asn1_cursor *cursor, unsigned int type)
Shrink ASN.1 cursor to fit object.
Definition: asn1.c:240
void * memcpy(void *dest, const void *src, size_t len) __nonnull
#define DBGC2_HDA(...)
Definition: compiler.h:523
char * strerror(int errno)
Retrieve string representation of error number.
Definition: strerror.c:78
An X.509 issuer.
Definition: x509.h:28
#define ASN1_SEQUENCE
ASN.1 sequence.
Definition: asn1.h:85
#define DBGC2(...)
Definition: compiler.h:522
__be32 raw[7]
Definition: CIB_PRM.h:28

References ASN1_SEQUENCE, asn1_shrink(), asn1_cursor::data, DBGC, DBGC2, DBGC2_HDA, x509_certificate::issuer, asn1_cursor::len, memcpy(), raw, x509_issuer::raw, rc, and strerror().

Referenced by x509_parse_tbscertificate().

◆ x509_parse_validity()

static int x509_parse_validity ( struct x509_certificate cert,
const struct asn1_cursor raw 
)
static

Parse X.509 certificate validity.

Parameters
certX.509 certificate
rawASN.1 cursor
Return values
rcReturn status code

Definition at line 258 of file x509.c.

259  {
260  struct x509_validity *validity = &cert->validity;
261  struct x509_time *not_before = &validity->not_before;
262  struct x509_time *not_after = &validity->not_after;
263  struct asn1_cursor cursor;
264  int rc;
265 
266  /* Enter validity */
267  memcpy ( &cursor, raw, sizeof ( cursor ) );
268  asn1_enter ( &cursor, ASN1_SEQUENCE );
269 
270  /* Parse notBefore */
271  if ( ( rc = asn1_generalized_time ( &cursor,
272  &not_before->time ) ) != 0 ) {
273  DBGC ( cert, "X509 %p cannot parse notBefore: %s\n",
274  cert, strerror ( rc ) );
275  return rc;
276  }
277  DBGC2 ( cert, "X509 %p valid from time %lld\n",
278  cert, not_before->time );
279  asn1_skip_any ( &cursor );
280 
281  /* Parse notAfter */
282  if ( ( rc = asn1_generalized_time ( &cursor,
283  &not_after->time ) ) != 0 ) {
284  DBGC ( cert, "X509 %p cannot parse notAfter: %s\n",
285  cert, strerror ( rc ) );
286  return rc;
287  }
288  DBGC2 ( cert, "X509 %p valid until time %lld\n",
289  cert, not_after->time );
290 
291  return 0;
292 }
struct arbelprm_rc_send_wqe rc
Definition: arbel.h:14
int asn1_enter(struct asn1_cursor *cursor, unsigned int type)
Enter ASN.1 object.
Definition: asn1.c:160
int asn1_generalized_time(const struct asn1_cursor *cursor, time_t *time)
Parse ASN.1 GeneralizedTime.
Definition: asn1.c:603
#define DBGC(...)
Definition: compiler.h:505
time_t time
Seconds since the Epoch.
Definition: x509.h:36
int asn1_skip_any(struct asn1_cursor *cursor)
Skip ASN.1 object of any type.
Definition: asn1.c:276
void * memcpy(void *dest, const void *src, size_t len) __nonnull
struct x509_time not_before
Not valid before.
Definition: x509.h:42
char * strerror(int errno)
Retrieve string representation of error number.
Definition: strerror.c:78
An X.509 certificate validity period.
Definition: x509.h:40
#define ASN1_SEQUENCE
ASN.1 sequence.
Definition: asn1.h:85
struct x509_validity validity
Validity.
Definition: x509.h:210
An X.509 time.
Definition: x509.h:34
#define DBGC2(...)
Definition: compiler.h:522
struct x509_time not_after
Not valid after.
Definition: x509.h:44
__be32 raw[7]
Definition: CIB_PRM.h:28
An ASN.1 object cursor.
Definition: asn1.h:19

References asn1_enter(), asn1_generalized_time(), ASN1_SEQUENCE, asn1_skip_any(), DBGC, DBGC2, memcpy(), x509_validity::not_after, x509_validity::not_before, raw, rc, strerror(), x509_time::time, and x509_certificate::validity.

Referenced by x509_parse_tbscertificate().

◆ x509_parse_common_name()

static int x509_parse_common_name ( struct x509_certificate cert,
const struct asn1_cursor raw 
)
static

Parse X.509 certificate common name.

Parameters
certX.509 certificate
rawASN.1 cursor
Return values
rcReturn status code

Definition at line 301 of file x509.c.

302  {
303  struct asn1_cursor cursor;
304  struct asn1_cursor oid_cursor;
305  struct asn1_cursor name_cursor;
306  int rc;
307 
308  /* Enter name */
309  memcpy ( &cursor, raw, sizeof ( cursor ) );
310  asn1_enter ( &cursor, ASN1_SEQUENCE );
311 
312  /* Scan through name list */
313  for ( ; cursor.len ; asn1_skip_any ( &cursor ) ) {
314 
315  /* Check for "commonName" OID */
316  memcpy ( &oid_cursor, &cursor, sizeof ( oid_cursor ) );
317  asn1_enter ( &oid_cursor, ASN1_SET );
318  asn1_enter ( &oid_cursor, ASN1_SEQUENCE );
319  memcpy ( &name_cursor, &oid_cursor, sizeof ( name_cursor ) );
320  asn1_enter ( &oid_cursor, ASN1_OID );
321  if ( asn1_compare ( &oid_common_name_cursor, &oid_cursor ) != 0)
322  continue;
323  asn1_skip_any ( &name_cursor );
324  if ( ( rc = asn1_enter_any ( &name_cursor ) ) != 0 ) {
325  DBGC ( cert, "X509 %p cannot locate name:\n", cert );
326  DBGC_HDA ( cert, 0, raw->data, raw->len );
327  return rc;
328  }
329 
330  /* Record common name */
331  memcpy ( &cert->subject.common_name, &name_cursor,
332  sizeof ( cert->subject.common_name ) );
333 
334  return 0;
335  }
336 
337  /* Certificates may not have a commonName */
338  DBGC2 ( cert, "X509 %p no commonName found:\n", cert );
339  return 0;
340 }
struct arbelprm_rc_send_wqe rc
Definition: arbel.h:14
int asn1_compare(const struct asn1_cursor *cursor1, const struct asn1_cursor *cursor2)
Compare two ASN.1 objects.
Definition: asn1.c:443
int asn1_enter(struct asn1_cursor *cursor, unsigned int type)
Enter ASN.1 object.
Definition: asn1.c:160
#define DBGC(...)
Definition: compiler.h:505
int asn1_skip_any(struct asn1_cursor *cursor)
Skip ASN.1 object of any type.
Definition: asn1.c:276
#define ASN1_SET
ASN.1 set.
Definition: asn1.h:88
void * memcpy(void *dest, const void *src, size_t len) __nonnull
#define DBGC_HDA(...)
Definition: compiler.h:506
struct x509_subject subject
Subject.
Definition: x509.h:212
static struct asn1_cursor oid_common_name_cursor
"commonName" object identifier cursor
Definition: x509.c:158
int asn1_enter_any(struct asn1_cursor *cursor)
Enter ASN.1 object of any type.
Definition: asn1.c:266
#define ASN1_SEQUENCE
ASN.1 sequence.
Definition: asn1.h:85
struct asn1_cursor common_name
Common name.
Definition: x509.h:62
#define ASN1_OID
ASN.1 object identifier.
Definition: asn1.h:73
#define DBGC2(...)
Definition: compiler.h:522
__be32 raw[7]
Definition: CIB_PRM.h:28
An ASN.1 object cursor.
Definition: asn1.h:19

References asn1_compare(), asn1_enter(), asn1_enter_any(), ASN1_OID, ASN1_SEQUENCE, ASN1_SET, asn1_skip_any(), x509_subject::common_name, DBGC, DBGC2, DBGC_HDA, asn1_cursor::len, memcpy(), oid_common_name_cursor, raw, rc, and x509_certificate::subject.

Referenced by x509_parse_subject().

◆ x509_parse_subject()

static int x509_parse_subject ( struct x509_certificate cert,
const struct asn1_cursor raw 
)
static

Parse X.509 certificate subject.

Parameters
certX.509 certificate
rawASN.1 cursor
Return values
rcReturn status code

Definition at line 349 of file x509.c.

350  {
351  struct x509_subject *subject = &cert->subject;
352  int rc;
353 
354  /* Record raw subject */
355  memcpy ( &subject->raw, raw, sizeof ( subject->raw ) );
356  asn1_shrink_any ( &subject->raw );
357  DBGC2 ( cert, "X509 %p subject is:\n", cert );
358  DBGC2_HDA ( cert, 0, subject->raw.data, subject->raw.len );
359 
360  /* Parse common name */
361  if ( ( rc = x509_parse_common_name ( cert, raw ) ) != 0 )
362  return rc;
363  DBGC2 ( cert, "X509 %p common name is \"%s\":\n", cert,
364  x509_name ( cert ) );
365 
366  return 0;
367 }
struct arbelprm_rc_send_wqe rc
Definition: arbel.h:14
const void * data
Start of data.
Definition: asn1.h:21
size_t len
Length of data.
Definition: asn1.h:23
void * memcpy(void *dest, const void *src, size_t len) __nonnull
#define DBGC2_HDA(...)
Definition: compiler.h:523
struct x509_subject subject
Subject.
Definition: x509.h:212
int asn1_shrink_any(struct asn1_cursor *cursor)
Shrink ASN.1 object of any type.
Definition: asn1.c:286
static int x509_parse_common_name(struct x509_certificate *cert, const struct asn1_cursor *raw)
Parse X.509 certificate common name.
Definition: x509.c:301
struct asn1_cursor raw
Raw subject.
Definition: x509.h:60
const char * x509_name(struct x509_certificate *cert)
Get X.509 certificate display name.
Definition: x509.c:131
#define DBGC2(...)
Definition: compiler.h:522
An X.509 certificate subject.
Definition: x509.h:58
__be32 raw[7]
Definition: CIB_PRM.h:28

References asn1_shrink_any(), asn1_cursor::data, DBGC2, DBGC2_HDA, asn1_cursor::len, memcpy(), raw, x509_subject::raw, rc, x509_certificate::subject, x509_name(), and x509_parse_common_name().

Referenced by x509_parse_tbscertificate().

◆ x509_parse_public_key()

static int x509_parse_public_key ( struct x509_certificate cert,
const struct asn1_cursor raw 
)
static

Parse X.509 certificate public key information.

Parameters
certX.509 certificate
rawASN.1 cursor
Return values
rcReturn status code

Definition at line 376 of file x509.c.

377  {
378  struct x509_public_key *public_key = &cert->subject.public_key;
379  struct asn1_algorithm **algorithm = &public_key->algorithm;
380  struct asn1_bit_string *raw_bits = &public_key->raw_bits;
381  struct asn1_cursor cursor;
382  int rc;
383 
384  /* Record raw subjectPublicKeyInfo */
385  memcpy ( &cursor, raw, sizeof ( cursor ) );
386  asn1_shrink_any ( &cursor );
387  memcpy ( &public_key->raw, &cursor, sizeof ( public_key->raw ) );
388  DBGC2 ( cert, "X509 %p public key is:\n", cert );
389  DBGC2_HDA ( cert, 0, public_key->raw.data, public_key->raw.len );
390 
391  /* Enter subjectPublicKeyInfo */
392  asn1_enter ( &cursor, ASN1_SEQUENCE );
393 
394  /* Parse algorithm */
395  if ( ( rc = asn1_pubkey_algorithm ( &cursor, algorithm ) ) != 0 ) {
396  DBGC ( cert, "X509 %p could not parse public key algorithm: "
397  "%s\n", cert, strerror ( rc ) );
398  return rc;
399  }
400  DBGC2 ( cert, "X509 %p public key algorithm is %s\n",
401  cert, (*algorithm)->name );
402  asn1_skip_any ( &cursor );
403 
404  /* Parse bit string */
405  if ( ( rc = asn1_bit_string ( &cursor, raw_bits ) ) != 0 ) {
406  DBGC ( cert, "X509 %p could not parse public key bits: %s\n",
407  cert, strerror ( rc ) );
408  return rc;
409  }
410 
411  return 0;
412 }
struct asn1_bit_string raw_bits
Raw public key bit string.
Definition: x509.h:54
An ASN.1 OID-identified algorithm.
Definition: asn1.h:298
struct asn1_cursor raw
Raw public key information.
Definition: x509.h:50
struct arbelprm_rc_send_wqe rc
Definition: arbel.h:14
int asn1_enter(struct asn1_cursor *cursor, unsigned int type)
Enter ASN.1 object.
Definition: asn1.c:160
const void * data
Start of data.
Definition: asn1.h:21
#define DBGC(...)
Definition: compiler.h:505
int asn1_skip_any(struct asn1_cursor *cursor)
Skip ASN.1 object of any type.
Definition: asn1.c:276
size_t len
Length of data.
Definition: asn1.h:23
void * memcpy(void *dest, const void *src, size_t len) __nonnull
An X.509 certificate public key.
Definition: x509.h:48
struct x509_public_key public_key
Public key information.
Definition: x509.h:64
#define DBGC2_HDA(...)
Definition: compiler.h:523
char * strerror(int errno)
Retrieve string representation of error number.
Definition: strerror.c:78
struct x509_subject subject
Subject.
Definition: x509.h:212
int asn1_pubkey_algorithm(const struct asn1_cursor *cursor, struct asn1_algorithm **algorithm)
Parse ASN.1 OID-identified public-key algorithm.
Definition: asn1.c:513
struct asn1_algorithm * algorithm
Public key algorithm.
Definition: x509.h:52
int asn1_shrink_any(struct asn1_cursor *cursor)
Shrink ASN.1 object of any type.
Definition: asn1.c:286
#define ASN1_SEQUENCE
ASN.1 sequence.
Definition: asn1.h:85
u16 algorithm
Authentication algorithm (Open System or Shared Key)
Definition: ieee80211.h:1030
#define DBGC2(...)
Definition: compiler.h:522
__be32 raw[7]
Definition: CIB_PRM.h:28
An ASN.1 object cursor.
Definition: asn1.h:19
An ASN.1 bit string.
Definition: asn1.h:316

References x509_public_key::algorithm, algorithm, asn1_enter(), asn1_pubkey_algorithm(), ASN1_SEQUENCE, asn1_shrink_any(), asn1_skip_any(), asn1_cursor::data, DBGC, DBGC2, DBGC2_HDA, asn1_cursor::len, memcpy(), x509_subject::public_key, raw, x509_public_key::raw, x509_public_key::raw_bits, rc, strerror(), and x509_certificate::subject.

Referenced by x509_parse_tbscertificate().

◆ x509_parse_basic_constraints()

static int x509_parse_basic_constraints ( struct x509_certificate cert,
const struct asn1_cursor raw 
)
static

Parse X.509 certificate basic constraints.

Parameters
certX.509 certificate
rawASN.1 cursor
Return values
rcReturn status code

Definition at line 421 of file x509.c.

422  {
423  struct x509_basic_constraints *basic = &cert->extensions.basic;
424  struct asn1_cursor cursor;
425  int ca = 0;
426  int path_len;
427  int rc;
428 
429  /* Enter basicConstraints */
430  memcpy ( &cursor, raw, sizeof ( cursor ) );
431  asn1_enter ( &cursor, ASN1_SEQUENCE );
432 
433  /* Parse "cA", if present */
434  if ( asn1_type ( &cursor ) == ASN1_BOOLEAN ) {
435  ca = asn1_boolean ( &cursor );
436  if ( ca < 0 ) {
437  rc = ca;
438  DBGC ( cert, "X509 %p cannot parse cA: %s\n",
439  cert, strerror ( rc ) );
440  DBGC_HDA ( cert, 0, raw->data, raw->len );
441  return rc;
442  }
443  asn1_skip_any ( &cursor );
444  }
445  basic->ca = ca;
446  DBGC2 ( cert, "X509 %p is %sa CA certificate\n",
447  cert, ( basic->ca ? "" : "not " ) );
448 
449  /* Ignore everything else unless "cA" is true */
450  if ( ! ca )
451  return 0;
452 
453  /* Parse "pathLenConstraint", if present and applicable */
455  if ( asn1_type ( &cursor ) == ASN1_INTEGER ) {
456  if ( ( rc = asn1_integer ( &cursor, &path_len ) ) != 0 ) {
457  DBGC ( cert, "X509 %p cannot parse pathLenConstraint: "
458  "%s\n", cert, strerror ( rc ) );
459  DBGC_HDA ( cert, 0, raw->data, raw->len );
460  return rc;
461  }
462  if ( path_len < 0 ) {
463  DBGC ( cert, "X509 %p invalid pathLenConstraint %d\n",
464  cert, path_len );
465  DBGC_HDA ( cert, 0, raw->data, raw->len );
466  return -EINVAL;
467  }
468  basic->path_len = path_len;
469  DBGC2 ( cert, "X509 %p path length constraint is %d\n",
470  cert, basic->path_len );
471  }
472 
473  return 0;
474 }
#define EINVAL
Invalid argument.
Definition: errno.h:428
struct arbelprm_rc_send_wqe rc
Definition: arbel.h:14
unsigned int path_len
Path length.
Definition: x509.h:80
An X.509 certificate basic constraints set.
Definition: x509.h:76
int asn1_enter(struct asn1_cursor *cursor, unsigned int type)
Enter ASN.1 object.
Definition: asn1.c:160
#define ASN1_BOOLEAN
ASN.1 boolean.
Definition: asn1.h:58
#define DBGC(...)
Definition: compiler.h:505
static unsigned int asn1_type(const struct asn1_cursor *cursor)
Extract ASN.1 type.
Definition: asn1.h:342
int asn1_skip_any(struct asn1_cursor *cursor)
Skip ASN.1 object of any type.
Definition: asn1.c:276
void * memcpy(void *dest, const void *src, size_t len) __nonnull
int asn1_boolean(const struct asn1_cursor *cursor)
Parse value of ASN.1 boolean.
Definition: asn1.c:296
#define DBGC_HDA(...)
Definition: compiler.h:506
char * strerror(int errno)
Retrieve string representation of error number.
Definition: strerror.c:78
int ca
Subject is a CA.
Definition: x509.h:78
#define ASN1_SEQUENCE
ASN.1 sequence.
Definition: asn1.h:85
#define ASN1_INTEGER
ASN.1 integer.
Definition: asn1.h:61
#define DBGC2(...)
Definition: compiler.h:522
int asn1_integer(const struct asn1_cursor *cursor, int *value)
Parse value of ASN.1 integer.
Definition: asn1.c:320
#define X509_PATH_LEN_UNLIMITED
Unlimited path length.
Definition: x509.h:88
__be32 raw[7]
Definition: CIB_PRM.h:28
An ASN.1 object cursor.
Definition: asn1.h:19
struct x509_basic_constraints basic
Basic constraints.
Definition: x509.h:157
struct x509_extensions extensions
Extensions.
Definition: x509.h:216

References ASN1_BOOLEAN, asn1_boolean(), asn1_enter(), ASN1_INTEGER, asn1_integer(), ASN1_SEQUENCE, asn1_skip_any(), asn1_type(), x509_extensions::basic, x509_basic_constraints::ca, DBGC, DBGC2, DBGC_HDA, EINVAL, x509_certificate::extensions, memcpy(), x509_basic_constraints::path_len, raw, rc, strerror(), and X509_PATH_LEN_UNLIMITED.

◆ x509_parse_key_usage()

static int x509_parse_key_usage ( struct x509_certificate cert,
const struct asn1_cursor raw 
)
static

Parse X.509 certificate key usage.

Parameters
certX.509 certificate
rawASN.1 cursor
Return values
rcReturn status code

Definition at line 483 of file x509.c.

484  {
485  struct x509_key_usage *usage = &cert->extensions.usage;
486  struct asn1_bit_string bit_string;
487  const uint8_t *bytes;
488  size_t len;
489  unsigned int i;
490  int rc;
491 
492  /* Mark extension as present */
493  usage->present = 1;
494 
495  /* Parse bit string */
496  if ( ( rc = asn1_bit_string ( raw, &bit_string ) ) != 0 ) {
497  DBGC ( cert, "X509 %p could not parse key usage: %s\n",
498  cert, strerror ( rc ) );
499  return rc;
500  }
501 
502  /* Parse key usage bits */
503  bytes = bit_string.data;
504  len = bit_string.len;
505  if ( len > sizeof ( usage->bits ) )
506  len = sizeof ( usage->bits );
507  for ( i = 0 ; i < len ; i++ ) {
508  usage->bits |= ( *(bytes++) << ( 8 * i ) );
509  }
510  DBGC2 ( cert, "X509 %p key usage is %08x\n", cert, usage->bits );
511 
512  return 0;
513 }
struct arbelprm_rc_send_wqe rc
Definition: arbel.h:14
#define DBGC(...)
Definition: compiler.h:505
int present
Key usage extension is present.
Definition: x509.h:93
char * strerror(int errno)
Retrieve string representation of error number.
Definition: strerror.c:78
unsigned char uint8_t
Definition: stdint.h:10
An X.509 certificate key usage.
Definition: x509.h:91
uint32_t len
Length.
Definition: ena.h:14
#define DBGC2(...)
Definition: compiler.h:522
unsigned int bits
Usage bits.
Definition: x509.h:95
__be32 raw[7]
Definition: CIB_PRM.h:28
struct x509_key_usage usage
Key usage.
Definition: x509.h:159
uint8_t bytes[64]
Definition: ib_mad.h:16
struct x509_extensions extensions
Extensions.
Definition: x509.h:216
An ASN.1 bit string.
Definition: asn1.h:316

References x509_key_usage::bits, bytes, asn1_bit_string::data, DBGC, DBGC2, x509_certificate::extensions, len, asn1_bit_string::len, x509_key_usage::present, raw, rc, strerror(), and x509_extensions::usage.

◆ x509_parse_key_purpose()

static int x509_parse_key_purpose ( struct x509_certificate cert,
const struct asn1_cursor raw 
)
static

Parse X.509 certificate key purpose identifier.

Parameters
certX.509 certificate
rawASN.1 cursor
Return values
rcReturn status code

Definition at line 542 of file x509.c.

543  {
544  struct x509_extended_key_usage *ext_usage = &cert->extensions.ext_usage;
545  struct x509_key_purpose *purpose;
546  struct asn1_cursor cursor;
547  unsigned int i;
548  int rc;
549 
550  /* Enter keyPurposeId */
551  memcpy ( &cursor, raw, sizeof ( cursor ) );
552  if ( ( rc = asn1_enter ( &cursor, ASN1_OID ) ) != 0 ) {
553  DBGC ( cert, "X509 %p invalid keyPurposeId:\n", cert );
554  DBGC_HDA ( cert, 0, raw->data, raw->len );
555  return rc;
556  }
557 
558  /* Identify key purpose */
559  for ( i = 0 ; i < ( sizeof ( x509_key_purposes ) /
560  sizeof ( x509_key_purposes[0] ) ) ; i++ ) {
561  purpose = &x509_key_purposes[i];
562  if ( asn1_compare ( &cursor, &purpose->oid ) == 0 ) {
563  DBGC2 ( cert, "X509 %p has key purpose %s\n",
564  cert, purpose->name );
565  ext_usage->bits |= purpose->bits;
566  return 0;
567  }
568  }
569 
570  /* Ignore unrecognised key purposes */
571  return 0;
572 }
struct arbelprm_rc_send_wqe rc
Definition: arbel.h:14
struct x509_extended_key_usage ext_usage
Extended key usage.
Definition: x509.h:161
int asn1_compare(const struct asn1_cursor *cursor1, const struct asn1_cursor *cursor2)
Compare two ASN.1 objects.
Definition: asn1.c:443
int asn1_enter(struct asn1_cursor *cursor, unsigned int type)
Enter ASN.1 object.
Definition: asn1.c:160
unsigned int bits
Usage bits.
Definition: x509.h:114
const char * name
Name.
Definition: x509.h:320
#define DBGC(...)
Definition: compiler.h:505
struct asn1_cursor oid
Object identifier.
Definition: x509.h:322
An X.509 key purpose.
Definition: x509.h:318
void * memcpy(void *dest, const void *src, size_t len) __nonnull
#define DBGC_HDA(...)
Definition: compiler.h:506
static struct x509_key_purpose x509_key_purposes[]
Supported key purposes.
Definition: x509.c:522
unsigned int bits
Extended key usage bits.
Definition: x509.h:324
#define ASN1_OID
ASN.1 object identifier.
Definition: asn1.h:73
An X.509 certificate extended key usage.
Definition: x509.h:112
#define DBGC2(...)
Definition: compiler.h:522
__be32 raw[7]
Definition: CIB_PRM.h:28
An ASN.1 object cursor.
Definition: asn1.h:19
struct x509_extensions extensions
Extensions.
Definition: x509.h:216

References asn1_compare(), asn1_enter(), ASN1_OID, x509_extended_key_usage::bits, x509_key_purpose::bits, DBGC, DBGC2, DBGC_HDA, x509_extensions::ext_usage, x509_certificate::extensions, memcpy(), x509_key_purpose::name, x509_key_purpose::oid, raw, rc, and x509_key_purposes.

Referenced by x509_parse_extended_key_usage().

◆ x509_parse_extended_key_usage()

static int x509_parse_extended_key_usage ( struct x509_certificate cert,
const struct asn1_cursor raw 
)
static

Parse X.509 certificate extended key usage.

Parameters
certX.509 certificate
rawASN.1 cursor
Return values
rcReturn status code

Definition at line 581 of file x509.c.

582  {
583  struct asn1_cursor cursor;
584  int rc;
585 
586  /* Enter extKeyUsage */
587  memcpy ( &cursor, raw, sizeof ( cursor ) );
588  asn1_enter ( &cursor, ASN1_SEQUENCE );
589 
590  /* Parse each extended key usage in turn */
591  while ( cursor.len ) {
592  if ( ( rc = x509_parse_key_purpose ( cert, &cursor ) ) != 0 )
593  return rc;
594  asn1_skip_any ( &cursor );
595  }
596 
597  return 0;
598 }
struct arbelprm_rc_send_wqe rc
Definition: arbel.h:14
int asn1_enter(struct asn1_cursor *cursor, unsigned int type)
Enter ASN.1 object.
Definition: asn1.c:160
int asn1_skip_any(struct asn1_cursor *cursor)
Skip ASN.1 object of any type.
Definition: asn1.c:276
void * memcpy(void *dest, const void *src, size_t len) __nonnull
#define ASN1_SEQUENCE
ASN.1 sequence.
Definition: asn1.h:85
static int x509_parse_key_purpose(struct x509_certificate *cert, const struct asn1_cursor *raw)
Parse X.509 certificate key purpose identifier.
Definition: x509.c:542
__be32 raw[7]
Definition: CIB_PRM.h:28
An ASN.1 object cursor.
Definition: asn1.h:19

References asn1_enter(), ASN1_SEQUENCE, asn1_skip_any(), asn1_cursor::len, memcpy(), raw, rc, and x509_parse_key_purpose().

◆ x509_parse_ocsp()

static int x509_parse_ocsp ( struct x509_certificate cert,
const struct asn1_cursor raw 
)
static

Parse X.509 certificate OCSP access method.

Parameters
certX.509 certificate
rawASN.1 cursor
Return values
rcReturn status code

Definition at line 607 of file x509.c.

608  {
609  struct x509_ocsp_responder *ocsp = &cert->extensions.auth_info.ocsp;
610  struct asn1_cursor *uri = &ocsp->uri;
611  int rc;
612 
613  /* Enter accessLocation */
614  memcpy ( uri, raw, sizeof ( *uri ) );
615  if ( ( rc = asn1_enter ( uri, X509_GENERAL_NAME_URI ) ) != 0 ) {
616  DBGC ( cert, "X509 %p OCSP does not contain "
617  "uniformResourceIdentifier:\n", cert );
618  DBGC_HDA ( cert, 0, raw->data, raw->len );
619  return rc;
620  }
621  DBGC2 ( cert, "X509 %p OCSP URI is:\n", cert );
622  DBGC2_HDA ( cert, 0, uri->data, uri->len );
623 
624  return 0;
625 }
struct arbelprm_rc_send_wqe rc
Definition: arbel.h:14
int asn1_enter(struct asn1_cursor *cursor, unsigned int type)
Enter ASN.1 object.
Definition: asn1.c:160
#define DBGC(...)
Definition: compiler.h:505
X.509 certificate OCSP responder.
Definition: x509.h:128
void * memcpy(void *dest, const void *src, size_t len) __nonnull
#define DBGC_HDA(...)
Definition: compiler.h:506
struct x509_authority_info_access auth_info
Authority information access.
Definition: x509.h:163
struct asn1_cursor uri
URI.
Definition: x509.h:130
#define DBGC2_HDA(...)
Definition: compiler.h:523
#define DBGC2(...)
Definition: compiler.h:522
__be32 raw[7]
Definition: CIB_PRM.h:28
A Uniform Resource Identifier.
Definition: uri.h:50
struct x509_ocsp_responder ocsp
OCSP responder.
Definition: x509.h:138
An ASN.1 object cursor.
Definition: asn1.h:19
struct x509_extensions extensions
Extensions.
Definition: x509.h:216

References asn1_enter(), x509_extensions::auth_info, DBGC, DBGC2, DBGC2_HDA, DBGC_HDA, x509_certificate::extensions, memcpy(), x509_authority_info_access::ocsp, raw, rc, x509_ocsp_responder::uri, and X509_GENERAL_NAME_URI.

◆ x509_find_access_method()

static struct x509_access_method* x509_find_access_method ( const struct asn1_cursor oid)
static

Identify X.509 access method by OID.

Parameters
oidOID
Return values
methodAccess method, or NULL

Definition at line 646 of file x509.c.

646  {
647  struct x509_access_method *method;
648  unsigned int i;
649 
650  for ( i = 0 ; i < ( sizeof ( x509_access_methods ) /
651  sizeof ( x509_access_methods[0] ) ) ; i++ ) {
653  if ( asn1_compare ( &method->oid, oid ) == 0 )
654  return method;
655  }
656 
657  return NULL;
658 }
int asn1_compare(const struct asn1_cursor *cursor1, const struct asn1_cursor *cursor2)
Compare two ASN.1 objects.
Definition: asn1.c:443
uint8_t method
Definition: ib_mad.h:14
static struct x509_access_method x509_access_methods[]
Supported access methods.
Definition: x509.c:631
struct asn1_cursor oid
Object identifier.
Definition: x509.h:332
#define NULL
NULL pointer (VOID *)
Definition: Base.h:362
An X.509 access method.
Definition: x509.h:328

References asn1_compare(), method, NULL, x509_access_method::oid, and x509_access_methods.

Referenced by x509_parse_access_description().

◆ x509_parse_access_description()

static int x509_parse_access_description ( struct x509_certificate cert,
const struct asn1_cursor raw 
)
static

Parse X.509 certificate access description.

Parameters
certX.509 certificate
rawASN.1 cursor
Return values
rcReturn status code

Definition at line 667 of file x509.c.

668  {
669  struct asn1_cursor cursor;
670  struct asn1_cursor subcursor;
671  struct x509_access_method *method;
672  int rc;
673 
674  /* Enter keyPurposeId */
675  memcpy ( &cursor, raw, sizeof ( cursor ) );
676  asn1_enter ( &cursor, ASN1_SEQUENCE );
677 
678  /* Try to identify access method */
679  memcpy ( &subcursor, &cursor, sizeof ( subcursor ) );
680  asn1_enter ( &subcursor, ASN1_OID );
681  method = x509_find_access_method ( &subcursor );
682  asn1_skip_any ( &cursor );
683  DBGC2 ( cert, "X509 %p found access method %s\n",
684  cert, ( method ? method->name : "<unknown>" ) );
685 
686  /* Parse access location, if applicable */
687  if ( method && ( ( rc = method->parse ( cert, &cursor ) ) != 0 ) )
688  return rc;
689 
690  return 0;
691 }
struct arbelprm_rc_send_wqe rc
Definition: arbel.h:14
int asn1_enter(struct asn1_cursor *cursor, unsigned int type)
Enter ASN.1 object.
Definition: asn1.c:160
uint8_t method
Definition: ib_mad.h:14
int asn1_skip_any(struct asn1_cursor *cursor)
Skip ASN.1 object of any type.
Definition: asn1.c:276
void * memcpy(void *dest, const void *src, size_t len) __nonnull
#define ASN1_SEQUENCE
ASN.1 sequence.
Definition: asn1.h:85
#define ASN1_OID
ASN.1 object identifier.
Definition: asn1.h:73
#define DBGC2(...)
Definition: compiler.h:522
__be32 raw[7]
Definition: CIB_PRM.h:28
An ASN.1 object cursor.
Definition: asn1.h:19
static struct x509_access_method * x509_find_access_method(const struct asn1_cursor *oid)
Identify X.509 access method by OID.
Definition: x509.c:646
An X.509 access method.
Definition: x509.h:328

References asn1_enter(), ASN1_OID, ASN1_SEQUENCE, asn1_skip_any(), DBGC2, memcpy(), method, raw, rc, and x509_find_access_method().

Referenced by x509_parse_authority_info_access().

◆ x509_parse_authority_info_access()

static int x509_parse_authority_info_access ( struct x509_certificate cert,
const struct asn1_cursor raw 
)
static

Parse X.509 certificate authority information access.

Parameters
certX.509 certificate
rawASN.1 cursor
Return values
rcReturn status code

Definition at line 700 of file x509.c.

701  {
702  struct asn1_cursor cursor;
703  int rc;
704 
705  /* Enter authorityInfoAccess */
706  memcpy ( &cursor, raw, sizeof ( cursor ) );
707  asn1_enter ( &cursor, ASN1_SEQUENCE );
708 
709  /* Parse each access description in turn */
710  while ( cursor.len ) {
711  if ( ( rc = x509_parse_access_description ( cert,
712  &cursor ) ) != 0 )
713  return rc;
714  asn1_skip_any ( &cursor );
715  }
716 
717  return 0;
718 }
struct arbelprm_rc_send_wqe rc
Definition: arbel.h:14
int asn1_enter(struct asn1_cursor *cursor, unsigned int type)
Enter ASN.1 object.
Definition: asn1.c:160
int asn1_skip_any(struct asn1_cursor *cursor)
Skip ASN.1 object of any type.
Definition: asn1.c:276
void * memcpy(void *dest, const void *src, size_t len) __nonnull
#define ASN1_SEQUENCE
ASN.1 sequence.
Definition: asn1.h:85
__be32 raw[7]
Definition: CIB_PRM.h:28
static int x509_parse_access_description(struct x509_certificate *cert, const struct asn1_cursor *raw)
Parse X.509 certificate access description.
Definition: x509.c:667
An ASN.1 object cursor.
Definition: asn1.h:19

References asn1_enter(), ASN1_SEQUENCE, asn1_skip_any(), asn1_cursor::len, memcpy(), raw, rc, and x509_parse_access_description().

◆ x509_parse_subject_alt_name()

static int x509_parse_subject_alt_name ( struct x509_certificate cert,
const struct asn1_cursor raw 
)
static

Parse X.509 certificate subject alternative name.

Parameters
certX.509 certificate
rawASN.1 cursor
Return values
rcReturn status code

Definition at line 727 of file x509.c.

728  {
729  struct x509_subject_alt_name *alt_name = &cert->extensions.alt_name;
730  struct asn1_cursor *names = &alt_name->names;
731  int rc;
732 
733  /* Enter subjectAltName */
734  memcpy ( names, raw, sizeof ( *names ) );
735  if ( ( rc = asn1_enter ( names, ASN1_SEQUENCE ) ) != 0 ) {
736  DBGC ( cert, "X509 %p invalid subjectAltName: %s\n",
737  cert, strerror ( rc ) );
738  DBGC_HDA ( cert, 0, raw->data, raw->len );
739  return rc;
740  }
741  DBGC2 ( cert, "X509 %p has subjectAltName:\n", cert );
742  DBGC2_HDA ( cert, 0, names->data, names->len );
743 
744  return 0;
745 }
struct arbelprm_rc_send_wqe rc
Definition: arbel.h:14
struct asn1_cursor names
Names.
Definition: x509.h:144
int asn1_enter(struct asn1_cursor *cursor, unsigned int type)
Enter ASN.1 object.
Definition: asn1.c:160
const void * data
Start of data.
Definition: asn1.h:21
#define DBGC(...)
Definition: compiler.h:505
size_t len
Length of data.
Definition: asn1.h:23
void * memcpy(void *dest, const void *src, size_t len) __nonnull
#define DBGC_HDA(...)
Definition: compiler.h:506
#define DBGC2_HDA(...)
Definition: compiler.h:523
char * strerror(int errno)
Retrieve string representation of error number.
Definition: strerror.c:78
#define ASN1_SEQUENCE
ASN.1 sequence.
Definition: asn1.h:85
struct x509_subject_alt_name alt_name
Subject alternative name.
Definition: x509.h:165
#define DBGC2(...)
Definition: compiler.h:522
X.509 certificate subject alternative name.
Definition: x509.h:142
__be32 raw[7]
Definition: CIB_PRM.h:28
An ASN.1 object cursor.
Definition: asn1.h:19
struct x509_extensions extensions
Extensions.
Definition: x509.h:216

References x509_extensions::alt_name, asn1_enter(), ASN1_SEQUENCE, asn1_cursor::data, DBGC, DBGC2, DBGC2_HDA, DBGC_HDA, x509_certificate::extensions, asn1_cursor::len, memcpy(), x509_subject_alt_name::names, raw, rc, and strerror().

◆ x509_find_extension()

static struct x509_extension* x509_find_extension ( const struct asn1_cursor oid)
static

Identify X.509 extension by OID.

Parameters
oidOID
Return values
extensionExtension, or NULL

Definition at line 803 of file x509.c.

803  {
804  struct x509_extension *extension;
805  unsigned int i;
806 
807  for ( i = 0 ; i < ( sizeof ( x509_extensions ) /
808  sizeof ( x509_extensions[0] ) ) ; i++ ) {
809  extension = &x509_extensions[i];
810  if ( asn1_compare ( &extension->oid, oid ) == 0 )
811  return extension;
812  }
813 
814  return NULL;
815 }
int asn1_compare(const struct asn1_cursor *cursor1, const struct asn1_cursor *cursor2)
Compare two ASN.1 objects.
Definition: asn1.c:443
struct asn1_cursor oid
Object identifier.
Definition: x509.h:306
static struct x509_extension x509_extensions[]
Supported certificate extensions.
Definition: x509.c:768
An X.509 certificate extensions set.
Definition: x509.h:155
#define NULL
NULL pointer (VOID *)
Definition: Base.h:362
An X.509 extension.
Definition: x509.h:302

References asn1_compare(), NULL, x509_extension::oid, and x509_extensions.

Referenced by x509_parse_extension().

◆ x509_parse_extension()

static int x509_parse_extension ( struct x509_certificate cert,
const struct asn1_cursor raw 
)
static

Parse X.509 certificate extension.

Parameters
certX.509 certificate
rawASN.1 cursor
Return values
rcReturn status code

Definition at line 824 of file x509.c.

825  {
826  struct asn1_cursor cursor;
827  struct asn1_cursor subcursor;
828  struct x509_extension *extension;
829  int is_critical = 0;
830  int rc;
831 
832  /* Enter extension */
833  memcpy ( &cursor, raw, sizeof ( cursor ) );
834  asn1_enter ( &cursor, ASN1_SEQUENCE );
835 
836  /* Try to identify extension */
837  memcpy ( &subcursor, &cursor, sizeof ( subcursor ) );
838  asn1_enter ( &subcursor, ASN1_OID );
839  extension = x509_find_extension ( &subcursor );
840  asn1_skip_any ( &cursor );
841  DBGC2 ( cert, "X509 %p found extension %s\n",
842  cert, ( extension ? extension->name : "<unknown>" ) );
843 
844  /* Identify criticality */
845  if ( asn1_type ( &cursor ) == ASN1_BOOLEAN ) {
846  is_critical = asn1_boolean ( &cursor );
847  if ( is_critical < 0 ) {
848  rc = is_critical;
849  DBGC ( cert, "X509 %p cannot parse extension "
850  "criticality: %s\n", cert, strerror ( rc ) );
851  DBGC_HDA ( cert, 0, raw->data, raw->len );
852  return rc;
853  }
854  asn1_skip_any ( &cursor );
855  }
856 
857  /* Handle unknown extensions */
858  if ( ! extension ) {
859  if ( is_critical ) {
860  /* Fail if we cannot handle a critical extension */
861  DBGC ( cert, "X509 %p cannot handle critical "
862  "extension:\n", cert );
863  DBGC_HDA ( cert, 0, raw->data, raw->len );
864  return -ENOTSUP_EXTENSION;
865  } else {
866  /* Ignore unknown non-critical extensions */
867  return 0;
868  }
869  };
870 
871  /* Extract extnValue */
872  if ( ( rc = asn1_enter ( &cursor, ASN1_OCTET_STRING ) ) != 0 ) {
873  DBGC ( cert, "X509 %p extension missing extnValue:\n", cert );
874  DBGC_HDA ( cert, 0, raw->data, raw->len );
875  return rc;
876  }
877 
878  /* Parse extension */
879  if ( ( rc = extension->parse ( cert, &cursor ) ) != 0 )
880  return rc;
881 
882  return 0;
883 }
struct arbelprm_rc_send_wqe rc
Definition: arbel.h:14
int asn1_enter(struct asn1_cursor *cursor, unsigned int type)
Enter ASN.1 object.
Definition: asn1.c:160
#define ASN1_BOOLEAN
ASN.1 boolean.
Definition: asn1.h:58
#define DBGC(...)
Definition: compiler.h:505
static unsigned int asn1_type(const struct asn1_cursor *cursor)
Extract ASN.1 type.
Definition: asn1.h:342
int asn1_skip_any(struct asn1_cursor *cursor)
Skip ASN.1 object of any type.
Definition: asn1.c:276
void * memcpy(void *dest, const void *src, size_t len) __nonnull
int asn1_boolean(const struct asn1_cursor *cursor)
Parse value of ASN.1 boolean.
Definition: asn1.c:296
#define DBGC_HDA(...)
Definition: compiler.h:506
char * strerror(int errno)
Retrieve string representation of error number.
Definition: strerror.c:78
#define ASN1_SEQUENCE
ASN.1 sequence.
Definition: asn1.h:85
const char * name
Name.
Definition: x509.h:304
#define ASN1_OID
ASN.1 object identifier.
Definition: asn1.h:73
#define DBGC2(...)
Definition: compiler.h:522
#define ENOTSUP_EXTENSION
Definition: x509.c:60
__be32 raw[7]
Definition: CIB_PRM.h:28
static struct x509_extension * x509_find_extension(const struct asn1_cursor *oid)
Identify X.509 extension by OID.
Definition: x509.c:803
#define ASN1_OCTET_STRING
ASN.1 octet string.
Definition: asn1.h:67
int(* parse)(struct x509_certificate *cert, const struct asn1_cursor *raw)
Parse extension.
Definition: x509.h:313
An ASN.1 object cursor.
Definition: asn1.h:19
An X.509 extension.
Definition: x509.h:302

References ASN1_BOOLEAN, asn1_boolean(), asn1_enter(), ASN1_OCTET_STRING, ASN1_OID, ASN1_SEQUENCE, asn1_skip_any(), asn1_type(), DBGC, DBGC2, DBGC_HDA, ENOTSUP_EXTENSION, memcpy(), x509_extension::name, x509_extension::parse, raw, rc, strerror(), and x509_find_extension().

Referenced by x509_parse_extensions().

◆ x509_parse_extensions()

static int x509_parse_extensions ( struct x509_certificate cert,
const struct asn1_cursor raw 
)
static

Parse X.509 certificate extensions, if present.

Parameters
certX.509 certificate
rawASN.1 cursor
Return values
rcReturn status code

Definition at line 892 of file x509.c.

893  {
894  struct asn1_cursor cursor;
895  int rc;
896 
897  /* Enter extensions, if present */
898  memcpy ( &cursor, raw, sizeof ( cursor ) );
899  asn1_enter ( &cursor, ASN1_EXPLICIT_TAG ( 3 ) );
900  asn1_enter ( &cursor, ASN1_SEQUENCE );
901 
902  /* Parse each extension in turn */
903  while ( cursor.len ) {
904  if ( ( rc = x509_parse_extension ( cert, &cursor ) ) != 0 )
905  return rc;
906  asn1_skip_any ( &cursor );
907  }
908 
909  return 0;
910 }
struct arbelprm_rc_send_wqe rc
Definition: arbel.h:14
int asn1_enter(struct asn1_cursor *cursor, unsigned int type)
Enter ASN.1 object.
Definition: asn1.c:160
int asn1_skip_any(struct asn1_cursor *cursor)
Skip ASN.1 object of any type.
Definition: asn1.c:276
void * memcpy(void *dest, const void *src, size_t len) __nonnull
static int x509_parse_extension(struct x509_certificate *cert, const struct asn1_cursor *raw)
Parse X.509 certificate extension.
Definition: x509.c:824
#define ASN1_SEQUENCE
ASN.1 sequence.
Definition: asn1.h:85
__be32 raw[7]
Definition: CIB_PRM.h:28
#define ASN1_EXPLICIT_TAG(number)
ASN.1 explicit tag.
Definition: asn1.h:94
An ASN.1 object cursor.
Definition: asn1.h:19

References asn1_enter(), ASN1_EXPLICIT_TAG, ASN1_SEQUENCE, asn1_skip_any(), asn1_cursor::len, memcpy(), raw, rc, and x509_parse_extension().

Referenced by x509_parse_tbscertificate().

◆ x509_parse_tbscertificate()

static int x509_parse_tbscertificate ( struct x509_certificate cert,
const struct asn1_cursor raw 
)
static

Parse X.509 certificate tbsCertificate.

Parameters
certX.509 certificate
rawASN.1 cursor
Return values
rcReturn status code

Definition at line 919 of file x509.c.

920  {
921  struct asn1_algorithm **algorithm = &cert->signature_algorithm;
922  struct asn1_cursor cursor;
923  int rc;
924 
925  /* Record raw tbsCertificate */
926  memcpy ( &cursor, raw, sizeof ( cursor ) );
927  asn1_shrink_any ( &cursor );
928  memcpy ( &cert->tbs, &cursor, sizeof ( cert->tbs ) );
929 
930  /* Enter tbsCertificate */
931  asn1_enter ( &cursor, ASN1_SEQUENCE );
932 
933  /* Parse version, if present */
934  if ( asn1_type ( &cursor ) == ASN1_EXPLICIT_TAG ( 0 ) ) {
935  if ( ( rc = x509_parse_version ( cert, &cursor ) ) != 0 )
936  return rc;
937  asn1_skip_any ( &cursor );
938  }
939 
940  /* Parse serialNumber */
941  if ( ( rc = x509_parse_serial ( cert, &cursor ) ) != 0 )
942  return rc;
943  asn1_skip_any ( &cursor );
944 
945  /* Parse signature */
946  if ( ( rc = asn1_signature_algorithm ( &cursor, algorithm ) ) != 0 ) {
947  DBGC ( cert, "X509 %p could not parse signature algorithm: "
948  "%s\n", cert, strerror ( rc ) );
949  return rc;
950  }
951  DBGC2 ( cert, "X509 %p tbsCertificate signature algorithm is %s\n",
952  cert, (*algorithm)->name );
953  asn1_skip_any ( &cursor );
954 
955  /* Parse issuer */
956  if ( ( rc = x509_parse_issuer ( cert, &cursor ) ) != 0 )
957  return rc;
958  asn1_skip_any ( &cursor );
959 
960  /* Parse validity */
961  if ( ( rc = x509_parse_validity ( cert, &cursor ) ) != 0 )
962  return rc;
963  asn1_skip_any ( &cursor );
964 
965  /* Parse subject */
966  if ( ( rc = x509_parse_subject ( cert, &cursor ) ) != 0 )
967  return rc;
968  asn1_skip_any ( &cursor );
969 
970  /* Parse subjectPublicKeyInfo */
971  if ( ( rc = x509_parse_public_key ( cert, &cursor ) ) != 0 )
972  return rc;
973  asn1_skip_any ( &cursor );
974 
975  /* Parse extensions, if present */
976  if ( ( rc = x509_parse_extensions ( cert, &cursor ) ) != 0 )
977  return rc;
978 
979  return 0;
980 }
An ASN.1 OID-identified algorithm.
Definition: asn1.h:298
struct arbelprm_rc_send_wqe rc
Definition: arbel.h:14
int asn1_enter(struct asn1_cursor *cursor, unsigned int type)
Enter ASN.1 object.
Definition: asn1.c:160
struct asn1_algorithm * signature_algorithm
Signature algorithm.
Definition: x509.h:206
#define DBGC(...)
Definition: compiler.h:505
static int x509_parse_issuer(struct x509_certificate *cert, const struct asn1_cursor *raw)
Parse X.509 certificate issuer.
Definition: x509.c:233
static unsigned int asn1_type(const struct asn1_cursor *cursor)
Extract ASN.1 type.
Definition: asn1.h:342
int asn1_skip_any(struct asn1_cursor *cursor)
Skip ASN.1 object of any type.
Definition: asn1.c:276
int asn1_signature_algorithm(const struct asn1_cursor *cursor, struct asn1_algorithm **algorithm)
Parse ASN.1 OID-identified signature algorithm.
Definition: asn1.c:565
static int x509_parse_serial(struct x509_certificate *cert, const struct asn1_cursor *raw)
Parse X.509 certificate serial number.
Definition: x509.c:208
void * memcpy(void *dest, const void *src, size_t len) __nonnull
static int x509_parse_version(struct x509_certificate *cert, const struct asn1_cursor *raw)
Parse X.509 certificate version.
Definition: x509.c:168
static int x509_parse_validity(struct x509_certificate *cert, const struct asn1_cursor *raw)
Parse X.509 certificate validity.
Definition: x509.c:258
char * strerror(int errno)
Retrieve string representation of error number.
Definition: strerror.c:78
int asn1_shrink_any(struct asn1_cursor *cursor)
Shrink ASN.1 object of any type.
Definition: asn1.c:286
#define ASN1_SEQUENCE
ASN.1 sequence.
Definition: asn1.h:85
u16 algorithm
Authentication algorithm (Open System or Shared Key)
Definition: ieee80211.h:1030
static int x509_parse_subject(struct x509_certificate *cert, const struct asn1_cursor *raw)
Parse X.509 certificate subject.
Definition: x509.c:349
#define DBGC2(...)
Definition: compiler.h:522
struct asn1_cursor tbs
Raw tbsCertificate.
Definition: x509.h:204
__be32 raw[7]
Definition: CIB_PRM.h:28
#define ASN1_EXPLICIT_TAG(number)
ASN.1 explicit tag.
Definition: asn1.h:94
static int x509_parse_extensions(struct x509_certificate *cert, const struct asn1_cursor *raw)
Parse X.509 certificate extensions, if present.
Definition: x509.c:892
An ASN.1 object cursor.
Definition: asn1.h:19
static int x509_parse_public_key(struct x509_certificate *cert, const struct asn1_cursor *raw)
Parse X.509 certificate public key information.
Definition: x509.c:376

References algorithm, asn1_enter(), ASN1_EXPLICIT_TAG, ASN1_SEQUENCE, asn1_shrink_any(), asn1_signature_algorithm(), asn1_skip_any(), asn1_type(), DBGC, DBGC2, memcpy(), raw, rc, x509_certificate::signature_algorithm, strerror(), x509_certificate::tbs, x509_parse_extensions(), x509_parse_issuer(), x509_parse_public_key(), x509_parse_serial(), x509_parse_subject(), x509_parse_validity(), and x509_parse_version().

Referenced by x509_parse().

◆ x509_parse()

int x509_parse ( struct x509_certificate cert,
const struct asn1_cursor raw 
)

Parse X.509 certificate from ASN.1 data.

Parameters
certX.509 certificate
rawASN.1 cursor
Return values
rcReturn status code

Definition at line 989 of file x509.c.

990  {
991  struct x509_signature *signature = &cert->signature;
992  struct asn1_algorithm **signature_algorithm = &signature->algorithm;
993  struct asn1_bit_string *signature_value = &signature->value;
994  struct asn1_cursor cursor;
995  int rc;
996 
997  /* Record raw certificate */
998  memcpy ( &cursor, raw, sizeof ( cursor ) );
999  memcpy ( &cert->raw, &cursor, sizeof ( cert->raw ) );
1000 
1001  /* Enter certificate */
1002  asn1_enter ( &cursor, ASN1_SEQUENCE );
1003 
1004  /* Parse tbsCertificate */
1005  if ( ( rc = x509_parse_tbscertificate ( cert, &cursor ) ) != 0 )
1006  return rc;
1007  asn1_skip_any ( &cursor );
1008 
1009  /* Parse signatureAlgorithm */
1010  if ( ( rc = asn1_signature_algorithm ( &cursor,
1011  signature_algorithm ) ) != 0 ) {
1012  DBGC ( cert, "X509 %p could not parse signature algorithm: "
1013  "%s\n", cert, strerror ( rc ) );
1014  return rc;
1015  }
1016  DBGC2 ( cert, "X509 %p signatureAlgorithm is %s\n",
1017  cert, (*signature_algorithm)->name );
1018  asn1_skip_any ( &cursor );
1019 
1020  /* Parse signatureValue */
1021  if ( ( rc = asn1_integral_bit_string ( &cursor,
1022  signature_value ) ) != 0 ) {
1023  DBGC ( cert, "X509 %p could not parse signature value: %s\n",
1024  cert, strerror ( rc ) );
1025  return rc;
1026  }
1027  DBGC2 ( cert, "X509 %p signatureValue is:\n", cert );
1028  DBGC2_HDA ( cert, 0, signature_value->data, signature_value->len );
1029 
1030  /* Check that algorithm in tbsCertificate matches algorithm in
1031  * signature
1032  */
1033  if ( signature->algorithm != (*signature_algorithm) ) {
1034  DBGC ( cert, "X509 %p signature algorithm %s does not match "
1035  "signatureAlgorithm %s\n",
1036  cert, signature->algorithm->name,
1037  (*signature_algorithm)->name );
1038  return -EINVAL_ALGORITHM_MISMATCH;
1039  }
1040 
1041  return 0;
1042 }
const void * data
Data.
Definition: asn1.h:318
An ASN.1 OID-identified algorithm.
Definition: asn1.h:298
struct arbelprm_rc_send_wqe rc
Definition: arbel.h:14
int asn1_enter(struct asn1_cursor *cursor, unsigned int type)
Enter ASN.1 object.
Definition: asn1.c:160
#define DBGC(...)
Definition: compiler.h:505
int asn1_skip_any(struct asn1_cursor *cursor)
Skip ASN.1 object of any type.
Definition: asn1.c:276
int asn1_signature_algorithm(const struct asn1_cursor *cursor, struct asn1_algorithm **algorithm)
Parse ASN.1 OID-identified signature algorithm.
Definition: asn1.c:565
u8 signature
Definition: CIB_PRM.h:35
void * memcpy(void *dest, const void *src, size_t len) __nonnull
struct x509_signature signature
Signature.
Definition: x509.h:214
#define DBGC2_HDA(...)
Definition: compiler.h:523
int asn1_integral_bit_string(const struct asn1_cursor *cursor, struct asn1_bit_string *bits)
Parse ASN.1 bit string that must be an integral number of bytes.
Definition: asn1.c:414
static int x509_parse_tbscertificate(struct x509_certificate *cert, const struct asn1_cursor *raw)
Parse X.509 certificate tbsCertificate.
Definition: x509.c:919
char * strerror(int errno)
Retrieve string representation of error number.
Definition: strerror.c:78
size_t len
Length.
Definition: asn1.h:320
#define ASN1_SEQUENCE
ASN.1 sequence.
Definition: asn1.h:85
#define DBGC2(...)
Definition: compiler.h:522
#define EINVAL_ALGORITHM_MISMATCH
Definition: x509.c:68
__be32 raw[7]
Definition: CIB_PRM.h:28
struct asn1_cursor raw
Raw certificate.
Definition: x509.h:198
An ASN.1 object cursor.
Definition: asn1.h:19
An ASN.1 bit string.
Definition: asn1.h:316
An X.509 certificate signature.
Definition: x509.h:68

References asn1_enter(), asn1_integral_bit_string(), ASN1_SEQUENCE, asn1_signature_algorithm(), asn1_skip_any(), asn1_bit_string::data, DBGC, DBGC2, DBGC2_HDA, EINVAL_ALGORITHM_MISMATCH, asn1_bit_string::len, memcpy(), raw, x509_certificate::raw, rc, signature, x509_certificate::signature, strerror(), and x509_parse_tbscertificate().

Referenced by certstore_init(), and x509_certificate().

◆ x509_certificate()

int x509_certificate ( const void *  data,
size_t  len,
struct x509_certificate **  cert 
)

Create X.509 certificate.

Parameters
dataRaw certificate data
lenLength of raw data
Return values
certX.509 certificate
rcReturn status code

On success, the caller holds a reference to the X.509 certificate, and is responsible for ultimately calling x509_put().

Definition at line 1055 of file x509.c.

1056  {
1057  struct asn1_cursor cursor;
1058  void *raw;
1059  int rc;
1060 
1061  /* Initialise cursor */
1062  cursor.data = data;
1063  cursor.len = len;
1064  asn1_shrink_any ( &cursor );
1065 
1066  /* Return stored certificate, if present */
1067  if ( ( *cert = certstore_find ( &cursor ) ) != NULL ) {
1068 
1069  /* Add caller's reference */
1070  x509_get ( *cert );
1071  return 0;
1072  }
1073 
1074  /* Allocate and initialise certificate */
1075  *cert = zalloc ( sizeof ( **cert ) + cursor.len );
1076  if ( ! *cert )
1077  return -ENOMEM;
1078  ref_init ( &(*cert)->refcnt, NULL );
1079  raw = ( *cert + 1 );
1080 
1081  /* Copy raw data */
1082  memcpy ( raw, cursor.data, cursor.len );
1083  cursor.data = raw;
1084 
1085  /* Parse certificate */
1086  if ( ( rc = x509_parse ( *cert, &cursor ) ) != 0 ) {
1087  x509_put ( *cert );
1088  *cert = NULL;
1089  return rc;
1090  }
1091 
1092  /* Add certificate to store */
1093  certstore_add ( *cert );
1094 
1095  return 0;
1096 }
struct arbelprm_rc_send_wqe rc
Definition: arbel.h:14
static struct x509_certificate * x509_get(struct x509_certificate *cert)
Get reference to X.509 certificate.
Definition: x509.h:236
#define ref_init(refcnt, free)
Initialise a reference counter.
Definition: refcnt.h:64
void certstore_add(struct x509_certificate *cert)
Add certificate to store.
Definition: certstore.c:138
#define ENOMEM
Not enough space.
Definition: errno.h:534
void * memcpy(void *dest, const void *src, size_t len) __nonnull
void * zalloc(size_t size)
Allocate cleared memory.
Definition: malloc.c:624
int asn1_shrink_any(struct asn1_cursor *cursor)
Shrink ASN.1 object of any type.
Definition: asn1.c:286
struct x509_certificate * certstore_find(struct asn1_cursor *raw)
Find certificate in store.
Definition: certstore.c:102
uint32_t len
Length.
Definition: ena.h:14
static void x509_put(struct x509_certificate *cert)
Drop reference to X.509 certificate.
Definition: x509.h:247
__be32 raw[7]
Definition: CIB_PRM.h:28
struct arbelprm_port_state_change_st data
Message.
Definition: arbel.h:12
struct arbelprm_wqe_segment_data_ptr data[ARBEL_MAX_GATHER]
Definition: arbel.h:237
#define NULL
NULL pointer (VOID *)
Definition: Base.h:362
An ASN.1 object cursor.
Definition: asn1.h:19
int x509_parse(struct x509_certificate *cert, const struct asn1_cursor *raw)
Parse X.509 certificate from ASN.1 data.
Definition: x509.c:989

References asn1_shrink_any(), certstore_add(), certstore_find(), data, asn1_cursor::data, ENOMEM, len, asn1_cursor::len, memcpy(), NULL, raw, rc, ref_init, x509_get(), x509_parse(), x509_put(), and zalloc().

◆ x509_check_signature()

static int x509_check_signature ( struct x509_certificate cert,
struct x509_public_key public_key 
)
static

Check X.509 certificate signature.

Parameters
certX.509 certificate
public_keyX.509 public key
Return values
rcReturn status code

Definition at line 1105 of file x509.c.

1106  {
1107  struct x509_signature *signature = &cert->signature;
1108  struct asn1_algorithm *algorithm = signature->algorithm;
1109  struct digest_algorithm *digest = algorithm->digest;
1110  struct pubkey_algorithm *pubkey = algorithm->pubkey;
1111  uint8_t digest_ctx[ digest->ctxsize ];
1112  uint8_t digest_out[ digest->digestsize ];
1113  uint8_t pubkey_ctx[ pubkey->ctxsize ];
1114  int rc;
1115 
1116  /* Sanity check */
1117  assert ( cert->signature_algorithm == cert->signature.algorithm );
1118 
1119  /* Calculate certificate digest */
1120  digest_init ( digest, digest_ctx );
1121  digest_update ( digest, digest_ctx, cert->tbs.data, cert->tbs.len );
1122  digest_final ( digest, digest_ctx, digest_out );
1123  DBGC2 ( cert, "X509 %p \"%s\" digest:\n", cert, x509_name ( cert ) );
1124  DBGC2_HDA ( cert, 0, digest_out, sizeof ( digest_out ) );
1125 
1126  /* Check that signature public key algorithm matches signer */
1127  if ( public_key->algorithm->pubkey != pubkey ) {
1128  DBGC ( cert, "X509 %p \"%s\" signature algorithm %s does not "
1129  "match signer's algorithm %s\n",
1130  cert, x509_name ( cert ), algorithm->name,
1131  public_key->algorithm->name );
1133  goto err_mismatch;
1134  }
1135 
1136  /* Verify signature using signer's public key */
1137  if ( ( rc = pubkey_init ( pubkey, pubkey_ctx, public_key->raw.data,
1138  public_key->raw.len ) ) != 0 ) {
1139  DBGC ( cert, "X509 %p \"%s\" cannot initialise public key: "
1140  "%s\n", cert, x509_name ( cert ), strerror ( rc ) );
1141  goto err_pubkey_init;
1142  }
1143  if ( ( rc = pubkey_verify ( pubkey, pubkey_ctx, digest, digest_out,
1144  signature->value.data,
1145  signature->value.len ) ) != 0 ) {
1146  DBGC ( cert, "X509 %p \"%s\" signature verification failed: "
1147  "%s\n", cert, x509_name ( cert ), strerror ( rc ) );
1148  goto err_pubkey_verify;
1149  }
1150 
1151  /* Success */
1152  rc = 0;
1153 
1154  err_pubkey_verify:
1155  pubkey_final ( pubkey, pubkey_ctx );
1156  err_pubkey_init:
1157  err_mismatch:
1158  return rc;
1159 }
An ASN.1 OID-identified algorithm.
Definition: asn1.h:298
struct asn1_cursor raw
Raw public key information.
Definition: x509.h:50
struct arbelprm_rc_send_wqe rc
Definition: arbel.h:14
static void digest_update(struct digest_algorithm *digest, void *ctx, const void *data, size_t len)
Definition: crypto.h:177
static void digest_final(struct digest_algorithm *digest, void *ctx, void *out)
Definition: crypto.h:182
struct asn1_algorithm * signature_algorithm
Signature algorithm.
Definition: x509.h:206
const void * data
Start of data.
Definition: asn1.h:21
#define DBGC(...)
Definition: compiler.h:505
struct asn1_algorithm * algorithm
Signature algorithm.
Definition: x509.h:70
struct md4_digest digest
Digest of data already processed.
Definition: md4.h:12
size_t ctxsize
Context size.
Definition: crypto.h:98
size_t len
Length of data.
Definition: asn1.h:23
struct pubkey_algorithm * pubkey
Public-key algorithm (if applicable)
Definition: asn1.h:304
u8 signature
Definition: CIB_PRM.h:35
static int pubkey_verify(struct pubkey_algorithm *pubkey, void *ctx, struct digest_algorithm *digest, const void *value, const void *signature, size_t signature_len)
Definition: crypto.h:247
assert((readw(&hdr->flags) &(GTF_reading|GTF_writing))==0)
struct x509_signature signature
Signature.
Definition: x509.h:214
#define DBGC2_HDA(...)
Definition: compiler.h:523
static void digest_init(struct digest_algorithm *digest, void *ctx)
Definition: crypto.h:172
char * strerror(int errno)
Retrieve string representation of error number.
Definition: strerror.c:78
struct asn1_algorithm * algorithm
Public key algorithm.
Definition: x509.h:52
unsigned char uint8_t
Definition: stdint.h:10
u16 algorithm
Authentication algorithm (Open System or Shared Key)
Definition: ieee80211.h:1030
const char * name
Name.
Definition: asn1.h:300
const char * x509_name(struct x509_certificate *cert)
Get X.509 certificate display name.
Definition: x509.c:131
#define DBGC2(...)
Definition: compiler.h:522
struct asn1_cursor tbs
Raw tbsCertificate.
Definition: x509.h:204
A message digest algorithm.
Definition: crypto.h:16
#define EINVAL_ALGORITHM_MISMATCH
Definition: x509.c:68
static void pubkey_final(struct pubkey_algorithm *pubkey, void *ctx)
Definition: crypto.h:254
A public key algorithm.
Definition: crypto.h:94
static int pubkey_init(struct pubkey_algorithm *pubkey, void *ctx, const void *key, size_t key_len)
Definition: crypto.h:221
An X.509 certificate signature.
Definition: x509.h:68

References x509_public_key::algorithm, x509_signature::algorithm, algorithm, assert(), pubkey_algorithm::ctxsize, asn1_cursor::data, DBGC, DBGC2, DBGC2_HDA, digest, digest_final(), digest_init(), digest_update(), EINVAL_ALGORITHM_MISMATCH, asn1_cursor::len, asn1_algorithm::name, asn1_algorithm::pubkey, pubkey_final(), pubkey_init(), pubkey_verify(), x509_public_key::raw, rc, signature, x509_certificate::signature, x509_certificate::signature_algorithm, strerror(), x509_certificate::tbs, and x509_name().

Referenced by x509_check_issuer().

◆ x509_check_issuer()

int x509_check_issuer ( struct x509_certificate cert,
struct x509_certificate issuer 
)

Check X.509 certificate against issuer certificate.

Parameters
certX.509 certificate
issuerX.509 issuer certificate
Return values
rcReturn status code

Definition at line 1168 of file x509.c.

1169  {
1170  struct x509_public_key *public_key = &issuer->subject.public_key;
1171  int rc;
1172 
1173  /* Check issuer. In theory, this should be a full X.500 DN
1174  * comparison, which would require support for a plethora of
1175  * abominations such as TeletexString (which allows the
1176  * character set to be changed mid-string using escape codes).
1177  * In practice, we assume that anyone who deliberately changes
1178  * the encoding of the issuer DN is probably a masochist who
1179  * will rather enjoy the process of figuring out exactly why
1180  * their certificate doesn't work.
1181  *
1182  * See http://www.cs.auckland.ac.nz/~pgut001/pubs/x509guide.txt
1183  * for some enjoyable ranting on this subject.
1184  */
1185  if ( asn1_compare ( &cert->issuer.raw, &issuer->subject.raw ) != 0 ) {
1186  DBGC ( cert, "X509 %p \"%s\" issuer does not match ",
1187  cert, x509_name ( cert ) );
1188  DBGC ( cert, "X509 %p \"%s\" subject\n",
1189  issuer, x509_name ( issuer ) );
1190  DBGC_HDA ( cert, 0, cert->issuer.raw.data,
1191  cert->issuer.raw.len );
1192  DBGC_HDA ( issuer, 0, issuer->subject.raw.data,
1193  issuer->subject.raw.len );
1194  return -EACCES_WRONG_ISSUER;
1195  }
1196 
1197  /* Check that issuer is allowed to sign certificates */
1198  if ( ! issuer->extensions.basic.ca ) {
1199  DBGC ( issuer, "X509 %p \"%s\" cannot sign ",
1200  issuer, x509_name ( issuer ) );
1201  DBGC ( issuer, "X509 %p \"%s\": not a CA certificate\n",
1202  cert, x509_name ( cert ) );
1203  return -EACCES_NOT_CA;
1204  }
1205  if ( issuer->extensions.usage.present &&
1206  ( ! ( issuer->extensions.usage.bits & X509_KEY_CERT_SIGN ) ) ) {
1207  DBGC ( issuer, "X509 %p \"%s\" cannot sign ",
1208  issuer, x509_name ( issuer ) );
1209  DBGC ( issuer, "X509 %p \"%s\": no keyCertSign usage\n",
1210  cert, x509_name ( cert ) );
1211  return -EACCES_KEY_USAGE;
1212  }
1213 
1214  /* Check signature */
1215  if ( ( rc = x509_check_signature ( cert, public_key ) ) != 0 )
1216  return rc;
1217 
1218  return 0;
1219 }
struct arbelprm_rc_send_wqe rc
Definition: arbel.h:14
struct asn1_cursor raw
Raw issuer.
Definition: x509.h:30
int asn1_compare(const struct asn1_cursor *cursor1, const struct asn1_cursor *cursor2)
Compare two ASN.1 objects.
Definition: asn1.c:443
struct x509_issuer issuer
Issuer.
Definition: x509.h:208
const void * data
Start of data.
Definition: asn1.h:21
#define DBGC(...)
Definition: compiler.h:505
int present
Key usage extension is present.
Definition: x509.h:93
size_t len
Length of data.
Definition: asn1.h:23
#define EACCES_KEY_USAGE
Definition: x509.c:88
#define DBGC_HDA(...)
Definition: compiler.h:506
An X.509 certificate public key.
Definition: x509.h:48
struct x509_public_key public_key
Public key information.
Definition: x509.h:64
struct x509_subject subject
Subject.
Definition: x509.h:212
int ca
Subject is a CA.
Definition: x509.h:78
#define EACCES_NOT_CA
Definition: x509.c:84
struct asn1_cursor raw
Raw subject.
Definition: x509.h:60
const char * x509_name(struct x509_certificate *cert)
Get X.509 certificate display name.
Definition: x509.c:131
static int x509_check_signature(struct x509_certificate *cert, struct x509_public_key *public_key)
Check X.509 certificate signature.
Definition: x509.c:1105
unsigned int bits
Usage bits.
Definition: x509.h:95
struct x509_key_usage usage
Key usage.
Definition: x509.h:159
#define EACCES_WRONG_ISSUER
Definition: x509.c:80
struct x509_basic_constraints basic
Basic constraints.
Definition: x509.h:157
struct x509_extensions extensions
Extensions.
Definition: x509.h:216

References asn1_compare(), x509_extensions::basic, x509_key_usage::bits, x509_basic_constraints::ca, asn1_cursor::data, DBGC, DBGC_HDA, EACCES_KEY_USAGE, EACCES_NOT_CA, EACCES_WRONG_ISSUER, x509_certificate::extensions, x509_certificate::issuer, asn1_cursor::len, x509_key_usage::present, x509_subject::public_key, x509_subject::raw, x509_issuer::raw, rc, x509_certificate::subject, x509_extensions::usage, x509_check_signature(), X509_KEY_CERT_SIGN, and x509_name().

Referenced by x509_check_issuer_fail_okx(), x509_check_issuer_okx(), and x509_validate().

◆ x509_fingerprint()

void x509_fingerprint ( struct x509_certificate cert,
struct digest_algorithm digest,
void *  fingerprint 
)

Calculate X.509 certificate fingerprint.

Parameters
certX.509 certificate
digestDigest algorithm
fingerprintFingerprint buffer

Definition at line 1228 of file x509.c.

1230  {
1231  uint8_t ctx[ digest->ctxsize ];
1232 
1233  /* Calculate fingerprint */
1234  digest_init ( digest, ctx );
1235  digest_update ( digest, ctx, cert->raw.data, cert->raw.len );
1236  digest_final ( digest, ctx, fingerprint );
1237 }
static void digest_update(struct digest_algorithm *digest, void *ctx, const void *data, size_t len)
Definition: crypto.h:177
static void digest_final(struct digest_algorithm *digest, void *ctx, void *out)
Definition: crypto.h:182
const void * data
Start of data.
Definition: asn1.h:21
struct golan_eq_context ctx
Definition: CIB_PRM.h:28
struct md4_digest digest
Digest of data already processed.
Definition: md4.h:12
size_t len
Length of data.
Definition: asn1.h:23
static void digest_init(struct digest_algorithm *digest, void *ctx)
Definition: crypto.h:172
unsigned char uint8_t
Definition: stdint.h:10
struct asn1_cursor raw
Raw certificate.
Definition: x509.h:198

References ctx, asn1_cursor::data, digest, digest_final(), digest_init(), digest_update(), asn1_cursor::len, and x509_certificate::raw.

Referenced by certstat(), x509_check_root(), x509_fingerprint_okx(), and x509_name().

◆ x509_check_root()

int x509_check_root ( struct x509_certificate cert,
struct x509_root root 
)

Check X.509 root certificate.

Parameters
certX.509 certificate
rootX.509 root certificate list
Return values
rcReturn status code

Definition at line 1246 of file x509.c.

1246  {
1247  struct digest_algorithm *digest = root->digest;
1248  uint8_t fingerprint[ digest->digestsize ];
1249  const uint8_t *root_fingerprint = root->fingerprints;
1250  unsigned int i;
1251 
1252  /* Calculate certificate fingerprint */
1253  x509_fingerprint ( cert, digest, fingerprint );
1254 
1255  /* Check fingerprint against all root certificates */
1256  for ( i = 0 ; i < root->count ; i++ ) {
1257  if ( memcmp ( fingerprint, root_fingerprint,
1258  sizeof ( fingerprint ) ) == 0 ) {
1259  DBGC ( cert, "X509 %p \"%s\" is a root certificate\n",
1260  cert, x509_name ( cert ) );
1261  return 0;
1262  }
1263  root_fingerprint += sizeof ( fingerprint );
1264  }
1265 
1266  DBGC2 ( cert, "X509 %p \"%s\" is not a root certificate\n",
1267  cert, x509_name ( cert ) );
1268  return -ENOENT;
1269 }
struct stp_switch root
Root switch.
Definition: stp.h:26
#define DBGC(...)
Definition: compiler.h:505
#define ENOENT
No such file or directory.
Definition: errno.h:514
struct md4_digest digest
Digest of data already processed.
Definition: md4.h:12
unsigned char uint8_t
Definition: stdint.h:10
void x509_fingerprint(struct x509_certificate *cert, struct digest_algorithm *digest, void *fingerprint)
Calculate X.509 certificate fingerprint.
Definition: x509.c:1228
const char * x509_name(struct x509_certificate *cert)
Get X.509 certificate display name.
Definition: x509.c:131
#define DBGC2(...)
Definition: compiler.h:522
A message digest algorithm.
Definition: crypto.h:16
int memcmp(const void *first, const void *second, size_t len)
Compare memory regions.
Definition: string.c:98

References DBGC, DBGC2, digest, ENOENT, memcmp(), root, x509_fingerprint(), and x509_name().

Referenced by x509_check_root_fail_okx(), x509_check_root_okx(), and x509_validate().

◆ x509_check_time()

int x509_check_time ( struct x509_certificate cert,
time_t  time 
)

Check X.509 certificate validity period.

Parameters
certX.509 certificate
timeTime at which to check certificate
Return values
rcReturn status code

Definition at line 1278 of file x509.c.

1278  {
1279  struct x509_validity *validity = &cert->validity;
1280 
1281  /* Check validity period */
1282  if ( validity->not_before.time > ( time + TIMESTAMP_ERROR_MARGIN ) ) {
1283  DBGC ( cert, "X509 %p \"%s\" is not yet valid (at time %lld)\n",
1284  cert, x509_name ( cert ), time );
1285  return -EACCES_EXPIRED;
1286  }
1287  if ( validity->not_after.time < ( time - TIMESTAMP_ERROR_MARGIN ) ) {
1288  DBGC ( cert, "X509 %p \"%s\" has expired (at time %lld)\n",
1289  cert, x509_name ( cert ), time );
1290  return -EACCES_EXPIRED;
1291  }
1292 
1293  DBGC2 ( cert, "X509 %p \"%s\" is valid (at time %lld)\n",
1294  cert, x509_name ( cert ), time );
1295  return 0;
1296 }
#define DBGC(...)
Definition: compiler.h:505
time_t time
Seconds since the Epoch.
Definition: x509.h:36
struct x509_time not_before
Not valid before.
Definition: x509.h:42
#define EACCES_EXPIRED
Definition: x509.c:92
An X.509 certificate validity period.
Definition: x509.h:40
struct x509_validity validity
Validity.
Definition: x509.h:210
const char * x509_name(struct x509_certificate *cert)
Get X.509 certificate display name.
Definition: x509.c:131
#define TIMESTAMP_ERROR_MARGIN
Margin of error (in seconds) allowed in signed timestamps.
Definition: crypto.h:51
#define DBGC2(...)
Definition: compiler.h:522
struct x509_time not_after
Not valid after.
Definition: x509.h:44
uint64_t time
Current time.
Definition: ntlm.h:20

References DBGC, DBGC2, EACCES_EXPIRED, x509_validity::not_after, x509_validity::not_before, time, x509_time::time, TIMESTAMP_ERROR_MARGIN, x509_certificate::validity, and x509_name().

Referenced by x509_check_time_fail_okx(), x509_check_time_okx(), and x509_validate().

◆ x509_validate()

int x509_validate ( struct x509_certificate cert,
struct x509_certificate issuer,
time_t  time,
struct x509_root root 
)

Validate X.509 certificate.

Parameters
certX.509 certificate
issuerIssuing X.509 certificate (or NULL)
timeTime at which to validate certificate
rootRoot certificate list, or NULL to use default
Return values
rcReturn status code

The issuing certificate must have already been validated.

Validation results are cached: if a certificate has already been successfully validated then issuer, time, and root will be ignored.

Definition at line 1313 of file x509.c.

1315  {
1316  unsigned int max_path_remaining;
1317  int rc;
1318 
1319  /* Use default root certificate store if none specified */
1320  if ( ! root )
1322 
1323  /* Return success if certificate has already been validated */
1324  if ( x509_is_valid ( cert ) )
1325  return 0;
1326 
1327  /* Fail if certificate is invalid at specified time */
1328  if ( ( rc = x509_check_time ( cert, time ) ) != 0 )
1329  return rc;
1330 
1331  /* Succeed if certificate is a trusted root certificate */
1332  if ( x509_check_root ( cert, root ) == 0 ) {
1333  cert->flags |= X509_FL_VALIDATED;
1334  cert->path_remaining = ( cert->extensions.basic.path_len + 1 );
1335  return 0;
1336  }
1337 
1338  /* Fail unless we have an issuer */
1339  if ( ! issuer ) {
1340  DBGC2 ( cert, "X509 %p \"%s\" has no issuer\n",
1341  cert, x509_name ( cert ) );
1342  return -EACCES_UNTRUSTED;
1343  }
1344 
1345  /* Fail unless issuer has already been validated */
1346  if ( ! x509_is_valid ( issuer ) ) {
1347  DBGC ( cert, "X509 %p \"%s\" ", cert, x509_name ( cert ) );
1348  DBGC ( cert, "issuer %p \"%s\" has not yet been validated\n",
1349  issuer, x509_name ( issuer ) );
1350  return -EACCES_OUT_OF_ORDER;
1351  }
1352 
1353  /* Fail if issuing certificate cannot validate this certificate */
1354  if ( ( rc = x509_check_issuer ( cert, issuer ) ) != 0 )
1355  return rc;
1356 
1357  /* Fail if path length constraint is violated */
1358  if ( issuer->path_remaining == 0 ) {
1359  DBGC ( cert, "X509 %p \"%s\" ", cert, x509_name ( cert ) );
1360  DBGC ( cert, "issuer %p \"%s\" path length exceeded\n",
1361  issuer, x509_name ( issuer ) );
1362  return -EACCES_PATH_LEN;
1363  }
1364 
1365  /* Fail if OCSP is required */
1366  if ( ocsp_required ( cert ) ) {
1367  DBGC ( cert, "X509 %p \"%s\" requires an OCSP check\n",
1368  cert, x509_name ( cert ) );
1369  return -EACCES_OCSP_REQUIRED;
1370  }
1371 
1372  /* Calculate effective path length */
1373  cert->path_remaining = ( issuer->path_remaining - 1 );
1374  max_path_remaining = ( cert->extensions.basic.path_len + 1 );
1375  if ( cert->path_remaining > max_path_remaining )
1376  cert->path_remaining = max_path_remaining;
1377 
1378  /* Mark certificate as valid */
1379  cert->flags |= X509_FL_VALIDATED;
1380 
1381  DBGC ( cert, "X509 %p \"%s\" successfully validated using ",
1382  cert, x509_name ( cert ) );
1383  DBGC ( cert, "issuer %p \"%s\"\n", issuer, x509_name ( issuer ) );
1384  return 0;
1385 }
struct arbelprm_rc_send_wqe rc
Definition: arbel.h:14
unsigned int path_remaining
Maximum number of subsequent certificates in chain.
Definition: x509.h:195
unsigned int path_len
Path length.
Definition: x509.h:80
struct stp_switch root
Root switch.
Definition: stp.h:26
struct x509_root root_certificates
Root certificates.
Definition: rootcert.c:73
#define DBGC(...)
Definition: compiler.h:505
static int ocsp_required(struct x509_certificate *cert)
Check if X.509 certificate requires an OCSP check.
Definition: ocsp.h:128
unsigned int flags
Flags.
Definition: x509.h:193
#define EACCES_OCSP_REQUIRED
Definition: x509.c:112
#define EACCES_OUT_OF_ORDER
Definition: x509.c:104
#define EACCES_PATH_LEN
Definition: x509.c:96
int x509_check_root(struct x509_certificate *cert, struct x509_root *root)
Check X.509 root certificate.
Definition: x509.c:1246
static int x509_is_valid(struct x509_certificate *cert)
Check if X.509 certificate is valid.
Definition: x509.h:391
Certificate has been validated.
Definition: x509.h:222
const char * x509_name(struct x509_certificate *cert)
Get X.509 certificate display name.
Definition: x509.c:131
#define DBGC2(...)
Definition: compiler.h:522
int x509_check_issuer(struct x509_certificate *cert, struct x509_certificate *issuer)
Check X.509 certificate against issuer certificate.
Definition: x509.c:1168
#define EACCES_UNTRUSTED
Definition: x509.c:100
uint64_t time
Current time.
Definition: ntlm.h:20
int x509_check_time(struct x509_certificate *cert, time_t time)
Check X.509 certificate validity period.
Definition: x509.c:1278
struct x509_basic_constraints basic
Basic constraints.
Definition: x509.h:157
struct x509_extensions extensions
Extensions.
Definition: x509.h:216

References x509_extensions::basic, DBGC, DBGC2, EACCES_OCSP_REQUIRED, EACCES_OUT_OF_ORDER, EACCES_PATH_LEN, EACCES_UNTRUSTED, x509_certificate::extensions, x509_certificate::flags, ocsp_required(), x509_basic_constraints::path_len, x509_certificate::path_remaining, rc, root, root_certificates, time, x509_check_issuer(), x509_check_root(), x509_check_time(), X509_FL_VALIDATED, x509_is_valid(), and x509_name().

Referenced by ocsp_validate(), and x509_validate_chain().

◆ x509_check_dnsname()

static int x509_check_dnsname ( struct x509_certificate cert,
const struct asn1_cursor raw,
const char *  name 
)
static

Check X.509 certificate alternative dNSName.

Parameters
certX.509 certificate
rawASN.1 cursor
nameName
Return values
rcReturn status code

Definition at line 1395 of file x509.c.

1397  {
1398  const char *fullname = name;
1399  const char *dnsname = raw->data;
1400  size_t len = raw->len;
1401 
1402  /* Check for wildcards */
1403  if ( ( len >= 2 ) && ( dnsname[0] == '*' ) && ( dnsname[1] == '.' ) ) {
1404 
1405  /* Skip initial "*." */
1406  dnsname += 2;
1407  len -= 2;
1408 
1409  /* Skip initial portion of name to be tested */
1410  name = strchr ( name, '.' );
1411  if ( ! name )
1412  return -ENOENT;
1413  name++;
1414  }
1415 
1416  /* Compare names */
1417  if ( ! ( ( strlen ( name ) == len ) &&
1418  ( memcmp ( name, dnsname, len ) == 0 ) ) )
1419  return -ENOENT;
1420 
1421  if ( name != fullname ) {
1422  DBGC2 ( cert, "X509 %p \"%s\" found wildcard match for "
1423  "\"*.%s\"\n", cert, x509_name ( cert ), name );
1424  }
1425  return 0;
1426 }
const char * name
Definition: ath9k_hw.c:1984
#define ENOENT
No such file or directory.
Definition: errno.h:514
char * strchr(const char *src, int character)
Find character within a string.
Definition: string.c:241
size_t strlen(const char *src)
Get length of string.
Definition: string.c:213
const char * x509_name(struct x509_certificate *cert)
Get X.509 certificate display name.
Definition: x509.c:131
uint32_t len
Length.
Definition: ena.h:14
#define DBGC2(...)
Definition: compiler.h:522
__be32 raw[7]
Definition: CIB_PRM.h:28
int memcmp(const void *first, const void *second, size_t len)
Compare memory regions.
Definition: string.c:98

References DBGC2, ENOENT, len, memcmp(), name, raw, strchr(), strlen(), and x509_name().

Referenced by x509_check_alt_name(), and x509_check_name().

◆ x509_check_ipaddress()

static int x509_check_ipaddress ( struct x509_certificate cert,
const struct asn1_cursor raw,
const char *  name 
)
static

Check X.509 certificate alternative iPAddress.

Parameters
certX.509 certificate
rawASN.1 cursor
nameName
Return values
rcReturn status code

Definition at line 1436 of file x509.c.

1438  {
1439  struct sockaddr sa;
1440  sa_family_t family;
1441  const void *address;
1442  int rc;
1443 
1444  /* Determine address family */
1445  if ( raw->len == sizeof ( struct in_addr ) ) {
1446  struct sockaddr_in *sin = ( ( struct sockaddr_in * ) &sa );
1447  family = AF_INET;
1448  address = &sin->sin_addr;
1449  } else if ( raw->len == sizeof ( struct in6_addr ) ) {
1450  struct sockaddr_in6 *sin6 = ( ( struct sockaddr_in6 * ) &sa );
1451  family = AF_INET6;
1452  address = &sin6->sin6_addr;
1453  } else {
1454  DBGC ( cert, "X509 %p \"%s\" has iPAddress with unexpected "
1455  "length %zd\n", cert, x509_name ( cert ), raw->len );
1456  DBGC_HDA ( cert, 0, raw->data, raw->len );
1457  return -EINVAL;
1458  }
1459 
1460  /* Attempt to convert name to a socket address */
1461  if ( ( rc = sock_aton ( name, &sa ) ) != 0 ) {
1462  DBGC2 ( cert, "X509 %p \"%s\" cannot parse \"%s\" as "
1463  "iPAddress: %s\n", cert, x509_name ( cert ), name,
1464  strerror ( rc ) );
1465  return rc;
1466  }
1467  if ( sa.sa_family != family )
1468  return -ENOENT;
1469 
1470  /* Compare addresses */
1471  if ( memcmp ( address, raw->data, raw->len ) != 0 )
1472  return -ENOENT;
1473 
1474  DBGC2 ( cert, "X509 %p \"%s\" found iPAddress match for \"%s\"\n",
1475  cert, x509_name ( cert ), sock_ntoa ( &sa ) );
1476  return 0;
1477 }
#define EINVAL
Invalid argument.
Definition: errno.h:428
struct arbelprm_rc_send_wqe rc
Definition: arbel.h:14
const char * name
Definition: ath9k_hw.c:1984
#define AF_INET6
IPv6 Internet addresses.
Definition: socket.h:64
struct sockaddr sa
Definition: dns.c:68
uint64_t address
Base address.
Definition: ena.h:24
sa_family_t sa_family
Socket address family.
Definition: socket.h:101
#define DBGC(...)
Definition: compiler.h:505
#define ENOENT
No such file or directory.
Definition: errno.h:514
IPv4 socket address.
Definition: in.h:82
int sock_aton(const char *string, struct sockaddr *sa)
Parse socket address.
Definition: socket.c:59
struct sockaddr_in sin
Definition: dns.c:70
#define DBGC_HDA(...)
Definition: compiler.h:506
uint16_t sa_family_t
A socket address family.
Definition: socket.h:85
IP6 address structure.
Definition: in.h:48
Generalized socket address structure.
Definition: socket.h:96
char * strerror(int errno)
Retrieve string representation of error number.
Definition: strerror.c:78
IP address structure.
Definition: in.h:39
struct in_addr sin_addr
IPv4 address.
Definition: in.h:98
const char * x509_name(struct x509_certificate *cert)
Get X.509 certificate display name.
Definition: x509.c:131
const char * sock_ntoa(struct sockaddr *sa)
Transcribe socket address.
Definition: socket.c:42
#define DBGC2(...)
Definition: compiler.h:522
struct sockaddr_in6 sin6
Definition: dns.c:71
__be32 raw[7]
Definition: CIB_PRM.h:28
IPv6 socket address.
Definition: in.h:115
int memcmp(const void *first, const void *second, size_t len)
Compare memory regions.
Definition: string.c:98
#define AF_INET
IPv4 Internet addresses.
Definition: socket.h:63
struct in6_addr sin6_addr
IPv6 address.
Definition: in.h:132

References address, AF_INET, AF_INET6, DBGC, DBGC2, DBGC_HDA, EINVAL, ENOENT, memcmp(), name, raw, rc, sa, sockaddr::sa_family, sin, sin6, sockaddr_in6::sin6_addr, sockaddr_in::sin_addr, sock_aton(), sock_ntoa(), strerror(), and x509_name().

Referenced by x509_check_alt_name().

◆ x509_check_alt_name()

static int x509_check_alt_name ( struct x509_certificate cert,
const struct asn1_cursor raw,
const char *  name 
)
static

Check X.509 certificate alternative name.

Parameters
certX.509 certificate
rawASN.1 cursor
nameName
Return values
rcReturn status code

Definition at line 1487 of file x509.c.

1489  {
1490  struct asn1_cursor alt_name;
1491  unsigned int type;
1492 
1493  /* Enter generalName */
1494  memcpy ( &alt_name, raw, sizeof ( alt_name ) );
1495  type = asn1_type ( &alt_name );
1496  asn1_enter_any ( &alt_name );
1497 
1498  /* Check this name */
1499  switch ( type ) {
1500  case X509_GENERAL_NAME_DNS :
1501  return x509_check_dnsname ( cert, &alt_name, name );
1502  case X509_GENERAL_NAME_IP :
1503  return x509_check_ipaddress ( cert, &alt_name, name );
1504  default:
1505  DBGC2 ( cert, "X509 %p \"%s\" unknown name of type %#02x:\n",
1506  cert, x509_name ( cert ), type );
1507  DBGC2_HDA ( cert, 0, alt_name.data, alt_name.len );
1508  return -ENOTSUP;
1509  }
1510 }
const char * name
Definition: ath9k_hw.c:1984
uint8_t type
Type.
Definition: ena.h:16
static unsigned int asn1_type(const struct asn1_cursor *cursor)
Extract ASN.1 type.
Definition: asn1.h:342
#define ENOTSUP
Operation not supported.
Definition: errno.h:589
void * memcpy(void *dest, const void *src, size_t len) __nonnull
static int x509_check_dnsname(struct x509_certificate *cert, const struct asn1_cursor *raw, const char *name)
Check X.509 certificate alternative dNSName.
Definition: x509.c:1395
#define DBGC2_HDA(...)
Definition: compiler.h:523
int asn1_enter_any(struct asn1_cursor *cursor)
Enter ASN.1 object of any type.
Definition: asn1.c:266
static int x509_check_ipaddress(struct x509_certificate *cert, const struct asn1_cursor *raw, const char *name)
Check X.509 certificate alternative iPAddress.
Definition: x509.c:1436
const char * x509_name(struct x509_certificate *cert)
Get X.509 certificate display name.
Definition: x509.c:131
#define DBGC2(...)
Definition: compiler.h:522
__be32 raw[7]
Definition: CIB_PRM.h:28
An ASN.1 object cursor.
Definition: asn1.h:19

References asn1_enter_any(), asn1_type(), asn1_cursor::data, DBGC2, DBGC2_HDA, ENOTSUP, asn1_cursor::len, memcpy(), name, raw, type, x509_check_dnsname(), x509_check_ipaddress(), X509_GENERAL_NAME_DNS, X509_GENERAL_NAME_IP, and x509_name().

Referenced by x509_check_name().

◆ x509_check_name()

int x509_check_name ( struct x509_certificate cert,
const char *  name 
)

Check X.509 certificate name.

Parameters
certX.509 certificate
nameName
Return values
rcReturn status code

Definition at line 1519 of file x509.c.

1519  {
1520  struct asn1_cursor *common_name = &cert->subject.common_name;
1521  struct asn1_cursor alt_name;
1522  int rc;
1523 
1524  /* Check commonName */
1525  if ( x509_check_dnsname ( cert, common_name, name ) == 0 ) {
1526  DBGC2 ( cert, "X509 %p \"%s\" commonName matches \"%s\"\n",
1527  cert, x509_name ( cert ), name );
1528  return 0;
1529  }
1530 
1531  /* Check any subjectAlternativeNames */
1532  memcpy ( &alt_name, &cert->extensions.alt_name.names,
1533  sizeof ( alt_name ) );
1534  for ( ; alt_name.len ; asn1_skip_any ( &alt_name ) ) {
1535  if ( ( rc = x509_check_alt_name ( cert, &alt_name,
1536  name ) ) == 0 ) {
1537  DBGC2 ( cert, "X509 %p \"%s\" subjectAltName matches "
1538  "\"%s\"\n", cert, x509_name ( cert ), name );
1539  return 0;
1540  }
1541  }
1542 
1543  DBGC ( cert, "X509 %p \"%s\" does not match name \"%s\"\n",
1544  cert, x509_name ( cert ), name );
1545  return -EACCES_WRONG_NAME;
1546 }
struct arbelprm_rc_send_wqe rc
Definition: arbel.h:14
const char * name
Definition: ath9k_hw.c:1984
struct asn1_cursor names
Names.
Definition: x509.h:144
static int x509_check_alt_name(struct x509_certificate *cert, const struct asn1_cursor *raw, const char *name)
Check X.509 certificate alternative name.
Definition: x509.c:1487
#define DBGC(...)
Definition: compiler.h:505
int asn1_skip_any(struct asn1_cursor *cursor)
Skip ASN.1 object of any type.
Definition: asn1.c:276
void * memcpy(void *dest, const void *src, size_t len) __nonnull
#define EACCES_WRONG_NAME
Definition: x509.c:116
static int x509_check_dnsname(struct x509_certificate *cert, const struct asn1_cursor *raw, const char *name)
Check X.509 certificate alternative dNSName.
Definition: x509.c:1395
struct x509_subject subject
Subject.
Definition: x509.h:212
struct asn1_cursor common_name
Common name.
Definition: x509.h:62
const char * x509_name(struct x509_certificate *cert)
Get X.509 certificate display name.
Definition: x509.c:131
struct x509_subject_alt_name alt_name
Subject alternative name.
Definition: x509.h:165
#define DBGC2(...)
Definition: compiler.h:522
An ASN.1 object cursor.
Definition: asn1.h:19
struct x509_extensions extensions
Extensions.
Definition: x509.h:216

References x509_extensions::alt_name, asn1_skip_any(), x509_subject::common_name, DBGC, DBGC2, EACCES_WRONG_NAME, x509_certificate::extensions, asn1_cursor::len, memcpy(), name, x509_subject_alt_name::names, rc, x509_certificate::subject, x509_check_alt_name(), x509_check_dnsname(), and x509_name().

Referenced by cert_exec(), cms_verify(), tls_validator_done(), x509_check_name_fail_okx(), and x509_check_name_okx().

◆ x509_free_chain()

static void x509_free_chain ( struct refcnt refcnt)
static

Free X.509 certificate chain.

Parameters
refcntReference count

Definition at line 1553 of file x509.c.

1553  {
1554  struct x509_chain *chain =
1555  container_of ( refcnt, struct x509_chain, refcnt );
1556  struct x509_link *link;
1557  struct x509_link *tmp;
1558 
1559  DBGC2 ( chain, "X509 chain %p freed\n", chain );
1560 
1561  /* Free each link in the chain */
1562  list_for_each_entry_safe ( link, tmp, &chain->links, list ) {
1563  x509_put ( link->cert );
1564  list_del ( &link->list );
1565  free ( link );
1566  }
1567 
1568  /* Free chain */
1569  free ( chain );
1570 }
struct list_head links
List of links.
Definition: x509.h:181
A reference counter.
Definition: refcnt.h:26
#define list_del(list)
Delete an entry from a list.
Definition: list.h:119
An X.509 certificate chain.
Definition: x509.h:177
#define container_of(ptr, type, field)
Get containing structure.
Definition: stddef.h:35
u32 link
Link to next descriptor.
Definition: ar9003_mac.h:68
#define list_for_each_entry_safe(pos, tmp, head, member)
Iterate over entries in a list, safe against deletion of the current entry.
Definition: list.h:447
static void(* free)(struct refcnt *refcnt))
Definition: refcnt.h:54
uint8_t * tmp
Definition: entropy.h:156
#define DBGC2(...)
Definition: compiler.h:522
static void x509_put(struct x509_certificate *cert)
Drop reference to X.509 certificate.
Definition: x509.h:247

References container_of, DBGC2, free, link, x509_chain::links, x509_link::list, list_del, list_for_each_entry_safe, tmp, and x509_put().

Referenced by x509_alloc_chain().

◆ x509_alloc_chain()

struct x509_chain* x509_alloc_chain ( void  )

Allocate X.509 certificate chain.

Return values
chainX.509 certificate chain, or NULL

Definition at line 1577 of file x509.c.

1577  {
1578  struct x509_chain *chain;
1579 
1580  /* Allocate chain */
1581  chain = zalloc ( sizeof ( *chain ) );
1582  if ( ! chain )
1583  return NULL;
1584 
1585  /* Initialise chain */
1586  ref_init ( &chain->refcnt, x509_free_chain );
1587  INIT_LIST_HEAD ( &chain->links );
1588 
1589  DBGC2 ( chain, "X509 chain %p allocated\n", chain );
1590  return chain;
1591 }
struct list_head links
List of links.
Definition: x509.h:181
#define ref_init(refcnt, free)
Initialise a reference counter.
Definition: refcnt.h:64
static void x509_free_chain(struct refcnt *refcnt)
Free X.509 certificate chain.
Definition: x509.c:1553
An X.509 certificate chain.
Definition: x509.h:177
void * zalloc(size_t size)
Allocate cleared memory.
Definition: malloc.c:624
#define INIT_LIST_HEAD(list)
Initialise a list head.
Definition: list.h:45
#define DBGC2(...)
Definition: compiler.h:522
#define NULL
NULL pointer (VOID *)
Definition: Base.h:362
struct refcnt refcnt
Reference count.
Definition: x509.h:179

References DBGC2, INIT_LIST_HEAD, x509_chain::links, NULL, ref_init, x509_chain::refcnt, x509_free_chain(), and zalloc().

Referenced by cms_parse(), cms_signature(), tls_parse_chain(), validator_append(), and x509_chain_okx().

◆ x509_append()

int x509_append ( struct x509_chain chain,
struct x509_certificate cert 
)

Append X.509 certificate to X.509 certificate chain.

Parameters
chainX.509 certificate chain
certX.509 certificate
Return values
rcReturn status code

Definition at line 1600 of file x509.c.

1600  {
1601  struct x509_link *link;
1602 
1603  /* Allocate link */
1604  link = zalloc ( sizeof ( *link ) );
1605  if ( ! link )
1606  return -ENOMEM;
1607 
1608  /* Add link to chain */
1609  link->cert = x509_get ( cert );
1610  list_add_tail ( &link->list, &chain->links );
1611  DBGC ( chain, "X509 chain %p added X509 %p \"%s\"\n",
1612  chain, cert, x509_name ( cert ) );
1613 
1614  return 0;
1615 }
static struct x509_certificate * x509_get(struct x509_certificate *cert)
Get reference to X.509 certificate.
Definition: x509.h:236
struct list_head links
List of links.
Definition: x509.h:181
#define DBGC(...)
Definition: compiler.h:505
#define ENOMEM
Not enough space.
Definition: errno.h:534
#define list_add_tail(new, head)
Add a new entry to the tail of a list.
Definition: list.h:93
u32 link
Link to next descriptor.
Definition: ar9003_mac.h:68
void * zalloc(size_t size)
Allocate cleared memory.
Definition: malloc.c:624
const char * x509_name(struct x509_certificate *cert)
Get X.509 certificate display name.
Definition: x509.c:131

References x509_link::cert, DBGC, ENOMEM, link, x509_chain::links, list_add_tail, x509_get(), x509_name(), and zalloc().

Referenced by cms_parse_signer_identifier(), x509_append_raw(), x509_auto_append(), and x509_chain_okx().

◆ x509_append_raw()

int x509_append_raw ( struct x509_chain chain,
const void *  data,
size_t  len 
)

Append X.509 certificate to X.509 certificate chain.

Parameters
chainX.509 certificate chain
dataRaw certificate data
lenLength of raw data
Return values
rcReturn status code

Definition at line 1625 of file x509.c.

1626  {
1627  struct x509_certificate *cert;
1628  int rc;
1629 
1630  /* Parse certificate */
1631  if ( ( rc = x509_certificate ( data, len, &cert ) ) != 0 )
1632  goto err_parse;
1633 
1634  /* Append certificate to chain */
1635  if ( ( rc = x509_append ( chain, cert ) ) != 0 )
1636  goto err_append;
1637 
1638  /* Drop reference to certificate */
1639  x509_put ( cert );
1640 
1641  return 0;
1642 
1643  err_append:
1644  x509_put ( cert );
1645  err_parse:
1646  return rc;
1647 }
struct arbelprm_rc_send_wqe rc
Definition: arbel.h:14
int x509_append(struct x509_chain *chain, struct x509_certificate *cert)
Append X.509 certificate to X.509 certificate chain.
Definition: x509.c:1600
An X.509 certificate.
Definition: x509.h:185
uint32_t len
Length.
Definition: ena.h:14
static void x509_put(struct x509_certificate *cert)
Drop reference to X.509 certificate.
Definition: x509.h:247
struct arbelprm_port_state_change_st data
Message.
Definition: arbel.h:12

References data, len, rc, x509_append(), and x509_put().

Referenced by cms_parse_certificates(), tls_parse_chain(), and validator_append().

◆ x509_find_subject()

static struct x509_certificate* x509_find_subject ( struct x509_chain certs,
const struct asn1_cursor subject 
)
static

Identify X.509 certificate by subject.

Parameters
certsX.509 certificate list
subjectSubject
Return values
certX.509 certificate, or NULL if not found

Definition at line 1657 of file x509.c.

1658  {
1659  struct x509_link *link;
1660  struct x509_certificate *cert;
1661 
1662  /* Scan through certificate list */
1663  list_for_each_entry ( link, &certs->links, list ) {
1664 
1665  /* Check subject */
1666  cert = link->cert;
1667  if ( asn1_compare ( subject, &cert->subject.raw ) == 0 )
1668  return cert;
1669  }
1670 
1671  return NULL;
1672 }
int asn1_compare(const struct asn1_cursor *cursor1, const struct asn1_cursor *cursor2)
Compare two ASN.1 objects.
Definition: asn1.c:443
struct list_head links
List of links.
Definition: x509.h:181
#define list_for_each_entry(pos, head, member)
Iterate over entries in a list.
Definition: list.h:420
u32 link
Link to next descriptor.
Definition: ar9003_mac.h:68
An X.509 certificate.
Definition: x509.h:185
struct x509_subject subject
Subject.
Definition: x509.h:212
struct asn1_cursor raw
Raw subject.
Definition: x509.h:60
#define NULL
NULL pointer (VOID *)
Definition: Base.h:362

References asn1_compare(), link, x509_chain::links, list_for_each_entry, NULL, x509_subject::raw, and x509_certificate::subject.

Referenced by x509_auto_append().

◆ x509_auto_append()

int x509_auto_append ( struct x509_chain chain,
struct x509_chain certs 
)

Append X.509 certificates to X.509 certificate chain.

Parameters
chainX.509 certificate chain
certsX.509 certificate list
Return values
rcReturn status code

Certificates will be automatically appended to the chain based upon the subject and issuer names.

Definition at line 1684 of file x509.c.

1684  {
1685  struct x509_certificate *cert;
1686  struct x509_certificate *previous;
1687  int rc;
1688 
1689  /* Get current certificate */
1690  cert = x509_last ( chain );
1691  if ( ! cert ) {
1692  DBGC ( chain, "X509 chain %p has no certificates\n", chain );
1693  return -EACCES_EMPTY;
1694  }
1695 
1696  /* Append certificates, in order */
1697  while ( 1 ) {
1698 
1699  /* Find issuing certificate */
1700  previous = cert;
1701  cert = x509_find_subject ( certs, &cert->issuer.raw );
1702  if ( ! cert )
1703  break;
1704  if ( cert == previous )
1705  break;
1706 
1707  /* Append certificate to chain */
1708  if ( ( rc = x509_append ( chain, cert ) ) != 0 )
1709  return rc;
1710  }
1711 
1712  return 0;
1713 }
struct arbelprm_rc_send_wqe rc
Definition: arbel.h:14
struct asn1_cursor raw
Raw issuer.
Definition: x509.h:30
#define EACCES_EMPTY
Definition: x509.c:108
struct x509_issuer issuer
Issuer.
Definition: x509.h:208
#define DBGC(...)
Definition: compiler.h:505
int x509_append(struct x509_chain *chain, struct x509_certificate *cert)
Append X.509 certificate to X.509 certificate chain.
Definition: x509.c:1600
static struct x509_certificate * x509_last(struct x509_chain *chain)
Get last certificate in X.509 certificate chain.
Definition: x509.h:294
An X.509 certificate.
Definition: x509.h:185
static struct x509_certificate * x509_find_subject(struct x509_chain *certs, const struct asn1_cursor *subject)
Identify X.509 certificate by subject.
Definition: x509.c:1657

References DBGC, EACCES_EMPTY, x509_certificate::issuer, x509_issuer::raw, rc, x509_append(), x509_find_subject(), and x509_last().

Referenced by cms_parse_signer_identifier(), validator_append(), and x509_validate_chain().

◆ x509_validate_chain()

int x509_validate_chain ( struct x509_chain chain,
time_t  time,
struct x509_chain store,
struct x509_root root 
)

Validate X.509 certificate chain.

Parameters
chainX.509 certificate chain
timeTime at which to validate certificates
storeCertificate store, or NULL to use default
rootRoot certificate list, or NULL to use default
Return values
rcReturn status code

Definition at line 1724 of file x509.c.

1725  {
1726  struct x509_certificate *issuer = NULL;
1727  struct x509_link *link;
1728  int rc;
1729 
1730  /* Use default certificate store if none specified */
1731  if ( ! store )
1732  store = &certstore;
1733 
1734  /* Append any applicable certificates from the certificate store */
1735  if ( ( rc = x509_auto_append ( chain, store ) ) != 0 )
1736  return rc;
1737 
1738  /* Find first certificate that can be validated as a
1739  * standalone (i.e. is already valid, or can be validated as
1740  * a trusted root certificate).
1741  */
1742  list_for_each_entry ( link, &chain->links, list ) {
1743 
1744  /* Try validating this certificate as a standalone */
1745  if ( ( rc = x509_validate ( link->cert, NULL, time,
1746  root ) ) != 0 )
1747  continue;
1748 
1749  /* Work back up to start of chain, performing pairwise
1750  * validation.
1751  */
1752  issuer = link->cert;
1754  list ) {
1755 
1756  /* Validate this certificate against its issuer */
1757  if ( ( rc = x509_validate ( link->cert, issuer, time,
1758  root ) ) != 0 )
1759  return rc;
1760  issuer = link->cert;
1761  }
1762 
1763  return 0;
1764  }
1765 
1766  DBGC ( chain, "X509 chain %p found no usable certificates\n", chain );
1767  return -EACCES_USELESS;
1768 }
struct arbelprm_rc_send_wqe rc
Definition: arbel.h:14
struct x509_chain certstore
Certificate store.
Definition: certstore.c:73
struct stp_switch root
Root switch.
Definition: stp.h:26
struct list_head links
List of links.
Definition: x509.h:181
struct x509_issuer issuer
Issuer.
Definition: x509.h:208
#define DBGC(...)
Definition: compiler.h:505
#define list_for_each_entry(pos, head, member)
Iterate over entries in a list.
Definition: list.h:420
int x509_validate(struct x509_certificate *cert, struct x509_certificate *issuer, time_t time, struct x509_root *root)
Validate X.509 certificate.
Definition: x509.c:1313
u32 link
Link to next descriptor.
Definition: ar9003_mac.h:68
An X.509 certificate.
Definition: x509.h:185
#define list_for_each_entry_continue_reverse(pos, head, member)
Iterate over entries in a list in reverse, starting after current position.
Definition: list.h:475
int x509_auto_append(struct x509_chain *chain, struct x509_chain *certs)
Append X.509 certificates to X.509 certificate chain.
Definition: x509.c:1684
#define EACCES_USELESS
Definition: x509.c:120
uint64_t time
Current time.
Definition: ntlm.h:20
#define NULL
NULL pointer (VOID *)
Definition: Base.h:362

References certstore, DBGC, EACCES_USELESS, x509_certificate::issuer, link, x509_chain::links, x509_link::list, list_for_each_entry, list_for_each_entry_continue_reverse, NULL, rc, root, time, x509_auto_append(), and x509_validate().

Referenced by cms_verify_signer_info(), validator_step(), x509_validate_chain_fail_okx(), and x509_validate_chain_okx().

◆ image_x509()

int image_x509 ( struct image image,
size_t  offset,
struct x509_certificate **  cert 
)

Extract X.509 certificate object from image.

Parameters
imageImage
offsetOffset within image
Return values
certX.509 certificate
nextOffset to next image, or negative error

On success, the caller holds a reference to the X.509 certificate, and is responsible for ultimately calling x509_put().

Definition at line 1781 of file x509.c.

1782  {
1783  struct asn1_cursor *cursor;
1784  int next;
1785  int rc;
1786 
1787  /* Get ASN.1 object */
1788  next = image_asn1 ( image, offset, &cursor );
1789  if ( next < 0 ) {
1790  rc = next;
1791  goto err_asn1;
1792  }
1793 
1794  /* Parse certificate */
1795  if ( ( rc = x509_certificate ( cursor->data, cursor->len,
1796  cert ) ) != 0 )
1797  goto err_certificate;
1798 
1799  /* Free ASN.1 object */
1800  free ( cursor );
1801 
1802  return next;
1803 
1804  x509_put ( *cert );
1805  err_certificate:
1806  free ( cursor );
1807  err_asn1:
1808  return rc;
1809 }
struct arbelprm_rc_send_wqe rc
Definition: arbel.h:14
uint32_t next
Next descriptor address.
Definition: myson.h:18
const void * data
Start of data.
Definition: asn1.h:21
int image_asn1(struct image *image, size_t offset, struct asn1_cursor **cursor)
Extract ASN.1 object from image.
Definition: asn1.c:854
An executable image.
Definition: image.h:24
size_t len
Length of data.
Definition: asn1.h:23
static userptr_t size_t offset
Offset of the first segment within the content.
Definition: deflate.h:259
An X.509 certificate.
Definition: x509.h:185
static void(* free)(struct refcnt *refcnt))
Definition: refcnt.h:54
static void x509_put(struct x509_certificate *cert)
Drop reference to X.509 certificate.
Definition: x509.h:247
An ASN.1 object cursor.
Definition: asn1.h:19

References asn1_cursor::data, free, image_asn1(), asn1_cursor::len, next, offset, rc, and x509_put().

Referenced by cert_exec().

◆ REQUIRING_SYMBOL()

REQUIRING_SYMBOL ( x509_validate  )

◆ REQUIRE_OBJECT() [1/2]

REQUIRE_OBJECT ( certstore  )

◆ REQUIRE_OBJECT() [2/2]

REQUIRE_OBJECT ( config_crypto  )

Variable Documentation

◆ oid_common_name

uint8_t oid_common_name[] = { ASN1_OID_COMMON_NAME }
static

"commonName" object identifier

Definition at line 155 of file x509.c.

◆ oid_common_name_cursor

struct asn1_cursor oid_common_name_cursor
static
Initial value:
=
#define ASN1_OID_CURSOR(oid_value)
Define an ASN.1 cursor containing an OID.
Definition: asn1.h:292
static uint8_t oid_common_name[]
"commonName" object identifier
Definition: x509.c:155

"commonName" object identifier cursor

Definition at line 158 of file x509.c.

Referenced by x509_parse_common_name().

◆ oid_code_signing

uint8_t oid_code_signing[] = { ASN1_OID_CODESIGNING }
static

"id-kp-codeSigning" object identifier

Definition at line 516 of file x509.c.

◆ oid_ocsp_signing

uint8_t oid_ocsp_signing[] = { ASN1_OID_OCSPSIGNING }
static

"id-kp-OCSPSigning" object identifier

Definition at line 519 of file x509.c.

◆ x509_key_purposes

struct x509_key_purpose x509_key_purposes[]
static
Initial value:
= {
{
.name = "codeSigning",
},
{
.name = "ocspSigning",
},
}
#define ASN1_OID_CURSOR(oid_value)
Define an ASN.1 cursor containing an OID.
Definition: asn1.h:292
static uint8_t oid_code_signing[]
"id-kp-codeSigning" object identifier
Definition: x509.c:516
static uint8_t oid_ocsp_signing[]
"id-kp-OCSPSigning" object identifier
Definition: x509.c:519

Supported key purposes.

Definition at line 522 of file x509.c.

Referenced by x509_parse_key_purpose().

◆ oid_ad_ocsp

uint8_t oid_ad_ocsp[] = { ASN1_OID_OCSP }
static

"id-ad-ocsp" object identifier

Definition at line 628 of file x509.c.

◆ x509_access_methods

struct x509_access_method x509_access_methods[]
static
Initial value:
= {
{
.name = "OCSP",
.parse = x509_parse_ocsp,
},
}
static int x509_parse_ocsp(struct x509_certificate *cert, const struct asn1_cursor *raw)
Parse X.509 certificate OCSP access method.
Definition: x509.c:607
#define ASN1_OID_CURSOR(oid_value)
Define an ASN.1 cursor containing an OID.
Definition: asn1.h:292
static uint8_t oid_ad_ocsp[]
"id-ad-ocsp" object identifier
Definition: x509.c:628

Supported access methods.

Definition at line 631 of file x509.c.

Referenced by x509_find_access_method().

◆ oid_ce_basic_constraints

uint8_t oid_ce_basic_constraints[]
static
Initial value:
=
#define ASN1_OID_BASICCONSTRAINTS
ASN.1 OID for id-ce-basicConstraints (2.5.29.19)
Definition: asn1.h:235

"id-ce-basicConstraints" object identifier

Definition at line 748 of file x509.c.

◆ oid_ce_key_usage

uint8_t oid_ce_key_usage[]
static
Initial value:
=
#define ASN1_OID_KEYUSAGE
ASN.1 OID for id-ce-keyUsage (2.5.29.15)
Definition: asn1.h:230

"id-ce-keyUsage" object identifier

Definition at line 752 of file x509.c.

◆ oid_ce_ext_key_usage

uint8_t oid_ce_ext_key_usage[]
static
Initial value:
=
#define ASN1_OID_EXTKEYUSAGE
ASN.1 OID for id-ce-extKeyUsage (2.5.29.37)
Definition: asn1.h:240

"id-ce-extKeyUsage" object identifier

Definition at line 756 of file x509.c.

◆ oid_pe_authority_info_access

uint8_t oid_pe_authority_info_access[]
static
Initial value:
=
#define ASN1_OID_AUTHORITYINFOACCESS
ASN.1 OID for id-pe-authorityInfoAccess (1.3.6.1.5.5.7.1.1)
Definition: asn1.h:258

"id-pe-authorityInfoAccess" object identifier

Definition at line 760 of file x509.c.

◆ oid_ce_subject_alt_name

uint8_t oid_ce_subject_alt_name[]
static
Initial value:
=
#define ASN1_OID_SUBJECTALTNAME
ASN.1 OID for id-ce-subjectAltName (2.5.29.17)
Definition: asn1.h:287

"id-ce-subjectAltName" object identifier

Definition at line 764 of file x509.c.

◆ x509_extensions

Initial value:
= {
{
.name = "basicConstraints",
},
{
.name = "keyUsage",
},
{
.name = "extKeyUsage",
},
{
.name = "authorityInfoAccess",
},
{
.name = "subjectAltName",
},
}
static int x509_parse_key_usage(struct x509_certificate *cert, const struct asn1_cursor *raw)
Parse X.509 certificate key usage.
Definition: x509.c:483
static uint8_t oid_ce_basic_constraints[]
"id-ce-basicConstraints" object identifier
Definition: x509.c:748
static int x509_parse_basic_constraints(struct x509_certificate *cert, const struct asn1_cursor *raw)
Parse X.509 certificate basic constraints.
Definition: x509.c:421
static int x509_parse_extended_key_usage(struct x509_certificate *cert, const struct asn1_cursor *raw)
Parse X.509 certificate extended key usage.
Definition: x509.c:581
#define ASN1_OID_CURSOR(oid_value)
Define an ASN.1 cursor containing an OID.
Definition: asn1.h:292
static uint8_t oid_ce_subject_alt_name[]
"id-ce-subjectAltName" object identifier
Definition: x509.c:764
static uint8_t oid_pe_authority_info_access[]
"id-pe-authorityInfoAccess" object identifier
Definition: x509.c:760
static int x509_parse_subject_alt_name(struct x509_certificate *cert, const struct asn1_cursor *raw)
Parse X.509 certificate subject alternative name.
Definition: x509.c:727
static int x509_parse_authority_info_access(struct x509_certificate *cert, const struct asn1_cursor *raw)
Parse X.509 certificate authority information access.
Definition: x509.c:700
static uint8_t oid_ce_key_usage[]
"id-ce-keyUsage" object identifier
Definition: x509.c:752
static uint8_t oid_ce_ext_key_usage[]
"id-ce-extKeyUsage" object identifier
Definition: x509.c:756

Supported certificate extensions.

Definition at line 768 of file x509.c.

Referenced by x509_find_extension().