Add EVP_KDF-X942 to the fips module
[openssl.git] / test / keymgmt_internal_test.c
1 /*
2  * Copyright 2019-2020 The OpenSSL Project Authors. All Rights Reserved.
3  *
4  * Licensed under the Apache License 2.0 (the "License").  You may not use
5  * this file except in compliance with the License.  You can obtain a copy
6  * in the file LICENSE in the source distribution or at
7  * https://www.openssl.org/source/license.html
8  */
9
10 /*
11  * RSA low level APIs are deprecated for public use, but still ok for
12  * internal use.
13  */
14 #include "internal/deprecated.h"
15
16 #include <string.h>
17
18 #include <openssl/bio.h>
19 #include <openssl/bn.h>
20 #include <openssl/rsa.h>
21 #include <openssl/evp.h>
22 #include <openssl/provider.h>
23 #include <openssl/core_names.h>
24 #include "internal/core.h"
25 #include "internal/nelem.h"
26 #include "crypto/evp.h"          /* For the internal API */
27 #include "testutil.h"
28
29 typedef struct {
30     OSSL_LIB_CTX *ctx1;
31     OSSL_PROVIDER *prov1;
32     OSSL_LIB_CTX *ctx2;
33     OSSL_PROVIDER *prov2;
34 } FIXTURE;
35
36 static void tear_down(FIXTURE *fixture)
37 {
38     if (fixture != NULL) {
39         OSSL_PROVIDER_unload(fixture->prov1);
40         OSSL_PROVIDER_unload(fixture->prov2);
41         OSSL_LIB_CTX_free(fixture->ctx1);
42         OSSL_LIB_CTX_free(fixture->ctx2);
43         OPENSSL_free(fixture);
44     }
45 }
46
47 static FIXTURE *set_up(const char *testcase_name)
48 {
49     FIXTURE *fixture;
50
51     if (!TEST_ptr(fixture = OPENSSL_zalloc(sizeof(*fixture)))
52         || !TEST_ptr(fixture->ctx1 = OSSL_LIB_CTX_new())
53         || !TEST_ptr(fixture->prov1 = OSSL_PROVIDER_load(fixture->ctx1,
54                                                          "default"))
55         || !TEST_ptr(fixture->ctx2 = OSSL_LIB_CTX_new())
56         || !TEST_ptr(fixture->prov2 = OSSL_PROVIDER_load(fixture->ctx2,
57                                                          "default"))) {
58         tear_down(fixture);
59         return NULL;
60     }
61     return fixture;
62 }
63
64 /* Array indexes */
65 #define N       0
66 #define E       1
67 #define D       2
68 #define P       3
69 #define Q       4
70 #define F3      5                /* Extra factor */
71 #define DP      6
72 #define DQ      7
73 #define E3      8                /* Extra exponent */
74 #define QINV    9
75 #define C2      10               /* Extra coefficient */
76
77 /*
78  * We have to do this because OSSL_PARAM_get_ulong() can't handle params
79  * holding data that isn't exactly sizeof(uint32_t) or sizeof(uint64_t),
80  * and because the other end deals with BIGNUM, the resulting param might
81  * be any size.  In this particular test, we know that the expected data
82  * fits within an unsigned long, and we want to get the data in that form
83  * to make testing of values easier.
84  */
85 static int get_ulong_via_BN(const OSSL_PARAM *p, unsigned long *goal)
86 {
87     BIGNUM *n = NULL;
88     int ret = 1;                 /* Ever so hopeful */
89
90     if (!TEST_true(OSSL_PARAM_get_BN(p, &n))
91         || !TEST_true(BN_bn2nativepad(n, (unsigned char *)goal, sizeof(*goal))))
92         ret = 0;
93     BN_free(n);
94     return ret;
95 }
96
97 static int export_cb(const OSSL_PARAM *params, void *arg)
98 {
99     unsigned long *keydata = arg;
100     const OSSL_PARAM *p = NULL;
101
102     if (keydata == NULL)
103         return 0;
104
105     if (!TEST_ptr(p = OSSL_PARAM_locate_const(params, OSSL_PKEY_PARAM_RSA_N))
106         || !TEST_true(get_ulong_via_BN(p, &keydata[N]))
107         || !TEST_ptr(p = OSSL_PARAM_locate_const(params, OSSL_PKEY_PARAM_RSA_E))
108         || !TEST_true(get_ulong_via_BN(p, &keydata[E]))
109         || !TEST_ptr(p = OSSL_PARAM_locate_const(params, OSSL_PKEY_PARAM_RSA_D))
110         || !TEST_true(get_ulong_via_BN(p, &keydata[D])))
111         return 0;
112
113     if (!TEST_ptr(p = OSSL_PARAM_locate_const(params, OSSL_PKEY_PARAM_RSA_FACTOR1))
114         || !TEST_true(get_ulong_via_BN(p, &keydata[P]))
115         || !TEST_ptr(p = OSSL_PARAM_locate_const(params, OSSL_PKEY_PARAM_RSA_FACTOR2))
116         || !TEST_true(get_ulong_via_BN(p, &keydata[Q]))
117         || !TEST_ptr(p = OSSL_PARAM_locate_const(params, OSSL_PKEY_PARAM_RSA_FACTOR3))
118         || !TEST_true(get_ulong_via_BN(p, &keydata[F3])))
119         return 0;
120
121     if (!TEST_ptr(p = OSSL_PARAM_locate_const(params, OSSL_PKEY_PARAM_RSA_EXPONENT1))
122         || !TEST_true(get_ulong_via_BN(p, &keydata[DP]))
123         || !TEST_ptr(p = OSSL_PARAM_locate_const(params, OSSL_PKEY_PARAM_RSA_EXPONENT2))
124         || !TEST_true(get_ulong_via_BN(p, &keydata[DQ]))
125         || !TEST_ptr(p = OSSL_PARAM_locate_const(params, OSSL_PKEY_PARAM_RSA_EXPONENT3))
126         || !TEST_true(get_ulong_via_BN(p, &keydata[E3])))
127         return 0;
128
129     if (!TEST_ptr(p = OSSL_PARAM_locate_const(params, OSSL_PKEY_PARAM_RSA_COEFFICIENT1))
130         || !TEST_true(get_ulong_via_BN(p, &keydata[QINV]))
131         || !TEST_ptr(p = OSSL_PARAM_locate_const(params, OSSL_PKEY_PARAM_RSA_COEFFICIENT2))
132         || !TEST_true(get_ulong_via_BN(p, &keydata[C2])))
133         return 0;
134
135     return 1;
136 }
137
138 static int test_pass_rsa(FIXTURE *fixture)
139 {
140     size_t i;
141     int ret = 0;
142     RSA *rsa = NULL;
143     BIGNUM *bn1 = NULL, *bn2 = NULL, *bn3 = NULL;
144     EVP_PKEY *pk = NULL;
145     EVP_KEYMGMT *km1 = NULL, *km2 = NULL;
146     void *provkey = NULL;
147     BIGNUM *bn_primes[1] = { NULL };
148     BIGNUM *bn_exps[1] = { NULL };
149     BIGNUM *bn_coeffs[1] = { NULL };
150     /*
151      * 32-bit RSA key, extracted from this command,
152      * executed with OpenSSL 1.0.2:
153      * An extra factor was added just for testing purposes.
154      *
155      * openssl genrsa 32 | openssl rsa -text
156      */
157     static BN_ULONG expected[] = {
158         0xbc747fc5,              /* N */
159         0x10001,                 /* E */
160         0x7b133399,              /* D */
161         0xe963,                  /* P */
162         0xceb7,                  /* Q */
163         1,                       /* F3 */
164         0x8599,                  /* DP */
165         0xbd87,                  /* DQ */
166         2,                       /* E3 */
167         0xcc3b,                  /* QINV */
168         3,                       /* C3 */
169         0                        /* Extra, should remain zero */
170     };
171     static unsigned long keydata[OSSL_NELEM(expected)] = { 0, };
172
173     if (!TEST_ptr(rsa = RSA_new()))
174         goto err;
175
176     if (!TEST_ptr(bn1 = BN_new())
177         || !TEST_true(BN_set_word(bn1, expected[N]))
178         || !TEST_ptr(bn2 = BN_new())
179         || !TEST_true(BN_set_word(bn2, expected[E]))
180         || !TEST_ptr(bn3 = BN_new())
181         || !TEST_true(BN_set_word(bn3, expected[D]))
182         || !TEST_true(RSA_set0_key(rsa, bn1, bn2, bn3)))
183         goto err;
184
185     if (!TEST_ptr(bn1 = BN_new())
186         || !TEST_true(BN_set_word(bn1, expected[P]))
187         || !TEST_ptr(bn2 = BN_new())
188         || !TEST_true(BN_set_word(bn2, expected[Q]))
189         || !TEST_true(RSA_set0_factors(rsa, bn1, bn2)))
190         goto err;
191
192     if (!TEST_ptr(bn1 = BN_new())
193         || !TEST_true(BN_set_word(bn1, expected[DP]))
194         || !TEST_ptr(bn2 = BN_new())
195         || !TEST_true(BN_set_word(bn2, expected[DQ]))
196         || !TEST_ptr(bn3 = BN_new())
197         || !TEST_true(BN_set_word(bn3, expected[QINV]))
198         || !TEST_true(RSA_set0_crt_params(rsa, bn1, bn2, bn3)))
199         goto err;
200     bn1 = bn2 = bn3 = NULL;
201
202     if (!TEST_ptr(bn_primes[0] = BN_new())
203         || !TEST_true(BN_set_word(bn_primes[0], expected[F3]))
204         || !TEST_ptr(bn_exps[0] = BN_new())
205         || !TEST_true(BN_set_word(bn_exps[0], expected[E3]))
206         || !TEST_ptr(bn_coeffs[0] = BN_new())
207         || !TEST_true(BN_set_word(bn_coeffs[0], expected[C2]))
208         || !TEST_true(RSA_set0_multi_prime_params(rsa, bn_primes, bn_exps,
209                                                   bn_coeffs, 1)))
210         goto err;
211
212     if (!TEST_ptr(pk = EVP_PKEY_new())
213         || !TEST_true(EVP_PKEY_assign_RSA(pk, rsa)))
214         goto err;
215     rsa = NULL;
216
217     if (!TEST_ptr(km1 = EVP_KEYMGMT_fetch(fixture->ctx1, "RSA", NULL))
218         || !TEST_ptr(km2 = EVP_KEYMGMT_fetch(fixture->ctx2, "RSA", NULL))
219         || !TEST_ptr_ne(km1, km2))
220         goto err;
221
222     if (!TEST_ptr(provkey = evp_pkey_export_to_provider(pk, NULL, &km1, NULL))
223         || !TEST_true(evp_keymgmt_export(km2, provkey,
224                                          OSSL_KEYMGMT_SELECT_KEYPAIR,
225                                          &export_cb, keydata)))
226         goto err;
227
228     /*
229      * At this point, the hope is that keydata will have all the numbers
230      * from the key.
231      */
232
233     for (i = 0; i < OSSL_NELEM(expected); i++) {
234         int rv = TEST_int_eq(expected[i], keydata[i]);
235
236         if (!rv)
237             TEST_info("i = %zu", i);
238         else
239             ret++;
240     }
241
242     ret = (ret == OSSL_NELEM(expected));
243
244  err:
245     RSA_free(rsa);
246     BN_free(bn1);
247     BN_free(bn2);
248     BN_free(bn3);
249     EVP_PKEY_free(pk);
250     EVP_KEYMGMT_free(km1);
251     EVP_KEYMGMT_free(km2);
252
253     return ret;
254 }
255
256 static int (*tests[])(FIXTURE *) = {
257     test_pass_rsa
258 };
259
260 static int test_pass_key(int n)
261 {
262     SETUP_TEST_FIXTURE(FIXTURE, set_up);
263     EXECUTE_TEST(tests[n], tear_down);
264     return result;
265 }
266
267 int setup_tests(void)
268 {
269     ADD_ALL_TESTS(test_pass_key, 1);
270     return 1;
271 }