From a305b6bb858897088d303c09c432a287a167645c Mon Sep 17 00:00:00 2001 From: Julian Arevalo Date: Mon, 7 Oct 2024 18:06:44 +0200 Subject: [PATCH] cx_aes_siv: Add new function to reset AES hw copro Update the syscall to have a signature that return an error that may be useful depending on the HW. --- include/cx_stubs.h | 1 + include/ox_aes.h | 2 +- lib_cxng/cx.export | 1 + lib_cxng/include/lcx_aes_siv.h | 11 +++++++++++ lib_cxng/src/cx_aes.c | 11 +++++++---- lib_cxng/src/cx_aes_siv.c | 23 ++++++++++++++++++++--- lib_cxng/src/cx_cipher.h | 2 +- src/cx_stubs.S | 1 + src/syscalls.c | 4 ++-- 9 files changed, 45 insertions(+), 11 deletions(-) diff --git a/include/cx_stubs.h b/include/cx_stubs.h index b0d5a5e7e..40ec737dd 100644 --- a/include/cx_stubs.h +++ b/include/cx_stubs.h @@ -145,3 +145,4 @@ #define _NR_cx_cmac_start 0x8d #define _NR_cx_cmac_update 0x8e #define _NR_cx_cmac_finish 0x8f +#define _NR_cx_aes_siv_reset 0x90 diff --git a/include/ox_aes.h b/include/ox_aes.h index f09cf751d..2ee7b87f8 100644 --- a/include/ox_aes.h +++ b/include/ox_aes.h @@ -99,7 +99,7 @@ cx_aes_set_key_hw(const cx_aes_key_t *key PLENGTH(sizeof(cx_aes_key_t)), uint32_ /** * @brief Resets the AES context. */ -SYSCALL void cx_aes_reset_hw(void); +SYSCALL cx_err_t cx_aes_reset_hw(void); /** * @brief Encrypts or decrypts a block with AES. diff --git a/lib_cxng/cx.export b/lib_cxng/cx.export index 19d47e726..b935b75ff 100644 --- a/lib_cxng/cx.export +++ b/lib_cxng/cx.export @@ -148,3 +148,4 @@ cx_cipher_reset cx_cmac_start cx_cmac_update cx_cmac_finish +cx_aes_siv_reset diff --git a/lib_cxng/include/lcx_aes_siv.h b/lib_cxng/include/lcx_aes_siv.h index 06905dc69..b4db323b2 100644 --- a/lib_cxng/include/lcx_aes_siv.h +++ b/lib_cxng/include/lcx_aes_siv.h @@ -55,6 +55,17 @@ typedef struct _cx_aes_siv_context { */ WARN_UNUSED_RESULT cx_err_t cx_aes_siv_init(cx_aes_siv_context_t *ctx); +/** + * @brief Reset the AES-SIV context and HW used. + * @details The cipher context must be initialized beforehand. + * This function must be called after calls to #cx_aes_siv_finish or + * #cx_aes_siv_update. + * + * @param[in] ctx Pointer to the AES-SIV context. + * @return Error code. + */ +WARN_UNUSED_RESULT cx_err_t cx_aes_siv_reset(cx_aes_siv_context_t *ctx); + /** * @brief Sets the key to compute AES-SIV. * diff --git a/lib_cxng/src/cx_aes.c b/lib_cxng/src/cx_aes.c index 338f5386c..49dd20cdd 100644 --- a/lib_cxng/src/cx_aes.c +++ b/lib_cxng/src/cx_aes.c @@ -28,21 +28,24 @@ cx_err_t cx_aes_init_key_no_throw(const uint8_t *raw_key, size_t key_len, cx_aes cx_err_t cx_aes_enc_block(const cx_aes_key_t *key, const uint8_t *inblock, uint8_t *outblock) { cx_err_t error; + cx_err_t err_reset = CX_INTERNAL_ERROR; CX_CHECK(cx_aes_set_key_hw(key, CX_ENCRYPT)); CX_CHECK(cx_aes_block_hw(inblock, outblock)); - cx_aes_reset_hw(); end: - return error; + err_reset = cx_aes_reset_hw(); + return error == CX_OK ? err_reset : error; } cx_err_t cx_aes_dec_block(const cx_aes_key_t *key, const uint8_t *inblock, uint8_t *outblock) { cx_err_t error; + cx_err_t err_reset = CX_INTERNAL_ERROR; + CX_CHECK(cx_aes_set_key_hw(key, CX_ENCRYPT)); CX_CHECK(cx_aes_set_key_hw(key, CX_DECRYPT)); CX_CHECK(cx_aes_block_hw(inblock, outblock)); - cx_aes_reset_hw(); end: - return error; + err_reset = cx_aes_reset_hw(); + return error == CX_OK ? err_reset : error; } cx_err_t cx_aes_iv_no_throw(const cx_aes_key_t *key, diff --git a/lib_cxng/src/cx_aes_siv.c b/lib_cxng/src/cx_aes_siv.c index ed106d3dd..e7d8fd762 100644 --- a/lib_cxng/src/cx_aes_siv.c +++ b/lib_cxng/src/cx_aes_siv.c @@ -22,6 +22,19 @@ cx_err_t cx_aes_siv_init(cx_aes_siv_context_t *ctx) return error; } +cx_err_t cx_aes_siv_reset(cx_aes_siv_context_t *ctx) +{ + cx_err_t error = CX_INVALID_PARAMETER_VALUE; + if (ctx->cipher_ctx == NULL) { + goto end; + } + CX_CHECK(ctx->cipher_ctx->cipher_info->base->ctx_reset()); + cx_cipher_reset(ctx->cipher_ctx); + +end: + return error; +} + cx_err_t cx_aes_siv_set_key(cx_aes_siv_context_t *ctx, const uint8_t *key, size_t key_bitlen) { // AES SIV uses two keys of either 128, 192 or 256 bits each @@ -156,12 +169,14 @@ cx_err_t cx_aes_siv_encrypt(cx_aes_siv_context_t *ctx, uint8_t *tag) { cx_err_t error; + cx_err_t err_reset = CX_INTERNAL_ERROR; CX_CHECK(cx_aes_siv_start(ctx, CX_ENCRYPT, NULL, 0)); CX_CHECK(cx_aes_siv_update_aad(ctx, aad, aad_len)); CX_CHECK(cx_aes_siv_finish(ctx, input, in_len, tag)); CX_CHECK(cx_aes_siv_update(ctx, input, output, in_len)); end: - return error; + err_reset = cx_aes_siv_reset(ctx); + return error == CX_OK ? err_reset : error; } cx_err_t cx_aes_siv_decrypt(cx_aes_siv_context_t *ctx, @@ -173,14 +188,16 @@ cx_err_t cx_aes_siv_decrypt(cx_aes_siv_context_t *ctx, uint8_t *tag) { cx_err_t error; + cx_err_t err_reset = CX_INTERNAL_ERROR; CX_CHECK(cx_aes_siv_start(ctx, CX_DECRYPT, tag, CX_AES_BLOCK_SIZE)); CX_CHECK(cx_aes_siv_update(ctx, input, output, in_len)); - cx_cipher_reset(ctx->cipher_ctx); + CX_CHECK(cx_aes_siv_reset(ctx)); CX_CHECK(cx_aes_siv_update_aad(ctx, aad, aad_len)); CX_CHECK(cx_aes_siv_finish(ctx, output, in_len, tag)); end: - return error; + err_reset = cx_aes_siv_reset(ctx); + return error == CX_OK ? err_reset : error; } #endif // HAVE_AES && HAVE_CMAC diff --git a/lib_cxng/src/cx_cipher.h b/lib_cxng/src/cx_cipher.h index 88eddd8a6..7b8741a25 100644 --- a/lib_cxng/src/cx_cipher.h +++ b/lib_cxng/src/cx_cipher.h @@ -31,7 +31,7 @@ extern const cx_cipher_info_t cx_aes_256_info; /** HW support */ WARN_UNUSED_RESULT cx_err_t cx_aes_set_key_hw(const cx_aes_key_t *keys, uint32_t mode); WARN_UNUSED_RESULT cx_err_t cx_aes_block_hw(const uint8_t *inblock, uint8_t *outblock); -void cx_aes_reset_hw(void); +WARN_UNUSED_RESULT cx_err_t cx_aes_reset_hw(void); #endif // HAVE_AES #endif /* CX_CIPHER_H */ diff --git a/src/cx_stubs.S b/src/cx_stubs.S index 49d1ade68..c4ab57a23 100644 --- a/src/cx_stubs.S +++ b/src/cx_stubs.S @@ -160,6 +160,7 @@ CX_TRAMPOLINE _NR_cx_cipher_reset cx_cipher_reset CX_TRAMPOLINE _NR_cx_cmac_start cx_cmac_start CX_TRAMPOLINE _NR_cx_cmac_update cx_cmac_update CX_TRAMPOLINE _NR_cx_cmac_finish cx_cmac_finish +CX_TRAMPOLINE _NR_cx_aes_siv_reset cx_aes_siv_reset .thumb_func cx_trampoline_helper: diff --git a/src/syscalls.c b/src/syscalls.c index c32c1f1c0..3e8b5edc3 100644 --- a/src/syscalls.c +++ b/src/syscalls.c @@ -252,11 +252,11 @@ cx_err_t cx_aes_set_key_hw(const cx_aes_key_t *keys, uint32_t mode) return SVC_cx_call(SYSCALL_cx_aes_set_key_hw_ID, parameters); } -void cx_aes_reset_hw(void) +cx_err_t cx_aes_reset_hw(void) { unsigned int parameters[2]; parameters[1] = 0; - SVC_cx_call(SYSCALL_cx_aes_reset_hw_ID, parameters); + return SVC_cx_call(SYSCALL_cx_aes_reset_hw_ID, parameters); } cx_err_t cx_aes_block_hw(const unsigned char *inblock, unsigned char *outblock)