amd_spi100: Implement memory-mapped reads

Query the RomRange2 register for the memory range (usually top below 4G)
and try to map that. Reads outside this range will still be served via
the command engine.

Change-Id: I21aa67d550ccda0f55a9cf3ff14545a881624d11
Signed-off-by: Nico Huber <nico.h@gmx.de>
Reviewed-on: https://review.coreboot.org/c/flashrom-stable/+/72583
Reviewed-by: Arthur Heymans <arthur@aheymans.xyz>
Tested-by: build bot (Jenkins) <no-reply@coreboot.org>
diff --git a/amd_spi100.c b/amd_spi100.c
index 39b293f..d0d2f28 100644
--- a/amd_spi100.c
+++ b/amd_spi100.c
@@ -25,6 +25,9 @@
 
 struct spi100 {
 	uint8_t *spibar;
+	uint8_t *memory;
+	size_t mapped_len;
+
 	unsigned int altspeed;
 };
 
@@ -123,6 +126,27 @@
 	return 0;
 }
 
+static int spi100_read(struct flashctx *const flash, uint8_t *buf, unsigned int start, unsigned int len)
+{
+	const struct spi100 *const spi100 = flash->mst->spi.data;
+
+	/* Use SPI100 engine for data outside the memory-mapped range */
+	const chipoff_t from_top = flashrom_flash_getsize(flash) - start;
+	if (from_top > spi100->mapped_len) {
+		const chipsize_t unmapped_len = MIN(len, from_top - spi100->mapped_len);
+		const int ret = default_spi_read(flash, buf, start, unmapped_len);
+		if (ret)
+			return ret;
+		start += unmapped_len;
+		buf += unmapped_len;
+		len -= unmapped_len;
+	}
+
+	mmio_readn_aligned(spi100->memory + start, buf, len, 8);
+
+	return 0;
+}
+
 static int spi100_shutdown(void *data)
 {
 	struct spi100 *const spi100 = data;
@@ -139,7 +163,7 @@
 	.max_data_write	= SPI100_FIFO_SIZE - 4,
 	.command	= spi100_send_command,
 	.multicommand	= default_spi_send_multicommand,
-	.read		= default_spi_read,
+	.read		= spi100_read,
 	.write_256	= default_spi_write_256,
 	.probe_opcode	= default_spi_probe_opcode,
 	.shutdown	= spi100_shutdown,
@@ -215,7 +239,7 @@
 	}
 }
 
-int amd_spi100_probe(void *const spibar)
+int amd_spi100_probe(void *const spibar, void *const memory_mapping, const size_t mapped_len)
 {
 	struct spi100 *const spi100 = malloc(sizeof(*spi100));
 	if (!spi100) {
@@ -223,6 +247,8 @@
 		return ERROR_FATAL;
 	}
 	spi100->spibar = spibar;
+	spi100->memory = memory_mapping;
+	spi100->mapped_len = mapped_len;
 
 	spi100_print(spi100);