xref: /freebsd/crypto/openssl/test/enginetest.c (revision e0c4386e)
1*e0c4386eSCy Schubert /*
2*e0c4386eSCy Schubert  * Copyright 2000-2022 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 /* We need to use some deprecated APIs */
11*e0c4386eSCy Schubert #define OPENSSL_SUPPRESS_DEPRECATED
12*e0c4386eSCy Schubert 
13*e0c4386eSCy Schubert #include <stdio.h>
14*e0c4386eSCy Schubert #include <string.h>
15*e0c4386eSCy Schubert #include <stdlib.h>
16*e0c4386eSCy Schubert #include <openssl/e_os2.h>
17*e0c4386eSCy Schubert 
18*e0c4386eSCy Schubert # include "testutil.h"
19*e0c4386eSCy Schubert 
20*e0c4386eSCy Schubert #ifndef OPENSSL_NO_ENGINE
21*e0c4386eSCy Schubert # include <openssl/buffer.h>
22*e0c4386eSCy Schubert # include <openssl/crypto.h>
23*e0c4386eSCy Schubert # include <openssl/engine.h>
24*e0c4386eSCy Schubert # include <openssl/rsa.h>
25*e0c4386eSCy Schubert # include <openssl/err.h>
26*e0c4386eSCy Schubert # include <openssl/x509.h>
27*e0c4386eSCy Schubert # include <openssl/pem.h>
28*e0c4386eSCy Schubert 
display_engine_list(void)29*e0c4386eSCy Schubert static void display_engine_list(void)
30*e0c4386eSCy Schubert {
31*e0c4386eSCy Schubert     ENGINE *h;
32*e0c4386eSCy Schubert     int loop;
33*e0c4386eSCy Schubert 
34*e0c4386eSCy Schubert     loop = 0;
35*e0c4386eSCy Schubert     for (h = ENGINE_get_first(); h != NULL; h = ENGINE_get_next(h)) {
36*e0c4386eSCy Schubert         TEST_info("#%d: id = \"%s\", name = \"%s\"",
37*e0c4386eSCy Schubert                loop++, ENGINE_get_id(h), ENGINE_get_name(h));
38*e0c4386eSCy Schubert     }
39*e0c4386eSCy Schubert 
40*e0c4386eSCy Schubert     /*
41*e0c4386eSCy Schubert      * ENGINE_get_first() increases the struct_ref counter, so we must call
42*e0c4386eSCy Schubert      * ENGINE_free() to decrease it again
43*e0c4386eSCy Schubert      */
44*e0c4386eSCy Schubert     ENGINE_free(h);
45*e0c4386eSCy Schubert }
46*e0c4386eSCy Schubert 
47*e0c4386eSCy Schubert #define NUMTOADD 512
48*e0c4386eSCy Schubert 
test_engines(void)49*e0c4386eSCy Schubert static int test_engines(void)
50*e0c4386eSCy Schubert {
51*e0c4386eSCy Schubert     ENGINE *block[NUMTOADD];
52*e0c4386eSCy Schubert     char *eid[NUMTOADD];
53*e0c4386eSCy Schubert     char *ename[NUMTOADD];
54*e0c4386eSCy Schubert     char buf[256];
55*e0c4386eSCy Schubert     ENGINE *ptr;
56*e0c4386eSCy Schubert     int loop;
57*e0c4386eSCy Schubert     int to_return = 0;
58*e0c4386eSCy Schubert     ENGINE *new_h1 = NULL;
59*e0c4386eSCy Schubert     ENGINE *new_h2 = NULL;
60*e0c4386eSCy Schubert     ENGINE *new_h3 = NULL;
61*e0c4386eSCy Schubert     ENGINE *new_h4 = NULL;
62*e0c4386eSCy Schubert 
63*e0c4386eSCy Schubert     memset(block, 0, sizeof(block));
64*e0c4386eSCy Schubert     if (!TEST_ptr(new_h1 = ENGINE_new())
65*e0c4386eSCy Schubert             || !TEST_true(ENGINE_set_id(new_h1, "test_id0"))
66*e0c4386eSCy Schubert             || !TEST_true(ENGINE_set_name(new_h1, "First test item"))
67*e0c4386eSCy Schubert             || !TEST_ptr(new_h2 = ENGINE_new())
68*e0c4386eSCy Schubert             || !TEST_true(ENGINE_set_id(new_h2, "test_id1"))
69*e0c4386eSCy Schubert             || !TEST_true(ENGINE_set_name(new_h2, "Second test item"))
70*e0c4386eSCy Schubert             || !TEST_ptr(new_h3 = ENGINE_new())
71*e0c4386eSCy Schubert             || !TEST_true(ENGINE_set_id(new_h3, "test_id2"))
72*e0c4386eSCy Schubert             || !TEST_true(ENGINE_set_name(new_h3, "Third test item"))
73*e0c4386eSCy Schubert             || !TEST_ptr(new_h4 = ENGINE_new())
74*e0c4386eSCy Schubert             || !TEST_true(ENGINE_set_id(new_h4, "test_id3"))
75*e0c4386eSCy Schubert             || !TEST_true(ENGINE_set_name(new_h4, "Fourth test item")))
76*e0c4386eSCy Schubert         goto end;
77*e0c4386eSCy Schubert     TEST_info("Engines:");
78*e0c4386eSCy Schubert     display_engine_list();
79*e0c4386eSCy Schubert 
80*e0c4386eSCy Schubert     if (!TEST_true(ENGINE_add(new_h1)))
81*e0c4386eSCy Schubert         goto end;
82*e0c4386eSCy Schubert     TEST_info("Engines:");
83*e0c4386eSCy Schubert     display_engine_list();
84*e0c4386eSCy Schubert 
85*e0c4386eSCy Schubert     ptr = ENGINE_get_first();
86*e0c4386eSCy Schubert     if (!TEST_true(ENGINE_remove(ptr)))
87*e0c4386eSCy Schubert         goto end;
88*e0c4386eSCy Schubert     ENGINE_free(ptr);
89*e0c4386eSCy Schubert     TEST_info("Engines:");
90*e0c4386eSCy Schubert     display_engine_list();
91*e0c4386eSCy Schubert 
92*e0c4386eSCy Schubert     if (!TEST_true(ENGINE_add(new_h3))
93*e0c4386eSCy Schubert             || !TEST_true(ENGINE_add(new_h2)))
94*e0c4386eSCy Schubert         goto end;
95*e0c4386eSCy Schubert     TEST_info("Engines:");
96*e0c4386eSCy Schubert     display_engine_list();
97*e0c4386eSCy Schubert 
98*e0c4386eSCy Schubert     if (!TEST_true(ENGINE_remove(new_h2)))
99*e0c4386eSCy Schubert         goto end;
100*e0c4386eSCy Schubert     TEST_info("Engines:");
101*e0c4386eSCy Schubert     display_engine_list();
102*e0c4386eSCy Schubert 
103*e0c4386eSCy Schubert     if (!TEST_true(ENGINE_add(new_h4)))
104*e0c4386eSCy Schubert         goto end;
105*e0c4386eSCy Schubert     TEST_info("Engines:");
106*e0c4386eSCy Schubert     display_engine_list();
107*e0c4386eSCy Schubert 
108*e0c4386eSCy Schubert     /* Should fail. */
109*e0c4386eSCy Schubert     if (!TEST_false(ENGINE_add(new_h3)))
110*e0c4386eSCy Schubert         goto end;
111*e0c4386eSCy Schubert     ERR_clear_error();
112*e0c4386eSCy Schubert 
113*e0c4386eSCy Schubert     /* Should fail. */
114*e0c4386eSCy Schubert     if (!TEST_false(ENGINE_remove(new_h2)))
115*e0c4386eSCy Schubert         goto end;
116*e0c4386eSCy Schubert     ERR_clear_error();
117*e0c4386eSCy Schubert 
118*e0c4386eSCy Schubert     if (!TEST_true(ENGINE_remove(new_h3)))
119*e0c4386eSCy Schubert         goto end;
120*e0c4386eSCy Schubert     TEST_info("Engines:");
121*e0c4386eSCy Schubert     display_engine_list();
122*e0c4386eSCy Schubert 
123*e0c4386eSCy Schubert     if (!TEST_true(ENGINE_remove(new_h4)))
124*e0c4386eSCy Schubert         goto end;
125*e0c4386eSCy Schubert     TEST_info("Engines:");
126*e0c4386eSCy Schubert     display_engine_list();
127*e0c4386eSCy Schubert 
128*e0c4386eSCy Schubert     /*
129*e0c4386eSCy Schubert      * At this point, we should have an empty list, unless some hardware
130*e0c4386eSCy Schubert      * support engine got added.  However, since we don't allow the config
131*e0c4386eSCy Schubert      * file to be loaded and don't otherwise load any built in engines,
132*e0c4386eSCy Schubert      * that is unlikely.  Still, we check, if for nothing else, then to
133*e0c4386eSCy Schubert      * notify that something is a little off (and might mean that |new_h1|
134*e0c4386eSCy Schubert      * wasn't unloaded when it should have)
135*e0c4386eSCy Schubert      */
136*e0c4386eSCy Schubert     if ((ptr = ENGINE_get_first()) != NULL) {
137*e0c4386eSCy Schubert         if (!ENGINE_remove(ptr))
138*e0c4386eSCy Schubert             TEST_info("Remove failed - probably no hardware support present");
139*e0c4386eSCy Schubert     }
140*e0c4386eSCy Schubert     ENGINE_free(ptr);
141*e0c4386eSCy Schubert     TEST_info("Engines:");
142*e0c4386eSCy Schubert     display_engine_list();
143*e0c4386eSCy Schubert 
144*e0c4386eSCy Schubert     if (!TEST_true(ENGINE_add(new_h1))
145*e0c4386eSCy Schubert             || !TEST_true(ENGINE_remove(new_h1)))
146*e0c4386eSCy Schubert         goto end;
147*e0c4386eSCy Schubert 
148*e0c4386eSCy Schubert     TEST_info("About to beef up the engine-type list");
149*e0c4386eSCy Schubert     for (loop = 0; loop < NUMTOADD; loop++) {
150*e0c4386eSCy Schubert         sprintf(buf, "id%d", loop);
151*e0c4386eSCy Schubert         eid[loop] = OPENSSL_strdup(buf);
152*e0c4386eSCy Schubert         sprintf(buf, "Fake engine type %d", loop);
153*e0c4386eSCy Schubert         ename[loop] = OPENSSL_strdup(buf);
154*e0c4386eSCy Schubert         if (!TEST_ptr(block[loop] = ENGINE_new())
155*e0c4386eSCy Schubert                 || !TEST_true(ENGINE_set_id(block[loop], eid[loop]))
156*e0c4386eSCy Schubert                 || !TEST_true(ENGINE_set_name(block[loop], ename[loop])))
157*e0c4386eSCy Schubert             goto end;
158*e0c4386eSCy Schubert     }
159*e0c4386eSCy Schubert     for (loop = 0; loop < NUMTOADD; loop++) {
160*e0c4386eSCy Schubert         if (!TEST_true(ENGINE_add(block[loop]))) {
161*e0c4386eSCy Schubert             test_note("Adding stopped at %d, (%s,%s)",
162*e0c4386eSCy Schubert                       loop, ENGINE_get_id(block[loop]),
163*e0c4386eSCy Schubert                       ENGINE_get_name(block[loop]));
164*e0c4386eSCy Schubert             goto cleanup_loop;
165*e0c4386eSCy Schubert         }
166*e0c4386eSCy Schubert     }
167*e0c4386eSCy Schubert  cleanup_loop:
168*e0c4386eSCy Schubert     TEST_info("About to empty the engine-type list");
169*e0c4386eSCy Schubert     while ((ptr = ENGINE_get_first()) != NULL) {
170*e0c4386eSCy Schubert         if (!TEST_true(ENGINE_remove(ptr)))
171*e0c4386eSCy Schubert             goto end;
172*e0c4386eSCy Schubert         ENGINE_free(ptr);
173*e0c4386eSCy Schubert     }
174*e0c4386eSCy Schubert     for (loop = 0; loop < NUMTOADD; loop++) {
175*e0c4386eSCy Schubert         OPENSSL_free(eid[loop]);
176*e0c4386eSCy Schubert         OPENSSL_free(ename[loop]);
177*e0c4386eSCy Schubert     }
178*e0c4386eSCy Schubert     to_return = 1;
179*e0c4386eSCy Schubert 
180*e0c4386eSCy Schubert  end:
181*e0c4386eSCy Schubert     ENGINE_free(new_h1);
182*e0c4386eSCy Schubert     ENGINE_free(new_h2);
183*e0c4386eSCy Schubert     ENGINE_free(new_h3);
184*e0c4386eSCy Schubert     ENGINE_free(new_h4);
185*e0c4386eSCy Schubert     for (loop = 0; loop < NUMTOADD; loop++)
186*e0c4386eSCy Schubert         ENGINE_free(block[loop]);
187*e0c4386eSCy Schubert     return to_return;
188*e0c4386eSCy Schubert }
189*e0c4386eSCy Schubert 
190*e0c4386eSCy Schubert /* Test EVP_PKEY method */
191*e0c4386eSCy Schubert static EVP_PKEY_METHOD *test_rsa = NULL;
192*e0c4386eSCy Schubert 
193*e0c4386eSCy Schubert static int called_encrypt = 0;
194*e0c4386eSCy Schubert 
195*e0c4386eSCy Schubert /* Test function to check operation has been redirected */
test_encrypt(EVP_PKEY_CTX * ctx,unsigned char * sig,size_t * siglen,const unsigned char * tbs,size_t tbslen)196*e0c4386eSCy Schubert static int test_encrypt(EVP_PKEY_CTX *ctx, unsigned char *sig,
197*e0c4386eSCy Schubert                         size_t *siglen, const unsigned char *tbs, size_t tbslen)
198*e0c4386eSCy Schubert {
199*e0c4386eSCy Schubert     called_encrypt = 1;
200*e0c4386eSCy Schubert     return 1;
201*e0c4386eSCy Schubert }
202*e0c4386eSCy Schubert 
test_pkey_meths(ENGINE * e,EVP_PKEY_METHOD ** pmeth,const int ** pnids,int nid)203*e0c4386eSCy Schubert static int test_pkey_meths(ENGINE *e, EVP_PKEY_METHOD **pmeth,
204*e0c4386eSCy Schubert                            const int **pnids, int nid)
205*e0c4386eSCy Schubert {
206*e0c4386eSCy Schubert     static const int rnid = EVP_PKEY_RSA;
207*e0c4386eSCy Schubert     if (pmeth == NULL) {
208*e0c4386eSCy Schubert         *pnids = &rnid;
209*e0c4386eSCy Schubert         return 1;
210*e0c4386eSCy Schubert     }
211*e0c4386eSCy Schubert 
212*e0c4386eSCy Schubert     if (nid == EVP_PKEY_RSA) {
213*e0c4386eSCy Schubert         *pmeth = test_rsa;
214*e0c4386eSCy Schubert         return 1;
215*e0c4386eSCy Schubert     }
216*e0c4386eSCy Schubert 
217*e0c4386eSCy Schubert     *pmeth = NULL;
218*e0c4386eSCy Schubert     return 0;
219*e0c4386eSCy Schubert }
220*e0c4386eSCy Schubert 
221*e0c4386eSCy Schubert /* Return a test EVP_PKEY value */
222*e0c4386eSCy Schubert 
get_test_pkey(void)223*e0c4386eSCy Schubert static EVP_PKEY *get_test_pkey(void)
224*e0c4386eSCy Schubert {
225*e0c4386eSCy Schubert     static unsigned char n[] =
226*e0c4386eSCy Schubert         "\x00\xAA\x36\xAB\xCE\x88\xAC\xFD\xFF\x55\x52\x3C\x7F\xC4\x52\x3F"
227*e0c4386eSCy Schubert         "\x90\xEF\xA0\x0D\xF3\x77\x4A\x25\x9F\x2E\x62\xB4\xC5\xD9\x9C\xB5"
228*e0c4386eSCy Schubert         "\xAD\xB3\x00\xA0\x28\x5E\x53\x01\x93\x0E\x0C\x70\xFB\x68\x76\x93"
229*e0c4386eSCy Schubert         "\x9C\xE6\x16\xCE\x62\x4A\x11\xE0\x08\x6D\x34\x1E\xBC\xAC\xA0\xA1"
230*e0c4386eSCy Schubert         "\xF5";
231*e0c4386eSCy Schubert     static unsigned char e[] = "\x11";
232*e0c4386eSCy Schubert 
233*e0c4386eSCy Schubert     RSA *rsa = RSA_new();
234*e0c4386eSCy Schubert     EVP_PKEY *pk = EVP_PKEY_new();
235*e0c4386eSCy Schubert 
236*e0c4386eSCy Schubert     if (rsa == NULL || pk == NULL || !EVP_PKEY_assign_RSA(pk, rsa)) {
237*e0c4386eSCy Schubert         RSA_free(rsa);
238*e0c4386eSCy Schubert         EVP_PKEY_free(pk);
239*e0c4386eSCy Schubert         return NULL;
240*e0c4386eSCy Schubert     }
241*e0c4386eSCy Schubert 
242*e0c4386eSCy Schubert     if (!RSA_set0_key(rsa, BN_bin2bn(n, sizeof(n)-1, NULL),
243*e0c4386eSCy Schubert                       BN_bin2bn(e, sizeof(e)-1, NULL), NULL)) {
244*e0c4386eSCy Schubert         EVP_PKEY_free(pk);
245*e0c4386eSCy Schubert         return NULL;
246*e0c4386eSCy Schubert     }
247*e0c4386eSCy Schubert 
248*e0c4386eSCy Schubert     return pk;
249*e0c4386eSCy Schubert }
250*e0c4386eSCy Schubert 
test_redirect(void)251*e0c4386eSCy Schubert static int test_redirect(void)
252*e0c4386eSCy Schubert {
253*e0c4386eSCy Schubert     const unsigned char pt[] = "Hello World\n";
254*e0c4386eSCy Schubert     unsigned char *tmp = NULL;
255*e0c4386eSCy Schubert     size_t len;
256*e0c4386eSCy Schubert     EVP_PKEY_CTX *ctx = NULL;
257*e0c4386eSCy Schubert     ENGINE *e = NULL;
258*e0c4386eSCy Schubert     EVP_PKEY *pkey = NULL;
259*e0c4386eSCy Schubert 
260*e0c4386eSCy Schubert     int to_return = 0;
261*e0c4386eSCy Schubert 
262*e0c4386eSCy Schubert     if (!TEST_ptr(pkey = get_test_pkey()))
263*e0c4386eSCy Schubert         goto err;
264*e0c4386eSCy Schubert 
265*e0c4386eSCy Schubert     len = EVP_PKEY_get_size(pkey);
266*e0c4386eSCy Schubert     if (!TEST_ptr(tmp = OPENSSL_malloc(len)))
267*e0c4386eSCy Schubert         goto err;
268*e0c4386eSCy Schubert 
269*e0c4386eSCy Schubert     if (!TEST_ptr(ctx = EVP_PKEY_CTX_new(pkey, NULL)))
270*e0c4386eSCy Schubert         goto err;
271*e0c4386eSCy Schubert     TEST_info("EVP_PKEY_encrypt test: no redirection");
272*e0c4386eSCy Schubert     /* Encrypt some data: should succeed but not be redirected */
273*e0c4386eSCy Schubert     if (!TEST_int_gt(EVP_PKEY_encrypt_init(ctx), 0)
274*e0c4386eSCy Schubert             || !TEST_int_gt(EVP_PKEY_encrypt(ctx, tmp, &len, pt, sizeof(pt)), 0)
275*e0c4386eSCy Schubert             || !TEST_false(called_encrypt))
276*e0c4386eSCy Schubert         goto err;
277*e0c4386eSCy Schubert     EVP_PKEY_CTX_free(ctx);
278*e0c4386eSCy Schubert     ctx = NULL;
279*e0c4386eSCy Schubert 
280*e0c4386eSCy Schubert     /* Create a test ENGINE */
281*e0c4386eSCy Schubert     if (!TEST_ptr(e = ENGINE_new())
282*e0c4386eSCy Schubert             || !TEST_true(ENGINE_set_id(e, "Test redirect engine"))
283*e0c4386eSCy Schubert             || !TEST_true(ENGINE_set_name(e, "Test redirect engine")))
284*e0c4386eSCy Schubert         goto err;
285*e0c4386eSCy Schubert 
286*e0c4386eSCy Schubert     /*
287*e0c4386eSCy Schubert      * Try to create a context for this engine and test key.
288*e0c4386eSCy Schubert      * Try setting test key engine. Both should fail because the
289*e0c4386eSCy Schubert      * engine has no public key methods.
290*e0c4386eSCy Schubert      */
291*e0c4386eSCy Schubert     if (!TEST_ptr_null(ctx = EVP_PKEY_CTX_new(pkey, e))
292*e0c4386eSCy Schubert             || !TEST_int_le(EVP_PKEY_set1_engine(pkey, e), 0))
293*e0c4386eSCy Schubert         goto err;
294*e0c4386eSCy Schubert 
295*e0c4386eSCy Schubert     /* Setup an empty test EVP_PKEY_METHOD and set callback to return it */
296*e0c4386eSCy Schubert     if (!TEST_ptr(test_rsa = EVP_PKEY_meth_new(EVP_PKEY_RSA, 0)))
297*e0c4386eSCy Schubert         goto err;
298*e0c4386eSCy Schubert     ENGINE_set_pkey_meths(e, test_pkey_meths);
299*e0c4386eSCy Schubert 
300*e0c4386eSCy Schubert     /* Getting a context for test ENGINE should now succeed */
301*e0c4386eSCy Schubert     if (!TEST_ptr(ctx = EVP_PKEY_CTX_new(pkey, e)))
302*e0c4386eSCy Schubert         goto err;
303*e0c4386eSCy Schubert     /* Encrypt should fail because operation is not supported */
304*e0c4386eSCy Schubert     if (!TEST_int_le(EVP_PKEY_encrypt_init(ctx), 0))
305*e0c4386eSCy Schubert         goto err;
306*e0c4386eSCy Schubert     EVP_PKEY_CTX_free(ctx);
307*e0c4386eSCy Schubert     ctx = NULL;
308*e0c4386eSCy Schubert 
309*e0c4386eSCy Schubert     /* Add test encrypt operation to method */
310*e0c4386eSCy Schubert     EVP_PKEY_meth_set_encrypt(test_rsa, 0, test_encrypt);
311*e0c4386eSCy Schubert 
312*e0c4386eSCy Schubert     TEST_info("EVP_PKEY_encrypt test: redirection via EVP_PKEY_CTX_new()");
313*e0c4386eSCy Schubert     if (!TEST_ptr(ctx = EVP_PKEY_CTX_new(pkey, e)))
314*e0c4386eSCy Schubert         goto err;
315*e0c4386eSCy Schubert     /* Encrypt some data: should succeed and be redirected */
316*e0c4386eSCy Schubert     if (!TEST_int_gt(EVP_PKEY_encrypt_init(ctx), 0)
317*e0c4386eSCy Schubert             || !TEST_int_gt(EVP_PKEY_encrypt(ctx, tmp, &len, pt, sizeof(pt)), 0)
318*e0c4386eSCy Schubert             || !TEST_true(called_encrypt))
319*e0c4386eSCy Schubert         goto err;
320*e0c4386eSCy Schubert 
321*e0c4386eSCy Schubert     EVP_PKEY_CTX_free(ctx);
322*e0c4386eSCy Schubert     ctx = NULL;
323*e0c4386eSCy Schubert     called_encrypt = 0;
324*e0c4386eSCy Schubert 
325*e0c4386eSCy Schubert     /* Create context with default engine: should not be redirected */
326*e0c4386eSCy Schubert     if (!TEST_ptr(ctx = EVP_PKEY_CTX_new(pkey, NULL))
327*e0c4386eSCy Schubert             || !TEST_int_gt(EVP_PKEY_encrypt_init(ctx), 0)
328*e0c4386eSCy Schubert             || !TEST_int_gt(EVP_PKEY_encrypt(ctx, tmp, &len, pt, sizeof(pt)), 0)
329*e0c4386eSCy Schubert             || !TEST_false(called_encrypt))
330*e0c4386eSCy Schubert         goto err;
331*e0c4386eSCy Schubert 
332*e0c4386eSCy Schubert     EVP_PKEY_CTX_free(ctx);
333*e0c4386eSCy Schubert     ctx = NULL;
334*e0c4386eSCy Schubert 
335*e0c4386eSCy Schubert     /* Set engine explicitly for test key */
336*e0c4386eSCy Schubert     if (!TEST_true(EVP_PKEY_set1_engine(pkey, e)))
337*e0c4386eSCy Schubert         goto err;
338*e0c4386eSCy Schubert 
339*e0c4386eSCy Schubert     TEST_info("EVP_PKEY_encrypt test: redirection via EVP_PKEY_set1_engine()");
340*e0c4386eSCy Schubert 
341*e0c4386eSCy Schubert     /* Create context with default engine: should be redirected now */
342*e0c4386eSCy Schubert     if (!TEST_ptr(ctx = EVP_PKEY_CTX_new(pkey, NULL))
343*e0c4386eSCy Schubert             || !TEST_int_gt(EVP_PKEY_encrypt_init(ctx), 0)
344*e0c4386eSCy Schubert             || !TEST_int_gt(EVP_PKEY_encrypt(ctx, tmp, &len, pt, sizeof(pt)), 0)
345*e0c4386eSCy Schubert             || !TEST_true(called_encrypt))
346*e0c4386eSCy Schubert         goto err;
347*e0c4386eSCy Schubert 
348*e0c4386eSCy Schubert     to_return = 1;
349*e0c4386eSCy Schubert 
350*e0c4386eSCy Schubert  err:
351*e0c4386eSCy Schubert     EVP_PKEY_CTX_free(ctx);
352*e0c4386eSCy Schubert     EVP_PKEY_free(pkey);
353*e0c4386eSCy Schubert     ENGINE_free(e);
354*e0c4386eSCy Schubert     OPENSSL_free(tmp);
355*e0c4386eSCy Schubert     return to_return;
356*e0c4386eSCy Schubert }
357*e0c4386eSCy Schubert 
test_x509_dup_w_engine(void)358*e0c4386eSCy Schubert static int test_x509_dup_w_engine(void)
359*e0c4386eSCy Schubert {
360*e0c4386eSCy Schubert     ENGINE *e = NULL;
361*e0c4386eSCy Schubert     X509 *cert = NULL, *dupcert = NULL;
362*e0c4386eSCy Schubert     X509_PUBKEY *pubkey, *duppubkey = NULL;
363*e0c4386eSCy Schubert     int ret = 0;
364*e0c4386eSCy Schubert     BIO *b = NULL;
365*e0c4386eSCy Schubert     RSA_METHOD *rsameth = NULL;
366*e0c4386eSCy Schubert 
367*e0c4386eSCy Schubert     if (!TEST_ptr(b = BIO_new_file(test_get_argument(0), "r"))
368*e0c4386eSCy Schubert         || !TEST_ptr(cert = PEM_read_bio_X509(b, NULL, NULL, NULL)))
369*e0c4386eSCy Schubert         goto err;
370*e0c4386eSCy Schubert 
371*e0c4386eSCy Schubert     /* Dup without an engine */
372*e0c4386eSCy Schubert     if (!TEST_ptr(dupcert = X509_dup(cert)))
373*e0c4386eSCy Schubert         goto err;
374*e0c4386eSCy Schubert     X509_free(dupcert);
375*e0c4386eSCy Schubert     dupcert = NULL;
376*e0c4386eSCy Schubert 
377*e0c4386eSCy Schubert     if (!TEST_ptr(pubkey = X509_get_X509_PUBKEY(cert))
378*e0c4386eSCy Schubert         || !TEST_ptr(duppubkey = X509_PUBKEY_dup(pubkey))
379*e0c4386eSCy Schubert         || !TEST_ptr_ne(duppubkey, pubkey)
380*e0c4386eSCy Schubert         || !TEST_ptr_ne(X509_PUBKEY_get0(duppubkey), X509_PUBKEY_get0(pubkey)))
381*e0c4386eSCy Schubert         goto err;
382*e0c4386eSCy Schubert 
383*e0c4386eSCy Schubert     X509_PUBKEY_free(duppubkey);
384*e0c4386eSCy Schubert     duppubkey = NULL;
385*e0c4386eSCy Schubert 
386*e0c4386eSCy Schubert     X509_free(cert);
387*e0c4386eSCy Schubert     cert = NULL;
388*e0c4386eSCy Schubert 
389*e0c4386eSCy Schubert     /* Create a test ENGINE */
390*e0c4386eSCy Schubert     if (!TEST_ptr(e = ENGINE_new())
391*e0c4386eSCy Schubert             || !TEST_true(ENGINE_set_id(e, "Test dummy engine"))
392*e0c4386eSCy Schubert             || !TEST_true(ENGINE_set_name(e, "Test dummy engine")))
393*e0c4386eSCy Schubert         goto err;
394*e0c4386eSCy Schubert 
395*e0c4386eSCy Schubert     if (!TEST_ptr(rsameth = RSA_meth_dup(RSA_get_default_method())))
396*e0c4386eSCy Schubert         goto err;
397*e0c4386eSCy Schubert 
398*e0c4386eSCy Schubert     ENGINE_set_RSA(e, rsameth);
399*e0c4386eSCy Schubert 
400*e0c4386eSCy Schubert     if (!TEST_true(ENGINE_set_default_RSA(e)))
401*e0c4386eSCy Schubert         goto err;
402*e0c4386eSCy Schubert 
403*e0c4386eSCy Schubert     if (!TEST_int_ge(BIO_seek(b, 0), 0)
404*e0c4386eSCy Schubert         || !TEST_ptr(cert = PEM_read_bio_X509(b, NULL, NULL, NULL)))
405*e0c4386eSCy Schubert         goto err;
406*e0c4386eSCy Schubert 
407*e0c4386eSCy Schubert     /* Dup with an engine set on the key */
408*e0c4386eSCy Schubert     if (!TEST_ptr(dupcert = X509_dup(cert)))
409*e0c4386eSCy Schubert         goto err;
410*e0c4386eSCy Schubert 
411*e0c4386eSCy Schubert     if (!TEST_ptr(pubkey = X509_get_X509_PUBKEY(cert))
412*e0c4386eSCy Schubert         || !TEST_ptr(duppubkey = X509_PUBKEY_dup(pubkey))
413*e0c4386eSCy Schubert         || !TEST_ptr_ne(duppubkey, pubkey)
414*e0c4386eSCy Schubert         || !TEST_ptr_ne(X509_PUBKEY_get0(duppubkey), X509_PUBKEY_get0(pubkey)))
415*e0c4386eSCy Schubert         goto err;
416*e0c4386eSCy Schubert 
417*e0c4386eSCy Schubert     ret = 1;
418*e0c4386eSCy Schubert 
419*e0c4386eSCy Schubert  err:
420*e0c4386eSCy Schubert     X509_free(cert);
421*e0c4386eSCy Schubert     X509_free(dupcert);
422*e0c4386eSCy Schubert     X509_PUBKEY_free(duppubkey);
423*e0c4386eSCy Schubert     if (e != NULL) {
424*e0c4386eSCy Schubert         ENGINE_unregister_RSA(e);
425*e0c4386eSCy Schubert         ENGINE_free(e);
426*e0c4386eSCy Schubert     }
427*e0c4386eSCy Schubert     RSA_meth_free(rsameth);
428*e0c4386eSCy Schubert     BIO_free(b);
429*e0c4386eSCy Schubert     return ret;
430*e0c4386eSCy Schubert }
431*e0c4386eSCy Schubert #endif
432*e0c4386eSCy Schubert 
global_init(void)433*e0c4386eSCy Schubert int global_init(void)
434*e0c4386eSCy Schubert {
435*e0c4386eSCy Schubert     /*
436*e0c4386eSCy Schubert      * If the config file gets loaded, the dynamic engine will be loaded,
437*e0c4386eSCy Schubert      * and that interferes with our test above.
438*e0c4386eSCy Schubert      */
439*e0c4386eSCy Schubert     return OPENSSL_init_crypto(OPENSSL_INIT_NO_LOAD_CONFIG, NULL);
440*e0c4386eSCy Schubert }
441*e0c4386eSCy Schubert 
442*e0c4386eSCy Schubert OPT_TEST_DECLARE_USAGE("certfile\n")
443*e0c4386eSCy Schubert 
setup_tests(void)444*e0c4386eSCy Schubert int setup_tests(void)
445*e0c4386eSCy Schubert {
446*e0c4386eSCy Schubert #ifdef OPENSSL_NO_ENGINE
447*e0c4386eSCy Schubert     TEST_note("No ENGINE support");
448*e0c4386eSCy Schubert #else
449*e0c4386eSCy Schubert     int n;
450*e0c4386eSCy Schubert 
451*e0c4386eSCy Schubert     if (!test_skip_common_options()) {
452*e0c4386eSCy Schubert         TEST_error("Error parsing test options\n");
453*e0c4386eSCy Schubert         return 0;
454*e0c4386eSCy Schubert     }
455*e0c4386eSCy Schubert 
456*e0c4386eSCy Schubert     n = test_get_argument_count();
457*e0c4386eSCy Schubert     if (n == 0)
458*e0c4386eSCy Schubert         return 0;
459*e0c4386eSCy Schubert 
460*e0c4386eSCy Schubert     ADD_TEST(test_engines);
461*e0c4386eSCy Schubert     ADD_TEST(test_redirect);
462*e0c4386eSCy Schubert     ADD_TEST(test_x509_dup_w_engine);
463*e0c4386eSCy Schubert #endif
464*e0c4386eSCy Schubert     return 1;
465*e0c4386eSCy Schubert }
466