2 * Copyright 2019-2023 The OpenSSL Project Authors. All Rights Reserved.
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
10 /* Dispatch functions for chacha20 cipher */
12 #include <openssl/proverr.h>
13 #include "cipher_chacha20.h"
14 #include "prov/implementations.h"
15 #include "prov/providercommon.h"
17 #define CHACHA20_KEYLEN (CHACHA_KEY_SIZE)
18 #define CHACHA20_BLKLEN (1)
19 #define CHACHA20_IVLEN (CHACHA_CTR_SIZE)
20 #define CHACHA20_FLAGS (PROV_CIPHER_FLAG_CUSTOM_IV)
22 static OSSL_FUNC_cipher_newctx_fn chacha20_newctx
;
23 static OSSL_FUNC_cipher_freectx_fn chacha20_freectx
;
24 static OSSL_FUNC_cipher_dupctx_fn chacha20_dupctx
;
25 static OSSL_FUNC_cipher_get_params_fn chacha20_get_params
;
26 static OSSL_FUNC_cipher_get_ctx_params_fn chacha20_get_ctx_params
;
27 static OSSL_FUNC_cipher_set_ctx_params_fn chacha20_set_ctx_params
;
28 static OSSL_FUNC_cipher_gettable_ctx_params_fn chacha20_gettable_ctx_params
;
29 static OSSL_FUNC_cipher_settable_ctx_params_fn chacha20_settable_ctx_params
;
30 #define chacha20_cipher ossl_cipher_generic_cipher
31 #define chacha20_update ossl_cipher_generic_stream_update
32 #define chacha20_final ossl_cipher_generic_stream_final
33 #define chacha20_gettable_params ossl_cipher_generic_gettable_params
35 void ossl_chacha20_initctx(PROV_CHACHA20_CTX
*ctx
)
37 ossl_cipher_generic_initkey(ctx
, CHACHA20_KEYLEN
* 8,
41 ossl_prov_cipher_hw_chacha20(CHACHA20_KEYLEN
* 8),
45 static void *chacha20_newctx(void *provctx
)
47 PROV_CHACHA20_CTX
*ctx
;
49 if (!ossl_prov_is_running())
52 ctx
= OPENSSL_zalloc(sizeof(*ctx
));
54 ossl_chacha20_initctx(ctx
);
58 static void chacha20_freectx(void *vctx
)
60 PROV_CHACHA20_CTX
*ctx
= (PROV_CHACHA20_CTX
*)vctx
;
63 ossl_cipher_generic_reset_ctx((PROV_CIPHER_CTX
*)vctx
);
64 OPENSSL_clear_free(ctx
, sizeof(*ctx
));
68 static void *chacha20_dupctx(void *vctx
)
70 PROV_CHACHA20_CTX
*ctx
= (PROV_CHACHA20_CTX
*)vctx
;
71 PROV_CHACHA20_CTX
*dupctx
= NULL
;
74 dupctx
= OPENSSL_memdup(ctx
, sizeof(*dupctx
));
75 if (dupctx
!= NULL
&& dupctx
->base
.tlsmac
!= NULL
&& dupctx
->base
.alloced
) {
76 dupctx
->base
.tlsmac
= OPENSSL_memdup(dupctx
->base
.tlsmac
,
77 dupctx
->base
.tlsmacsize
);
78 if (dupctx
->base
.tlsmac
== NULL
) {
87 static int chacha20_get_params(OSSL_PARAM params
[])
89 return ossl_cipher_generic_get_params(params
, 0, CHACHA20_FLAGS
,
95 static int chacha20_get_ctx_params(void *vctx
, OSSL_PARAM params
[])
99 p
= OSSL_PARAM_locate(params
, OSSL_CIPHER_PARAM_IVLEN
);
100 if (p
!= NULL
&& !OSSL_PARAM_set_size_t(p
, CHACHA20_IVLEN
)) {
101 ERR_raise(ERR_LIB_PROV
, PROV_R_FAILED_TO_SET_PARAMETER
);
104 p
= OSSL_PARAM_locate(params
, OSSL_CIPHER_PARAM_KEYLEN
);
105 if (p
!= NULL
&& !OSSL_PARAM_set_size_t(p
, CHACHA20_KEYLEN
)) {
106 ERR_raise(ERR_LIB_PROV
, PROV_R_FAILED_TO_SET_PARAMETER
);
113 static const OSSL_PARAM chacha20_known_gettable_ctx_params
[] = {
114 OSSL_PARAM_size_t(OSSL_CIPHER_PARAM_KEYLEN
, NULL
),
115 OSSL_PARAM_size_t(OSSL_CIPHER_PARAM_IVLEN
, NULL
),
118 const OSSL_PARAM
*chacha20_gettable_ctx_params(ossl_unused
void *cctx
,
119 ossl_unused
void *provctx
)
121 return chacha20_known_gettable_ctx_params
;
124 static int chacha20_set_ctx_params(void *vctx
, const OSSL_PARAM params
[])
132 p
= OSSL_PARAM_locate_const(params
, OSSL_CIPHER_PARAM_KEYLEN
);
134 if (!OSSL_PARAM_get_size_t(p
, &len
)) {
135 ERR_raise(ERR_LIB_PROV
, PROV_R_FAILED_TO_GET_PARAMETER
);
138 if (len
!= CHACHA20_KEYLEN
) {
139 ERR_raise(ERR_LIB_PROV
, PROV_R_INVALID_KEY_LENGTH
);
143 p
= OSSL_PARAM_locate_const(params
, OSSL_CIPHER_PARAM_IVLEN
);
145 if (!OSSL_PARAM_get_size_t(p
, &len
)) {
146 ERR_raise(ERR_LIB_PROV
, PROV_R_FAILED_TO_GET_PARAMETER
);
149 if (len
!= CHACHA20_IVLEN
) {
150 ERR_raise(ERR_LIB_PROV
, PROV_R_INVALID_IV_LENGTH
);
157 static const OSSL_PARAM chacha20_known_settable_ctx_params
[] = {
158 OSSL_PARAM_size_t(OSSL_CIPHER_PARAM_KEYLEN
, NULL
),
159 OSSL_PARAM_size_t(OSSL_CIPHER_PARAM_IVLEN
, NULL
),
162 const OSSL_PARAM
*chacha20_settable_ctx_params(ossl_unused
void *cctx
,
163 ossl_unused
void *provctx
)
165 return chacha20_known_settable_ctx_params
;
168 int ossl_chacha20_einit(void *vctx
, const unsigned char *key
, size_t keylen
,
169 const unsigned char *iv
, size_t ivlen
,
170 const OSSL_PARAM params
[])
174 /* The generic function checks for ossl_prov_is_running() */
175 ret
= ossl_cipher_generic_einit(vctx
, key
, keylen
, iv
, ivlen
, NULL
);
176 if (ret
&& iv
!= NULL
) {
177 PROV_CIPHER_CTX
*ctx
= (PROV_CIPHER_CTX
*)vctx
;
178 PROV_CIPHER_HW_CHACHA20
*hw
= (PROV_CIPHER_HW_CHACHA20
*)ctx
->hw
;
182 if (ret
&& !chacha20_set_ctx_params(vctx
, params
))
187 int ossl_chacha20_dinit(void *vctx
, const unsigned char *key
, size_t keylen
,
188 const unsigned char *iv
, size_t ivlen
,
189 const OSSL_PARAM params
[])
193 /* The generic function checks for ossl_prov_is_running() */
194 ret
= ossl_cipher_generic_dinit(vctx
, key
, keylen
, iv
, ivlen
, NULL
);
195 if (ret
&& iv
!= NULL
) {
196 PROV_CIPHER_CTX
*ctx
= (PROV_CIPHER_CTX
*)vctx
;
197 PROV_CIPHER_HW_CHACHA20
*hw
= (PROV_CIPHER_HW_CHACHA20
*)ctx
->hw
;
201 if (ret
&& !chacha20_set_ctx_params(vctx
, params
))
206 /* ossl_chacha20_functions */
207 const OSSL_DISPATCH ossl_chacha20_functions
[] = {
208 { OSSL_FUNC_CIPHER_NEWCTX
, (void (*)(void))chacha20_newctx
},
209 { OSSL_FUNC_CIPHER_FREECTX
, (void (*)(void))chacha20_freectx
},
210 { OSSL_FUNC_CIPHER_DUPCTX
, (void (*)(void))chacha20_dupctx
},
211 { OSSL_FUNC_CIPHER_ENCRYPT_INIT
, (void (*)(void))ossl_chacha20_einit
},
212 { OSSL_FUNC_CIPHER_DECRYPT_INIT
, (void (*)(void))ossl_chacha20_dinit
},
213 { OSSL_FUNC_CIPHER_UPDATE
, (void (*)(void))chacha20_update
},
214 { OSSL_FUNC_CIPHER_FINAL
, (void (*)(void))chacha20_final
},
215 { OSSL_FUNC_CIPHER_CIPHER
, (void (*)(void))chacha20_cipher
},
216 { OSSL_FUNC_CIPHER_GET_PARAMS
, (void (*)(void))chacha20_get_params
},
217 { OSSL_FUNC_CIPHER_GETTABLE_PARAMS
, (void (*)(void))chacha20_gettable_params
},
218 { OSSL_FUNC_CIPHER_GET_CTX_PARAMS
, (void (*)(void))chacha20_get_ctx_params
},
219 { OSSL_FUNC_CIPHER_GETTABLE_CTX_PARAMS
,
220 (void (*)(void))chacha20_gettable_ctx_params
},
221 { OSSL_FUNC_CIPHER_SET_CTX_PARAMS
, (void (*)(void))chacha20_set_ctx_params
},
222 { OSSL_FUNC_CIPHER_SETTABLE_CTX_PARAMS
,
223 (void (*)(void))chacha20_settable_ctx_params
},