Ashish Kumar Mishra has uploaded this change for review. ( https://review.coreboot.org/c/coreboot/+/82079?usp=email )
Change subject: block/fast_spi: Use read32p/write32p for spi rw ......................................................................
block/fast_spi: Use read32p/write32p for spi rw
The current fast_spi impl. uses memcpy for rw. The memcpy impl. for x86_64 changed to 8 byte copy and due to 4 byte limit, spi rw fails. MRC cache rw regression observed in existing X86_64 platforms. Hence update rw ops to use read32p/write32p isntead of updating the memcpy.
BUG=b:242829490 TEST=Build and boot mtl 64-bit and verified MRC cache working.
Change-Id: I317c7160bf192dd2aeacebf6029a809bc97f3420 Signed-off-by: Ashish Kumar Mishra ashish.k.mishra@intel.com --- M src/soc/intel/common/block/fast_spi/fast_spi_flash.c 1 file changed, 30 insertions(+), 4 deletions(-)
git pull ssh://review.coreboot.org:29418/coreboot refs/changes/79/82079/1
diff --git a/src/soc/intel/common/block/fast_spi/fast_spi_flash.c b/src/soc/intel/common/block/fast_spi/fast_spi_flash.c index e9cfc23..45a9285 100644 --- a/src/soc/intel/common/block/fast_spi/fast_spi_flash.c +++ b/src/soc/intel/common/block/fast_spi/fast_spi_flash.c @@ -77,16 +77,42 @@ static void fill_xfer_fifo(struct fast_spi_flash_ctx *ctx, const void *data, size_t len) { - /* YES! memcpy() works. FDATAn does not require 32-bit accesses. */ - memcpy((void *)(ctx->mmio_base + SPIBAR_FDATA(0)), data, len); + const uint8_t *byte_ptr = (const uint8_t *)data; + size_t bytes_to_copy; + union { + uint32_t full; + uint8_t bytes[4]; + } dword; + + for (size_t i = 0; i < len; i += 4) { + dword.full = 0; + + bytes_to_copy = (len - i < 4) ? len - i : 4; + for (size_t j = 0; j < bytes_to_copy; j++) + dword.bytes[j] = byte_ptr[i + j]; + + write32p(ctx->mmio_base + SPIBAR_FDATA(i >> 2), dword.full); + } }
/* Drain FDATAn FIFO after a read transaction populates data. */ static void drain_xfer_fifo(struct fast_spi_flash_ctx *ctx, void *dest, size_t len) { - /* YES! memcpy() works. FDATAn does not require 32-bit accesses. */ - memcpy(dest, (void *)(ctx->mmio_base + SPIBAR_FDATA(0)), len); + uint8_t *byte_ptr = (uint8_t *)dest; + size_t bytes_to_copy; + union { + uint32_t full; + uint8_t bytes[4]; + } dword; + + for (size_t i = 0; i < len; i += 4) { + dword.full = read32p(ctx->mmio_base + SPIBAR_FDATA(i >> 2)); + + bytes_to_copy = (len - i < 4) ? len - i : 4; + for (size_t j = 0; j < bytes_to_copy; j++) + byte_ptr[i + j] = dword.bytes[j]; + } }
/* Fire up a transfer using the hardware sequencer. */