• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 // SPDX-License-Identifier: GPL-2.0-or-later
2 /* X.509 certificate parser
3  *
4  * Copyright (C) 2012 Red Hat, Inc. All Rights Reserved.
5  * Written by David Howells (dhowells@redhat.com)
6  */
7 
8 #define pr_fmt(fmt) "X.509: "fmt
9 #include <linux/kernel.h>
10 #ifndef __UBOOT__
11 #include <linux/export.h>
12 #include <linux/slab.h>
13 #endif
14 #include <linux/err.h>
15 #include <linux/oid_registry.h>
16 #ifdef __UBOOT__
17 #include <linux/string.h>
18 #endif
19 #include <crypto/public_key.h>
20 #include "x509_parser.h"
21 #include "x509.asn1.h"
22 #include "x509_akid.asn1.h"
23 
24 struct x509_parse_context {
25 	struct x509_certificate	*cert;		/* Certificate being constructed */
26 	unsigned long	data;			/* Start of data */
27 	const void	*cert_start;		/* Start of cert content */
28 	const void	*key;			/* Key data */
29 	size_t		key_size;		/* Size of key data */
30 	const void	*params;		/* Key parameters */
31 	size_t		params_size;		/* Size of key parameters */
32 	enum OID	key_algo;		/* Public key algorithm */
33 	enum OID	last_oid;		/* Last OID encountered */
34 	enum OID	algo_oid;		/* Algorithm OID */
35 	unsigned char	nr_mpi;			/* Number of MPIs stored */
36 	u8		o_size;			/* Size of organizationName (O) */
37 	u8		cn_size;		/* Size of commonName (CN) */
38 	u8		email_size;		/* Size of emailAddress */
39 	u16		o_offset;		/* Offset of organizationName (O) */
40 	u16		cn_offset;		/* Offset of commonName (CN) */
41 	u16		email_offset;		/* Offset of emailAddress */
42 	unsigned	raw_akid_size;
43 	const void	*raw_akid;		/* Raw authorityKeyId in ASN.1 */
44 	const void	*akid_raw_issuer;	/* Raw directoryName in authorityKeyId */
45 	unsigned	akid_raw_issuer_size;
46 };
47 
48 /*
49  * Free an X.509 certificate
50  */
x509_free_certificate(struct x509_certificate * cert)51 void x509_free_certificate(struct x509_certificate *cert)
52 {
53 	if (cert) {
54 		public_key_free(cert->pub);
55 		public_key_signature_free(cert->sig);
56 		kfree(cert->issuer);
57 		kfree(cert->subject);
58 		kfree(cert->id);
59 		kfree(cert->skid);
60 		kfree(cert);
61 	}
62 }
63 EXPORT_SYMBOL_GPL(x509_free_certificate);
64 
65 /*
66  * Parse an X.509 certificate
67  */
x509_cert_parse(const void * data,size_t datalen)68 struct x509_certificate *x509_cert_parse(const void *data, size_t datalen)
69 {
70 	struct x509_certificate *cert;
71 	struct x509_parse_context *ctx;
72 	struct asymmetric_key_id *kid;
73 	long ret;
74 
75 	ret = -ENOMEM;
76 	cert = kzalloc(sizeof(struct x509_certificate), GFP_KERNEL);
77 	if (!cert)
78 		goto error_no_cert;
79 	cert->pub = kzalloc(sizeof(struct public_key), GFP_KERNEL);
80 	if (!cert->pub)
81 		goto error_no_ctx;
82 	cert->sig = kzalloc(sizeof(struct public_key_signature), GFP_KERNEL);
83 	if (!cert->sig)
84 		goto error_no_ctx;
85 	ctx = kzalloc(sizeof(struct x509_parse_context), GFP_KERNEL);
86 	if (!ctx)
87 		goto error_no_ctx;
88 
89 	ctx->cert = cert;
90 	ctx->data = (unsigned long)data;
91 
92 	/* Attempt to decode the certificate */
93 	ret = asn1_ber_decoder(&x509_decoder, ctx, data, datalen);
94 	if (ret < 0)
95 		goto error_decode;
96 
97 	/* Decode the AuthorityKeyIdentifier */
98 	if (ctx->raw_akid) {
99 		pr_devel("AKID: %u %*phN\n",
100 			 ctx->raw_akid_size, ctx->raw_akid_size, ctx->raw_akid);
101 		ret = asn1_ber_decoder(&x509_akid_decoder, ctx,
102 				       ctx->raw_akid, ctx->raw_akid_size);
103 		if (ret < 0) {
104 			pr_warn("Couldn't decode AuthKeyIdentifier\n");
105 			goto error_decode;
106 		}
107 	}
108 
109 	ret = -ENOMEM;
110 	cert->pub->key = kmemdup(ctx->key, ctx->key_size, GFP_KERNEL);
111 	if (!cert->pub->key)
112 		goto error_decode;
113 
114 	cert->pub->keylen = ctx->key_size;
115 
116 	cert->pub->params = kmemdup(ctx->params, ctx->params_size, GFP_KERNEL);
117 	if (!cert->pub->params)
118 		goto error_decode;
119 
120 	cert->pub->paramlen = ctx->params_size;
121 	cert->pub->algo = ctx->key_algo;
122 
123 	/* Grab the signature bits */
124 	ret = x509_get_sig_params(cert);
125 	if (ret < 0)
126 		goto error_decode;
127 
128 	/* Generate cert issuer + serial number key ID */
129 	kid = asymmetric_key_generate_id(cert->raw_serial,
130 					 cert->raw_serial_size,
131 					 cert->raw_issuer,
132 					 cert->raw_issuer_size);
133 	if (IS_ERR(kid)) {
134 		ret = PTR_ERR(kid);
135 		goto error_decode;
136 	}
137 	cert->id = kid;
138 
139 #ifndef __UBOOT__
140 	/* Detect self-signed certificates */
141 	ret = x509_check_for_self_signed(cert);
142 	if (ret < 0)
143 		goto error_decode;
144 #endif
145 
146 	kfree(ctx);
147 	return cert;
148 
149 error_decode:
150 	kfree(ctx);
151 error_no_ctx:
152 	x509_free_certificate(cert);
153 error_no_cert:
154 	return ERR_PTR(ret);
155 }
156 EXPORT_SYMBOL_GPL(x509_cert_parse);
157 
158 /*
159  * Note an OID when we find one for later processing when we know how
160  * to interpret it.
161  */
x509_note_OID(void * context,size_t hdrlen,unsigned char tag,const void * value,size_t vlen)162 int x509_note_OID(void *context, size_t hdrlen,
163 	     unsigned char tag,
164 	     const void *value, size_t vlen)
165 {
166 	struct x509_parse_context *ctx = context;
167 
168 	ctx->last_oid = look_up_OID(value, vlen);
169 	if (ctx->last_oid == OID__NR) {
170 		char buffer[50];
171 		sprint_oid(value, vlen, buffer, sizeof(buffer));
172 		pr_debug("Unknown OID: [%lu] %s\n",
173 			 (unsigned long)value - ctx->data, buffer);
174 	}
175 	return 0;
176 }
177 
178 /*
179  * Save the position of the TBS data so that we can check the signature over it
180  * later.
181  */
x509_note_tbs_certificate(void * context,size_t hdrlen,unsigned char tag,const void * value,size_t vlen)182 int x509_note_tbs_certificate(void *context, size_t hdrlen,
183 			      unsigned char tag,
184 			      const void *value, size_t vlen)
185 {
186 	struct x509_parse_context *ctx = context;
187 
188 	pr_debug("x509_note_tbs_certificate(,%zu,%02x,%ld,%zu)!\n",
189 		 hdrlen, tag, (unsigned long)value - ctx->data, vlen);
190 
191 	ctx->cert->tbs = value - hdrlen;
192 	ctx->cert->tbs_size = vlen + hdrlen;
193 	return 0;
194 }
195 
196 /*
197  * Record the public key algorithm
198  */
x509_note_pkey_algo(void * context,size_t hdrlen,unsigned char tag,const void * value,size_t vlen)199 int x509_note_pkey_algo(void *context, size_t hdrlen,
200 			unsigned char tag,
201 			const void *value, size_t vlen)
202 {
203 	struct x509_parse_context *ctx = context;
204 
205 	pr_debug("PubKey Algo: %u\n", ctx->last_oid);
206 
207 	switch (ctx->last_oid) {
208 	case OID_md2WithRSAEncryption:
209 	case OID_md3WithRSAEncryption:
210 	default:
211 		return -ENOPKG; /* Unsupported combination */
212 
213 	case OID_md4WithRSAEncryption:
214 		ctx->cert->sig->hash_algo = "md4";
215 		goto rsa_pkcs1;
216 
217 	case OID_sha1WithRSAEncryption:
218 		ctx->cert->sig->hash_algo = "sha1";
219 		goto rsa_pkcs1;
220 
221 	case OID_sha256WithRSAEncryption:
222 		ctx->cert->sig->hash_algo = "sha256";
223 		goto rsa_pkcs1;
224 
225 	case OID_sha384WithRSAEncryption:
226 		ctx->cert->sig->hash_algo = "sha384";
227 		goto rsa_pkcs1;
228 
229 	case OID_sha512WithRSAEncryption:
230 		ctx->cert->sig->hash_algo = "sha512";
231 		goto rsa_pkcs1;
232 
233 	case OID_sha224WithRSAEncryption:
234 		ctx->cert->sig->hash_algo = "sha224";
235 		goto rsa_pkcs1;
236 
237 	case OID_gost2012Signature256:
238 		ctx->cert->sig->hash_algo = "streebog256";
239 		goto ecrdsa;
240 
241 	case OID_gost2012Signature512:
242 		ctx->cert->sig->hash_algo = "streebog512";
243 		goto ecrdsa;
244 	}
245 
246 rsa_pkcs1:
247 	ctx->cert->sig->pkey_algo = "rsa";
248 	ctx->cert->sig->encoding = "pkcs1";
249 	ctx->algo_oid = ctx->last_oid;
250 	return 0;
251 ecrdsa:
252 	ctx->cert->sig->pkey_algo = "ecrdsa";
253 	ctx->cert->sig->encoding = "raw";
254 	ctx->algo_oid = ctx->last_oid;
255 	return 0;
256 }
257 
258 /*
259  * Note the whereabouts and type of the signature.
260  */
x509_note_signature(void * context,size_t hdrlen,unsigned char tag,const void * value,size_t vlen)261 int x509_note_signature(void *context, size_t hdrlen,
262 			unsigned char tag,
263 			const void *value, size_t vlen)
264 {
265 	struct x509_parse_context *ctx = context;
266 
267 	pr_debug("Signature type: %u size %zu\n", ctx->last_oid, vlen);
268 
269 	if (ctx->last_oid != ctx->algo_oid) {
270 		pr_warn("Got cert with pkey (%u) and sig (%u) algorithm OIDs\n",
271 			ctx->algo_oid, ctx->last_oid);
272 		return -EINVAL;
273 	}
274 
275 	if (strcmp(ctx->cert->sig->pkey_algo, "rsa") == 0 ||
276 	    strcmp(ctx->cert->sig->pkey_algo, "ecrdsa") == 0) {
277 		/* Discard the BIT STRING metadata */
278 		if (vlen < 1 || *(const u8 *)value != 0)
279 			return -EBADMSG;
280 
281 		value++;
282 		vlen--;
283 	}
284 
285 	ctx->cert->raw_sig = value;
286 	ctx->cert->raw_sig_size = vlen;
287 	return 0;
288 }
289 
290 /*
291  * Note the certificate serial number
292  */
x509_note_serial(void * context,size_t hdrlen,unsigned char tag,const void * value,size_t vlen)293 int x509_note_serial(void *context, size_t hdrlen,
294 		     unsigned char tag,
295 		     const void *value, size_t vlen)
296 {
297 	struct x509_parse_context *ctx = context;
298 	ctx->cert->raw_serial = value;
299 	ctx->cert->raw_serial_size = vlen;
300 	return 0;
301 }
302 
303 /*
304  * Note some of the name segments from which we'll fabricate a name.
305  */
x509_extract_name_segment(void * context,size_t hdrlen,unsigned char tag,const void * value,size_t vlen)306 int x509_extract_name_segment(void *context, size_t hdrlen,
307 			      unsigned char tag,
308 			      const void *value, size_t vlen)
309 {
310 	struct x509_parse_context *ctx = context;
311 
312 	switch (ctx->last_oid) {
313 	case OID_commonName:
314 		ctx->cn_size = vlen;
315 		ctx->cn_offset = (unsigned long)value - ctx->data;
316 		break;
317 	case OID_organizationName:
318 		ctx->o_size = vlen;
319 		ctx->o_offset = (unsigned long)value - ctx->data;
320 		break;
321 	case OID_email_address:
322 		ctx->email_size = vlen;
323 		ctx->email_offset = (unsigned long)value - ctx->data;
324 		break;
325 	default:
326 		break;
327 	}
328 
329 	return 0;
330 }
331 
332 /*
333  * Fabricate and save the issuer and subject names
334  */
x509_fabricate_name(struct x509_parse_context * ctx,size_t hdrlen,unsigned char tag,char ** _name,size_t vlen)335 static int x509_fabricate_name(struct x509_parse_context *ctx, size_t hdrlen,
336 			       unsigned char tag,
337 			       char **_name, size_t vlen)
338 {
339 	const void *name, *data = (const void *)ctx->data;
340 	size_t namesize;
341 	char *buffer;
342 
343 	if (*_name)
344 		return -EINVAL;
345 
346 	/* Empty name string if no material */
347 	if (!ctx->cn_size && !ctx->o_size && !ctx->email_size) {
348 		buffer = kmalloc(1, GFP_KERNEL);
349 		if (!buffer)
350 			return -ENOMEM;
351 		buffer[0] = 0;
352 		goto done;
353 	}
354 
355 	if (ctx->cn_size && ctx->o_size) {
356 		/* Consider combining O and CN, but use only the CN if it is
357 		 * prefixed by the O, or a significant portion thereof.
358 		 */
359 		namesize = ctx->cn_size;
360 		name = data + ctx->cn_offset;
361 		if (ctx->cn_size >= ctx->o_size &&
362 		    memcmp(data + ctx->cn_offset, data + ctx->o_offset,
363 			   ctx->o_size) == 0)
364 			goto single_component;
365 		if (ctx->cn_size >= 7 &&
366 		    ctx->o_size >= 7 &&
367 		    memcmp(data + ctx->cn_offset, data + ctx->o_offset, 7) == 0)
368 			goto single_component;
369 
370 		buffer = kmalloc(ctx->o_size + 2 + ctx->cn_size + 1,
371 				 GFP_KERNEL);
372 		if (!buffer)
373 			return -ENOMEM;
374 
375 		memcpy(buffer,
376 		       data + ctx->o_offset, ctx->o_size);
377 		buffer[ctx->o_size + 0] = ':';
378 		buffer[ctx->o_size + 1] = ' ';
379 		memcpy(buffer + ctx->o_size + 2,
380 		       data + ctx->cn_offset, ctx->cn_size);
381 		buffer[ctx->o_size + 2 + ctx->cn_size] = 0;
382 		goto done;
383 
384 	} else if (ctx->cn_size) {
385 		namesize = ctx->cn_size;
386 		name = data + ctx->cn_offset;
387 	} else if (ctx->o_size) {
388 		namesize = ctx->o_size;
389 		name = data + ctx->o_offset;
390 	} else {
391 		namesize = ctx->email_size;
392 		name = data + ctx->email_offset;
393 	}
394 
395 single_component:
396 	buffer = kmalloc(namesize + 1, GFP_KERNEL);
397 	if (!buffer)
398 		return -ENOMEM;
399 	memcpy(buffer, name, namesize);
400 	buffer[namesize] = 0;
401 
402 done:
403 	*_name = buffer;
404 	ctx->cn_size = 0;
405 	ctx->o_size = 0;
406 	ctx->email_size = 0;
407 	return 0;
408 }
409 
x509_note_issuer(void * context,size_t hdrlen,unsigned char tag,const void * value,size_t vlen)410 int x509_note_issuer(void *context, size_t hdrlen,
411 		     unsigned char tag,
412 		     const void *value, size_t vlen)
413 {
414 	struct x509_parse_context *ctx = context;
415 	ctx->cert->raw_issuer = value;
416 	ctx->cert->raw_issuer_size = vlen;
417 	return x509_fabricate_name(ctx, hdrlen, tag, &ctx->cert->issuer, vlen);
418 }
419 
x509_note_subject(void * context,size_t hdrlen,unsigned char tag,const void * value,size_t vlen)420 int x509_note_subject(void *context, size_t hdrlen,
421 		      unsigned char tag,
422 		      const void *value, size_t vlen)
423 {
424 	struct x509_parse_context *ctx = context;
425 	ctx->cert->raw_subject = value;
426 	ctx->cert->raw_subject_size = vlen;
427 	return x509_fabricate_name(ctx, hdrlen, tag, &ctx->cert->subject, vlen);
428 }
429 
430 /*
431  * Extract the parameters for the public key
432  */
x509_note_params(void * context,size_t hdrlen,unsigned char tag,const void * value,size_t vlen)433 int x509_note_params(void *context, size_t hdrlen,
434 		     unsigned char tag,
435 		     const void *value, size_t vlen)
436 {
437 	struct x509_parse_context *ctx = context;
438 
439 	/*
440 	 * AlgorithmIdentifier is used three times in the x509, we should skip
441 	 * first and ignore third, using second one which is after subject and
442 	 * before subjectPublicKey.
443 	 */
444 	if (!ctx->cert->raw_subject || ctx->key)
445 		return 0;
446 	ctx->params = value - hdrlen;
447 	ctx->params_size = vlen + hdrlen;
448 	return 0;
449 }
450 
451 /*
452  * Extract the data for the public key algorithm
453  */
x509_extract_key_data(void * context,size_t hdrlen,unsigned char tag,const void * value,size_t vlen)454 int x509_extract_key_data(void *context, size_t hdrlen,
455 			  unsigned char tag,
456 			  const void *value, size_t vlen)
457 {
458 	struct x509_parse_context *ctx = context;
459 
460 	ctx->key_algo = ctx->last_oid;
461 	if (ctx->last_oid == OID_rsaEncryption)
462 		ctx->cert->pub->pkey_algo = "rsa";
463 	else if (ctx->last_oid == OID_gost2012PKey256 ||
464 		 ctx->last_oid == OID_gost2012PKey512)
465 		ctx->cert->pub->pkey_algo = "ecrdsa";
466 	else
467 		return -ENOPKG;
468 
469 	/* Discard the BIT STRING metadata */
470 	if (vlen < 1 || *(const u8 *)value != 0)
471 		return -EBADMSG;
472 	ctx->key = value + 1;
473 	ctx->key_size = vlen - 1;
474 	return 0;
475 }
476 
477 /* The keyIdentifier in AuthorityKeyIdentifier SEQUENCE is tag(CONT,PRIM,0) */
478 #define SEQ_TAG_KEYID (ASN1_CONT << 6)
479 
480 /*
481  * Process certificate extensions that are used to qualify the certificate.
482  */
x509_process_extension(void * context,size_t hdrlen,unsigned char tag,const void * value,size_t vlen)483 int x509_process_extension(void *context, size_t hdrlen,
484 			   unsigned char tag,
485 			   const void *value, size_t vlen)
486 {
487 	struct x509_parse_context *ctx = context;
488 	struct asymmetric_key_id *kid;
489 	const unsigned char *v = value;
490 
491 	pr_debug("Extension: %u\n", ctx->last_oid);
492 
493 	if (ctx->last_oid == OID_subjectKeyIdentifier) {
494 		/* Get hold of the key fingerprint */
495 		if (ctx->cert->skid || vlen < 3)
496 			return -EBADMSG;
497 		if (v[0] != ASN1_OTS || v[1] != vlen - 2)
498 			return -EBADMSG;
499 		v += 2;
500 		vlen -= 2;
501 
502 		ctx->cert->raw_skid_size = vlen;
503 		ctx->cert->raw_skid = v;
504 		kid = asymmetric_key_generate_id(v, vlen, "", 0);
505 		if (IS_ERR(kid))
506 			return PTR_ERR(kid);
507 		ctx->cert->skid = kid;
508 		pr_debug("subjkeyid %*phN\n", kid->len, kid->data);
509 		return 0;
510 	}
511 
512 	if (ctx->last_oid == OID_authorityKeyIdentifier) {
513 		/* Get hold of the CA key fingerprint */
514 		ctx->raw_akid = v;
515 		ctx->raw_akid_size = vlen;
516 		return 0;
517 	}
518 
519 	return 0;
520 }
521 
522 /**
523  * x509_decode_time - Decode an X.509 time ASN.1 object
524  * @_t: The time to fill in
525  * @hdrlen: The length of the object header
526  * @tag: The object tag
527  * @value: The object value
528  * @vlen: The size of the object value
529  *
530  * Decode an ASN.1 universal time or generalised time field into a struct the
531  * kernel can handle and check it for validity.  The time is decoded thus:
532  *
533  *	[RFC5280 §4.1.2.5]
534  *	CAs conforming to this profile MUST always encode certificate validity
535  *	dates through the year 2049 as UTCTime; certificate validity dates in
536  *	2050 or later MUST be encoded as GeneralizedTime.  Conforming
537  *	applications MUST be able to process validity dates that are encoded in
538  *	either UTCTime or GeneralizedTime.
539  */
x509_decode_time(time64_t * _t,size_t hdrlen,unsigned char tag,const unsigned char * value,size_t vlen)540 int x509_decode_time(time64_t *_t,  size_t hdrlen,
541 		     unsigned char tag,
542 		     const unsigned char *value, size_t vlen)
543 {
544 	static const unsigned char month_lengths[] = { 31, 28, 31, 30, 31, 30,
545 						       31, 31, 30, 31, 30, 31 };
546 	const unsigned char *p = value;
547 	unsigned year, mon, day, hour, min, sec, mon_len;
548 
549 #define dec2bin(X) ({ unsigned char x = (X) - '0'; if (x > 9) goto invalid_time; x; })
550 #define DD2bin(P) ({ unsigned x = dec2bin(P[0]) * 10 + dec2bin(P[1]); P += 2; x; })
551 
552 	if (tag == ASN1_UNITIM) {
553 		/* UTCTime: YYMMDDHHMMSSZ */
554 		if (vlen != 13)
555 			goto unsupported_time;
556 		year = DD2bin(p);
557 		if (year >= 50)
558 			year += 1900;
559 		else
560 			year += 2000;
561 	} else if (tag == ASN1_GENTIM) {
562 		/* GenTime: YYYYMMDDHHMMSSZ */
563 		if (vlen != 15)
564 			goto unsupported_time;
565 		year = DD2bin(p) * 100 + DD2bin(p);
566 		if (year >= 1950 && year <= 2049)
567 			goto invalid_time;
568 	} else {
569 		goto unsupported_time;
570 	}
571 
572 	mon  = DD2bin(p);
573 	day = DD2bin(p);
574 	hour = DD2bin(p);
575 	min  = DD2bin(p);
576 	sec  = DD2bin(p);
577 
578 	if (*p != 'Z')
579 		goto unsupported_time;
580 
581 	if (year < 1970 ||
582 	    mon < 1 || mon > 12)
583 		goto invalid_time;
584 
585 	mon_len = month_lengths[mon - 1];
586 	if (mon == 2) {
587 		if (year % 4 == 0) {
588 			mon_len = 29;
589 			if (year % 100 == 0) {
590 				mon_len = 28;
591 				if (year % 400 == 0)
592 					mon_len = 29;
593 			}
594 		}
595 	}
596 
597 	if (day < 1 || day > mon_len ||
598 	    hour > 24 || /* ISO 8601 permits 24:00:00 as midnight tomorrow */
599 	    min > 59 ||
600 	    sec > 60) /* ISO 8601 permits leap seconds [X.680 46.3] */
601 		goto invalid_time;
602 
603 	*_t = mktime64(year, mon, day, hour, min, sec);
604 	return 0;
605 
606 unsupported_time:
607 	pr_debug("Got unsupported time [tag %02x]: '%*phN'\n",
608 		 tag, (int)vlen, value);
609 	return -EBADMSG;
610 invalid_time:
611 	pr_debug("Got invalid time [tag %02x]: '%*phN'\n",
612 		 tag, (int)vlen, value);
613 	return -EBADMSG;
614 }
615 EXPORT_SYMBOL_GPL(x509_decode_time);
616 
x509_note_not_before(void * context,size_t hdrlen,unsigned char tag,const void * value,size_t vlen)617 int x509_note_not_before(void *context, size_t hdrlen,
618 			 unsigned char tag,
619 			 const void *value, size_t vlen)
620 {
621 	struct x509_parse_context *ctx = context;
622 	return x509_decode_time(&ctx->cert->valid_from, hdrlen, tag, value, vlen);
623 }
624 
x509_note_not_after(void * context,size_t hdrlen,unsigned char tag,const void * value,size_t vlen)625 int x509_note_not_after(void *context, size_t hdrlen,
626 			unsigned char tag,
627 			const void *value, size_t vlen)
628 {
629 	struct x509_parse_context *ctx = context;
630 	return x509_decode_time(&ctx->cert->valid_to, hdrlen, tag, value, vlen);
631 }
632 
633 /*
634  * Note a key identifier-based AuthorityKeyIdentifier
635  */
x509_akid_note_kid(void * context,size_t hdrlen,unsigned char tag,const void * value,size_t vlen)636 int x509_akid_note_kid(void *context, size_t hdrlen,
637 		       unsigned char tag,
638 		       const void *value, size_t vlen)
639 {
640 	struct x509_parse_context *ctx = context;
641 	struct asymmetric_key_id *kid;
642 
643 	pr_debug("AKID: keyid: %*phN\n", (int)vlen, value);
644 
645 	if (ctx->cert->sig->auth_ids[1])
646 		return 0;
647 
648 	kid = asymmetric_key_generate_id(value, vlen, "", 0);
649 	if (IS_ERR(kid))
650 		return PTR_ERR(kid);
651 	pr_debug("authkeyid %*phN\n", kid->len, kid->data);
652 	ctx->cert->sig->auth_ids[1] = kid;
653 	return 0;
654 }
655 
656 /*
657  * Note a directoryName in an AuthorityKeyIdentifier
658  */
x509_akid_note_name(void * context,size_t hdrlen,unsigned char tag,const void * value,size_t vlen)659 int x509_akid_note_name(void *context, size_t hdrlen,
660 			unsigned char tag,
661 			const void *value, size_t vlen)
662 {
663 	struct x509_parse_context *ctx = context;
664 
665 	pr_debug("AKID: name: %*phN\n", (int)vlen, value);
666 
667 	ctx->akid_raw_issuer = value;
668 	ctx->akid_raw_issuer_size = vlen;
669 	return 0;
670 }
671 
672 /*
673  * Note a serial number in an AuthorityKeyIdentifier
674  */
x509_akid_note_serial(void * context,size_t hdrlen,unsigned char tag,const void * value,size_t vlen)675 int x509_akid_note_serial(void *context, size_t hdrlen,
676 			  unsigned char tag,
677 			  const void *value, size_t vlen)
678 {
679 	struct x509_parse_context *ctx = context;
680 	struct asymmetric_key_id *kid;
681 
682 	pr_debug("AKID: serial: %*phN\n", (int)vlen, value);
683 
684 	if (!ctx->akid_raw_issuer || ctx->cert->sig->auth_ids[0])
685 		return 0;
686 
687 	kid = asymmetric_key_generate_id(value,
688 					 vlen,
689 					 ctx->akid_raw_issuer,
690 					 ctx->akid_raw_issuer_size);
691 	if (IS_ERR(kid))
692 		return PTR_ERR(kid);
693 
694 	pr_debug("authkeyid %*phN\n", kid->len, kid->data);
695 	ctx->cert->sig->auth_ids[0] = kid;
696 	return 0;
697 }
698