Software APIs
sysrst_ctrl_inputs_test.c
1 // Copyright lowRISC contributors (OpenTitan project).
2 // Licensed under the Apache License, Version 2.0, see LICENSE for details.
3 // SPDX-License-Identifier: Apache-2.0
4 
9 #include "sw/device/lib/testing/sysrst_ctrl_testutils.h"
10 #include "sw/device/lib/testing/test_framework/check.h"
12 #include "sw/device/lib/testing/test_framework/ottf_utils.h"
13 
15 
16 /* We need control flow for the ujson messages exchanged
17  * with the host in OTTF_WAIT_FOR on real devices. */
18 OTTF_DEFINE_TEST_CONFIG(.enable_uart_flow_control = true);
19 
20 static dif_sysrst_ctrl_t sysrst_ctrl;
21 const uint32_t kNumPhases = 10;
22 
23 // On DV, we must use variables in flash but on a real device,
24 // we must use variables in RAM.
25 static const volatile uint8_t kTestPhaseDV = 0;
26 static const volatile uint8_t kTestExpectedDV = 0;
27 // In DV, the sequence can ensure that the pins are set even before the test
28 // runs. On a real device, this is not the case and if the initial value of
29 // kTestPhase is 0, the very first OTTF_WAIT_FOR could succeed before the host
30 // can set the pins. To avoid this, and only on real devices, set the initial
31 // value to an invalid value so that we have to wait for the host.
32 static volatile uint8_t kTestPhaseReal = 0xff;
33 static volatile uint8_t kTestExpectedReal = 0;
34 
35 enum {
36  kOutputNumPads = 0x8,
37  kOutputNumMioPads = 0x6,
38 };
39 
40 static const dif_pinmux_index_t kPeripheralInputs[] = {
47 };
48 
49 static const dif_pinmux_index_t kInputPadsDV[] = {
53 };
54 
55 // We need different pins on the hyperdebug boards since certain
56 // pins are not routed to the hyperdebug.
57 static const dif_pinmux_index_t kInputPadsReal[] = {
61 };
62 
63 static const dif_sysrst_ctrl_pin_t kSysrstCtrlInputs[] = {
68 };
69 
70 static uint8_t read_input_pins(void) {
71  bool input_value;
72  uint8_t inputs = 0;
73  for (int i = 0; i < kOutputNumPads; ++i) {
74  CHECK_DIF_OK(dif_sysrst_ctrl_input_pin_read(
75  &sysrst_ctrl, kSysrstCtrlInputs[i], &input_value));
76  inputs |= input_value << i;
77  }
78  return inputs;
79 }
80 
81 bool test_main(void) {
82  CHECK_DIF_OK(dif_sysrst_ctrl_init(
84  &sysrst_ctrl));
85 
86  dif_pinmux_t pinmux;
87  CHECK_DIF_OK(dif_pinmux_init(
89 
90  /* On real devices, we also need to configure the DIO pins */
91  if (kDeviceType != kDeviceSimDV) {
92  sysrst_ctrl_testutils_setup_dio(&pinmux);
93  // Release pins so the host can control them.
94  sysrst_ctrl_testutils_release_dio(&sysrst_ctrl, true, true);
95  // Disable the EC reset pulse so that it does not interfere with the test.
96  sysrst_ctrl_testutils_set_ec_rst_pulse_width(&sysrst_ctrl, 0);
97  }
98  const dif_pinmux_index_t *kInputPads =
99  kDeviceType == kDeviceSimDV ? kInputPadsDV : kInputPadsReal;
100  for (int i = 0; i < kOutputNumMioPads; ++i) {
101  CHECK_DIF_OK(
102  dif_pinmux_input_select(&pinmux, kPeripheralInputs[i], kInputPads[i]));
103  }
104 
105  const uint32_t kTestPhaseTimeoutUsec =
106  kDeviceType == kDeviceSimDV ? 10 : 1000000;
107  // See explanation at the top of this file.
108  const volatile uint8_t *kTestPhase =
109  kDeviceType == kDeviceSimDV ? &kTestPhaseDV : &kTestPhaseReal;
110  const volatile uint8_t *kTestExpected =
111  kDeviceType == kDeviceSimDV ? &kTestExpectedDV : &kTestExpectedReal;
112 
113  for (int i = 0; i < kNumPhases; ++i) {
114  OTTF_WAIT_FOR(i == *kTestPhase, kTestPhaseTimeoutUsec);
115  uint8_t input_pins = read_input_pins();
116  LOG_INFO("Expect pins: %x, got: %x", *kTestExpected, input_pins);
117  CHECK(*kTestExpected == input_pins);
118  // Test status set to InTest then Wfi for testbench synchronization,
119  // an actual WFI instruction is not issued.
120  test_status_set(kTestStatusInTest);
121  test_status_set(kTestStatusInWfi);
122  }
123 
124  test_status_set(kTestStatusInTest);
125  return true;
126 }