path: root/pc-bios/optionrom
diff options
authorPaolo Bonzini <pbonzini@redhat.com>2016-08-05 10:51:37 +0200
committerPaolo Bonzini <pbonzini@redhat.com>2016-08-09 22:57:36 +0200
commit7f2569246c81d5f88e74c142b8fbdc0ee601bffe (patch)
tree6f76bd0576c31d849f31cb960de0e0c7af7a5573 /pc-bios/optionrom
parent2bb15bddf2607110820d5ce5aa43baac27292fb3 (diff)
linuxboot_dma: avoid guest ABI breakage on gcc vs. clang compilation
Recent GCC compiles linuxboot_dma.c to 921 bytes, while CentOS 6 needs 1029 and clang needs 1527. Because the size of the ROM, rounded to the next 512 bytes, must match, this causes the API to break between a <1K ROM and one that is bigger. We want to make the ROM 1.5 KB in size, but it's better to make clang produce leaner ROMs, because currently it is worryingly close to the limit. To fix this prevent clang's happy inlining (which -Os cannot prevent). This only requires adding a noinline attribute. Second, the patch makes sure that the ROM has enough padding to prevent ABI breakage on different compilers. The size is now hardcoded in the file that is passed to signrom.py, as was the case before commit 6f71b77 ("scripts/signrom.py: Allow option ROM checksum script to write the size header.", 2016-05-23); signrom.py however will still pad the input to the requested size. This ensures that the padding goes beyond the next multiple of 512 if necessary, and also avoids the need for -fno-toplevel-reorder which clang doesn't support. signrom.py can then error out if the requested size is too small for the actual size of the compiled ROM. Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
Diffstat (limited to 'pc-bios/optionrom')
1 files changed, 6 insertions, 2 deletions
diff --git a/pc-bios/optionrom/linuxboot_dma.c b/pc-bios/optionrom/linuxboot_dma.c
index 8509b287ba..7549797732 100644
--- a/pc-bios/optionrom/linuxboot_dma.c
+++ b/pc-bios/optionrom/linuxboot_dma.c
@@ -25,7 +25,7 @@ asm(
".global _start\n"
" .short 0xaa55\n"
-" .byte 0\n" /* size in 512 units, filled in by signrom.py */
+" .byte 3\n" /* desired size in 512 units; signrom.py adds padding */
" .byte 0xcb\n" /* far return without prefix */
" .org 0x18\n"
" .short 0\n"
@@ -157,7 +157,11 @@ static inline uint32_t be32_to_cpu(uint32_t x)
return bswap32(x);
-static void bios_cfg_read_entry(void *buf, uint16_t entry, uint32_t len)
+/* clang is happy to inline this function, and bloats the
+ * ROM.
+ */
+static __attribute__((__noinline__))
+void bios_cfg_read_entry(void *buf, uint16_t entry, uint32_t len)
FWCfgDmaAccess access;
uint32_t control = (entry << 16) | BIOS_CFG_DMA_CTL_SELECT