[SeaBIOS] [PATCH 1/3] Record boot priority for each BAID/BCV/BEV.

Gleb Natapov gleb at redhat.com
Sun Dec 26 16:33:23 CET 2010


For each BAID/BCV/BEV lookup its boot priority in boot order file. If
there is no entry for a device there assign it the lowest boot priority.

Signed-off-by: Gleb Natapov <gleb at redhat.com>
---
 src/ahci.c       |    4 ++--
 src/ata.c        |   10 ++++++++--
 src/boot.c       |   38 ++++++++++++++++++++++++++++++++++----
 src/boot.h       |   15 +++++++++++----
 src/floppy.c     |   22 ++++++++++++++++++++--
 src/optionroms.c |   19 ++++++++++++++++---
 src/usb-msc.c    |    2 +-
 src/virtio-blk.c |    2 +-
 8 files changed, 93 insertions(+), 19 deletions(-)

diff --git a/src/ahci.c b/src/ahci.c
index 70c0f1c..a209c86 100644
--- a/src/ahci.c
+++ b/src/ahci.c
@@ -382,7 +382,7 @@ ahci_port_init(struct ahci_ctrl_s *ctrl, u32 pnr)
         // Setup disk geometry translation.
         setup_translation(&port->drive);
         // Register with bcv system.
-        add_bcv_internal(&port->drive);
+        add_bcv_internal(&port->drive, MAX_BOOT_PRIO);
     } else {
         // found cdrom (atapi)
         port->drive.blksize = CDROM_SECTOR_SIZE;
@@ -397,7 +397,7 @@ ahci_port_init(struct ahci_ctrl_s *ctrl, u32 pnr)
         // fill cdidmap
         if (iscd) {
             map_cd_drive(&port->drive);
-            add_baid_cdrom(&port->drive);
+            add_baid_cdrom(&port->drive, MAX_BOOT_PRIO);
 	}
     }
     dprintf(1, "%s\n", port->drive.desc);
diff --git a/src/ata.c b/src/ata.c
index d971480..e45de50 100644
--- a/src/ata.c
+++ b/src/ata.c
@@ -783,8 +783,11 @@ init_drive_atapi(struct atadrive_s *dummy, u16 *buffer)
 
     // fill cdidmap
     if (iscd) {
+        int prio = bootprio_find_ata_device(adrive_g->chan_gf->pci_bdf,
+                                            adrive_g->chan_gf->chanid,
+                                            adrive_g->slave);
         map_cd_drive(&adrive_g->drive);
-        add_baid_cdrom(&adrive_g->drive);
+        add_baid_cdrom(&adrive_g->drive, prio);
     }
 
     return adrive_g;
@@ -834,8 +837,11 @@ init_drive_ata(struct atadrive_s *dummy, u16 *buffer)
     // Setup disk geometry translation.
     setup_translation(&adrive_g->drive);
 
+    int prio = bootprio_find_ata_device(adrive_g->chan_gf->pci_bdf,
+                                        adrive_g->chan_gf->chanid,
+                                        adrive_g->slave);
     // Register with bcv system.
-    add_bcv_internal(&adrive_g->drive);
+    add_bcv_internal(&adrive_g->drive, prio);
 
     return adrive_g;
 }
diff --git a/src/boot.c b/src/boot.c
index 5137345..8a9246e 100644
--- a/src/boot.c
+++ b/src/boot.c
@@ -113,7 +113,7 @@ boot_setup(void)
 
 // Add a BEV vector for a given pnp compatible option rom.
 void
-add_bev(u16 seg, u16 bev, u16 desc)
+add_bev(u16 seg, u16 bev, u16 desc, u8 prio)
 {
     if (! CONFIG_BOOT)
         return;
@@ -127,11 +127,12 @@ add_bev(u16 seg, u16 bev, u16 desc)
     if (desc)
         d = MAKE_FLATPTR(seg, desc);
     ie->description = d;
+    ie->prio = prio;
 }
 
 // Add a IPL entry for BAID cdrom.
 void
-add_baid_cdrom(struct drive_s *drive_g)
+add_baid_cdrom(struct drive_s *drive_g, u8 prio)
 {
     if (! CONFIG_CDROM_BOOT)
         return;
@@ -146,11 +147,18 @@ add_baid_cdrom(struct drive_s *drive_g)
     ie->type = IPL_TYPE_CDROM;
     ie->vector = (u32)drive_g;
     ie->description = "DVD/CD";
+    ie->prio = prio;
+}
+
+void set_floppy_baid_prio(u8 prio)
+{
+    struct ipl_entry_s *ie = &IPL.bev[0];
+    ie->prio = prio;
 }
 
 // Add a bcv entry for an expansion card harddrive or legacy option rom
 void
