• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * X.509v3 certificate parsing and processing (RFC 3280 profile)
3  * Copyright (c) 2006-2015, Jouni Malinen <j@w1.fi>
4  *
5  * This software may be distributed under the terms of the BSD license.
6  * See README for more details.
7  */
8 
9 #include "includes.h"
10 
11 #include "common.h"
12 #include "crypto/crypto.h"
13 #include "asn1.h"
14 #include "x509v3.h"
15 
16 
x509_free_name(struct x509_name * name)17 void x509_free_name(struct x509_name *name)
18 {
19 	size_t i;
20 
21 	for (i = 0; i < name->num_attr; i++) {
22 		os_free(name->attr[i].value);
23 		name->attr[i].value = NULL;
24 		name->attr[i].type = X509_NAME_ATTR_NOT_USED;
25 	}
26 	name->num_attr = 0;
27 	os_free(name->email);
28 	name->email = NULL;
29 
30 	os_free(name->alt_email);
31 	os_free(name->dns);
32 	os_free(name->uri);
33 	os_free(name->ip);
34 	name->alt_email = name->dns = name->uri = NULL;
35 	name->ip = NULL;
36 	name->ip_len = 0;
37 	os_memset(&name->rid, 0, sizeof(name->rid));
38 }
39 
40 
41 /**
42  * x509_certificate_free - Free an X.509 certificate
43  * @cert: Certificate to be freed
44  */
x509_certificate_free(struct x509_certificate * cert)45 void x509_certificate_free(struct x509_certificate *cert)
46 {
47 	if (cert == NULL)
48 		return;
49 	if (cert->next) {
50 		wpa_printf(MSG_DEBUG, "X509: x509_certificate_free: cer=%p "
51 			   "was still on a list (next=%p)\n",
52 			   cert, cert->next);
53 	}
54 	x509_free_name(&cert->issuer);
55 	x509_free_name(&cert->subject);
56 	os_free(cert->public_key);
57 	os_free(cert->sign_value);
58 	os_free(cert->subject_dn);
59 	os_free(cert);
60 }
61 
62 
63 /**
64  * x509_certificate_free - Free an X.509 certificate chain
65  * @cert: Pointer to the first certificate in the chain
66  */
x509_certificate_chain_free(struct x509_certificate * cert)67 void x509_certificate_chain_free(struct x509_certificate *cert)
68 {
69 	struct x509_certificate *next;
70 
71 	while (cert) {
72 		next = cert->next;
73 		cert->next = NULL;
74 		x509_certificate_free(cert);
75 		cert = next;
76 	}
77 }
78 
79 
x509_whitespace(char c)80 static int x509_whitespace(char c)
81 {
82 	return c == ' ' || c == '\t';
83 }
84 
85 
x509_str_strip_whitespace(char * a)86 static void x509_str_strip_whitespace(char *a)
87 {
88 	char *ipos, *opos;
89 	int remove_whitespace = 1;
90 
91 	ipos = opos = a;
92 
93 	while (*ipos) {
94 		if (remove_whitespace && x509_whitespace(*ipos))
95 			ipos++;
96 		else {
97 			remove_whitespace = x509_whitespace(*ipos);
98 			*opos++ = *ipos++;
99 		}
100 	}
101 
102 	*opos-- = '\0';
103 	if (opos > a && x509_whitespace(*opos))
104 		*opos = '\0';
105 }
106 
107 
x509_str_compare(const char * a,const char * b)108 static int x509_str_compare(const char *a, const char *b)
109 {
110 	char *aa, *bb;
111 	int ret;
112 
113 	if (!a && b)
114 		return -1;
115 	if (a && !b)
116 		return 1;
117 	if (!a && !b)
118 		return 0;
119 
120 	aa = os_strdup(a);
121 	bb = os_strdup(b);
122 
123 	if (aa == NULL || bb == NULL) {
124 		os_free(aa);
125 		os_free(bb);
126 		return os_strcasecmp(a, b);
127 	}
128 
129 	x509_str_strip_whitespace(aa);
130 	x509_str_strip_whitespace(bb);
131 
132 	ret = os_strcasecmp(aa, bb);
133 
134 	os_free(aa);
135 	os_free(bb);
136 
137 	return ret;
138 }
139 
140 
141 /**
142  * x509_name_compare - Compare X.509 certificate names
143  * @a: Certificate name
144  * @b: Certificate name
145  * Returns: <0, 0, or >0 based on whether a is less than, equal to, or
146  * greater than b
147  */
x509_name_compare(struct x509_name * a,struct x509_name * b)148 int x509_name_compare(struct x509_name *a, struct x509_name *b)
149 {
150 	int res;
151 	size_t i;
152 
153 	if (!a && b)
154 		return -1;
155 	if (a && !b)
156 		return 1;
157 	if (!a && !b)
158 		return 0;
159 	if (a->num_attr < b->num_attr)
160 		return -1;
161 	if (a->num_attr > b->num_attr)
162 		return 1;
163 
164 	for (i = 0; i < a->num_attr; i++) {
165 		if (a->attr[i].type < b->attr[i].type)
166 			return -1;
167 		if (a->attr[i].type > b->attr[i].type)
168 			return -1;
169 		res = x509_str_compare(a->attr[i].value, b->attr[i].value);
170 		if (res)
171 			return res;
172 	}
173 	res = x509_str_compare(a->email, b->email);
174 	if (res)
175 		return res;
176 
177 	return 0;
178 }
179 
180 
x509_parse_algorithm_identifier(const u8 * buf,size_t len,struct x509_algorithm_identifier * id,const u8 ** next)181 int x509_parse_algorithm_identifier(const u8 *buf, size_t len,
182 				    struct x509_algorithm_identifier *id,
183 				    const u8 **next)
184 {
185 	struct asn1_hdr hdr;
186 	const u8 *pos, *end;
187 
188 	/*
189 	 * AlgorithmIdentifier ::= SEQUENCE {
190 	 *     algorithm            OBJECT IDENTIFIER,
191 	 *     parameters           ANY DEFINED BY algorithm OPTIONAL
192 	 * }
193 	 */
194 
195 	if (asn1_get_next(buf, len, &hdr) < 0 || !asn1_is_sequence(&hdr)) {
196 		asn1_unexpected(&hdr,
197 				"X509: Expected SEQUENCE (AlgorithmIdentifier)");
198 		return -1;
199 	}
200 	if (hdr.length > buf + len - hdr.payload)
201 		return -1;
202 	pos = hdr.payload;
203 	end = pos + hdr.length;
204 
205 	*next = end;
206 
207 	if (asn1_get_oid(pos, end - pos, &id->oid, &pos))
208 		return -1;
209 
210 	/* TODO: optional parameters */
211 
212 	return 0;
213 }
214 
215 
x509_parse_public_key(const u8 * buf,size_t len,struct x509_certificate * cert,const u8 ** next)216 static int x509_parse_public_key(const u8 *buf, size_t len,
217 				 struct x509_certificate *cert,
218 				 const u8 **next)
219 {
220 	struct asn1_hdr hdr;
221 	const u8 *pos, *end;
222 
223 	/*
224 	 * SubjectPublicKeyInfo ::= SEQUENCE {
225 	 *     algorithm            AlgorithmIdentifier,
226 	 *     subjectPublicKey     BIT STRING
227 	 * }
228 	 */
229 
230 	pos = buf;
231 	end = buf + len;
232 
233 	if (asn1_get_next(pos, end - pos, &hdr) < 0 ||
234 	    !asn1_is_sequence(&hdr)) {
235 		asn1_unexpected(&hdr,
236 				"X509: Expected SEQUENCE (SubjectPublicKeyInfo)");
237 		return -1;
238 	}
239 	pos = hdr.payload;
240 
241 	if (hdr.length > end - pos)
242 		return -1;
243 	end = pos + hdr.length;
244 	*next = end;
245 
246 	if (x509_parse_algorithm_identifier(pos, end - pos,
247 					    &cert->public_key_alg, &pos))
248 		return -1;
249 
250 	if (asn1_get_next(pos, end - pos, &hdr) < 0 ||
251 	    !asn1_is_bitstring(&hdr)) {
252 		asn1_unexpected(&hdr,
253 				"X509: Expected BITSTRING (subjectPublicKey)");
254 		return -1;
255 	}
256 	if (hdr.length < 1)
257 		return -1;
258 	pos = hdr.payload;
259 	if (*pos) {
260 		wpa_printf(MSG_DEBUG,
261 			   "X509: BITSTRING (subjectPublicKey) - %d unused bits",
262 			   *pos);
263 		/*
264 		 * TODO: should this be rejected? X.509 certificates are
265 		 * unlikely to use such a construction. Now we would end up
266 		 * including the extra bits in the buffer which may also be
267 		 * ok.
268 		 */
269 	}
270 	os_free(cert->public_key);
271 	cert->public_key = os_memdup(pos + 1, hdr.length - 1);
272 	if (cert->public_key == NULL) {
273 		wpa_printf(MSG_DEBUG, "X509: Failed to allocate memory for "
274 			   "public key");
275 		return -1;
276 	}
277 	cert->public_key_len = hdr.length - 1;
278 	wpa_hexdump(MSG_MSGDUMP, "X509: subjectPublicKey",
279 		    cert->public_key, cert->public_key_len);
280 
281 	return 0;
282 }
283 
284 
x509_parse_name(const u8 * buf,size_t len,struct x509_name * name,const u8 ** next)285 int x509_parse_name(const u8 *buf, size_t len, struct x509_name *name,
286 		    const u8 **next)
287 {
288 	struct asn1_hdr hdr;
289 	const u8 *pos, *end, *set_pos, *set_end, *seq_pos, *seq_end;
290 	struct asn1_oid oid;
291 	char *val;
292 
293 	/*
294 	 * Name ::= CHOICE { RDNSequence }
295 	 * RDNSequence ::= SEQUENCE OF RelativeDistinguishedName
296 	 * RelativeDistinguishedName ::= SET OF AttributeTypeAndValue
297 	 * AttributeTypeAndValue ::= SEQUENCE {
298 	 *     type     AttributeType,
299 	 *     value    AttributeValue
300 	 * }
301 	 * AttributeType ::= OBJECT IDENTIFIER
302 	 * AttributeValue ::= ANY DEFINED BY AttributeType
303 	 */
304 
305 	if (asn1_get_next(buf, len, &hdr) < 0 || !asn1_is_sequence(&hdr)) {
306 		asn1_unexpected(&hdr,
307 				"X509: Expected SEQUENCE (Name / RDNSequencer)");
308 		return -1;
309 	}
310 	pos = hdr.payload;
311 
312 	if (hdr.length > buf + len - pos)
313 		return -1;
314 
315 	end = *next = pos + hdr.length;
316 
317 	while (pos < end) {
318 		enum x509_name_attr_type type;
319 
320 		if (asn1_get_next(pos, end - pos, &hdr) < 0 ||
321 		    !asn1_is_set(&hdr)) {
322 			asn1_unexpected(&hdr,
323 					"X509: Expected SET (RelativeDistinguishedName)");
324 			x509_free_name(name);
325 			return -1;
326 		}
327 
328 		set_pos = hdr.payload;
329 		pos = set_end = hdr.payload + hdr.length;
330 
331 		if (asn1_get_next(set_pos, set_end - set_pos, &hdr) < 0 ||
332 		    !asn1_is_sequence(&hdr)) {
333 			asn1_unexpected(&hdr,
334 					"X509: Expected SEQUENCE (AttributeTypeAndValue)");
335 			x509_free_name(name);
336 			return -1;
337 		}
338 
339 		seq_pos = hdr.payload;
340 		seq_end = hdr.payload + hdr.length;
341 
342 		if (asn1_get_oid(seq_pos, seq_end - seq_pos, &oid, &seq_pos)) {
343 			x509_free_name(name);
344 			return -1;
345 		}
346 
347 		if (asn1_get_next(seq_pos, seq_end - seq_pos, &hdr) < 0 ||
348 		    hdr.class != ASN1_CLASS_UNIVERSAL) {
349 			wpa_printf(MSG_DEBUG, "X509: Failed to parse "
350 				   "AttributeValue");
351 			x509_free_name(name);
352 			return -1;
353 		}
354 
355 		if (!asn1_is_string_type(&hdr)) {
356 			wpa_printf(MSG_DEBUG,
357 				   "X509: Ignore non-string type attribute (tag 0x%x)",
358 				   hdr.tag);
359 			continue;
360 		}
361 
362 		/* RFC 3280:
363 		 * MUST: country, organization, organizational-unit,
364 		 * distinguished name qualifier, state or province name,
365 		 * common name, serial number.
366 		 * SHOULD: locality, title, surname, given name, initials,
367 		 * pseudonym, generation qualifier.
368 		 * MUST: domainComponent (RFC 2247).
369 		 */
370 		type = X509_NAME_ATTR_NOT_USED;
371 		if (oid.len == 4 &&
372 		    oid.oid[0] == 2 && oid.oid[1] == 5 && oid.oid[2] == 4) {
373 			/* id-at ::= 2.5.4 */
374 			switch (oid.oid[3]) {
375 			case 3:
376 				/* commonName */
377 				type = X509_NAME_ATTR_CN;
378 				break;
379 			case 6:
380 				/*  countryName */
381 				type = X509_NAME_ATTR_C;
382 				break;
383 			case 7:
384 				/* localityName */
385 				type = X509_NAME_ATTR_L;
386 				break;
387 			case 8:
388 				/* stateOrProvinceName */
389 				type = X509_NAME_ATTR_ST;
390 				break;
391 			case 10:
392 				/* organizationName */
393 				type = X509_NAME_ATTR_O;
394 				break;
395 			case 11:
396 				/* organizationalUnitName */
397 				type = X509_NAME_ATTR_OU;
398 				break;
399 			}
400 		} else if (oid.len == 7 &&
401 			   oid.oid[0] == 1 && oid.oid[1] == 2 &&
402 			   oid.oid[2] == 840 && oid.oid[3] == 113549 &&
403 			   oid.oid[4] == 1 && oid.oid[5] == 9 &&
404 			   oid.oid[6] == 1) {
405 			/* 1.2.840.113549.1.9.1 - e-mailAddress */
406 			os_free(name->email);
407 			name->email = os_malloc(hdr.length + 1);
408 			if (name->email == NULL) {
409 				x509_free_name(name);
410 				return -1;
411 			}
412 			os_memcpy(name->email, hdr.payload, hdr.length);
413 			name->email[hdr.length] = '\0';
414 			continue;
415 		} else if (oid.len == 7 &&
416 			   oid.oid[0] == 0 && oid.oid[1] == 9 &&
417 			   oid.oid[2] == 2342 && oid.oid[3] == 19200300 &&
418 			   oid.oid[4] == 100 && oid.oid[5] == 1 &&
419 			   oid.oid[6] == 25) {
420 			/* 0.9.2342.19200300.100.1.25 - domainComponent */
421 			type = X509_NAME_ATTR_DC;
422 		}
423 
424 		if (type == X509_NAME_ATTR_NOT_USED) {
425 			wpa_hexdump(MSG_DEBUG, "X509: Unrecognized OID",
426 				    (u8 *) oid.oid,
427 				    oid.len * sizeof(oid.oid[0]));
428 			wpa_hexdump_ascii(MSG_MSGDUMP, "X509: Attribute Data",
429 					  hdr.payload, hdr.length);
430 			continue;
431 		}
432 
433 		if (name->num_attr == X509_MAX_NAME_ATTRIBUTES) {
434 			wpa_printf(MSG_INFO, "X509: Too many Name attributes");
435 			x509_free_name(name);
436 			return -1;
437 		}
438 
439 		val = dup_binstr(hdr.payload, hdr.length);
440 		if (val == NULL) {
441 			x509_free_name(name);
442 			return -1;
443 		}
444 		if (os_strlen(val) != hdr.length) {
445 			wpa_printf(MSG_INFO, "X509: Reject certificate with "
446 				   "embedded NUL byte in a string (%s[NUL])",
447 				   val);
448 			os_free(val);
449 			x509_free_name(name);
450 			return -1;
451 		}
452 
453 		name->attr[name->num_attr].type = type;
454 		name->attr[name->num_attr].value = val;
455 		name->num_attr++;
456 	}
457 
458 	return 0;
459 }
460 
461 
x509_name_attr_str(enum x509_name_attr_type type)462 static char * x509_name_attr_str(enum x509_name_attr_type type)
463 {
464 	switch (type) {
465 	case X509_NAME_ATTR_NOT_USED:
466 		return "[N/A]";
467 	case X509_NAME_ATTR_DC:
468 		return "DC";
469 	case X509_NAME_ATTR_CN:
470 		return "CN";
471 	case X509_NAME_ATTR_C:
472 		return "C";
473 	case X509_NAME_ATTR_L:
474 		return "L";
475 	case X509_NAME_ATTR_ST:
476 		return "ST";
477 	case X509_NAME_ATTR_O:
478 		return "O";
479 	case X509_NAME_ATTR_OU:
480 		return "OU";
481 	}
482 	return "?";
483 }
484 
485 
486 /**
487  * x509_name_string - Convert an X.509 certificate name into a string
488  * @name: Name to convert
489  * @buf: Buffer for the string
490  * @len: Maximum buffer length
491  */
x509_name_string(struct x509_name * name,char * buf,size_t len)492 void x509_name_string(struct x509_name *name, char *buf, size_t len)
493 {
494 	char *pos, *end;
495 	int ret;
496 	size_t i;
497 
498 	if (len == 0)
499 		return;
500 
501 	pos = buf;
502 	end = buf + len;
503 
504 	for (i = 0; i < name->num_attr; i++) {
505 		ret = os_snprintf(pos, end - pos, "%s=%s, ",
506 				  x509_name_attr_str(name->attr[i].type),
507 				  name->attr[i].value);
508 		if (os_snprintf_error(end - pos, ret))
509 			goto done;
510 		pos += ret;
511 	}
512 
513 	if (pos > buf + 1 && pos[-1] == ' ' && pos[-2] == ',') {
514 		pos--;
515 		*pos = '\0';
516 		pos--;
517 		*pos = '\0';
518 	}
519 
520 	if (name->email) {
521 		ret = os_snprintf(pos, end - pos, "/emailAddress=%s",
522 				  name->email);
523 		if (os_snprintf_error(end - pos, ret))
524 			goto done;
525 		pos += ret;
526 	}
527 
528 done:
529 	if (pos < end)
530 		*pos = '\0';
531 	end[-1] = '\0';
532 }
533 
534 
parse_uint2(const char * pos,size_t len)535 static int parse_uint2(const char *pos, size_t len)
536 {
537 	char buf[3];
538 	int ret;
539 
540 	if (len < 2)
541 		return -1;
542 	buf[0] = pos[0];
543 	buf[1] = pos[1];
544 	buf[2] = 0x00;
545 	if (sscanf(buf, "%2d", &ret) != 1)
546 		return -1;
547 	return ret;
548 }
549 
550 
parse_uint4(const char * pos,size_t len)551 static int parse_uint4(const char *pos, size_t len)
552 {
553 	char buf[5];
554 	int ret;
555 
556 	if (len < 4)
557 		return -1;
558 	buf[0] = pos[0];
559 	buf[1] = pos[1];
560 	buf[2] = pos[2];
561 	buf[3] = pos[3];
562 	buf[4] = 0x00;
563 	if (sscanf(buf, "%4d", &ret) != 1)
564 		return -1;
565 	return ret;
566 }
567 
568 
x509_parse_time(const u8 * buf,size_t len,u8 asn1_tag,os_time_t * val)569 int x509_parse_time(const u8 *buf, size_t len, u8 asn1_tag, os_time_t *val)
570 {
571 	const char *pos, *end;
572 	int year, month, day, hour, min, sec;
573 
574 	/*
575 	 * Time ::= CHOICE {
576 	 *     utcTime        UTCTime,
577 	 *     generalTime    GeneralizedTime
578 	 * }
579 	 *
580 	 * UTCTime: YYMMDDHHMMSSZ
581 	 * GeneralizedTime: YYYYMMDDHHMMSSZ
582 	 */
583 
584 	pos = (const char *) buf;
585 	end = pos + len;
586 
587 	switch (asn1_tag) {
588 	case ASN1_TAG_UTCTIME:
589 		if (len != 13 || buf[12] != 'Z') {
590 			wpa_hexdump_ascii(MSG_DEBUG, "X509: Unrecognized "
591 					  "UTCTime format", buf, len);
592 			return -1;
593 		}
594 		year = parse_uint2(pos, end - pos);
595 		if (year < 0) {
596 			wpa_hexdump_ascii(MSG_DEBUG, "X509: Failed to parse "
597 					  "UTCTime year", buf, len);
598 			return -1;
599 		}
600 		if (year < 50)
601 			year += 2000;
602 		else
603 			year += 1900;
604 		pos += 2;
605 		break;
606 	case ASN1_TAG_GENERALIZEDTIME:
607 		if (len != 15 || buf[14] != 'Z') {
608 			wpa_hexdump_ascii(MSG_DEBUG, "X509: Unrecognized "
609 					  "GeneralizedTime format", buf, len);
610 			return -1;
611 		}
612 		year = parse_uint4(pos, end - pos);
613 		if (year < 0) {
614 			wpa_hexdump_ascii(MSG_DEBUG, "X509: Failed to parse "
615 					  "GeneralizedTime year", buf, len);
616 			return -1;
617 		}
618 		pos += 4;
619 		break;
620 	default:
621 		wpa_printf(MSG_DEBUG, "X509: Expected UTCTime or "
622 			   "GeneralizedTime - found tag 0x%x", asn1_tag);
623 		return -1;
624 	}
625 
626 	month = parse_uint2(pos, end - pos);
627 	if (month < 0) {
628 		wpa_hexdump_ascii(MSG_DEBUG, "X509: Failed to parse Time "
629 				  "(month)", buf, len);
630 		return -1;
631 	}
632 	pos += 2;
633 
634 	day = parse_uint2(pos, end - pos);
635 	if (day < 0) {
636 		wpa_hexdump_ascii(MSG_DEBUG, "X509: Failed to parse Time "
637 				  "(day)", buf, len);
638 		return -1;
639 	}
640 	pos += 2;
641 
642 	hour = parse_uint2(pos, end - pos);
643 	if (hour < 0) {
644 		wpa_hexdump_ascii(MSG_DEBUG, "X509: Failed to parse Time "
645 				  "(hour)", buf, len);
646 		return -1;
647 	}
648 	pos += 2;
649 
650 	min = parse_uint2(pos, end - pos);
651 	if (min < 0) {
652 		wpa_hexdump_ascii(MSG_DEBUG, "X509: Failed to parse Time "
653 				  "(min)", buf, len);
654 		return -1;
655 	}
656 	pos += 2;
657 
658 	sec = parse_uint2(pos, end - pos);
659 	if (sec < 0) {
660 		wpa_hexdump_ascii(MSG_DEBUG, "X509: Failed to parse Time "
661 				  "(sec)", buf, len);
662 		return -1;
663 	}
664 
665 	if (os_mktime(year, month, day, hour, min, sec, val) < 0) {
666 		wpa_hexdump_ascii(MSG_DEBUG, "X509: Failed to convert Time",
667 				  buf, len);
668 		if (year < 1970) {
669 			/*
670 			 * At least some test certificates have been configured
671 			 * to use dates prior to 1970. Set the date to
672 			 * beginning of 1970 to handle these case.
673 			 */
674 			wpa_printf(MSG_DEBUG, "X509: Year=%d before epoch - "
675 				   "assume epoch as the time", year);
676 			*val = 0;
677 			return 0;
678 		}
679 		return -1;
680 	}
681 
682 	return 0;
683 }
684 
685 
x509_parse_validity(const u8 * buf,size_t len,struct x509_certificate * cert,const u8 ** next)686 static int x509_parse_validity(const u8 *buf, size_t len,
687 			       struct x509_certificate *cert, const u8 **next)
688 {
689 	struct asn1_hdr hdr;
690 	const u8 *pos;
691 	size_t plen;
692 
693 	/*
694 	 * Validity ::= SEQUENCE {
695 	 *     notBefore      Time,
696 	 *     notAfter       Time
697 	 * }
698 	 *
699 	 * RFC 3280, 4.1.2.5:
700 	 * CAs conforming to this profile MUST always encode certificate
701 	 * validity dates through the year 2049 as UTCTime; certificate
702 	 * validity dates in 2050 or later MUST be encoded as GeneralizedTime.
703 	 */
704 
705 	if (asn1_get_next(buf, len, &hdr) < 0 || !asn1_is_sequence(&hdr)) {
706 		asn1_unexpected(&hdr, "X509: Expected SEQUENCE (Validity)");
707 		return -1;
708 	}
709 	pos = hdr.payload;
710 	plen = hdr.length;
711 
712 	if (plen > (size_t) (buf + len - pos))
713 		return -1;
714 
715 	*next = pos + plen;
716 
717 	if (asn1_get_next(pos, plen, &hdr) < 0 ||
718 	    (!asn1_is_utctime(&hdr) && !asn1_is_generalizedtime(&hdr)) ||
719 	    x509_parse_time(hdr.payload, hdr.length, hdr.tag,
720 			    &cert->not_before) < 0) {
721 		wpa_hexdump_ascii(MSG_DEBUG, "X509: Failed to parse notBefore "
722 				  "Time", hdr.payload, hdr.length);
723 		return -1;
724 	}
725 
726 	pos = hdr.payload + hdr.length;
727 	plen = *next - pos;
728 
729 	if (asn1_get_next(pos, plen, &hdr) < 0 ||
730 	    (!asn1_is_utctime(&hdr) && !asn1_is_generalizedtime(&hdr)) ||
731 	    x509_parse_time(hdr.payload, hdr.length, hdr.tag,
732 			    &cert->not_after) < 0) {
733 		wpa_hexdump_ascii(MSG_DEBUG, "X509: Failed to parse notAfter "
734 				  "Time", hdr.payload, hdr.length);
735 		return -1;
736 	}
737 
738 	wpa_printf(MSG_MSGDUMP, "X509: Validity: notBefore: %lu notAfter: %lu",
739 		   (unsigned long) cert->not_before,
740 		   (unsigned long) cert->not_after);
741 
742 	return 0;
743 }
744 
745 
x509_id_ce_oid(struct asn1_oid * oid)746 static int x509_id_ce_oid(struct asn1_oid *oid)
747 {
748 	/* id-ce arc from X.509 for standard X.509v3 extensions */
749 	return oid->len >= 4 &&
750 		oid->oid[0] == 2 /* joint-iso-ccitt */ &&
751 		oid->oid[1] == 5 /* ds */ &&
752 		oid->oid[2] == 29 /* id-ce */;
753 }
754 
755 
x509_any_ext_key_usage_oid(struct asn1_oid * oid)756 static int x509_any_ext_key_usage_oid(struct asn1_oid *oid)
757 {
758 	return oid->len == 6 &&
759 		x509_id_ce_oid(oid) &&
760 		oid->oid[3] == 37 /* extKeyUsage */ &&
761 		oid->oid[4] == 0 /* anyExtendedKeyUsage */;
762 }
763 
764 
x509_parse_ext_key_usage(struct x509_certificate * cert,const u8 * pos,size_t len)765 static int x509_parse_ext_key_usage(struct x509_certificate *cert,
766 				    const u8 *pos, size_t len)
767 {
768 	struct asn1_hdr hdr;
769 
770 	/*
771 	 * KeyUsage ::= BIT STRING {
772 	 *     digitalSignature        (0),
773 	 *     nonRepudiation          (1),
774 	 *     keyEncipherment         (2),
775 	 *     dataEncipherment        (3),
776 	 *     keyAgreement            (4),
777 	 *     keyCertSign             (5),
778 	 *     cRLSign                 (6),
779 	 *     encipherOnly            (7),
780 	 *     decipherOnly            (8) }
781 	 */
782 
783 	if (asn1_get_next(pos, len, &hdr) < 0 || !asn1_is_bitstring(&hdr) ||
784 	    hdr.length < 1) {
785 		asn1_unexpected(&hdr, "X509: Expected BIT STRING in KeyUsage");
786 		return -1;
787 	}
788 
789 	cert->extensions_present |= X509_EXT_KEY_USAGE;
790 	cert->key_usage = asn1_bit_string_to_long(hdr.payload, hdr.length);
791 
792 	wpa_printf(MSG_DEBUG, "X509: KeyUsage 0x%lx", cert->key_usage);
793 
794 	return 0;
795 }
796 
797 
x509_parse_ext_basic_constraints(struct x509_certificate * cert,const u8 * pos,size_t len)798 static int x509_parse_ext_basic_constraints(struct x509_certificate *cert,
799 					    const u8 *pos, size_t len)
800 {
801 	struct asn1_hdr hdr;
802 	unsigned long value;
803 	size_t left;
804 	const u8 *end_seq;
805 
806 	/*
807 	 * BasicConstraints ::= SEQUENCE {
808 	 * cA                      BOOLEAN DEFAULT FALSE,
809 	 * pathLenConstraint       INTEGER (0..MAX) OPTIONAL }
810 	 */
811 
812 	if (asn1_get_next(pos, len, &hdr) < 0 || !asn1_is_sequence(&hdr)) {
813 		asn1_unexpected(&hdr,
814 				"X509: Expected SEQUENCE in BasicConstraints");
815 		return -1;
816 	}
817 
818 	cert->extensions_present |= X509_EXT_BASIC_CONSTRAINTS;
819 
820 	if (hdr.length == 0)
821 		return 0;
822 
823 	end_seq = hdr.payload + hdr.length;
824 	if (asn1_get_next(hdr.payload, hdr.length, &hdr) < 0) {
825 		wpa_printf(MSG_DEBUG, "X509: Failed to parse "
826 			   "BasicConstraints");
827 		return -1;
828 	}
829 
830 	if (asn1_is_boolean(&hdr)) {
831 		cert->ca = hdr.payload[0];
832 
833 		pos = hdr.payload + hdr.length;
834 		if (pos >= end_seq) {
835 			/* No optional pathLenConstraint */
836 			wpa_printf(MSG_DEBUG, "X509: BasicConstraints - cA=%d",
837 				   cert->ca);
838 			return 0;
839 		}
840 		if (asn1_get_next(pos, end_seq - pos, &hdr) < 0) {
841 			wpa_printf(MSG_DEBUG, "X509: Failed to parse "
842 				   "BasicConstraints");
843 			return -1;
844 		}
845 	}
846 
847 	if (!asn1_is_integer(&hdr)) {
848 		asn1_unexpected(&hdr,
849 				"X509: Expected INTEGER in BasicConstraints");
850 		return -1;
851 	}
852 
853 	pos = hdr.payload;
854 	left = hdr.length;
855 	value = 0;
856 	while (left) {
857 		value <<= 8;
858 		value |= *pos++;
859 		left--;
860 	}
861 
862 	cert->path_len_constraint = value;
863 	cert->extensions_present |= X509_EXT_PATH_LEN_CONSTRAINT;
864 
865 	wpa_printf(MSG_DEBUG, "X509: BasicConstraints - cA=%d "
866 		   "pathLenConstraint=%lu",
867 		   cert->ca, cert->path_len_constraint);
868 
869 	return 0;
870 }
871 
872 
x509_parse_alt_name_rfc8222(struct x509_name * name,const u8 * pos,size_t len)873 static int x509_parse_alt_name_rfc8222(struct x509_name *name,
874 				       const u8 *pos, size_t len)
875 {
876 	/* rfc822Name IA5String */
877 	wpa_hexdump_ascii(MSG_MSGDUMP, "X509: altName - rfc822Name", pos, len);
878 	os_free(name->alt_email);
879 	name->alt_email = os_zalloc(len + 1);
880 	if (name->alt_email == NULL)
881 		return -1;
882 	os_memcpy(name->alt_email, pos, len);
883 	if (os_strlen(name->alt_email) != len) {
884 		wpa_printf(MSG_INFO, "X509: Reject certificate with "
885 			   "embedded NUL byte in rfc822Name (%s[NUL])",
886 			   name->alt_email);
887 		os_free(name->alt_email);
888 		name->alt_email = NULL;
889 		return -1;
890 	}
891 	return 0;
892 }
893 
894 
x509_parse_alt_name_dns(struct x509_name * name,const u8 * pos,size_t len)895 static int x509_parse_alt_name_dns(struct x509_name *name,
896 				   const u8 *pos, size_t len)
897 {
898 	/* dNSName IA5String */
899 	wpa_hexdump_ascii(MSG_MSGDUMP, "X509: altName - dNSName", pos, len);
900 	os_free(name->dns);
901 	name->dns = os_zalloc(len + 1);
902 	if (name->dns == NULL)
903 		return -1;
904 	os_memcpy(name->dns, pos, len);
905 	if (os_strlen(name->dns) != len) {
906 		wpa_printf(MSG_INFO, "X509: Reject certificate with "
907 			   "embedded NUL byte in dNSName (%s[NUL])",
908 			   name->dns);
909 		os_free(name->dns);
910 		name->dns = NULL;
911 		return -1;
912 	}
913 	return 0;
914 }
915 
916 
x509_parse_alt_name_uri(struct x509_name * name,const u8 * pos,size_t len)917 static int x509_parse_alt_name_uri(struct x509_name *name,
918 				   const u8 *pos, size_t len)
919 {
920 	/* uniformResourceIdentifier IA5String */
921 	wpa_hexdump_ascii(MSG_MSGDUMP,
922 			  "X509: altName - uniformResourceIdentifier",
923 			  pos, len);
924 	os_free(name->uri);
925 	name->uri = os_zalloc(len + 1);
926 	if (name->uri == NULL)
927 		return -1;
928 	os_memcpy(name->uri, pos, len);
929 	if (os_strlen(name->uri) != len) {
930 		wpa_printf(MSG_INFO, "X509: Reject certificate with "
931 			   "embedded NUL byte in uniformResourceIdentifier "
932 			   "(%s[NUL])", name->uri);
933 		os_free(name->uri);
934 		name->uri = NULL;
935 		return -1;
936 	}
937 	return 0;
938 }
939 
940 
x509_parse_alt_name_ip(struct x509_name * name,const u8 * pos,size_t len)941 static int x509_parse_alt_name_ip(struct x509_name *name,
942 				       const u8 *pos, size_t len)
943 {
944 	/* iPAddress OCTET STRING */
945 	wpa_hexdump(MSG_MSGDUMP, "X509: altName - iPAddress", pos, len);
946 	os_free(name->ip);
947 	name->ip = os_memdup(pos, len);
948 	if (name->ip == NULL)
949 		return -1;
950 	name->ip_len = len;
951 	return 0;
952 }
953 
954 
x509_parse_alt_name_rid(struct x509_name * name,const u8 * pos,size_t len)955 static int x509_parse_alt_name_rid(struct x509_name *name,
956 				   const u8 *pos, size_t len)
957 {
958 	char buf[80];
959 
960 	/* registeredID OBJECT IDENTIFIER */
961 	if (asn1_parse_oid(pos, len, &name->rid) < 0)
962 		return -1;
963 
964 	asn1_oid_to_str(&name->rid, buf, sizeof(buf));
965 	wpa_printf(MSG_MSGDUMP, "X509: altName - registeredID: %s", buf);
966 
967 	return 0;
968 }
969 
970 
x509_parse_ext_alt_name(struct x509_name * name,const u8 * pos,size_t len)971 static int x509_parse_ext_alt_name(struct x509_name *name,
972 				   const u8 *pos, size_t len)
973 {
974 	struct asn1_hdr hdr;
975 	const u8 *p, *end;
976 
977 	/*
978 	 * GeneralNames ::= SEQUENCE SIZE (1..MAX) OF GeneralName
979 	 *
980 	 * GeneralName ::= CHOICE {
981 	 *     otherName                       [0]     OtherName,
982 	 *     rfc822Name                      [1]     IA5String,
983 	 *     dNSName                         [2]     IA5String,
984 	 *     x400Address                     [3]     ORAddress,
985 	 *     directoryName                   [4]     Name,
986 	 *     ediPartyName                    [5]     EDIPartyName,
987 	 *     uniformResourceIdentifier       [6]     IA5String,
988 	 *     iPAddress                       [7]     OCTET STRING,
989 	 *     registeredID                    [8]     OBJECT IDENTIFIER }
990 	 *
991 	 * OtherName ::= SEQUENCE {
992 	 *     type-id    OBJECT IDENTIFIER,
993 	 *     value      [0] EXPLICIT ANY DEFINED BY type-id }
994 	 *
995 	 * EDIPartyName ::= SEQUENCE {
996 	 *     nameAssigner            [0]     DirectoryString OPTIONAL,
997 	 *     partyName               [1]     DirectoryString }
998 	 */
999 
1000 	for (p = pos, end = pos + len; p < end; p = hdr.payload + hdr.length) {
1001 		int res;
1002 
1003 		if (asn1_get_next(p, end - p, &hdr) < 0) {
1004 			wpa_printf(MSG_DEBUG, "X509: Failed to parse "
1005 				   "SubjectAltName item");
1006 			return -1;
1007 		}
1008 
1009 		if (hdr.class != ASN1_CLASS_CONTEXT_SPECIFIC)
1010 			continue;
1011 
1012 		switch (hdr.tag) {
1013 		case 1:
1014 			res = x509_parse_alt_name_rfc8222(name, hdr.payload,
1015 							  hdr.length);
1016 			break;
1017 		case 2:
1018 			res = x509_parse_alt_name_dns(name, hdr.payload,
1019 						      hdr.length);
1020 			break;
1021 		case 6:
1022 			res = x509_parse_alt_name_uri(name, hdr.payload,
1023 						      hdr.length);
1024 			break;
1025 		case 7:
1026 			res = x509_parse_alt_name_ip(name, hdr.payload,
1027 						     hdr.length);
1028 			break;
1029 		case 8:
1030 			res = x509_parse_alt_name_rid(name, hdr.payload,
1031 						      hdr.length);
1032 			break;
1033 		case 0: /* TODO: otherName */
1034 		case 3: /* TODO: x500Address */
1035 		case 4: /* TODO: directoryName */
1036 		case 5: /* TODO: ediPartyName */
1037 		default:
1038 			res = 0;
1039 			break;
1040 		}
1041 		if (res < 0)
1042 			return res;
1043 	}
1044 
1045 	return 0;
1046 }
1047 
1048 
x509_parse_ext_subject_alt_name(struct x509_certificate * cert,const u8 * pos,size_t len)1049 static int x509_parse_ext_subject_alt_name(struct x509_certificate *cert,
1050 					   const u8 *pos, size_t len)
1051 {
1052 	struct asn1_hdr hdr;
1053 
1054 	/* SubjectAltName ::= GeneralNames */
1055 
1056 	if (asn1_get_next(pos, len, &hdr) < 0 || !asn1_is_sequence(&hdr)) {
1057 		asn1_unexpected(&hdr,
1058 				"X509: Expected SEQUENCE in SubjectAltName");
1059 		return -1;
1060 	}
1061 
1062 	wpa_printf(MSG_DEBUG, "X509: SubjectAltName");
1063 	cert->extensions_present |= X509_EXT_SUBJECT_ALT_NAME;
1064 
1065 	if (hdr.length == 0)
1066 		return 0;
1067 
1068 	return x509_parse_ext_alt_name(&cert->subject, hdr.payload,
1069 				       hdr.length);
1070 }
1071 
1072 
x509_parse_ext_issuer_alt_name(struct x509_certificate * cert,const u8 * pos,size_t len)1073 static int x509_parse_ext_issuer_alt_name(struct x509_certificate *cert,
1074 					  const u8 *pos, size_t len)
1075 {
1076 	struct asn1_hdr hdr;
1077 
1078 	/* IssuerAltName ::= GeneralNames */
1079 
1080 	if (asn1_get_next(pos, len, &hdr) < 0 || !asn1_is_sequence(&hdr)) {
1081 		asn1_unexpected(&hdr,
1082 				"X509: Expected SEQUENCE in IssuerAltName");
1083 		return -1;
1084 	}
1085 
1086 	wpa_printf(MSG_DEBUG, "X509: IssuerAltName");
1087 	cert->extensions_present |= X509_EXT_ISSUER_ALT_NAME;
1088 
1089 	if (hdr.length == 0)
1090 		return 0;
1091 
1092 	return x509_parse_ext_alt_name(&cert->issuer, hdr.payload,
1093 				       hdr.length);
1094 }
1095 
1096 
x509_id_cert_policy_any_oid(struct asn1_oid * oid)1097 static int x509_id_cert_policy_any_oid(struct asn1_oid *oid)
1098 {
1099 	return oid->len == 5 &&
1100 		oid->oid[0] == 2 /* iso/itu-t */ &&
1101 		oid->oid[1] == 5 /* X.500 Directory Services */ &&
1102 		oid->oid[2] == 29 /* id-ce */ &&
1103 		oid->oid[3] == 32 /* id-ce-certificate-policies */ &&
1104 		oid->oid[4] == 0 /* anyPolicy */;
1105 }
1106 
1107 
x509_id_wfa_oid(struct asn1_oid * oid)1108 static int x509_id_wfa_oid(struct asn1_oid *oid)
1109 {
1110 	return oid->len >= 7 &&
1111 		oid->oid[0] == 1 /* iso */ &&
1112 		oid->oid[1] == 3 /* identified-organization */ &&
1113 		oid->oid[2] == 6 /* dod */ &&
1114 		oid->oid[3] == 1 /* internet */ &&
1115 		oid->oid[4] == 4 /* private */ &&
1116 		oid->oid[5] == 1 /* enterprise */ &&
1117 		oid->oid[6] == 40808 /* WFA */;
1118 }
1119 
1120 
x509_id_wfa_tod_oid(struct asn1_oid * oid)1121 static int x509_id_wfa_tod_oid(struct asn1_oid *oid)
1122 {
1123 	return oid->len >= 9 &&
1124 		x509_id_wfa_oid(oid) &&
1125 		oid->oid[7] == 1 &&
1126 		oid->oid[8] == 3;
1127 }
1128 
1129 
x509_id_wfa_tod_strict_oid(struct asn1_oid * oid)1130 static int x509_id_wfa_tod_strict_oid(struct asn1_oid *oid)
1131 {
1132 	return oid->len == 10 &&
1133 		x509_id_wfa_tod_oid(oid) &&
1134 		oid->oid[9] == 1;
1135 }
1136 
1137 
x509_id_wfa_tod_tofu_oid(struct asn1_oid * oid)1138 static int x509_id_wfa_tod_tofu_oid(struct asn1_oid *oid)
1139 {
1140 	return oid->len == 10 &&
1141 		x509_id_wfa_tod_oid(oid) &&
1142 		oid->oid[9] == 2;
1143 }
1144 
1145 
x509_parse_ext_certificate_policies(struct x509_certificate * cert,const u8 * pos,size_t len)1146 static int x509_parse_ext_certificate_policies(struct x509_certificate *cert,
1147 					       const u8 *pos, size_t len)
1148 {
1149 	struct asn1_hdr hdr;
1150 	const u8 *end;
1151 
1152 	/*
1153 	 * certificatePolicies ::= SEQUENCE SIZE (1..MAX) OF PolicyInformation
1154 	 *
1155 	 * PolicyInformation ::= SEQUENCE {
1156 	 *      policyIdentifier   CertPolicyId,
1157 	 *      policyQualifiers   SEQUENCE SIZE (1..MAX) OF
1158 	 *                              PolicyQualifierInfo OPTIONAL }
1159 	 *
1160 	 * CertPolicyId ::= OBJECT IDENTIFIER
1161 	 */
1162 
1163 	if (asn1_get_next(pos, len, &hdr) < 0 || !asn1_is_sequence(&hdr)) {
1164 		asn1_unexpected(&hdr,
1165 				"X509: Expected SEQUENCE (certificatePolicies)");
1166 		return -1;
1167 	}
1168 	if (hdr.length > pos + len - hdr.payload)
1169 		return -1;
1170 	pos = hdr.payload;
1171 	end = pos + hdr.length;
1172 
1173 	wpa_hexdump(MSG_MSGDUMP, "X509: certificatePolicies", pos, end - pos);
1174 
1175 	while (pos < end) {
1176 		const u8 *pol_end;
1177 		struct asn1_oid oid;
1178 		char buf[80];
1179 
1180 		if (asn1_get_next(pos, end - pos, &hdr) < 0 ||
1181 		    !asn1_is_sequence(&hdr)) {
1182 			asn1_unexpected(&hdr,
1183 					"X509: Expected SEQUENCE (PolicyInformation)");
1184 			return -1;
1185 		}
1186 		if (hdr.length > end - hdr.payload)
1187 			return -1;
1188 		pos = hdr.payload;
1189 		pol_end = pos + hdr.length;
1190 		wpa_hexdump(MSG_MSGDUMP, "X509: PolicyInformation",
1191 			    pos, pol_end - pos);
1192 
1193 		if (asn1_get_oid(pos, pol_end - pos, &oid, &pos))
1194 			return -1;
1195 		if (x509_id_cert_policy_any_oid(&oid)) {
1196 			os_strlcpy(buf, "anyPolicy-STRICT", sizeof(buf));
1197 			cert->certificate_policy |=
1198 				X509_EXT_CERT_POLICY_ANY;
1199 		} else if (x509_id_wfa_tod_strict_oid(&oid)) {
1200 			os_strlcpy(buf, "TOD-STRICT", sizeof(buf));
1201 			cert->certificate_policy |=
1202 				X509_EXT_CERT_POLICY_TOD_STRICT;
1203 		} else if (x509_id_wfa_tod_tofu_oid(&oid)) {
1204 			os_strlcpy(buf, "TOD-TOFU", sizeof(buf));
1205 			cert->certificate_policy |=
1206 				X509_EXT_CERT_POLICY_TOD_TOFU;
1207 		} else {
1208 			asn1_oid_to_str(&oid, buf, sizeof(buf));
1209 		}
1210 		wpa_printf(MSG_DEBUG, "policyIdentifier: %s", buf);
1211 
1212 		pos = pol_end;
1213 	}
1214 
1215 	cert->extensions_present |= X509_EXT_CERTIFICATE_POLICY;
1216 
1217 	return 0;
1218 }
1219 
1220 
x509_id_pkix_oid(struct asn1_oid * oid)1221 static int x509_id_pkix_oid(struct asn1_oid *oid)
1222 {
1223 	return oid->len >= 7 &&
1224 		oid->oid[0] == 1 /* iso */ &&
1225 		oid->oid[1] == 3 /* identified-organization */ &&
1226 		oid->oid[2] == 6 /* dod */ &&
1227 		oid->oid[3] == 1 /* internet */ &&
1228 		oid->oid[4] == 5 /* security */ &&
1229 		oid->oid[5] == 5 /* mechanisms */ &&
1230 		oid->oid[6] == 7 /* id-pkix */;
1231 }
1232 
1233 
x509_id_kp_oid(struct asn1_oid * oid)1234 static int x509_id_kp_oid(struct asn1_oid *oid)
1235 {
1236 	/* id-kp */
1237 	return oid->len >= 8 &&
1238 		x509_id_pkix_oid(oid) &&
1239 		oid->oid[7] == 3 /* id-kp */;
1240 }
1241 
1242 
x509_id_kp_server_auth_oid(struct asn1_oid * oid)1243 static int x509_id_kp_server_auth_oid(struct asn1_oid *oid)
1244 {
1245 	/* id-kp */
1246 	return oid->len == 9 &&
1247 		x509_id_kp_oid(oid) &&
1248 		oid->oid[8] == 1 /* id-kp-serverAuth */;
1249 }
1250 
1251 
x509_id_kp_client_auth_oid(struct asn1_oid * oid)1252 static int x509_id_kp_client_auth_oid(struct asn1_oid *oid)
1253 {
1254 	/* id-kp */
1255 	return oid->len == 9 &&
1256 		x509_id_kp_oid(oid) &&
1257 		oid->oid[8] == 2 /* id-kp-clientAuth */;
1258 }
1259 
1260 
x509_id_kp_ocsp_oid(struct asn1_oid * oid)1261 static int x509_id_kp_ocsp_oid(struct asn1_oid *oid)
1262 {
1263 	/* id-kp */
1264 	return oid->len == 9 &&
1265 		x509_id_kp_oid(oid) &&
1266 		oid->oid[8] == 9 /* id-kp-OCSPSigning */;
1267 }
1268 
1269 
x509_parse_ext_ext_key_usage(struct x509_certificate * cert,const u8 * pos,size_t len)1270 static int x509_parse_ext_ext_key_usage(struct x509_certificate *cert,
1271 					const u8 *pos, size_t len)
1272 {
1273 	struct asn1_hdr hdr;
1274 	const u8 *end;
1275 	struct asn1_oid oid;
1276 
1277 	/*
1278 	 * ExtKeyUsageSyntax ::= SEQUENCE SIZE (1..MAX) OF KeyPurposeId
1279 	 *
1280 	 * KeyPurposeId ::= OBJECT IDENTIFIER
1281 	 */
1282 
1283 	if (asn1_get_next(pos, len, &hdr) < 0 || !asn1_is_sequence(&hdr)) {
1284 		asn1_unexpected(&hdr,
1285 				"X509: Expected SEQUENCE (ExtKeyUsageSyntax)");
1286 		return -1;
1287 	}
1288 	if (hdr.length > pos + len - hdr.payload)
1289 		return -1;
1290 	pos = hdr.payload;
1291 	end = pos + hdr.length;
1292 
1293 	wpa_hexdump(MSG_MSGDUMP, "X509: ExtKeyUsageSyntax", pos, end - pos);
1294 
1295 	while (pos < end) {
1296 		char buf[80];
1297 
1298 		if (asn1_get_oid(pos, end - pos, &oid, &pos))
1299 			return -1;
1300 		if (x509_any_ext_key_usage_oid(&oid)) {
1301 			os_strlcpy(buf, "anyExtendedKeyUsage", sizeof(buf));
1302 			cert->ext_key_usage |= X509_EXT_KEY_USAGE_ANY;
1303 		} else if (x509_id_kp_server_auth_oid(&oid)) {
1304 			os_strlcpy(buf, "id-kp-serverAuth", sizeof(buf));
1305 			cert->ext_key_usage |= X509_EXT_KEY_USAGE_SERVER_AUTH;
1306 		} else if (x509_id_kp_client_auth_oid(&oid)) {
1307 			os_strlcpy(buf, "id-kp-clientAuth", sizeof(buf));
1308 			cert->ext_key_usage |= X509_EXT_KEY_USAGE_CLIENT_AUTH;
1309 		} else if (x509_id_kp_ocsp_oid(&oid)) {
1310 			os_strlcpy(buf, "id-kp-OCSPSigning", sizeof(buf));
1311 			cert->ext_key_usage |= X509_EXT_KEY_USAGE_OCSP;
1312 		} else {
1313 			asn1_oid_to_str(&oid, buf, sizeof(buf));
1314 		}
1315 		wpa_printf(MSG_DEBUG, "ExtKeyUsage KeyPurposeId: %s", buf);
1316 	}
1317 
1318 	cert->extensions_present |= X509_EXT_EXT_KEY_USAGE;
1319 
1320 	return 0;
1321 }
1322 
1323 
x509_parse_extension_data(struct x509_certificate * cert,struct asn1_oid * oid,const u8 * pos,size_t len)1324 static int x509_parse_extension_data(struct x509_certificate *cert,
1325 				     struct asn1_oid *oid,
1326 				     const u8 *pos, size_t len)
1327 {
1328 	if (!x509_id_ce_oid(oid))
1329 		return 1;
1330 
1331 	/* TODO: add other extensions required by RFC 3280, Ch 4.2:
1332 	 * name constraints (section 4.2.1.11)
1333 	 * policy constraints (section 4.2.1.12)
1334 	 * inhibit any-policy (section 4.2.1.15)
1335 	 */
1336 	switch (oid->oid[3]) {
1337 	case 15: /* id-ce-keyUsage */
1338 		return x509_parse_ext_key_usage(cert, pos, len);
1339 	case 17: /* id-ce-subjectAltName */
1340 		return x509_parse_ext_subject_alt_name(cert, pos, len);
1341 	case 18: /* id-ce-issuerAltName */
1342 		return x509_parse_ext_issuer_alt_name(cert, pos, len);
1343 	case 19: /* id-ce-basicConstraints */
1344 		return x509_parse_ext_basic_constraints(cert, pos, len);
1345 	case 32: /* id-ce-certificatePolicies */
1346 		return x509_parse_ext_certificate_policies(cert, pos, len);
1347 	case 37: /* id-ce-extKeyUsage */
1348 		return x509_parse_ext_ext_key_usage(cert, pos, len);
1349 	default:
1350 		return 1;
1351 	}
1352 }
1353 
1354 
x509_parse_extension(struct x509_certificate * cert,const u8 * pos,size_t len,const u8 ** next)1355 static int x509_parse_extension(struct x509_certificate *cert,
1356 				const u8 *pos, size_t len, const u8 **next)
1357 {
1358 	const u8 *end;
1359 	struct asn1_hdr hdr;
1360 	struct asn1_oid oid;
1361 	int critical_ext = 0, res;
1362 	char buf[80];
1363 
1364 	/*
1365 	 * Extension  ::=  SEQUENCE  {
1366 	 *     extnID      OBJECT IDENTIFIER,
1367 	 *     critical    BOOLEAN DEFAULT FALSE,
1368 	 *     extnValue   OCTET STRING
1369 	 * }
1370 	 */
1371 
1372 	if (asn1_get_next(pos, len, &hdr) < 0 || !asn1_is_sequence(&hdr)) {
1373 		asn1_unexpected(&hdr, "X509: Expected SEQUENCE in Extensions");
1374 		return -1;
1375 	}
1376 	pos = hdr.payload;
1377 	*next = end = pos + hdr.length;
1378 
1379 	if (asn1_get_oid(pos, end - pos, &oid, &pos) < 0) {
1380 		wpa_printf(MSG_DEBUG, "X509: Unexpected ASN.1 data for "
1381 			   "Extension (expected OID)");
1382 		return -1;
1383 	}
1384 
1385 	if (asn1_get_next(pos, end - pos, &hdr) < 0 ||
1386 	    (!asn1_is_boolean(&hdr) && !asn1_is_octetstring(&hdr))) {
1387 		asn1_unexpected(&hdr,
1388 				"X509: Expected BOOLEAN or OCTETSTRING in Extensions");
1389 		return -1;
1390 	}
1391 
1392 	if (hdr.tag == ASN1_TAG_BOOLEAN) {
1393 		critical_ext = hdr.payload[0];
1394 		pos = hdr.payload;
1395 		/*
1396 		 * Number of CA certificates seem to be using Private class in
1397 		 * one of the X.509v3 extensions, so let's accept that instead
1398 		 * of rejecting the certificate. asn1_is_octetstring() covers
1399 		 * the more common case.
1400 		 */
1401 		if (asn1_get_next(pos, end - pos, &hdr) < 0 ||
1402 		    (!asn1_is_octetstring(&hdr) &&
1403 		     !(hdr.class == ASN1_CLASS_PRIVATE &&
1404 		       hdr.tag == ASN1_TAG_OCTETSTRING))) {
1405 			asn1_unexpected(&hdr,
1406 					"X509: Expected OCTETSTRING in Extensions");
1407 			return -1;
1408 		}
1409 	}
1410 
1411 	asn1_oid_to_str(&oid, buf, sizeof(buf));
1412 	wpa_printf(MSG_DEBUG, "X509: Extension: extnID=%s critical=%d",
1413 		   buf, critical_ext);
1414 	wpa_hexdump(MSG_MSGDUMP, "X509: extnValue", hdr.payload, hdr.length);
1415 
1416 	res = x509_parse_extension_data(cert, &oid, hdr.payload, hdr.length);
1417 	if (res < 0)
1418 		return res;
1419 	if (res == 1 && critical_ext) {
1420 		wpa_printf(MSG_INFO, "X509: Unknown critical extension %s",
1421 			   buf);
1422 		return -1;
1423 	}
1424 
1425 	return 0;
1426 }
1427 
1428 
x509_parse_extensions(struct x509_certificate * cert,const u8 * pos,size_t len)1429 static int x509_parse_extensions(struct x509_certificate *cert,
1430 				 const u8 *pos, size_t len)
1431 {
1432 	const u8 *end;
1433 	struct asn1_hdr hdr;
1434 
1435 	/* Extensions  ::=  SEQUENCE SIZE (1..MAX) OF Extension */
1436 
1437 	if (asn1_get_next(pos, len, &hdr) < 0 || !asn1_is_sequence(&hdr)) {
1438 		asn1_unexpected(&hdr, "X509: Expected SEQUENCE for Extensions");
1439 		return -1;
1440 	}
1441 
1442 	pos = hdr.payload;
1443 	end = pos + hdr.length;
1444 
1445 	while (pos < end) {
1446 		if (x509_parse_extension(cert, pos, end - pos, &pos)
1447 		    < 0)
1448 			return -1;
1449 	}
1450 
1451 	return 0;
1452 }
1453 
1454 
x509_parse_tbs_certificate(const u8 * buf,size_t len,struct x509_certificate * cert,const u8 ** next)1455 static int x509_parse_tbs_certificate(const u8 *buf, size_t len,
1456 				      struct x509_certificate *cert,
1457 				      const u8 **next)
1458 {
1459 	struct asn1_hdr hdr;
1460 	const u8 *pos, *end;
1461 	size_t left;
1462 	char sbuf[128];
1463 	unsigned long value;
1464 	const u8 *subject_dn;
1465 
1466 	/* tbsCertificate TBSCertificate ::= SEQUENCE */
1467 	if (asn1_get_next(buf, len, &hdr) < 0 || !asn1_is_sequence(&hdr)) {
1468 		asn1_unexpected(&hdr,
1469 				"X509: tbsCertificate did not start with a valid SEQUENCE");
1470 		return -1;
1471 	}
1472 	pos = hdr.payload;
1473 	end = *next = pos + hdr.length;
1474 
1475 	/*
1476 	 * version [0]  EXPLICIT Version DEFAULT v1
1477 	 * Version  ::=  INTEGER  {  v1(0), v2(1), v3(2)  }
1478 	 */
1479 	if (asn1_get_next(pos, end - pos, &hdr) < 0)
1480 		return -1;
1481 	pos = hdr.payload;
1482 
1483 	if (asn1_is_cs_tag(&hdr, 0) && hdr.constructed) {
1484 		if (asn1_get_next(pos, end - pos, &hdr) < 0 ||
1485 		    !asn1_is_integer(&hdr)) {
1486 			asn1_unexpected(&hdr,
1487 					"X509: No INTEGER tag found for version field");
1488 			return -1;
1489 		}
1490 		if (hdr.length != 1) {
1491 			wpa_printf(MSG_DEBUG, "X509: Unexpected version field "
1492 				   "length %u (expected 1)", hdr.length);
1493 			return -1;
1494 		}
1495 		pos = hdr.payload;
1496 		left = hdr.length;
1497 		value = 0;
1498 		while (left) {
1499 			value <<= 8;
1500 			value |= *pos++;
1501 			left--;
1502 		}
1503 
1504 		cert->version = value;
1505 		if (cert->version != X509_CERT_V1 &&
1506 		    cert->version != X509_CERT_V2 &&
1507 		    cert->version != X509_CERT_V3) {
1508 			wpa_printf(MSG_DEBUG, "X509: Unsupported version %d",
1509 				   cert->version + 1);
1510 			return -1;
1511 		}
1512 
1513 		if (asn1_get_next(pos, end - pos, &hdr) < 0)
1514 			return -1;
1515 	} else
1516 		cert->version = X509_CERT_V1;
1517 	wpa_printf(MSG_MSGDUMP, "X509: Version X.509v%d", cert->version + 1);
1518 
1519 	/* serialNumber CertificateSerialNumber ::= INTEGER */
1520 	if (!asn1_is_integer(&hdr) ||
1521 	    hdr.length < 1 || hdr.length > X509_MAX_SERIAL_NUM_LEN) {
1522 		asn1_unexpected(&hdr,
1523 				"X509: No INTEGER tag found for serialNumber");
1524 		return -1;
1525 	}
1526 
1527 	pos = hdr.payload + hdr.length;
1528 	while (hdr.length > 0 && hdr.payload[0] == 0) {
1529 		hdr.payload++;
1530 		hdr.length--;
1531 	}
1532 	os_memcpy(cert->serial_number, hdr.payload, hdr.length);
1533 	cert->serial_number_len = hdr.length;
1534 	wpa_hexdump(MSG_MSGDUMP, "X509: serialNumber", cert->serial_number,
1535 		    cert->serial_number_len);
1536 
1537 	/* signature AlgorithmIdentifier */
1538 	if (x509_parse_algorithm_identifier(pos, end - pos, &cert->signature,
1539 					    &pos))
1540 		return -1;
1541 
1542 	/* issuer Name */
1543 	if (x509_parse_name(pos, end - pos, &cert->issuer, &pos))
1544 		return -1;
1545 	x509_name_string(&cert->issuer, sbuf, sizeof(sbuf));
1546 	wpa_printf(MSG_MSGDUMP, "X509: issuer %s", sbuf);
1547 
1548 	/* validity Validity */
1549 	if (x509_parse_validity(pos, end - pos, cert, &pos))
1550 		return -1;
1551 
1552 	/* subject Name */
1553 	subject_dn = pos;
1554 	if (x509_parse_name(pos, end - pos, &cert->subject, &pos))
1555 		return -1;
1556 	cert->subject_dn = os_malloc(pos - subject_dn);
1557 	if (!cert->subject_dn)
1558 		return -1;
1559 	cert->subject_dn_len = pos - subject_dn;
1560 	os_memcpy(cert->subject_dn, subject_dn, cert->subject_dn_len);
1561 	x509_name_string(&cert->subject, sbuf, sizeof(sbuf));
1562 	wpa_printf(MSG_MSGDUMP, "X509: subject %s", sbuf);
1563 
1564 	/* subjectPublicKeyInfo SubjectPublicKeyInfo */
1565 	if (x509_parse_public_key(pos, end - pos, cert, &pos))
1566 		return -1;
1567 
1568 	if (pos == end)
1569 		return 0;
1570 
1571 	if (cert->version == X509_CERT_V1)
1572 		return 0;
1573 
1574 	if (asn1_get_next(pos, end - pos, &hdr) < 0 ||
1575 	    hdr.class != ASN1_CLASS_CONTEXT_SPECIFIC) {
1576 		asn1_unexpected(&hdr,
1577 				"X509: Expected Context-Specific tag to parse optional tbsCertificate field(s)");
1578 		return -1;
1579 	}
1580 
1581 	if (hdr.tag == 1) {
1582 		/* issuerUniqueID  [1]  IMPLICIT UniqueIdentifier OPTIONAL */
1583 		wpa_printf(MSG_DEBUG, "X509: issuerUniqueID");
1584 		/* TODO: parse UniqueIdentifier ::= BIT STRING */
1585 
1586 		pos = hdr.payload + hdr.length;
1587 		if (pos == end)
1588 			return 0;
1589 
1590 		if (asn1_get_next(pos, end - pos, &hdr) < 0 ||
1591 		    hdr.class != ASN1_CLASS_CONTEXT_SPECIFIC) {
1592 			asn1_unexpected(&hdr,
1593 					"X509: Expected Context-Specific tag to parse optional tbsCertificate field(s)");
1594 			return -1;
1595 		}
1596 	}
1597 
1598 	if (hdr.tag == 2) {
1599 		/* subjectUniqueID [2]  IMPLICIT UniqueIdentifier OPTIONAL */
1600 		wpa_printf(MSG_DEBUG, "X509: subjectUniqueID");
1601 		/* TODO: parse UniqueIdentifier ::= BIT STRING */
1602 
1603 		pos = hdr.payload + hdr.length;
1604 		if (pos == end)
1605 			return 0;
1606 
1607 		if (asn1_get_next(pos, end - pos, &hdr) < 0 ||
1608 		    hdr.class != ASN1_CLASS_CONTEXT_SPECIFIC) {
1609 			asn1_unexpected(&hdr,
1610 					"X509: Expected Context-Specific tag to parse optional tbsCertificate field(s)");
1611 			return -1;
1612 		}
1613 	}
1614 
1615 	if (hdr.tag != 3) {
1616 		wpa_printf(MSG_DEBUG,
1617 			   "X509: Ignored unexpected Context-Specific constructed %d tag %d in optional tbsCertificate fields",
1618 			   hdr.constructed, hdr.tag);
1619 		return 0;
1620 	}
1621 
1622 	/* extensions      [3]  EXPLICIT Extensions OPTIONAL */
1623 
1624 	if (cert->version != X509_CERT_V3) {
1625 		wpa_printf(MSG_DEBUG, "X509: X.509%d certificate and "
1626 			   "Extensions data which are only allowed for "
1627 			   "version 3", cert->version + 1);
1628 		return -1;
1629 	}
1630 
1631 	if (x509_parse_extensions(cert, hdr.payload, hdr.length) < 0)
1632 		return -1;
1633 
1634 	pos = hdr.payload + hdr.length;
1635 	if (pos < end) {
1636 		wpa_hexdump(MSG_DEBUG,
1637 			    "X509: Ignored extra tbsCertificate data",
1638 			    pos, end - pos);
1639 	}
1640 
1641 	return 0;
1642 }
1643 
1644 
x509_rsadsi_oid(struct asn1_oid * oid)1645 static int x509_rsadsi_oid(struct asn1_oid *oid)
1646 {
1647 	return oid->len >= 4 &&
1648 		oid->oid[0] == 1 /* iso */ &&
1649 		oid->oid[1] == 2 /* member-body */ &&
1650 		oid->oid[2] == 840 /* us */ &&
1651 		oid->oid[3] == 113549 /* rsadsi */;
1652 }
1653 
1654 
x509_pkcs_oid(struct asn1_oid * oid)1655 static int x509_pkcs_oid(struct asn1_oid *oid)
1656 {
1657 	return oid->len >= 5 &&
1658 		x509_rsadsi_oid(oid) &&
1659 		oid->oid[4] == 1 /* pkcs */;
1660 }
1661 
1662 
x509_digest_oid(struct asn1_oid * oid)1663 static int x509_digest_oid(struct asn1_oid *oid)
1664 {
1665 	return oid->len >= 5 &&
1666 		x509_rsadsi_oid(oid) &&
1667 		oid->oid[4] == 2 /* digestAlgorithm */;
1668 }
1669 
1670 
x509_sha1_oid(struct asn1_oid * oid)1671 int x509_sha1_oid(struct asn1_oid *oid)
1672 {
1673 	return oid->len == 6 &&
1674 		oid->oid[0] == 1 /* iso */ &&
1675 		oid->oid[1] == 3 /* identified-organization */ &&
1676 		oid->oid[2] == 14 /* oiw */ &&
1677 		oid->oid[3] == 3 /* secsig */ &&
1678 		oid->oid[4] == 2 /* algorithms */ &&
1679 		oid->oid[5] == 26 /* id-sha1 */;
1680 }
1681 
1682 
x509_sha2_oid(struct asn1_oid * oid)1683 static int x509_sha2_oid(struct asn1_oid *oid)
1684 {
1685 	return oid->len == 9 &&
1686 		oid->oid[0] == 2 /* joint-iso-itu-t */ &&
1687 		oid->oid[1] == 16 /* country */ &&
1688 		oid->oid[2] == 840 /* us */ &&
1689 		oid->oid[3] == 1 /* organization */ &&
1690 		oid->oid[4] == 101 /* gov */ &&
1691 		oid->oid[5] == 3 /* csor */ &&
1692 		oid->oid[6] == 4 /* nistAlgorithm */ &&
1693 		oid->oid[7] == 2 /* hashAlgs */;
1694 }
1695 
1696 
x509_sha256_oid(struct asn1_oid * oid)1697 int x509_sha256_oid(struct asn1_oid *oid)
1698 {
1699 	return x509_sha2_oid(oid) &&
1700 		oid->oid[8] == 1 /* sha256 */;
1701 }
1702 
1703 
x509_sha384_oid(struct asn1_oid * oid)1704 int x509_sha384_oid(struct asn1_oid *oid)
1705 {
1706 	return x509_sha2_oid(oid) &&
1707 		oid->oid[8] == 2 /* sha384 */;
1708 }
1709 
1710 
x509_sha512_oid(struct asn1_oid * oid)1711 int x509_sha512_oid(struct asn1_oid *oid)
1712 {
1713 	return x509_sha2_oid(oid) &&
1714 		oid->oid[8] == 3 /* sha512 */;
1715 }
1716 
1717 
1718 /**
1719  * x509_certificate_parse - Parse a X.509 certificate in DER format
1720  * @buf: Pointer to the X.509 certificate in DER format
1721  * @len: Buffer length
1722  * Returns: Pointer to the parsed certificate or %NULL on failure
1723  *
1724  * Caller is responsible for freeing the returned certificate by calling
1725  * x509_certificate_free().
1726  */
x509_certificate_parse(const u8 * buf,size_t len)1727 struct x509_certificate * x509_certificate_parse(const u8 *buf, size_t len)
1728 {
1729 	struct asn1_hdr hdr;
1730 	const u8 *pos, *end, *hash_start;
1731 	struct x509_certificate *cert;
1732 
1733 	cert = os_zalloc(sizeof(*cert) + len);
1734 	if (cert == NULL)
1735 		return NULL;
1736 	os_memcpy(cert + 1, buf, len);
1737 	cert->cert_start = (u8 *) (cert + 1);
1738 	cert->cert_len = len;
1739 
1740 	pos = buf;
1741 	end = buf + len;
1742 
1743 	/* RFC 3280 - X.509 v3 certificate / ASN.1 DER */
1744 
1745 	/* Certificate ::= SEQUENCE */
1746 	if (asn1_get_next(pos, len, &hdr) < 0 || !asn1_is_sequence(&hdr)) {
1747 		asn1_unexpected(&hdr,
1748 				"X509: Certificate did not start with a valid SEQUENCE");
1749 		x509_certificate_free(cert);
1750 		return NULL;
1751 	}
1752 	pos = hdr.payload;
1753 
1754 	if (hdr.length > end - pos) {
1755 		x509_certificate_free(cert);
1756 		return NULL;
1757 	}
1758 
1759 	if (hdr.length < end - pos) {
1760 		wpa_hexdump(MSG_MSGDUMP, "X509: Ignoring extra data after DER "
1761 			    "encoded certificate",
1762 			    pos + hdr.length, end - (pos + hdr.length));
1763 		end = pos + hdr.length;
1764 	}
1765 
1766 	hash_start = pos;
1767 	cert->tbs_cert_start = cert->cert_start + (hash_start - buf);
1768 	if (x509_parse_tbs_certificate(pos, end - pos, cert, &pos)) {
1769 		x509_certificate_free(cert);
1770 		return NULL;
1771 	}
1772 	cert->tbs_cert_len = pos - hash_start;
1773 
1774 	/* signatureAlgorithm AlgorithmIdentifier */
1775 	if (x509_parse_algorithm_identifier(pos, end - pos,
1776 					    &cert->signature_alg, &pos)) {
1777 		x509_certificate_free(cert);
1778 		return NULL;
1779 	}
1780 
1781 	/* signatureValue BIT STRING */
1782 	if (asn1_get_next(pos, end - pos, &hdr) < 0 ||
1783 	    !asn1_is_bitstring(&hdr)) {
1784 		asn1_unexpected(&hdr,
1785 				"X509: Expected BITSTRING (signatureValue)");
1786 		x509_certificate_free(cert);
1787 		return NULL;
1788 	}
1789 	if (hdr.length < 1) {
1790 		x509_certificate_free(cert);
1791 		return NULL;
1792 	}
1793 	pos = hdr.payload;
1794 	if (*pos) {
1795 		wpa_printf(MSG_DEBUG,
1796 			   "X509: BITSTRING (signatureValue) - %d unused bits",
1797 			   *pos);
1798 		/* PKCS #1 v1.5 10.2.1:
1799 		 * It is an error if the length in bits of the signature S is
1800 		 * not a multiple of eight.
1801 		 */
1802 		x509_certificate_free(cert);
1803 		return NULL;
1804 	}
1805 	os_free(cert->sign_value);
1806 	cert->sign_value = os_memdup(pos + 1, hdr.length - 1);
1807 	if (cert->sign_value == NULL) {
1808 		wpa_printf(MSG_DEBUG, "X509: Failed to allocate memory for "
1809 			   "signatureValue");
1810 		x509_certificate_free(cert);
1811 		return NULL;
1812 	}
1813 	cert->sign_value_len = hdr.length - 1;
1814 	wpa_hexdump(MSG_MSGDUMP, "X509: signature",
1815 		    cert->sign_value, cert->sign_value_len);
1816 
1817 	return cert;
1818 }
1819 
1820 
1821 /**
1822  * x509_certificate_check_signature - Verify certificate signature
1823  * @issuer: Issuer certificate
1824  * @cert: Certificate to be verified
1825  * Returns: 0 if cert has a valid signature that was signed by the issuer,
1826  * -1 if not
1827  */
x509_certificate_check_signature(struct x509_certificate * issuer,struct x509_certificate * cert)1828 int x509_certificate_check_signature(struct x509_certificate *issuer,
1829 				     struct x509_certificate *cert)
1830 {
1831 	return x509_check_signature(issuer, &cert->signature,
1832 				    cert->sign_value, cert->sign_value_len,
1833 				    cert->tbs_cert_start, cert->tbs_cert_len);
1834 }
1835 
1836 
x509_check_signature(struct x509_certificate * issuer,struct x509_algorithm_identifier * signature,const u8 * sign_value,size_t sign_value_len,const u8 * signed_data,size_t signed_data_len)1837 int x509_check_signature(struct x509_certificate *issuer,
1838 			 struct x509_algorithm_identifier *signature,
1839 			 const u8 *sign_value, size_t sign_value_len,
1840 			 const u8 *signed_data, size_t signed_data_len)
1841 {
1842 	struct crypto_public_key *pk;
1843 	u8 *data;
1844 	const u8 *pos, *end, *next, *da_end;
1845 	size_t data_len;
1846 	struct asn1_hdr hdr;
1847 	struct asn1_oid oid;
1848 	u8 hash[64];
1849 	size_t hash_len;
1850 	const u8 *addr[1] = { signed_data };
1851 	size_t len[1] = { signed_data_len };
1852 
1853 	if (!x509_pkcs_oid(&signature->oid) ||
1854 	    signature->oid.len != 7 ||
1855 	    signature->oid.oid[5] != 1 /* pkcs-1 */) {
1856 		wpa_printf(MSG_DEBUG, "X509: Unrecognized signature "
1857 			   "algorithm");
1858 		return -1;
1859 	}
1860 
1861 	pk = crypto_public_key_import(issuer->public_key,
1862 				      issuer->public_key_len);
1863 	if (pk == NULL)
1864 		return -1;
1865 
1866 	data_len = sign_value_len;
1867 	data = os_malloc(data_len);
1868 	if (data == NULL) {
1869 		crypto_public_key_free(pk);
1870 		return -1;
1871 	}
1872 
1873 	if (crypto_public_key_decrypt_pkcs1(pk, sign_value,
1874 					    sign_value_len, data,
1875 					    &data_len) < 0) {
1876 		wpa_printf(MSG_DEBUG, "X509: Failed to decrypt signature");
1877 		crypto_public_key_free(pk);
1878 		os_free(data);
1879 		return -1;
1880 	}
1881 	crypto_public_key_free(pk);
1882 
1883 	wpa_hexdump(MSG_MSGDUMP, "X509: Signature data D", data, data_len);
1884 
1885 	/*
1886 	 * PKCS #1 v1.5, 10.1.2:
1887 	 *
1888 	 * DigestInfo ::= SEQUENCE {
1889 	 *     digestAlgorithm DigestAlgorithmIdentifier,
1890 	 *     digest Digest
1891 	 * }
1892 	 *
1893 	 * DigestAlgorithmIdentifier ::= AlgorithmIdentifier
1894 	 *
1895 	 * Digest ::= OCTET STRING
1896 	 *
1897 	 */
1898 	if (asn1_get_next(data, data_len, &hdr) < 0 ||
1899 	    !asn1_is_sequence(&hdr)) {
1900 		asn1_unexpected(&hdr, "X509: Expected SEQUENCE (DigestInfo)");
1901 		os_free(data);
1902 		return -1;
1903 	}
1904 	wpa_hexdump(MSG_MSGDUMP, "X509: DigestInfo", hdr.payload, hdr.length);
1905 
1906     wpa_hexdump(MSG_MSGDUMP, "X509: DigestInfo", hdr.payload, hdr.length);
1907 
1908 	pos = hdr.payload;
1909 	end = pos + hdr.length;
1910 
1911 	/*
1912 	 * X.509:
1913 	 * AlgorithmIdentifier ::= SEQUENCE {
1914 	 *     algorithm            OBJECT IDENTIFIER,
1915 	 *     parameters           ANY DEFINED BY algorithm OPTIONAL
1916 	 * }
1917 	 */
1918 
1919 	if (asn1_get_next(pos, end - pos, &hdr) < 0 ||
1920 	    !asn1_is_sequence(&hdr)) {
1921 		asn1_unexpected(&hdr,
1922 				"X509: Expected SEQUENCE (AlgorithmIdentifier)");
1923 		os_free(data);
1924 		return -1;
1925 	}
1926 	wpa_hexdump(MSG_MSGDUMP, "X509: DigestAlgorithmIdentifier",
1927 		    hdr.payload, hdr.length);
1928 	da_end = hdr.payload + hdr.length;
1929 
1930 	if (asn1_get_oid(hdr.payload, hdr.length, &oid, &next)) {
1931 		wpa_printf(MSG_DEBUG, "X509: Failed to parse digestAlgorithm");
1932 		os_free(data);
1933 		return -1;
1934 	}
1935 	wpa_hexdump(MSG_MSGDUMP, "X509: Digest algorithm parameters",
1936 		    next, da_end - next);
1937 
1938 	/*
1939 	 * RFC 5754: The correct encoding for the SHA2 algorithms would be to
1940 	 * omit the parameters, but there are implementation that encode these
1941 	 * as a NULL element. Allow these two cases and reject anything else.
1942 	 */
1943 	if (da_end > next &&
1944 	    (asn1_get_next(next, da_end - next, &hdr) < 0 ||
1945 	     !asn1_is_null(&hdr) ||
1946 	     hdr.payload + hdr.length != da_end)) {
1947 		wpa_printf(MSG_DEBUG,
1948 			   "X509: Unexpected digest algorithm parameters");
1949 		os_free(data);
1950 		return -1;
1951 	}
1952 
1953 	if (x509_sha1_oid(&oid)) {
1954 		if (signature->oid.oid[6] != 5 /* sha-1WithRSAEncryption */) {
1955 			wpa_printf(MSG_DEBUG, "X509: digestAlgorithm SHA1 "
1956 				   "does not match with certificate "
1957 				   "signatureAlgorithm (%lu)",
1958 				   signature->oid.oid[6]);
1959 			os_free(data);
1960 			return -1;
1961 		}
1962 		goto skip_digest_oid;
1963 	}
1964 
1965 	if (x509_sha256_oid(&oid)) {
1966 		if (signature->oid.oid[6] !=
1967 		    11 /* sha2561WithRSAEncryption */) {
1968 			wpa_printf(MSG_DEBUG, "X509: digestAlgorithm SHA256 "
1969 				   "does not match with certificate "
1970 				   "signatureAlgorithm (%lu)",
1971 				   signature->oid.oid[6]);
1972 			os_free(data);
1973 			return -1;
1974 		}
1975 		goto skip_digest_oid;
1976 	}
1977 
1978 	if (x509_sha384_oid(&oid)) {
1979 		if (signature->oid.oid[6] != 12 /* sha384WithRSAEncryption */) {
1980 			wpa_printf(MSG_DEBUG, "X509: digestAlgorithm SHA384 "
1981 				   "does not match with certificate "
1982 				   "signatureAlgorithm (%lu)",
1983 				   signature->oid.oid[6]);
1984 			os_free(data);
1985 			return -1;
1986 		}
1987 		goto skip_digest_oid;
1988 	}
1989 
1990 	if (x509_sha512_oid(&oid)) {
1991 		if (signature->oid.oid[6] != 13 /* sha512WithRSAEncryption */) {
1992 			wpa_printf(MSG_DEBUG, "X509: digestAlgorithm SHA512 "
1993 				   "does not match with certificate "
1994 				   "signatureAlgorithm (%lu)",
1995 				   signature->oid.oid[6]);
1996 			os_free(data);
1997 			return -1;
1998 		}
1999 		goto skip_digest_oid;
2000 	}
2001 
2002 	if (!x509_digest_oid(&oid)) {
2003 		wpa_printf(MSG_DEBUG, "X509: Unrecognized digestAlgorithm");
2004 		os_free(data);
2005 		return -1;
2006 	}
2007 	switch (oid.oid[5]) {
2008 	case 5: /* md5 */
2009 		if (signature->oid.oid[6] != 4 /* md5WithRSAEncryption */) {
2010 			wpa_printf(MSG_DEBUG, "X509: digestAlgorithm MD5 does "
2011 				   "not match with certificate "
2012 				   "signatureAlgorithm (%lu)",
2013 				   signature->oid.oid[6]);
2014 			os_free(data);
2015 			return -1;
2016 		}
2017 		break;
2018 	case 2: /* md2 */
2019 	case 4: /* md4 */
2020 	default:
2021 		wpa_printf(MSG_DEBUG, "X509: Unsupported digestAlgorithm "
2022 			   "(%lu)", oid.oid[5]);
2023 		os_free(data);
2024 		return -1;
2025 	}
2026 
2027 skip_digest_oid:
2028 	/* Digest ::= OCTET STRING */
2029 	pos = da_end;
2030 
2031 	if (asn1_get_next(pos, end - pos, &hdr) < 0 ||
2032 	    !asn1_is_octetstring(&hdr)) {
2033 		asn1_unexpected(&hdr, "X509: Expected OCTETSTRING (Digest)");
2034 		os_free(data);
2035 		return -1;
2036 	}
2037 	wpa_hexdump(MSG_MSGDUMP, "X509: Decrypted Digest",
2038 		    hdr.payload, hdr.length);
2039 
2040 	switch (signature->oid.oid[6]) {
2041 	case 4: /* md5WithRSAEncryption */
2042 		md5_vector(1, addr, len, hash);
2043 		hash_len = 16;
2044 		wpa_hexdump(MSG_MSGDUMP, "X509: Certificate hash (MD5)",
2045 			    hash, hash_len);
2046 		break;
2047 	case 5: /* sha-1WithRSAEncryption */
2048 		sha1_vector(1, addr, len, hash);
2049 		hash_len = 20;
2050 		wpa_hexdump(MSG_MSGDUMP, "X509: Certificate hash (SHA1)",
2051 			    hash, hash_len);
2052 		break;
2053 	case 11: /* sha256WithRSAEncryption */
2054 		sha256_vector(1, addr, len, hash);
2055 		hash_len = 32;
2056 		wpa_hexdump(MSG_MSGDUMP, "X509: Certificate hash (SHA256)",
2057 			    hash, hash_len);
2058 		break;
2059 	case 12: /* sha384WithRSAEncryption */
2060 		sha384_vector(1, addr, len, hash);
2061 		hash_len = 48;
2062 		wpa_hexdump(MSG_MSGDUMP, "X509: Certificate hash (SHA384)",
2063 			    hash, hash_len);
2064 		break;
2065 	case 13: /* sha512WithRSAEncryption */
2066 		sha512_vector(1, addr, len, hash);
2067 		hash_len = 64;
2068 		wpa_hexdump(MSG_MSGDUMP, "X509: Certificate hash (SHA512)",
2069 			    hash, hash_len);
2070 		break;
2071 	case 2: /* md2WithRSAEncryption */
2072 	default:
2073 		wpa_printf(MSG_INFO, "X509: Unsupported certificate signature "
2074 			   "algorithm (%lu)", signature->oid.oid[6]);
2075 		os_free(data);
2076 		return -1;
2077 	}
2078 
2079 	if (hdr.length != hash_len ||
2080 	    os_memcmp_const(hdr.payload, hash, hdr.length) != 0) {
2081 		wpa_printf(MSG_INFO, "X509: Certificate Digest does not match "
2082 			   "with calculated tbsCertificate hash");
2083 		os_free(data);
2084 		return -1;
2085 	}
2086 
2087 	if (hdr.payload + hdr.length < data + data_len) {
2088 		wpa_hexdump(MSG_INFO,
2089 			    "X509: Extra data after certificate signature hash",
2090 			    hdr.payload + hdr.length,
2091 			    data + data_len - hdr.payload - hdr.length);
2092 		os_free(data);
2093 		return -1;
2094 	}
2095 
2096 	os_free(data);
2097 
2098 	wpa_printf(MSG_DEBUG, "X509: Certificate Digest matches with "
2099 		   "calculated tbsCertificate hash");
2100 
2101 	return 0;
2102 }
2103 
2104 
x509_valid_issuer(const struct x509_certificate * cert)2105 static int x509_valid_issuer(const struct x509_certificate *cert)
2106 {
2107 	if ((cert->extensions_present & X509_EXT_BASIC_CONSTRAINTS) &&
2108 	    !cert->ca) {
2109 		wpa_printf(MSG_DEBUG, "X509: Non-CA certificate used as an "
2110 			   "issuer");
2111 		return -1;
2112 	}
2113 
2114 	if (cert->version == X509_CERT_V3 &&
2115 	    !(cert->extensions_present & X509_EXT_BASIC_CONSTRAINTS)) {
2116 		wpa_printf(MSG_DEBUG, "X509: v3 CA certificate did not "
2117 			   "include BasicConstraints extension");
2118 		return -1;
2119 	}
2120 
2121 	if ((cert->extensions_present & X509_EXT_KEY_USAGE) &&
2122 	    !(cert->key_usage & X509_KEY_USAGE_KEY_CERT_SIGN)) {
2123 		wpa_printf(MSG_DEBUG, "X509: Issuer certificate did not have "
2124 			   "keyCertSign bit in Key Usage");
2125 		return -1;
2126 	}
2127 
2128 	return 0;
2129 }
2130 
2131 
2132 /**
2133  * x509_certificate_chain_validate - Validate X.509 certificate chain
2134  * @trusted: List of trusted certificates
2135  * @chain: Certificate chain to be validated (first chain must be issued by
2136  * signed by the second certificate in the chain and so on)
2137  * @reason: Buffer for returning failure reason (X509_VALIDATE_*)
2138  * Returns: 0 if chain is valid, -1 if not
2139  */
x509_certificate_chain_validate(struct x509_certificate * trusted,struct x509_certificate * chain,int * reason,int disable_time_checks)2140 int x509_certificate_chain_validate(struct x509_certificate *trusted,
2141 				    struct x509_certificate *chain,
2142 				    int *reason, int disable_time_checks)
2143 {
2144 	long unsigned idx;
2145 	int chain_trusted = 0;
2146 	struct x509_certificate *cert, *trust;
2147 	char buf[128];
2148 	struct os_time now;
2149 
2150 	*reason = X509_VALIDATE_OK;
2151 
2152 	wpa_printf(MSG_DEBUG, "X509: Validate certificate chain");
2153 	os_get_time(&now);
2154 
2155 	for (cert = chain, idx = 0; cert; cert = cert->next, idx++) {
2156 		cert->issuer_trusted = 0;
2157 		x509_name_string(&cert->subject, buf, sizeof(buf));
2158 		wpa_printf(MSG_DEBUG, "X509: %lu: %s", idx, buf);
2159 
2160 		if (chain_trusted)
2161 			continue;
2162 
2163 		if (!disable_time_checks &&
2164 		    ((unsigned long) now.sec <
2165 		     (unsigned long) cert->not_before ||
2166 		     (unsigned long) now.sec >
2167 		     (unsigned long) cert->not_after)) {
2168 			wpa_printf(MSG_INFO, "X509: Certificate not valid "
2169 				   "(now=%lu not_before=%lu not_after=%lu)",
2170 				   now.sec, cert->not_before, cert->not_after);
2171 			*reason = X509_VALIDATE_CERTIFICATE_EXPIRED;
2172 			return -1;
2173 		}
2174 
2175 		if (cert->next) {
2176 			if (x509_name_compare(&cert->issuer,
2177 					      &cert->next->subject) != 0) {
2178 				wpa_printf(MSG_DEBUG, "X509: Certificate "
2179 					   "chain issuer name mismatch");
2180 				x509_name_string(&cert->issuer, buf,
2181 						 sizeof(buf));
2182 				wpa_printf(MSG_DEBUG, "X509: cert issuer: %s",
2183 					   buf);
2184 				x509_name_string(&cert->next->subject, buf,
2185 						 sizeof(buf));
2186 				wpa_printf(MSG_DEBUG, "X509: next cert "
2187 					   "subject: %s", buf);
2188 				*reason = X509_VALIDATE_CERTIFICATE_UNKNOWN;
2189 				return -1;
2190 			}
2191 
2192 			if (x509_valid_issuer(cert->next) < 0) {
2193 				*reason = X509_VALIDATE_BAD_CERTIFICATE;
2194 				return -1;
2195 			}
2196 
2197 			if ((cert->next->extensions_present &
2198 			     X509_EXT_PATH_LEN_CONSTRAINT) &&
2199 			    idx > cert->next->path_len_constraint) {
2200 				wpa_printf(MSG_DEBUG, "X509: pathLenConstraint"
2201 					   " not met (idx=%lu issuer "
2202 					   "pathLenConstraint=%lu)", idx,
2203 					   cert->next->path_len_constraint);
2204 				*reason = X509_VALIDATE_BAD_CERTIFICATE;
2205 				return -1;
2206 			}
2207 
2208 			if (x509_certificate_check_signature(cert->next, cert)
2209 			    < 0) {
2210 				wpa_printf(MSG_DEBUG, "X509: Invalid "
2211 					   "certificate signature within "
2212 					   "chain");
2213 				*reason = X509_VALIDATE_BAD_CERTIFICATE;
2214 				return -1;
2215 			}
2216 		}
2217 
2218 		for (trust = trusted; trust; trust = trust->next) {
2219 			if (x509_name_compare(&cert->issuer, &trust->subject)
2220 			    == 0)
2221 				break;
2222 		}
2223 
2224 		if (trust) {
2225 			wpa_printf(MSG_DEBUG, "X509: Found issuer from the "
2226 				   "list of trusted certificates");
2227 			if (x509_valid_issuer(trust) < 0) {
2228 				*reason = X509_VALIDATE_BAD_CERTIFICATE;
2229 				return -1;
2230 			}
2231 
2232 			if (x509_certificate_check_signature(trust, cert) < 0)
2233 			{
2234 				wpa_printf(MSG_DEBUG, "X509: Invalid "
2235 					   "certificate signature");
2236 				*reason = X509_VALIDATE_BAD_CERTIFICATE;
2237 				return -1;
2238 			}
2239 
2240 			wpa_printf(MSG_DEBUG, "X509: Trusted certificate "
2241 				   "found to complete the chain");
2242 			cert->issuer_trusted = 1;
2243 			chain_trusted = 1;
2244 		}
2245 	}
2246 
2247 	if (!chain_trusted) {
2248 		wpa_printf(MSG_DEBUG, "X509: Did not find any of the issuers "
2249 			   "from the list of trusted certificates");
2250 		if (trusted) {
2251 			*reason = X509_VALIDATE_UNKNOWN_CA;
2252 			return -1;
2253 		}
2254 		wpa_printf(MSG_DEBUG, "X509: Certificate chain validation "
2255 			   "disabled - ignore unknown CA issue");
2256 	}
2257 
2258 	wpa_printf(MSG_DEBUG, "X509: Certificate chain valid");
2259 
2260 	return 0;
2261 }
2262 
2263 
2264 /**
2265  * x509_certificate_get_subject - Get a certificate based on Subject name
2266  * @chain: Certificate chain to search through
2267  * @name: Subject name to search for
2268  * Returns: Pointer to the certificate with the given Subject name or
2269  * %NULL on failure
2270  */
2271 struct x509_certificate *
x509_certificate_get_subject(struct x509_certificate * chain,struct x509_name * name)2272 x509_certificate_get_subject(struct x509_certificate *chain,
2273 			     struct x509_name *name)
2274 {
2275 	struct x509_certificate *cert;
2276 
2277 	for (cert = chain; cert; cert = cert->next) {
2278 		if (x509_name_compare(&cert->subject, name) == 0)
2279 			return cert;
2280 	}
2281 	return NULL;
2282 }
2283 
2284 
2285 /**
2286  * x509_certificate_self_signed - Is the certificate self-signed?
2287  * @cert: Certificate
2288  * Returns: 1 if certificate is self-signed, 0 if not
2289  */
x509_certificate_self_signed(struct x509_certificate * cert)2290 int x509_certificate_self_signed(struct x509_certificate *cert)
2291 {
2292 	return x509_name_compare(&cert->issuer, &cert->subject) == 0;
2293 }
2294