/src/openssl/crypto/evp/mac_meth.c
Line | Count | Source (jump to first uncovered line) |
1 | | /* |
2 | | * Copyright 2022-2023 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/evp.h> |
11 | | #include <openssl/err.h> |
12 | | #include <openssl/core.h> |
13 | | #include <openssl/core_dispatch.h> |
14 | | #include "internal/provider.h" |
15 | | #include "internal/core.h" |
16 | | #include "crypto/evp.h" |
17 | | #include "evp_local.h" |
18 | | |
19 | | static int evp_mac_up_ref(void *vmac) |
20 | 56.6k | { |
21 | 56.6k | EVP_MAC *mac = vmac; |
22 | 56.6k | int ref = 0; |
23 | | |
24 | 56.6k | CRYPTO_UP_REF(&mac->refcnt, &ref); |
25 | 56.6k | return 1; |
26 | 56.6k | } |
27 | | |
28 | | static void evp_mac_free(void *vmac) |
29 | 56.6k | { |
30 | 56.6k | EVP_MAC *mac = vmac; |
31 | 56.6k | int ref = 0; |
32 | | |
33 | 56.6k | if (mac == NULL) |
34 | 0 | return; |
35 | | |
36 | 56.6k | CRYPTO_DOWN_REF(&mac->refcnt, &ref); |
37 | 56.6k | if (ref > 0) |
38 | 56.6k | return; |
39 | 18 | OPENSSL_free(mac->type_name); |
40 | 18 | ossl_provider_free(mac->prov); |
41 | 18 | CRYPTO_FREE_REF(&mac->refcnt); |
42 | 18 | OPENSSL_free(mac); |
43 | 18 | } |
44 | | |
45 | | static void *evp_mac_new(void) |
46 | 18 | { |
47 | 18 | EVP_MAC *mac = NULL; |
48 | | |
49 | 18 | if ((mac = OPENSSL_zalloc(sizeof(*mac))) == NULL |
50 | 18 | || !CRYPTO_NEW_REF(&mac->refcnt, 1)) { |
51 | 0 | evp_mac_free(mac); |
52 | 0 | return NULL; |
53 | 0 | } |
54 | 18 | return mac; |
55 | 18 | } |
56 | | |
57 | | static void *evp_mac_from_algorithm(int name_id, |
58 | | const OSSL_ALGORITHM *algodef, |
59 | | OSSL_PROVIDER *prov) |
60 | 18 | { |
61 | 18 | const OSSL_DISPATCH *fns = algodef->implementation; |
62 | 18 | EVP_MAC *mac = NULL; |
63 | 18 | int fnmaccnt = 0, fnctxcnt = 0; |
64 | | |
65 | 18 | if ((mac = evp_mac_new()) == NULL) { |
66 | 0 | ERR_raise(ERR_LIB_EVP, ERR_R_EVP_LIB); |
67 | 0 | return NULL; |
68 | 0 | } |
69 | 18 | mac->name_id = name_id; |
70 | 18 | if ((mac->type_name = ossl_algorithm_get1_first_name(algodef)) == NULL) { |
71 | 0 | evp_mac_free(mac); |
72 | 0 | return NULL; |
73 | 0 | } |
74 | 18 | mac->description = algodef->algorithm_description; |
75 | | |
76 | 198 | for (; fns->function_id != 0; fns++) { |
77 | 180 | switch (fns->function_id) { |
78 | 18 | case OSSL_FUNC_MAC_NEWCTX: |
79 | 18 | if (mac->newctx != NULL) |
80 | 0 | break; |
81 | 18 | mac->newctx = OSSL_FUNC_mac_newctx(fns); |
82 | 18 | fnctxcnt++; |
83 | 18 | break; |
84 | 18 | case OSSL_FUNC_MAC_DUPCTX: |
85 | 18 | if (mac->dupctx != NULL) |
86 | 0 | break; |
87 | 18 | mac->dupctx = OSSL_FUNC_mac_dupctx(fns); |
88 | 18 | break; |
89 | 18 | case OSSL_FUNC_MAC_FREECTX: |
90 | 18 | if (mac->freectx != NULL) |
91 | 0 | break; |
92 | 18 | mac->freectx = OSSL_FUNC_mac_freectx(fns); |
93 | 18 | fnctxcnt++; |
94 | 18 | break; |
95 | 18 | case OSSL_FUNC_MAC_INIT: |
96 | 18 | if (mac->init != NULL) |
97 | 0 | break; |
98 | 18 | mac->init = OSSL_FUNC_mac_init(fns); |
99 | 18 | fnmaccnt++; |
100 | 18 | break; |
101 | 18 | case OSSL_FUNC_MAC_UPDATE: |
102 | 18 | if (mac->update != NULL) |
103 | 0 | break; |
104 | 18 | mac->update = OSSL_FUNC_mac_update(fns); |
105 | 18 | fnmaccnt++; |
106 | 18 | break; |
107 | 18 | case OSSL_FUNC_MAC_FINAL: |
108 | 18 | if (mac->final != NULL) |
109 | 0 | break; |
110 | 18 | mac->final = OSSL_FUNC_mac_final(fns); |
111 | 18 | fnmaccnt++; |
112 | 18 | break; |
113 | 4 | case OSSL_FUNC_MAC_GETTABLE_PARAMS: |
114 | 4 | if (mac->gettable_params != NULL) |
115 | 0 | break; |
116 | 4 | mac->gettable_params = |
117 | 4 | OSSL_FUNC_mac_gettable_params(fns); |
118 | 4 | break; |
119 | 14 | case OSSL_FUNC_MAC_GETTABLE_CTX_PARAMS: |
120 | 14 | if (mac->gettable_ctx_params != NULL) |
121 | 0 | break; |
122 | 14 | mac->gettable_ctx_params = |
123 | 14 | OSSL_FUNC_mac_gettable_ctx_params(fns); |
124 | 14 | break; |
125 | 18 | case OSSL_FUNC_MAC_SETTABLE_CTX_PARAMS: |
126 | 18 | if (mac->settable_ctx_params != NULL) |
127 | 0 | break; |
128 | 18 | mac->settable_ctx_params = |
129 | 18 | OSSL_FUNC_mac_settable_ctx_params(fns); |
130 | 18 | break; |
131 | 4 | case OSSL_FUNC_MAC_GET_PARAMS: |
132 | 4 | if (mac->get_params != NULL) |
133 | 0 | break; |
134 | 4 | mac->get_params = OSSL_FUNC_mac_get_params(fns); |
135 | 4 | break; |
136 | 14 | case OSSL_FUNC_MAC_GET_CTX_PARAMS: |
137 | 14 | if (mac->get_ctx_params != NULL) |
138 | 0 | break; |
139 | 14 | mac->get_ctx_params = OSSL_FUNC_mac_get_ctx_params(fns); |
140 | 14 | break; |
141 | 18 | case OSSL_FUNC_MAC_SET_CTX_PARAMS: |
142 | 18 | if (mac->set_ctx_params != NULL) |
143 | 0 | break; |
144 | 18 | mac->set_ctx_params = OSSL_FUNC_mac_set_ctx_params(fns); |
145 | 18 | break; |
146 | 180 | } |
147 | 180 | } |
148 | 18 | if (fnmaccnt != 3 |
149 | 18 | || fnctxcnt != 2) { |
150 | | /* |
151 | | * In order to be a consistent set of functions we must have at least |
152 | | * a complete set of "mac" functions, and a complete set of context |
153 | | * management functions, as well as the size function. |
154 | | */ |
155 | 0 | evp_mac_free(mac); |
156 | 0 | ERR_raise(ERR_LIB_EVP, EVP_R_INVALID_PROVIDER_FUNCTIONS); |
157 | 0 | return NULL; |
158 | 0 | } |
159 | 18 | mac->prov = prov; |
160 | 18 | if (prov != NULL) |
161 | 18 | ossl_provider_up_ref(prov); |
162 | | |
163 | 18 | return mac; |
164 | 18 | } |
165 | | |
166 | | EVP_MAC *EVP_MAC_fetch(OSSL_LIB_CTX *libctx, const char *algorithm, |
167 | | const char *properties) |
168 | 3.27k | { |
169 | 3.27k | return evp_generic_fetch(libctx, OSSL_OP_MAC, algorithm, properties, |
170 | 3.27k | evp_mac_from_algorithm, evp_mac_up_ref, |
171 | 3.27k | evp_mac_free); |
172 | 3.27k | } |
173 | | |
174 | | int EVP_MAC_up_ref(EVP_MAC *mac) |
175 | 53.3k | { |
176 | 53.3k | return evp_mac_up_ref(mac); |
177 | 53.3k | } |
178 | | |
179 | | void EVP_MAC_free(EVP_MAC *mac) |
180 | 56.6k | { |
181 | 56.6k | evp_mac_free(mac); |
182 | 56.6k | } |
183 | | |
184 | | const OSSL_PROVIDER *EVP_MAC_get0_provider(const EVP_MAC *mac) |
185 | 211 | { |
186 | 211 | return mac->prov; |
187 | 211 | } |
188 | | |
189 | | const OSSL_PARAM *EVP_MAC_gettable_params(const EVP_MAC *mac) |
190 | 0 | { |
191 | 0 | if (mac->gettable_params == NULL) |
192 | 0 | return NULL; |
193 | 0 | return mac->gettable_params(ossl_provider_ctx(EVP_MAC_get0_provider(mac))); |
194 | 0 | } |
195 | | |
196 | | const OSSL_PARAM *EVP_MAC_gettable_ctx_params(const EVP_MAC *mac) |
197 | 0 | { |
198 | 0 | void *alg; |
199 | |
|
200 | 0 | if (mac->gettable_ctx_params == NULL) |
201 | 0 | return NULL; |
202 | 0 | alg = ossl_provider_ctx(EVP_MAC_get0_provider(mac)); |
203 | 0 | return mac->gettable_ctx_params(NULL, alg); |
204 | 0 | } |
205 | | |
206 | | const OSSL_PARAM *EVP_MAC_settable_ctx_params(const EVP_MAC *mac) |
207 | 211 | { |
208 | 211 | void *alg; |
209 | | |
210 | 211 | if (mac->settable_ctx_params == NULL) |
211 | 0 | return NULL; |
212 | 211 | alg = ossl_provider_ctx(EVP_MAC_get0_provider(mac)); |
213 | 211 | return mac->settable_ctx_params(NULL, alg); |
214 | 211 | } |
215 | | |
216 | | const OSSL_PARAM *EVP_MAC_CTX_gettable_params(EVP_MAC_CTX *ctx) |
217 | 0 | { |
218 | 0 | void *alg; |
219 | |
|
220 | 0 | if (ctx->meth->gettable_ctx_params == NULL) |
221 | 0 | return NULL; |
222 | 0 | alg = ossl_provider_ctx(EVP_MAC_get0_provider(ctx->meth)); |
223 | 0 | return ctx->meth->gettable_ctx_params(ctx->algctx, alg); |
224 | 0 | } |
225 | | |
226 | | const OSSL_PARAM *EVP_MAC_CTX_settable_params(EVP_MAC_CTX *ctx) |
227 | 0 | { |
228 | 0 | void *alg; |
229 | |
|
230 | 0 | if (ctx->meth->settable_ctx_params == NULL) |
231 | 0 | return NULL; |
232 | 0 | alg = ossl_provider_ctx(EVP_MAC_get0_provider(ctx->meth)); |
233 | 0 | return ctx->meth->settable_ctx_params(ctx->algctx, alg); |
234 | 0 | } |
235 | | |
236 | | void EVP_MAC_do_all_provided(OSSL_LIB_CTX *libctx, |
237 | | void (*fn)(EVP_MAC *mac, void *arg), |
238 | | void *arg) |
239 | 0 | { |
240 | 0 | evp_generic_do_all(libctx, OSSL_OP_MAC, |
241 | 0 | (void (*)(void *, void *))fn, arg, |
242 | 0 | evp_mac_from_algorithm, evp_mac_up_ref, evp_mac_free); |
243 | 0 | } |