5#include "sw/device/silicon_creator/lib/drivers/ibex.h"
7#include "hw/top/dt/dt_rv_core_ibex.h"
13#include "hw/top/rv_core_ibex_regs.h"
21static inline uint32_t rv_core_ibex_base(
void) {
25uint32_t ibex_fpga_version(
void) {
26 const uint32_t kBase = rv_core_ibex_base();
27 return abs_mmio_read32(kBase + RV_CORE_IBEX_FPGA_INFO_REG_OFFSET);
30size_t ibex_addr_remap_slots(
void) {
return RV_CORE_IBEX_PARAM_NUM_REGIONS; }
32void ibex_addr_remap_set(
size_t slot, uint32_t matching_addr,
33 uint32_t remap_addr,
size_t size) {
34 HARDENED_CHECK_LT(slot, RV_CORE_IBEX_PARAM_NUM_REGIONS);
35 const uint32_t kBase = rv_core_ibex_base();
36 slot *=
sizeof(uint32_t);
40 uint32_t match = (matching_addr & ~size) | size >> 1;
43 sec_mmio_write32(kBase + RV_CORE_IBEX_IBUS_ADDR_MATCHING_0_REG_OFFSET + slot,
45 sec_mmio_write32(kBase + RV_CORE_IBEX_DBUS_ADDR_MATCHING_0_REG_OFFSET + slot,
58uint32_t ibex_addr_remap_get(
size_t slot) {
59 const uint32_t kBase = rv_core_ibex_base();
60 HARDENED_CHECK_LT(slot, RV_CORE_IBEX_PARAM_NUM_REGIONS);
61 slot *=
sizeof(uint32_t);
62 if (abs_mmio_read32(kBase + RV_CORE_IBEX_IBUS_ADDR_EN_0_REG_OFFSET + slot)) {
63 return abs_mmio_read32(kBase + RV_CORE_IBEX_IBUS_REMAP_ADDR_0_REG_OFFSET +
70void ibex_addr_remap_lockdown(
size_t slot) {
71 const uint32_t kBase = rv_core_ibex_base();
72 HARDENED_CHECK_LT(slot, RV_CORE_IBEX_PARAM_NUM_REGIONS);
73 slot *=
sizeof(uint32_t);
78bool ibex_addr_remap_is_enabled(
size_t slot) {
79 const uint32_t kBase = rv_core_ibex_base();
80 HARDENED_CHECK_LT(slot, RV_CORE_IBEX_PARAM_NUM_REGIONS);
81 slot *=
sizeof(uint32_t);
85 uint32_t reg_en_i_mask = 1 << RV_CORE_IBEX_DBUS_ADDR_EN_0_EN_0_BIT;
88 uint32_t reg_en_d_mask = 1 << RV_CORE_IBEX_IBUS_ADDR_EN_0_EN_0_BIT;
90 return (reg_en_i & reg_en_i_mask) && (reg_en_d & reg_en_d_mask);
93static bool remap_verify(uint32_t reg_matching, uint32_t reg_remap,
94 uint32_t matching_addr, uint32_t remap_addr,
98 if (reg_matching == 0) {
103 uint32_t reg_matching_size =
104 1 << bitfield_count_trailing_zeroes32(~reg_matching);
105 uint32_t reg_matching_addr = reg_matching & ~(reg_matching_size - 1);
108 if (matching_addr < reg_matching_addr ||
109 matching_addr - reg_matching_addr >= reg_matching_size) {
115 if (size > reg_matching_size - (matching_addr - reg_matching_addr)) {
120 if (remap_addr - matching_addr != reg_remap - reg_matching_addr) {
127bool ibex_addr_remap_verify(
size_t slot, uint32_t matching_addr,
128 uint32_t remap_addr,
size_t size) {
129 const uint32_t kBase = rv_core_ibex_base();
130 HARDENED_CHECK_LT(slot, RV_CORE_IBEX_PARAM_NUM_REGIONS);
131 slot *=
sizeof(uint32_t);
135 kBase + RV_CORE_IBEX_IBUS_ADDR_MATCHING_0_REG_OFFSET + slot);
136 uint32_t reg_remap_addr =
137 sec_mmio_read32(kBase + RV_CORE_IBEX_IBUS_REMAP_ADDR_0_REG_OFFSET + slot);
138 if (!remap_verify(reg_matching, reg_remap_addr, matching_addr, remap_addr,
145 kBase + RV_CORE_IBEX_DBUS_ADDR_MATCHING_0_REG_OFFSET + slot);
147 sec_mmio_read32(kBase + RV_CORE_IBEX_DBUS_REMAP_ADDR_0_REG_OFFSET + slot);
148 if (!remap_verify(reg_matching, reg_remap_addr, matching_addr, remap_addr,
156void ibex_enable_nmi(ibex_nmi_source_t nmi_src) {
157 abs_mmio_write32(rv_core_ibex_base() + RV_CORE_IBEX_NMI_ENABLE_REG_OFFSET,
161void ibex_clear_nmi(ibex_nmi_source_t nmi_src) {
162 abs_mmio_write32(rv_core_ibex_base() + RV_CORE_IBEX_NMI_STATE_REG_OFFSET,
168extern void ibex_mcycle_zero(
void);
169extern uint32_t ibex_mcycle32(
void);
170extern uint64_t ibex_mcycle(
void);
171extern uint64_t ibex_time_to_cycles(uint64_t time_us);