xref: /openbsd/lib/libcrypto/asn1/a_int.c (revision 7523ec26)
1 /* $OpenBSD: a_int.c,v 1.48 2024/07/08 14:52:31 beck Exp $ */
2 /* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com)
3  * All rights reserved.
4  *
5  * This package is an SSL implementation written
6  * by Eric Young (eay@cryptsoft.com).
7  * The implementation was written so as to conform with Netscapes SSL.
8  *
9  * This library is free for commercial and non-commercial use as long as
10  * the following conditions are aheared to.  The following conditions
11  * apply to all code found in this distribution, be it the RC4, RSA,
12  * lhash, DES, etc., code; not just the SSL code.  The SSL documentation
13  * included with this distribution is covered by the same copyright terms
14  * except that the holder is Tim Hudson (tjh@cryptsoft.com).
15  *
16  * Copyright remains Eric Young's, and as such any Copyright notices in
17  * the code are not to be removed.
18  * If this package is used in a product, Eric Young should be given attribution
19  * as the author of the parts of the library used.
20  * This can be in the form of a textual message at program startup or
21  * in documentation (online or textual) provided with the package.
22  *
23  * Redistribution and use in source and binary forms, with or without
24  * modification, are permitted provided that the following conditions
25  * are met:
26  * 1. Redistributions of source code must retain the copyright
27  *    notice, this list of conditions and the following disclaimer.
28  * 2. Redistributions in binary form must reproduce the above copyright
29  *    notice, this list of conditions and the following disclaimer in the
30  *    documentation and/or other materials provided with the distribution.
31  * 3. All advertising materials mentioning features or use of this software
32  *    must display the following acknowledgement:
33  *    "This product includes cryptographic software written by
34  *     Eric Young (eay@cryptsoft.com)"
35  *    The word 'cryptographic' can be left out if the rouines from the library
36  *    being used are not cryptographic related :-).
37  * 4. If you include any Windows specific code (or a derivative thereof) from
38  *    the apps directory (application code) you must include an acknowledgement:
39  *    "This product includes software written by Tim Hudson (tjh@cryptsoft.com)"
40  *
41  * THIS SOFTWARE IS PROVIDED BY ERIC YOUNG ``AS IS'' AND
42  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
43  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
44  * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
45  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
46  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
47  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
48  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
49  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
50  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
51  * SUCH DAMAGE.
52  *
53  * The licence and distribution terms for any publically available version or
54  * derivative of this code cannot be changed.  i.e. this code cannot simply be
55  * copied and put under another distribution licence
56  * [including the GNU Public Licence.]
57  */
58 
59 #include <limits.h>
60 #include <stdio.h>
61 #include <string.h>
62 
63 #include <openssl/asn1.h>
64 #include <openssl/asn1t.h>
65 #include <openssl/bn.h>
66 #include <openssl/buffer.h>
67 #include <openssl/err.h>
68 
69 #include "bytestring.h"
70 
71 const ASN1_ITEM ASN1_INTEGER_it = {
72 	.itype = ASN1_ITYPE_PRIMITIVE,
73 	.utype = V_ASN1_INTEGER,
74 	.sname = "ASN1_INTEGER",
75 };
76 LCRYPTO_ALIAS(ASN1_INTEGER_it);
77 
78 ASN1_INTEGER *
ASN1_INTEGER_new(void)79 ASN1_INTEGER_new(void)
80 {
81 	return (ASN1_INTEGER *)ASN1_item_new(&ASN1_INTEGER_it);
82 }
83 LCRYPTO_ALIAS(ASN1_INTEGER_new);
84 
85 static void
asn1_aint_clear(ASN1_INTEGER * aint)86 asn1_aint_clear(ASN1_INTEGER *aint)
87 {
88 	freezero(aint->data, aint->length);
89 
90 	memset(aint, 0, sizeof(*aint));
91 
92 	aint->type = V_ASN1_INTEGER;
93 }
94 
95 void
ASN1_INTEGER_free(ASN1_INTEGER * a)96 ASN1_INTEGER_free(ASN1_INTEGER *a)
97 {
98 	ASN1_item_free((ASN1_VALUE *)a, &ASN1_INTEGER_it);
99 }
100 LCRYPTO_ALIAS(ASN1_INTEGER_free);
101 
102 static int
ASN1_INTEGER_valid(const ASN1_INTEGER * a)103 ASN1_INTEGER_valid(const ASN1_INTEGER *a)
104 {
105 	return (a != NULL && a->length >= 0);
106 }
107 
108 ASN1_INTEGER *
ASN1_INTEGER_dup(const ASN1_INTEGER * x)109 ASN1_INTEGER_dup(const ASN1_INTEGER *x)
110 {
111 	if (!ASN1_INTEGER_valid(x))
112 		return NULL;
113 
114 	return ASN1_STRING_dup(x);
115 }
116 LCRYPTO_ALIAS(ASN1_INTEGER_dup);
117 
118 int
ASN1_INTEGER_cmp(const ASN1_INTEGER * a,const ASN1_INTEGER * b)119 ASN1_INTEGER_cmp(const ASN1_INTEGER *a, const ASN1_INTEGER *b)
120 {
121 	int ret = 1;
122 
123 	/* Compare sign, then content. */
124 	if ((a->type & V_ASN1_NEG) == (b->type & V_ASN1_NEG))
125 		ret = ASN1_STRING_cmp(a, b);
126 
127 	if ((a->type & V_ASN1_NEG) != 0)
128 		return -ret;
129 
130 	return ret;
131 }
132 LCRYPTO_ALIAS(ASN1_INTEGER_cmp);
133 
134 int
asn1_aint_get_uint64(CBS * cbs,uint64_t * out_val)135 asn1_aint_get_uint64(CBS *cbs, uint64_t *out_val)
136 {
137 	uint64_t val = 0;
138 	uint8_t u8;
139 
140 	*out_val = 0;
141 
142 	while (CBS_len(cbs) > 0) {
143 		if (!CBS_get_u8(cbs, &u8))
144 			return 0;
145 		if (val > (UINT64_MAX >> 8)) {
146 			ASN1error(ASN1_R_TOO_LARGE);
147 			return 0;
148 		}
149 		val = val << 8 | u8;
150 	}
151 
152 	*out_val = val;
153 
154 	return 1;
155 }
156 
157 int
asn1_aint_set_uint64(uint64_t val,uint8_t ** out_data,int * out_len)158 asn1_aint_set_uint64(uint64_t val, uint8_t **out_data, int *out_len)
159 {
160 	uint8_t *data = NULL;
161 	size_t data_len = 0;
162 	int started = 0;
163 	uint8_t u8;
164 	CBB cbb;
165 	int i;
166 	int ret = 0;
167 
168 	if (!CBB_init(&cbb, sizeof(long)))
169 		goto err;
170 
171 	if (out_data == NULL || out_len == NULL)
172 		goto err;
173 	if (*out_data != NULL || *out_len != 0)
174 		goto err;
175 
176 	for (i = sizeof(uint64_t) - 1; i >= 0; i--) {
177 		u8 = (val >> (i * 8)) & 0xff;
178 		if (!started && i != 0 && u8 == 0)
179 			continue;
180 		if (!CBB_add_u8(&cbb, u8))
181 			goto err;
182 		started = 1;
183 	}
184 
185 	if (!CBB_finish(&cbb, &data, &data_len))
186 		goto err;
187 	if (data_len > INT_MAX)
188 		goto err;
189 
190 	*out_data = data;
191 	*out_len = (int)data_len;
192 	data = NULL;
193 
194 	ret = 1;
195  err:
196 	CBB_cleanup(&cbb);
197 	freezero(data, data_len);
198 
199 	return ret;
200 }
201 
202 int
asn1_aint_get_int64(CBS * cbs,int negative,int64_t * out_val)203 asn1_aint_get_int64(CBS *cbs, int negative, int64_t *out_val)
204 {
205 	uint64_t val;
206 
207 	if (!asn1_aint_get_uint64(cbs, &val))
208 		return 0;
209 
210 	if (negative) {
211 		if (val > (uint64_t)INT64_MIN) {
212 			ASN1error(ASN1_R_TOO_SMALL);
213 			return 0;
214 		}
215 		*out_val = (int64_t)-val;
216 	} else {
217 		if (val > (uint64_t)INT64_MAX) {
218 			ASN1error(ASN1_R_TOO_LARGE);
219 			return 0;
220 		}
221 		*out_val = (int64_t)val;
222 	}
223 
224 	return 1;
225 }
226 
227 int
ASN1_INTEGER_get_uint64(uint64_t * out_val,const ASN1_INTEGER * aint)228 ASN1_INTEGER_get_uint64(uint64_t *out_val, const ASN1_INTEGER *aint)
229 {
230 	uint64_t val;
231 	CBS cbs;
232 
233 	*out_val = 0;
234 
235 	if (aint == NULL || aint->length < 0)
236 		return 0;
237 
238 	if (aint->type == V_ASN1_NEG_INTEGER) {
239 		ASN1error(ASN1_R_ILLEGAL_NEGATIVE_VALUE);
240 		return 0;
241 	}
242 	if (aint->type != V_ASN1_INTEGER) {
243 		ASN1error(ASN1_R_WRONG_INTEGER_TYPE);
244 		return 0;
245 	}
246 
247 	CBS_init(&cbs, aint->data, aint->length);
248 
249 	if (!asn1_aint_get_uint64(&cbs, &val))
250 		return 0;
251 
252 	*out_val = val;
253 
254 	return 1;
255 }
256 LCRYPTO_ALIAS(ASN1_INTEGER_get_uint64);
257 
258 int
ASN1_INTEGER_set_uint64(ASN1_INTEGER * aint,uint64_t val)259 ASN1_INTEGER_set_uint64(ASN1_INTEGER *aint, uint64_t val)
260 {
261 	asn1_aint_clear(aint);
262 
263 	return asn1_aint_set_uint64(val, &aint->data, &aint->length);
264 }
265 LCRYPTO_ALIAS(ASN1_INTEGER_set_uint64);
266 
267 int
ASN1_INTEGER_get_int64(int64_t * out_val,const ASN1_INTEGER * aint)268 ASN1_INTEGER_get_int64(int64_t *out_val, const ASN1_INTEGER *aint)
269 {
270 	CBS cbs;
271 
272 	*out_val = 0;
273 
274 	if (aint == NULL || aint->length < 0)
275 		return 0;
276 
277 	if (aint->type != V_ASN1_INTEGER &&
278 	    aint->type != V_ASN1_NEG_INTEGER) {
279 		ASN1error(ASN1_R_WRONG_INTEGER_TYPE);
280 		return 0;
281 	}
282 
283 	CBS_init(&cbs, aint->data, aint->length);
284 
285 	return asn1_aint_get_int64(&cbs, (aint->type == V_ASN1_NEG_INTEGER),
286 	    out_val);
287 }
288 LCRYPTO_ALIAS(ASN1_INTEGER_get_int64);
289 
290 int
ASN1_INTEGER_set_int64(ASN1_INTEGER * aint,int64_t val)291 ASN1_INTEGER_set_int64(ASN1_INTEGER *aint, int64_t val)
292 {
293 	uint64_t uval;
294 
295 	asn1_aint_clear(aint);
296 
297 	uval = (uint64_t)val;
298 
299 	if (val < 0) {
300 		aint->type = V_ASN1_NEG_INTEGER;
301 		uval = -uval;
302 	}
303 
304 	return asn1_aint_set_uint64(uval, &aint->data, &aint->length);
305 }
306 LCRYPTO_ALIAS(ASN1_INTEGER_set_int64);
307 
308 long
ASN1_INTEGER_get(const ASN1_INTEGER * aint)309 ASN1_INTEGER_get(const ASN1_INTEGER *aint)
310 {
311 	int64_t val;
312 
313 	if (aint == NULL)
314 		return 0;
315 	if (!ASN1_INTEGER_get_int64(&val, aint))
316 		return -1;
317 	if (val < LONG_MIN || val > LONG_MAX) {
318 		/* hmm... a bit ugly, return all ones */
319 		return -1;
320 	}
321 
322 	return (long)val;
323 }
324 LCRYPTO_ALIAS(ASN1_INTEGER_get);
325 
326 int
ASN1_INTEGER_set(ASN1_INTEGER * aint,long val)327 ASN1_INTEGER_set(ASN1_INTEGER *aint, long val)
328 {
329 	return ASN1_INTEGER_set_int64(aint, val);
330 }
331 LCRYPTO_ALIAS(ASN1_INTEGER_set);
332 
333 ASN1_INTEGER *
BN_to_ASN1_INTEGER(const BIGNUM * bn,ASN1_INTEGER * ai)334 BN_to_ASN1_INTEGER(const BIGNUM *bn, ASN1_INTEGER *ai)
335 {
336 	ASN1_INTEGER *ret;
337 	int len, j;
338 
339 	if (ai == NULL)
340 		ret = ASN1_INTEGER_new();
341 	else
342 		ret = ai;
343 	if (ret == NULL) {
344 		ASN1error(ERR_R_NESTED_ASN1_ERROR);
345 		goto err;
346 	}
347 
348 	if (!ASN1_INTEGER_valid(ret))
349 		goto err;
350 
351 	if (BN_is_negative(bn))
352 		ret->type = V_ASN1_NEG_INTEGER;
353 	else
354 		ret->type = V_ASN1_INTEGER;
355 	j = BN_num_bits(bn);
356 	len = ((j == 0) ? 0 : ((j / 8) + 1));
357 	if (ret->length < len + 4) {
358 		unsigned char *new_data = realloc(ret->data, len + 4);
359 		if (!new_data) {
360 			ASN1error(ERR_R_MALLOC_FAILURE);
361 			goto err;
362 		}
363 		ret->data = new_data;
364 	}
365 	ret->length = BN_bn2bin(bn, ret->data);
366 
367 	/* Correct zero case */
368 	if (!ret->length) {
369 		ret->data[0] = 0;
370 		ret->length = 1;
371 	}
372 	return (ret);
373 
374  err:
375 	if (ret != ai)
376 		ASN1_INTEGER_free(ret);
377 	return (NULL);
378 }
379 LCRYPTO_ALIAS(BN_to_ASN1_INTEGER);
380 
381 BIGNUM *
ASN1_INTEGER_to_BN(const ASN1_INTEGER * ai,BIGNUM * bn)382 ASN1_INTEGER_to_BN(const ASN1_INTEGER *ai, BIGNUM *bn)
383 {
384 	BIGNUM *ret;
385 
386 	if (!ASN1_INTEGER_valid(ai))
387 		return (NULL);
388 
389 	if ((ret = BN_bin2bn(ai->data, ai->length, bn)) == NULL)
390 		ASN1error(ASN1_R_BN_LIB);
391 	else if (ai->type == V_ASN1_NEG_INTEGER)
392 		BN_set_negative(ret, 1);
393 	return (ret);
394 }
395 LCRYPTO_ALIAS(ASN1_INTEGER_to_BN);
396 
397 int
i2a_ASN1_INTEGER(BIO * bp,const ASN1_INTEGER * a)398 i2a_ASN1_INTEGER(BIO *bp, const ASN1_INTEGER *a)
399 {
400 	int i, n = 0;
401 	static const char h[] = "0123456789ABCDEF";
402 	char buf[2];
403 
404 	if (a == NULL)
405 		return (0);
406 
407 	if (a->type & V_ASN1_NEG) {
408 		if (BIO_write(bp, "-", 1) != 1)
409 			goto err;
410 		n = 1;
411 	}
412 
413 	if (a->length == 0) {
414 		if (BIO_write(bp, "00", 2) != 2)
415 			goto err;
416 		n += 2;
417 	} else {
418 		for (i = 0; i < a->length; i++) {
419 			if ((i != 0) && (i % 35 == 0)) {
420 				if (BIO_write(bp, "\\\n", 2) != 2)
421 					goto err;
422 				n += 2;
423 			}
424 			buf[0] = h[((unsigned char)a->data[i] >> 4) & 0x0f];
425 			buf[1] = h[((unsigned char)a->data[i]) & 0x0f];
426 			if (BIO_write(bp, buf, 2) != 2)
427 				goto err;
428 			n += 2;
429 		}
430 	}
431 	return (n);
432 
433  err:
434 	return (-1);
435 }
436 LCRYPTO_ALIAS(i2a_ASN1_INTEGER);
437 
438 int
a2i_ASN1_INTEGER(BIO * bp,ASN1_INTEGER * bs,char * buf,int size)439 a2i_ASN1_INTEGER(BIO *bp, ASN1_INTEGER *bs, char *buf, int size)
440 {
441 	int ret = 0;
442 	int i, j,k, m,n, again, bufsize;
443 	unsigned char *s = NULL, *sp;
444 	unsigned char *bufp;
445 	int num = 0, slen = 0, first = 1;
446 
447 	bs->type = V_ASN1_INTEGER;
448 
449 	bufsize = BIO_gets(bp, buf, size);
450 	for (;;) {
451 		if (bufsize < 1)
452 			goto err_sl;
453 		i = bufsize;
454 		if (buf[i - 1] == '\n')
455 			buf[--i] = '\0';
456 		if (i == 0)
457 			goto err_sl;
458 		if (buf[i - 1] == '\r')
459 			buf[--i] = '\0';
460 		if (i == 0)
461 			goto err_sl;
462 		if (buf[i - 1] == '\\') {
463 			i--;
464 			again = 1;
465 		} else
466 			again = 0;
467 		buf[i] = '\0';
468 		if (i < 2)
469 			goto err_sl;
470 
471 		bufp = (unsigned char *)buf;
472 		if (first) {
473 			first = 0;
474 			if ((bufp[0] == '0') && (buf[1] == '0')) {
475 				bufp += 2;
476 				i -= 2;
477 			}
478 		}
479 		k = 0;
480 		if (i % 2 != 0) {
481 			ASN1error(ASN1_R_ODD_NUMBER_OF_CHARS);
482 			goto err;
483 		}
484 		i /= 2;
485 		if (num + i > slen) {
486 			if ((sp = recallocarray(s, slen, num + i, 1)) == NULL) {
487 				ASN1error(ERR_R_MALLOC_FAILURE);
488 				goto err;
489 			}
490 			s = sp;
491 			slen = num + i;
492 		}
493 		for (j = 0; j < i; j++, k += 2) {
494 			for (n = 0; n < 2; n++) {
495 				m = bufp[k + n];
496 				if ((m >= '0') && (m <= '9'))
497 					m -= '0';
498 				else if ((m >= 'a') && (m <= 'f'))
499 					m = m - 'a' + 10;
500 				else if ((m >= 'A') && (m <= 'F'))
501 					m = m - 'A' + 10;
502 				else {
503 					ASN1error(ASN1_R_NON_HEX_CHARACTERS);
504 					goto err;
505 				}
506 				s[num + j] <<= 4;
507 				s[num + j] |= m;
508 			}
509 		}
510 		num += i;
511 		if (again)
512 			bufsize = BIO_gets(bp, buf, size);
513 		else
514 			break;
515 	}
516 	bs->length = num;
517 	bs->data = s;
518 	return (1);
519 
520  err_sl:
521 	ASN1error(ASN1_R_SHORT_LINE);
522  err:
523 	free(s);
524 	return (ret);
525 }
526 LCRYPTO_ALIAS(a2i_ASN1_INTEGER);
527 
528 static void
asn1_aint_twos_complement(uint8_t * data,size_t data_len)529 asn1_aint_twos_complement(uint8_t *data, size_t data_len)
530 {
531 	uint8_t carry = 1;
532 	ssize_t i;
533 
534 	for (i = data_len - 1; i >= 0; i--) {
535 		data[i] = (data[i] ^ 0xff) + carry;
536 		if (data[i] != 0)
537 			carry = 0;
538 	}
539 }
540 
541 static int
asn1_aint_keep_twos_padding(const uint8_t * data,size_t data_len)542 asn1_aint_keep_twos_padding(const uint8_t *data, size_t data_len)
543 {
544 	size_t i;
545 
546 	/*
547 	 * If a two's complement value has a padding byte (0xff) and the rest
548 	 * of the value is all zeros, the padding byte cannot be removed as when
549 	 * converted from two's complement this becomes 0x01 (in the place of
550 	 * the padding byte) followed by the same number of zero bytes.
551 	 */
552 	if (data_len <= 1 || data[0] != 0xff)
553 		return 0;
554 	for (i = 1; i < data_len; i++) {
555 		if (data[i] != 0)
556 			return 0;
557 	}
558 	return 1;
559 }
560 
561 static int
i2c_ASN1_INTEGER_cbb(ASN1_INTEGER * aint,CBB * cbb)562 i2c_ASN1_INTEGER_cbb(ASN1_INTEGER *aint, CBB *cbb)
563 {
564 	uint8_t *data = NULL;
565 	size_t data_len = 0;
566 	uint8_t padding, val;
567 	uint8_t msb;
568 	CBS cbs;
569 	int ret = 0;
570 
571 	if (aint->length < 0)
572 		goto err;
573 	if (aint->data == NULL && aint->length != 0)
574 		goto err;
575 
576 	if ((aint->type & ~V_ASN1_NEG) != V_ASN1_ENUMERATED &&
577 	    (aint->type & ~V_ASN1_NEG) != V_ASN1_INTEGER)
578 		goto err;
579 
580 	CBS_init(&cbs, aint->data, aint->length);
581 
582 	/* Find the first non-zero byte. */
583 	while (CBS_len(&cbs) > 0) {
584 		if (!CBS_peek_u8(&cbs, &val))
585 			goto err;
586 		if (val != 0)
587 			break;
588 		if (!CBS_skip(&cbs, 1))
589 			goto err;
590 	}
591 
592 	/* A zero value is encoded as a single octet. */
593 	if (CBS_len(&cbs) == 0) {
594 		if (!CBB_add_u8(cbb, 0))
595 			goto err;
596 		goto done;
597 	}
598 
599 	if (!CBS_stow(&cbs, &data, &data_len))
600 		goto err;
601 
602 	if ((aint->type & V_ASN1_NEG) != 0)
603 		asn1_aint_twos_complement(data, data_len);
604 
605 	/* Topmost bit indicates sign, padding is all zeros or all ones. */
606 	msb = (data[0] >> 7);
607 	padding = (msb - 1) & 0xff;
608 
609 	/* See if we need a padding octet to avoid incorrect sign. */
610 	if (((aint->type & V_ASN1_NEG) == 0 && msb == 1) ||
611 	    ((aint->type & V_ASN1_NEG) != 0 && msb == 0)) {
612 		if (!CBB_add_u8(cbb, padding))
613 			goto err;
614 	}
615 	if (!CBB_add_bytes(cbb, data, data_len))
616 		goto err;
617 
618  done:
619 	ret = 1;
620 
621  err:
622 	freezero(data, data_len);
623 
624 	return ret;
625 }
626 
627 int
i2c_ASN1_INTEGER(ASN1_INTEGER * aint,unsigned char ** pp)628 i2c_ASN1_INTEGER(ASN1_INTEGER *aint, unsigned char **pp)
629 {
630 	uint8_t *data = NULL;
631 	size_t data_len = 0;
632 	CBB cbb;
633 	int ret = -3;
634 
635 	if (!CBB_init(&cbb, 0))
636 		goto err;
637 	if (!i2c_ASN1_INTEGER_cbb(aint, &cbb))
638 		goto err;
639 	if (!CBB_finish(&cbb, &data, &data_len))
640 		goto err;
641 	if (data_len > INT_MAX)
642 		goto err;
643 
644 	if (pp != NULL) {
645 		if ((uintptr_t)*pp > UINTPTR_MAX - data_len)
646 			goto err;
647 		memcpy(*pp, data, data_len);
648 		*pp += data_len;
649 	}
650 
651 	ret = data_len;
652 
653  err:
654 	freezero(data, data_len);
655 	CBB_cleanup(&cbb);
656 
657 	return ret;
658 }
659 
660 int
c2i_ASN1_INTEGER_cbs(ASN1_INTEGER ** out_aint,CBS * cbs)661 c2i_ASN1_INTEGER_cbs(ASN1_INTEGER **out_aint, CBS *cbs)
662 {
663 	ASN1_INTEGER *aint = NULL;
664 	uint8_t *data = NULL;
665 	size_t data_len = 0;
666 	uint8_t padding, val;
667 	uint8_t negative;
668 	int ret = 0;
669 
670 	if (out_aint == NULL)
671 		goto err;
672 
673 	if (*out_aint != NULL) {
674 		ASN1_INTEGER_free(*out_aint);
675 		*out_aint = NULL;
676 	}
677 
678 	if (CBS_len(cbs) == 0) {
679 		/* XXX INVALID ENCODING? */
680 		ASN1error(ERR_R_ASN1_LENGTH_MISMATCH);
681 		goto err;
682 	}
683 	if (!CBS_peek_u8(cbs, &val))
684 		goto err;
685 
686 	/* Topmost bit indicates sign, padding is all zeros or all ones. */
687 	negative = (val >> 7);
688 	padding = ~(negative - 1) & 0xff;
689 
690 	/*
691 	 * Ensure that the first 9 bits are not all zero or all one, as per
692 	 * X.690 section 8.3.2. Remove the padding octet if possible.
693 	 */
694 	if (CBS_len(cbs) > 1 && val == padding) {
695 		if (!asn1_aint_keep_twos_padding(CBS_data(cbs), CBS_len(cbs))) {
696 			if (!CBS_get_u8(cbs, &padding))
697 				goto err;
698 			if (!CBS_peek_u8(cbs, &val))
699 				goto err;
700 			if ((val >> 7) == (padding >> 7)) {
701 				/* XXX INVALID ENCODING? */
702 				ASN1error(ERR_R_ASN1_LENGTH_MISMATCH);
703 				goto err;
704 			}
705 		}
706 	}
707 
708 	if (!CBS_stow(cbs, &data, &data_len))
709 		goto err;
710 	if (data_len > INT_MAX)
711 		goto err;
712 
713 	if ((aint = ASN1_INTEGER_new()) == NULL)
714 		goto err;
715 
716 	/*
717 	 * Negative integers are handled as a separate type - convert from
718 	 * two's complement for internal representation.
719 	 */
720 	if (negative) {
721 		aint->type = V_ASN1_NEG_INTEGER;
722 		asn1_aint_twos_complement(data, data_len);
723 	}
724 
725 	aint->data = data;
726 	aint->length = (int)data_len;
727 	data = NULL;
728 
729 	*out_aint = aint;
730 	aint = NULL;
731 
732 	ret = 1;
733 
734  err:
735 	ASN1_INTEGER_free(aint);
736 	freezero(data, data_len);
737 
738 	return ret;
739 }
740 
741 ASN1_INTEGER *
c2i_ASN1_INTEGER(ASN1_INTEGER ** out_aint,const unsigned char ** pp,long len)742 c2i_ASN1_INTEGER(ASN1_INTEGER **out_aint, const unsigned char **pp, long len)
743 {
744 	ASN1_INTEGER *aint = NULL;
745 	CBS content;
746 
747 	if (out_aint != NULL) {
748 		ASN1_INTEGER_free(*out_aint);
749 		*out_aint = NULL;
750 	}
751 
752 	if (len < 0) {
753 		ASN1error(ASN1_R_LENGTH_ERROR);
754 		return NULL;
755 	}
756 
757 	CBS_init(&content, *pp, len);
758 
759 	if (!c2i_ASN1_INTEGER_cbs(&aint, &content))
760 		return NULL;
761 
762 	*pp = CBS_data(&content);
763 
764 	if (out_aint != NULL)
765 		*out_aint = aint;
766 
767 	return aint;
768 }
769 
770 int
i2d_ASN1_INTEGER(ASN1_INTEGER * a,unsigned char ** out)771 i2d_ASN1_INTEGER(ASN1_INTEGER *a, unsigned char **out)
772 {
773 	return ASN1_item_i2d((ASN1_VALUE *)a, out, &ASN1_INTEGER_it);
774 }
775 LCRYPTO_ALIAS(i2d_ASN1_INTEGER);
776 
777 ASN1_INTEGER *
d2i_ASN1_INTEGER(ASN1_INTEGER ** a,const unsigned char ** in,long len)778 d2i_ASN1_INTEGER(ASN1_INTEGER **a, const unsigned char **in, long len)
779 {
780 	return (ASN1_INTEGER *)ASN1_item_d2i((ASN1_VALUE **)a, in, len,
781 	    &ASN1_INTEGER_it);
782 }
783 LCRYPTO_ALIAS(d2i_ASN1_INTEGER);
784 
785 /* This is a version of d2i_ASN1_INTEGER that ignores the sign bit of
786  * ASN1 integers: some broken software can encode a positive INTEGER
787  * with its MSB set as negative (it doesn't add a padding zero).
788  */
789 
790 ASN1_INTEGER *
d2i_ASN1_UINTEGER(ASN1_INTEGER ** a,const unsigned char ** pp,long length)791 d2i_ASN1_UINTEGER(ASN1_INTEGER **a, const unsigned char **pp, long length)
792 {
793 	ASN1_INTEGER *ret = NULL;
794 	const unsigned char *p;
795 	unsigned char *s;
796 	long len;
797 	int inf, tag, xclass;
798 	int i;
799 
800 	if ((a == NULL) || ((*a) == NULL)) {
801 		if ((ret = ASN1_INTEGER_new()) == NULL)
802 			return (NULL);
803 	} else
804 		ret = (*a);
805 
806 	if (!ASN1_INTEGER_valid(ret)) {
807 		i = ERR_R_ASN1_LENGTH_MISMATCH;
808 		goto err;
809 	}
810 
811 	p = *pp;
812 	inf = ASN1_get_object(&p, &len, &tag, &xclass, length);
813 	if (inf & 0x80) {
814 		i = ASN1_R_BAD_OBJECT_HEADER;
815 		goto err;
816 	}
817 
818 	if (tag != V_ASN1_INTEGER) {
819 		i = ASN1_R_EXPECTING_AN_INTEGER;
820 		goto err;
821 	}
822 
823 	/* We must malloc stuff, even for 0 bytes otherwise it
824 	 * signifies a missing NULL parameter. */
825 	if (len < 0 || len > INT_MAX) {
826 		i = ERR_R_ASN1_LENGTH_MISMATCH;
827 		goto err;
828 	}
829 	s = malloc(len + 1);
830 	if (s == NULL) {
831 		i = ERR_R_MALLOC_FAILURE;
832 		goto err;
833 	}
834 	ret->type = V_ASN1_INTEGER;
835 	if (len) {
836 		if ((*p == 0) && (len != 1)) {
837 			p++;
838 			len--;
839 		}
840 		memcpy(s, p, len);
841 		p += len;
842 	}
843 
844 	free(ret->data);
845 	ret->data = s;
846 	ret->length = (int)len;
847 	if (a != NULL)
848 		(*a) = ret;
849 	*pp = p;
850 	return (ret);
851 
852  err:
853 	ASN1error(i);
854 	if (a == NULL || *a != ret)
855 		ASN1_INTEGER_free(ret);
856 	return (NULL);
857 }
858 LCRYPTO_ALIAS(d2i_ASN1_UINTEGER);
859