Merge "Add 3 pwrmgr tests to edacloud"
diff --git a/hw/top_matcha/dv/chip_sim_cfg.hjson b/hw/top_matcha/dv/chip_sim_cfg.hjson
index be83664..4452cc6 100644
--- a/hw/top_matcha/dv/chip_sim_cfg.hjson
+++ b/hw/top_matcha/dv/chip_sim_cfg.hjson
@@ -2175,7 +2175,6 @@
"chip_sw_sleep_pin_retention",
"chip_sw_sleep_pin_wake",
"chip_sw_sleep_pwm_pulses",
- "chip_sw_sleep_sram_ret_contents",
"chip_sw_smc_cam_irq_test",
"chip_sw_smc_ctrl_test",
"chip_sw_smc_env_test",
@@ -2210,7 +2209,6 @@
"chip_sw_uart_smoketest",
"chip_sw_uart_tx_rx",
"chip_tap_straps_dev",
- "chip_tap_straps_prod",
"chip_tap_straps_rma",
]
}
diff --git a/sw/device/tests/kelvin/fpga_tests/BUILD b/sw/device/tests/kelvin/fpga_tests/BUILD
index 364d0cf..612828e 100644
--- a/sw/device/tests/kelvin/fpga_tests/BUILD
+++ b/sw/device/tests/kelvin/fpga_tests/BUILD
@@ -23,11 +23,10 @@
"//hw/top_matcha/ip/ml_top/data:ml_top_regs",
"//hw/top_matcha/sw/autogen:top_matcha",
"//sw/device/lib:spi_flash",
+ "//sw/device/lib/dif:rv_plic_sec",
"//sw/device/lib/dif:smc_ctrl",
- "//sw/device/lib/testing/test_framework:ottf_start",
- "//sw/device/lib/testing/test_framework:test_util",
- "@lowrisc_opentitan//sw/device/lib/testing/test_framework:ottf_test_config",
- "@lowrisc_opentitan//sw/device/silicon_creator/lib:manifest_def",
+ "//sw/device/lib/dif:tlul_mailbox",
+ "//sw/device/tests:test_lib",
],
)
@@ -43,11 +42,13 @@
per_device_deps = {
"fpga_nexus": [NEXUS_CORE_TARGETS.get("smc")],
},
- var_name = "kelvin_test_smc_fpga_nexus_bin",
deps = [
+ "//hw/top_matcha/ip/ml_top/data:ml_top_regs",
"//hw/top_matcha/sw/autogen:top_matcha",
- "//sw/device/lib/testing/test_framework:ottf_start_smc",
- "//sw/device/lib/testing/test_framework:test_util",
- "@lowrisc_opentitan//sw/device/lib/testing/test_framework:ottf_test_config",
+ "//sw/device/lib/dif:ml_top",
+ "//sw/device/lib/dif:rv_plic_smc",
+ "//sw/device/lib/dif:tlul_mailbox",
+ "//sw/device/tests:test_lib_smc",
+ "@lowrisc_opentitan//sw/device/lib/dif:rv_timer",
],
)
diff --git a/sw/device/tests/kelvin/fpga_tests/kelvin_test_sc.c b/sw/device/tests/kelvin/fpga_tests/kelvin_test_sc.c
index 0031960..4887bd2 100644
--- a/sw/device/tests/kelvin/fpga_tests/kelvin_test_sc.c
+++ b/sw/device/tests/kelvin/fpga_tests/kelvin_test_sc.c
@@ -3,8 +3,11 @@
#include "hw/top_matcha/ip/ml_top/data/ml_top_regs.h" // Generated.
#include "hw/top_matcha/sw/autogen/top_matcha.h"
#include "sw/device/lib/arch/device.h"
+#include "sw/device/lib/dif/dif_rv_plic.h"
#include "sw/device/lib/dif/dif_smc_ctrl.h"
+#include "sw/device/lib/dif/dif_tlul_mailbox.h"
#include "sw/device/lib/dif/dif_uart.h"
+#include "sw/device/lib/runtime/irq.h"
#include "sw/device/lib/runtime/print.h"
#include "sw/device/lib/spi_flash.h"
#include "sw/device/lib/testing/test_framework/check.h"
@@ -13,16 +16,31 @@
#include "sw/device/lib/testing/test_framework/test_util.h"
/*
- * Sample program to run some code on all cores in the system.
- * SC - Orchestrate the other cores, print status to UART.
- * SMC - Print to UART.
- * Kelvin - SW program built to run on Kelvin.
+ * SC - Initialize SMC, load kelvin program, and print status to UART.
+ * SMC - Print to UART and orchestrate ML core/programs.
*/
OTTF_DEFINE_TEST_CONFIG();
static dif_smc_ctrl_t smc_ctrl;
static dif_uart_t uart;
+static dif_rv_plic_t plic_sec;
+static dif_tlul_mailbox_t tlul_mailbox;
+
+volatile uint32_t message;
+
+void ottf_external_isr(void) {
+ dif_rv_plic_irq_id_t plic_irq_id;
+ uint32_t rx;
+ CHECK_DIF_OK(dif_rv_plic_irq_claim(&plic_sec, kTopMatchaPlicTargetIbex0,
+ &plic_irq_id));
+ CHECK_DIF_OK(
+ dif_tlul_mailbox_irq_acknowledge(&tlul_mailbox, kDifTlulMailboxIrqRtirq));
+ CHECK_DIF_OK(dif_tlul_mailbox_read_message(&tlul_mailbox, &rx));
+ message = rx;
+ CHECK_DIF_OK(dif_rv_plic_irq_complete(&plic_sec, kTopMatchaPlicTargetIbex0,
+ plic_irq_id));
+}
void _ottf_main(void) {
test_status_set(kTestStatusInTest);
@@ -44,17 +62,33 @@
mmio_region_write32(ml_dmem, i * sizeof(uint32_t), 0);
}
+ // Setup mailbox.
+ CHECK_DIF_OK(dif_tlul_mailbox_init(
+ mmio_region_from_addr(TOP_MATCHA_TLUL_MAILBOX_SEC_BASE_ADDR),
+ &tlul_mailbox));
+ CHECK_DIF_OK(dif_tlul_mailbox_irq_set_enabled(
+ &tlul_mailbox, kDifTlulMailboxIrqRtirq, kDifToggleEnabled));
+ CHECK_DIF_OK(dif_tlul_mailbox_irq_set_enabled(
+ &tlul_mailbox, kDifTlulMailboxIrqWtirq, kDifToggleEnabled));
+ CHECK_DIF_OK(dif_tlul_mailbox_irq_set_enabled(
+ &tlul_mailbox, kDifTlulMailboxIrqEirq, kDifToggleEnabled));
+
+ // Set Interrupt.
+ CHECK_DIF_OK(dif_rv_plic_init(
+ mmio_region_from_addr(TOP_MATCHA_RV_PLIC_BASE_ADDR), &plic_sec));
+ CHECK_DIF_OK(dif_rv_plic_irq_set_enabled(
+ &plic_sec, kTopMatchaPlicIrqIdTlulMailboxSecRtirq,
+ kTopMatchaPlicTargetIbex0, kDifToggleEnabled));
+ CHECK_DIF_OK(dif_rv_plic_irq_set_priority(
+ &plic_sec, kTopMatchaPlicIrqIdTlulMailboxSecRtirq, 1));
+ irq_global_ctrl(true);
+ irq_external_ctrl(true);
+
// Enable SMC.
CHECK_DIF_OK(dif_smc_ctrl_init(
mmio_region_from_addr(TOP_MATCHA_SMC_CTRL_BASE_ADDR), &smc_ctrl));
CHECK_DIF_OK(dif_smc_ctrl_set_en(&smc_ctrl));
- // Reset and Freeze Kelvin.
- mmio_region_t base_addr =
- mmio_region_from_addr(TOP_MATCHA_ML_TOP_CORE_BASE_ADDR);
- mmio_region_write32(base_addr, ML_TOP_CTRL_REG_OFFSET,
- ML_TOP_CTRL_REG_RESVAL | (1 << ML_TOP_CTRL_FREEZE_BIT));
-
// Copy binary to ML_DMEM.
char kelvin_bin_name[256] = {'\0'};
size_t bin_offset = 0;
@@ -70,32 +104,15 @@
CHECK_DIF_OK(kelvin_load_result, "Failed to load %s", kelvin_bin_name);
test_num++;
LOG_INFO("Test %d: Run kelvin binary %s", test_num, kelvin_bin_name);
- // Start up Kelvin.
- mmio_region_write32(base_addr, ML_TOP_CTRL_REG_OFFSET, 0x0);
- uint32_t intr_state =
- mmio_region_read32(base_addr, ML_TOP_INTR_STATE_REG_OFFSET);
- // TODO(ykwang): Change this to interrupt handler.
- while (intr_state == 0x0) {
- busy_spin_micros(10 * 1000); // Wait for 10ms.
- intr_state = mmio_region_read32(base_addr, ML_TOP_INTR_STATE_REG_OFFSET);
- }
- // Received interrupts from Kelvin core, check if only FINISH asserted
- if (intr_state != (1 << ML_TOP_INTR_STATE_FINISH_BIT)) {
- LOG_ERROR("INTR_STATE read out: expected : 0x%x | actual: 0x%x",
- (1 << ML_TOP_INTR_STATE_FINISH_BIT), intr_state);
+ uint32_t tx = 0;
+ // Send to smc to kickoff ML program
+ CHECK_DIF_OK(dif_tlul_mailbox_send_message(&tlul_mailbox, &tx));
+ // Wait for mailbox interrupt
+ asm volatile("wfi");
+ if (message != (1 << ML_TOP_INTR_STATE_FINISH_BIT)) {
+ LOG_ERROR(" Test finish with fault");
failed_test++;
}
- // Reset and halt Kelvin
- mmio_region_write32(base_addr, ML_TOP_CTRL_REG_OFFSET,
- ML_TOP_CTRL_REG_RESVAL | (1 << ML_TOP_CTRL_FREEZE_BIT));
- // Write 1 to clear INTR_STATE
- mmio_region_write32(base_addr, ML_TOP_INTR_STATE_REG_OFFSET, intr_state);
- intr_state = mmio_region_read32(base_addr, ML_TOP_INTR_STATE_REG_OFFSET);
- CHECK(
- intr_state == 0,
- "ML_TOP_Core offset 0 INTR_STATE read again - Expected: 0 | Actual: "
- "0x%x",
- intr_state);
}
LOG_INFO("Total test: %d, failed test: %d", test_num, failed_test);
if (failed_test == 0) {
diff --git a/sw/device/tests/kelvin/fpga_tests/kelvin_test_smc.c b/sw/device/tests/kelvin/fpga_tests/kelvin_test_smc.c
index ec9f4a8..916b4c8 100644
--- a/sw/device/tests/kelvin/fpga_tests/kelvin_test_smc.c
+++ b/sw/device/tests/kelvin/fpga_tests/kelvin_test_smc.c
@@ -1,17 +1,167 @@
+#include "hw/top_matcha/ip/ml_top/data/ml_top_regs.h" // Generated.
#include "hw/top_matcha/sw/autogen/top_matcha.h"
#include "sw/device/lib/arch/device.h"
+#include "sw/device/lib/dif/dif_ml_top.h"
+#include "sw/device/lib/dif/dif_rv_plic.h"
+#include "sw/device/lib/dif/dif_rv_timer.h"
+#include "sw/device/lib/dif/dif_tlul_mailbox.h"
#include "sw/device/lib/dif/dif_uart.h"
+#include "sw/device/lib/runtime/irq.h"
#include "sw/device/lib/runtime/print.h"
#include "sw/device/lib/testing/test_framework/check.h"
#include "sw/device/lib/testing/test_framework/ottf_test_config.h"
#include "sw/device/lib/testing/test_framework/test_util.h"
+/*
+ * Sample program to run some code on all cores in the system.
+ * SMC - Print to UART and orchestrate ML core/programs.
+ * Kelvin - SW program built to run on Kelvin.
+ */
+
OTTF_DEFINE_TEST_CONFIG();
static dif_uart_t smc_uart;
+static dif_tlul_mailbox_t tlul_mailbox;
+static dif_rv_plic_t plic_smc;
+static dif_rv_timer_t rv_timer;
+static dif_ml_top_t ml_top;
+
+static volatile bool ml_top_done = false;
+static volatile bool bin_loaded = false;
+static volatile uint32_t ml_result = 0;
+
+void ottf_external_isr(void) {
+ dif_rv_plic_irq_id_t plic_irq_id;
+ CHECK_DIF_OK(dif_rv_plic_irq_claim(&plic_smc, kTopMatchaPlicTargetIbex0Smc,
+ &plic_irq_id));
+ top_matcha_plic_peripheral_smc_t peripheral_id =
+ top_matcha_plic_interrupt_for_peripheral_smc[plic_irq_id];
+ CHECK(peripheral_id == kTopMatchaPlicPeripheralTlulMailboxSmc ||
+ peripheral_id == kTopMatchaPlicPeripheralMlTop,
+ "Unexpected peripheral in ISR: %d", peripheral_id);
+ switch (peripheral_id) {
+ case kTopMatchaPlicPeripheralTlulMailboxSmc: {
+ uint32_t rx;
+ CHECK_DIF_OK(dif_tlul_mailbox_irq_acknowledge(&tlul_mailbox,
+ kDifTlulMailboxIrqRtirq));
+ CHECK_DIF_OK(dif_tlul_mailbox_read_message(&tlul_mailbox, &rx));
+ bin_loaded = true;
+ break;
+ }
+ case kTopMatchaPlicPeripheralMlTop: {
+ mmio_region_t base_addr =
+ mmio_region_from_addr(TOP_MATCHA_ML_TOP_CORE_BASE_ADDR);
+ // Reset and halt Kelvin
+ mmio_region_write32(
+ base_addr, ML_TOP_CTRL_REG_OFFSET,
+ ML_TOP_CTRL_REG_RESVAL | (1 << ML_TOP_CTRL_FREEZE_BIT));
+ ml_result = mmio_region_read32(base_addr, ML_TOP_INTR_STATE_REG_OFFSET);
+ // Write 1 to clear INTR_STATE
+ mmio_region_write32(base_addr, ML_TOP_INTR_STATE_REG_OFFSET, ml_result);
+ uint32_t intr_state =
+ mmio_region_read32(base_addr, ML_TOP_INTR_STATE_REG_OFFSET);
+ CHECK(intr_state == 0,
+ "ML Top interrupt reset failed: expect 0, actual 0x%x", intr_state);
+ ml_top_done = true;
+ break;
+ }
+ default:
+ LOG_FATAL("Peripheral is not implemented!");
+ }
+ CHECK_DIF_OK(dif_rv_plic_irq_complete(&plic_smc, kTopMatchaPlicTargetIbex0Smc,
+ plic_irq_id));
+}
+
+/*
+ * Configures all the relevant interrupts in PLIC_SMC.
+ */
+static void plic_smc_configure_irqs(dif_rv_plic_t *plic) {
+ // Set ML_TOP IRQ priorities to MAX
+ CHECK_DIF_OK(dif_rv_plic_irq_set_priority(
+ plic, kTopMatchaPlicIrqIdMlTopFinish, kDifRvPlicMaxPriority));
+ CHECK_DIF_OK(dif_rv_plic_irq_set_priority(plic, kTopMatchaPlicIrqIdMlTopFault,
+ kDifRvPlicMaxPriority));
+ // Set Ibex IRQ priority threshold level
+ CHECK_DIF_OK(dif_rv_plic_target_set_threshold(
+ plic, kTopMatchaPlicTargetIbex0Smc, kDifRvPlicMinPriority));
+
+ // Enable Mailbox IRQs
+ CHECK_DIF_OK(dif_rv_plic_irq_set_enabled(
+ plic, kTopMatchaPlicIrqIdTlulMailboxSmcRtirq,
+ kTopMatchaPlicTargetIbex0Smc, kDifToggleEnabled));
+ CHECK_DIF_OK(dif_rv_plic_irq_set_priority(
+ plic, kTopMatchaPlicIrqIdTlulMailboxSmcRtirq, 1));
+ // Enable ML core IRQs
+ CHECK_DIF_OK(dif_rv_plic_irq_set_enabled(plic, kTopMatchaPlicIrqIdMlTopFinish,
+ kTopMatchaPlicTargetIbex0Smc,
+ kDifToggleEnabled));
+ CHECK_DIF_OK(dif_rv_plic_irq_set_enabled(plic, kTopMatchaPlicIrqIdMlTopFault,
+ kTopMatchaPlicTargetIbex0Smc,
+ kDifToggleEnabled));
+}
void _ottf_main(void) {
init_uart(TOP_MATCHA_SMC_UART_BASE_ADDR, &smc_uart);
LOG_INFO("kelvin_test_smc");
- asm volatile("wfi");
+
+ // Configure Mailbox.
+ CHECK_DIF_OK(dif_tlul_mailbox_init(
+ mmio_region_from_addr(TOP_MATCHA_TLUL_MAILBOX_SMC_BASE_ADDR),
+ &tlul_mailbox));
+ CHECK_DIF_OK(dif_tlul_mailbox_irq_set_enabled(
+ &tlul_mailbox, kDifTlulMailboxIrqRtirq, kDifToggleEnabled));
+ CHECK_DIF_OK(dif_tlul_mailbox_irq_set_enabled(
+ &tlul_mailbox, kDifTlulMailboxIrqWtirq, kDifToggleEnabled));
+ CHECK_DIF_OK(dif_tlul_mailbox_irq_set_enabled(
+ &tlul_mailbox, kDifTlulMailboxIrqEirq, kDifToggleEnabled));
+
+ // Init ML_TOP
+ CHECK_DIF_OK(dif_ml_top_init(
+ mmio_region_from_addr(TOP_MATCHA_ML_TOP_CORE_BASE_ADDR), &ml_top));
+ CHECK_DIF_OK(dif_ml_top_irq_set_enabled(&ml_top, kDifMlTopIrqFinish,
+ kDifToggleEnabled));
+ CHECK_DIF_OK(dif_ml_top_irq_set_enabled(&ml_top, kDifMlTopIrqFault,
+ kDifToggleEnabled));
+ dif_ml_top_reset_ctrl_en(&ml_top);
+
+ // Set interrupt.
+ CHECK_DIF_OK(dif_rv_plic_init(
+ mmio_region_from_addr(TOP_MATCHA_RV_PLIC_SMC_BASE_ADDR), &plic_smc));
+ plic_smc_configure_irqs(&plic_smc);
+ irq_global_ctrl(true);
+ irq_external_ctrl(true);
+
+ // Set timer.
+ dif_rv_timer_tick_params_t tick_params;
+ CHECK_DIF_OK(dif_rv_timer_init(
+ mmio_region_from_addr(TOP_MATCHA_RV_TIMER_SMC_BASE_ADDR), &rv_timer));
+ CHECK_DIF_OK(dif_rv_timer_approximate_tick_params(kClockFreqPeripheralHz,
+ 1000, &tick_params));
+ CHECK_DIF_OK(dif_rv_timer_set_tick_params(&rv_timer, 0, tick_params));
+ CHECK_DIF_OK(
+ dif_rv_timer_counter_set_enabled(&rv_timer, 0, kDifToggleEnabled));
+
+ uint32_t bin_index = 0;
+ while (true) {
+ uint64_t timer_start, timer_end;
+ bin_loaded = false;
+ while (!bin_loaded) {
+ asm volatile("wfi");
+ }
+ // Start up Kelvin.
+ ml_top_done = false;
+ ml_result = 0;
+ CHECK_DIF_OK(dif_rv_timer_counter_read(&rv_timer, 0, &timer_start));
+ mmio_region_t base_addr =
+ mmio_region_from_addr(TOP_MATCHA_ML_TOP_CORE_BASE_ADDR);
+ mmio_region_write32(base_addr, ML_TOP_CTRL_REG_OFFSET, 0x0);
+ while (!ml_top_done) {
+ asm volatile("wfi");
+ }
+ CHECK_DIF_OK(dif_rv_timer_counter_read(&rv_timer, 0, &timer_end));
+ LOG_INFO("Test %d: Finish in %d ms", ++bin_index,
+ (uint32_t)(timer_end - timer_start));
+ uint32_t tx = ml_result;
+ CHECK_DIF_OK(dif_tlul_mailbox_send_message(&tlul_mailbox, &tx));
+ }
}