Software APIs
entropy_src_testutils.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#include "sw/device/lib/testing/entropy_src_testutils.h"
5
6#include "sw/device/lib/base/crc32.h"
9#include "sw/device/lib/testing/test_framework/check.h"
10
11#include "hw/top/entropy_src_regs.h" // Generated.
12
13#define MODULE_ID MAKE_MODULE_ID('e', 'n', 's')
14
15status_t entropy_src_testutils_fw_override_enable(
16 dif_entropy_src_t *entropy_src, uint8_t buffer_threshold,
17 bool route_to_firmware, bool bypass_conditioner) {
18 const dif_entropy_src_fw_override_config_t fw_override_config = {
19 .entropy_insert_enable = true,
20 .buffer_threshold = buffer_threshold,
21 };
22 TRY(dif_entropy_src_fw_override_configure(entropy_src, fw_override_config,
24
25 const dif_entropy_src_config_t config = {
26 .fips_enable = true,
27 .fips_flag = true,
28 .rng_fips = true,
29 .route_to_firmware = route_to_firmware,
30 .bypass_conditioner = bypass_conditioner,
31 .single_bit_mode = kDifEntropySrcSingleBitModeDisabled,
32 .health_test_threshold_scope = false,
33 .health_test_window_size = 0x0200,
34 .alert_threshold = 2,
35 };
36 TRY(dif_entropy_src_configure(entropy_src, config, kDifToggleEnabled));
37 return OK_STATUS();
38}
39
40status_t entropy_src_testutils_wait_for_state(
41 const dif_entropy_src_t *entropy_src, dif_entropy_src_main_fsm_t state) {
43
44 do {
45 TRY(dif_entropy_src_get_main_fsm_state(entropy_src, &cur_state));
46 } while (cur_state != state);
47 return OK_STATUS();
48}
49
50status_t entropy_src_testutils_drain_observe_fifo(
51 dif_entropy_src_t *entropy_src) {
52 // This value is arbitrary, it could be 1 but since there is some
53 // overhead in dif_entropy_src_observe_fifo_nonblocking_read, it's better
54 // to read several words every time to drain the FIFO quickly.
55 const size_t kDrainCount = 32;
56 size_t len;
57 // Read from the FIFO until we get a short read which means that the FIFO was
58 // emptied.
59 do {
60 len = kDrainCount;
61 TRY(dif_entropy_src_observe_fifo_nonblocking_read(entropy_src, NULL, &len));
62 } while (len == kDrainCount);
63
64 return OK_STATUS();
65}
66
67status_t entropy_src_testutils_disable_health_tests(
68 dif_entropy_src_t *entropy_src) {
69 static dif_entropy_src_test_t kHealthTest[] = {
76 for (size_t i = 0; i < ARRAYSIZE(kHealthTest); i++) {
77 TRY(dif_entropy_src_health_test_configure(
78 entropy_src,
79 (dif_entropy_src_health_test_config_t){.test_type = kHealthTest[i],
80 .high_threshold = 0xffff,
81 .low_threshold = 0}));
82 }
83
84 return OK_STATUS();
85}
86
87uint32_t entropy_src_config_crc32(dif_entropy_src_t *entropy_src) {
88 uint32_t ctx;
89 crc32_init(&ctx);
90
91 // Health test thresholds.
92 crc32_add32(&ctx,
93 mmio_region_read32(entropy_src->base_addr,
94 ENTROPY_SRC_REPCNT_THRESHOLD_REG_OFFSET));
95 crc32_add32(&ctx,
96 mmio_region_read32(entropy_src->base_addr,
97 ENTROPY_SRC_REPCNTS_THRESHOLD_REG_OFFSET));
98 crc32_add32(&ctx,
99 mmio_region_read32(entropy_src->base_addr,
100 ENTROPY_SRC_ADAPTP_HI_THRESHOLD_REG_OFFSET));
101 crc32_add32(&ctx,
102 mmio_region_read32(entropy_src->base_addr,
103 ENTROPY_SRC_ADAPTP_LO_THRESHOLD_REG_OFFSET));
104 crc32_add32(&ctx,
105 mmio_region_read32(entropy_src->base_addr,
106 ENTROPY_SRC_ADAPTPS_THRESHOLD_REG_OFFSET));
107 crc32_add32(&ctx,
108 mmio_region_read32(entropy_src->base_addr,
109 ENTROPY_SRC_BUCKET_THRESHOLD_REG_OFFSET));
110 crc32_add32(&ctx,
111 mmio_region_read32(entropy_src->base_addr,
112 ENTROPY_SRC_MARKOV_HI_THRESHOLD_REG_OFFSET));
113 crc32_add32(&ctx,
114 mmio_region_read32(entropy_src->base_addr,
115 ENTROPY_SRC_MARKOV_LO_THRESHOLD_REG_OFFSET));
116 crc32_add32(&ctx,
117 mmio_region_read32(entropy_src->base_addr,
118 ENTROPY_SRC_EXTHT_HI_THRESHOLD_REG_OFFSET));
119 crc32_add32(&ctx,
120 mmio_region_read32(entropy_src->base_addr,
121 ENTROPY_SRC_EXTHT_LO_THRESHOLD_REG_OFFSET));
122
123 // Alert threshold.
124 crc32_add32(&ctx, mmio_region_read32(entropy_src->base_addr,
125 ENTROPY_SRC_ALERT_THRESHOLD_REG_OFFSET));
126
127 return crc32_finish(&ctx);
128}