diff options
author | tb <> | 2023-03-06 08:08:31 +0000 |
---|---|---|
committer | tb <> | 2023-03-06 08:08:31 +0000 |
commit | ec79b8a0caa19718e16811a1ca55f0c980ef6d2f (patch) | |
tree | eed7711b1cc0c71d0017dc611ab43527b1c7ef41 | |
parent | 6bac610727a591217d2872d33752ba81334680ae (diff) | |
download | openbsd-ec79b8a0caa19718e16811a1ca55f0c980ef6d2f.tar.gz openbsd-ec79b8a0caa19718e16811a1ca55f0c980ef6d2f.tar.bz2 openbsd-ec79b8a0caa19718e16811a1ca55f0c980ef6d2f.zip |
ASN.1 enc: check ASN1_item_ex_i2d() consistency
The i2d API design is: call a function first with a pointer to NULL, get
the length, allocate a buffer, call the function passing the buffer in.
Both calls should be checked since ther are still internal allocations.
At the heart of ASN.1 encoding, this idiom is used and the second call
is assumed to succeed after the length was determined. This is far from
guaranteed. Check that the second call returns the same length and error
otherwise.
ok jsing
-rw-r--r-- | src/lib/libcrypto/asn1/tasn_enc.c | 11 |
1 files changed, 8 insertions, 3 deletions
diff --git a/src/lib/libcrypto/asn1/tasn_enc.c b/src/lib/libcrypto/asn1/tasn_enc.c index 55e65895f8..1b9cfa1a0e 100644 --- a/src/lib/libcrypto/asn1/tasn_enc.c +++ b/src/lib/libcrypto/asn1/tasn_enc.c | |||
@@ -1,4 +1,4 @@ | |||
1 | /* $OpenBSD: tasn_enc.c,v 1.27 2022/11/26 16:08:50 tb Exp $ */ | 1 | /* $OpenBSD: tasn_enc.c,v 1.28 2023/03/06 08:08:31 tb Exp $ */ |
2 | /* Written by Dr Stephen N Henson (steve@openssl.org) for the OpenSSL | 2 | /* Written by Dr Stephen N Henson (steve@openssl.org) for the OpenSSL |
3 | * project 2000. | 3 | * project 2000. |
4 | */ | 4 | */ |
@@ -108,7 +108,7 @@ asn1_item_flags_i2d(ASN1_VALUE *val, unsigned char **out, const ASN1_ITEM *it, | |||
108 | { | 108 | { |
109 | if (out && !*out) { | 109 | if (out && !*out) { |
110 | unsigned char *p, *buf; | 110 | unsigned char *p, *buf; |
111 | int len; | 111 | int len, len2; |
112 | len = ASN1_item_ex_i2d(&val, NULL, it, -1, flags); | 112 | len = ASN1_item_ex_i2d(&val, NULL, it, -1, flags); |
113 | if (len <= 0) | 113 | if (len <= 0) |
114 | return len; | 114 | return len; |
@@ -116,7 +116,12 @@ asn1_item_flags_i2d(ASN1_VALUE *val, unsigned char **out, const ASN1_ITEM *it, | |||
116 | if (!buf) | 116 | if (!buf) |
117 | return -1; | 117 | return -1; |
118 | p = buf; | 118 | p = buf; |
119 | ASN1_item_ex_i2d(&val, &p, it, -1, flags); | 119 | len2 = ASN1_item_ex_i2d(&val, &p, it, -1, flags); |
120 | if (len2 != len) { | ||
121 | freezero(buf, len); | ||
122 | ASN1error(ASN1_R_LENGTH_ERROR); | ||
123 | return -1; | ||
124 | } | ||
120 | *out = buf; | 125 | *out = buf; |
121 | return len; | 126 | return len; |
122 | } | 127 | } |