5 #include "sw/device/lib/testing/spi_flash_testutils.h"
10 #include "sw/device/lib/testing/spi_device_testutils.h"
11 #include "sw/device/lib/testing/test_framework/check.h"
13 #define MODULE_ID MAKE_MODULE_ID('s', 'f', 't')
15 status_t spi_flash_testutils_read_id(dif_spi_host_t *spih,
17 TRY_CHECK(spih != NULL);
18 TRY_CHECK(
id != NULL);
23 .opcode = {.opcode = kSpiDeviceFlashOpReadJedec,
31 .length =
sizeof(buffer),
39 while ((page <
sizeof(buffer)) && (buffer[page] == 0x7fu)) {
42 TRY_CHECK(page + 3 <=
sizeof(buffer));
43 TRY_CHECK(page <= UINT8_MAX);
44 id->continuation_len = (uint8_t)page;
45 id->manufacturer_id = buffer[page];
46 id->device_id = buffer[page + 1];
47 id->device_id |= (uint16_t)buffer[page + 2] << 8;
51 status_t spi_flash_testutils_read_sfdp(dif_spi_host_t *spih, uint32_t address,
52 void *buffer,
size_t length) {
53 TRY_CHECK(spih != NULL);
54 TRY_CHECK(buffer != NULL);
58 .opcode = {.opcode = kSpiDeviceFlashOpReadSfdp,
92 status_t spi_flash_testutils_read_status(dif_spi_host_t *spih, uint8_t opcode,
94 TRY_CHECK(spih != NULL);
95 TRY_CHECK(length <= 3);
112 return OK_STATUS((int32_t)
status);
115 status_t spi_flash_testutils_write_status(dif_spi_host_t *spih, uint8_t opcode,
116 uint32_t
status,
size_t length) {
117 TRY_CHECK(spih != NULL);
118 TRY_CHECK(length <= 3);
119 TRY(spi_flash_testutils_issue_write_enable(spih));
138 status_t spi_flash_testutils_wait_until_not_busy(dif_spi_host_t *spih) {
139 TRY_CHECK(spih != NULL);
144 spi_flash_testutils_read_status(spih, kSpiDeviceFlashOpReadStatus1, 1));
145 }
while (
status & kSpiFlashStatusBitWip);
149 status_t spi_flash_testutils_issue_write_enable(dif_spi_host_t *spih) {
150 TRY_CHECK(spih != NULL);
153 .opcode = {.opcode = kSpiDeviceFlashOpWriteEnable,
161 status_t spi_flash_testutils_erase_chip(dif_spi_host_t *spih) {
162 TRY_CHECK(spih != NULL);
163 TRY(spi_flash_testutils_issue_write_enable(spih));
167 .opcode = {.opcode = kSpiDeviceFlashOpChipErase,
172 return spi_flash_testutils_wait_until_not_busy(spih);
175 status_t spi_flash_testutils_erase_op(dif_spi_host_t *spih, uint8_t opcode,
176 uint32_t address,
bool addr_is_4b) {
177 TRY_CHECK(spih != NULL);
178 TRY(spi_flash_testutils_issue_write_enable(spih));
198 return spi_flash_testutils_wait_until_not_busy(spih);
201 status_t spi_flash_testutils_erase_sector(dif_spi_host_t *spih,
202 uint32_t address,
bool addr_is_4b) {
203 return spi_flash_testutils_erase_op(spih, kSpiDeviceFlashOpSectorErase,
204 address, addr_is_4b);
207 status_t spi_flash_testutils_erase_block32k(dif_spi_host_t *spih,
208 uint32_t address,
bool addr_is_4b) {
209 return spi_flash_testutils_erase_op(spih, kSpiDeviceFlashOpBlockErase32k,
210 address, addr_is_4b);
213 status_t spi_flash_testutils_erase_block64k(dif_spi_host_t *spih,
214 uint32_t address,
bool addr_is_4b) {
215 return spi_flash_testutils_erase_op(spih, kSpiDeviceFlashOpBlockErase64k,
216 address, addr_is_4b);
219 status_t spi_flash_testutils_program_op(
220 dif_spi_host_t *spih, uint8_t opcode,
const void *payload,
size_t length,
221 uint32_t address,
bool addr_is_4b,
222 spi_flash_testutils_transaction_width_mode_t page_program_mode) {
223 TRY_CHECK(spih != NULL);
224 TRY_CHECK(payload != NULL);
225 TRY_CHECK(length <= 256);
227 TRY(spi_flash_testutils_issue_write_enable(spih));
233 .opcode = {.opcode = opcode,
235 spi_flash_testutils_get_opcode_width(page_program_mode)}},
241 spi_flash_testutils_get_address_width(page_program_mode),
251 spi_flash_testutils_get_data_width(page_program_mode),
260 return spi_flash_testutils_wait_until_not_busy(spih);
263 status_t spi_flash_testutils_program_page(dif_spi_host_t *spih,
264 const void *payload,
size_t length,
265 uint32_t address,
bool addr_is_4b) {
266 return spi_flash_testutils_program_op(spih, kSpiDeviceFlashOpPageProgram,
267 payload, length, address, addr_is_4b,
268 kTransactionWidthMode111);
271 status_t spi_flash_testutils_read_op(dif_spi_host_t *spih, uint8_t opcode,
272 void *payload,
size_t length,
273 uint32_t address,
bool addr_is_4b,
274 uint8_t width, uint8_t dummy) {
275 TRY_CHECK(spih != NULL);
276 TRY_CHECK(payload != NULL);
277 TRY_CHECK(length <= 256);
278 TRY_CHECK(width == 1 || width == 2 || width == 4);
321 status_t spi_flash_testutils_quad_enable(dif_spi_host_t *spih, uint8_t method,
332 status = (uint32_t)TRY(spi_flash_testutils_read_status(
333 spih, kSpiDeviceFlashOpReadStatus1, 2));
335 TRY(spi_flash_testutils_write_status(spih, kSpiDeviceFlashOpWriteStatus1,
336 status, enabled ? 2 : 1));
340 status = (uint32_t)TRY(spi_flash_testutils_read_status(
341 spih, kSpiDeviceFlashOpReadStatus1, 1));
343 TRY(spi_flash_testutils_write_status(spih, kSpiDeviceFlashOpWriteStatus1,
349 status = (uint32_t)TRY(spi_flash_testutils_read_status(
350 spih, kSpiDeviceFlashOpReadStatus2, 1));
352 TRY(spi_flash_testutils_write_status(spih, kSpiDeviceFlashOpWriteStatus2,
359 status = (uint32_t)TRY(spi_flash_testutils_read_status(
360 spih, kSpiDeviceFlashOpReadStatus1, 2));
362 TRY(spi_flash_testutils_write_status(spih, kSpiDeviceFlashOpWriteStatus1,
369 status = (uint32_t)TRY(spi_flash_testutils_read_status(
370 spih, kSpiDeviceFlashOpReadStatus1, 1));
371 status |= (uint32_t)(TRY(spi_flash_testutils_read_status(
372 spih, kSpiDeviceFlashOpReadStatus2, 1))
375 TRY(spi_flash_testutils_write_status(spih, kSpiDeviceFlashOpWriteStatus1,
382 status = (uint32_t)TRY(spi_flash_testutils_read_status(
383 spih, kSpiDeviceFlashOpReadStatus2, 1));
385 TRY(spi_flash_testutils_write_status(spih, kSpiDeviceFlashOpWriteStatus2,
390 return INVALID_ARGUMENT();
396 status_t spi_flash_testutils_enter_4byte_address_mode(dif_spi_host_t *spih) {
399 .opcode = {.opcode = kSpiDeviceFlashOpEnter4bAddr,
405 status_t spi_flash_testutils_exit_4byte_address_mode(dif_spi_host_t *spih) {
407 .opcode = {.opcode = kSpiDeviceFlashOpExit4bAddr,