summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorMichael Brown2014-08-21 17:34:26 +0200
committerMichael Brown2014-08-22 18:34:07 +0200
commit705907f9a9f4ba4f8f3bcb806ee18cd457d1dffb (patch)
tree7b3862b12e923fb1e7451aa278145d6f5a28e6c7
parent[build] Remove obsolete references to .zrom build targets (diff)
downloadipxe-705907f9a9f4ba4f8f3bcb806ee18cd457d1dffb.tar.gz
ipxe-705907f9a9f4ba4f8f3bcb806ee18cd457d1dffb.tar.xz
ipxe-705907f9a9f4ba4f8f3bcb806ee18cd457d1dffb.zip
[build] Allow ISA ROMs to be built
The build process has for a long time assumed that every ROM is a PCI ROM, and will always include the PCI header and PCI-related functionality (such as checking the PCI BIOS version, including the PCI bus:dev.fn address within the ROM product name string, etc.). While real ISA cards are no longer in use, some virtualisation environments (notably VirtualBox) have support only for ISA ROMs. This can cause problems: in particular, VirtualBox will call our initialisation entry point with random garbage in %ax, which we then treat as the PCI bus:dev.fn address of the autoboot device: this generally prevents the default boot sequence from using any network devices. Create .isarom and .pcirom prefixes which can be used to explicitly specify the type of ROM to be created. (Note that the .mrom prefix always implies a PCI ROM, since the .mrom mechanism relies on reconfiguring PCI BARs.) Make .rom a magic prefix which will automatically select the appropriate PCI or ISA ROM prefix for ROMs defined via a PCI_ROM() or ISA_ROM() macro. To maintain backwards compatibility, we default to building a PCI ROM for anything which is not directly derived from a PCI_ROM() or ISA_ROM() macro (e.g. bin/intel.rom). Add a selection of targets to "make everything" to ensure that the (relatively obscure) ISA ROM build process is included within the per-commit QA checks. Signed-off-by: Michael Brown <mcb30@ipxe.org>
-rw-r--r--src/Makefile1
-rw-r--r--src/Makefile.housekeeping7
-rw-r--r--src/arch/i386/Makefile.pcbios10
-rw-r--r--src/arch/i386/prefix/isaromprefix.S25
-rw-r--r--src/arch/i386/prefix/libprefix.S27
-rw-r--r--src/arch/i386/prefix/mromprefix.S4
-rw-r--r--src/arch/i386/prefix/pciromprefix.S25
-rw-r--r--src/arch/i386/prefix/romprefix.S77
8 files changed, 146 insertions, 30 deletions
diff --git a/src/Makefile b/src/Makefile
index aeeabcda..c6f4d590 100644
--- a/src/Makefile
+++ b/src/Makefile
@@ -147,6 +147,7 @@ all : $(ALL)
#
everything :
$(Q)$(MAKE) --no-print-directory $(ALL) \
+ bin/3c509.rom bin/intel.rom bin/intel.mrom \
bin-i386-efi/ipxe.efi bin-i386-efi/ipxe.efidrv \
bin-i386-efi/ipxe.efirom \
bin-x86_64-efi/ipxe.efi bin-x86_64-efi/ipxe.efidrv \
diff --git a/src/Makefile.housekeeping b/src/Makefile.housekeeping
index 5af4958d..0e490f61 100644
--- a/src/Makefile.housekeeping
+++ b/src/Makefile.housekeeping
@@ -902,19 +902,22 @@ CLEANUP += $(BIN)/NIC # Doesn't match the $(BIN)/*.* pattern
# derive the variables:
#
# TGT_ELEMENTS : the elements of the target (e.g. "dfe538 prism2_pci")
-# TGT_PREFIX : the prefix type (e.g. "rom")
+# TGT_PREFIX : the prefix type (e.g. "pcirom")
# TGT_DRIVERS : the driver for each element (e.g. "rtl8139 prism2_pci")
# TGT_ROM_NAME : the ROM name (e.g. "dfe538")
#
DRIVERS_ipxe = $(DRIVERS)
CARD_DRIVER = $(firstword $(DRIVER_$(1)) $(1))
TGT_ELEMENTS = $(subst --, ,$(firstword $(subst ., ,$(notdir $@))))
-TGT_PREFIX = $(word 2,$(subst ., ,$(notdir $@)))
TGT_ROM_NAME = $(firstword $(TGT_ELEMENTS))
TGT_DRIVERS = $(strip $(if $(DRIVERS_$(TGT_ROM_NAME)), \
$(DRIVERS_$(TGT_ROM_NAME)), \
$(foreach TGT_ELEMENT,$(TGT_ELEMENTS), \
$(call CARD_DRIVER,$(TGT_ELEMENT))) ))
+TGT_PREFIX_NAME = $(word 2,$(subst ., ,$(notdir $@)))
+TGT_PREFIX = $(strip $(if $(filter rom,$(TGT_PREFIX_NAME)), \
+ $(ROM_TYPE_$(TGT_ROM_NAME))rom, \
+ $(TGT_PREFIX_NAME)))
# Look up ROM IDs for the current target
# (e.g. "bin/dfe538--prism2_pci.rom.tmp") and derive the variables:
diff --git a/src/arch/i386/Makefile.pcbios b/src/arch/i386/Makefile.pcbios
index 50e93144..ff823737 100644
--- a/src/arch/i386/Makefile.pcbios
+++ b/src/arch/i386/Makefile.pcbios
@@ -16,6 +16,8 @@ SRCDIRS += arch/i386/drivers/net
#
MEDIA += rom
MEDIA += mrom
+MEDIA += pcirom
+MEDIA += isarom
MEDIA += pxe
MEDIA += kpxe
MEDIA += kkpxe
@@ -31,6 +33,8 @@ MEDIA += exe
#
PAD_rom = $(PERL) $(PADIMG) --blksize=512 --byte=0xff
PAD_mrom = $(PAD_rom)
+PAD_pcirom = $(PAD_rom)
+PAD_isarom = $(PAD_rom)
PAD_dsk = $(PERL) $(PADIMG) --blksize=512
PAD_hd = $(PERL) $(PADIMG) --blksize=32768
PAD_exe = $(PERL) $(PADIMG) --blksize=512
@@ -39,11 +43,15 @@ PAD_exe = $(PERL) $(PADIMG) --blksize=512
#
FINALISE_rom = $(PERL) $(FIXROM)
FINALISE_mrom = $(FINALISE_rom)
+FINALISE_pcirom = $(FINALISE_rom)
+FINALISE_isarom = $(FINALISE_rom)
-# Use $(ROMS) rather than $(DRIVERS) for "allroms" and "allmroms"
+# Use $(ROMS) rather than $(DRIVERS) for "allroms", "allmroms", etc.
#
LIST_NAME_rom := ROMS
LIST_NAME_mrom := ROMS
+LIST_NAME_pcirom := ROMS
+LIST_NAME_isarom := ROMS
# rule to make a non-emulation ISO boot image
NON_AUTO_MEDIA += iso
diff --git a/src/arch/i386/prefix/isaromprefix.S b/src/arch/i386/prefix/isaromprefix.S
new file mode 100644
index 00000000..e2820808
--- /dev/null
+++ b/src/arch/i386/prefix/isaromprefix.S
@@ -0,0 +1,25 @@
+/*
+ * Copyright (C) 2014 Michael Brown <mbrown@fensystems.co.uk>.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License as
+ * published by the Free Software Foundation; either version 2 of the
+ * License, or any later version.
+ *
+ * This program is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+ * 02110-1301, USA.
+ *
+ */
+
+FILE_LICENCE ( GPL2_OR_LATER )
+
+#define BUSTYPE "ISAR"
+#define _rom_start _isarom_start
+#include "romprefix.S"
diff --git a/src/arch/i386/prefix/libprefix.S b/src/arch/i386/prefix/libprefix.S
index 3aee415f..13da652e 100644
--- a/src/arch/i386/prefix/libprefix.S
+++ b/src/arch/i386/prefix/libprefix.S
@@ -95,6 +95,29 @@ print_character:
.size print_character, . - print_character
/*****************************************************************************
+ * Utility function: print space
+ *
+ * Parameters:
+ * %ds:di : output buffer (or %di=0 to print to console)
+ * Returns:
+ * %ds:di : next character in output buffer (if applicable)
+ *****************************************************************************
+ */
+ .section ".prefix.lib", "awx", @progbits
+ .code16
+ .globl print_space
+print_space:
+ /* Preserve registers */
+ pushw %ax
+ /* Print space */
+ movb $( ' ' ), %al
+ call print_character
+ /* Restore registers and return */
+ popw %ax
+ ret
+ .size print_space, . - print_space
+
+/*****************************************************************************
* Utility function: print a NUL-terminated string
*
* Parameters:
@@ -231,12 +254,10 @@ print_kill_line:
movb $( '\r' ), %al
call print_character
/* Print 79 spaces */
- movb $( ' ' ), %al
movw $79, %cx
-1: call print_character
+1: call print_space
loop 1b
/* Print CR */
- movb $( '\r' ), %al
call print_character
/* Restore registers and return */
popw %cx
diff --git a/src/arch/i386/prefix/mromprefix.S b/src/arch/i386/prefix/mromprefix.S
index 0f0847e5..c4e4ca06 100644
--- a/src/arch/i386/prefix/mromprefix.S
+++ b/src/arch/i386/prefix/mromprefix.S
@@ -32,8 +32,8 @@ FILE_LICENCE ( GPL2_OR_LATER )
#define ROMPREFIX_EXCLUDE_PAYLOAD 1
#define ROMPREFIX_MORE_IMAGES 1
-#define _rom_start _mrom_start
-#include "romprefix.S"
+#define _pcirom_start _mrom_start
+#include "pciromprefix.S"
.text
.arch i386
diff --git a/src/arch/i386/prefix/pciromprefix.S b/src/arch/i386/prefix/pciromprefix.S
new file mode 100644
index 00000000..45ba31f5
--- /dev/null
+++ b/src/arch/i386/prefix/pciromprefix.S
@@ -0,0 +1,25 @@
+/*
+ * Copyright (C) 2014 Michael Brown <mbrown@fensystems.co.uk>.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License as
+ * published by the Free Software Foundation; either version 2 of the
+ * License, or any later version.
+ *
+ * This program is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+ * 02110-1301, USA.
+ *
+ */
+
+FILE_LICENCE ( GPL2_OR_LATER )
+
+#define BUSTYPE "PCIR"
+#define _rom_start _pcirom_start
+#include "romprefix.S"
diff --git a/src/arch/i386/prefix/romprefix.S b/src/arch/i386/prefix/romprefix.S
index 99994401..7bc4fe8c 100644
--- a/src/arch/i386/prefix/romprefix.S
+++ b/src/arch/i386/prefix/romprefix.S
@@ -46,6 +46,12 @@ FILE_LICENCE ( GPL2_OR_LATER )
#define INDICATOR 0x80
#endif
+/* Default to building a PCI ROM if no bus type is specified
+ */
+#ifndef BUSTYPE
+#define BUSTYPE "PCIR"
+#endif
+
.text
.code16
.arch i386
@@ -64,8 +70,10 @@ checksum:
.word ipxeheader
.org 0x16
.word undiheader
+.ifeqs BUSTYPE, "PCIR"
.org 0x18
.word pciheader
+.endif
.org 0x1a
.word pnpheader
.size romheader, . - romheader
@@ -77,6 +85,7 @@ checksum:
.long 0
.previous
+.ifeqs BUSTYPE, "PCIR"
pciheader:
.ascii "PCIR" /* Signature */
.word pci_vendor_id /* Vendor identification */
@@ -107,6 +116,7 @@ pciheader_runtime_length:
.long 512
.long 0
.previous
+.endif /* PCIR */
/* PnP doesn't require any particular alignment, but IBM
* BIOSes will scan on 16-byte boundaries rather than using
@@ -148,11 +158,14 @@ mfgstr:
*/
prodstr:
.ascii PRODUCT_SHORT_NAME
+.ifeqs BUSTYPE, "PCIR"
prodstr_separator:
.byte 0
.ascii "(PCI "
prodstr_pci_id:
- .asciz "xx:xx.x)" /* Filled in by init code */
+ .ascii "xx:xx.x)" /* Filled in by init code */
+.endif /* PCIR */
+ .byte 0
.size prodstr, . - prodstr
.globl undiheader
@@ -167,7 +180,7 @@ undiheader:
.word _data16_memsz /* Stack segment size */
.word _data16_memsz /* Data segment size */
.word _text16_memsz /* Code segment size */
- .ascii "PCIR" /* Bus type */
+ .ascii BUSTYPE /* Bus type */
.equ undiheader_len, . - undiheader
.size undiheader, . - undiheader
@@ -208,31 +221,39 @@ init:
pushw %cs
popw %ds
- /* Store PCI 3.0 runtime segment address for later use */
- movw %bx, %gs
-
- /* Store PCI bus:dev.fn address */
- movw %ax, init_pci_busdevfn
-
/* Print message as early as possible */
movw $init_message, %si
xorw %di, %di
call print_message
- call print_pci_busdevfn
- /* Fill in product name string, if possible */
+ /* Store PCI 3.0 runtime segment address for later use, if
+ * applicable.
+ */
+.ifeqs BUSTYPE, "PCIR"
+ movw %bx, %gs
+.endif
+
+ /* Store PCI bus:dev.fn address, print PCI bus:dev.fn, and add
+ * PCI bus:dev.fn to product name string, if applicable.
+ */
+.ifeqs BUSTYPE, "PCIR"
+ xorw %di, %di
+ call print_space
+ movw %ax, init_pci_busdevfn
+ call print_pci_busdevfn
movw $prodstr_pci_id, %di
call print_pci_busdevfn
movb $( ' ' ), prodstr_separator
+.endif
/* Print segment address */
- movb $( ' ' ), %al
xorw %di, %di
- call print_character
+ call print_space
movw %cs, %ax
call print_hex_word
- /* Check for PCI BIOS version */
+ /* Check for PCI BIOS version, if applicable */
+.ifeqs BUSTYPE, "PCIR"
pushl %ebx
pushl %edx
pushl %edi
@@ -283,6 +304,7 @@ no_pci3:
1: popl %edi
popl %edx
popl %ebx
+.endif /* PCIR */
/* Check for PnP BIOS. Although %es:di should point to the
* PnP BIOS signature on entry, some BIOSes fail to do this.
@@ -396,13 +418,13 @@ no_pmm:
loop 1b
subb %bl, checksum
- /* Copy self to option ROM space. Required for PCI3.0, which
- * loads us to a temporary location in low memory. Will be a
- * no-op for lower PCI versions.
+ /* Copy self to option ROM space, if applicable. Required for
+ * PCI3.0, which loads us to a temporary location in low
+ * memory. Will be a no-op for lower PCI versions.
*/
- movb $( ' ' ), %al
+.ifeqs BUSTYPE, "PCIR"
xorw %di, %di
- call print_character
+ call print_space
movw %gs, %ax
call print_hex_word
movzbw romheader_size, %cx
@@ -411,10 +433,13 @@ no_pmm:
xorw %si, %si
xorw %di, %di
cs rep movsb
+.endif
- /* Skip prompt if this is not the first PCI function */
+ /* Skip prompt if this is not the first PCI function, if applicable */
+.ifeqs BUSTYPE, "PCIR"
testb $PCI_FUNC_MASK, init_pci_busdevfn
jnz no_shell
+.endif
/* Prompt for POST-time shell */
movw $init_message_prompt, %si
xorw %di, %di
@@ -564,11 +589,13 @@ init_message:
.ascii "\n"
.ascii PRODUCT_NAME
.ascii "\n"
- .asciz "iPXE (http://ipxe.org) "
+ .asciz "iPXE (http://ipxe.org)"
.size init_message, . - init_message
+.ifeqs BUSTYPE, "PCIR"
init_message_pci:
.asciz " PCI"
.size init_message_pci, . - init_message_pci
+.endif /* PCIR */
init_message_pnp:
.asciz " PnP"
.size init_message_pnp, . - init_message_pnp
@@ -591,9 +618,11 @@ init_message_done:
/* PCI bus:dev.fn
*
*/
+.ifeqs BUSTYPE, "PCIR"
init_pci_busdevfn:
.word 0
.size init_pci_busdevfn, . - init_pci_busdevfn
+.endif /* PCIR */
/* Image source area
*
@@ -732,14 +761,18 @@ exec: /* Set %ds = %cs */
lret
.section ".text16", "awx", @progbits
1:
- /* Retrieve PCI bus:dev.fn */
+ /* Retrieve PCI bus:dev.fn, if applicable */
+.ifeqs BUSTYPE, "PCIR"
movw init_pci_busdevfn, %ax
+.endif
/* Set up %ds for access to .data16 */
movw %bx, %ds
- /* Store PCI bus:dev.fn */
+ /* Store PCI bus:dev.fn, if applicable */
+.ifeqs BUSTYPE, "PCIR"
movw %ax, autoboot_busdevfn
+.endif
/* Call main() */
pushl $main