Skip to content

Commit

Permalink
[manuf] erase AST config data from flash after use
Browse files Browse the repository at this point in the history
This updates the individualization firmware to erase the AST
configuration data from flash info after committing it to OTP.

This fixes lowRISC#24526.

Signed-off-by: Tim Trippel <[email protected]>
  • Loading branch information
timothytrippel committed Sep 24, 2024
1 parent 8cfe060 commit 757edad
Show file tree
Hide file tree
Showing 4 changed files with 51 additions and 13 deletions.
1 change: 1 addition & 0 deletions sw/device/silicon_creator/manuf/lib/BUILD
Original file line number Diff line number Diff line change
Expand Up @@ -177,6 +177,7 @@ cc_library(
"//hw/ip/otp_ctrl/data:otp_ctrl_c_regs",
"//hw/top_earlgrey/sw/autogen:top_earlgrey",
"//sw/device/lib/base:macros",
"//sw/device/lib/base:memory",
"//sw/device/lib/base:status",
"//sw/device/lib/crypto/impl:hash",
"//sw/device/lib/dif:flash_ctrl",
Expand Down
2 changes: 0 additions & 2 deletions sw/device/silicon_creator/manuf/lib/ast_program_functest.c
Original file line number Diff line number Diff line change
Expand Up @@ -63,8 +63,6 @@ static status_t program_page(void) {
for (size_t i = 0; i < ARRAYSIZE(ast_cfg_data); ++i) {
ast_cfg_data[i] = i;
}

// The AST blob is 1 count word plus 2 additional words for every <count>.
return flash_ctrl_testutils_write(
&flash_state, byte_address, kFlashInfoFieldAstCalibrationData.partition,
ast_cfg_data, kDifFlashCtrlPartitionTypeInfo,
Expand Down
47 changes: 38 additions & 9 deletions sw/device/silicon_creator/manuf/lib/individualize_sw_cfg.c
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@
#include "sw/device/silicon_creator/manuf/lib/individualize_sw_cfg.h"

#include "sw/device/lib/base/macros.h"
#include "sw/device/lib/base/memory.h"
#include "sw/device/lib/crypto/include/datatypes.h"
#include "sw/device/lib/crypto/include/hash.h"
#include "sw/device/lib/dif/dif_flash_ctrl.h"
Expand All @@ -15,6 +16,7 @@
#include "sw/device/silicon_creator/manuf/lib/otp_img_types.h"
#include "sw/device/silicon_creator/manuf/lib/util.h"

#include "flash_ctrl_regs.h" // Generated.
#include "hw/top_earlgrey/sw/autogen/top_earlgrey.h"
#include "otp_ctrl_regs.h" // Generated.

Expand All @@ -25,6 +27,9 @@ enum {

};

static uint32_t
flash_info_page_buf[FLASH_CTRL_PARAM_BYTES_PER_PAGE / sizeof(uint32_t)];

/**
* Writes OTP values to target OTP `partition`.
*
Expand Down Expand Up @@ -124,29 +129,38 @@ static status_t lock_otp_partition(const dif_otp_ctrl_t *otp_ctrl,

static status_t manuf_individualize_device_ast_cfg(
const dif_otp_ctrl_t *otp_ctrl, dif_flash_ctrl_state_t *flash_state) {
// Copy AST configuration data out of the flash info page.
uint32_t ast_cfg_data[kFlashInfoAstCalibrationDataSizeIn32BitWords];
// Clear flash info page buffer.
memset(flash_info_page_buf, UINT8_MAX, FLASH_CTRL_PARAM_BYTES_PER_PAGE);

// Copy all of flash info page 0 into RAM. This contains the AST configuration
// data, which we will extract and then delete.
uint32_t page_byte_address = 0;
TRY(flash_ctrl_testutils_info_region_setup_properties(
flash_state, kFlashInfoFieldAstCalibrationData.page,
kFlashInfoFieldAstCalibrationData.bank,
kFlashInfoFieldAstCalibrationData.partition,
(dif_flash_ctrl_region_properties_t){
.ecc_en = kMultiBitBool4True,
.high_endurance_en = kMultiBitBool4False,
.erase_en = kMultiBitBool4False,
.prog_en = kMultiBitBool4False,
.erase_en = kMultiBitBool4True,
.prog_en = kMultiBitBool4True,
.rd_en = kMultiBitBool4True,
.scramble_en = kMultiBitBool4False},
/*offset=*/NULL));
TRY(manuf_flash_info_field_read(
flash_state, kFlashInfoFieldAstCalibrationData, ast_cfg_data,
kFlashInfoAstCalibrationDataSizeIn32BitWords));
&page_byte_address));
TRY(flash_ctrl_testutils_read(
flash_state, page_byte_address,
kFlashInfoFieldAstCalibrationData.partition, flash_info_page_buf,
kDifFlashCtrlPartitionTypeInfo,
FLASH_CTRL_PARAM_BYTES_PER_PAGE / sizeof(uint32_t),
/*delay=*/0));

