1*e0c4386eSCy Schubert /*
2*e0c4386eSCy Schubert  * Copyright 2020-2021 The OpenSSL Project Authors. All Rights Reserved.
3*e0c4386eSCy Schubert  *
4*e0c4386eSCy Schubert  * Licensed under the Apache License 2.0 (the "License").  You may not use
5*e0c4386eSCy Schubert  * this file except in compliance with the License.  You can obtain a copy
6*e0c4386eSCy Schubert  * in the file LICENSE in the source distribution or at
7*e0c4386eSCy Schubert  * https://www.openssl.org/source/license.html
8*e0c4386eSCy Schubert  */
9*e0c4386eSCy Schubert 
10*e0c4386eSCy Schubert /*
11*e0c4386eSCy Schubert  * This program tests the following known key type specific function against
12*e0c4386eSCy Schubert  * the corresponding OSSL_ENCODER implementation:
13*e0c4386eSCy Schubert  *
14*e0c4386eSCy Schubert  * - i2d_{TYPE}PrivateKey()
15*e0c4386eSCy Schubert  * - i2d_{TYPE}PublicKey(),
16*e0c4386eSCy Schubert  * - i2d_{TYPE}params(),
17*e0c4386eSCy Schubert  * - i2d_{TYPE}_PUBKEY(),
18*e0c4386eSCy Schubert  * - PEM_write_bio_{TYPE}PrivateKey()
19*e0c4386eSCy Schubert  * - PEM_write_bio_{TYPE}PublicKey()
20*e0c4386eSCy Schubert  * - PEM_write_bio_{TYPE}params()
21*e0c4386eSCy Schubert  * - PEM_write_bio_{TYPE}_PUBKEY()
22*e0c4386eSCy Schubert  *
23*e0c4386eSCy Schubert  * as well as the following functions against the corresponding OSSL_DECODER
24*e0c4386eSCy Schubert  * implementation.
25*e0c4386eSCy Schubert  *
26*e0c4386eSCy Schubert  * - d2i_{TYPE}PrivateKey()
27*e0c4386eSCy Schubert  * - d2i_{TYPE}PublicKey(),
28*e0c4386eSCy Schubert  * - d2i_{TYPE}params(),
29*e0c4386eSCy Schubert  * - d2i_{TYPE}_PUBKEY(),
30*e0c4386eSCy Schubert  * - PEM_read_bio_{TYPE}PrivateKey()
31*e0c4386eSCy Schubert  * - PEM_read_bio_{TYPE}PublicKey()
32*e0c4386eSCy Schubert  * - PEM_read_bio_{TYPE}params()
33*e0c4386eSCy Schubert  * - PEM_read_bio_{TYPE}_PUBKEY()
34*e0c4386eSCy Schubert  */
35*e0c4386eSCy Schubert 
36*e0c4386eSCy Schubert #include <stdlib.h>
37*e0c4386eSCy Schubert #include <string.h>
38*e0c4386eSCy Schubert 
39*e0c4386eSCy Schubert /*
40*e0c4386eSCy Schubert  * We test deprecated functions, so we need to suppress deprecation warnings.
41*e0c4386eSCy Schubert  */
42*e0c4386eSCy Schubert #define OPENSSL_SUPPRESS_DEPRECATED
43*e0c4386eSCy Schubert 
44*e0c4386eSCy Schubert #include <openssl/bio.h>
45*e0c4386eSCy Schubert #include <openssl/evp.h>
46*e0c4386eSCy Schubert #include <openssl/asn1.h>
47*e0c4386eSCy Schubert #include <openssl/pem.h>
48*e0c4386eSCy Schubert #include <openssl/params.h>
49*e0c4386eSCy Schubert #include <openssl/encoder.h>
50*e0c4386eSCy Schubert #include <openssl/decoder.h>
51*e0c4386eSCy Schubert #include <openssl/dh.h>
52*e0c4386eSCy Schubert #include <openssl/dsa.h>
53*e0c4386eSCy Schubert #ifndef OPENSSL_NO_DEPRECATED_3_0
54*e0c4386eSCy Schubert # include <openssl/rsa.h>
55*e0c4386eSCy Schubert #endif
56*e0c4386eSCy Schubert #include "internal/nelem.h"
57*e0c4386eSCy Schubert #include "crypto/evp.h"
58*e0c4386eSCy Schubert 
59*e0c4386eSCy Schubert #include "testutil.h"
60*e0c4386eSCy Schubert 
61*e0c4386eSCy Schubert typedef int PEM_write_bio_of_void_protected(BIO *out, const void *obj,
62*e0c4386eSCy Schubert                                             const EVP_CIPHER *enc,
63*e0c4386eSCy Schubert                                             unsigned char *kstr, int klen,
64*e0c4386eSCy Schubert                                             pem_password_cb *cb, void *u);
65*e0c4386eSCy Schubert typedef int PEM_write_bio_of_void_unprotected(BIO *out, const void *obj);
66*e0c4386eSCy Schubert typedef void *PEM_read_bio_of_void(BIO *out, void **obj,
67*e0c4386eSCy Schubert                                    pem_password_cb *cb, void *u);
68*e0c4386eSCy Schubert typedef int EVP_PKEY_print_fn(BIO *out, const EVP_PKEY *pkey,
69*e0c4386eSCy Schubert                               int indent, ASN1_PCTX *pctx);
70*e0c4386eSCy Schubert typedef int EVP_PKEY_eq_fn(const EVP_PKEY *a, const EVP_PKEY *b);
71*e0c4386eSCy Schubert 
72*e0c4386eSCy Schubert static struct test_stanza_st {
73*e0c4386eSCy Schubert     const char *keytype;
74*e0c4386eSCy Schubert     const char *structure[2];
75*e0c4386eSCy Schubert     int evp_type;
76*e0c4386eSCy Schubert 
77*e0c4386eSCy Schubert     i2d_of_void *i2d_PrivateKey;
78*e0c4386eSCy Schubert     i2d_of_void *i2d_PublicKey;
79*e0c4386eSCy Schubert     i2d_of_void *i2d_params;
80*e0c4386eSCy Schubert     i2d_of_void *i2d_PUBKEY;
81*e0c4386eSCy Schubert     PEM_write_bio_of_void_protected *pem_write_bio_PrivateKey;
82*e0c4386eSCy Schubert     PEM_write_bio_of_void_unprotected *pem_write_bio_PublicKey;
83*e0c4386eSCy Schubert     PEM_write_bio_of_void_unprotected *pem_write_bio_params;
84*e0c4386eSCy Schubert     PEM_write_bio_of_void_unprotected *pem_write_bio_PUBKEY;
85*e0c4386eSCy Schubert 
86*e0c4386eSCy Schubert     d2i_of_void *d2i_PrivateKey;
87*e0c4386eSCy Schubert     d2i_of_void *d2i_PublicKey;
88*e0c4386eSCy Schubert     d2i_of_void *d2i_params;
89*e0c4386eSCy Schubert     d2i_of_void *d2i_PUBKEY;
90*e0c4386eSCy Schubert     PEM_read_bio_of_void *pem_read_bio_PrivateKey;
91*e0c4386eSCy Schubert     PEM_read_bio_of_void *pem_read_bio_PublicKey;
92*e0c4386eSCy Schubert     PEM_read_bio_of_void *pem_read_bio_params;
93*e0c4386eSCy Schubert     PEM_read_bio_of_void *pem_read_bio_PUBKEY;
94*e0c4386eSCy Schubert } test_stanzas[] = {
95*e0c4386eSCy Schubert #ifndef OPENSSL_NO_DH
96*e0c4386eSCy Schubert     { "DH", { "DH", "type-specific" }, EVP_PKEY_DH,
97*e0c4386eSCy Schubert       NULL,                      /* No i2d_DHPrivateKey */
98*e0c4386eSCy Schubert       NULL,                      /* No i2d_DHPublicKey */
99*e0c4386eSCy Schubert       (i2d_of_void *)i2d_DHparams,
100*e0c4386eSCy Schubert       NULL,                      /* No i2d_DH_PUBKEY */
101*e0c4386eSCy Schubert       NULL,                      /* No PEM_write_bio_DHPrivateKey */
102*e0c4386eSCy Schubert       NULL,                      /* No PEM_write_bio_DHPublicKey */
103*e0c4386eSCy Schubert       (PEM_write_bio_of_void_unprotected *)PEM_write_bio_DHparams,
104*e0c4386eSCy Schubert       NULL,                      /* No PEM_write_bio_DH_PUBKEY */
105*e0c4386eSCy Schubert       NULL,                      /* No d2i_DHPrivateKey */
106*e0c4386eSCy Schubert       NULL,                      /* No d2i_DHPublicKey */
107*e0c4386eSCy Schubert       (d2i_of_void *)d2i_DHparams,
108*e0c4386eSCy Schubert       NULL,                      /* No d2i_DH_PUBKEY */
109*e0c4386eSCy Schubert       NULL,                      /* No PEM_read_bio_DHPrivateKey */
110*e0c4386eSCy Schubert       NULL,                      /* No PEM_read_bio_DHPublicKey */
111*e0c4386eSCy Schubert       (PEM_read_bio_of_void *)PEM_read_bio_DHparams,
112*e0c4386eSCy Schubert       NULL },                    /* No PEM_read_bio_DH_PUBKEY */
113*e0c4386eSCy Schubert     { "DHX", { "DHX", "type-specific" }, EVP_PKEY_DHX,
114*e0c4386eSCy Schubert       NULL,                      /* No i2d_DHxPrivateKey */
115*e0c4386eSCy Schubert       NULL,                      /* No i2d_DHxPublicKey */
116*e0c4386eSCy Schubert       (i2d_of_void *)i2d_DHxparams,
117*e0c4386eSCy Schubert       NULL,                      /* No i2d_DHx_PUBKEY */
118*e0c4386eSCy Schubert       NULL,                      /* No PEM_write_bio_DHxPrivateKey */
119*e0c4386eSCy Schubert       NULL,                      /* No PEM_write_bio_DHxPublicKey */
120*e0c4386eSCy Schubert       (PEM_write_bio_of_void_unprotected *)PEM_write_bio_DHxparams,
121*e0c4386eSCy Schubert       NULL,                      /* No PEM_write_bio_DHx_PUBKEY */
122*e0c4386eSCy Schubert       NULL,                      /* No d2i_DHxPrivateKey */
123*e0c4386eSCy Schubert       NULL,                      /* No d2i_DHxPublicKey */
124*e0c4386eSCy Schubert       (d2i_of_void *)d2i_DHxparams,
125*e0c4386eSCy Schubert       NULL,                      /* No d2i_DHx_PUBKEY */
126*e0c4386eSCy Schubert       NULL,                      /* No PEM_read_bio_DHxPrivateKey */
127*e0c4386eSCy Schubert       NULL,                      /* No PEM_read_bio_DHxPublicKey */
128*e0c4386eSCy Schubert       NULL,                      /* No PEM_read_bio_DHxparams */
129*e0c4386eSCy Schubert       NULL },                    /* No PEM_read_bio_DHx_PUBKEY */
130*e0c4386eSCy Schubert #endif
131*e0c4386eSCy Schubert #ifndef OPENSSL_NO_DSA
132*e0c4386eSCy Schubert     { "DSA", { "DSA", "type-specific" }, EVP_PKEY_DSA,
133*e0c4386eSCy Schubert       (i2d_of_void *)i2d_DSAPrivateKey,
134*e0c4386eSCy Schubert       (i2d_of_void *)i2d_DSAPublicKey,
135*e0c4386eSCy Schubert       (i2d_of_void *)i2d_DSAparams,
136*e0c4386eSCy Schubert       (i2d_of_void *)i2d_DSA_PUBKEY,
137*e0c4386eSCy Schubert       (PEM_write_bio_of_void_protected *)PEM_write_bio_DSAPrivateKey,
138*e0c4386eSCy Schubert       NULL,                      /* No PEM_write_bio_DSAPublicKey */
139*e0c4386eSCy Schubert       (PEM_write_bio_of_void_unprotected *)PEM_write_bio_DSAparams,
140*e0c4386eSCy Schubert       (PEM_write_bio_of_void_unprotected *)PEM_write_bio_DSA_PUBKEY,
141*e0c4386eSCy Schubert       (d2i_of_void *)d2i_DSAPrivateKey,
142*e0c4386eSCy Schubert       (d2i_of_void *)d2i_DSAPublicKey,
143*e0c4386eSCy Schubert       (d2i_of_void *)d2i_DSAparams,
144*e0c4386eSCy Schubert       (d2i_of_void *)d2i_DSA_PUBKEY,
145*e0c4386eSCy Schubert       (PEM_read_bio_of_void *)PEM_read_bio_DSAPrivateKey,
146*e0c4386eSCy Schubert       NULL,                      /* No PEM_write_bio_DSAPublicKey */
147*e0c4386eSCy Schubert       (PEM_read_bio_of_void *)PEM_read_bio_DSAparams,
148*e0c4386eSCy Schubert       (PEM_read_bio_of_void *)PEM_read_bio_DSA_PUBKEY },
149*e0c4386eSCy Schubert #endif
150*e0c4386eSCy Schubert #ifndef OPENSSL_NO_EC
151*e0c4386eSCy Schubert     { "EC", { "EC", "type-specific" }, EVP_PKEY_EC,
152*e0c4386eSCy Schubert       (i2d_of_void *)i2d_ECPrivateKey,
153*e0c4386eSCy Schubert       NULL,                      /* No i2d_ECPublicKey */
154*e0c4386eSCy Schubert       (i2d_of_void *)i2d_ECParameters,
155*e0c4386eSCy Schubert       (i2d_of_void *)i2d_EC_PUBKEY,
156*e0c4386eSCy Schubert       (PEM_write_bio_of_void_protected *)PEM_write_bio_ECPrivateKey,
157*e0c4386eSCy Schubert       NULL,                      /* No PEM_write_bio_ECPublicKey */
158*e0c4386eSCy Schubert       NULL,                      /* No PEM_write_bio_ECParameters */
159*e0c4386eSCy Schubert       (PEM_write_bio_of_void_unprotected *)PEM_write_bio_EC_PUBKEY,
160*e0c4386eSCy Schubert       (d2i_of_void *)d2i_ECPrivateKey,
161*e0c4386eSCy Schubert       NULL,                      /* No d2i_ECPublicKey */
162*e0c4386eSCy Schubert       (d2i_of_void *)d2i_ECParameters,
163*e0c4386eSCy Schubert       (d2i_of_void *)d2i_EC_PUBKEY,
164*e0c4386eSCy Schubert       (PEM_read_bio_of_void *)PEM_read_bio_ECPrivateKey,
165*e0c4386eSCy Schubert       NULL,                      /* No PEM_read_bio_ECPublicKey */
166*e0c4386eSCy Schubert       NULL,                      /* No PEM_read_bio_ECParameters */
167*e0c4386eSCy Schubert       (PEM_read_bio_of_void *)PEM_read_bio_EC_PUBKEY, },
168*e0c4386eSCy Schubert #endif
169*e0c4386eSCy Schubert     { "RSA", { "RSA", "type-specific" }, EVP_PKEY_RSA,
170*e0c4386eSCy Schubert       (i2d_of_void *)i2d_RSAPrivateKey,
171*e0c4386eSCy Schubert       (i2d_of_void *)i2d_RSAPublicKey,
172*e0c4386eSCy Schubert       NULL,                      /* No i2d_RSAparams */
173*e0c4386eSCy Schubert       (i2d_of_void *)i2d_RSA_PUBKEY,
174*e0c4386eSCy Schubert       (PEM_write_bio_of_void_protected *)PEM_write_bio_RSAPrivateKey,
175*e0c4386eSCy Schubert       (PEM_write_bio_of_void_unprotected *)PEM_write_bio_RSAPublicKey,
176*e0c4386eSCy Schubert       NULL,                      /* No PEM_write_bio_RSAparams */
177*e0c4386eSCy Schubert       (PEM_write_bio_of_void_unprotected *)PEM_write_bio_RSA_PUBKEY,
178*e0c4386eSCy Schubert       (d2i_of_void *)d2i_RSAPrivateKey,
179*e0c4386eSCy Schubert       (d2i_of_void *)d2i_RSAPublicKey,
180*e0c4386eSCy Schubert       NULL,                      /* No d2i_RSAparams */
181*e0c4386eSCy Schubert       (d2i_of_void *)d2i_RSA_PUBKEY,
182*e0c4386eSCy Schubert       (PEM_read_bio_of_void *)PEM_read_bio_RSAPrivateKey,
183*e0c4386eSCy Schubert       (PEM_read_bio_of_void *)PEM_read_bio_RSAPublicKey,
184*e0c4386eSCy Schubert       NULL,                      /* No PEM_read_bio_RSAparams */
185*e0c4386eSCy Schubert       (PEM_read_bio_of_void *)PEM_read_bio_RSA_PUBKEY }
186*e0c4386eSCy Schubert };
187*e0c4386eSCy Schubert 
188*e0c4386eSCy Schubert /*
189*e0c4386eSCy Schubert  * Keys that we're going to test with.  We initialize this with the intended
190*e0c4386eSCy Schubert  * key types, and generate the keys themselves on program setup.
191*e0c4386eSCy Schubert  * They must all be downgradable with EVP_PKEY_get0()
192*e0c4386eSCy Schubert  */
193*e0c4386eSCy Schubert 
194*e0c4386eSCy Schubert #ifndef OPENSSL_NO_DH
195*e0c4386eSCy Schubert static const OSSL_PARAM DH_params[] = { OSSL_PARAM_END };
196*e0c4386eSCy Schubert static const OSSL_PARAM DHX_params[] = { OSSL_PARAM_END };
197*e0c4386eSCy Schubert #endif
198*e0c4386eSCy Schubert #ifndef OPENSSL_NO_DSA
199*e0c4386eSCy Schubert static size_t qbits = 160;  /* PVK only tolerates 160 Q bits */
200*e0c4386eSCy Schubert static size_t pbits = 1024; /* With 160 Q bits, we MUST use 1024 P bits */
201*e0c4386eSCy Schubert static const OSSL_PARAM DSA_params[] = {
202*e0c4386eSCy Schubert     OSSL_PARAM_size_t("pbits", &pbits),
203*e0c4386eSCy Schubert     OSSL_PARAM_size_t("qbits", &qbits),
204*e0c4386eSCy Schubert     OSSL_PARAM_END
205*e0c4386eSCy Schubert };
206*e0c4386eSCy Schubert #endif
207*e0c4386eSCy Schubert #ifndef OPENSSL_NO_EC
208*e0c4386eSCy Schubert static char groupname[] = "prime256v1";
209*e0c4386eSCy Schubert static const OSSL_PARAM EC_params[] = {
210*e0c4386eSCy Schubert     OSSL_PARAM_utf8_string("group", groupname, sizeof(groupname) - 1),
211*e0c4386eSCy Schubert     OSSL_PARAM_END
212*e0c4386eSCy Schubert };
213*e0c4386eSCy Schubert #endif
214*e0c4386eSCy Schubert 
215*e0c4386eSCy Schubert static struct key_st {
216*e0c4386eSCy Schubert     const char *keytype;
217*e0c4386eSCy Schubert     int evp_type;
218*e0c4386eSCy Schubert     /* non-NULL if a template EVP_PKEY must be generated first */
219*e0c4386eSCy Schubert     const OSSL_PARAM *template_params;
220*e0c4386eSCy Schubert 
221*e0c4386eSCy Schubert     EVP_PKEY *key;
222*e0c4386eSCy Schubert } keys[] = {
223*e0c4386eSCy Schubert #ifndef OPENSSL_NO_DH
224*e0c4386eSCy Schubert     { "DH", EVP_PKEY_DH, DH_params, NULL },
225*e0c4386eSCy Schubert     { "DHX", EVP_PKEY_DHX, DHX_params, NULL },
226*e0c4386eSCy Schubert #endif
227*e0c4386eSCy Schubert #ifndef OPENSSL_NO_DSA
228*e0c4386eSCy Schubert     { "DSA", EVP_PKEY_DSA, DSA_params, NULL },
229*e0c4386eSCy Schubert #endif
230*e0c4386eSCy Schubert #ifndef OPENSSL_NO_EC
231*e0c4386eSCy Schubert     { "EC", EVP_PKEY_EC, EC_params, NULL },
232*e0c4386eSCy Schubert #endif
233*e0c4386eSCy Schubert #ifndef OPENSSL_NO_DEPRECATED_3_0
234*e0c4386eSCy Schubert     { "RSA", EVP_PKEY_RSA, NULL, NULL },
235*e0c4386eSCy Schubert #endif
236*e0c4386eSCy Schubert };
237*e0c4386eSCy Schubert 
make_key(const char * type,const OSSL_PARAM * gen_template_params)238*e0c4386eSCy Schubert static EVP_PKEY *make_key(const char *type,
239*e0c4386eSCy Schubert                           const OSSL_PARAM *gen_template_params)
240*e0c4386eSCy Schubert {
241*e0c4386eSCy Schubert     EVP_PKEY *template = NULL;
242*e0c4386eSCy Schubert     EVP_PKEY *pkey = NULL;
243*e0c4386eSCy Schubert     EVP_PKEY_CTX *ctx = NULL;
244*e0c4386eSCy Schubert     OSSL_PARAM *gen_template_params_noconst =
245*e0c4386eSCy Schubert         (OSSL_PARAM *)gen_template_params;
246*e0c4386eSCy Schubert 
247*e0c4386eSCy Schubert     if (gen_template_params != NULL
248*e0c4386eSCy Schubert         && ((ctx = EVP_PKEY_CTX_new_from_name(NULL, type, NULL)) == NULL
249*e0c4386eSCy Schubert             || EVP_PKEY_paramgen_init(ctx) <= 0
250*e0c4386eSCy Schubert             || (gen_template_params[0].key != NULL
251*e0c4386eSCy Schubert                 && EVP_PKEY_CTX_set_params(ctx, gen_template_params_noconst) <= 0)
252*e0c4386eSCy Schubert             || EVP_PKEY_generate(ctx, &template) <= 0))
253*e0c4386eSCy Schubert         goto end;
254*e0c4386eSCy Schubert     EVP_PKEY_CTX_free(ctx);
255*e0c4386eSCy Schubert 
256*e0c4386eSCy Schubert     /*
257*e0c4386eSCy Schubert      * No real need to check the errors other than for the cascade
258*e0c4386eSCy Schubert      * effect.  |pkey| will simply remain NULL if something goes wrong.
259*e0c4386eSCy Schubert      */
260*e0c4386eSCy Schubert     ctx =
261*e0c4386eSCy Schubert         template != NULL
262*e0c4386eSCy Schubert         ? EVP_PKEY_CTX_new(template, NULL)
263*e0c4386eSCy Schubert         : EVP_PKEY_CTX_new_from_name(NULL, type, NULL);
264*e0c4386eSCy Schubert 
265*e0c4386eSCy Schubert     (void)(ctx != NULL
266*e0c4386eSCy Schubert            && EVP_PKEY_keygen_init(ctx) > 0
267*e0c4386eSCy Schubert            && EVP_PKEY_keygen(ctx, &pkey) > 0);
268*e0c4386eSCy Schubert 
269*e0c4386eSCy Schubert  end:
270*e0c4386eSCy Schubert     EVP_PKEY_free(template);
271*e0c4386eSCy Schubert     EVP_PKEY_CTX_free(ctx);
272*e0c4386eSCy Schubert     return pkey;
273*e0c4386eSCy Schubert }
274*e0c4386eSCy Schubert 
lookup_key(const char * type)275*e0c4386eSCy Schubert static struct key_st *lookup_key(const char *type)
276*e0c4386eSCy Schubert {
277*e0c4386eSCy Schubert     size_t i;
278*e0c4386eSCy Schubert 
279*e0c4386eSCy Schubert     for (i = 0; i < OSSL_NELEM(keys); i++) {
280*e0c4386eSCy Schubert         if (strcmp(keys[i].keytype, type) == 0)
281*e0c4386eSCy Schubert             return &keys[i];
282*e0c4386eSCy Schubert     }
283*e0c4386eSCy Schubert     return NULL;
284*e0c4386eSCy Schubert }
285*e0c4386eSCy Schubert 
test_membio_str_eq(BIO * bio_provided,BIO * bio_legacy)286*e0c4386eSCy Schubert static int test_membio_str_eq(BIO *bio_provided, BIO *bio_legacy)
287*e0c4386eSCy Schubert {
288*e0c4386eSCy Schubert     char *str_provided = NULL, *str_legacy = NULL;
289*e0c4386eSCy Schubert     long len_provided = BIO_get_mem_data(bio_provided, &str_provided);
290*e0c4386eSCy Schubert     long len_legacy = BIO_get_mem_data(bio_legacy, &str_legacy);
291*e0c4386eSCy Schubert 
292*e0c4386eSCy Schubert     return TEST_long_ge(len_legacy, 0)
293*e0c4386eSCy Schubert            && TEST_long_ge(len_provided, 0)
294*e0c4386eSCy Schubert            && TEST_strn2_eq(str_provided, len_provided,
295*e0c4386eSCy Schubert                             str_legacy, len_legacy);
296*e0c4386eSCy Schubert }
297*e0c4386eSCy Schubert 
test_protected_PEM(const char * keytype,int evp_type,const void * legacy_key,PEM_write_bio_of_void_protected * pem_write_bio,PEM_read_bio_of_void * pem_read_bio,EVP_PKEY_eq_fn * evp_pkey_eq,EVP_PKEY_print_fn * evp_pkey_print,EVP_PKEY * provided_pkey,int selection,const char * structure)298*e0c4386eSCy Schubert static int test_protected_PEM(const char *keytype, int evp_type,
299*e0c4386eSCy Schubert                               const void *legacy_key,
300*e0c4386eSCy Schubert                               PEM_write_bio_of_void_protected *pem_write_bio,
301*e0c4386eSCy Schubert                               PEM_read_bio_of_void *pem_read_bio,
302*e0c4386eSCy Schubert                               EVP_PKEY_eq_fn *evp_pkey_eq,
303*e0c4386eSCy Schubert                               EVP_PKEY_print_fn *evp_pkey_print,
304*e0c4386eSCy Schubert                               EVP_PKEY *provided_pkey, int selection,
305*e0c4386eSCy Schubert                               const char *structure)
306*e0c4386eSCy Schubert {
307*e0c4386eSCy Schubert     int ok = 0;
308*e0c4386eSCy Schubert     BIO *membio_legacy = NULL;
309*e0c4386eSCy Schubert     BIO *membio_provided = NULL;
310*e0c4386eSCy Schubert     OSSL_ENCODER_CTX *ectx = NULL;
311*e0c4386eSCy Schubert     OSSL_DECODER_CTX *dctx = NULL;
312*e0c4386eSCy Schubert     void *decoded_legacy_key = NULL;
313*e0c4386eSCy Schubert     EVP_PKEY *decoded_legacy_pkey = NULL;
314*e0c4386eSCy Schubert     EVP_PKEY *decoded_provided_pkey = NULL;
315*e0c4386eSCy Schubert 
316*e0c4386eSCy Schubert     /* Set up the BIOs, so we have them */
317*e0c4386eSCy Schubert     if (!TEST_ptr(membio_legacy = BIO_new(BIO_s_mem()))
318*e0c4386eSCy Schubert         || !TEST_ptr(membio_provided = BIO_new(BIO_s_mem())))
319*e0c4386eSCy Schubert         goto end;
320*e0c4386eSCy Schubert 
321*e0c4386eSCy Schubert     if (!TEST_ptr(ectx =
322*e0c4386eSCy Schubert                   OSSL_ENCODER_CTX_new_for_pkey(provided_pkey, selection,
323*e0c4386eSCy Schubert                                                 "PEM", structure,
324*e0c4386eSCy Schubert                                                 NULL))
325*e0c4386eSCy Schubert         || !TEST_true(OSSL_ENCODER_to_bio(ectx, membio_provided))
326*e0c4386eSCy Schubert         || !TEST_true(pem_write_bio(membio_legacy, legacy_key,
327*e0c4386eSCy Schubert                                    NULL, NULL, 0, NULL, NULL))
328*e0c4386eSCy Schubert         || !test_membio_str_eq(membio_provided, membio_legacy))
329*e0c4386eSCy Schubert         goto end;
330*e0c4386eSCy Schubert 
331*e0c4386eSCy Schubert     if (pem_read_bio != NULL) {
332*e0c4386eSCy Schubert         /* Now try decoding the results and compare the resulting keys */
333*e0c4386eSCy Schubert 
334*e0c4386eSCy Schubert         if (!TEST_ptr(decoded_legacy_pkey = EVP_PKEY_new())
335*e0c4386eSCy Schubert             || !TEST_ptr(dctx =
336*e0c4386eSCy Schubert                          OSSL_DECODER_CTX_new_for_pkey(&decoded_provided_pkey,
337*e0c4386eSCy Schubert                                                        "PEM", structure,
338*e0c4386eSCy Schubert                                                        keytype, selection,
339*e0c4386eSCy Schubert                                                        NULL, NULL))
340*e0c4386eSCy Schubert             || !TEST_true(OSSL_DECODER_from_bio(dctx, membio_provided))
341*e0c4386eSCy Schubert             || !TEST_ptr(decoded_legacy_key =
342*e0c4386eSCy Schubert                          pem_read_bio(membio_legacy, NULL, NULL, NULL))
343*e0c4386eSCy Schubert             || !TEST_true(EVP_PKEY_assign(decoded_legacy_pkey, evp_type,
344*e0c4386eSCy Schubert                                           decoded_legacy_key)))
345*e0c4386eSCy Schubert             goto end;
346*e0c4386eSCy Schubert 
347*e0c4386eSCy Schubert         if (!TEST_int_gt(evp_pkey_eq(decoded_provided_pkey,
348*e0c4386eSCy Schubert                                      decoded_legacy_pkey), 0)) {
349*e0c4386eSCy Schubert             TEST_info("decoded_provided_pkey:");
350*e0c4386eSCy Schubert             evp_pkey_print(bio_out, decoded_provided_pkey, 0, NULL);
351*e0c4386eSCy Schubert             TEST_info("decoded_legacy_pkey:");
352*e0c4386eSCy Schubert             evp_pkey_print(bio_out, decoded_legacy_pkey, 0, NULL);
353*e0c4386eSCy Schubert         }
354*e0c4386eSCy Schubert     }
355*e0c4386eSCy Schubert     ok = 1;
356*e0c4386eSCy Schubert  end:
357*e0c4386eSCy Schubert     EVP_PKEY_free(decoded_legacy_pkey);
358*e0c4386eSCy Schubert     EVP_PKEY_free(decoded_provided_pkey);
359*e0c4386eSCy Schubert     OSSL_ENCODER_CTX_free(ectx);
360*e0c4386eSCy Schubert     OSSL_DECODER_CTX_free(dctx);
361*e0c4386eSCy Schubert     BIO_free(membio_provided);
362*e0c4386eSCy Schubert     BIO_free(membio_legacy);
363*e0c4386eSCy Schubert     return ok;
364*e0c4386eSCy Schubert }
365*e0c4386eSCy Schubert 
test_unprotected_PEM(const char * keytype,int evp_type,const void * legacy_key,PEM_write_bio_of_void_unprotected * pem_write_bio,PEM_read_bio_of_void * pem_read_bio,EVP_PKEY_eq_fn * evp_pkey_eq,EVP_PKEY_print_fn * evp_pkey_print,EVP_PKEY * provided_pkey,int selection,const char * structure)366*e0c4386eSCy Schubert static int test_unprotected_PEM(const char *keytype, int evp_type,
367*e0c4386eSCy Schubert                                 const void *legacy_key,
368*e0c4386eSCy Schubert                                 PEM_write_bio_of_void_unprotected *pem_write_bio,
369*e0c4386eSCy Schubert                                 PEM_read_bio_of_void *pem_read_bio,
370*e0c4386eSCy Schubert                                 EVP_PKEY_eq_fn *evp_pkey_eq,
371*e0c4386eSCy Schubert                                 EVP_PKEY_print_fn *evp_pkey_print,
372*e0c4386eSCy Schubert                                 EVP_PKEY *provided_pkey, int selection,
373*e0c4386eSCy Schubert                                 const char *structure)
374*e0c4386eSCy Schubert {
375*e0c4386eSCy Schubert     int ok = 0;
376*e0c4386eSCy Schubert     BIO *membio_legacy = NULL;
377*e0c4386eSCy Schubert     BIO *membio_provided = NULL;
378*e0c4386eSCy Schubert     OSSL_ENCODER_CTX *ectx = NULL;
379*e0c4386eSCy Schubert     OSSL_DECODER_CTX *dctx = NULL;
380*e0c4386eSCy Schubert     void *decoded_legacy_key = NULL;
381*e0c4386eSCy Schubert     EVP_PKEY *decoded_legacy_pkey = NULL;
382*e0c4386eSCy Schubert     EVP_PKEY *decoded_provided_pkey = NULL;
383*e0c4386eSCy Schubert 
384*e0c4386eSCy Schubert     /* Set up the BIOs, so we have them */
385*e0c4386eSCy Schubert     if (!TEST_ptr(membio_legacy = BIO_new(BIO_s_mem()))
386*e0c4386eSCy Schubert         || !TEST_ptr(membio_provided = BIO_new(BIO_s_mem())))
387*e0c4386eSCy Schubert         goto end;
388*e0c4386eSCy Schubert 
389*e0c4386eSCy Schubert     if (!TEST_ptr(ectx =
390*e0c4386eSCy Schubert                   OSSL_ENCODER_CTX_new_for_pkey(provided_pkey, selection,
391*e0c4386eSCy Schubert                                                 "PEM", structure,
392*e0c4386eSCy Schubert                                                 NULL))
393*e0c4386eSCy Schubert         || !TEST_true(OSSL_ENCODER_to_bio(ectx, membio_provided))
394*e0c4386eSCy Schubert         || !TEST_true(pem_write_bio(membio_legacy, legacy_key))
395*e0c4386eSCy Schubert         || !test_membio_str_eq(membio_provided, membio_legacy))
396*e0c4386eSCy Schubert         goto end;
397*e0c4386eSCy Schubert 
398*e0c4386eSCy Schubert     if (pem_read_bio != NULL) {
399*e0c4386eSCy Schubert         /* Now try decoding the results and compare the resulting keys */
400*e0c4386eSCy Schubert 
401*e0c4386eSCy Schubert         if (!TEST_ptr(decoded_legacy_pkey = EVP_PKEY_new())
402*e0c4386eSCy Schubert             || !TEST_ptr(dctx =
403*e0c4386eSCy Schubert                          OSSL_DECODER_CTX_new_for_pkey(&decoded_provided_pkey,
404*e0c4386eSCy Schubert                                                        "PEM", structure,
405*e0c4386eSCy Schubert                                                        keytype, selection,
406*e0c4386eSCy Schubert                                                        NULL, NULL))
407*e0c4386eSCy Schubert             || !TEST_true(OSSL_DECODER_from_bio(dctx, membio_provided))
408*e0c4386eSCy Schubert             || !TEST_ptr(decoded_legacy_key =
409*e0c4386eSCy Schubert                          pem_read_bio(membio_legacy, NULL, NULL, NULL))
410*e0c4386eSCy Schubert             || !TEST_true(EVP_PKEY_assign(decoded_legacy_pkey, evp_type,
411*e0c4386eSCy Schubert                                           decoded_legacy_key)))
412*e0c4386eSCy Schubert             goto end;
413*e0c4386eSCy Schubert 
414*e0c4386eSCy Schubert         if (!TEST_int_gt(evp_pkey_eq(decoded_provided_pkey,
415*e0c4386eSCy Schubert                                      decoded_legacy_pkey), 0)) {
416*e0c4386eSCy Schubert             TEST_info("decoded_provided_pkey:");
417*e0c4386eSCy Schubert             evp_pkey_print(bio_out, decoded_provided_pkey, 0, NULL);
418*e0c4386eSCy Schubert             TEST_info("decoded_legacy_pkey:");
419*e0c4386eSCy Schubert             evp_pkey_print(bio_out, decoded_legacy_pkey, 0, NULL);
420*e0c4386eSCy Schubert         }
421*e0c4386eSCy Schubert     }
422*e0c4386eSCy Schubert     ok = 1;
423*e0c4386eSCy Schubert  end:
424*e0c4386eSCy Schubert     EVP_PKEY_free(decoded_legacy_pkey);
425*e0c4386eSCy Schubert     EVP_PKEY_free(decoded_provided_pkey);
426*e0c4386eSCy Schubert     OSSL_ENCODER_CTX_free(ectx);
427*e0c4386eSCy Schubert     OSSL_DECODER_CTX_free(dctx);
428*e0c4386eSCy Schubert     BIO_free(membio_provided);
429*e0c4386eSCy Schubert     BIO_free(membio_legacy);
430*e0c4386eSCy Schubert     return ok;
431*e0c4386eSCy Schubert }
432*e0c4386eSCy Schubert 
test_DER(const char * keytype,int evp_type,const void * legacy_key,i2d_of_void * i2d,d2i_of_void * d2i,EVP_PKEY_eq_fn * evp_pkey_eq,EVP_PKEY_print_fn * evp_pkey_print,EVP_PKEY * provided_pkey,int selection,const char * structure)433*e0c4386eSCy Schubert static int test_DER(const char *keytype, int evp_type,
434*e0c4386eSCy Schubert                     const void *legacy_key, i2d_of_void *i2d, d2i_of_void *d2i,
435*e0c4386eSCy Schubert                     EVP_PKEY_eq_fn *evp_pkey_eq,
436*e0c4386eSCy Schubert                     EVP_PKEY_print_fn *evp_pkey_print,
437*e0c4386eSCy Schubert                     EVP_PKEY *provided_pkey, int selection,
438*e0c4386eSCy Schubert                     const char *structure)
439*e0c4386eSCy Schubert {
440*e0c4386eSCy Schubert     int ok = 0;
441*e0c4386eSCy Schubert     unsigned char *der_legacy = NULL;
442*e0c4386eSCy Schubert     const unsigned char *pder_legacy = NULL;
443*e0c4386eSCy Schubert     size_t der_legacy_len = 0;
444*e0c4386eSCy Schubert     unsigned char *der_provided = NULL;
445*e0c4386eSCy Schubert     const unsigned char *pder_provided = NULL;
446*e0c4386eSCy Schubert     size_t der_provided_len = 0;
447*e0c4386eSCy Schubert     size_t tmp_size;
448*e0c4386eSCy Schubert     OSSL_ENCODER_CTX *ectx = NULL;
449*e0c4386eSCy Schubert     OSSL_DECODER_CTX *dctx = NULL;
450*e0c4386eSCy Schubert     void *decoded_legacy_key = NULL;
451*e0c4386eSCy Schubert     EVP_PKEY *decoded_legacy_pkey = NULL;
452*e0c4386eSCy Schubert     EVP_PKEY *decoded_provided_pkey = NULL;
453*e0c4386eSCy Schubert 
454*e0c4386eSCy Schubert     if (!TEST_ptr(ectx =
455*e0c4386eSCy Schubert                  OSSL_ENCODER_CTX_new_for_pkey(provided_pkey, selection,
456*e0c4386eSCy Schubert                                                "DER", structure,
457*e0c4386eSCy Schubert                                                NULL))
458*e0c4386eSCy Schubert         || !TEST_true(OSSL_ENCODER_to_data(ectx,
459*e0c4386eSCy Schubert                                           &der_provided, &der_provided_len))
460*e0c4386eSCy Schubert         || !TEST_size_t_gt(der_legacy_len = i2d(legacy_key, &der_legacy), 0)
461*e0c4386eSCy Schubert         || !TEST_mem_eq(der_provided, der_provided_len,
462*e0c4386eSCy Schubert                         der_legacy, der_legacy_len))
463*e0c4386eSCy Schubert         goto end;
464*e0c4386eSCy Schubert 
465*e0c4386eSCy Schubert     if (d2i != NULL) {
466*e0c4386eSCy Schubert         /* Now try decoding the results and compare the resulting keys */
467*e0c4386eSCy Schubert 
468*e0c4386eSCy Schubert         if (!TEST_ptr(decoded_legacy_pkey = EVP_PKEY_new())
469*e0c4386eSCy Schubert             || !TEST_ptr(dctx =
470*e0c4386eSCy Schubert                          OSSL_DECODER_CTX_new_for_pkey(&decoded_provided_pkey,
471*e0c4386eSCy Schubert                                                        "DER", structure,
472*e0c4386eSCy Schubert                                                        keytype, selection,
473*e0c4386eSCy Schubert                                                        NULL, NULL))
474*e0c4386eSCy Schubert             || !TEST_true((pder_provided = der_provided,
475*e0c4386eSCy Schubert                            tmp_size = der_provided_len,
476*e0c4386eSCy Schubert                            OSSL_DECODER_from_data(dctx, &pder_provided,
477*e0c4386eSCy Schubert                                                   &tmp_size)))
478*e0c4386eSCy Schubert             || !TEST_ptr((pder_legacy = der_legacy,
479*e0c4386eSCy Schubert                           decoded_legacy_key = d2i(NULL, &pder_legacy,
480*e0c4386eSCy Schubert                                                    (long)der_legacy_len)))
481*e0c4386eSCy Schubert             || !TEST_true(EVP_PKEY_assign(decoded_legacy_pkey, evp_type,
482*e0c4386eSCy Schubert                                           decoded_legacy_key)))
483*e0c4386eSCy Schubert             goto end;
484*e0c4386eSCy Schubert 
485*e0c4386eSCy Schubert         if (!TEST_int_gt(evp_pkey_eq(decoded_provided_pkey,
486*e0c4386eSCy Schubert                                      decoded_legacy_pkey), 0)) {
487*e0c4386eSCy Schubert             TEST_info("decoded_provided_pkey:");
488*e0c4386eSCy Schubert             evp_pkey_print(bio_out, decoded_provided_pkey, 0, NULL);
489*e0c4386eSCy Schubert             TEST_info("decoded_legacy_pkey:");
490*e0c4386eSCy Schubert             evp_pkey_print(bio_out, decoded_legacy_pkey, 0, NULL);
491*e0c4386eSCy Schubert         }
492*e0c4386eSCy Schubert     }
493*e0c4386eSCy Schubert     ok = 1;
494*e0c4386eSCy Schubert  end:
495*e0c4386eSCy Schubert     EVP_PKEY_free(decoded_legacy_pkey);
496*e0c4386eSCy Schubert     EVP_PKEY_free(decoded_provided_pkey);
497*e0c4386eSCy Schubert     OSSL_ENCODER_CTX_free(ectx);
498*e0c4386eSCy Schubert     OSSL_DECODER_CTX_free(dctx);
499*e0c4386eSCy Schubert     OPENSSL_free(der_provided);
500*e0c4386eSCy Schubert     OPENSSL_free(der_legacy);
501*e0c4386eSCy Schubert     return ok;
502*e0c4386eSCy Schubert }
503*e0c4386eSCy Schubert 
test_key(int idx)504*e0c4386eSCy Schubert static int test_key(int idx)
505*e0c4386eSCy Schubert {
506*e0c4386eSCy Schubert     struct test_stanza_st *test_stanza = NULL;
507*e0c4386eSCy Schubert     struct key_st *key = NULL;
508*e0c4386eSCy Schubert     int ok = 0;
509*e0c4386eSCy Schubert     size_t i;
510*e0c4386eSCy Schubert     EVP_PKEY *pkey = NULL, *downgraded_pkey = NULL;
511*e0c4386eSCy Schubert     const void *legacy_obj = NULL;
512*e0c4386eSCy Schubert 
513*e0c4386eSCy Schubert     /* Get the test data */
514*e0c4386eSCy Schubert     if (!TEST_ptr(test_stanza = &test_stanzas[idx])
515*e0c4386eSCy Schubert         || !TEST_ptr(key = lookup_key(test_stanza->keytype)))
516*e0c4386eSCy Schubert         goto end;
517*e0c4386eSCy Schubert 
518*e0c4386eSCy Schubert     /* Set up the keys */
519*e0c4386eSCy Schubert     if (!TEST_ptr(pkey = key->key)
520*e0c4386eSCy Schubert         || !TEST_true(evp_pkey_copy_downgraded(&downgraded_pkey, pkey))
521*e0c4386eSCy Schubert         || !TEST_ptr(downgraded_pkey)
522*e0c4386eSCy Schubert         || !TEST_int_eq(EVP_PKEY_get_id(downgraded_pkey), key->evp_type)
523*e0c4386eSCy Schubert         || !TEST_ptr(legacy_obj = EVP_PKEY_get0(downgraded_pkey)))
524*e0c4386eSCy Schubert         goto end;
525*e0c4386eSCy Schubert 
526*e0c4386eSCy Schubert     ok = 1;
527*e0c4386eSCy Schubert 
528*e0c4386eSCy Schubert     /* Test PrivateKey to PEM */
529*e0c4386eSCy Schubert     if (test_stanza->pem_write_bio_PrivateKey != NULL) {
530*e0c4386eSCy Schubert         int selection = OSSL_KEYMGMT_SELECT_ALL;
531*e0c4386eSCy Schubert 
532*e0c4386eSCy Schubert         for (i = 0; i < OSSL_NELEM(test_stanza->structure); i++) {
533*e0c4386eSCy Schubert             const char *structure = test_stanza->structure[i];
534*e0c4386eSCy Schubert 
535*e0c4386eSCy Schubert             TEST_info("Test OSSL_ENCODER against PEM_write_bio_{TYPE}PrivateKey for %s, %s",
536*e0c4386eSCy Schubert                       test_stanza->keytype, structure);
537*e0c4386eSCy Schubert             if (!test_protected_PEM(key->keytype, key->evp_type, legacy_obj,
538*e0c4386eSCy Schubert                                     test_stanza->pem_write_bio_PrivateKey,
539*e0c4386eSCy Schubert                                     test_stanza->pem_read_bio_PrivateKey,
540*e0c4386eSCy Schubert                                     EVP_PKEY_eq, EVP_PKEY_print_private,
541*e0c4386eSCy Schubert                                     pkey, selection, structure))
542*e0c4386eSCy Schubert                 ok = 0;
543*e0c4386eSCy Schubert         }
544*e0c4386eSCy Schubert     }
545*e0c4386eSCy Schubert 
546*e0c4386eSCy Schubert     /* Test PublicKey to PEM */
547*e0c4386eSCy Schubert     if (test_stanza->pem_write_bio_PublicKey != NULL) {
548*e0c4386eSCy Schubert         int selection =
549*e0c4386eSCy Schubert             OSSL_KEYMGMT_SELECT_PUBLIC_KEY
550*e0c4386eSCy Schubert             | OSSL_KEYMGMT_SELECT_ALL_PARAMETERS;
551*e0c4386eSCy Schubert 
552*e0c4386eSCy Schubert         for (i = 0; i < OSSL_NELEM(test_stanza->structure); i++) {
553*e0c4386eSCy Schubert             const char *structure = test_stanza->structure[i];
554*e0c4386eSCy Schubert 
555*e0c4386eSCy Schubert             TEST_info("Test OSSL_ENCODER against PEM_write_bio_{TYPE}PublicKey for %s, %s",
556*e0c4386eSCy Schubert                       test_stanza->keytype, structure);
557*e0c4386eSCy Schubert             if (!test_unprotected_PEM(key->keytype, key->evp_type, legacy_obj,
558*e0c4386eSCy Schubert                                       test_stanza->pem_write_bio_PublicKey,
559*e0c4386eSCy Schubert                                       test_stanza->pem_read_bio_PublicKey,
560*e0c4386eSCy Schubert                                       EVP_PKEY_eq, EVP_PKEY_print_public,
561*e0c4386eSCy Schubert                                       pkey, selection, structure))
562*e0c4386eSCy Schubert                 ok = 0;
563*e0c4386eSCy Schubert         }
564*e0c4386eSCy Schubert     }
565*e0c4386eSCy Schubert 
566*e0c4386eSCy Schubert     /* Test params to PEM */
567*e0c4386eSCy Schubert     if (test_stanza->pem_write_bio_params != NULL) {
568*e0c4386eSCy Schubert         int selection = OSSL_KEYMGMT_SELECT_ALL_PARAMETERS;
569*e0c4386eSCy Schubert 
570*e0c4386eSCy Schubert         for (i = 0; i < OSSL_NELEM(test_stanza->structure); i++) {
571*e0c4386eSCy Schubert             const char *structure = test_stanza->structure[i];
572*e0c4386eSCy Schubert 
573*e0c4386eSCy Schubert             TEST_info("Test OSSL_ENCODER against PEM_write_bio_{TYPE}params for %s, %s",
574*e0c4386eSCy Schubert                       test_stanza->keytype, structure);
575*e0c4386eSCy Schubert             if (!test_unprotected_PEM(key->keytype, key->evp_type, legacy_obj,
576*e0c4386eSCy Schubert                                       test_stanza->pem_write_bio_params,
577*e0c4386eSCy Schubert                                       test_stanza->pem_read_bio_params,
578*e0c4386eSCy Schubert                                       EVP_PKEY_parameters_eq,
579*e0c4386eSCy Schubert                                       EVP_PKEY_print_params,
580*e0c4386eSCy Schubert                                       pkey, selection, structure))
581*e0c4386eSCy Schubert                 ok = 0;
582*e0c4386eSCy Schubert         }
583*e0c4386eSCy Schubert     }
584*e0c4386eSCy Schubert 
585*e0c4386eSCy Schubert     /* Test PUBKEY to PEM */
586*e0c4386eSCy Schubert     if (test_stanza->pem_write_bio_PUBKEY != NULL) {
587*e0c4386eSCy Schubert         int selection =
588*e0c4386eSCy Schubert             OSSL_KEYMGMT_SELECT_PUBLIC_KEY
589*e0c4386eSCy Schubert             | OSSL_KEYMGMT_SELECT_ALL_PARAMETERS;
590*e0c4386eSCy Schubert         const char *structure = "SubjectPublicKeyInfo";
591*e0c4386eSCy Schubert 
592*e0c4386eSCy Schubert         TEST_info("Test OSSL_ENCODER against PEM_write_bio_{TYPE}_PUBKEY for %s, %s",
593*e0c4386eSCy Schubert                   test_stanza->keytype, structure);
594*e0c4386eSCy Schubert         if (!test_unprotected_PEM(key->keytype, key->evp_type, legacy_obj,
595*e0c4386eSCy Schubert                                   test_stanza->pem_write_bio_PUBKEY,
596*e0c4386eSCy Schubert                                   test_stanza->pem_read_bio_PUBKEY,
597*e0c4386eSCy Schubert                                   EVP_PKEY_eq, EVP_PKEY_print_public,
598*e0c4386eSCy Schubert                                   pkey, selection, structure))
599*e0c4386eSCy Schubert             ok = 0;
600*e0c4386eSCy Schubert     }
601*e0c4386eSCy Schubert 
602*e0c4386eSCy Schubert 
603*e0c4386eSCy Schubert     /* Test PrivateKey to DER */
604*e0c4386eSCy Schubert     if (test_stanza->i2d_PrivateKey != NULL) {
605*e0c4386eSCy Schubert         int selection = OSSL_KEYMGMT_SELECT_ALL;
606*e0c4386eSCy Schubert 
607*e0c4386eSCy Schubert         for (i = 0; i < OSSL_NELEM(test_stanza->structure); i++) {
608*e0c4386eSCy Schubert             const char *structure = test_stanza->structure[i];
609*e0c4386eSCy Schubert 
610*e0c4386eSCy Schubert             TEST_info("Test OSSL_ENCODER against i2d_{TYPE}PrivateKey for %s, %s",
611*e0c4386eSCy Schubert                       test_stanza->keytype, structure);
612*e0c4386eSCy Schubert             if (!test_DER(key->keytype, key->evp_type, legacy_obj,
613*e0c4386eSCy Schubert                           test_stanza->i2d_PrivateKey,
614*e0c4386eSCy Schubert                           test_stanza->d2i_PrivateKey,
615*e0c4386eSCy Schubert                           EVP_PKEY_eq, EVP_PKEY_print_private,
616*e0c4386eSCy Schubert                           pkey, selection, structure))
617*e0c4386eSCy Schubert                 ok = 0;
618*e0c4386eSCy Schubert         }
619*e0c4386eSCy Schubert     }
620*e0c4386eSCy Schubert 
621*e0c4386eSCy Schubert     /* Test PublicKey to DER */
622*e0c4386eSCy Schubert     if (test_stanza->i2d_PublicKey != NULL) {
623*e0c4386eSCy Schubert         int selection =
624*e0c4386eSCy Schubert             OSSL_KEYMGMT_SELECT_PUBLIC_KEY
625*e0c4386eSCy Schubert             | OSSL_KEYMGMT_SELECT_ALL_PARAMETERS;
626*e0c4386eSCy Schubert 
627*e0c4386eSCy Schubert         for (i = 0; i < OSSL_NELEM(test_stanza->structure); i++) {
628*e0c4386eSCy Schubert             const char *structure = test_stanza->structure[i];
629*e0c4386eSCy Schubert 
630*e0c4386eSCy Schubert             TEST_info("Test OSSL_ENCODER against i2d_{TYPE}PublicKey for %s, %s",
631*e0c4386eSCy Schubert                       test_stanza->keytype, structure);
632*e0c4386eSCy Schubert             if (!test_DER(key->keytype, key->evp_type, legacy_obj,
633*e0c4386eSCy Schubert                           test_stanza->i2d_PublicKey,
634*e0c4386eSCy Schubert                           test_stanza->d2i_PublicKey,
635*e0c4386eSCy Schubert                           EVP_PKEY_eq, EVP_PKEY_print_public,
636*e0c4386eSCy Schubert                           pkey, selection, structure))
637*e0c4386eSCy Schubert                 ok = 0;
638*e0c4386eSCy Schubert         }
639*e0c4386eSCy Schubert     }
640*e0c4386eSCy Schubert 
641*e0c4386eSCy Schubert     /* Test params to DER */
642*e0c4386eSCy Schubert     if (test_stanza->i2d_params != NULL) {
643*e0c4386eSCy Schubert         int selection = OSSL_KEYMGMT_SELECT_ALL_PARAMETERS;
644*e0c4386eSCy Schubert 
645*e0c4386eSCy Schubert         for (i = 0; i < OSSL_NELEM(test_stanza->structure); i++) {
646*e0c4386eSCy Schubert             const char *structure = test_stanza->structure[i];
647*e0c4386eSCy Schubert 
648*e0c4386eSCy Schubert             TEST_info("Test OSSL_ENCODER against i2d_{TYPE}params for %s, %s",
649*e0c4386eSCy Schubert                       test_stanza->keytype, structure);
650*e0c4386eSCy Schubert             if (!test_DER(key->keytype, key->evp_type, legacy_obj,
651*e0c4386eSCy Schubert                           test_stanza->i2d_params, test_stanza->d2i_params,
652*e0c4386eSCy Schubert                           EVP_PKEY_parameters_eq, EVP_PKEY_print_params,
653*e0c4386eSCy Schubert                           pkey, selection, structure))
654*e0c4386eSCy Schubert                 ok = 0;
655*e0c4386eSCy Schubert         }
656*e0c4386eSCy Schubert     }
657*e0c4386eSCy Schubert 
658*e0c4386eSCy Schubert     /* Test PUBKEY to DER */
659*e0c4386eSCy Schubert     if (test_stanza->i2d_PUBKEY != NULL) {
660*e0c4386eSCy Schubert         int selection =
661*e0c4386eSCy Schubert             OSSL_KEYMGMT_SELECT_PUBLIC_KEY
662*e0c4386eSCy Schubert             | OSSL_KEYMGMT_SELECT_ALL_PARAMETERS;
663*e0c4386eSCy Schubert         const char *structure = "SubjectPublicKeyInfo";
664*e0c4386eSCy Schubert 
665*e0c4386eSCy Schubert         TEST_info("Test OSSL_ENCODER against i2d_{TYPE}_PUBKEY for %s, %s",
666*e0c4386eSCy Schubert                   test_stanza->keytype, structure);
667*e0c4386eSCy Schubert         if (!test_DER(key->keytype, key->evp_type, legacy_obj,
668*e0c4386eSCy Schubert                       test_stanza->i2d_PUBKEY, test_stanza->d2i_PUBKEY,
669*e0c4386eSCy Schubert                       EVP_PKEY_eq, EVP_PKEY_print_public,
670*e0c4386eSCy Schubert                       pkey, selection, structure))
671*e0c4386eSCy Schubert             ok = 0;
672*e0c4386eSCy Schubert     }
673*e0c4386eSCy Schubert  end:
674*e0c4386eSCy Schubert     EVP_PKEY_free(downgraded_pkey);
675*e0c4386eSCy Schubert     return ok;
676*e0c4386eSCy Schubert }
677*e0c4386eSCy Schubert 
678*e0c4386eSCy Schubert #define USAGE "rsa-key.pem dh-key.pem\n"
OPT_TEST_DECLARE_USAGE(USAGE)679*e0c4386eSCy Schubert OPT_TEST_DECLARE_USAGE(USAGE)
680*e0c4386eSCy Schubert 
681*e0c4386eSCy Schubert int setup_tests(void)
682*e0c4386eSCy Schubert {
683*e0c4386eSCy Schubert     size_t i;
684*e0c4386eSCy Schubert 
685*e0c4386eSCy Schubert     if (!test_skip_common_options()) {
686*e0c4386eSCy Schubert         TEST_error("Error parsing test options\n");
687*e0c4386eSCy Schubert         return 0;
688*e0c4386eSCy Schubert     }
689*e0c4386eSCy Schubert     if (test_get_argument_count() != 2) {
690*e0c4386eSCy Schubert         TEST_error("usage: endecoder_legacy_test %s", USAGE);
691*e0c4386eSCy Schubert         return 0;
692*e0c4386eSCy Schubert     }
693*e0c4386eSCy Schubert 
694*e0c4386eSCy Schubert     TEST_info("Generating keys...");
695*e0c4386eSCy Schubert 
696*e0c4386eSCy Schubert     for (i = 0; i < OSSL_NELEM(keys); i++) {
697*e0c4386eSCy Schubert #ifndef OPENSSL_NO_DH
698*e0c4386eSCy Schubert         if (strcmp(keys[i].keytype, "DH") == 0) {
699*e0c4386eSCy Schubert             if (!TEST_ptr(keys[i].key =
700*e0c4386eSCy Schubert                           load_pkey_pem(test_get_argument(1), NULL)))
701*e0c4386eSCy Schubert                 return  0;
702*e0c4386eSCy Schubert             continue;
703*e0c4386eSCy Schubert         }
704*e0c4386eSCy Schubert #endif
705*e0c4386eSCy Schubert #ifndef OPENSSL_NO_DEPRECATED_3_0
706*e0c4386eSCy Schubert         if (strcmp(keys[i].keytype, "RSA") == 0) {
707*e0c4386eSCy Schubert             if (!TEST_ptr(keys[i].key =
708*e0c4386eSCy Schubert                           load_pkey_pem(test_get_argument(0), NULL)))
709*e0c4386eSCy Schubert                 return  0;
710*e0c4386eSCy Schubert             continue;
711*e0c4386eSCy Schubert         }
712*e0c4386eSCy Schubert #endif
713*e0c4386eSCy Schubert         TEST_info("Generating %s key...", keys[i].keytype);
714*e0c4386eSCy Schubert         if (!TEST_ptr(keys[i].key =
715*e0c4386eSCy Schubert                       make_key(keys[i].keytype, keys[i].template_params)))
716*e0c4386eSCy Schubert             return 0;
717*e0c4386eSCy Schubert     }
718*e0c4386eSCy Schubert 
719*e0c4386eSCy Schubert     TEST_info("Generating keys done");
720*e0c4386eSCy Schubert 
721*e0c4386eSCy Schubert     ADD_ALL_TESTS(test_key, OSSL_NELEM(test_stanzas));
722*e0c4386eSCy Schubert     return 1;
723*e0c4386eSCy Schubert }
724*e0c4386eSCy Schubert 
cleanup_tests(void)725*e0c4386eSCy Schubert void cleanup_tests(void)
726*e0c4386eSCy Schubert {
727*e0c4386eSCy Schubert     size_t i;
728*e0c4386eSCy Schubert 
729*e0c4386eSCy Schubert     for (i = 0; i < OSSL_NELEM(keys); i++)
730*e0c4386eSCy Schubert         EVP_PKEY_free(keys[i].key);
731*e0c4386eSCy Schubert }
732