5 #include "dt/dt_rv_core_ibex.h"
9 #include "sw/device/lib/dif/dif_rv_core_ibex.h"
12 #include "sw/device/lib/testing/test_framework/check.h"
13 #include "sw/device/lib/testing/test_framework/ottf_isrs.h"
14 #include "sw/device/lib/testing/test_framework/ottf_macros.h"
16 #include "sw/device/silicon_creator/lib/epmp_state.h"
18 #define TEST_STR "Hello there, WHaT 1S Y0Ur N@ME?"
19 #define EXPECTED_RESULT_MAKE_LOWER_CASE "hello there, what 1s y0ur n@me?"
20 #define EXPECTED_RESULT_GET_NAME "My name is Titan, Open Titan"
22 OTTF_DEFINE_TEST_CONFIG();
25 typedef void (*str_fn_t)(
char *);
34 extern void get_name(
char *input);
42 extern void make_lower_case(
char *input);
48 extern void remapped_function(
char *input);
52 kRemapAlignment = 256,
56 const dif_rv_core_ibex_addr_translation_slot_t kSlots[] = {
57 kDifRvCoreIbexAddrTranslationSlot_0, kDifRvCoreIbexAddrTranslationSlot_1};
65 .remap_addr = (uintptr_t)make_lower_case +
66 (uintptr_t)(0xDEADBEEF & (kRemapAlignment - 1)),
67 .size = kRemapAlignment,
72 (uintptr_t)get_name + (uintptr_t)(0xDEADBEEF & (kRemapAlignment - 1)),
73 .size = kRemapAlignment,
77 static volatile bool illegal_instr_fault =
false;
98 void ottf_exception_handler(uint32_t *exc_info) {
113 uintptr_t ret_addr = *(uintptr_t *)(mepc_stack_addr + OTTF_WORD_SIZE);
119 case kIbexExcIllegalInstrFault:
120 LOG_INFO(
"Illegal instruction fault handler");
121 illegal_instr_fault =
true;
122 *(uintptr_t *)mepc_stack_addr = ret_addr;
125 LOG_FATAL(
"Unexpected exception id = 0x%x", exception);
138 void map_to_slot(dif_rv_core_ibex_t *ibex_core,
size_t slot,
139 dif_rv_core_ibex_addr_translation_bus_t bus,
141 CHECK_DIF_OK(dif_rv_core_ibex_configure_addr_translation(
142 ibex_core, kSlots[slot], bus, mapping));
152 void enable_slot(dif_rv_core_ibex_t *ibex_core,
size_t slot,
153 dif_rv_core_ibex_addr_translation_bus_t bus) {
155 dif_rv_core_ibex_enable_addr_translation(ibex_core, kSlots[slot], bus));
165 void disable_slot(dif_rv_core_ibex_t *ibex_core,
size_t slot,
166 dif_rv_core_ibex_addr_translation_bus_t bus) {
168 dif_rv_core_ibex_disable_addr_translation(ibex_core, kSlots[slot], bus));
171 void check_ibus_map(dif_rv_core_ibex_t *ibex_core) {
173 char test_str[] = TEST_STR;
174 make_lower_case(test_str);
175 CHECK_STR_EQ(test_str, EXPECTED_RESULT_MAKE_LOWER_CASE);
178 CHECK_STR_EQ(test_str, EXPECTED_RESULT_GET_NAME);
181 map_to_slot(ibex_core, 1, kDifRvCoreIbexAddrTranslationIBus,
182 kMakeLowerCaseMapping);
185 enable_slot(ibex_core, 1, kDifRvCoreIbexAddrTranslationIBus);
188 memcpy(test_str, TEST_STR,
sizeof(test_str));
191 remapped_function(test_str);
192 CHECK_STR_EQ(test_str, EXPECTED_RESULT_MAKE_LOWER_CASE);
195 map_to_slot(ibex_core, 1, kDifRvCoreIbexAddrTranslationIBus, kGetNameMapping);
198 remapped_function(test_str);
199 CHECK_STR_EQ(test_str, EXPECTED_RESULT_GET_NAME);
206 map_to_slot(ibex_core, 0, kDifRvCoreIbexAddrTranslationIBus,
207 kMakeLowerCaseMapping);
210 enable_slot(ibex_core, 0, kDifRvCoreIbexAddrTranslationIBus);
213 memcpy(test_str, TEST_STR,
sizeof(test_str));
216 remapped_function(test_str);
217 CHECK_STR_EQ(test_str, EXPECTED_RESULT_MAKE_LOWER_CASE);
224 for (
size_t slot_i = 0; slot_i < 2; ++slot_i) {
225 disable_slot(ibex_core, slot_i, kDifRvCoreIbexAddrTranslationIBus);
229 CHECK(!illegal_instr_fault);
232 remapped_function(test_str);
235 CHECK(illegal_instr_fault);
238 void check_dbus_map(dif_rv_core_ibex_t *ibex_core) {
239 CHECK_ARRAYS_NE((uint8_t *)make_lower_case, (uint8_t *)get_name,
241 "make_lower_case and get_name are the same!");
242 CHECK_ARRAYS_NE((uint8_t *)make_lower_case, (uint8_t *)remapped_function,
244 "make_lower_case and remapped_function are the same!");
245 CHECK_ARRAYS_NE((uint8_t *)get_name, (uint8_t *)remapped_function,
247 "get_name and remapped_function are the same!");
250 map_to_slot(ibex_core, 1, kDifRvCoreIbexAddrTranslationDBus,
251 kMakeLowerCaseMapping);
254 enable_slot(ibex_core, 1, kDifRvCoreIbexAddrTranslationDBus);
256 CHECK_ARRAYS_EQ((uint8_t *)make_lower_case, (uint8_t *)remapped_function,
258 "remapped_function is not mapped to make_lower_case!");
261 map_to_slot(ibex_core, 1, kDifRvCoreIbexAddrTranslationDBus, kGetNameMapping);
263 CHECK_ARRAYS_EQ((uint8_t *)get_name, (uint8_t *)remapped_function,
265 "remapped_function is not mapped to get_name!");
272 map_to_slot(ibex_core, 0, kDifRvCoreIbexAddrTranslationDBus,
273 kMakeLowerCaseMapping);
276 enable_slot(ibex_core, 0, kDifRvCoreIbexAddrTranslationDBus);
278 CHECK_ARRAYS_EQ((uint8_t *)make_lower_case, (uint8_t *)remapped_function,
280 "remapped_function is not mapped to make_lower_case!");
287 for (
size_t slot_i = 0; slot_i < 2; ++slot_i) {
288 disable_slot(ibex_core, slot_i, kDifRvCoreIbexAddrTranslationDBus);
291 CHECK_ARRAYS_NE((uint8_t *)make_lower_case, (uint8_t *)remapped_function,
293 "make_lower_case and remapped_function are the same!");
294 CHECK_ARRAYS_NE((uint8_t *)get_name, (uint8_t *)remapped_function,
296 "make_lower_case and remapped_function are the same!");
301 dif_rv_core_ibex_t ibex_core;
302 dt_rv_core_ibex_t kRvCoreIbexDt = (dt_rv_core_ibex_t)0;
303 static_assert(kDtRvCoreIbexCount >= 1,
304 "This test requires at least one Ibex core");
305 CHECK_DIF_OK(dif_rv_core_ibex_init_from_dt(kRvCoreIbexDt, &ibex_core));
307 check_ibus_map(&ibex_core);
308 check_dbus_map(&ibex_core);