1 /* SPDX-License-Identifier: GPL-2.0-only */
3 /* Inspired by OvmfPkg/QemuFlashFvbServicesRuntimeDxe/QemuFlash.c from edk2 */
6 #include <boot_device.h>
7 #include <console/console.h>
8 #include <commonlib/helpers.h>
9 #include <commonlib/region.h>
12 #define WRITE_BYTE_CMD 0x10
13 #define BLOCK_ERASE_CMD 0x20
14 #define CLEAR_STATUS_CMD 0x50
15 #define READ_STATUS_CMD 0x70
16 #define BLOCK_ERASE_CONFIRM_CMD 0xD0
17 #define READ_ARRAY_CMD 0xFF
19 #define CLEARED_ARRAY_STATUS 0x00
21 #define QEMU_FLASH_BLOCK_SIZE 0x1000
24 #include <southbridge/intel/common/pmutil.h>
27 * ELOG and VBOOT options are automatically enabled when building with
28 * CHROMEOS=y. While the former allows for logging PCH state (not that there is
29 * much to log on QEMU), the latter currently forces 16 MiB ROM size, which in
30 * turn doesn't allow mounting as pflash in QEMU. Using pflash is required to
31 * have writable flash, which means that the following function will not be
32 * able to write to the flash based log until ROM size and layout is changed in
33 * Flashmap used when building for vboot.
35 void pch_log_state(void) {}
38 static ssize_t
qemu_writeat(const struct region_device
*rd
, const void *b
,
39 size_t offset
, size_t size
)
41 const struct mem_region_device
*mdev
;
46 mdev
= container_of(rd
, __typeof__(*mdev
), rdev
);
47 ptr
= &mdev
->base
[offset
];
49 for (i
= 0; i
< size
; i
++) {
50 write8(ptr
, WRITE_BYTE_CMD
);
55 /* Restore flash to read mode. */
57 write8(ptr
- 1, READ_ARRAY_CMD
);
63 static ssize_t
qemu_eraseat(const struct region_device
*rd
, size_t offset
,
66 const struct mem_region_device
*mdev
;
70 mdev
= container_of(rd
, __typeof__(*mdev
), rdev
);
71 ptr
= &mdev
->base
[offset
];
73 if (!IS_ALIGNED(offset
, QEMU_FLASH_BLOCK_SIZE
)) {
74 printk(BIOS_ERR
, "%s: erased offset isn't multiple of block size\n",
79 if (!IS_ALIGNED(size
, QEMU_FLASH_BLOCK_SIZE
)) {
80 printk(BIOS_ERR
, "%s: erased size isn't multiple of block size\n",
85 for (i
= 0; i
< size
; i
+= QEMU_FLASH_BLOCK_SIZE
) {
86 write8(ptr
, BLOCK_ERASE_CMD
);
87 write8(ptr
, BLOCK_ERASE_CONFIRM_CMD
);
88 ptr
+= QEMU_FLASH_BLOCK_SIZE
;
91 /* Restore flash to read mode. */
93 write8(ptr
- QEMU_FLASH_BLOCK_SIZE
, READ_ARRAY_CMD
);
99 static struct region_device_ops flash_ops
;
100 static const struct mem_region_device boot_dev
=
101 MEM_REGION_DEV_INIT(0x100000000ULL
- CONFIG_ROM_SIZE
, CONFIG_ROM_SIZE
, &flash_ops
);
104 * Depending on how firmware image was passed to QEMU, it may behave as:
106 * - ROM - memory mapped reads, writes are ignored (FW image mounted with
108 * - RAM - memory mapped reads and writes (FW image mounted with e.g.
110 * - flash - memory mapped reads, write and erase possible through commands.
111 * Contrary to physical flash devices erase is not required before writing,
112 * but it also doesn't hurt. Flash may be split into read-only and read-write
113 * parts, like OVMF_CODE.fd and OVMF_VARS.fd. Maximal combined size of system
114 * firmware is hardcoded (QEMU < 5.0.0) or set by default to 8 MiB. On QEMU
115 * version 5.0.0 or newer, it is configurable with `max-fw-size` machine
116 * configuration option, up to 16 MiB to not overlap with IOAPIC memory range
117 * (FW image(s) mounted with '-drive if=pflash').
119 * This function detects which of the above applies and fills region_device_ops
122 void boot_device_init(void)
125 char original
, readback
;
126 static bool initialized
= false;
132 * mmap, munmap and readat are always identical to mem_rdev_rw_ops, other
133 * functions may vary.
135 flash_ops
= mem_rdev_rw_ops
;
138 * Find first byte different than any of the commands, simplified.
140 * Detection code few lines below writes commands and tries to read back
141 * the response. To make that code simpler, make sure that original byte
142 * is different than any of the commands or expected responses. It is
143 * expected that such byte will always be found - it is virtually
144 * impossible to write valid x86 code with just bytes ending with 0, and
145 * there are also ASCII characters in metadata (CBFS, FMAP) that has bytes
146 * matching those assumptions.
148 ptr
= (volatile char *)boot_dev
.base
;
149 original
= read8(ptr
);
150 while (original
== (char)0xFF || (original
& 0x0F) == 0)
151 original
= read8(++ptr
);
154 * Detect what type of flash we're dealing with. This also clears any stale
155 * status bits, so the next read of status register should return known
156 * value (if pflash is used).
158 write8(ptr
, CLEAR_STATUS_CMD
);
159 readback
= read8(ptr
);
160 if (readback
== CLEAR_STATUS_CMD
) {
161 printk(BIOS_DEBUG
, "QEMU flash behaves as RAM\n");
162 /* Restore original content. */
163 write8(ptr
, original
);
165 /* Either ROM or QEMU flash implementation. */
166 write8(ptr
, READ_STATUS_CMD
);
167 readback
= read8(ptr
);
168 if (readback
== original
) {
169 printk(BIOS_DEBUG
, "QEMU flash behaves as ROM\n");
170 /* ROM means no writing nor erasing. */
171 flash_ops
.writeat
= NULL
;
172 flash_ops
.eraseat
= NULL
;
173 } else if (readback
== CLEARED_ARRAY_STATUS
) {
174 /* Try writing original value to test whether flash is writable. */
175 write8(ptr
, WRITE_BYTE_CMD
);
176 write8(ptr
, original
);
177 write8(ptr
, READ_STATUS_CMD
);
178 readback
= read8(ptr
);
179 if (readback
& 0x10 /* programming error */) {
181 "QEMU flash behaves as write-protected flash\n");
182 flash_ops
.writeat
= NULL
;
183 flash_ops
.eraseat
= NULL
;
185 printk(BIOS_DEBUG
, "QEMU flash behaves as writable flash\n");
186 flash_ops
.writeat
= qemu_writeat
;
187 flash_ops
.eraseat
= qemu_eraseat
;
189 /* Restore flash to read mode. */
190 write8(ptr
, READ_ARRAY_CMD
);
192 printk(BIOS_ERR
, "Unexpected QEMU flash behavior, assuming ROM\n");
194 * This shouldn't happen and first byte of flash may already be
195 * corrupted by testing, but don't take any further risk.
197 flash_ops
.writeat
= NULL
;
198 flash_ops
.eraseat
= NULL
;
205 /* boot_device_ro() is defined in arch/x86/mmap_boot.c */
206 const struct region_device
*boot_device_rw(void)
208 return &boot_dev
.rdev
;