diff --git a/ChangeLog b/ChangeLog index 51c6a644e..ba26f07d7 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,3 +1,18 @@ +2010-01-03 Robert Millan + + * boot/i386/pc/diskboot.S: Fix inaccurate comment. + + * util/i386/pc/grub-setup.c: Include `'. + (struct boot_blocklist): Move from here ... + * include/grub/i386/pc/boot.h [ASM_FILE] + (struct grub_boot_blocklist): ... to here. Update all users. + (setup): Only initialize `start' member of `first_block' + structure. Add assert() calls to verify the other members. + + * util/i386/pc/grub-mkimage.c: Include `'. + (generate_image): Fix broken blocklist length initialization. + Add assert() call to verify blocklist `segment' field. + 2010-01-03 Robert Millan * loader/efi/appleloader.c: Remove. Update all users. diff --git a/boot/i386/pc/diskboot.S b/boot/i386/pc/diskboot.S index 6b621190d..92f223f0d 100644 --- a/boot/i386/pc/diskboot.S +++ b/boot/i386/pc/diskboot.S @@ -1,6 +1,6 @@ /* * GRUB -- GRand Unified Bootloader - * Copyright (C) 1999,2000,2001,2002,2006,2007,2009 Free Software Foundation, Inc. + * Copyright (C) 1999,2000,2001,2002,2006,2007,2009,2010 Free Software Foundation, Inc. * * GRUB is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by @@ -370,7 +370,7 @@ blocklist_default_start: the start of the disk, sector 0 */ .long 2, 0 blocklist_default_len: - /* this is the number of sectors to read the command "install" + /* this is the number of sectors to read. grub-mkimage will fill this up */ .word 0 blocklist_default_seg: diff --git a/include/grub/i386/pc/boot.h b/include/grub/i386/pc/boot.h index f45fe6da0..508b10742 100644 --- a/include/grub/i386/pc/boot.h +++ b/include/grub/i386/pc/boot.h @@ -1,6 +1,6 @@ /* * GRUB -- GRand Unified Bootloader - * Copyright (C) 1999,2000,2002,2005,2006,2007,2008 Free Software Foundation, Inc. + * Copyright (C) 1999,2000,2002,2005,2006,2007,2008,2010 Free Software Foundation, Inc. * * GRUB is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by @@ -66,4 +66,16 @@ /* The size of a block list used in the kernel startup code. */ #define GRUB_BOOT_MACHINE_LIST_SIZE 12 +#ifndef ASM_FILE + +/* This is the blocklist used in the diskboot image. */ +struct grub_boot_blocklist +{ + grub_uint64_t start; + grub_uint16_t len; + grub_uint16_t segment; +} __attribute__ ((packed)); + +#endif /* ! ASM_FILE */ + #endif /* ! BOOT_MACHINE_HEADER */ diff --git a/util/i386/pc/grub-mkimage.c b/util/i386/pc/grub-mkimage.c index aaa1a13db..ebf1bc7ff 100644 --- a/util/i386/pc/grub-mkimage.c +++ b/util/i386/pc/grub-mkimage.c @@ -33,6 +33,7 @@ #include #include #include +#include #define _GNU_SOURCE 1 #include @@ -212,10 +213,17 @@ generate_image (const char *dir, char *prefix, FILE *out, char *mods[], boot_img = grub_util_read_image (boot_path); - /* i386 is a little endian architecture. */ - *((grub_uint16_t *) (boot_img + GRUB_DISK_SECTOR_SIZE - - GRUB_BOOT_MACHINE_LIST_SIZE + 8)) - = grub_cpu_to_le16 (num); + { + struct grub_boot_blocklist *block; + block = (struct grub_boot_blocklist *) (boot_img + + GRUB_DISK_SECTOR_SIZE + - sizeof (*block)); + block->len = grub_host_to_target16 (num); + + /* This is filled elsewhere. Verify it just in case. */ + assert (block->segment == grub_host_to_target16 (GRUB_BOOT_MACHINE_KERNEL_SEG + + (GRUB_DISK_SECTOR_SIZE >> 4))); + } grub_util_write_image (boot_img, boot_size, out); free (boot_img); diff --git a/util/i386/pc/grub-setup.c b/util/i386/pc/grub-setup.c index 5a1cbb27a..909a521eb 100644 --- a/util/i386/pc/grub-setup.c +++ b/util/i386/pc/grub-setup.c @@ -48,6 +48,7 @@ static const grub_gpt_part_type_t grub_gpt_partition_type_bios_boot = GRUB_GPT_P #include #include #include +#include #include "progname.h" #define _GNU_SOURCE 1 @@ -56,14 +57,6 @@ static const grub_gpt_part_type_t grub_gpt_partition_type_bios_boot = GRUB_GPT_P #define DEFAULT_BOOT_FILE "boot.img" #define DEFAULT_CORE_FILE "core.img" -/* This is the blocklist used in the diskboot image. */ -struct boot_blocklist -{ - grub_uint64_t start; - grub_uint16_t len; - grub_uint16_t segment; -} __attribute__ ((packed)); - void grub_putchar (int c) { @@ -99,7 +92,7 @@ setup (const char *dir, grub_uint8_t *boot_drive; grub_disk_addr_t *kernel_sector; grub_uint16_t *boot_drive_check; - struct boot_blocklist *first_block, *block; + struct grub_boot_blocklist *first_block, *block; grub_int32_t *install_dos_part, *install_bsd_part; grub_int32_t dos_part, bsd_part; char *tmp_img; @@ -171,7 +164,7 @@ setup (const char *dir, void NESTED_FUNC_ATTR save_blocklists (grub_disk_addr_t sector, unsigned offset, unsigned length) { - struct boot_blocklist *prev = block + 1; + struct grub_boot_blocklist *prev = block + 1; grub_util_info ("saving <%llu,%u,%u> with the segment 0x%x", sector, offset, length, (unsigned) current_segment); @@ -226,9 +219,9 @@ setup (const char *dir, core_img = grub_util_read_image (core_path); /* Have FIRST_BLOCK to point to the first blocklist. */ - first_block = (struct boot_blocklist *) (core_img - + GRUB_DISK_SECTOR_SIZE - - sizeof (*block)); + first_block = (struct grub_boot_blocklist *) (core_img + + GRUB_DISK_SECTOR_SIZE + - sizeof (*block)); install_dos_part = (grub_int32_t *) (core_img + GRUB_DISK_SECTOR_SIZE + GRUB_KERNEL_MACHINE_INSTALL_DOS_PART); @@ -389,10 +382,11 @@ setup (const char *dir, /* The first blocklist contains the whole sectors. */ first_block->start = grub_cpu_to_le64 (embed_region.start + 1); - first_block->len = grub_cpu_to_le16 (core_sectors - 1); - first_block->segment - = grub_cpu_to_le16 (GRUB_BOOT_MACHINE_KERNEL_SEG - + (GRUB_DISK_SECTOR_SIZE >> 4)); + + /* These are filled elsewhere. Verify them just in case. */ + assert (first_block->len == grub_host_to_target16 (core_sectors - 1)); + assert (first_block->segment == grub_host_to_target16 (GRUB_BOOT_MACHINE_KERNEL_SEG + + (GRUB_DISK_SECTOR_SIZE >> 4))); /* Make sure that the second blocklist is a terminator. */ block = first_block - 1;