12 #include "sw/device/lib/runtime/irq.h"
14 #include "sw/device/lib/testing/spi_device_testutils.h"
15 #include "sw/device/lib/testing/test_framework/check.h"
17 #include "sw/device/lib/testing/test_framework/status.h"
20 #include "sw/device/lib/testing/autogen/isr_testutils.h"
22 OTTF_DEFINE_TEST_CONFIG();
25 static dif_pinmux_t pinmux;
26 static dif_rv_plic_t plic;
30 kTpmWriteCommand = 0x0,
31 kTpmReadCommand = 0x80,
32 kTpmCommandMask = 0xbf
37 kTpmCommandRwMask = 0x80,
38 kTpmCommandSizeMask = 0x3f,
43 .disable_return_by_hardware =
false,
44 .disable_address_prefix_check =
false,
45 .disable_locality_check =
false};
47 static volatile bool header_interrupt_received =
false;
49 static void en_plic_irqs(dif_rv_plic_t *plic) {
60 for (uint32_t i = 0; i <
ARRAYSIZE(kIrqs); ++i) {
70 irq_global_ctrl(
true);
71 irq_external_ctrl(
true);
74 static void en_spi_device_irqs(dif_spi_device_t *spi_device) {
75 const dif_spi_device_irq_t kIrqs[] = {kDifSpiDeviceIrqUploadCmdfifoNotEmpty,
76 kDifSpiDeviceIrqUploadPayloadNotEmpty,
77 kDifSpiDeviceIrqUploadPayloadOverflow,
78 kDifSpiDeviceIrqReadbufWatermark,
79 kDifSpiDeviceIrqReadbufFlip,
80 kDifSpiDeviceIrqTpmHeaderNotEmpty};
82 for (uint32_t i = 0; i <
ARRAYSIZE(kIrqs); ++i) {
83 CHECK_DIF_OK(dif_spi_device_irq_set_enabled(spi_device, kIrqs[i],
88 void ottf_external_isr(uint32_t *exc_info) {
89 plic_isr_ctx_t plic_ctx = {.rv_plic = &plic,
94 spi_device_isr_ctx_t spi_device_ctx = {
95 .spi_device = &spi_device.
dev,
96 .plic_spi_device_start_irq_id =
98 .expected_irq = kDifSpiDeviceIrqTpmHeaderNotEmpty,
99 .is_only_irq =
false};
102 dif_spi_device_irq_t spi_device_irq;
103 isr_testutils_spi_device_isr(plic_ctx, spi_device_ctx,
false, &peripheral,
106 switch (spi_device_irq) {
107 case kDifSpiDeviceIrqTpmHeaderNotEmpty:
108 header_interrupt_received =
true;
110 CHECK_DIF_OK(dif_spi_device_irq_set_enabled(
111 &spi_device.
dev, kDifSpiDeviceIrqTpmHeaderNotEmpty,
115 LOG_ERROR(
"Unexpected interrupt: %d", spi_device_irq);
122 header_interrupt_received =
false;
123 CHECK_DIF_OK(dif_spi_device_irq_acknowledge(
124 &spi_device->
dev, kDifSpiDeviceIrqTpmHeaderNotEmpty));
125 CHECK_DIF_OK(dif_spi_device_irq_set_enabled(
130 CHECK_DIF_OK(dif_pinmux_init(
136 CHECK_DIF_OK(dif_rv_plic_init(
151 .flags = kDifPinmuxPadAttrPullResistorEnable |
152 kDifPinmuxPadAttrPullResistorUp};
160 CHECK_STATUS_OK(spi_device_testutils_configure_pad_attrs(&pinmux));
167 en_spi_device_irqs(&spi_device.
dev);
172 for (uint32_t i = 0; i < kIterations; i++) {
176 ATOMIC_WAIT_FOR_INTERRUPT(header_interrupt_received);
180 uint8_t write_command = 0;
181 uint32_t write_addr = 0;
184 CHECK((write_command & kTpmCommandRwMask) == kTpmWriteCommand,
185 "Expected write command, received read");
188 uint32_t num_bytes = (write_command & kTpmCommandSizeMask) + 1;
189 LOG_INFO(
"Expecting %d bytes from tpm write", num_bytes);
191 uint8_t buf[64] = {0};
200 ack_spi_tpm_header_irq(&spi_device);
204 ATOMIC_WAIT_FOR_INTERRUPT(header_interrupt_received);
206 uint8_t read_command = 0;
207 uint32_t read_addr = 0;
212 ack_spi_tpm_header_irq(&spi_device);
215 read_command &= kTpmCommandMask;
216 LOG_INFO(
"Expected 0x%x, received 0x%x",
217 (kTpmReadCommand | (num_bytes - 1)), read_command);
218 CHECK((kTpmReadCommand | (num_bytes - 1)) == read_command,
219 "Expected read command, received write");
220 CHECK(write_addr == read_addr,
"Received address did not match");