summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorjsing <>2021-12-25 12:00:22 +0000
committerjsing <>2021-12-25 12:00:22 +0000
commit346d30a52f494d9f2e76e352a6ba8ca2ebdcf62f (patch)
treef8066c2e1b162d8419257da2a38cd910b7453a40
parenta1aa360082915390f4dce8cb202c7a908f0801d7 (diff)
downloadopenbsd-346d30a52f494d9f2e76e352a6ba8ca2ebdcf62f.tar.gz
openbsd-346d30a52f494d9f2e76e352a6ba8ca2ebdcf62f.tar.bz2
openbsd-346d30a52f494d9f2e76e352a6ba8ca2ebdcf62f.zip
More consolidation of ASN.1 code.
Consolidate various ASN1_item_* functions into asn1_item.c and the remaining NO_OLD_ASN1 code (not to be confused with the NO_ASN1_OLD code) into asn1_old.c. This is preferable to having many files, often with one or two functions per file. No functional change. Discussed with tb@
-rw-r--r--src/lib/libcrypto/Makefile8
-rw-r--r--src/lib/libcrypto/asn1/a_d2i_fp.c289
-rw-r--r--src/lib/libcrypto/asn1/a_digest.c87
-rw-r--r--src/lib/libcrypto/asn1/a_dup.c118
-rw-r--r--src/lib/libcrypto/asn1/a_verify.c168
-rw-r--r--src/lib/libcrypto/asn1/asn1_item.c (renamed from src/lib/libcrypto/asn1/a_sign.c)379
-rw-r--r--src/lib/libcrypto/asn1/asn1_locl.h4
-rw-r--r--src/lib/libcrypto/asn1/asn1_old.c (renamed from src/lib/libcrypto/asn1/a_i2d_fp.c)100
8 files changed, 438 insertions, 715 deletions
diff --git a/src/lib/libcrypto/Makefile b/src/lib/libcrypto/Makefile
index cc53d8e6fe..9b9d448fa2 100644
--- a/src/lib/libcrypto/Makefile
+++ b/src/lib/libcrypto/Makefile
@@ -1,4 +1,4 @@
1# $OpenBSD: Makefile,v 1.60 2021/12/25 07:04:03 jsing Exp $ 1# $OpenBSD: Makefile,v 1.61 2021/12/25 12:00:22 jsing Exp $
2 2
3LIB= crypto 3LIB= crypto
4LIBREBUILD=y 4LIBREBUILD=y
@@ -53,8 +53,8 @@ SRCS+= aes_ctr.c aes_ige.c aes_wrap.c
53 53
54# asn1/ 54# asn1/
55SRCS+= a_object.c a_bitstr.c a_time.c a_int.c a_octet.c a_pkey.c a_pubkey.c 55SRCS+= a_object.c a_bitstr.c a_time.c a_int.c a_octet.c a_pkey.c a_pubkey.c
56SRCS+= a_print.c a_type.c a_dup.c a_d2i_fp.c a_i2d_fp.c a_string.c 56SRCS+= a_print.c a_type.c a_string.c
57SRCS+= a_enum.c a_utf8.c a_sign.c a_digest.c a_verify.c a_mbstr.c a_strex.c 57SRCS+= a_enum.c a_utf8.c a_mbstr.c a_strex.c
58SRCS+= x_algor.c x_val.c x_pubkey.c x_sig.c x_req.c x_attrib.c x_bignum.c 58SRCS+= x_algor.c x_val.c x_pubkey.c x_sig.c x_req.c x_attrib.c x_bignum.c
59SRCS+= x_long.c x_name.c x_x509.c x_x509a.c x_crl.c x_info.c x_spki.c nsseq.c 59SRCS+= x_long.c x_name.c x_x509.c x_x509a.c x_crl.c x_info.c x_spki.c nsseq.c
60SRCS+= x_nx509.c 60SRCS+= x_nx509.c
@@ -65,7 +65,7 @@ SRCS+= n_pkey.c
65SRCS+= x_pkey.c x_exten.c bio_asn1.c bio_ndef.c asn_mime.c 65SRCS+= x_pkey.c x_exten.c bio_asn1.c bio_ndef.c asn_mime.c
66SRCS+= asn1_gen.c asn1_par.c asn1_old_lib.c asn1_err.c a_strnid.c 66SRCS+= asn1_gen.c asn1_par.c asn1_old_lib.c asn1_err.c a_strnid.c
67SRCS+= evp_asn1.c asn_pack.c p5_pbe.c p5_pbev2.c p8_pkey.c asn_moid.c 67SRCS+= evp_asn1.c asn_pack.c p5_pbe.c p5_pbev2.c p8_pkey.c asn_moid.c
68SRCS+= a_time_tm.c asn1_types.c asn1_lib.c 68SRCS+= a_time_tm.c asn1_item.c asn1_old.c asn1_types.c asn1_lib.c
69 69
70# bf/ 70# bf/
71SRCS+= bf_skey.c bf_ecb.c bf_cfb64.c bf_ofb64.c 71SRCS+= bf_skey.c bf_ecb.c bf_cfb64.c bf_ofb64.c
diff --git a/src/lib/libcrypto/asn1/a_d2i_fp.c b/src/lib/libcrypto/asn1/a_d2i_fp.c
deleted file mode 100644
index 907ddd0aa9..0000000000
--- a/src/lib/libcrypto/asn1/a_d2i_fp.c
+++ /dev/null
@@ -1,289 +0,0 @@
1/* $OpenBSD: a_d2i_fp.c,v 1.17 2021/11/18 15:58:31 tb 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
62#include <openssl/asn1.h>
63#include <openssl/buffer.h>
64#include <openssl/err.h>
65
66static int asn1_d2i_read_bio(BIO *in, BUF_MEM **pb);
67
68#ifndef NO_OLD_ASN1
69
70void *
71ASN1_d2i_fp(void *(*xnew)(void), d2i_of_void *d2i, FILE *in, void **x)
72{
73 BIO *b;
74 void *ret;
75
76 if ((b = BIO_new(BIO_s_file())) == NULL) {
77 ASN1error(ERR_R_BUF_LIB);
78 return (NULL);
79 }
80 BIO_set_fp(b, in, BIO_NOCLOSE);
81 ret = ASN1_d2i_bio(xnew, d2i, b, x);
82 BIO_free(b);
83 return (ret);
84}
85
86void *
87ASN1_d2i_bio(void *(*xnew)(void), d2i_of_void *d2i, BIO *in, void **x)
88{
89 BUF_MEM *b = NULL;
90 const unsigned char *p;
91 void *ret = NULL;
92 int len;
93
94 len = asn1_d2i_read_bio(in, &b);
95 if (len < 0)
96 goto err;
97
98 p = (unsigned char *)b->data;
99 ret = d2i(x, &p, len);
100
101err:
102 if (b != NULL)
103 BUF_MEM_free(b);
104 return (ret);
105}
106
107#endif
108
109void *
110ASN1_item_d2i_bio(const ASN1_ITEM *it, BIO *in, void *x)
111{
112 BUF_MEM *b = NULL;
113 const unsigned char *p;
114 void *ret = NULL;
115 int len;
116
117 len = asn1_d2i_read_bio(in, &b);
118 if (len < 0)
119 goto err;
120
121 p = (const unsigned char *)b->data;
122 ret = ASN1_item_d2i(x, &p, len, it);
123
124err:
125 if (b != NULL)
126 BUF_MEM_free(b);
127 return (ret);
128}
129
130void *
131ASN1_item_d2i_fp(const ASN1_ITEM *it, FILE *in, void *x)
132{
133 BIO *b;
134 char *ret;
135
136 if ((b = BIO_new(BIO_s_file())) == NULL) {
137 ASN1error(ERR_R_BUF_LIB);
138 return (NULL);
139 }
140 BIO_set_fp(b, in, BIO_NOCLOSE);
141 ret = ASN1_item_d2i_bio(it, b, x);
142 BIO_free(b);
143 return (ret);
144}
145
146#define HEADER_SIZE 8
147#define ASN1_CHUNK_INITIAL_SIZE (16 * 1024)
148static int
149asn1_d2i_read_bio(BIO *in, BUF_MEM **pb)
150{
151 BUF_MEM *b;
152 unsigned char *p;
153 const unsigned char *q;
154 long slen;
155 int i, inf, tag, xclass;
156 size_t want = HEADER_SIZE;
157 int eos = 0;
158 size_t off = 0;
159 size_t len = 0;
160
161 b = BUF_MEM_new();
162 if (b == NULL) {
163 ASN1error(ERR_R_MALLOC_FAILURE);
164 return -1;
165 }
166
167 ERR_clear_error();
168 for (;;) {
169 if (want >= (len - off)) {
170 want -= (len - off);
171
172 if (len + want < len ||
173 !BUF_MEM_grow_clean(b, len + want)) {
174 ASN1error(ERR_R_MALLOC_FAILURE);
175 goto err;
176 }
177 i = BIO_read(in, &(b->data[len]), want);
178 if ((i < 0) && ((len - off) == 0)) {
179 ASN1error(ASN1_R_NOT_ENOUGH_DATA);
180 goto err;
181 }
182 if (i > 0) {
183 if (len + i < len) {
184 ASN1error(ASN1_R_TOO_LONG);
185 goto err;
186 }
187 len += i;
188 }
189 }
190 /* else data already loaded */
191
192 p = (unsigned char *) & (b->data[off]);
193 q = p;
194 inf = ASN1_get_object(&q, &slen, &tag, &xclass, len - off);
195 if (inf & 0x80) {
196 unsigned long e;
197
198 e = ERR_GET_REASON(ERR_peek_error());
199 if (e != ASN1_R_TOO_LONG)
200 goto err;
201 else
202 ERR_clear_error(); /* clear error */
203 }
204 i = q - p; /* header length */
205 off += i; /* end of data */
206
207 if (inf & 1) {
208 /* no data body so go round again */
209 eos++;
210 if (eos < 0) {
211 ASN1error(ASN1_R_HEADER_TOO_LONG);
212 goto err;
213 }
214 want = HEADER_SIZE;
215 } else if (eos && slen == 0 && tag == V_ASN1_EOC) {
216 /* eos value, so go back and read another header */
217 eos--;
218 if (eos <= 0)
219 break;
220 else
221 want = HEADER_SIZE;
222 } else {
223 /* suck in slen bytes of data */
224 want = slen;
225 if (want > (len - off)) {
226 size_t chunk_max = ASN1_CHUNK_INITIAL_SIZE;
227
228 want -= (len - off);
229 if (want > INT_MAX /* BIO_read takes an int length */ ||
230 len+want < len) {
231 ASN1error(ASN1_R_TOO_LONG);
232 goto err;
233 }
234 while (want > 0) {
235 /*
236 * Read content in chunks of increasing size
237 * so we can return an error for EOF without
238 * having to allocate the entire content length
239 * in one go.
240 */
241 size_t chunk = want > chunk_max ? chunk_max : want;
242
243 if (!BUF_MEM_grow_clean(b, len + chunk)) {
244 ASN1error(ERR_R_MALLOC_FAILURE);
245 goto err;
246 }
247 want -= chunk;
248 while (chunk > 0) {
249 i = BIO_read(in, &(b->data[len]), chunk);
250 if (i <= 0) {
251 ASN1error(ASN1_R_NOT_ENOUGH_DATA);
252 goto err;
253 }
254 /*
255 * This can't overflow because |len+want|
256 * didn't overflow.
257 */
258 len += i;
259 chunk -= i;
260 }
261 if (chunk_max < INT_MAX/2)
262 chunk_max *= 2;
263 }
264 }
265 if (off + slen < off) {
266 ASN1error(ASN1_R_TOO_LONG);
267 goto err;
268 }
269 off += slen;
270 if (eos <= 0) {
271 break;
272 } else
273 want = HEADER_SIZE;
274 }
275 }
276
277 if (off > INT_MAX) {
278 ASN1error(ASN1_R_TOO_LONG);
279 goto err;
280 }
281
282 *pb = b;
283 return off;
284
285err:
286 if (b != NULL)
287 BUF_MEM_free(b);
288 return -1;
289}
diff --git a/src/lib/libcrypto/asn1/a_digest.c b/src/lib/libcrypto/asn1/a_digest.c
deleted file mode 100644
index 5b95adf115..0000000000
--- a/src/lib/libcrypto/asn1/a_digest.c
+++ /dev/null
@@ -1,87 +0,0 @@
1/* $OpenBSD: a_digest.c,v 1.16 2018/04/06 09:19:36 tb 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 <sys/types.h>
60
61#include <stdio.h>
62#include <time.h>
63
64#include <openssl/buffer.h>
65#include <openssl/err.h>
66#include <openssl/evp.h>
67#include <openssl/x509.h>
68
69int
70ASN1_item_digest(const ASN1_ITEM *it, const EVP_MD *type, void *asn,
71 unsigned char *md, unsigned int *len)
72{
73 int i;
74 unsigned char *str = NULL;
75
76 i = ASN1_item_i2d(asn, &str, it);
77 if (!str)
78 return (0);
79
80 if (!EVP_Digest(str, i, md, len, type, NULL)) {
81 free(str);
82 return (0);
83 }
84
85 free(str);
86 return (1);
87}
diff --git a/src/lib/libcrypto/asn1/a_dup.c b/src/lib/libcrypto/asn1/a_dup.c
deleted file mode 100644
index 2e17a1e219..0000000000
--- a/src/lib/libcrypto/asn1/a_dup.c
+++ /dev/null
@@ -1,118 +0,0 @@
1/* $OpenBSD: a_dup.c,v 1.14 2017/01/29 17:49:22 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 <stdio.h>
60
61#include <openssl/asn1.h>
62#include <openssl/err.h>
63
64#ifndef NO_OLD_ASN1
65
66void *
67ASN1_dup(i2d_of_void *i2d, d2i_of_void *d2i, void *x)
68{
69 unsigned char *b, *p;
70 const unsigned char *p2;
71 int i;
72 char *ret;
73
74 if (x == NULL)
75 return (NULL);
76
77 i = i2d(x, NULL);
78 b = malloc(i + 10);
79 if (b == NULL) {
80 ASN1error(ERR_R_MALLOC_FAILURE);
81 return (NULL);
82 }
83 p = b;
84 i = i2d(x, &p);
85 p2 = b;
86 ret = d2i(NULL, &p2, i);
87 free(b);
88 return (ret);
89}
90
91#endif
92
93/* ASN1_ITEM version of dup: this follows the model above except we don't need
94 * to allocate the buffer. At some point this could be rewritten to directly dup
95 * the underlying structure instead of doing and encode and decode.
96 */
97
98void *
99ASN1_item_dup(const ASN1_ITEM *it, void *x)
100{
101 unsigned char *b = NULL;
102 const unsigned char *p;
103 long i;
104 void *ret;
105
106 if (x == NULL)
107 return (NULL);
108
109 i = ASN1_item_i2d(x, &b, it);
110 if (b == NULL) {
111 ASN1error(ERR_R_MALLOC_FAILURE);
112 return (NULL);
113 }
114 p = b;
115 ret = ASN1_item_d2i(NULL, &p, i, it);
116 free(b);
117 return (ret);
118}
diff --git a/src/lib/libcrypto/asn1/a_verify.c b/src/lib/libcrypto/asn1/a_verify.c
deleted file mode 100644
index a8a3790882..0000000000
--- a/src/lib/libcrypto/asn1/a_verify.c
+++ /dev/null
@@ -1,168 +0,0 @@
1/* $OpenBSD: a_verify.c,v 1.25 2021/12/12 21:30:13 tb 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 <sys/types.h>
60
61#include <stdio.h>
62#include <string.h>
63#include <time.h>
64
65#include <openssl/bn.h>
66#include <openssl/buffer.h>
67#include <openssl/err.h>
68#include <openssl/evp.h>
69#include <openssl/objects.h>
70#include <openssl/x509.h>
71
72#include "asn1_locl.h"
73#include "evp_locl.h"
74
75int
76ASN1_item_verify(const ASN1_ITEM *it, X509_ALGOR *a,
77 ASN1_BIT_STRING *signature, void *asn, EVP_PKEY *pkey)
78{
79 EVP_MD_CTX ctx;
80 unsigned char *buf_in = NULL;
81 int ret = -1, inl;
82
83 int mdnid, pknid;
84
85 if (!pkey) {
86 ASN1error(ERR_R_PASSED_NULL_PARAMETER);
87 return -1;
88 }
89
90 if (signature->type == V_ASN1_BIT_STRING && signature->flags & 0x7)
91 {
92 ASN1error(ASN1_R_INVALID_BIT_STRING_BITS_LEFT);
93 return -1;
94 }
95
96 EVP_MD_CTX_init(&ctx);
97
98 /* Convert signature OID into digest and public key OIDs */
99 if (!OBJ_find_sigid_algs(OBJ_obj2nid(a->algorithm), &mdnid, &pknid)) {
100 ASN1error(ASN1_R_UNKNOWN_SIGNATURE_ALGORITHM);
101 goto err;
102 }
103 if (mdnid == NID_undef) {
104 if (!pkey->ameth || !pkey->ameth->item_verify) {
105 ASN1error(ASN1_R_UNKNOWN_SIGNATURE_ALGORITHM);
106 goto err;
107 }
108 ret = pkey->ameth->item_verify(&ctx, it, asn, a,
109 signature, pkey);
110 /* Return value of 2 means carry on, anything else means we
111 * exit straight away: either a fatal error of the underlying
112 * verification routine handles all verification.
113 */
114 if (ret != 2)
115 goto err;
116 ret = -1;
117 } else {
118 const EVP_MD *type;
119 type = EVP_get_digestbynid(mdnid);
120 if (type == NULL) {
121 ASN1error(ASN1_R_UNKNOWN_MESSAGE_DIGEST_ALGORITHM);
122 goto err;
123 }
124
125 /* Check public key OID matches public key type */
126 if (EVP_PKEY_type(pknid) != pkey->ameth->pkey_id) {
127 ASN1error(ASN1_R_WRONG_PUBLIC_KEY_TYPE);
128 goto err;
129 }
130
131 if (!EVP_DigestVerifyInit(&ctx, NULL, type, NULL, pkey)) {
132 ASN1error(ERR_R_EVP_LIB);
133 ret = 0;
134 goto err;
135 }
136
137 }
138
139 inl = ASN1_item_i2d(asn, &buf_in, it);
140
141 if (buf_in == NULL) {
142 ASN1error(ERR_R_MALLOC_FAILURE);
143 goto err;
144 }
145
146 if (!EVP_DigestVerifyUpdate(&ctx, buf_in, inl)) {
147 ASN1error(ERR_R_EVP_LIB);
148 ret = 0;
149 goto err;
150 }
151
152 freezero(buf_in, (unsigned int)inl);
153
154 if (EVP_DigestVerifyFinal(&ctx, signature->data,
155 (size_t)signature->length) <= 0) {
156 ASN1error(ERR_R_EVP_LIB);
157 ret = 0;
158 goto err;
159 }
160 /* we don't need to zero the 'ctx' because we just checked
161 * public information */
162 /* memset(&ctx,0,sizeof(ctx)); */
163 ret = 1;
164
165err:
166 EVP_MD_CTX_cleanup(&ctx);
167 return (ret);
168}
diff --git a/src/lib/libcrypto/asn1/a_sign.c b/src/lib/libcrypto/asn1/asn1_item.c
index b6b4c20970..8db1713b29 100644
--- a/src/lib/libcrypto/asn1/a_sign.c
+++ b/src/lib/libcrypto/asn1/asn1_item.c
@@ -1,4 +1,4 @@
1/* $OpenBSD: a_sign.c,v 1.24 2021/12/12 21:30:13 tb Exp $ */ 1/* $OpenBSD: asn1_item.c,v 1.1 2021/12/25 12:00:22 jsing Exp $ */
2/* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com) 2/* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com)
3 * All rights reserved. 3 * All rights reserved.
4 * 4 *
@@ -109,22 +109,64 @@
109 * 109 *
110 */ 110 */
111 111
112#include <sys/types.h> 112#include <limits.h>
113 113
114#include <stdio.h>
115#include <string.h>
116#include <time.h>
117
118#include <openssl/bn.h>
119#include <openssl/buffer.h> 114#include <openssl/buffer.h>
120#include <openssl/err.h> 115#include <openssl/err.h>
121#include <openssl/evp.h> 116#include <openssl/evp.h>
122#include <openssl/objects.h>
123#include <openssl/x509.h> 117#include <openssl/x509.h>
124 118
125#include "asn1_locl.h" 119#include "asn1_locl.h"
126#include "evp_locl.h" 120#include "evp_locl.h"
127 121
122/*
123 * ASN1_ITEM version of dup: this follows the model above except we don't need
124 * to allocate the buffer. At some point this could be rewritten to directly dup
125 * the underlying structure instead of doing and encode and decode.
126 */
127
128int
129ASN1_item_digest(const ASN1_ITEM *it, const EVP_MD *type, void *asn,
130 unsigned char *md, unsigned int *len)
131{
132 int i;
133 unsigned char *str = NULL;
134
135 i = ASN1_item_i2d(asn, &str, it);
136 if (!str)
137 return (0);
138
139 if (!EVP_Digest(str, i, md, len, type, NULL)) {
140 free(str);
141 return (0);
142 }
143
144 free(str);
145 return (1);
146}
147
148void *
149ASN1_item_dup(const ASN1_ITEM *it, void *x)
150{
151 unsigned char *b = NULL;
152 const unsigned char *p;
153 long i;
154 void *ret;
155
156 if (x == NULL)
157 return (NULL);
158
159 i = ASN1_item_i2d(x, &b, it);
160 if (b == NULL) {
161 ASN1error(ERR_R_MALLOC_FAILURE);
162 return (NULL);
163 }
164 p = b;
165 ret = ASN1_item_d2i(NULL, &p, i, it);
166 free(b);
167 return (ret);
168}
169
128int 170int
129ASN1_item_sign(const ASN1_ITEM *it, X509_ALGOR *algor1, X509_ALGOR *algor2, 171ASN1_item_sign(const ASN1_ITEM *it, X509_ALGOR *algor1, X509_ALGOR *algor2,
130 ASN1_BIT_STRING *signature, void *asn, EVP_PKEY *pkey, const EVP_MD *type) 172 ASN1_BIT_STRING *signature, void *asn, EVP_PKEY *pkey, const EVP_MD *type)
@@ -138,7 +180,6 @@ ASN1_item_sign(const ASN1_ITEM *it, X509_ALGOR *algor1, X509_ALGOR *algor2,
138 return ASN1_item_sign_ctx(it, algor1, algor2, signature, asn, &ctx); 180 return ASN1_item_sign_ctx(it, algor1, algor2, signature, asn, &ctx);
139} 181}
140 182
141
142int 183int
143ASN1_item_sign_ctx(const ASN1_ITEM *it, X509_ALGOR *algor1, X509_ALGOR *algor2, 184ASN1_item_sign_ctx(const ASN1_ITEM *it, X509_ALGOR *algor1, X509_ALGOR *algor2,
144 ASN1_BIT_STRING *signature, void *asn, EVP_MD_CTX *ctx) 185 ASN1_BIT_STRING *signature, void *asn, EVP_MD_CTX *ctx)
@@ -232,3 +273,323 @@ err:
232 freezero((char *)buf_out, outll); 273 freezero((char *)buf_out, outll);
233 return (outl); 274 return (outl);
234} 275}
276
277int
278ASN1_item_verify(const ASN1_ITEM *it, X509_ALGOR *a,
279 ASN1_BIT_STRING *signature, void *asn, EVP_PKEY *pkey)
280{
281 EVP_MD_CTX ctx;
282 unsigned char *buf_in = NULL;
283 int ret = -1, inl;
284
285 int mdnid, pknid;
286
287 if (!pkey) {
288 ASN1error(ERR_R_PASSED_NULL_PARAMETER);
289 return -1;
290 }
291
292 if (signature->type == V_ASN1_BIT_STRING && signature->flags & 0x7)
293 {
294 ASN1error(ASN1_R_INVALID_BIT_STRING_BITS_LEFT);
295 return -1;
296 }
297
298 EVP_MD_CTX_init(&ctx);
299
300 /* Convert signature OID into digest and public key OIDs */
301 if (!OBJ_find_sigid_algs(OBJ_obj2nid(a->algorithm), &mdnid, &pknid)) {
302 ASN1error(ASN1_R_UNKNOWN_SIGNATURE_ALGORITHM);
303 goto err;
304 }
305 if (mdnid == NID_undef) {
306 if (!pkey->ameth || !pkey->ameth->item_verify) {
307 ASN1error(ASN1_R_UNKNOWN_SIGNATURE_ALGORITHM);
308 goto err;
309 }
310 ret = pkey->ameth->item_verify(&ctx, it, asn, a,
311 signature, pkey);
312 /* Return value of 2 means carry on, anything else means we
313 * exit straight away: either a fatal error of the underlying
314 * verification routine handles all verification.
315 */
316 if (ret != 2)
317 goto err;
318 ret = -1;
319 } else {
320 const EVP_MD *type;
321 type = EVP_get_digestbynid(mdnid);
322 if (type == NULL) {
323 ASN1error(ASN1_R_UNKNOWN_MESSAGE_DIGEST_ALGORITHM);
324 goto err;
325 }
326
327 /* Check public key OID matches public key type */
328 if (EVP_PKEY_type(pknid) != pkey->ameth->pkey_id) {
329 ASN1error(ASN1_R_WRONG_PUBLIC_KEY_TYPE);
330 goto err;
331 }
332
333 if (!EVP_DigestVerifyInit(&ctx, NULL, type, NULL, pkey)) {
334 ASN1error(ERR_R_EVP_LIB);
335 ret = 0;
336 goto err;
337 }
338
339 }
340
341 inl = ASN1_item_i2d(asn, &buf_in, it);
342
343 if (buf_in == NULL) {
344 ASN1error(ERR_R_MALLOC_FAILURE);
345 goto err;
346 }
347
348 if (!EVP_DigestVerifyUpdate(&ctx, buf_in, inl)) {
349 ASN1error(ERR_R_EVP_LIB);
350 ret = 0;
351 goto err;
352 }
353
354 freezero(buf_in, (unsigned int)inl);
355
356 if (EVP_DigestVerifyFinal(&ctx, signature->data,
357 (size_t)signature->length) <= 0) {
358 ASN1error(ERR_R_EVP_LIB);
359 ret = 0;
360 goto err;
361 }
362 /* we don't need to zero the 'ctx' because we just checked
363 * public information */
364 /* memset(&ctx,0,sizeof(ctx)); */
365 ret = 1;
366
367err:
368 EVP_MD_CTX_cleanup(&ctx);
369 return (ret);
370}
371
372#define HEADER_SIZE 8
373#define ASN1_CHUNK_INITIAL_SIZE (16 * 1024)
374int
375asn1_d2i_read_bio(BIO *in, BUF_MEM **pb)
376{
377 BUF_MEM *b;
378 unsigned char *p;
379 const unsigned char *q;
380 long slen;
381 int i, inf, tag, xclass;
382 size_t want = HEADER_SIZE;
383 int eos = 0;
384 size_t off = 0;
385 size_t len = 0;
386
387 b = BUF_MEM_new();
388 if (b == NULL) {
389 ASN1error(ERR_R_MALLOC_FAILURE);
390 return -1;
391 }
392
393 ERR_clear_error();
394 for (;;) {
395 if (want >= (len - off)) {
396 want -= (len - off);
397
398 if (len + want < len ||
399 !BUF_MEM_grow_clean(b, len + want)) {
400 ASN1error(ERR_R_MALLOC_FAILURE);
401 goto err;
402 }
403 i = BIO_read(in, &(b->data[len]), want);
404 if ((i < 0) && ((len - off) == 0)) {
405 ASN1error(ASN1_R_NOT_ENOUGH_DATA);
406 goto err;
407 }
408 if (i > 0) {
409 if (len + i < len) {
410 ASN1error(ASN1_R_TOO_LONG);
411 goto err;
412 }
413 len += i;
414 }
415 }
416 /* else data already loaded */
417
418 p = (unsigned char *) & (b->data[off]);
419 q = p;
420 inf = ASN1_get_object(&q, &slen, &tag, &xclass, len - off);
421 if (inf & 0x80) {
422 unsigned long e;
423
424 e = ERR_GET_REASON(ERR_peek_error());
425 if (e != ASN1_R_TOO_LONG)
426 goto err;
427 else
428 ERR_clear_error(); /* clear error */
429 }
430 i = q - p; /* header length */
431 off += i; /* end of data */
432
433 if (inf & 1) {
434 /* no data body so go round again */
435 eos++;
436 if (eos < 0) {
437 ASN1error(ASN1_R_HEADER_TOO_LONG);
438 goto err;
439 }
440 want = HEADER_SIZE;
441 } else if (eos && slen == 0 && tag == V_ASN1_EOC) {
442 /* eos value, so go back and read another header */
443 eos--;
444 if (eos <= 0)
445 break;
446 else
447 want = HEADER_SIZE;
448 } else {
449 /* suck in slen bytes of data */
450 want = slen;
451 if (want > (len - off)) {
452 size_t chunk_max = ASN1_CHUNK_INITIAL_SIZE;
453
454 want -= (len - off);
455 if (want > INT_MAX /* BIO_read takes an int length */ ||
456 len+want < len) {
457 ASN1error(ASN1_R_TOO_LONG);
458 goto err;
459 }
460 while (want > 0) {
461 /*
462 * Read content in chunks of increasing size
463 * so we can return an error for EOF without
464 * having to allocate the entire content length
465 * in one go.
466 */
467 size_t chunk = want > chunk_max ? chunk_max : want;
468
469 if (!BUF_MEM_grow_clean(b, len + chunk)) {
470 ASN1error(ERR_R_MALLOC_FAILURE);
471 goto err;
472 }
473 want -= chunk;
474 while (chunk > 0) {
475 i = BIO_read(in, &(b->data[len]), chunk);
476 if (i <= 0) {
477 ASN1error(ASN1_R_NOT_ENOUGH_DATA);
478 goto err;
479 }
480 /*
481 * This can't overflow because |len+want|
482 * didn't overflow.
483 */
484 len += i;
485 chunk -= i;
486 }
487 if (chunk_max < INT_MAX/2)
488 chunk_max *= 2;
489 }
490 }
491 if (off + slen < off) {
492 ASN1error(ASN1_R_TOO_LONG);
493 goto err;
494 }
495 off += slen;
496 if (eos <= 0) {
497 break;
498 } else
499 want = HEADER_SIZE;
500 }
501 }
502
503 if (off > INT_MAX) {
504 ASN1error(ASN1_R_TOO_LONG);
505 goto err;
506 }
507
508 *pb = b;
509 return off;
510
511err:
512 if (b != NULL)
513 BUF_MEM_free(b);
514 return -1;
515}
516
517void *
518ASN1_item_d2i_bio(const ASN1_ITEM *it, BIO *in, void *x)
519{
520 BUF_MEM *b = NULL;
521 const unsigned char *p;
522 void *ret = NULL;
523 int len;
524
525 len = asn1_d2i_read_bio(in, &b);
526 if (len < 0)
527 goto err;
528
529 p = (const unsigned char *)b->data;
530 ret = ASN1_item_d2i(x, &p, len, it);
531
532err:
533 if (b != NULL)
534 BUF_MEM_free(b);
535 return (ret);
536}
537
538void *
539ASN1_item_d2i_fp(const ASN1_ITEM *it, FILE *in, void *x)
540{
541 BIO *b;
542 char *ret;
543
544 if ((b = BIO_new(BIO_s_file())) == NULL) {
545 ASN1error(ERR_R_BUF_LIB);
546 return (NULL);
547 }
548 BIO_set_fp(b, in, BIO_NOCLOSE);
549 ret = ASN1_item_d2i_bio(it, b, x);
550 BIO_free(b);
551 return (ret);
552}
553
554int
555ASN1_item_i2d_bio(const ASN1_ITEM *it, BIO *out, void *x)
556{
557 unsigned char *b = NULL;
558 int i, j = 0, n, ret = 1;
559
560 n = ASN1_item_i2d(x, &b, it);
561 if (b == NULL) {
562 ASN1error(ERR_R_MALLOC_FAILURE);
563 return (0);
564 }
565
566 for (;;) {
567 i = BIO_write(out, &(b[j]), n);
568 if (i == n)
569 break;
570 if (i <= 0) {
571 ret = 0;
572 break;
573 }
574 j += i;
575 n -= i;
576 }
577 free(b);
578 return (ret);
579}
580
581int
582ASN1_item_i2d_fp(const ASN1_ITEM *it, FILE *out, void *x)
583{
584 BIO *b;
585 int ret;
586
587 if ((b = BIO_new(BIO_s_file())) == NULL) {
588 ASN1error(ERR_R_BUF_LIB);
589 return (0);
590 }
591 BIO_set_fp(b, out, BIO_NOCLOSE);
592 ret = ASN1_item_i2d_bio(it, b, x);
593 BIO_free(b);
594 return (ret);
595}
diff --git a/src/lib/libcrypto/asn1/asn1_locl.h b/src/lib/libcrypto/asn1/asn1_locl.h
index 851c6e3400..3b949dba65 100644
--- a/src/lib/libcrypto/asn1/asn1_locl.h
+++ b/src/lib/libcrypto/asn1/asn1_locl.h
@@ -1,4 +1,4 @@
1/* $OpenBSD: asn1_locl.h,v 1.14 2021/12/25 07:04:03 jsing Exp $ */ 1/* $OpenBSD: asn1_locl.h,v 1.15 2021/12/25 12:00:22 jsing 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 2006. 3 * project 2006.
4 */ 4 */
@@ -157,6 +157,8 @@ struct x509_crl_method_st {
157int UTF8_getc(const unsigned char *str, int len, unsigned long *val); 157int UTF8_getc(const unsigned char *str, int len, unsigned long *val);
158int UTF8_putc(unsigned char *str, int len, unsigned long value); 158int UTF8_putc(unsigned char *str, int len, unsigned long value);
159 159
160int asn1_d2i_read_bio(BIO *in, BUF_MEM **pb);
161
160int asn1_get_object_cbs(CBS *cbs, int der_mode, uint8_t *out_class, 162int asn1_get_object_cbs(CBS *cbs, int der_mode, uint8_t *out_class,
161 int *out_constructed, uint32_t *out_tag_number, int *out_indefinite, 163 int *out_constructed, uint32_t *out_tag_number, int *out_indefinite,
162 uint32_t *out_length); 164 uint32_t *out_length);
diff --git a/src/lib/libcrypto/asn1/a_i2d_fp.c b/src/lib/libcrypto/asn1/asn1_old.c
index 6398978aac..d23cae06fb 100644
--- a/src/lib/libcrypto/asn1/a_i2d_fp.c
+++ b/src/lib/libcrypto/asn1/asn1_old.c
@@ -1,4 +1,4 @@
1/* $OpenBSD: a_i2d_fp.c,v 1.15 2017/01/29 17:49:22 beck Exp $ */ 1/* $OpenBSD: asn1_old.c,v 1.1 2021/12/25 12:00:22 jsing Exp $ */
2/* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com) 2/* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com)
3 * All rights reserved. 3 * All rights reserved.
4 * 4 *
@@ -56,66 +56,81 @@
56 * [including the GNU Public Licence.] 56 * [including the GNU Public Licence.]
57 */ 57 */
58 58
59#include <limits.h>
59#include <stdio.h> 60#include <stdio.h>
60 61
61#include <openssl/asn1.h> 62#include <openssl/asn1.h>
62#include <openssl/buffer.h> 63#include <openssl/buffer.h>
63#include <openssl/err.h> 64#include <openssl/err.h>
64 65
66#include "asn1_locl.h"
67
65#ifndef NO_OLD_ASN1 68#ifndef NO_OLD_ASN1
66 69
67int 70void *
68ASN1_i2d_fp(i2d_of_void *i2d, FILE *out, void *x) 71ASN1_dup(i2d_of_void *i2d, d2i_of_void *d2i, void *x)
72{
73 unsigned char *b, *p;
74 const unsigned char *p2;
75 int i;
76 char *ret;
77
78 if (x == NULL)
79 return (NULL);
80
81 i = i2d(x, NULL);
82 b = malloc(i + 10);
83 if (b == NULL) {
84 ASN1error(ERR_R_MALLOC_FAILURE);
85 return (NULL);
86 }
87 p = b;
88 i = i2d(x, &p);
89 p2 = b;
90 ret = d2i(NULL, &p2, i);
91 free(b);
92 return (ret);
93}
94
95void *
96ASN1_d2i_fp(void *(*xnew)(void), d2i_of_void *d2i, FILE *in, void **x)
69{ 97{
70 BIO *b; 98 BIO *b;
71 int ret; 99 void *ret;
72 100
73 if ((b = BIO_new(BIO_s_file())) == NULL) { 101 if ((b = BIO_new(BIO_s_file())) == NULL) {
74 ASN1error(ERR_R_BUF_LIB); 102 ASN1error(ERR_R_BUF_LIB);
75 return (0); 103 return (NULL);
76 } 104 }
77 BIO_set_fp(b, out, BIO_NOCLOSE); 105 BIO_set_fp(b, in, BIO_NOCLOSE);
78 ret = ASN1_i2d_bio(i2d, b, x); 106 ret = ASN1_d2i_bio(xnew, d2i, b, x);
79 BIO_free(b); 107 BIO_free(b);
80 return (ret); 108 return (ret);
81} 109}
82 110
83int 111void *
84ASN1_i2d_bio(i2d_of_void *i2d, BIO *out, unsigned char *x) 112ASN1_d2i_bio(void *(*xnew)(void), d2i_of_void *d2i, BIO *in, void **x)
85{ 113{
86 char *b; 114 BUF_MEM *b = NULL;
87 unsigned char *p; 115 const unsigned char *p;
88 int i, j = 0, n, ret = 1; 116 void *ret = NULL;
117 int len;
89 118
90 n = i2d(x, NULL); 119 len = asn1_d2i_read_bio(in, &b);
91 b = malloc(n); 120 if (len < 0)
92 if (b == NULL) { 121 goto err;
93 ASN1error(ERR_R_MALLOC_FAILURE);
94 return (0);
95 }
96 122
97 p = (unsigned char *)b; 123 p = (unsigned char *)b->data;
98 i2d(x, &p); 124 ret = d2i(x, &p, len);
99 125
100 for (;;) { 126err:
101 i = BIO_write(out, &(b[j]), n); 127 if (b != NULL)
102 if (i == n) 128 BUF_MEM_free(b);
103 break;
104 if (i <= 0) {
105 ret = 0;
106 break;
107 }
108 j += i;
109 n -= i;
110 }
111 free(b);
112 return (ret); 129 return (ret);
113} 130}
114 131
115#endif
116
117int 132int
118ASN1_item_i2d_fp(const ASN1_ITEM *it, FILE *out, void *x) 133ASN1_i2d_fp(i2d_of_void *i2d, FILE *out, void *x)
119{ 134{
120 BIO *b; 135 BIO *b;
121 int ret; 136 int ret;
@@ -125,23 +140,28 @@ ASN1_item_i2d_fp(const ASN1_ITEM *it, FILE *out, void *x)
125 return (0); 140 return (0);
126 } 141 }
127 BIO_set_fp(b, out, BIO_NOCLOSE); 142 BIO_set_fp(b, out, BIO_NOCLOSE);
128 ret = ASN1_item_i2d_bio(it, b, x); 143 ret = ASN1_i2d_bio(i2d, b, x);
129 BIO_free(b); 144 BIO_free(b);
130 return (ret); 145 return (ret);
131} 146}
132 147
133int 148int
134ASN1_item_i2d_bio(const ASN1_ITEM *it, BIO *out, void *x) 149ASN1_i2d_bio(i2d_of_void *i2d, BIO *out, unsigned char *x)
135{ 150{
136 unsigned char *b = NULL; 151 char *b;
152 unsigned char *p;
137 int i, j = 0, n, ret = 1; 153 int i, j = 0, n, ret = 1;
138 154
139 n = ASN1_item_i2d(x, &b, it); 155 n = i2d(x, NULL);
156 b = malloc(n);
140 if (b == NULL) { 157 if (b == NULL) {
141 ASN1error(ERR_R_MALLOC_FAILURE); 158 ASN1error(ERR_R_MALLOC_FAILURE);
142 return (0); 159 return (0);
143 } 160 }
144 161
162 p = (unsigned char *)b;
163 i2d(x, &p);
164
145 for (;;) { 165 for (;;) {
146 i = BIO_write(out, &(b[j]), n); 166 i = BIO_write(out, &(b[j]), n);
147 if (i == n) 167 if (i == n)
@@ -156,3 +176,5 @@ ASN1_item_i2d_bio(const ASN1_ITEM *it, BIO *out, void *x)
156 free(b); 176 free(b);
157 return (ret); 177 return (ret);
158} 178}
179
180#endif