15 #include "sw/device/lib/dif/dif_rv_core_ibex.h"
19 #include "sw/device/lib/runtime/irq.h"
21 #include "sw/device/lib/testing/alert_handler_testutils.h"
22 #include "sw/device/lib/testing/lc_ctrl_testutils.h"
23 #include "sw/device/lib/testing/ret_sram_testutils.h"
24 #include "sw/device/lib/testing/rstmgr_testutils.h"
25 #include "sw/device/lib/testing/rv_plic_testutils.h"
26 #include "sw/device/lib/testing/test_framework/FreeRTOSConfig.h"
27 #include "sw/device/lib/testing/test_framework/check.h"
30 #include "alert_handler_regs.h"
42 OTTF_DEFINE_TEST_CONFIG();
62 static dif_alert_handler_t alert_handler;
63 static dif_lc_ctrl_t lc_ctrl;
64 static dif_rstmgr_t rstmgr;
67 static dif_rv_plic_t plic;
68 static dif_rv_core_ibex_t rv_core_ibex;
71 static volatile bool alert_irq_seen =
false;
80 .duration_cycles = 10000},
83 .duration_cycles = 10000}};
87 .accumulator_threshold = 0,
88 .irq_deadline_cycles = 0,
89 .escalation_phases = kEscProfiles,
90 .escalation_phases_len = 2,
95 typedef void (*FaultCheckerFunction)(bool,
const char *inst);
98 FaultCheckerFunction
function;
107 uint32_t function_addr = (uint32_t)(
fault_checker->function);
110 ret_sram_testutils_scratch_write(kScratchFunction, 1, &function_addr));
112 ret_sram_testutils_scratch_write(kScratchIpInst, 1, &ip_inst_addr));
116 CHECK_STATUS_OK(ret_sram_testutils_scratch_read(
117 kScratchFunction, 1, (uint32_t *)&(
fault_checker->function)));
118 CHECK_STATUS_OK(ret_sram_testutils_scratch_read(
122 static const char *lc_ctrl_inst_name =
"lc_ctrl";
125 static void lc_ctrl_fault_checker(
bool enable,
const char *ip_inst) {
131 uint32_t relevant_status =
status & mask;
132 uint32_t fatal_prog_error =
134 uint32_t expected_status = enable ? fatal_prog_error : 0;
135 CHECK(relevant_status == expected_status,
136 "For %s got codes 0x%x, expected 0x%x", ip_inst, relevant_status,
147 void ottf_external_isr(uint32_t *exc_info) {
150 LOG_INFO(
"At regular external ISR");
154 CHECK_STATUS_OK(ret_sram_testutils_counter_increment(kCounterInterrupt));
167 CHECK(
false,
"Unexpected aon timer interrupt %d", irq);
181 CHECK_DIF_OK(dif_alert_handler_irq_set_enabled(&alert_handler, irq,
194 alert_irq_seen =
true;
196 LOG_INFO(
"Regular external ISR exiting");
204 void ottf_external_nmi_handler(uint32_t *exc_info) {
209 CHECK_STATUS_OK(ret_sram_testutils_counter_increment(kCounterNmi));
213 CHECK_DIF_OK(dif_rv_core_ibex_get_nmi_state(
216 "Alert handler NMI state not expected:\n\t"
217 "alert_enable:%x\n\talert_raised:%x\n",
220 "Watchdog NMI state not expected:\n\t"
221 "wdog_enabled:%x\n\twdog_barked:%x\n",
227 &alert_handler, kDifAlertHandlerClassA, &state));
231 bool is_cause =
false;
242 void check_alert_dump(
void) {
252 for (
int i = 0; i < seg_size; i++) {
253 LOG_INFO(
"DUMP:%d: 0x%x", i, dump[i]);
256 CHECK(seg_size <= INT_MAX,
"seg_size must fit in int");
258 alert_handler_testutils_info_parse(dump, (
int)seg_size, &actual_info));
259 LOG_INFO(
"The alert info crash dump:");
260 alert_handler_testutils_info_dump(&actual_info);
262 for (
int i = 0; i < ALERT_HANDLER_PARAM_N_ALERTS; ++i) {
264 CHECK(actual_info.alert_cause[i],
"Expected alert cause %d to be set", i);
268 if (actual_info.alert_cause[i]) {
269 LOG_INFO(
"Unexpected alert cause %d, may be triggered by %d", i,
278 irq_global_ctrl(
true);
279 irq_external_ctrl(
true);
282 CHECK_DIF_OK(dif_rv_core_ibex_init(
286 CHECK_DIF_OK(dif_lc_ctrl_init(
289 CHECK_DIF_OK(dif_rstmgr_init(
292 CHECK_DIF_OK(dif_alert_handler_init(
298 rstmgr_testutils_reason_clear();
300 ret_sram_testutils_init();
304 "Wrong reset reason %02X", rst_info);
307 LOG_INFO(
"Booting for the first time: starting test");
309 CHECK_STATUS_OK(ret_sram_testutils_counter_clear(kCounterReset));
310 CHECK_STATUS_OK(ret_sram_testutils_counter_clear(kCounterInterrupt));
311 CHECK_STATUS_OK(ret_sram_testutils_counter_clear(kCounterNmi));
313 LOG_INFO(
"Enabling rstmgr alert info capture");
317 LOG_INFO(
"Configuring alert handlers");
327 &alert_handler, kDifAlertHandlerClassA, kConfigProfiles[0],
331 LOG_INFO(
"Configuring fault checker");
336 LOG_INFO(
"Saving fault checker to Flash");
340 LOG_INFO(
"Enabling watchdog and alert NMIs");
342 CHECK_DIF_OK(dif_rv_core_ibex_enable_nmi(&rv_core_ibex,
343 kDifRvCoreIbexNmiSourceAlert));
344 CHECK_DIF_OK(dif_rv_core_ibex_enable_nmi(&rv_core_ibex,
345 kDifRvCoreIbexNmiSourceWdog));
353 ret_sram_testutils_scratch_write(kScratchLcState, 1, &state));
356 LOG_INFO(
"Begin life cycle transition");
364 LOG_INFO(
"Configuring lc transition to scrap state");
373 "Got unexpected lc-side error");
374 LOG_INFO(
"lc STATUS:0x%x", lc_status);
380 LOG_INFO(
"Booting for the second time due to escalation reset");
383 uint32_t interrupt_count = 0;
385 ret_sram_testutils_counter_get(kCounterInterrupt, &interrupt_count));
386 uint32_t nmi_count = 0;
387 CHECK_STATUS_OK(ret_sram_testutils_counter_get(kCounterNmi, &nmi_count));
389 LOG_INFO(
"Interrupt count %d", interrupt_count);
390 LOG_INFO(
"NMI count %d", nmi_count);
392 CHECK(interrupt_count == 0,
393 "Regular ISR should not run for "
394 "kTopEarlgreyAlertIdLcCtrlFatalProgError");
395 CHECK(nmi_count == 0,
396 "NMI should not run for kTopEarlgreyAlertIdLcCtrlFatalProgError");
399 uint32_t reset_count;
400 CHECK_STATUS_OK(ret_sram_testutils_counter_get(kCounterReset,
401 (uint32_t *)&reset_count));
402 LOG_INFO(
"Reset counter value: %u", reset_count);
403 CHECK(reset_count <= 1,
"Too many resets, expected only one non-POR");
406 CHECK_STATUS_OK(ret_sram_testutils_counter_increment(kCounterReset));
409 bool is_cause =
true;
424 CHECK_STATUS_OK(ret_sram_testutils_scratch_read(kScratchLcState, 1,
425 (uint32_t *)&prior_state));
426 CHECK(state == prior_state,
"Unexpected lc state change");
430 LOG_FATAL(
"unexpected reset info %d", rst_info);