Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[crypto] Pass buffers by value. #20891

Merged
merged 4 commits into from
Jan 25, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
73 changes: 35 additions & 38 deletions sw/device/lib/crypto/impl/aes.c
Original file line number Diff line number Diff line change
Expand Up @@ -574,31 +574,30 @@ otcrypto_status_t otcrypto_aes_gcm_encrypt(const otcrypto_blinded_key_t *key,
otcrypto_const_word32_buf_t iv,
otcrypto_const_byte_buf_t aad,
otcrypto_aes_gcm_tag_len_t tag_len,
otcrypto_byte_buf_t *ciphertext,
otcrypto_word32_buf_t *auth_tag) {
otcrypto_byte_buf_t ciphertext,
otcrypto_word32_buf_t auth_tag) {
// Check for NULL pointers in input pointers and required-nonzero-length data
// buffers.
if (key == NULL || iv.data == NULL || ciphertext == NULL ||
auth_tag == NULL || auth_tag->data == NULL) {
if (key == NULL || iv.data == NULL || auth_tag.data == NULL) {
return OTCRYPTO_BAD_ARGS;
}

// Conditionally check for null pointers in data buffers that may be
// 0-length.
if ((aad.len != 0 && aad.data == NULL) ||
(ciphertext->len != 0 && ciphertext->data == NULL) ||
(ciphertext.len != 0 && ciphertext.data == NULL) ||
(plaintext.len != 0 && plaintext.data == NULL)) {
return OTCRYPTO_BAD_ARGS;
}

// Ensure the plaintext and ciphertext lengths match.
if (launder32(ciphertext->len) != plaintext.len) {
if (launder32(ciphertext.len) != plaintext.len) {
return OTCRYPTO_BAD_ARGS;
}
HARDENED_CHECK_EQ(ciphertext->len, plaintext.len);
HARDENED_CHECK_EQ(ciphertext.len, plaintext.len);

// Check the tag length.
HARDENED_TRY(aes_gcm_check_tag_length(auth_tag->len, tag_len));
HARDENED_TRY(aes_gcm_check_tag_length(auth_tag.len, tag_len));

// Construct the AES key.
aes_key_t aes_key;
Expand All @@ -607,8 +606,8 @@ otcrypto_status_t otcrypto_aes_gcm_encrypt(const otcrypto_blinded_key_t *key,

// Call the core encryption operation.
HARDENED_TRY(aes_gcm_encrypt(aes_key, iv.len, iv.data, plaintext.len,
plaintext.data, aad.len, aad.data, auth_tag->len,
auth_tag->data, ciphertext->data));
plaintext.data, aad.len, aad.data, auth_tag.len,
auth_tag.data, ciphertext.data));

HARDENED_TRY(clear_key_if_sideloaded(aes_key));
return OTCRYPTO_OK;
Expand All @@ -618,19 +617,18 @@ otcrypto_status_t otcrypto_aes_gcm_decrypt(
const otcrypto_blinded_key_t *key, otcrypto_const_byte_buf_t ciphertext,
otcrypto_const_word32_buf_t iv, otcrypto_const_byte_buf_t aad,
otcrypto_aes_gcm_tag_len_t tag_len, otcrypto_const_word32_buf_t auth_tag,
otcrypto_byte_buf_t *plaintext, hardened_bool_t *success) {
otcrypto_byte_buf_t plaintext, hardened_bool_t *success) {
// Check for NULL pointers in input pointers and required-nonzero-length data
// buffers.
if (key == NULL || iv.data == NULL || plaintext == NULL ||
auth_tag.data == NULL) {
if (key == NULL || iv.data == NULL || auth_tag.data == NULL) {
return OTCRYPTO_BAD_ARGS;
}

// Conditionally check for null pointers in data buffers that may be
// 0-length.
if ((aad.len != 0 && aad.data == NULL) ||
(ciphertext.len != 0 && ciphertext.data == NULL) ||
(plaintext->len != 0 && plaintext->data == NULL)) {
(plaintext.len != 0 && plaintext.data == NULL)) {
return OTCRYPTO_BAD_ARGS;
}

Expand All @@ -640,18 +638,18 @@ otcrypto_status_t otcrypto_aes_gcm_decrypt(
HARDENED_TRY(load_key_if_sideloaded(aes_key));

// Ensure the plaintext and ciphertext lengths match.
if (launder32(ciphertext.len) != plaintext->len) {
if (launder32(ciphertext.len) != plaintext.len) {
return OTCRYPTO_BAD_ARGS;
}
HARDENED_CHECK_EQ(ciphertext.len, plaintext->len);
HARDENED_CHECK_EQ(ciphertext.len, plaintext.len);

// Check the tag length.
HARDENED_TRY(aes_gcm_check_tag_length(auth_tag.len, tag_len));

// Call the core decryption operation.
HARDENED_TRY(aes_gcm_decrypt(aes_key, iv.len, iv.data, ciphertext.len,
ciphertext.data, aad.len, aad.data, auth_tag.len,
auth_tag.data, plaintext->data, success));
auth_tag.data, plaintext.data, success));

HARDENED_TRY(clear_key_if_sideloaded(aes_key));
return OTCRYPTO_OK;
Expand Down Expand Up @@ -770,19 +768,19 @@ otcrypto_status_t otcrypto_aes_gcm_update_encrypted_data(

otcrypto_status_t otcrypto_aes_gcm_encrypt_final(
otcrypto_aes_gcm_context_t *ctx, otcrypto_aes_gcm_tag_len_t tag_len,
otcrypto_byte_buf_t *ciphertext, size_t *ciphertext_bytes_written,
otcrypto_word32_buf_t *auth_tag) {
if (ctx == NULL || ciphertext == NULL || ciphertext_bytes_written == NULL ||
auth_tag == NULL || auth_tag->data == NULL) {
otcrypto_byte_buf_t ciphertext, size_t *ciphertext_bytes_written,
otcrypto_word32_buf_t auth_tag) {
if (ctx == NULL || ciphertext_bytes_written == NULL ||
auth_tag.data == NULL) {
return OTCRYPTO_BAD_ARGS;
}
if (ciphertext->len != 0 && ciphertext->data == NULL) {
if (ciphertext.len != 0 && ciphertext.data == NULL) {
return OTCRYPTO_BAD_ARGS;
}
*ciphertext_bytes_written = 0;

// Check the tag length.
HARDENED_TRY(aes_gcm_check_tag_length(auth_tag->len, tag_len));
HARDENED_TRY(aes_gcm_check_tag_length(auth_tag.len, tag_len));

// Restore the AES-GCM context object and load the key if needed.
aes_gcm_context_t internal_ctx;
Expand All @@ -792,14 +790,14 @@ otcrypto_status_t otcrypto_aes_gcm_encrypt_final(
// If the partial block is nonempty, the output must be at least as long as
// the partial block.
size_t partial_block_len = internal_ctx.input_len % kAesBlockNumBytes;
if (ciphertext->len < partial_block_len) {
if (ciphertext.len < partial_block_len) {
return OTCRYPTO_BAD_ARGS;
}

// Call the internal final operation.
HARDENED_TRY(aes_gcm_encrypt_final(&internal_ctx, auth_tag->len,
auth_tag->data, ciphertext_bytes_written,
ciphertext->data));
HARDENED_TRY(aes_gcm_encrypt_final(&internal_ctx, auth_tag.len, auth_tag.data,
ciphertext_bytes_written,
ciphertext.data));

// Clear the context and the key if needed.
hardened_memshred(ctx->data, ARRAYSIZE(ctx->data));
Expand All @@ -809,13 +807,13 @@ otcrypto_status_t otcrypto_aes_gcm_encrypt_final(

otcrypto_status_t otcrypto_aes_gcm_decrypt_final(
otcrypto_aes_gcm_context_t *ctx, otcrypto_const_word32_buf_t auth_tag,
otcrypto_aes_gcm_tag_len_t tag_len, otcrypto_byte_buf_t *plaintext,
otcrypto_aes_gcm_tag_len_t tag_len, otcrypto_byte_buf_t plaintext,
size_t *plaintext_bytes_written, hardened_bool_t *success) {
if (ctx == NULL || plaintext == NULL || plaintext_bytes_written == NULL ||
auth_tag.data == NULL || success == NULL) {
if (ctx == NULL || plaintext_bytes_written == NULL || auth_tag.data == NULL ||
success == NULL) {
return OTCRYPTO_BAD_ARGS;
}
if (plaintext->len != 0 && plaintext->data == NULL) {
if (plaintext.len != 0 && plaintext.data == NULL) {
return OTCRYPTO_BAD_ARGS;
}
*plaintext_bytes_written = 0;
Expand All @@ -832,13 +830,13 @@ otcrypto_status_t otcrypto_aes_gcm_decrypt_final(
// If the partial block is nonempty, the output must be at least as long as
// the partial block.
size_t partial_block_len = internal_ctx.input_len % kAesBlockNumBytes;
if (plaintext->len < partial_block_len) {
if (plaintext.len < partial_block_len) {
return OTCRYPTO_BAD_ARGS;
}

// Call the internal final operation.
HARDENED_TRY(aes_gcm_decrypt_final(&internal_ctx, auth_tag.len, auth_tag.data,
plaintext_bytes_written, plaintext->data,
plaintext_bytes_written, plaintext.data,
success));

// Clear the context and the key if needed.
Expand Down Expand Up @@ -925,10 +923,9 @@ static status_t aes_kwp_key_construct(const otcrypto_blinded_key_t *key_kek,

otcrypto_status_t otcrypto_aes_kwp_wrap(
const otcrypto_blinded_key_t *key_to_wrap,
const otcrypto_blinded_key_t *key_kek, otcrypto_word32_buf_t *wrapped_key) {
const otcrypto_blinded_key_t *key_kek, otcrypto_word32_buf_t wrapped_key) {
if (key_to_wrap == NULL || key_to_wrap->keyblob == NULL || key_kek == NULL ||
key_kek->keyblob == NULL || wrapped_key == NULL ||
wrapped_key->data == NULL) {
key_kek->keyblob == NULL || wrapped_key.data == NULL) {
return OTCRYPTO_BAD_ARGS;
}

Expand All @@ -943,7 +940,7 @@ otcrypto_status_t otcrypto_aes_kwp_wrap(
// Check the length of the output buffer.
size_t exp_len;
HARDENED_TRY(otcrypto_aes_kwp_wrapped_len(key_to_wrap->config, &exp_len));
if (wrapped_key->len != exp_len) {
if (wrapped_key.len != exp_len) {
return OTCRYPTO_BAD_ARGS;
}

Expand Down Expand Up @@ -975,7 +972,7 @@ otcrypto_status_t otcrypto_aes_kwp_wrap(
keyblob_words);

// Wrap the key.
return aes_kwp_wrap(kek, plaintext, sizeof(plaintext), wrapped_key->data);
return aes_kwp_wrap(kek, plaintext, sizeof(plaintext), wrapped_key.data);
}

otcrypto_status_t otcrypto_aes_kwp_unwrap(
Expand Down
17 changes: 7 additions & 10 deletions sw/device/lib/crypto/impl/drbg.c
Original file line number Diff line number Diff line change
Expand Up @@ -168,37 +168,34 @@ otcrypto_status_t otcrypto_drbg_manual_reseed(
*/
static otcrypto_status_t generate(hardened_bool_t fips_check,
otcrypto_const_byte_buf_t additional_input,
otcrypto_word32_buf_t *drbg_output) {
if (drbg_output == NULL) {
return OTCRYPTO_BAD_ARGS;
}
if (drbg_output->len == 0) {
otcrypto_word32_buf_t drbg_output) {
if (drbg_output.len == 0) {
// Nothing to do.
return OTCRYPTO_OK;
}
if ((additional_input.len != 0 && additional_input.data == NULL) ||
drbg_output->data == NULL) {
drbg_output.data == NULL) {
return OTCRYPTO_BAD_ARGS;
}

entropy_seed_material_t seed_material;
seed_material_construct(additional_input, &seed_material);
HARDENED_TRY(entropy_csrng_generate(&seed_material, drbg_output->data,
drbg_output->len, fips_check));
HARDENED_TRY(entropy_csrng_generate(&seed_material, drbg_output.data,
drbg_output.len, fips_check));

return OTCRYPTO_OK;
}

otcrypto_status_t otcrypto_drbg_generate(
otcrypto_const_byte_buf_t additional_input,
otcrypto_word32_buf_t *drbg_output) {
otcrypto_word32_buf_t drbg_output) {
return generate(/*fips_check=*/kHardenedBoolTrue, additional_input,
drbg_output);
}

otcrypto_status_t otcrypto_drbg_manual_generate(
otcrypto_const_byte_buf_t additional_input,
otcrypto_word32_buf_t *drbg_output) {
otcrypto_word32_buf_t drbg_output) {
return generate(/*fips_check=*/kHardenedBoolFalse, additional_input,
drbg_output);
}
Expand Down
32 changes: 15 additions & 17 deletions sw/device/lib/crypto/impl/ecc.c
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,7 @@ otcrypto_status_t otcrypto_ecdsa_keygen(

otcrypto_status_t otcrypto_ecdsa_sign(
const otcrypto_blinded_key_t *private_key,
const otcrypto_hash_digest_t *message_digest,
const otcrypto_hash_digest_t message_digest,
const otcrypto_ecc_curve_t *elliptic_curve,
otcrypto_word32_buf_t signature) {
HARDENED_TRY(otcrypto_ecdsa_sign_async_start(private_key, message_digest,
Expand All @@ -35,7 +35,7 @@ otcrypto_status_t otcrypto_ecdsa_sign(

otcrypto_status_t otcrypto_ecdsa_verify(
const otcrypto_unblinded_key_t *public_key,
const otcrypto_hash_digest_t *message_digest,
const otcrypto_hash_digest_t message_digest,
otcrypto_const_word32_buf_t signature,
const otcrypto_ecc_curve_t *elliptic_curve,
hardened_bool_t *verification_result) {
Expand Down Expand Up @@ -326,12 +326,12 @@ otcrypto_status_t otcrypto_ecdsa_keygen_async_finalize(
*/
static status_t internal_ecdsa_p256_sign_start(
const otcrypto_blinded_key_t *private_key,
const otcrypto_hash_digest_t *message_digest) {
const otcrypto_hash_digest_t message_digest) {
// Check the digest length.
if (launder32(message_digest->len) != kP256ScalarWords) {
if (launder32(message_digest.len) != kP256ScalarWords) {
return OTCRYPTO_BAD_ARGS;
}
HARDENED_CHECK_EQ(message_digest->len, kP256ScalarWords);
HARDENED_CHECK_EQ(message_digest.len, kP256ScalarWords);

// Check the key length.
HARDENED_TRY(p256_private_key_length_check(private_key));
Expand All @@ -340,12 +340,12 @@ static status_t internal_ecdsa_p256_sign_start(
// Start the asynchronous signature-generation routine.
HARDENED_CHECK_EQ(private_key->config.hw_backed, kHardenedBoolFalse);
p256_masked_scalar_t *sk = (p256_masked_scalar_t *)private_key->keyblob;
return ecdsa_p256_sign_start(message_digest->data, sk);
return ecdsa_p256_sign_start(message_digest.data, sk);
} else if (launder32(private_key->config.hw_backed) == kHardenedBoolTrue) {
// Load the key and start in sideloaded-key mode.
HARDENED_CHECK_EQ(private_key->config.hw_backed, kHardenedBoolTrue);
HARDENED_TRY(sideload_key_seed(private_key));
return ecdsa_p256_sideload_sign_start(message_digest->data);
return ecdsa_p256_sideload_sign_start(message_digest.data);
}

// Invalid value for private_key->hw_backed.
Expand All @@ -354,11 +354,10 @@ static status_t internal_ecdsa_p256_sign_start(

otcrypto_status_t otcrypto_ecdsa_sign_async_start(
const otcrypto_blinded_key_t *private_key,
const otcrypto_hash_digest_t *message_digest,
const otcrypto_hash_digest_t message_digest,
const otcrypto_ecc_curve_t *elliptic_curve) {
if (private_key == NULL || private_key->keyblob == NULL ||
elliptic_curve == NULL || message_digest == NULL ||
message_digest->data == NULL) {
elliptic_curve == NULL || message_digest.data == NULL) {
return OTCRYPTO_BAD_ARGS;
}

Expand Down Expand Up @@ -465,34 +464,33 @@ otcrypto_status_t otcrypto_ecdsa_sign_async_finalize(
*/
static status_t internal_ecdsa_p256_verify_start(
const otcrypto_unblinded_key_t *public_key,
const otcrypto_hash_digest_t *message_digest,
const otcrypto_hash_digest_t message_digest,
otcrypto_const_word32_buf_t signature) {
// Check the public key size.
HARDENED_TRY(p256_public_key_length_check(public_key));
p256_point_t *pk = (p256_point_t *)public_key->key;

// Check the digest length.
if (launder32(message_digest->len) != kP256ScalarWords) {
if (launder32(message_digest.len) != kP256ScalarWords) {
return OTCRYPTO_BAD_ARGS;
}
HARDENED_CHECK_EQ(message_digest->len, kP256ScalarWords);
HARDENED_CHECK_EQ(message_digest.len, kP256ScalarWords);

// Check the signature lengths.
HARDENED_TRY(p256_signature_length_check(signature.len));
ecdsa_p256_signature_t *sig = (ecdsa_p256_signature_t *)signature.data;

// Start the asynchronous signature-verification routine.
return ecdsa_p256_verify_start(sig, message_digest->data, pk);
return ecdsa_p256_verify_start(sig, message_digest.data, pk);
}

otcrypto_status_t otcrypto_ecdsa_verify_async_start(
const otcrypto_unblinded_key_t *public_key,
const otcrypto_hash_digest_t *message_digest,
const otcrypto_hash_digest_t message_digest,
otcrypto_const_word32_buf_t signature,
const otcrypto_ecc_curve_t *elliptic_curve) {
if (public_key == NULL || elliptic_curve == NULL || signature.data == NULL ||
message_digest == NULL || message_digest->data == NULL ||
public_key->key == NULL) {
message_digest.data == NULL || public_key->key == NULL) {
return OTCRYPTO_BAD_ARGS;
}

Expand Down
Loading
Loading