// Write AST configuration data to OTP.
size_t ast_cfg_offset =
kFlashInfoFieldAstCalibrationData.byte_offset / sizeof(uint32_t);
for (size_t i = 0; i < kFlashInfoAstCalibrationDataSizeIn32BitWords; ++i) {
uint32_t addr =
OTP_CTRL_PARAM_CREATOR_SW_CFG_AST_CFG_OFFSET + i * sizeof(uint32_t);
uint32_t data = ast_cfg_data[i];
uint32_t data = flash_info_page_buf[ast_cfg_offset + i];
uint32_t relative_addr;
// Check the range is valid.
if (addr < kValidAstCfgOtpAddrLow || addr >= kInvalidAstCfgOtpAddrHigh) {
Expand All @@ -157,7 +171,22 @@ static status_t manuf_individualize_device_ast_cfg(
TRY(otp_ctrl_testutils_dai_write32(otp_ctrl,
kDifOtpCtrlPartitionCreatorSwCfg,
relative_addr, &data, /*len=*/1));
flash_info_page_buf[ast_cfg_offset + i] =
UINT32_MAX; // Erase AST config data after use.
}

// Erase AST data from flash by erasing the entire page and rewriting the
// modified buffered contents back to the page.
TRY(flash_ctrl_testutils_erase_page(
flash_state, page_byte_address,
kFlashInfoFieldAstCalibrationData.partition,
kDifFlashCtrlPartitionTypeInfo));
TRY(flash_ctrl_testutils_write(
flash_state, page_byte_address,
kFlashInfoFieldAstCalibrationData.partition, flash_info_page_buf,
kDifFlashCtrlPartitionTypeInfo,
FLASH_CTRL_PARAM_BYTES_PER_PAGE / sizeof(uint32_t)));

return OK_STATUS();
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -54,7 +54,8 @@ static status_t peripheral_handles_init(void) {

/**
* Initializes flash info page 0 fields required to complete the
* individualization step.
* individualization step, which include:
* - AST configuration data
*/
static status_t init_flash_info_page0(void) {
uint32_t byte_address = 0;
Expand Down Expand Up @@ -85,9 +86,9 @@ static status_t init_flash_info_page0(void) {
* Check the AST configuration data was programmed correctly.
*/
static status_t check_otp_ast_cfg(void) {
// Check OTP fields were programmed correctly.
uint32_t data;
uint32_t relative_addr;

for (size_t i = 0; i < kFlashInfoAstCalibrationDataSizeIn32BitWords; ++i) {
TRY(dif_otp_ctrl_relative_address(
kDifOtpCtrlPartitionCreatorSwCfg,
Expand All @@ -98,6 +99,15 @@ static status_t check_otp_ast_cfg(void) {
TRY_CHECK(data == i);
}

// Check that the AST configuration data was erased from flash info page 0.
uint32_t ast_cfg_data[kFlashInfoAstCalibrationDataSizeIn32BitWords] = {0};
TRY(manuf_flash_info_field_read(
&flash_ctrl_state, kFlashInfoFieldAstCalibrationData, ast_cfg_data,
kFlashInfoAstCalibrationDataSizeIn32BitWords));
for (size_t i = 0; i < kFlashInfoAstCalibrationDataSizeIn32BitWords; ++i) {
TRY_CHECK(ast_cfg_data[i] == UINT32_MAX);
}

return OK_STATUS();
}

Expand Down

0 comments on commit 757edad

Please sign in to comment.