diff --git a/boot/boot_serial/src/boot_serial_encryption.c b/boot/boot_serial/src/boot_serial_encryption.c index 7d3b47c72..bbc639694 100644 --- a/boot/boot_serial/src/boot_serial_encryption.c +++ b/boot/boot_serial/src/boot_serial_encryption.c @@ -171,9 +171,18 @@ decrypt_region_inplace(struct boot_loader_state *state, blk_sz = tlv_off - (off + bytes_copied); } } - boot_encrypt(BOOT_CURR_ENC(state), slot, - (off + bytes_copied + idx) - hdr->ih_hdr_size, blk_sz, - blk_off, &buf[idx]); + /* slot determines direction: running on secondary slot (1) means + * decryption, running on primary slot (0) means encryption. + */ + if (slot == 0) { + boot_enc_encrypt(BOOT_CURR_ENC(state), slot, + (off + bytes_copied + idx) - hdr->ih_hdr_size, blk_sz, + blk_off, &buf[idx]); + } else { + boot_enc_decrypt(BOOT_CURR_ENC(state), slot, + (off + bytes_copied + idx) - hdr->ih_hdr_size, blk_sz, + blk_off, &buf[idx]); + } } rc = flash_area_erase(fap, off + bytes_copied, chunk_sz); if (rc != 0) { diff --git a/boot/bootutil/include/bootutil/enc_key.h b/boot/bootutil/include/bootutil/enc_key.h index a86430937..e1696b045 100644 --- a/boot/bootutil/include/bootutil/enc_key.h +++ b/boot/bootutil/include/bootutil/enc_key.h @@ -60,7 +60,9 @@ int boot_enc_load(struct enc_key_data *enc_state, int slot, struct boot_status *bs); bool boot_enc_valid(struct enc_key_data *enc_state, int image_index, const struct flash_area *fap); -void boot_encrypt(struct enc_key_data *enc_state, int slot, +void boot_enc_encrypt(struct enc_key_data *enc_state, int slot, + uint32_t off, uint32_t sz, uint32_t blk_off, uint8_t *buf); +void boot_enc_decrypt(struct enc_key_data *enc_state, int slot, uint32_t off, uint32_t sz, uint32_t blk_off, uint8_t *buf); void boot_enc_zeroize(struct enc_key_data *enc_state); diff --git a/boot/bootutil/src/encrypted.c b/boot/bootutil/src/encrypted.c index f4b960e88..3489eadcc 100644 --- a/boot/bootutil/src/encrypted.c +++ b/boot/bootutil/src/encrypted.c @@ -673,10 +673,10 @@ boot_enc_valid(struct enc_key_data *enc_state, int image_index, } void -boot_encrypt(struct enc_key_data *enc_state, int slot, uint32_t off, +boot_enc_encrypt(struct enc_key_data *enc_state, int slot, uint32_t off, uint32_t sz, uint32_t blk_off, uint8_t *buf) { - struct enc_key_data *enc; + struct enc_key_data *enc = &enc_state[slot]; uint8_t nonce[16]; /* boot_copy_region will call boot_encrypt with sz = 0 when skipping over @@ -697,6 +697,31 @@ boot_encrypt(struct enc_key_data *enc_state, int slot, uint32_t off, bootutil_aes_ctr_encrypt(&enc->aes_ctr, nonce, buf, sz, blk_off, buf); } +void +boot_enc_decrypt(struct enc_key_data *enc_state, int slot, uint32_t off, + uint32_t sz, uint32_t blk_off, uint8_t *buf) +{ + struct enc_key_data *enc = &enc_state[slot]; + uint8_t nonce[16]; + + /* boot_copy_region will call boot_encrypt with sz = 0 when skipping over + the TLVs. */ + if (sz == 0) { + return; + } + + memset(nonce, 0, 12); + off >>= 4; + nonce[12] = (uint8_t)(off >> 24); + nonce[13] = (uint8_t)(off >> 16); + nonce[14] = (uint8_t)(off >> 8); + nonce[15] = (uint8_t)off; + + enc = &enc_state[slot]; + assert(enc->valid == 1); + bootutil_aes_ctr_decrypt(&enc->aes_ctr, nonce, buf, sz, blk_off, buf); +} + /** * Clears encrypted state after use. */ diff --git a/boot/bootutil/src/image_validate.c b/boot/bootutil/src/image_validate.c index 911322b13..18bc1f676 100644 --- a/boot/bootutil/src/image_validate.c +++ b/boot/bootutil/src/image_validate.c @@ -150,8 +150,8 @@ bootutil_img_hash(struct enc_key_data *enc_state, int image_index, /* Only payload is encrypted (area between header and TLVs) */ if (off >= hdr_size && off < tlv_off) { blk_off = (off - hdr_size) & 0xf; - boot_encrypt(enc_state, 1, off - hdr_size, - blk_sz, blk_off, tmp_buf); + boot_enc_decrypt(enc_state, 1, off - hdr_size, + blk_sz, blk_off, tmp_buf); } } #endif diff --git a/boot/bootutil/src/loader.c b/boot/bootutil/src/loader.c index 3f459738a..6bb91d690 100644 --- a/boot/bootutil/src/loader.c +++ b/boot/bootutil/src/loader.c @@ -1299,6 +1299,15 @@ boot_copy_region(struct boot_loader_state *state, (abs_off + idx) - hdr->ih_hdr_size, blk_sz, blk_off, &buf[idx]); } + if (source_slot == 0) { + boot_enc_encrypt(BOOT_CURR_ENC(state), source_slot, + (abs_off + idx) - hdr->ih_hdr_size, blk_sz, + blk_off, &buf[idx]); + } else { + boot_enc_decrypt(BOOT_CURR_ENC(state), source_slot, + (abs_off + idx) - hdr->ih_hdr_size, blk_sz, + blk_off, &buf[idx]); + } } } #endif @@ -2772,18 +2781,16 @@ boot_decrypt_and_copy_image_to_sram(struct boot_loader_state *state, cur_dst = ram_dst + bytes_copied; blk_sz = chunk_sz; idx = 0; + blk_off = ((bytes_copied) - hdr->ih_hdr_size) & 0xf; if (bytes_copied + chunk_sz > tlv_off) { - /* Going over TLV section - * Part of the chunk is encrypted payload */ - blk_off = ((bytes_copied) - hdr->ih_hdr_size) & 0xf; blk_sz = tlv_off - (bytes_copied); - boot_encrypt(BOOT_CURR_ENC(state), slot, - (bytes_copied + idx) - hdr->ih_hdr_size, blk_sz, - blk_off, cur_dst); + } + if (slot == 0) { + boot_enc_encrypt(BOOT_CURR_ENC(state), slot, + (bytes_copied + idx) - hdr->ih_hdr_size, blk_sz, + blk_off, cur_dst); } else { - /* Image encrypted payload section */ - blk_off = ((bytes_copied) - hdr->ih_hdr_size) & 0xf; - boot_encrypt(BOOT_CURR_ENC(state), slot, + boot_enc_decrypt(BOOT_CURR_ENC(state), slot, (bytes_copied + idx) - hdr->ih_hdr_size, blk_sz, blk_off, cur_dst); }