diff options
author | Dr. David von Oheimb <David.von.Oheimb@siemens.com> | 2021-03-01 14:45:23 +0100 |
---|---|---|
committer | Dr. David von Oheimb <dev@ddvo.net> | 2021-04-21 15:06:21 +0200 |
commit | 3e73111d133dda63ec42437ff5706ac3142f17a5 (patch) | |
tree | 7d80a020a81b9b0412e228dd5e65a76f9dec12f8 /crypto/asn1/a_d2i_fp.c | |
parent | db76a35e26ea09781caa5b941bdfeacb52e720d8 (diff) |
ASN.1: Add some sanity checks for input len <= 0; related coding improvements
Reviewed-by: Tomas Mraz <tomas@openssl.org>
(Merged from https://github.com/openssl/openssl/pull/14357)
Diffstat (limited to 'crypto/asn1/a_d2i_fp.c')
-rw-r--r-- | crypto/asn1/a_d2i_fp.c | 16 |
1 files changed, 10 insertions, 6 deletions
diff --git a/crypto/asn1/a_d2i_fp.c b/crypto/asn1/a_d2i_fp.c index 4151a96561..6dfa37c7a2 100644 --- a/crypto/asn1/a_d2i_fp.c +++ b/crypto/asn1/a_d2i_fp.c @@ -101,6 +101,7 @@ int asn1_d2i_read_bio(BIO *in, BUF_MEM **pb) uint32_t eos = 0; size_t off = 0; size_t len = 0; + size_t diff; const unsigned char *q; long slen; @@ -114,15 +115,16 @@ int asn1_d2i_read_bio(BIO *in, BUF_MEM **pb) ERR_clear_error(); for (;;) { - if (want >= (len - off)) { - want -= (len - off); + diff = len - off; + if (want >= diff) { + want -= diff; if (len + want < len || !BUF_MEM_grow_clean(b, len + want)) { ERR_raise(ERR_LIB_ASN1, ERR_R_MALLOC_FAILURE); goto err; } i = BIO_read(in, &(b->data[len]), want); - if ((i < 0) && ((len - off) == 0)) { + if (i < 0 && diff == 0) { ERR_raise(ERR_LIB_ASN1, ASN1_R_NOT_ENOUGH_DATA); goto err; } @@ -138,15 +140,17 @@ int asn1_d2i_read_bio(BIO *in, BUF_MEM **pb) p = (unsigned char *)&(b->data[off]); q = p; - inf = ASN1_get_object(&q, &slen, &tag, &xclass, len - off); + diff = len - off; + if (diff == 0) + goto err; + inf = ASN1_get_object(&q, &slen, &tag, &xclass, diff); if (inf & 0x80) { unsigned long e; e = ERR_GET_REASON(ERR_peek_error()); if (e != ASN1_R_TOO_LONG) goto err; - else - ERR_clear_error(); /* clear error */ + ERR_clear_error(); } i = q - p; /* header length */ off += i; /* end of data */ |