grub4dos icon indicating copy to clipboard operation
grub4dos copied to clipboard

hidden sector count fixes for fat12_16_dbr, fat32_dbr, exfat_dbr and ntfs_dbr

Open pts opened this issue 5 years ago • 3 comments

Before this change, fat12_16_dbr, fat32_dbr, exfat_dbr and ntfs_dbr rely on the correct hidden sectors value, after this change, for EBIOS they will use the partition_table_entry.start_sector_ofs value passed by the MBR boot code in 32-bit 8(%si). This copies the behavior of ext2_3_4_dbr, which was already using this latter value.

This change fixes the No GRLDR failure reported by the GRUB2 boot code (typically installed by bootlace.com --floppy /dev/sda1) when trying to load GRLDR for FAT12, FAT16, FAT32, exFAT and NTFS filesystems.

Before this change, the GRUB2 boot code used as partition and filesystem start offset the hidden sectors value in the boot sector (BPB) of the filesystem on the partition. However, this value is often incorrect, for example when creating the filesystem as a image file by the mkfs.vfat, mkfs.exfat and mkfs.ntfs Linux tools, this value is 0 by default, as the tool has no way to know at filesystem creation time where within the the disk image the partition image will be copied to. Also if the partition is moved after it was created, some tools don't update the hidden sectors value.

As explained in https://en.wikipedia.org/wiki/Volume_boot_record , the MBR boot code makes partition sector offset value available at boot time in 32-bit 8(%si) (as part of the MBR partition table entry), thus it can be used instead of the hidden sectors value.

However, on some very old systems 8(%si) may be incorrect. To prevent this change from breaking them, the 8(%si) value is only used if EBIOS is detected. On systems without EBIOS, the user has already taken care of setting sectors per track and number of heads in the boot sector (BPB) (because otherwise the system wouldn't boot), and the tool setting these values correctly has probably set hidden sectors correctly as well.

I've verified that these changes work end-to-end, for example with the attached FAT16 filesystem (with hidden sectors value 0) in hdfat16.bin.xz.zip:

$ unzip hdfat16.bin.xz.zip
$ xz -cd <hdfat16.bin.xz >hdfat16.bin
$ qemu-system-i386 -m 16 -rtc base=localtime -no-acpi -drive file=hdfat16.bin,index=0,media=disk,format=raw -net none
...
grub> ls
 GRLDR
grub> ls (bd)/
 GRLDR
grub> ls (hd0,0)/
 GRLDR

Please note that ext2_3_4_dbr is already correct, it uses the 8(%si) value in https://github.com/chenall/grub4dos/blob/6dfb6d4213b337d398861e40ff4759319e4a8f37/stage2/grldrstart.S#L1961 .

pts avatar Nov 11 '19 23:11 pts

Any updates on this? Is there anything I can do to get this merged?

pts avatar Dec 09 '19 23:12 pts

fat, exfat, ntfs 是微软创建的文件系统,应当遵循微软的规定,至少应当适应其习俗。隐含扇区数是一个关键参数,格式化的工具就应当正确地确定他。 mkfs.vfat, mkfs.exfat and mkfs.ntfs 等 Linux 工具,格式化时,既然写磁盘,不可能不确定书写位置,也就是知道分区在磁盘的位置(隐含扇区数),而故意不将其填写到规定位置。grub4dos 尽量迁就有 bug 的硬件,而不迁就不遵循规范的软件。

yaya2007 avatar Dec 12 '19 01:12 yaya2007

grub4dos 从分区启动时,隐藏扇区数不使用启动分区自有的 bpb 表,却使用一个传入的值,有些怪怪的。

再说,当映射磁盘时,把启动分区复制到 0x7c00,传入驱动器号,跳转到 0x7c00 执行,此时没有执行由 int13/ah=42 ,不会传入隐藏扇区数。

不采用此方案。

yaya2007 avatar Dec 12 '19 10:12 yaya2007