blob: 73553058c9f6c011c21e0dbe2a9c6a43f01d0fda [file] [log] [blame]
// Copyright lowRISC contributors.
// Licensed under the Apache License, Version 2.0, see LICENSE for details.
// SPDX-License-Identifier: Apache-2.0
{
name: "keymgr",
human_name: "Key Manager",
one_line_desc: "Managing identities and root keys; shielding confidential assets from software; providing a key derivation interface for software",
one_paragraph_desc: '''
Key Manager implements the hardware component of the identities and root keys strategy of OpenTitan.
It shields confidential assets from direct software access and provides an interface for software to use derived keys and identity outputs.
The key derivation functionality interfaces KMAC Accelerator.
Key Manager provides AES Accelerator, OTBN, and KMAC Accelerator with confidential keys over sideload interfaces that are not accessible from software.
In addition, it supports the [Open Profile for DICE][pigweed-open-dice].
[pigweed-open-dice]: https://pigweed.googlesource.com/open-dice/+/HEAD/docs/specification.md#Open-Profile-for-DICE
'''
design_spec: "../doc",
dv_doc: "../doc/dv",
hw_checklist: "../doc/checklist",
sw_checklist: "/sw/device/lib/dif/dif_keymgr",
revisions: [
{
version: "1.0",
life_stage: "L1",
design_stage: "D2S",
verification_stage: "V2S",
dif_stage: "S2",
}
]
clocking: [
{clock: "clk_i", reset: "rst_ni", primary: true},
{clock: "clk_edn_i", reset: "rst_edn_ni"}
]
bus_interfaces: [
{ protocol: "tlul", direction: "device" }
],
interrupt_list: [
{ name: "op_done", desc: "Operation complete" },
],
alert_list: [
{ name: "recov_operation_err",
desc: '''
Alert for key manager operation errors. These errors could have been caused by
software'''
},
{ name: "fatal_fault_err",
desc: "Alert for key manager faults. These errors cannot be caused by software",
},
],
inter_signal_list: [
{ struct: "edn",
type: "req_rsp",
name: "edn",
act: "req",
package: "edn_pkg",
},
{ struct: "hw_key_req", // aes_key_req_t
type: "uni",
name: "aes_key", // aes_key_o (req)
act: "req",
package: "keymgr_pkg", // Origin package (only needs for the requester)
},
{ struct: "hw_key_req", // kmac_key_req_t
type: "uni",
name: "kmac_key", // kmac_key_o (req)
act: "req",
package: "keymgr_pkg", // Origin package (only needs for the requester)
},
{ struct: "otbn_key_req",
type: "uni",
name: "otbn_key",
act: "req",
package: "keymgr_pkg",
},
{ struct: "app", // kmac_pkg::app_req_t, kmac_pkg::app_rsp_t
type: "req_rsp",
name: "kmac_data", // kmac_data_o (req), kmac_data_i (rsp)
act: "req",
package: "kmac_pkg", // Origin package (only needs for the requester)
},
{ struct: "otp_keymgr_key",
type: "uni",
name: "otp_key",
act: "rcv",
package: "otp_ctrl_pkg",
},
{ struct: "otp_device_id",
type: "uni",
name: "otp_device_id",
act: "rcv",
package: "otp_ctrl_pkg",
},
{ struct: "keymgr_flash",
type: "uni",
name: "flash",
act: "rcv",
package: "flash_ctrl_pkg",
},
{ struct: "lc_tx",
type: "uni",
name: "lc_keymgr_en",
act: "rcv",
package: "lc_ctrl_pkg",
default: "lc_ctrl_pkg::On",
},
{ struct: "lc_keymgr_div",
type: "uni",
name: "lc_keymgr_div",
act: "rcv",
package: "lc_ctrl_pkg",
},
{ struct: "keymgr_data"
type: "uni"
name: "rom_digest"
act: "rcv"
package: "rom_ctrl_pkg"
},
{ struct: "logic"
type: "uni"
name: "kmac_en_masking"
act: "rcv"
},
],
param_list: [
{ name: "KmacEnMasking",
desc: "Flag indicating with kmac masking is enabled",
type: "bit",
default: "1",
local: "false",
expose: "true",
}
// Random netlist constants
{ name: "RndCnstLfsrSeed",
desc: "Compile-time random bits for initial LFSR seed",
type: "keymgr_pkg::lfsr_seed_t"
randcount: "64",
randtype: "data",
}
{ name: "RndCnstLfsrPerm",
desc: "Compile-time random permutation for LFSR output",
type: "keymgr_pkg::lfsr_perm_t"
randcount: "64",
randtype: "perm",
},
{ name: "RndCnstRandPerm",
desc: "Compile-time random permutation for entropy used in share overriding",
type: "keymgr_pkg::rand_perm_t"
randcount: "32",
randtype: "perm",
}
{ name: "RndCnstRevisionSeed",
desc: "Compile-time random bits for revision seed",
type: "keymgr_pkg::seed_t"
randcount: "256",
randtype: "data",
},
{ name: "RndCnstCreatorIdentitySeed",
desc: "Compile-time random bits for creator identity seed",
type: "keymgr_pkg::seed_t"
randcount: "256",
randtype: "data",
},
{ name: "RndCnstOwnerIntIdentitySeed",
desc: "Compile-time random bits for owner intermediate identity seed",
type: "keymgr_pkg::seed_t"
randcount: "256",
randtype: "data",
},
{ name: "RndCnstOwnerIdentitySeed",
desc: "Compile-time random bits for owner identity seed",
type: "keymgr_pkg::seed_t"
randcount: "256",
randtype: "data",
},
{ name: "RndCnstSoftOutputSeed",
desc: "Compile-time random bits for software generation seed",
type: "keymgr_pkg::seed_t"
randcount: "256",
randtype: "data",
},
{ name: "RndCnstHardOutputSeed",
desc: "Compile-time random bits for hardware generation seed",
type: "keymgr_pkg::seed_t"
randcount: "256",
randtype: "data",
},
{ name: "RndCnstAesSeed",
desc: "Compile-time random bits for generation seed when aes destination selected",
type: "keymgr_pkg::seed_t"
randcount: "256",
randtype: "data",
},
{ name: "RndCnstKmacSeed",
desc: "Compile-time random bits for generation seed when kmac destination selected",
type: "keymgr_pkg::seed_t"
randcount: "256",
randtype: "data",
},
{ name: "RndCnstOtbnSeed",
desc: "Compile-time random bits for generation seed when otbn destination selected",
type: "keymgr_pkg::seed_t"
randcount: "256",
randtype: "data",
},
{ name: "RndCnstCdi",
desc: "Compile-time random bits for generation seed when no CDI is selected",
type: "keymgr_pkg::seed_t"
randcount: "256",
randtype: "data",
},
{ name: "RndCnstNoneSeed",
desc: "Compile-time random bits for generation seed when no destination selected",
type: "keymgr_pkg::seed_t"
randcount: "256",
randtype: "data",
},
{ name: "NumSaltReg",
desc: "Number of Registers for SW inputs (Salt)",
type: "int",
default: "8",
local: "true"
},
{ name: "NumSwBindingReg",
desc: "Number of Registers for SW inputs (SW binding)",
type: "int",
default: "8",
local: "true"
},
{ name: "NumOutReg",
desc: "Number of Registers for SW outputs",
type: "int",
default: "8",
local: "true"
},
{ name: "NumKeyVersion",
desc: "Number of Registers for key version",
type: "int",
default: "1",
local: "true"
},
],
countermeasures: [
{ name: "BUS.INTEGRITY",
desc: "End-to-end bus integrity scheme."
}
{ name: "CONFIG.SHADOW",
desc: '''
Various critical registers are shadowed: including operation control, reseed interval,
and key max version (creator, owner intermediate, owner).
'''
}
{ name: "OP.CONFIG.REGWEN",
desc: '''
Various controls locked during the duration of an operation: including operation start,
operation control, sideload clear, salt and key version.
'''
}
{ name: "RESEED.CONFIG.REGWEN",
desc: '''
Reseed interval is software lockable.
'''
}
{ name: "SW_BINDING.CONFIG.REGWEN",
desc: '''
Software binding is lockable by software in each stage. When keymgr successfully advances,
the lock is released to allow the next stage the freedom to program.
'''
}
{ name: "MAX_KEY_VER.CONFIG.REGWEN",
desc: '''
Max key version is software lockable.
'''
}
{ name: "LC_CTRL.INTERSIG.MUBI",
desc: '''
Life cycle control signal is multibit
'''
}
{ name: "CONSTANTS.CONSISTENCY",
desc: '''
Basic consistency checks (all 0's or all 1's) for keymgr diversification constants
'''
}
{ name: "INTERSIG.CONSISTENCY",
desc: '''
Basic consistency checks (all 0's or all 1's) for otp diversification inputs
'''
}
{ name: "HW.KEY.SW_NOACCESS",
desc: '''
Sideload keys are not directly accessible by software.
'''
}
{ name: "OUTPUT_KEYS.CTRL.REDUN",
desc: '''
Software and sideload keys are redundantly controlled. Each generate operation
creates a valid and a data enable (software and sideload specific).
In order for a key to be populated into the software register, both the software valid
and the software data enable must be asserted. The same is true for sideload.
This makes it more difficult for an attack to fault a sideload key into the software key slot.
An attacker would need to fault both the software valid and the software data enable.
During a sideload operation, if an attacker manages to fault the valid but not the data enable,
the software key is populated with random data. If an atacker manages to fault the data enable but
not the valid, then the software key retains its previous value.
'''
}
{ name: "CTRL.FSM.SPARSE",
desc: '''
Main control fsm is sparsely encoded.
'''
}
{ name: "DATA.FSM.SPARSE",
desc: '''
Control data fsm (for redundant data control) is sparsely encoded.
'''
}
{ name: "CTRL.FSM.LOCAL_ESC",
desc: '''
Main control fsm locally escalates based on any detected fault in keymgr.
When a fault is detected (sync or async) the fsm transitions to invalid state to prevent
further legal operations from executing.
'''
}
{ name: "CTRL.FSM.CONSISTENCY",
desc: '''
Main and operational fsm transitions are consistent with software commands.
'''
}
{ name: "CTRL.FSM.GLOBAL_ESC",
desc: '''
When the system globally escalates, the main control fsm also transitions to invalid state
to prevent further legal operations from executing.
'''
}
{ name: "CTRL.CTR.REDUN",
desc: '''
Primary count is duplicated.
'''
}
{ name: "KMAC_IF.FSM.SPARSE",
desc: '''
kmac interface fsm is sparsely encoded.
'''
}
{ name: "KMAC_IF.CTR.REDUN",
desc: '''
Primary count uses cross count.
'''
}
{ name: "KMAC_IF_CMD.CTRL.CONSISTENCY",
desc: '''
One hot check for kmac interface commands.
Also, command enable (adv_en, id_en, gen_en) is checked for consistency
throughout the operation.
'''
}
{ name: "KMAC_IF_DONE.CTRL.CONSISTENCY",
desc: '''
Spurious kmac done check.
'''
}
{ name: "RESEED.CTR.REDUN",
desc: '''
Primary count is duplicated.
'''
}
{ name: "SIDE_LOAD_SEL.CTRL.CONSISTENCY",
desc: '''
Sideload key slot select is checked for consistency.
When a key slot is valid when it should not be, an error is triggered.
The reverse case is not checked, since an invalid key cannot be used
anyways.
'''
}
{ name: "SIDELOAD_CTRL.FSM.SPARSE",
desc: '''
Sideload control fsm is sparsely encoded.
'''
}
{ name: "CTRL.KEY.INTEGRITY",
desc: '''
Internal secret key is protected with ECC.
'''
}
]
regwidth: "32",
registers: [
{ name: "CFG_REGWEN",
desc: "Key manager configuration enable",
swaccess: "ro", // this lock is HW managed
hwaccess: "hwo",
hwext: "true",
fields: [
{ bits: "0",
name: "EN",
resval: "1"
desc: '''
key manager configuration enable.
When key manager operation is started (see CONTROL), registers protected by this EN are no longer
modifiable until the operation completes.
'''
},
]
},
{ name: "START",
desc: "Key manager operation start",
swaccess: "rw",
hwaccess: "hrw",
regwen: "CFG_REGWEN",
fields: [
{ bits: "0",
hwaccess: "hrw",
name: "EN",
desc: "Start key manager operations",
resval: "0"
enum: [
{ value: "1",
name: "Valid state",
desc: '''
To trigger a start, this value must be programmed. All other values are considered no operation start.
'''
},
]
tags: [// bit self clears, handle in directed test
"excl:CsrNonInitTests:CsrExclWrite"]
}
]
},
{ name: "CONTROL_SHADOWED",
desc: "Key manager operation controls",
regwen: "CFG_REGWEN",
swaccess: "rw",
hwaccess: "hro",
shadowed: "true",
update_err_alert: "recov_operation_err",
storage_err_alert: "fatal_fault_err",
fields: [
{ bits: "6:4",
name: "OPERATION",
desc: "Key manager operation selection. All values not enumerated below behave the same as disable",
resval: "1",
enum: [
{ value: "0",
name: "Advance",
desc: '''
Advance key manager state.
Advances key manager to the next stage.
If key manager is already at last functional state, the advance operation is equivalent to the
disable operation.
'''
},
{ value: "1",
name: "Generate ID",
desc: '''
Generates an identity seed from the current state.
'''
},
{ value: "2",
name: "Generate SW Output",
desc: '''
Generates a key manager output that is visible to software from the current state.
'''
},
{ value: "3",
name: "Generate HW Output",
desc: '''
Generates a key manager output that is visible only to hardware crypto blocks.
'''
},
{ value: "4",
name: "Disable",
desc: '''
Disables key manager operation and moves it to the disabled state.
Note the disabled state is terminal and cannot be recovered without a reset.
'''
},
],
},
{ bits: "7",
name: "CDI_SEL",
desc: '''
When the OPERATION field is programmed to generate output, this field selects
the appropriate CDI to use.
This field should be programmed for both hw / sw generation.
''',
resval: "0"
enum: [
{ value: "0",
name: "Sealing CDI",
desc: '''
Sealing CDI is selected
'''
},
{ value: "1",
name: "Attestation CDI",
desc: '''
Attestation CDI is selected
'''
},
],
},
{ bits: "13:12",
name: "DEST_SEL",
desc: '''
When the OPERATION field is programmed to generate output, this field selects
the appropriate crypto cipher target.
This field should be programmed for both hw / sw generation, as this helps diverisifies the output.
''',
resval: "0"
enum: [
{ value: "0",
name: "None",
desc: '''
No target selected
'''
},
{ value: "1",
name: "AES",
desc: '''
AES selected
'''
},
{ value: "2",
name: "KMAC",
desc: '''
KMAC selected
'''
},
{ value: "3",
name: "OTBN",
desc: '''
OTBN selected. Note for OTBN hardware operations, the generated output is 384-bits, while for all
other operations (including OTBN software), it is 256-bits.
Generating a hardware 384-bit seed directly for OTBN sideload reduces some of the OTBN code burden for entropy expansion.
When generating for software, this is not a concern.
'''
},
]
},
],
},
{ name: "SIDELOAD_CLEAR",
desc: "sideload key slots clear"
swaccess: "rw",
hwaccess: "hro",
regwen: "CFG_REGWEN",
fields: [
{ bits: "2:0",
name: "VAL",
resval: "0"
desc: '''
Depending on the value programmed, a different sideload key slot is cleared.
If the value programmed is not one of the enumerated values below, ALL sideload
key slots are continuously cleared. In order to stop continuous clearing, SW should
toggle the clear bit again (i.e. disable continuous clearing).
''',
enum: [
{ value: "0",
name: "None",
desc: '''
No sideload keys cleared.
'''
},
{ value: "1",
name: "AES",
desc: '''
The AES sideload key is continuously cleared with entropy.
'''
},
{ value: "2",
name: "KMAC",
desc: '''
The KMAC sideload key is continuously cleared with entropy.
'''
},
{ value: "3",
name: "OTBN",
desc: '''
The OTBN sideload key is continuously cleared with entropy.
'''
},
]
},
]
},
{ name: "RESEED_INTERVAL_REGWEN",
desc: "regwen for reseed interval",
swaccess: "rw0c",
hwaccess: "none",
fields: [
{ bits: "0",
name: "EN",
resval: "1"
desc: '''
Configuration enable for reseed interval
'''
},
]
},
{ name: "RESEED_INTERVAL_SHADOWED",
desc: "Reseed interval for key manager entropy reseed",
shadowed: "true",
update_err_alert: "recov_operation_err",
storage_err_alert: "fatal_fault_err",
regwen: "RESEED_INTERVAL_REGWEN",
swaccess: "rw",
hwaccess: "hro",
fields: [
{ bits: "15:0",
name: "VAL",
resval: "0x100"
desc: '''
Number of key manager cycles before the entropy is reseeded
'''
},
]
},
// The following can potentially be replaced by a RAM if it gets too large
// Currently there are 32b * NumSaltReg bits for salt inputs
// 32b * NumSwBindingReg bits for software binding inputs
// 32b * NumOutReg * 2 (if key shares desired) for outputs
// 32b * NumOutReg * NumCryptos * 2 (if key shares desired) for hidden key bus
// This totals to over 2kb of storage
{ name: "SW_BINDING_REGWEN",
desc: "Register write enable for SOFTWARE_BINDING",
swaccess: "rw0c",
hwaccess: "hrw",
hwext: "true",
hwqe: "true",
fields: [
{ bits: "0",
name: "EN",
resval: "1"
desc: '''
Software binding register write enable.
This is locked by software and unlocked by hardware upon a successful advance call.
Software binding resets to 1, and its value cannot be altered by software until advancement to Init state.
'''
},
]
},
{ multireg: {
cname: "KEYMGR",
name: "SEALING_SW_BINDING",
regwen: "SW_BINDING_REGWEN",
desc: '''
Software binding input to sealing portion of the key manager.
This register is lockable and shared between key manager stages.
This binding value is not considered secret, however its integrity is very important.
The software binding is locked by software and unlocked by hardware upon a successful advance operation.
''',
count: "NumSwBindingReg",
swaccess: "rw",
hwaccess: "hro",
fields: [
{ bits: "31:0",
name: "VAL",
desc: '''
Software binding value
''',
resval: "0"
},
],
},
},
{ multireg: {
cname: "KEYMGR",
name: "ATTEST_SW_BINDING",
regwen: "SW_BINDING_REGWEN",
desc: '''
Software binding input to the attestation portion of the key manager.
This register is lockable and shared between key manager stages.
This binding value is not considered secret, however its integrity is very important.
The software binding is locked by software and unlocked by hardware upon a successful advance operation.
''',
count: "NumSwBindingReg",
swaccess: "rw",
hwaccess: "hro",
fields: [
{ bits: "31:0",
name: "VAL",
desc: '''
Software binding value
''',
resval: "0"
},
],
},
},
{ multireg: {
cname: "KEYMGR",
name: "Salt",
regwen: "CFG_REGWEN",
desc: '''
Salt value used as part of output generation
''',
count: "NumSaltReg",
swaccess: "rw",
hwaccess: "hro",
fields: [
{ bits: "31:0",
name: "VAL",
desc: '''
Salt value
''',
resval: "0"
},
],
},
},
{ multireg: {
cname: "KEYMGR",
name: "KEY_VERSION",
regwen: "CFG_REGWEN",
desc: '''
Version used as part of output generation
''',
count: "NumKeyVersion",
swaccess: "rw",
hwaccess: "hro",
fields: [
{ bits: "31:0",
name: "VAL",
desc: '''
Key version
''',
resval: "0"
},
],
},
},
// since there is not a good way to define a separate enable register per multireg
// the following version registers are manually separated
// further, it should be possible to reduce the number of max_versions held
// as long as clearly specify the boot sequence relative to when keys are generated.
// should check with the security team.
//
// The following storage is also huge, should consider switching to RAMs after examining
// the security implications
{ name: "MAX_CREATOR_KEY_VER_REGWEN",
desc: "Register write enable for MAX_CREATOR_KEY_VERSION",
swaccess: "rw0c",
hwaccess: "none",
fields: [
{ bits: "0",
name: "EN",
resval: "1"
desc: '''
MAX_CREATOR_KEY_VERSION configure enable.
'''
},
]
},
{ name: "MAX_CREATOR_KEY_VER_SHADOWED",
desc: "Max creator key version",
swaccess: "rw",
hwaccess: "hro",
shadowed: "true",
update_err_alert: "recov_operation_err",
storage_err_alert: "fatal_fault_err",
regwen: "MAX_CREATOR_KEY_VER_REGWEN",
fields: [
{ bits: "31:0",
name: "VAL",
resval: "0x0"
desc: '''
Max key version.
Any key version up to the value specificed in this register is valid.
'''
},
]
},
{ name: "MAX_OWNER_INT_KEY_VER_REGWEN",
desc: "Register write enable for MAX_OWNER_INT_KEY_VERSION",
swaccess: "rw0c",
hwaccess: "none",
fields: [
{ bits: "0",
name: "EN",
resval: "1"
desc: '''
MAX_OWNER_INTERMEDIATE_KEY configure enable.
'''
},
]
},
{ name: "MAX_OWNER_INT_KEY_VER_SHADOWED",
desc: "Max owner intermediate key version",
swaccess: "rw",
hwaccess: "hro",
shadowed: "true",
update_err_alert: "recov_operation_err",
storage_err_alert: "fatal_fault_err",
regwen: "MAX_OWNER_INT_KEY_VER_REGWEN",
fields: [
{ bits: "31:0",
name: "VAL",
resval: "1"
desc: '''
Max key version.
Any key version up to the value specificed in this register is valid.
'''
},
]
},
{ name: "MAX_OWNER_KEY_VER_REGWEN",
desc: "Register write enable for MAX_OWNER_KEY_VERSION",
swaccess: "rw0c",
hwaccess: "none",
fields: [
{ bits: "0",
name: "EN",
resval: "1"
desc: '''
MAX_OWNER_KEY configure enable.
'''
},
]
},
{ name: "MAX_OWNER_KEY_VER_SHADOWED",
desc: "Max owner key version",
swaccess: "rw",
hwaccess: "hro",
shadowed: "true",
update_err_alert: "recov_operation_err",
storage_err_alert: "fatal_fault_err",
regwen: "MAX_OWNER_KEY_VER_REGWEN",
fields: [
{ bits: "31:0",
name: "VAL",
resval: "0x0"
desc: '''
Max key version.
Any key version up to the value specificed in this register is valid.
'''
},
]
},
{ multireg: {
cname: "KEYMGR",
name: "SW_SHARE0_OUTPUT",
desc: '''
Key manager software output.
When a software output operation is selected, the results of the operation are placed
here.
''',
count: "NumOutReg",
swaccess: "rc",
hwaccess: "hwo",
fields: [
{ bits: "31:0",
name: "VAL",
desc: '''
Software output value
''',
resval: "0"
},
],
tags: [// HW-update reg
// When a fault happens (e.g. when we test TL integrity error), this CSR will be
// wiped with random value.
"excl:CsrNonInitTests:CsrExclCheck"]
},
},
{ multireg: {
cname: "KEYMGR",
name: "SW_SHARE1_OUTPUT",
desc: '''
Key manager software output.
When a software output operation is selected, the results of the operation are placed
here.
''',
count: "NumOutReg",
swaccess: "rc",
hwaccess: "hwo",
fields: [
{ bits: "31:0",
name: "VAL",
desc: '''
Software output value
''',
resval: "0"
},
],
tags: [// HW-update reg
// When a fault happens (e.g. when we test TL integrity error), this CSR will be
// wiped with random value.
"excl:CsrNonInitTests:CsrExclCheck"]
},
},
{ name: "WORKING_STATE",
desc: '''
Key manager working state.
This is a readout of the current key manager working state
''',
swaccess: "ro",
hwaccess: "hwo",
fields: [
{ bits: "2:0",
name: "STATE",
resval: "0x0"
desc: "Key manager control state",
enum: [
{ value: "0",
name: "Reset",
desc: '''
Key manager control is still in reset. Please wait for initialization complete
before issuing operations
'''
},
{ value: "1",
name: "Init",
desc: '''
Key manager control has finished initialization and will now accept
software commands.
'''
},
{ value: "2",
name: "Creator Root Key",
desc: '''
Key manager control currently contains the creator root key.
'''
},
{ value: "3",
name: "Owner Intermediate Key",
desc: '''
Key manager control currently contains the owner intermediate key.
'''
},
{ value: "4",
name: "Owner Key",
desc: '''
Key manager control currently contains the owner key.
'''
},
{ value: "5",
name: "Disabled",
desc: '''
Key manager currently disabled. Please reset the key manager.
Sideload keys are still valid.
'''
},
{ value: "6",
name: "Invalid",
desc: '''
Key manager currently invalid. Please reset the key manager.
Sideload keys are no longer valid.
'''
},
]
}
]
},
{ name: "OP_STATUS",
desc: '''
Key manager status.
Hardware sets the status based on software initiated operations.
This register must be explicitly cleared by software.
Software clears by writing back whatever it reads.
''',
swaccess: "rw1c",
hwaccess: "hwo",
fields: [
{ bits: "1:0",
name: "STATUS",
resval: "0x0"
desc: "Operation status.",
enum: [
{ value: "0",
name: "Idle",
desc: '''
Key manager is idle
'''
},
{ value: "1",
name: "WIP",
desc: '''
Work in progress.
A key manager operation has been started and is ongoing
'''
},
{ value: "2",
name: "DONE_SUCCESS",
desc: '''
Operation finished without errors
'''
},
{ value: "3",
name: "DONE_ERROR",
desc: '''
Operation finished with errors, please see ERR_CODE register.
'''
},
]
},
]
},
{ name: "ERR_CODE",
desc: '''
Key manager error code.
This register must be explicitly cleared by software.
This register represents both synchronous and asynchronous recoverable
errors.
Synchronous errors refer to those that only happen when a keymgr operation is
invoked, while asynchronous refers to errors that can happen at any time.
''',
swaccess: "rw1c",
hwaccess: "hwo",
fields: [
{ bits: "0",
name: "INVALID_OP",
resval: "0x0"
desc: "Invalid operation issued to key manager, synchronous error",
},
{ bits: "1",
name: "INVALID_KMAC_INPUT",
resval: "0x0"
desc: "Invalid data issued to kmac interface, synchronous error",
},
{ bits: "2",
name: "INVALID_SHADOW_UPDATE",
resval: "0x0"
desc: "An error observed during shadow register updates, asynchronous error",
},
]
},
{ name: "FAULT_STATUS",
desc: '''
This register represents both synchronous and asynchronous fatal faults.
Synchronous faults refer to those that only happen when a keymgr operation is
invoked, while asynchronous refers to faults that can happen at any time.
''',
swaccess: "ro",
hwaccess: "hrw",
fields: [
{ bits: "0",
name: "CMD",
resval: "0x0"
desc: "A non-onehot command was seen in kmac, asynchronous fault.",
},
{ bits: "1",
name: "KMAC_FSM",
resval: "0x0"
desc: "The kmac transfer interface FSM is in an invalid state, asynchronous fault.",
},
{ bits: "2",
name: "KMAC_DONE",
resval: "0x0"
desc: "The kmac transfer interface encountered an unexpected done, asynchronous fault.",
},
{ bits: "3",
name: "KMAC_OP",
resval: "0x0"
desc: "KMAC reported an error during keymgr usage, this should never happen - synchronous fault.",
},
{ bits: "4",
name: "KMAC_OUT",
resval: "0x0"
desc: "KMAC data returned as all 0's or all 1's - synchronous fault",
},
{ bits: "5",
name: "REGFILE_INTG",
resval: "0x0"
desc: "Register file integrity error, asynchronous fault",
},
{ bits: "6",
name: "SHADOW",
resval: "0x0"
desc: "Shadow copy storage error, asynchronous fault",
},
{ bits: "7",
name: "CTRL_FSM_INTG",
resval: "0x0"
desc: "Control FSM integrity error, asynchronous fault",
},
{ bits: "8",
name: "CTRL_FSM_CHK",
resval: "0x0"
desc: "Control FSM cross check error, asynchronous fault",
},
{ bits: "9",
name: "CTRL_FSM_CNT",
resval: "0x0"
desc: "Control FSM counter integrity error, asynchronous fault",
},
{ bits: "10",
name: "RESEED_CNT",
resval: "0x0"
desc: "Reseed counter integrity error, asynchronous fault",
},
{ bits: "11",
name: "SIDE_CTRL_FSM",
resval: "0x0"
desc: "Sideload control FSM integrity error, asynchronous fault",
},
{ bits: "12",
name: "SIDE_CTRL_SEL",
resval: "0x0"
desc: "Sideload control key select error, synchronous fault",
},
{ bits: "13",
name: "KEY_ECC",
resval: "0x0"
desc: "Secret key ecc error, asynchronous fault",
},
]
},
{ name: "DEBUG",
desc: '''
The register holds some debug information that may be convenient if keymgr
misbehaves.
''',
swaccess: "rw0c",
hwaccess: "hwo",
fields: [
{ bits: "0",
name: "INVALID_CREATOR_SEED",
resval: "0x0"
desc: "Creator seed failed input checks during operation",
},
{ bits: "1",
name: "INVALID_OWNER_SEED",
resval: "0x0"
desc: "Owner seed failed input checks during operation",
},
{ bits: "2",
name: "INVALID_DEV_ID",
resval: "0x0"
desc: "Device ID failed input checks during operation",
},
{ bits: "3",
name: "INVALID_HEALTH_STATE",
resval: "0x0"
desc: "Health state failed input checks during operation",
},
{ bits: "4",
name: "INVALID_KEY_VERSION",
resval: "0x0"
desc: "Key version failed input checks during operation",
},
{ bits: "5",
name: "INVALID_KEY",
resval: "0x0"
desc: "Key fed to kmac failed input checks during operation",
},
{ bits: "6",
name: "INVALID_DIGEST",
resval: "0x0"
desc: "ROM digest failed input checks during operation",
},
]
},
],
}