From 0cfe1680d19f38aea275759d9df10b864c0372a0 Mon Sep 17 00:00:00 2001
From: "Brian C. Lane" <bcl@redhat.com>
Date: Fri, 7 Oct 2011 16:53:49 -0700
Subject: [PATCH] libparted: make pc98 detection depend on signatures

pc98 is not a common disk label. Change pc98_probe to only return true
if one of the recognized signatures is present.
Currently these include:

IPL1
Linux 98
GRUB/98

This prevents false-positive detection on msdos labeled disks.

* libparted/labels/pc98.c (pc98_probe): Change to require signature
(pc98_check_ipl_signature): Add more signatures
(check_partition_consistency): Remove unused function
Reported by Zach Carter in http://bugzilla.redhat.com/646053
---
 NEWS                    |    4 ++
 libparted/labels/pc98.c |   65 ++++++------------------------------------------
 2 files changed, 13 insertions(+), 56 deletions(-)

Index: parted-2.3/NEWS
===================================================================
--- parted-2.3.orig/NEWS
+++ parted-2.3/NEWS
@@ -47,6 +47,10 @@ GNU parted NEWS
   sector support being "HIGHLY EXPERIMENTAL".  It seems to have matured
   enough to be usable at least with GPT and MSDOS partition tables.
 
+  libparted: strengthen the pc98 test so that it is much less likely to
+  cause an MSDOS partition table to be mistakenly identified as pc98.
+  [bug present since the beginning]
+
 
 * Noteworthy changes in release 2.2 (2010-02-26) [stable]
 
Index: parted-2.3/libparted/labels/pc98.c
===================================================================
--- parted-2.3.orig/libparted/labels/pc98.c
+++ parted-2.3/libparted/labels/pc98.c
@@ -140,45 +140,20 @@ pc98_check_magic (const PC98RawTable *pa
 static int
 pc98_check_ipl_signature (const PC98RawTable *part_table)
 {
-	return !memcmp (part_table->boot_code + 4, "IPL1", 4);
-}
-
-static int
-check_partition_consistency (const PedDevice* dev,
-	       		     const PC98RawPartition* raw_part)
-{
-	if (raw_part->ipl_sect >= dev->hw_geom.sectors
-	   || raw_part->sector >= dev->hw_geom.sectors
-	   || raw_part->end_sector >= dev->hw_geom.sectors
-	   || raw_part->ipl_head >= dev->hw_geom.heads
-	   || raw_part->head >= dev->hw_geom.heads
-	   || raw_part->end_head >= dev->hw_geom.heads
-	   || PED_LE16_TO_CPU(raw_part->ipl_cyl) >= dev->hw_geom.cylinders
-	   || PED_LE16_TO_CPU(raw_part->cyl) >= dev->hw_geom.cylinders
-	   || PED_LE16_TO_CPU(raw_part->end_cyl) >= dev->hw_geom.cylinders
-	   || PED_LE16_TO_CPU(raw_part->cyl)
-	   	> PED_LE16_TO_CPU(raw_part->end_cyl)
-#if 0
-	   || !chs_to_sector(dev, PED_LE16_TO_CPU(raw_part->ipl_cyl),
-			     raw_part->ipl_head, raw_part->ipl_sect)
-	   || !chs_to_sector(dev, PED_LE16_TO_CPU(raw_part->cyl),
-			     raw_part->head, raw_part->sector)
-	   || !chs_to_sector(dev, PED_LE16_TO_CPU(raw_part->end_cyl),
-			     raw_part->end_head, raw_part->end_sector)
-#endif
-	   || PED_LE16_TO_CPU(raw_part->end_cyl)
-	  		< PED_LE16_TO_CPU(raw_part->cyl))
+	if (memcmp (part_table->boot_code + 4, "IPL1", 4) == 0)
+		return 1;
+	else if (memcmp (part_table->boot_code + 4, "Linux 98", 8) == 0)
+		return 1;
+	else if (memcmp (part_table->boot_code + 4, "GRUB/98 ", 8) == 0)
+		return 1;
+	else
 		return 0;
-
-	return 1;
 }
 
 static int
 pc98_probe (const PedDevice *dev)
 {
 	PC98RawTable		part_table;
-	int			empty;
-	const PC98RawPartition*	p;
 
 	PED_ASSERT (dev != NULL, return 0);
 
@@ -192,30 +167,8 @@ pc98_probe (const PedDevice *dev)
 	if (!pc98_check_magic (&part_table))
 		return 0;
 
-	/* check consistency */
-	empty = 1;
-	for (p = part_table.partitions;
-	     p < part_table.partitions + MAX_PART_COUNT;
-	     p++)
-	{
-		if (p->mid == 0 && p->sid == 0)
-			continue;
-		empty = 0;
-		if (!check_partition_consistency (dev, p))
-			return 0;
-	}
-
-	/* check boot loader */
-	if (pc98_check_ipl_signature (&part_table))
-		return 1;
-	else if (part_table.boot_code[0])	/* invalid boot loader */
-		return 0;
-
-	/* Not to mistake msdos disk map for PC-9800's empty disk map  */
-	if (empty)
-		return 0;
-
-	return 1;
+	/* check for boot loader signatures */
+	return pc98_check_ipl_signature (&part_table);
 }
 
 static PedDisk*
