blob: 9bfdb9f3b3112e057cf0cf526428a6fd99535ab6 [file] [log] [blame]
// Copyright lowRISC contributors.
// Licensed under the Apache License, Version 2.0, see LICENSE for details.
// SPDX-License-Identifier: Apache-2.0
#ifndef OPENTITAN_SW_DEVICE_LIB_DIF_DIF_SRAM_CTRL_H_
#define OPENTITAN_SW_DEVICE_LIB_DIF_DIF_SRAM_CTRL_H_
/**
* @file
* @brief <a href="/hw/ip/sram_ctrl/doc/">SRAM Controller</a> Device Interface
* Functions
*/
#include <stdint.h>
#include "sw/device/lib/dif/autogen/dif_sram_ctrl_autogen.h"
#ifdef __cplusplus
extern "C" {
#endif // __cplusplus
/**
* SRAM Controller status information bitfield.
*/
typedef uint32_t dif_sram_ctrl_status_bitfield_t;
/**
* SRAM Controller status flags.
*
* Invariants are used to extract information encoded in
* `dif_sram_ctrl_status_bitfield_t`.
*
* More than one status flag can be set at the same time, and a caller may use
* these invariants to look-up individual or a group of flags.
*
* Note: these must match the autogenerated register definition bit offsets.
*/
typedef enum dif_sram_ctrl_status {
/**
* Bus integrity fault is detected. This error triggers a fatal_error alert.
* This condition is terminal.
*/
kDifSramCtrlStatusBusIntegErr = 0x1,
/**
* Initialization counter has reached an invalid state. This error triggers
* a fatal_error alert. This condition is terminal.
*/
kDifSramCtrlStatusInitErr = (0x1 << 1),
/**
* SRAM Controller has received an escalate request, the scrambling keys have
* been reset to the default values and all subsequent memory requests will
* be blocked. This condition is terminal.
*/
kDifSramCtrlStatusEscalated = (0x1 << 2),
/**
* New scrambling key has been successfully obtained from OTP. If the flag is
* not set, the SRAM contents are still scrambled, but a default all-zero key
* and nonce are used to do so.
*/
kDifSramCtrlStatusScrKeyValid = (0x1 << 3),
/**
* Scrambling key has been derived from a valid key seed in OTP. When
* `kDifSramCtrlStatusScrKeyValid` is set, but this flag is unset - the
* scrambling key is still ephemeral (i.e., it is derived using entropy from
* CSRNG), but a default all-zero value is used as the key seed. This could
* happen when the scrambling key seeds have not yet been provisioned to OTP.
*/
kDifSramCtrlStatusScrKeySeedValid = (0x1 << 4),
/**
* Hardware initialization triggered via `dif_sram_ctrl_scramble` or
* `dif_sram_ctrl_wipe` has completed.
*/
kDifSramCtrlStatusInitDone = (0x1 << 5),
} dif_sram_ctrl_status_t;
/**
* SRAM Controller lockable functionality.
*/
typedef enum dif_sram_ctrl_lock {
/**
* SRAM scrambling key renewal and "wiping" lock, which includes the following
* API: `dif_sram_ctrl_scramble`, `dif_sram_ctrl_request_new_key`
* and `dif_sram_ctrl_wipe`.
*/
kDifSramCtrlLockCtrl = 0,
/**
* Code execution from SRAM lock, which includes the following API:
* `dif_sram_ctrl_exec_set_enabled`.
*
* Note: this setting may not be available depending on the OTP configuration
* of the chip (EN_SRAM_IFETCH fuse).
*/
kDifSramCtrlLockExec,
} dif_sram_ctrl_lock_t;
/**
* Performs blocking SRAM scrambling operation.
*
* This function should only be called when the data is no longer used.
*
* This is a compound operation covering both data and address "scrambling".
* In other words logical re-mapping of the physical addresses and data
* scrambling, followed by the entire SRAM overwriting with a pseudo-random
* data.
*
* The intention of this operation is to ensure that there is no predefined
* values or predictable data that could potentially make "unscrambling"
* easier.
*
* This operation is expected to take a significant amount of CPU cycles. If
* a non-blocking alternative is required, then `dif_sram_ctrl_request_new_key`,
* should be used followed by `dif_sram_ctrl_wipe`. The status of these
* operations can be found through `dif_sram_ctrl_get_status`.
*
* Note: when dealing with the Main RAM, additional implication is that the
* C runtime can be invalidated by the call to this function, and must be
* re-configured prior to any C code execution.
*
* @param sram_ctrl A SRAM Controller handle.
* @return The result of the operation.
*/
OT_WARN_UNUSED_RESULT
dif_result_t dif_sram_ctrl_scramble(const dif_sram_ctrl_t *sram_ctrl);
/**
* Requests a new scrambling key.
*
* This function should only be called when the data is no longer used.
*
* On successful completion SRAM addresses (due to different logical mapping of
* the physical addresses) and the data are scrambled. However, it is
* recommended to additionally overwrite SRAM with pseudo-random data by calling
* `dif_sram_ctrl_wipe`. This should minimize the chances of revealing the XOR
* key-stream.
*
* This operation is expected to take a significant amount of CPU cycles. The
* status can be checked via `kDifSramCtrlStatusScrKeyValid`, which is useful
* when a non-blocking work flow is desirable. Otherwise any SRAM access will
* automatically block until this operation has finished.
*
* Note: when dealing with the Main RAM, additional implication is that the
* C runtime can be invalidated by the call to this function, and must be
* re-configured prior to any C code execution.
*
* @param sram_ctrl A SRAM Controller handle.
* @return The result of the operation.
*/
OT_WARN_UNUSED_RESULT
dif_result_t dif_sram_ctrl_request_new_key(const dif_sram_ctrl_t *sram_ctrl);
/**
* Overwrites "wipes" the entire SRAM with pseudo-random data.
*
* This function should only be called when the data is no longer used.
*
* This operation is expected to take a significant amount of CPU cycles. The
* status can be checked via `kDifSramCtrlStatusInitDone`, which is useful when
* a non-blocking work flow is desirable. Otherwise any SRAM access will
* automatically block until this operation has finished.
*
* Note: when dealing with the Main RAM, additional implication is that the
* C runtime can be invalidated by the call to this function, and must be
* re-configured prior to any C code execution.
*
* @param sram_ctrl A SRAM Controller handle.
* @return The result of the operation.
*/
OT_WARN_UNUSED_RESULT
dif_result_t dif_sram_ctrl_wipe(const dif_sram_ctrl_t *sram_ctrl);
/**
* Checks whether execution from SRAM is currently enabled or disabled.
*
* @param sram_ctrl A SRAM Controller handle.
* @param[out] state Out-param toggle state of the SRAM execution.
* @return The result of the operation.
*/
OT_WARN_UNUSED_RESULT
dif_result_t dif_sram_ctrl_exec_get_enabled(const dif_sram_ctrl_t *sram_ctrl,
dif_toggle_t *state);
/**
* Sets whether execution from SRAM enabled or disabled.
*
* @param sram_ctrl A SRAM Controller handle.
* @param state The new toggle state for the SRAM execution.
* @return The result of the operation.
*/
OT_WARN_UNUSED_RESULT
dif_result_t dif_sram_ctrl_exec_set_enabled(const dif_sram_ctrl_t *sram_ctrl,
dif_toggle_t state);
/**
* Queries the SRAM Controller status.
*
* `dif_sram_ctrl_status_t` is used to then extract individual status bits.
*
* @param sram_ctrl A SRAM Controller handle.
* @param[out] SRAM Controller status bitfield.
* @return The result of the operation.
*/
OT_WARN_UNUSED_RESULT
dif_result_t dif_sram_ctrl_get_status(const dif_sram_ctrl_t *sram_ctrl,
dif_sram_ctrl_status_bitfield_t *status);
/**
* Locks out requested SRAM Controller functionality.
*
* This function is reentrant: calling it while functionality is locked will
* have no effect and return `kDifOk`.
*
* @param sram_ctrl A SRAM Controller handle.
* @param lock SRAM functionality to lock.
* @return The result of the operation.
*/
OT_WARN_UNUSED_RESULT
dif_result_t dif_sram_ctrl_lock(const dif_sram_ctrl_t *sram_ctrl,
dif_sram_ctrl_lock_t lock);
/**
* Checks whether requested SRAM Controller functionality is locked.
*
* @param sram_ctrl A SRAM Controller handle.
* @param lock SRAM functionality to query locked state for.
* @param[out] is_locked Out-param for the locked state.
* @return The result of the operation.
*/
OT_WARN_UNUSED_RESULT
dif_result_t dif_sram_ctrl_is_locked(const dif_sram_ctrl_t *sram_ctrl,
dif_sram_ctrl_lock_t lock,
bool *is_locked);
#ifdef __cplusplus
} // extern "C"
#endif // __cplusplus
#endif // OPENTITAN_SW_DEVICE_LIB_DIF_DIF_SRAM_CTRL_H_