-add_bcv(u16 seg, u16 ip, u16 desc)
+add_bcv(u16 seg, u16 ip, u16 desc, u8 prio)
 {
     if (! CONFIG_BOOT)
         return;
@@ -164,11 +172,12 @@ add_bcv(u16 seg, u16 ip, u16 desc)
     if (desc)
         d = MAKE_FLATPTR(seg, desc);
     ie->description = d;
+    ie->prio = prio;
 }
 
 // Add a bcv entry for an internal harddrive
 void
-add_bcv_internal(struct drive_s *drive_g)
+add_bcv_internal(struct drive_s *drive_g, u8 prio)
 {
     if (! CONFIG_BOOT)
         return;
@@ -196,6 +205,7 @@ add_bcv_internal(struct drive_s *drive_g)
     ie->type = BCV_TYPE_INTERNAL;
     ie->vector = (u32)drive_g;
     ie->description = "";
+    ie->prio = prio;
 }
 
 
@@ -571,3 +581,23 @@ handle_19(void)
     SET_EBDA(boot_sequence, 0);
     do_boot(0);
 }
+
+u8 bootprio_find_pci_device(int bdf)
+{
+    return MAX_BOOT_PRIO;
+}
+
+u8 bootprio_find_ata_device(int bdf, int chanid, int slave)
+{
+    return MAX_BOOT_PRIO;
+}
+
+u8 bootprio_find_fdc_device(int bfd, int port, int fdid)
+{
+    return MAX_BOOT_PRIO;
+}
+
+u8 bootprio_find_named_rom(const char *name)
+{
+    return MAX_BOOT_PRIO;
+}
diff --git a/src/boot.h b/src/boot.h
index 778aebd..5a4c6ea 100644
--- a/src/boot.h
+++ b/src/boot.h
@@ -12,6 +12,7 @@ struct ipl_entry_s {
     u16 subchoice;
     u32 vector;
     const char *description;
+    u8 prio;
 };
 
 struct ipl_s {
@@ -33,6 +34,7 @@ struct ipl_s {
 #define BCV_TYPE_EXTERNAL    0x80
 #define BCV_TYPE_INTERNAL    0x02
 
+#define MAX_BOOT_PRIO        255
 
 /****************************************************************
  * Function defs
@@ -41,12 +43,17 @@ struct ipl_s {
 // boot.c
 extern struct ipl_s IPL;
 void boot_setup(void);
-void add_bev(u16 seg, u16 bev, u16 desc);
-void add_bcv(u16 seg, u16 ip, u16 desc);
+void add_bev(u16 seg, u16 bev, u16 desc, u8 prio);
+void add_bcv(u16 seg, u16 ip, u16 desc, u8 prio);
 struct drive_s;
-void add_bcv_internal(struct drive_s *drive_g);
-void add_baid_cdrom(struct drive_s *drive_g);
+void add_bcv_internal(struct drive_s *drive_g, u8 prio);
+void add_baid_cdrom(struct drive_s *drive_g, u8 prio);
+void set_floppy_baid_prio(u8 prio);
 
 void boot_prep(void);
+u8 bootprio_find_pci_device(int bdf);
+u8 bootprio_find_ata_device(int bdf, int chanid, int slave);
+u8 bootprio_find_fdc_device(int bfd, int port, int fdid);
+u8 bootprio_find_named_rom(const char *name);
 
 #endif // __BOOT_H
diff --git a/src/floppy.c b/src/floppy.c
index 6491b96..7dd3083 100644
--- a/src/floppy.c
+++ b/src/floppy.c
@@ -13,6 +13,9 @@
 #include "cmos.h" // inb_cmos
 #include "pic.h" // eoi_pic1
 #include "bregs.h" // struct bregs
+#include "pci.h" // pci_to_bdf
+#include "pci_ids.h" // PCI_CLASS_BRIDGE_ISA
+#include "boot.h" // bootprio_find_fdc_device
 
 #define FLOPPY_SIZE_CODE 0x02 // 512 byte sectors
 #define FLOPPY_DATALEN 0xff   // Not used - because size code is 0x02
@@ -131,10 +134,25 @@ floppy_setup(void)
         // XXX - disable floppies on coreboot for now.
     } else {
         u8 type = inb_cmos(CMOS_FLOPPY_DRIVE_TYPE);
-        if (type & 0xf0)
+        unsigned int prio0 = -1, prio1 = -1;
+        int bdf = pci_find_class(PCI_CLASS_BRIDGE_ISA); /* isa-to-pci bridge */
+
+        if (type & 0xf0) {
             addFloppy(0, type >> 4, DTYPE_FLOPPY);
-        if (type & 0x0f)
+            prio0 = bootprio_find_fdc_device(bdf, 0x3f0, 0);
+        }
+        if (type & 0x0f) {
             addFloppy(1, type & 0x0f, DTYPE_FLOPPY);
+            prio1 = bootprio_find_fdc_device(bdf, 0x3f0, 1);
+        }
+        if (prio1 < prio0) {
+            /* if B has lower boot priority swap it with A  */
+            struct drive_s *tmp = Drives.idmap[EXTTYPE_FLOPPY][0];
+            Drives.idmap[EXTTYPE_FLOPPY][0] = Drives.idmap[EXTTYPE_FLOPPY][1];
+            Drives.idmap[EXTTYPE_FLOPPY][1] = tmp;
+            set_floppy_baid_prio(prio1);
+        } else
+            set_floppy_baid_prio(prio0);
     }
 
     outb(0x02, PORT_DMA1_MASK_REG);
diff --git a/src/optionroms.c b/src/optionroms.c
index 19672f7..171ec1c 100644
--- a/src/optionroms.c
+++ b/src/optionroms.c
@@ -75,6 +75,7 @@ struct pnp_data {
 u32 RomEnd = BUILD_ROM_START;
 
 
+
 /****************************************************************
  * Helper functions
  ****************************************************************/
@@ -220,6 +221,17 @@ setRomSource(u64 *sources, struct rom_header *rom, u64 source)
         sources[((u32)rom - BUILD_ROM_START) / OPTION_ROM_ALIGN] = source;
 }
 
+static u8
+getRomPriority(u64 *sources, struct rom_header *rom)
+{
+    u64 source = sources[((u32)rom - BUILD_ROM_START) / OPTION_ROM_ALIGN];
+    if (!source)
+        return -1;
+    if (source & RS_PCIROM)
+        return bootprio_find_pci_device(source);
+    return bootprio_find_named_rom(romfile_name(source));
+}
+
 
 /****************************************************************
  * Roms in CBFS
@@ -408,21 +420,22 @@ optionrom_setup(void)
             pos += OPTION_ROM_ALIGN;
             continue;
         }
+        u8 romprio = getRomPriority(sources, rom);
         pos += ALIGN(rom->size * 512, OPTION_ROM_ALIGN);
         struct pnp_data *pnp = get_pnp_rom(rom);
         if (! pnp) {
             // Legacy rom.
-            add_bcv(FLATPTR_TO_SEG(rom), OPTION_ROM_INITVECTOR, 0);
+            add_bcv(FLATPTR_TO_SEG(rom), OPTION_ROM_INITVECTOR, 0, romprio);
             continue;
         }
         // PnP rom.
         if (pnp->bev)
             // Can boot system - add to IPL list.
-            add_bev(FLATPTR_TO_SEG(rom), pnp->bev, pnp->productname);
+            add_bev(FLATPTR_TO_SEG(rom), pnp->bev, pnp->productname, romprio);
         else
             // Check for BCV (there may be multiple).
             while (pnp && pnp->bcv) {
-                add_bcv(FLATPTR_TO_SEG(rom), pnp->bcv, pnp->productname);
+                add_bcv(FLATPTR_TO_SEG(rom), pnp->bcv, pnp->productname, romprio);
                 pnp = get_pnp_next(rom, pnp);
             }
     }
diff --git a/src/usb-msc.c b/src/usb-msc.c
index 080efdc..c3ffe0b 100644
--- a/src/usb-msc.c
+++ b/src/usb-msc.c
@@ -171,7 +171,7 @@ setup_drive_hd(struct disk_op_s *op)
     setup_translation(op->drive_g);
 
     // Register with bcv system.
-    add_bcv_internal(op->drive_g);
+    add_bcv_internal(op->drive_g, MAX_BOOT_PRIO);
 
     return 0;
 }
diff --git a/src/virtio-blk.c b/src/virtio-blk.c
index 7a25826..3d2b7a6 100644
--- a/src/virtio-blk.c
+++ b/src/virtio-blk.c
@@ -153,7 +153,7 @@ init_virtio_blk(u16 bdf)
     vdrive_g->drive.pchs.spt = cfg.sectors;
 
     setup_translation(&vdrive_g->drive);
-    add_bcv_internal(&vdrive_g->drive);
+    add_bcv_internal(&vdrive_g->drive, bootprio_find_pci_device(bdf));
 
     snprintf(desc, MAXDESCSIZE, "Virtio disk PCI:%x:%x",
              pci_bdf_to_bus(bdf), pci_bdf_to_dev(bdf));
-- 
1.7.2.3




More information about the SeaBIOS mailing list