An Option ROM is a piece of firmware that resides in BIOS or on an expansion card, which gets shadowed into memory and executed to initialise the device and register it with the BIOS. It is essentially a driver that interfaces between BIOS services and hardware.
BIOS Boot Specification
The BIOS Boot Specification was developed by a consortium comprising Compaq, Intel and Phoenix Technologies to standardise the initialisation sequence of PnP BIOS option ROMs and legacy option ROMs not conforming to the PnP BIOS standard and the order in which they hook interrupts. The standard presents the notion of a BCV table and BCV priority. The core principles of the standard make behaviour more defined and debuggable and gives BIOS manufacturers room to further dynamise boot device selection for the user on top of suggestions of the standard. A common option ROM is the video BIOS which gets loaded very early on in the boot process and hooks INT 10h so that output from the power-on self-test can be displayed. The video BIOS is almost always located in the C000memory segment, the start of the memory area reserved for option ROMs; this is because when the motherboard has a built in VGA controller, the option ROM will reside in the BIOS – the BIOS knows where it is and shadows it into memory at a fixed time. Other ROMs can be located from segments C800all the way up to F400 in early PCs. The final search address was eventually limited to E000Personal Computer BIOS Interface Technical Reference">, pg. 4-12 in later products. The BIOS Boot Specification requires that option ROMs be aligned to 2kB boundaries. The first two bytes of the ROM must be 55 AA. After the basic POST checks are complete, the BBS specifies that the BIOS will detect and shadow all option ROMs that reside in the BIOS into the aforementioned region and it will traverse the PCI configuration space, filling in XROMBARs and copying the expansion card option ROMs from MMIO space to the region. The BIOS then scans the region, and if the option ROM has a PnP Expansion header, it does a far call to offset +03h in the option ROM header to initialise it. It then rescans the region after all the PnP option ROMs have been initialised. It adds the BCV pointer in the PnP Expansion headers it finds the BCV Table or the BEV pointer to the IPL priority table. The BCV entries in the BCV table are then called according to priority togglable in NVRAM. The BCV table is full of BCV function pointers but has a fixed entry representing legacy option ROMs which is a pointer to a BIOS routine which calls +03h in all the remaining option ROMs that don't have a PnP Expansion header. The BCV function initialises the INT 13h and INT 19h hooks, which the BBS stipulates must not be done in the initialisation routine at +03h. If a device has no PnP Expansion header, it may perform any hook in the routine at +03h, as it is a legacy card. In the initial initialisation routine, as the Option ROM points to a PCI data structure, the option ROM code knows the device and vendor ID is at a fixed offset from RIP. This allows it to scan the PCI configuration space to find the correct device and BARs it needs to use. To prevent this scan, and in case of two identical cards in the system, the BIOS passes the PFA to the initialisation routine in AX, and the card select number for ISA option ROMs is passed in BX. It can then interact with the device using PMIO / MMIO to see how many disks it has and which ones are bootable by reading the MBR. The BIOS will have already combed the configuration space, allocated the BARs and filled in the ACPI table prior to the initialisation routine call, so the option ROM would use the addresses allocated to its BARs. The BCV, however, hooks interrupt routines which interact with the device which are adjusted based on a base MMIO address location, disk information ascertained in the option ROM initialisation routine and the current disk number in the BDA. The BIOS INT 19h procedure then uses the IPL table priority in NVRAM to decide whether to call an entry containing a boot handler which will read the MBR of 00h, an entry containing a boot handler which will read the MBR of 80h or one of the BEV entries in the table. A device only has a BEV or a BCV if it is a bootable device.
An ISA SCSI controller card may hook INT 13 which is responsible for providing disk services. It will do so in its BCV if it is a PnP ISA card. Once it has done this, any subsequent calls to INT 13h will be "caught" by the SCSI option ROM, allowing it to respond for disks that may exist on the SCSI bus. Before it had hooked the interrupt there may have been no disks on the system, but by intercepting the interrupt and altering the values returned, the SCSI BIOS can make all the disks on the SCSI bus visible to the system. In this particular case, the BIOS itself may call INT 13h to provide a list of possible boot devices to the user, and because the SCSI BIOS has hooked the interrupt the user will be able to choose not only which standard system devices to boot from, but also which SCSI disks as well. This is because, as suggested in Appendix D of the Boot BIOS Specification, the BIOS could populate the IPL table with device and vendor information from INT 13h calls to the different disks, paired with the Hard Disk Number, to allow any Hard Disk Device to be booted from, rather than just the first disk of the first controller to hook INT 13h be bootable, referred to as a BIOS Aware IPL Device in the specification. Multiple controllers can hook INT 13h at once. For instance, after the SCSI controller, an AHCI controller can also hook INT 13h by putting a call to the previous handler, which was stored in the IDT at entry 13h by the SCSI controller, at the end of its own handler, which it then puts in the IDT at entry 13h. If INT 13h is called with DL = 83h, then the controller that assigned a disk range containing 83h will respond, otherwise it will skip and call the previous handler. The first controller to hook INT 13h will see that 0 disks have been installed by checking the byte at 0040:0075, which resides in the BIOS Data Area, and if it has 4 disks to enumerate, it will assign the range 80h–83h and store '4' in the BDA.
Another common option ROM is a network boot ROM. The option ROM contains the program required to download the boot code. The original IBM Personal Computer ROMs hooked INT 18H and INT 19H, as these two interrupts were designated when the boot process is about to begin. INT 19H is called to initiate the boot process, while INT 18H is called when the system tries to boot from all possible devices and none were bootable. Originally, by hooking INT 18H, the system would invoke Cassette BASIC or try to boot from the network when all other boot devices had failed. By hooking INT 19H, the system would attempt to boot from the network before any other devices. The BBS specifies that the NIC option ROM does not hook 19h, instead the BIOS 19h handler should call the BEV, which will then download the boot code.
UEFI Option ROMs
The PCI spec allows multiple option ROM images on the same device. These option ROMs could be Legacy x86 & UEFI. If the Option ROM format is set to UEFI Compatible in the UEFI Firmware, the DXE stage will load the newer EFI ROM if one is present and the legacy ROM if one is not. UEFI can use legacy option ROMs when a Compatibility Support Module is enabled. Note that when Secure Boot is enabled, execution of the Compatibility Support Module and legacy ROMs is prohibited because legacy firmware drivers do not support authentication, which is a security threat.