1 /*
2 * PSA hashing layer on top of Mbed TLS software crypto
3 */
4 /*
5 * Copyright The Mbed TLS Contributors
6 * SPDX-License-Identifier: Apache-2.0 OR GPL-2.0-or-later
7 */
8
9 #include "common.h"
10
11 #if defined(MBEDTLS_PSA_CRYPTO_C)
12
13 #include <psa/crypto.h>
14 #include "psa_crypto_core.h"
15 #include "psa_crypto_hash.h"
16
17 #include <mbedtls/error.h>
18 #include <string.h>
19
20 #if defined(MBEDTLS_PSA_BUILTIN_HASH)
mbedtls_psa_hash_abort(mbedtls_psa_hash_operation_t * operation)21 psa_status_t mbedtls_psa_hash_abort(
22 mbedtls_psa_hash_operation_t *operation)
23 {
24 switch (operation->alg) {
25 case 0:
26 /* The object has (apparently) been initialized but it is not
27 * in use. It's ok to call abort on such an object, and there's
28 * nothing to do. */
29 break;
30 #if defined(MBEDTLS_PSA_BUILTIN_ALG_MD5)
31 case PSA_ALG_MD5:
32 mbedtls_md5_free(&operation->ctx.md5);
33 break;
34 #endif
35 #if defined(MBEDTLS_PSA_BUILTIN_ALG_RIPEMD160)
36 case PSA_ALG_RIPEMD160:
37 mbedtls_ripemd160_free(&operation->ctx.ripemd160);
38 break;
39 #endif
40 #if defined(MBEDTLS_PSA_BUILTIN_ALG_SHA_1)
41 case PSA_ALG_SHA_1:
42 mbedtls_sha1_free(&operation->ctx.sha1);
43 break;
44 #endif
45 #if defined(MBEDTLS_PSA_BUILTIN_ALG_SHA_224)
46 case PSA_ALG_SHA_224:
47 mbedtls_sha256_free(&operation->ctx.sha256);
48 break;
49 #endif
50 #if defined(MBEDTLS_PSA_BUILTIN_ALG_SHA_256)
51 case PSA_ALG_SHA_256:
52 mbedtls_sha256_free(&operation->ctx.sha256);
53 break;
54 #endif
55 #if defined(MBEDTLS_PSA_BUILTIN_ALG_SHA_384)
56 case PSA_ALG_SHA_384:
57 mbedtls_sha512_free(&operation->ctx.sha512);
58 break;
59 #endif
60 #if defined(MBEDTLS_PSA_BUILTIN_ALG_SHA_512)
61 case PSA_ALG_SHA_512:
62 mbedtls_sha512_free(&operation->ctx.sha512);
63 break;
64 #endif
65 #if defined(MBEDTLS_PSA_BUILTIN_ALG_SHA3_224)
66 case PSA_ALG_SHA3_224:
67 #endif
68 #if defined(MBEDTLS_PSA_BUILTIN_ALG_SHA3_256)
69 case PSA_ALG_SHA3_256:
70 #endif
71 #if defined(MBEDTLS_PSA_BUILTIN_ALG_SHA3_384)
72 case PSA_ALG_SHA3_384:
73 #endif
74 #if defined(MBEDTLS_PSA_BUILTIN_ALG_SHA3_512)
75 case PSA_ALG_SHA3_512:
76 #endif
77 #if defined(MBEDTLS_PSA_BUILTIN_ALG_SHA3_224) || \
78 defined(MBEDTLS_PSA_BUILTIN_ALG_SHA3_256) || \
79 defined(MBEDTLS_PSA_BUILTIN_ALG_SHA3_384) || \
80 defined(MBEDTLS_PSA_BUILTIN_ALG_SHA3_512)
81 mbedtls_sha3_free(&operation->ctx.sha3);
82 break;
83 #endif
84 default:
85 return PSA_ERROR_BAD_STATE;
86 }
87 operation->alg = 0;
88 return PSA_SUCCESS;
89 }
90
mbedtls_psa_hash_setup(mbedtls_psa_hash_operation_t * operation,psa_algorithm_t alg)91 psa_status_t mbedtls_psa_hash_setup(
92 mbedtls_psa_hash_operation_t *operation,
93 psa_algorithm_t alg)
94 {
95 int ret = MBEDTLS_ERR_ERROR_CORRUPTION_DETECTED;
96
97 /* A context must be freshly initialized before it can be set up. */
98 if (operation->alg != 0) {
99 return PSA_ERROR_BAD_STATE;
100 }
101
102 switch (alg) {
103 #if defined(MBEDTLS_PSA_BUILTIN_ALG_MD5)
104 case PSA_ALG_MD5:
105 mbedtls_md5_init(&operation->ctx.md5);
106 ret = mbedtls_md5_starts(&operation->ctx.md5);
107 break;
108 #endif
109 #if defined(MBEDTLS_PSA_BUILTIN_ALG_RIPEMD160)
110 case PSA_ALG_RIPEMD160:
111 mbedtls_ripemd160_init(&operation->ctx.ripemd160);
112 ret = mbedtls_ripemd160_starts(&operation->ctx.ripemd160);
113 break;
114 #endif
115 #if defined(MBEDTLS_PSA_BUILTIN_ALG_SHA_1)
116 case PSA_ALG_SHA_1:
117 mbedtls_sha1_init(&operation->ctx.sha1);
118 ret = mbedtls_sha1_starts(&operation->ctx.sha1);
119 break;
120 #endif
121 #if defined(MBEDTLS_PSA_BUILTIN_ALG_SHA_224)
122 case PSA_ALG_SHA_224:
123 mbedtls_sha256_init(&operation->ctx.sha256);
124 ret = mbedtls_sha256_starts(&operation->ctx.sha256, 1);
125 break;
126 #endif
127 #if defined(MBEDTLS_PSA_BUILTIN_ALG_SHA_256)
128 case PSA_ALG_SHA_256:
129 mbedtls_sha256_init(&operation->ctx.sha256);
130 ret = mbedtls_sha256_starts(&operation->ctx.sha256, 0);
131 break;
132 #endif
133 #if defined(MBEDTLS_PSA_BUILTIN_ALG_SHA_384)
134 case PSA_ALG_SHA_384:
135 mbedtls_sha512_init(&operation->ctx.sha512);
136 ret = mbedtls_sha512_starts(&operation->ctx.sha512, 1);
137 break;
138 #endif
139 #if defined(MBEDTLS_PSA_BUILTIN_ALG_SHA_512)
140 case PSA_ALG_SHA_512:
141 mbedtls_sha512_init(&operation->ctx.sha512);
142 ret = mbedtls_sha512_starts(&operation->ctx.sha512, 0);
143 break;
144 #endif
145 #if defined(MBEDTLS_PSA_BUILTIN_ALG_SHA3_224)
146 case PSA_ALG_SHA3_224:
147 mbedtls_sha3_init(&operation->ctx.sha3);
148 ret = mbedtls_sha3_starts(&operation->ctx.sha3, MBEDTLS_SHA3_224);
149 break;
150 #endif
151 #if defined(MBEDTLS_PSA_BUILTIN_ALG_SHA3_256)
152 case PSA_ALG_SHA3_256:
153 mbedtls_sha3_init(&operation->ctx.sha3);
154 ret = mbedtls_sha3_starts(&operation->ctx.sha3, MBEDTLS_SHA3_256);
155 break;
156 #endif
157 #if defined(MBEDTLS_PSA_BUILTIN_ALG_SHA3_384)
158 case PSA_ALG_SHA3_384:
159 mbedtls_sha3_init(&operation->ctx.sha3);
160 ret = mbedtls_sha3_starts(&operation->ctx.sha3, MBEDTLS_SHA3_384);
161 break;
162 #endif
163 #if defined(MBEDTLS_PSA_BUILTIN_ALG_SHA3_512)
164 case PSA_ALG_SHA3_512:
165 mbedtls_sha3_init(&operation->ctx.sha3);
166 ret = mbedtls_sha3_starts(&operation->ctx.sha3, MBEDTLS_SHA3_512);
167 break;
168 #endif
169 default:
170 return PSA_ALG_IS_HASH(alg) ?
171 PSA_ERROR_NOT_SUPPORTED :
172 PSA_ERROR_INVALID_ARGUMENT;
173 }
174 if (ret == 0) {
175 operation->alg = alg;
176 } else {
177 mbedtls_psa_hash_abort(operation);
178 }
179 return mbedtls_to_psa_error(ret);
180 }
181
mbedtls_psa_hash_clone(const mbedtls_psa_hash_operation_t * source_operation,mbedtls_psa_hash_operation_t * target_operation)182 psa_status_t mbedtls_psa_hash_clone(
183 const mbedtls_psa_hash_operation_t *source_operation,
184 mbedtls_psa_hash_operation_t *target_operation)
185 {
186 switch (source_operation->alg) {
187 case 0:
188 return PSA_ERROR_BAD_STATE;
189 #if defined(MBEDTLS_PSA_BUILTIN_ALG_MD5)
190 case PSA_ALG_MD5:
191 mbedtls_md5_clone(&target_operation->ctx.md5,
192 &source_operation->ctx.md5);
193 break;
194 #endif
195 #if defined(MBEDTLS_PSA_BUILTIN_ALG_RIPEMD160)
196 case PSA_ALG_RIPEMD160:
197 mbedtls_ripemd160_clone(&target_operation->ctx.ripemd160,
198 &source_operation->ctx.ripemd160);
199 break;
200 #endif
201 #if defined(MBEDTLS_PSA_BUILTIN_ALG_SHA_1)
202 case PSA_ALG_SHA_1:
203 mbedtls_sha1_clone(&target_operation->ctx.sha1,
204 &source_operation->ctx.sha1);
205 break;
206 #endif
207 #if defined(MBEDTLS_PSA_BUILTIN_ALG_SHA_224)
208 case PSA_ALG_SHA_224:
209 mbedtls_sha256_clone(&target_operation->ctx.sha256,
210 &source_operation->ctx.sha256);
211 break;
212 #endif
213 #if defined(MBEDTLS_PSA_BUILTIN_ALG_SHA_256)
214 case PSA_ALG_SHA_256:
215 mbedtls_sha256_clone(&target_operation->ctx.sha256,
216 &source_operation->ctx.sha256);
217 break;
218 #endif
219 #if defined(MBEDTLS_PSA_BUILTIN_ALG_SHA_384)
220 case PSA_ALG_SHA_384:
221 mbedtls_sha512_clone(&target_operation->ctx.sha512,
222 &source_operation->ctx.sha512);
223 break;
224 #endif
225 #if defined(MBEDTLS_PSA_BUILTIN_ALG_SHA_512)
226 case PSA_ALG_SHA_512:
227 mbedtls_sha512_clone(&target_operation->ctx.sha512,
228 &source_operation->ctx.sha512);
229 break;
230 #endif
231 #if defined(MBEDTLS_PSA_BUILTIN_ALG_SHA3_224)
232 case PSA_ALG_SHA3_224:
233 #endif
234 #if defined(MBEDTLS_PSA_BUILTIN_ALG_SHA3_256)
235 case PSA_ALG_SHA3_256:
236 #endif
237 #if defined(MBEDTLS_PSA_BUILTIN_ALG_SHA3_384)
238 case PSA_ALG_SHA3_384:
239 #endif
240 #if defined(MBEDTLS_PSA_BUILTIN_ALG_SHA3_512)
241 case PSA_ALG_SHA3_512:
242 #endif
243 #if defined(MBEDTLS_PSA_BUILTIN_ALG_SHA3_224) || \
244 defined(MBEDTLS_PSA_BUILTIN_ALG_SHA3_256) || \
245 defined(MBEDTLS_PSA_BUILTIN_ALG_SHA3_384) || \
246 defined(MBEDTLS_PSA_BUILTIN_ALG_SHA3_512)
247 mbedtls_sha3_clone(&target_operation->ctx.sha3,
248 &source_operation->ctx.sha3);
249 break;
250 #endif
251 default:
252 (void) source_operation;
253 (void) target_operation;
254 return PSA_ERROR_NOT_SUPPORTED;
255 }
256
257 target_operation->alg = source_operation->alg;
258 return PSA_SUCCESS;
259 }
260
mbedtls_psa_hash_update(mbedtls_psa_hash_operation_t * operation,const uint8_t * input,size_t input_length)261 psa_status_t mbedtls_psa_hash_update(
262 mbedtls_psa_hash_operation_t *operation,
263 const uint8_t *input,
264 size_t input_length)
265 {
266 int ret = MBEDTLS_ERR_ERROR_CORRUPTION_DETECTED;
267
268 switch (operation->alg) {
269 #if defined(MBEDTLS_PSA_BUILTIN_ALG_MD5)
270 case PSA_ALG_MD5:
271 ret = mbedtls_md5_update(&operation->ctx.md5,
272 input, input_length);
273 break;
274 #endif
275 #if defined(MBEDTLS_PSA_BUILTIN_ALG_RIPEMD160)
276 case PSA_ALG_RIPEMD160:
277 ret = mbedtls_ripemd160_update(&operation->ctx.ripemd160,
278 input, input_length);
279 break;
280 #endif
281 #if defined(MBEDTLS_PSA_BUILTIN_ALG_SHA_1)
282 case PSA_ALG_SHA_1:
283 ret = mbedtls_sha1_update(&operation->ctx.sha1,
284 input, input_length);
285 break;
286 #endif
287 #if defined(MBEDTLS_PSA_BUILTIN_ALG_SHA_224)
288 case PSA_ALG_SHA_224:
289 ret = mbedtls_sha256_update(&operation->ctx.sha256,
290 input, input_length);
291 break;
292 #endif
293 #if defined(MBEDTLS_PSA_BUILTIN_ALG_SHA_256)
294 case PSA_ALG_SHA_256:
295 ret = mbedtls_sha256_update(&operation->ctx.sha256,
296 input, input_length);
297 break;
298 #endif
299 #if defined(MBEDTLS_PSA_BUILTIN_ALG_SHA_384)
300 case PSA_ALG_SHA_384:
301 ret = mbedtls_sha512_update(&operation->ctx.sha512,
302 input, input_length);
303 break;
304 #endif
305 #if defined(MBEDTLS_PSA_BUILTIN_ALG_SHA_512)
306 case PSA_ALG_SHA_512:
307 ret = mbedtls_sha512_update(&operation->ctx.sha512,
308 input, input_length);
309 break;
310 #endif
311 #if defined(MBEDTLS_PSA_BUILTIN_ALG_SHA3_224)
312 case PSA_ALG_SHA3_224:
313 #endif
314 #if defined(MBEDTLS_PSA_BUILTIN_ALG_SHA3_256)
315 case PSA_ALG_SHA3_256:
316 #endif
317 #if defined(MBEDTLS_PSA_BUILTIN_ALG_SHA3_384)
318 case PSA_ALG_SHA3_384:
319 #endif
320 #if defined(MBEDTLS_PSA_BUILTIN_ALG_SHA3_512)
321 case PSA_ALG_SHA3_512:
322 #endif
323 #if defined(MBEDTLS_PSA_BUILTIN_ALG_SHA3_224) || \
324 defined(MBEDTLS_PSA_BUILTIN_ALG_SHA3_256) || \
325 defined(MBEDTLS_PSA_BUILTIN_ALG_SHA3_384) || \
326 defined(MBEDTLS_PSA_BUILTIN_ALG_SHA3_512)
327 ret = mbedtls_sha3_update(&operation->ctx.sha3,
328 input, input_length);
329 break;
330 #endif
331 default:
332 (void) input;
333 (void) input_length;
334 return PSA_ERROR_BAD_STATE;
335 }
336
337 return mbedtls_to_psa_error(ret);
338 }
339
mbedtls_psa_hash_finish(mbedtls_psa_hash_operation_t * operation,uint8_t * hash,size_t hash_size,size_t * hash_length)340 psa_status_t mbedtls_psa_hash_finish(
341 mbedtls_psa_hash_operation_t *operation,
342 uint8_t *hash,
343 size_t hash_size,
344 size_t *hash_length)
345 {
346 psa_status_t status;
347 int ret = MBEDTLS_ERR_ERROR_CORRUPTION_DETECTED;
348 size_t actual_hash_length = PSA_HASH_LENGTH(operation->alg);
349
350 /* Fill the output buffer with something that isn't a valid hash
351 * (barring an attack on the hash and deliberately-crafted input),
352 * in case the caller doesn't check the return status properly. */
353 *hash_length = hash_size;
354 /* If hash_size is 0 then hash may be NULL and then the
355 * call to memset would have undefined behavior. */
356 if (hash_size != 0) {
357 memset(hash, '!', hash_size);
358 }
359
360 if (hash_size < actual_hash_length) {
361 status = PSA_ERROR_BUFFER_TOO_SMALL;
362 goto exit;
363 }
364
365 switch (operation->alg) {
366 #if defined(MBEDTLS_PSA_BUILTIN_ALG_MD5)
367 case PSA_ALG_MD5:
368 ret = mbedtls_md5_finish(&operation->ctx.md5, hash);
369 break;
370 #endif
371 #if defined(MBEDTLS_PSA_BUILTIN_ALG_RIPEMD160)
372 case PSA_ALG_RIPEMD160:
373 ret = mbedtls_ripemd160_finish(&operation->ctx.ripemd160, hash);
374 break;
375 #endif
376 #if defined(MBEDTLS_PSA_BUILTIN_ALG_SHA_1)
377 case PSA_ALG_SHA_1:
378 ret = mbedtls_sha1_finish(&operation->ctx.sha1, hash);
379 break;
380 #endif
381 #if defined(MBEDTLS_PSA_BUILTIN_ALG_SHA_224)
382 case PSA_ALG_SHA_224:
383 ret = mbedtls_sha256_finish(&operation->ctx.sha256, hash);
384 break;
385 #endif
386 #if defined(MBEDTLS_PSA_BUILTIN_ALG_SHA_256)
387 case PSA_ALG_SHA_256:
388 ret = mbedtls_sha256_finish(&operation->ctx.sha256, hash);
389 break;
390 #endif
391 #if defined(MBEDTLS_PSA_BUILTIN_ALG_SHA_384)
392 case PSA_ALG_SHA_384:
393 ret = mbedtls_sha512_finish(&operation->ctx.sha512, hash);
394 break;
395 #endif
396 #if defined(MBEDTLS_PSA_BUILTIN_ALG_SHA_512)
397 case PSA_ALG_SHA_512:
398 ret = mbedtls_sha512_finish(&operation->ctx.sha512, hash);
399 break;
400 #endif
401 #if defined(MBEDTLS_PSA_BUILTIN_ALG_SHA3_224)
402 case PSA_ALG_SHA3_224:
403 #endif
404 #if defined(MBEDTLS_PSA_BUILTIN_ALG_SHA3_256)
405 case PSA_ALG_SHA3_256:
406 #endif
407 #if defined(MBEDTLS_PSA_BUILTIN_ALG_SHA3_384)
408 case PSA_ALG_SHA3_384:
409 #endif
410 #if defined(MBEDTLS_PSA_BUILTIN_ALG_SHA3_512)
411 case PSA_ALG_SHA3_512:
412 #endif
413 #if defined(MBEDTLS_PSA_BUILTIN_ALG_SHA3_224) || \
414 defined(MBEDTLS_PSA_BUILTIN_ALG_SHA3_256) || \
415 defined(MBEDTLS_PSA_BUILTIN_ALG_SHA3_384) || \
416 defined(MBEDTLS_PSA_BUILTIN_ALG_SHA3_512)
417 ret = mbedtls_sha3_finish(&operation->ctx.sha3, hash, hash_size);
418 break;
419 #endif
420 default:
421 (void) hash;
422 return PSA_ERROR_BAD_STATE;
423 }
424 status = mbedtls_to_psa_error(ret);
425
426 exit:
427 if (status == PSA_SUCCESS) {
428 *hash_length = actual_hash_length;
429 }
430 return status;
431 }
432
mbedtls_psa_hash_compute(psa_algorithm_t alg,const uint8_t * input,size_t input_length,uint8_t * hash,size_t hash_size,size_t * hash_length)433 psa_status_t mbedtls_psa_hash_compute(
434 psa_algorithm_t alg,
435 const uint8_t *input,
436 size_t input_length,
437 uint8_t *hash,
438 size_t hash_size,
439 size_t *hash_length)
440 {
441 mbedtls_psa_hash_operation_t operation = MBEDTLS_PSA_HASH_OPERATION_INIT;
442 psa_status_t status = PSA_ERROR_CORRUPTION_DETECTED;
443 psa_status_t abort_status = PSA_ERROR_CORRUPTION_DETECTED;
444
445 *hash_length = hash_size;
446 status = mbedtls_psa_hash_setup(&operation, alg);
447 if (status != PSA_SUCCESS) {
448 goto exit;
449 }
450 status = mbedtls_psa_hash_update(&operation, input, input_length);
451 if (status != PSA_SUCCESS) {
452 goto exit;
453 }
454 status = mbedtls_psa_hash_finish(&operation, hash, hash_size, hash_length);
455 if (status != PSA_SUCCESS) {
456 goto exit;
457 }
458
459 exit:
460 abort_status = mbedtls_psa_hash_abort(&operation);
461 if (status == PSA_SUCCESS) {
462 return abort_status;
463 } else {
464 return status;
465 }
466
467 }
468 #endif /* MBEDTLS_PSA_BUILTIN_HASH */
469
470 #endif /* MBEDTLS_PSA_CRYPTO_C */
471