nvmxip.c 4.1 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145
  1. // SPDX-License-Identifier: GPL-2.0+
  2. /*
  3. * Functional tests for UCLASS_FFA class
  4. *
  5. * Copyright 2023 Arm Limited and/or its affiliates <open-source-office@arm.com>
  6. *
  7. * Authors:
  8. * Abdellatif El Khlifi <abdellatif.elkhlifi@arm.com>
  9. */
  10. #include <common.h>
  11. #include <blk.h>
  12. #include <console.h>
  13. #include <dm.h>
  14. #include <mapmem.h>
  15. #include <dm/test.h>
  16. #include <linux/bitops.h>
  17. #include <test/test.h>
  18. #include <test/ut.h>
  19. #include <nvmxip.h>
  20. /* NVMXIP devices described in the device tree */
  21. #define SANDBOX_NVMXIP_DEVICES 2
  22. /* reference device tree data for the probed devices */
  23. static struct nvmxip_plat nvmqspi_refdata[SANDBOX_NVMXIP_DEVICES] = {
  24. {0x08000000, 9, 4096}, {0x08200000, 9, 2048}
  25. };
  26. #define NVMXIP_BLK_START_PATTERN 0x1122334455667788ULL
  27. #define NVMXIP_BLK_END_PATTERN 0xa1a2a3a4a5a6a7a8ULL
  28. /**
  29. * dm_nvmxip_flash_sanity() - check flash data
  30. * @uts: test state
  31. * @device_idx: the NVMXIP device index
  32. * @buffer: the user buffer where the blocks data is copied to
  33. *
  34. * Mode 1: When buffer is NULL, initialize the flash with pattern data at the start
  35. * and at the end of each block. This pattern data will be used to check data consistency
  36. * when verifying the data read.
  37. * Mode 2: When the user buffer is provided in the argument (not NULL), compare the data
  38. * of the start and the end of each block in the user buffer with the expected pattern data.
  39. * Return an error when the check fails.
  40. *
  41. * Return:
  42. *
  43. * 0 on success. Otherwise, failure
  44. */
  45. static int dm_nvmxip_flash_sanity(struct unit_test_state *uts, u8 device_idx, void *buffer)
  46. {
  47. int i;
  48. u64 *ptr;
  49. u8 *base;
  50. unsigned long blksz;
  51. blksz = BIT(nvmqspi_refdata[device_idx].lba_shift);
  52. if (!buffer) {
  53. /* Mode 1: point at the flash start address. Pattern data will be written */
  54. base = map_sysmem(nvmqspi_refdata[device_idx].phys_base, 0);
  55. } else {
  56. /* Mode 2: point at the user buffer containing the data read and to be verified */
  57. base = buffer;
  58. }
  59. for (i = 0; i < nvmqspi_refdata[device_idx].lba ; i++) {
  60. ptr = (u64 *)(base + i * blksz);
  61. /* write an 8 bytes pattern at the start of the current block */
  62. if (!buffer)
  63. *ptr = NVMXIP_BLK_START_PATTERN;
  64. else
  65. ut_asserteq_64(NVMXIP_BLK_START_PATTERN, *ptr);
  66. ptr = (u64 *)((u8 *)ptr + blksz - sizeof(u64));
  67. /* write an 8 bytes pattern at the end of the current block */
  68. if (!buffer)
  69. *ptr = NVMXIP_BLK_END_PATTERN;
  70. else
  71. ut_asserteq_64(NVMXIP_BLK_END_PATTERN, *ptr);
  72. }
  73. if (!buffer)
  74. unmap_sysmem(base);
  75. return 0;
  76. }
  77. /**
  78. * dm_test_nvmxip() - check flash data
  79. * @uts: test state
  80. * Return:
  81. *
  82. * CMD_RET_SUCCESS on success. Otherwise, failure
  83. */
  84. static int dm_test_nvmxip(struct unit_test_state *uts)
  85. {
  86. struct nvmxip_plat *plat_data = NULL;
  87. struct udevice *dev = NULL, *bdev = NULL;
  88. u8 device_idx;
  89. void *buffer = NULL;
  90. unsigned long flashsz;
  91. /* set the flash content first for both devices */
  92. dm_nvmxip_flash_sanity(uts, 0, NULL);
  93. dm_nvmxip_flash_sanity(uts, 1, NULL);
  94. /* probing all NVM XIP QSPI devices */
  95. for (device_idx = 0, uclass_first_device(UCLASS_NVMXIP, &dev);
  96. dev;
  97. uclass_next_device(&dev), device_idx++) {
  98. plat_data = dev_get_plat(dev);
  99. /* device tree entries checks */
  100. ut_assertok(nvmqspi_refdata[device_idx].phys_base != plat_data->phys_base);
  101. ut_assertok(nvmqspi_refdata[device_idx].lba_shift != plat_data->lba_shift);
  102. ut_assertok(nvmqspi_refdata[device_idx].lba != plat_data->lba);
  103. /* before reading all the flash blocks, let's calculate the flash size */
  104. flashsz = plat_data->lba << plat_data->lba_shift;
  105. /* allocate the user buffer where to copy the blocks data to */
  106. buffer = calloc(flashsz, 1);
  107. ut_assertok(!buffer);
  108. /* the block device is the child of the parent device probed with DT */
  109. ut_assertok(device_find_first_child(dev, &bdev));
  110. /* reading all the flash blocks */
  111. ut_asserteq(plat_data->lba, blk_read(bdev, 0, plat_data->lba, buffer));
  112. /* compare the data read from flash with the expected data */
  113. dm_nvmxip_flash_sanity(uts, device_idx, buffer);
  114. free(buffer);
  115. }
  116. ut_assertok(device_idx != SANDBOX_NVMXIP_DEVICES);
  117. return CMD_RET_SUCCESS;
  118. }
  119. DM_TEST(dm_test_nvmxip, UT_TESTF_SCAN_FDT | UT_TESTF_CONSOLE_REC);