Skip to content

Commit

Permalink
[bazel,otp] update ROM_EXT immutable section OTP gen tooling
Browse files Browse the repository at this point in the history
This updates the logic to consider both `_ottf_start_address` and
 `_rom_ext_start_address` when determining the manifest start address.
This ensures compatibility with different ELF file formats that
generated from linker scripts such as `ottf_silicon_owner_a.ld` and
`rom_ext_slot_a.ld`, which may use either symbol to represent the start
address of the ROM_EXT section.

This also introduces a new feature that conditionally updates the OTP
JSON file with data from immutable ROM_EXT section. This update is
performed only if the immutable ROM_EXT is enabled.

Signed-off-by: Anthony Chen <[email protected]>
  • Loading branch information
anthonychen1251 committed Oct 21, 2024
1 parent d6150d9 commit 681d0a9
Show file tree
Hide file tree
Showing 2 changed files with 51 additions and 2 deletions.
1 change: 1 addition & 0 deletions rules/otp.bzl
Original file line number Diff line number Diff line change
Expand Up @@ -169,6 +169,7 @@ def _otp_json_immutable_rom_ext_impl(ctx):
args.add("--input", intput_file)
args.add("--elf", rom_ext_elf_file)
args.add("--output", output_file)
args.add("--hardened-true-value", CONST.HARDENED_TRUE)

tc = ctx.toolchains[LOCALTOOLS_TOOLCHAIN]
ctx.actions.run(
Expand Down
52 changes: 50 additions & 2 deletions util/design/gen-otp-immutable-rom-ext-json.py
Original file line number Diff line number Diff line change
Expand Up @@ -16,8 +16,10 @@
_OTP_PARTITION_NAME = "CREATOR_SW_CFG"

_OTTF_START_OFFSET_SYMBOL_NAME = "_ottf_start_address"
_ROM_EXT_SATRT_OFFSET_SYMBOL_NAME = "_rom_ext_start_address"
_ROM_EXT_IMMUTABLE_SECTION_NAME = ".rom_ext_immutable"

_ENABLE_FIELD_NAME = "CREATOR_SW_CFG_IMMUTABLE_ROM_EXT_EN"
_START_OFFSET_FIELD_NAME = "CREATOR_SW_CFG_IMMUTABLE_ROM_EXT_START_OFFSET"
_SIZE_FIELD_NAME = "CREATOR_SW_CFG_IMMUTABLE_ROM_EXT_LENGTH"
_HASH_FIELD_NAME = "CREATOR_SW_CFG_IMMUTABLE_ROM_EXT_SHA256_HASH"
Expand All @@ -33,11 +35,21 @@ def __init__(self, rom_ext_elf, json_data):
self.start_offset = None
self.size_in_bytes = None
self.hash = None

with open(self.rom_ext_elf, 'rb') as f:
elf = elffile.ELFFile(f)
# Find the offset of the current slot we are in.
for symbol in elf.get_section_by_name(".symtab").iter_symbols():
if symbol.name == _OTTF_START_OFFSET_SYMBOL_NAME:
if symbol.name in [
_OTTF_START_OFFSET_SYMBOL_NAME,
_ROM_EXT_SATRT_OFFSET_SYMBOL_NAME,
]:
if self.manifest_offset is not None:
raise ValueError(
f"More than one manifest start address exists. "
f"Current offset: {self.manifest_offset}, "
f"new offset: {symbol.entry['st_value']}"
)
self.manifest_offset = symbol.entry["st_value"]
assert self.manifest_offset, "Manifest start address not found."

Expand Down Expand Up @@ -74,6 +86,20 @@ def insert_key_value(self, item_name: str, value: str):
return
partition["items"].append({"name": item_name, "value": value})

def get_key_value(self, item_name: str):
"""Get the value of the item if it exists.
Args:
item_name: The name of the item to insert.
Returns:
The value of the item if found, otherwise "0x0".
"""
for partition in self.json_data["partitions"]:
if partition["name"] == _OTP_PARTITION_NAME:
for item in partition["items"]:
if item["name"] == item_name:
return item["value"]
return "0x0"

def update_json_with_immutable_rom_ext_section_data(self):
"""Update the JSON with the ROM_EXT immutable section data.
Args:
Expand All @@ -86,6 +112,22 @@ def update_json_with_immutable_rom_ext_section_data(self):
self.insert_key_value(_SIZE_FIELD_NAME, f"{hex(self.size_in_bytes)}")
self.insert_key_value(_HASH_FIELD_NAME, f"0x{self.hash.hex()}")

def immutable_rom_ext_enable(self, hardened_true_value: int):
"""Checks if immutable ROM extension is enabled.
This method retrieves the value of the enable field from the OTP
partition and compares it with the provided hardened true value.
Args:
hardened_true_value: The expected value for the enable field
when immutable ROM extension is enabled.
Returns:
True if immutable ROM extension is enabled, False otherwise.
"""
immutable_rom_ext_en_value = int(self.get_key_value(_ENABLE_FIELD_NAME), 0)
return immutable_rom_ext_en_value == hardened_true_value


def main():
parser = argparse.ArgumentParser(
Expand All @@ -107,6 +149,10 @@ def main():
type=str,
metavar='<path>',
help='Output JSON file path.')
parser.add_argument('--hardened-true-value',
type=int,
help='The integer value representing "true" for the '
'enable field in the OTP partition.')
args = parser.parse_args()

# Read in the OTP fields (encoded in JSON) we will be updating.
Expand All @@ -121,7 +167,9 @@ def main():
logging.error("Cannot find {} section in ROM_EXT ELF {}.".format(
_ROM_EXT_IMMUTABLE_SECTION_NAME, args.elf))
sys.exit(1)
imm_section_otp.update_json_with_immutable_rom_ext_section_data()

if imm_section_otp.immutable_rom_ext_enable(args.hardened_true_value):
imm_section_otp.update_json_with_immutable_rom_ext_section_data()

# Write out the OTP fields to a JSON file.
with open(args.output, 'w') as f:
Expand Down

0 comments on commit 681d0a9

Please sign in to comment.