]>
Commit | Line | Data |
---|---|---|
ac2d58c7 MC |
1 | /* |
2 | * Copyright 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 | #include <openssl/crypto.h> | |
11 | #include <openssl/kdf.h> | |
12 | #include <openssl/core_dispatch.h> | |
13 | #include <openssl/core_names.h> | |
14 | #include <openssl/params.h> | |
15 | #include "prov/implementations.h" | |
16 | #include "prov/provider_ctx.h" | |
17 | #include "prov/kdfexchange.h" | |
ca94057f | 18 | #include "prov/providercommon.h" |
ac2d58c7 | 19 | |
05d2f72e MC |
20 | static OSSL_FUNC_keyexch_newctx_fn kdf_tls1_prf_newctx; |
21 | static OSSL_FUNC_keyexch_newctx_fn kdf_hkdf_newctx; | |
194de849 | 22 | static OSSL_FUNC_keyexch_newctx_fn kdf_scrypt_newctx; |
ac2d58c7 MC |
23 | static OSSL_FUNC_keyexch_init_fn kdf_init; |
24 | static OSSL_FUNC_keyexch_derive_fn kdf_derive; | |
25 | static OSSL_FUNC_keyexch_freectx_fn kdf_freectx; | |
26 | static OSSL_FUNC_keyexch_dupctx_fn kdf_dupctx; | |
27 | static OSSL_FUNC_keyexch_set_ctx_params_fn kdf_set_ctx_params; | |
05d2f72e MC |
28 | static OSSL_FUNC_keyexch_settable_ctx_params_fn kdf_tls1_prf_settable_ctx_params; |
29 | static OSSL_FUNC_keyexch_settable_ctx_params_fn kdf_hkdf_settable_ctx_params; | |
194de849 | 30 | static OSSL_FUNC_keyexch_settable_ctx_params_fn kdf_scrypt_settable_ctx_params; |
ac2d58c7 MC |
31 | |
32 | typedef struct { | |
33 | void *provctx; | |
34 | EVP_KDF_CTX *kdfctx; | |
35 | KDF_DATA *kdfdata; | |
36 | } PROV_KDF_CTX; | |
37 | ||
9d1ae03c MC |
38 | static void *kdf_newctx(const char *kdfname, void *provctx) |
39 | { | |
ca94057f | 40 | PROV_KDF_CTX *kdfctx; |
9d1ae03c MC |
41 | EVP_KDF *kdf = NULL; |
42 | ||
ca94057f P |
43 | if (!ossl_prov_is_running()) |
44 | return NULL; | |
45 | ||
46 | kdfctx = OPENSSL_zalloc(sizeof(PROV_KDF_CTX)); | |
9d1ae03c MC |
47 | if (kdfctx == NULL) |
48 | return NULL; | |
49 | ||
50 | kdfctx->provctx = provctx; | |
51 | ||
52 | kdf = EVP_KDF_fetch(PROV_LIBRARY_CONTEXT_OF(provctx), kdfname, NULL); | |
53 | if (kdf == NULL) | |
54 | goto err; | |
55 | kdfctx->kdfctx = EVP_KDF_CTX_new(kdf); | |
56 | EVP_KDF_free(kdf); | |
57 | ||
58 | if (kdfctx->kdfctx == NULL) | |
59 | goto err; | |
60 | ||
61 | return kdfctx; | |
62 | err: | |
63 | OPENSSL_free(kdfctx); | |
64 | return NULL; | |
65 | } | |
66 | ||
05d2f72e MC |
67 | #define KDF_NEWCTX(funcname, kdfname) \ |
68 | static void *kdf_##funcname##_newctx(void *provctx) \ | |
69 | { \ | |
9d1ae03c | 70 | return kdf_newctx(kdfname, provctx); \ |
05d2f72e | 71 | } |
ac2d58c7 | 72 | |
05d2f72e MC |
73 | KDF_NEWCTX(tls1_prf, "TLS1-PRF") |
74 | KDF_NEWCTX(hkdf, "HKDF") | |
194de849 | 75 | KDF_NEWCTX(scrypt, "SCRYPT") |
ac2d58c7 MC |
76 | |
77 | static int kdf_init(void *vpkdfctx, void *vkdf) | |
78 | { | |
79 | PROV_KDF_CTX *pkdfctx = (PROV_KDF_CTX *)vpkdfctx; | |
80 | ||
ca94057f P |
81 | if (!ossl_prov_is_running() |
82 | || pkdfctx == NULL | |
83 | || vkdf == NULL | |
84 | || !kdf_data_up_ref(vkdf)) | |
ac2d58c7 MC |
85 | return 0; |
86 | pkdfctx->kdfdata = vkdf; | |
87 | ||
88 | return 1; | |
89 | } | |
90 | ||
91 | static int kdf_derive(void *vpkdfctx, unsigned char *secret, size_t *secretlen, | |
92 | size_t outlen) | |
93 | { | |
94 | PROV_KDF_CTX *pkdfctx = (PROV_KDF_CTX *)vpkdfctx; | |
95 | ||
ca94057f P |
96 | if (!ossl_prov_is_running()) |
97 | return 0; | |
ac2d58c7 MC |
98 | return EVP_KDF_derive(pkdfctx->kdfctx, secret, *secretlen); |
99 | } | |
100 | ||
101 | static void kdf_freectx(void *vpkdfctx) | |
102 | { | |
103 | PROV_KDF_CTX *pkdfctx = (PROV_KDF_CTX *)vpkdfctx; | |
104 | ||
105 | EVP_KDF_CTX_free(pkdfctx->kdfctx); | |
106 | kdf_data_free(pkdfctx->kdfdata); | |
107 | ||
108 | OPENSSL_free(pkdfctx); | |
109 | } | |
110 | ||
111 | static void *kdf_dupctx(void *vpkdfctx) | |
112 | { | |
113 | PROV_KDF_CTX *srcctx = (PROV_KDF_CTX *)vpkdfctx; | |
114 | PROV_KDF_CTX *dstctx; | |
115 | ||
ca94057f P |
116 | if (!ossl_prov_is_running()) |
117 | return NULL; | |
118 | ||
ac2d58c7 MC |
119 | dstctx = OPENSSL_zalloc(sizeof(*srcctx)); |
120 | if (dstctx == NULL) | |
121 | return NULL; | |
122 | ||
123 | *dstctx = *srcctx; | |
124 | ||
05d2f72e | 125 | dstctx->kdfctx = EVP_KDF_CTX_dup(srcctx->kdfctx); |
ac2d58c7 MC |
126 | if (dstctx->kdfctx == NULL) { |
127 | OPENSSL_free(dstctx); | |
128 | return NULL; | |
129 | } | |
130 | if (!kdf_data_up_ref(dstctx->kdfdata)) { | |
131 | EVP_KDF_CTX_free(dstctx->kdfctx); | |
132 | OPENSSL_free(dstctx); | |
133 | return NULL; | |
134 | } | |
135 | ||
136 | return dstctx; | |
137 | } | |
138 | ||
139 | static int kdf_set_ctx_params(void *vpkdfctx, const OSSL_PARAM params[]) | |
140 | { | |
141 | PROV_KDF_CTX *pkdfctx = (PROV_KDF_CTX *)vpkdfctx; | |
142 | ||
05d2f72e | 143 | return EVP_KDF_CTX_set_params(pkdfctx->kdfctx, params); |
ac2d58c7 MC |
144 | } |
145 | ||
9d1ae03c MC |
146 | static const OSSL_PARAM *kdf_settable_ctx_params(void *provctx, |
147 | const char *kdfname) | |
148 | { | |
149 | EVP_KDF *kdf = EVP_KDF_fetch(PROV_LIBRARY_CONTEXT_OF(provctx), kdfname, | |
150 | NULL); | |
151 | const OSSL_PARAM *params; | |
152 | ||
153 | if (kdf == NULL) | |
154 | return NULL; | |
155 | ||
156 | params = EVP_KDF_settable_ctx_params(kdf); | |
157 | EVP_KDF_free(kdf); | |
158 | ||
159 | return params; | |
160 | } | |
161 | ||
05d2f72e | 162 | #define KDF_SETTABLE_CTX_PARAMS(funcname, kdfname) \ |
9d1ae03c | 163 | static const OSSL_PARAM *kdf_##funcname##_settable_ctx_params(void *provctx) \ |
05d2f72e | 164 | { \ |
9d1ae03c | 165 | return kdf_settable_ctx_params(provctx, kdfname); \ |
05d2f72e | 166 | } |
ac2d58c7 | 167 | |
05d2f72e MC |
168 | KDF_SETTABLE_CTX_PARAMS(tls1_prf, "TLS1-PRF") |
169 | KDF_SETTABLE_CTX_PARAMS(hkdf, "HKDF") | |
194de849 | 170 | KDF_SETTABLE_CTX_PARAMS(scrypt, "SCRYPT") |
05d2f72e | 171 | |
05d2f72e | 172 | #define KDF_KEYEXCH_FUNCTIONS(funcname) \ |
1be63951 | 173 | const OSSL_DISPATCH ossl_kdf_##funcname##_keyexch_functions[] = { \ |
05d2f72e MC |
174 | { OSSL_FUNC_KEYEXCH_NEWCTX, (void (*)(void))kdf_##funcname##_newctx }, \ |
175 | { OSSL_FUNC_KEYEXCH_INIT, (void (*)(void))kdf_init }, \ | |
176 | { OSSL_FUNC_KEYEXCH_DERIVE, (void (*)(void))kdf_derive }, \ | |
177 | { OSSL_FUNC_KEYEXCH_FREECTX, (void (*)(void))kdf_freectx }, \ | |
178 | { OSSL_FUNC_KEYEXCH_DUPCTX, (void (*)(void))kdf_dupctx }, \ | |
179 | { OSSL_FUNC_KEYEXCH_SET_CTX_PARAMS, (void (*)(void))kdf_set_ctx_params }, \ | |
180 | { OSSL_FUNC_KEYEXCH_SETTABLE_CTX_PARAMS, \ | |
181 | (void (*)(void))kdf_##funcname##_settable_ctx_params }, \ | |
182 | { 0, NULL } \ | |
183 | }; | |
184 | ||
185 | KDF_KEYEXCH_FUNCTIONS(tls1_prf) | |
186 | KDF_KEYEXCH_FUNCTIONS(hkdf) | |
194de849 | 187 | KDF_KEYEXCH_FUNCTIONS(scrypt) |