diff options
author | Pierre-Alexandre Meyer <pierre@mouraf.org> | 2009-09-07 16:12:59 -0700 |
---|---|---|
committer | Pierre-Alexandre Meyer <pierre@mouraf.org> | 2009-09-07 16:22:36 -0700 |
commit | e9069caefc1460ec7f4d058796005474c125fc61 (patch) | |
tree | 25cd847439fb004798251a63fa8886073134009f | |
parent | c93e27af183de1cdf591706448d42887d0fbc0eb (diff) | |
parent | 03b2384b6e9f54d9697e87d2a19c321e6fd96ed5 (diff) | |
download | syslinux-e9069caefc1460ec7f4d058796005474c125fc61.tar.gz |
Merge branch 'bootloader-detection' into hdt-next
Conflicts:
com32/hdt/hdt-cli-disk.c
com32/hdt/hdt-common.h
com32/hdt/hdt-menu-disk.c
Signed-off-by: Pierre-Alexandre Meyer <pierre@mouraf.org>
-rw-r--r-- | com32/gplinclude/disk/bootloaders.h | 18 | ||||
-rw-r--r-- | com32/gplinclude/disk/mbrs.h | 18 | ||||
-rw-r--r-- | com32/gpllib/disk/bootloaders.c | 46 | ||||
-rw-r--r-- | com32/gpllib/disk/mbrs.c | 82 | ||||
-rw-r--r-- | com32/hdt/hdt-cli-disk.c | 36 | ||||
-rw-r--r-- | com32/hdt/hdt-common.c | 4 | ||||
-rw-r--r-- | com32/hdt/hdt-common.h | 9 | ||||
-rw-r--r-- | com32/hdt/hdt-menu-disk.c | 30 | ||||
-rw-r--r-- | com32/hdt/hdt-menu.c | 2 | ||||
-rw-r--r-- | com32/hdt/hdt-menu.h | 2 |
10 files changed, 232 insertions, 15 deletions
diff --git a/com32/gplinclude/disk/bootloaders.h b/com32/gplinclude/disk/bootloaders.h new file mode 100644 index 00000000..6aec9b3d --- /dev/null +++ b/com32/gplinclude/disk/bootloaders.h @@ -0,0 +1,18 @@ +/* ----------------------------------------------------------------------- * + * + * Copyright 2009 Pierre-Alexandre Meyer + * + * This file is part of Syslinux, and is made available under + * the terms of the GNU General Public License version 2. + * + * ----------------------------------------------------------------------- */ + +#ifndef __BOOTLOADERS_H_ +#define __BOOTLOADERS_H_ + +#include <stdint.h> +#include <disk/geom.h> +#include <disk/partition.h> + +int get_bootloader_string(const struct driveinfo *, const struct part_entry *, char*, const int); +#endif /* __BOOTLOADERS_H_ */ diff --git a/com32/gplinclude/disk/mbrs.h b/com32/gplinclude/disk/mbrs.h new file mode 100644 index 00000000..ad104ff7 --- /dev/null +++ b/com32/gplinclude/disk/mbrs.h @@ -0,0 +1,18 @@ +/* ----------------------------------------------------------------------- * + * + * Copyright 2009 Pierre-Alexandre Meyer + * + * This file is part of Syslinux, and is made available under + * the terms of the GNU General Public License version 2. + * + * ----------------------------------------------------------------------- */ + +#ifndef __MBRS_H_ +#define __MBRS_H_ + +#include <stdint.h> +#include <disk/geom.h> + +void get_mbr_string(const uint32_t, void *, const int); +uint32_t get_mbr_id(const struct driveinfo *); +#endif /* __MBRS_H_ */ diff --git a/com32/gpllib/disk/bootloaders.c b/com32/gpllib/disk/bootloaders.c new file mode 100644 index 00000000..4b3962ae --- /dev/null +++ b/com32/gpllib/disk/bootloaders.c @@ -0,0 +1,46 @@ +/* ----------------------------------------------------------------------- * + * + * Copyright 2009 Pierre-Alexandre Meyer + * + * This file is part of Syslinux, and is made available under + * the terms of the GNU General Public License version 2. + * + * ----------------------------------------------------------------------- */ + +#include <disk/bootloaders.h> +#include <disk/common.h> +#include <disk/geom.h> +#include <disk/read.h> +#include <stdlib.h> +#include <string.h> + +/** + * get_bootloader_string - return a string describing the boot code in a + * bootsector + * @d: driveinfo struct describing the drive + * @p: partition to scan (usually the active one) + * @buffer: pre-allocated buffer + * @buffer_size: @buffer size + **/ +int get_bootloader_string(const struct driveinfo *d, const struct part_entry *p, + char* buffer, const int buffer_size) +{ + char boot_sector[SECTOR * sizeof(char)]; + + if (read_sectors(d, &boot_sector, p->start_lba, 1) == -1) + return -1; + else { + if (!strncmp(boot_sector + 3, "SYSLINUX", 8)) + strncpy(buffer, "SYSLINUX", buffer_size - 1); + else if (!strncmp(boot_sector + 3, "EXTLINUX", 8)) + strncpy(buffer, "EXTLINUX", buffer_size - 1); + else if (!strncmp(boot_sector + 3, "MSWIN4.1", 8)) + strncpy(buffer, "MSWIN4.1", buffer_size - 1); + else + return -1; + /* Add more... */ + + buffer[buffer_size - 1] = '\0'; + return 0; + } +} diff --git a/com32/gpllib/disk/mbrs.c b/com32/gpllib/disk/mbrs.c new file mode 100644 index 00000000..b5e271b7 --- /dev/null +++ b/com32/gpllib/disk/mbrs.c @@ -0,0 +1,82 @@ +/* ----------------------------------------------------------------------- * + * + * Copyright 2009 Pierre-Alexandre Meyer + * + * This file is part of Syslinux, and is made available under + * the terms of the GNU General Public License version 2. + * + * ----------------------------------------------------------------------- */ + +#include <disk/common.h> +#include <disk/geom.h> +#include <disk/read.h> +#include <stdlib.h> +#include <string.h> +#include <stdio.h> + +/** + * get_mbr_string - return a string describing the boot code + * @label: first four bytes of the MBR + * @buffer: pre-allocated buffer + * @buffer_size: @buffer size + **/ +void get_mbr_string(const uint32_t label, char* buffer, const int buffer_size) +{ + /* 2 bytes are usually enough to identify the MBR */ + uint16_t s_label = label >> 16; + + switch (s_label) { + case 0x0000: + case 0xfa33: + case 0xfab8: + case 0xfabe: + strncpy(buffer, "No bootloader", buffer_size - 1); break; + case 0x0ebe: strncpy(buffer, "ThinkPad", buffer_size - 1); break; + case 0x31c0: strncpy(buffer, "Acer 3", buffer_size - 1); break; + case 0x33c0: strncpy(buffer, "Windows", buffer_size - 1); break; + case 0x33ff: strncpy(buffer, "HP/Gateway", buffer_size - 1); break; + case 0xb800: strncpy(buffer, "Plop", buffer_size - 1); break; + case 0xea1e: strncpy(buffer, "Truecrypt Boot Loader", buffer_size - 1); break; + case 0xeb04: strncpy(buffer, "Solaris", buffer_size - 1); break; + case 0xeb48: strncpy(buffer, "Grub", buffer_size - 1); break; + case 0xeb4c: strncpy(buffer, "Grub2", buffer_size - 1); break; + case 0xeb5e: strncpy(buffer, "Grub4Dos", buffer_size - 1); break; + case 0xfa31: + /* We need more than 2 bytes */ + if ((label >> 8) & 0xff == 0xc9) + strncpy(buffer, "Master Boot LoaDeR", buffer_size - 1); + else if ((label >> 8) & 0xff == 0xc0) + strncpy(buffer, "Syslinux", buffer_size - 1); + else + strncpy(buffer, "Unknown mbr", buffer_size - 1); break; + break; + case 0xfaeb: strncpy(buffer, "Lilo", buffer_size - 1); break; + case 0xfc31: strncpy(buffer, "Testdisk", buffer_size - 1); break; + case 0xfc33: strncpy(buffer, "Gag", buffer_size - 1); break; + case 0xfceb: strncpy(buffer, "BootIT NG", buffer_size - 1); break; + default: strncpy(buffer, "Unknown mbr", buffer_size - 1); break; + } + + buffer[buffer_size - 1] = '\0'; +} + +/** + * get_mbr_id - return the first four bytes of the MBR + * @d: driveinfo struct describing the drive + **/ +uint32_t get_mbr_id(const struct driveinfo *d) +{ + char mbr[SECTOR * sizeof(char)]; + + if (read_mbr(d->disk, &mbr) == -1) + return -1; + else { + uint32_t mbr_id; + /* Reverse the opcodes */ + mbr_id = (*(uint8_t *) (mbr + 3)); + mbr_id += (*(uint8_t *) (mbr + 2) << 8); + mbr_id += (*(uint8_t *) (mbr + 1) << 16); + mbr_id += (*(uint8_t *) mbr) << 24; + return mbr_id; + } +} diff --git a/com32/hdt/hdt-cli-disk.c b/com32/hdt/hdt-cli-disk.c index bcd4400c..48f19012 100644 --- a/com32/hdt/hdt-cli-disk.c +++ b/com32/hdt/hdt-cli-disk.c @@ -56,6 +56,7 @@ static void show_partition_information(struct driveinfo *drive_info, int nb_partitions_seen) { char size[9]; + char bootloader_name[9]; char *parttype; unsigned int start, end; @@ -70,10 +71,10 @@ static void show_partition_information(struct driveinfo *drive_info, memset(size, 0, sizeof size); if (i == 1) - more_printf(" # B Start End Size Id Type\n"); + more_printf(" # B Start End Size Id Type\n"); get_label(ptab->ostype, &parttype); - more_printf(" %2d %s %11d %11d %s %02X %s", + more_printf("%2d %s %11d %11d %s %02X %s", i, (ptab->active_flag == 0x80) ? "x" : " ", start, end, @@ -84,6 +85,9 @@ static void show_partition_information(struct driveinfo *drive_info, if (ptab->ostype == 0x82 && swsusp_check(drive_info, ptab)) more_printf("%s", " (Swsusp sig. detected)"); + if (get_bootloader_string(drive_info, ptab, bootloader_name, 9) == 0) + more_printf("%-46s %s %s", " ", "Bootloader:", bootloader_name); + more_printf("\n"); free(parttype); @@ -107,11 +111,14 @@ void main_show_disk(int argc, char **argv, int i = drive - 0x80; struct driveinfo *d = &hardware->disk_info[i]; char disk_size[9]; + char mbr_name[50]; detect_disks(hardware); if (!hardware->disk_info[i].cbios) return; /* Invalid geometry */ + get_mbr_string(hardware->mbr_ids[i], &mbr_name, 50); + if ((int) d->edd_params.sectors > 0) sectors_to_size((int) d->edd_params.sectors, disk_size); else @@ -119,14 +126,17 @@ void main_show_disk(int argc, char **argv, more_printf("DISK 0x%X:\n" " C/H/S: %d cylinders, %d heads, %d sectors/track\n" - " EDD: Version: %X\n" + " EDD: Version: %X\n" " Size: %s, %d bytes/sector, %d sectors/track\n" - " Host bus: %s, Interface type: %s\n\n", + " Host bus: %s, Interface type: %s\n" + " MBR: %s (id 0x%X)\n\n", d->disk, d->legacy_max_cylinder + 1, d->legacy_max_head + 1, d->legacy_sectors_per_track, d->edd_version, disk_size, (int) d->edd_params.bytes_per_sector, (int) d->edd_params.sectors_per_track, - remove_spaces((char *) d->edd_params.host_bus_type), remove_spaces((char*) d->edd_params.interface_type)); + remove_spaces((char *) d->edd_params.host_bus_type), remove_spaces((char*) d->edd_params.interface_type), + mbr_name, hardware->mbr_ids[i]); + display_line_nb += 6; if (parse_partition_table(d, &show_partition_information)) { if (errno_disk) { @@ -147,11 +157,19 @@ void main_show_disks(int argc __unused, char **argv __unused, reset_more_printf(); detect_disks(hardware); + int first_one = 0; for (int drive = 0x80; drive < 0xff; drive++) { - char buf[5] = ""; - sprintf(buf, "0x%x", drive); - char *argv[1] = { buf }; - main_show_disk(1, argv, hardware); + if (hardware->disk_info[drive - 0x80].cbios) { + if (!first_one) { + first_one = 1; + } else { + pause_printf(); + } + char buf[5] = ""; + sprintf(buf, "0x%x", drive); + char *argv[1] = { buf }; + main_show_disk(1, argv, hardware); + } } } diff --git a/com32/hdt/hdt-common.c b/com32/hdt/hdt-common.c index 80305a3e..11887c39 100644 --- a/com32/hdt/hdt-common.c +++ b/com32/hdt/hdt-common.c @@ -35,6 +35,7 @@ #include "hdt-common.h" #include "lib-ansi.h" #include <disk/util.h> +#include <disk/mbrs.h> /* ISOlinux requires a 8.3 format */ void convert_isolinux_filename(char *filename, struct s_hardware *hardware) { @@ -269,6 +270,9 @@ void detect_disks(struct s_hardware *hardware) if (err == -1 || !hardware->disk_info[i].cbios) continue; + /* Detect MBR */ + hardware->mbr_ids[i] = get_mbr_id(&hardware->disk_info[i]); + hardware->disks_count++; } } diff --git a/com32/hdt/hdt-common.h b/com32/hdt/hdt-common.h index e326cb12..ef9382b7 100644 --- a/com32/hdt/hdt-common.h +++ b/com32/hdt/hdt-common.h @@ -32,9 +32,11 @@ #include <syslinux/pxe.h> #include "sys/pci.h" +#include <disk/bootloaders.h> #include <disk/errno_disk.h> #include <disk/error.h> #include <disk/geom.h> +#include <disk/mbrs.h> #include <disk/msdos.h> #include <disk/partition.h> #include <disk/swsusp.h> @@ -56,6 +58,12 @@ extern int display_line_nb; +#define pause_printf() do {\ + printf("--More--");\ + get_key(stdin, 0);\ + printf("\n");\ +} while (0); + #define more_printf(...) do {\ if (display_line_nb == 20) {\ printf("\nPress any key to continue");\ @@ -120,6 +128,7 @@ struct s_hardware { s_vpd vpd; /* VPD information */ struct pci_domain *pci_domain; /* PCI Devices */ struct driveinfo disk_info[256]; /* Disk Information */ + uint32_t mbr_ids[256]; /* MBR ids */ int disks_count; /* Number of detected disks */ struct s_pxe pxe; struct s_vesa vesa; diff --git a/com32/hdt/hdt-menu-disk.c b/com32/hdt/hdt-menu-disk.c index 668b7cb4..2f3571b9 100644 --- a/com32/hdt/hdt-menu-disk.c +++ b/com32/hdt/hdt-menu-disk.c @@ -74,6 +74,7 @@ static void compute_partition_information(struct driveinfo *drive_info, int nb_partitions_seen) { char size[9]; + char bootloader_name[9]; char *parttype; unsigned int start, end; char buffer[SUBMENULEN+1]; @@ -113,6 +114,14 @@ static void compute_partition_information(struct driveinfo *drive_info, parttype); add_item(buffer, statbuffer, OPT_INACTIVE, NULL, 0); + if (get_bootloader_string(drive_info, ptab, bootloader_name, 9) == 0) { + snprintf(buffer, sizeof buffer, "Bootloader : %s", + bootloader_name); + snprintf(statbuffer, sizeof statbuffer, "Bootloader: %s", + bootloader_name); + add_item(buffer, statbuffer, OPT_INACTIVE, NULL, 0); + } + snprintf(buffer, sizeof buffer, "Bootable : %s", (ptab->active_flag == 0x80) ? "Yes" : "No"); snprintf(statbuffer, sizeof statbuffer, "Bootable: %s", @@ -150,10 +159,12 @@ static void compute_partition_information(struct driveinfo *drive_info, /* Compute the disk submenu */ static int compute_disk_module(struct s_my_menu *menu, int nb_sub_disk_menu, - struct driveinfo *d, int disk_number) + const struct s_hardware *hardware, int disk_number) { char buffer[MENULEN + 1]; char statbuffer[STATLEN + 1]; + char mbr_name[50]; + struct driveinfo *d = (struct driveinfo*) hardware->disk_info; snprintf(buffer, sizeof buffer, " Disk <0x%X> (EDD %X)", d[disk_number].disk, d[disk_number].edd_version); @@ -200,6 +211,17 @@ static int compute_disk_module(struct s_my_menu *menu, int nb_sub_disk_menu, add_item(buffer, statbuffer, OPT_INACTIVE, NULL, 0); menu[nb_sub_disk_menu].items_count++; + get_mbr_string(hardware->mbr_ids[disk_number], &mbr_name, 50); + + snprintf(buffer, sizeof buffer, "MBR : %s (0x%X)", + remove_spaces(mbr_name), + hardware->mbr_ids[disk_number]); + snprintf(statbuffer, sizeof statbuffer, "MBR: %s (id 0x%X)", + remove_spaces(mbr_name), + hardware->mbr_ids[disk_number]); + add_item(buffer, statbuffer, OPT_INACTIVE, NULL, 0); + menu[nb_sub_disk_menu].items_count++; + dn=disk_number; parse_partition_table(&d[disk_number], &show_partition_information); @@ -212,7 +234,7 @@ static int compute_disk_module(struct s_my_menu *menu, int nb_sub_disk_menu, } /* Compute the Disks menu */ -void compute_disks(struct s_hdt_menu *menu, struct driveinfo *disk_info, struct s_hardware *hardware) +void compute_disks(struct s_hdt_menu *menu, struct s_hardware *hardware) { char buffer[MENULEN + 1]; int nb_sub_disk_menu = 0; @@ -225,8 +247,8 @@ void compute_disks(struct s_hdt_menu *menu, struct driveinfo *disk_info, struct if (!hardware->disk_info[i].cbios) continue; /* Invalid geometry */ compute_disk_module - ((struct s_my_menu*) &(menu->disk_sub_menu), nb_sub_disk_menu, disk_info, - i); + ((struct s_my_menu*) &(menu->disk_sub_menu), nb_sub_disk_menu, + hardware, i); nb_sub_disk_menu++; } diff --git a/com32/hdt/hdt-menu.c b/com32/hdt/hdt-menu.c index c37fd41b..53afefc9 100644 --- a/com32/hdt/hdt-menu.c +++ b/com32/hdt/hdt-menu.c @@ -154,7 +154,7 @@ void compute_submenus(struct s_hdt_menu *hdt_menu, struct s_hardware *hardware) compute_processor(&(hdt_menu->cpu_menu), hardware); compute_vpd(&(hdt_menu->vpd_menu), hardware); - compute_disks(hdt_menu, hardware->disk_info, hardware); + compute_disks(hdt_menu, hardware); #ifdef WITH_PCI compute_PCI(hdt_menu, hardware); diff --git a/com32/hdt/hdt-menu.h b/com32/hdt/hdt-menu.h index 1cd2c129..6ac688f7 100644 --- a/com32/hdt/hdt-menu.h +++ b/com32/hdt/hdt-menu.h @@ -91,7 +91,7 @@ int compute_PCI(struct s_hdt_menu *hdt_menu, struct s_hardware *hardware); void compute_kernel(struct s_my_menu *menu, struct s_hardware *hardware); // Disk Stuff -void compute_disks(struct s_hdt_menu *menu, struct driveinfo *disk_info, struct s_hardware *hardware); +void compute_disks(struct s_hdt_menu *menu, struct s_hardware *hardware); // DMI Stuff void compute_motherboard(struct s_my_menu *menu, s_dmi * dmi); |