From: Michal Soltys Date: Mon, 16 Aug 2010 11:07:12 +0000 (+0200) Subject: chain.c: Don't bruteforce loops detecting fixed drives. X-Git-Tag: syslinux-4.06-pre3~3^2~68 X-Git-Url: http://review.tizen.org/git/?a=commitdiff_plain;h=d4d713c9ccfe08bf5e129a398d4f2a313b7ffe62;p=profile%2Fivi%2Fsyslinux.git chain.c: Don't bruteforce loops detecting fixed drives. Previously chain module looped all possible fixed disks from 0x80 to 0xFF. It's prone to BIOS bugs, where BIOS can report nonexistent or phantom drives at higher numbers. It's safer to use fixed disk count value from 40:75 to limit such loops. Signed-off-by: Michal Soltys --- diff --git a/com32/chain/chain.c b/com32/chain/chain.c index 6b69302..6c11a4d 100644 --- a/com32/chain/chain.c +++ b/com32/chain/chain.c @@ -39,6 +39,7 @@ #define ADDRMIN 0x500 static const char cmldr_signature[8] = "cmdcons"; +static int fixed_cnt; static struct options { uint32_t flin; @@ -83,7 +84,7 @@ static int find_by_sig(uint32_t mbr_sig, struct disk_info diskinfo; int drive; - for (drive = 0x80; drive <= 0xff; drive++) { + for (drive = 0x80; drive < 0x80 + fixed_cnt; drive++) { if (disk_get_params(drive, &diskinfo)) continue; /* Drive doesn't exist */ if (!(boot_part = pi_begin(&diskinfo))) @@ -118,7 +119,7 @@ static int find_by_guid(const struct guid *gpt_guid, struct disk_info diskinfo; int drive; - for (drive = 0x80; drive <= 0xff; drive++) { + for (drive = 0x80; drive < 0x80 + fixed_cnt; drive++) { if (disk_get_params(drive, &diskinfo)) continue; /* Drive doesn't exist */ if (!(boot_part = pi_begin(&diskinfo))) @@ -157,7 +158,7 @@ static int find_by_label(const char *label, struct part_iter **_boot_part) struct disk_info diskinfo; int drive; - for (drive = 0x80; drive <= 0xff; drive++) { + for (drive = 0x80; drive < 0x80 + fixed_cnt; drive++) { if (disk_get_params(drive, &diskinfo)) continue; /* Drive doesn't exist */ if (!(boot_part = pi_begin(&diskinfo))) @@ -651,21 +652,25 @@ int find_dp(struct part_iter **_iter) "'boot' and 'fs' are meaningless.\n"); goto bail; } +#if 0 /* offsets match, but in case it changes in the future */ if(sdi->c.filesystem == SYSLINUX_FS_ISOLINUX) { drive = sdi->iso.drive_number; fs_lba = *sdi->iso.partoffset; } else { +#endif drive = sdi->disk.drive_number; fs_lba = *sdi->disk.partoffset; +#if 0 } +#endif if (disk_get_params(drive, &diskinfo)) goto bail; if (!(iter = pi_begin(&diskinfo))) goto bail; - /* 'fs' => we should lookup the Syslinux partition number and use it */ + /* 'fs' => we should lookup the syslinux partition number and use it */ if (!strcmp(opt.drivename, "fs")) { while (pi_next(&iter)) { if (iter->start_lba == fs_lba) @@ -963,6 +968,10 @@ int main(int argc, char *argv[]) if(opt.regs.ip == 0x7C00 && !opt.regs.cs) opt.regs.esp.l = 0x7C00; + /* Get max fixed disk number */ + + fixed_cnt = *(uint8_t *)(0x475); + /* Get disk/part iterator matching user supplied options */ if(find_dp(&iter)) goto bail;