NeilBrown: IMSM/DDF: don't recognised these metadata on partitions.

Martin F. Krafft madduck at alioth.debian.org
Sat Aug 28 18:44:05 UTC 2010


Module: mdadm
Branch: build
Commit: 691c6ee1b6bb77bc44a5474d856771b0aec9882d
URL:    http://git.debian.org/?p=pkg-mdadm/mdadm.git;a=commit;h=691c6ee1b6bb77bc44a5474d856771b0aec9882d

Author: NeilBrown <neilb at suse.de>
Date:   Thu Apr 29 16:09:59 2010 +1000

IMSM/DDF: don't recognised these metadata on partitions.

These metadata are not expected on partitions, and they have
no way of differentiation whether which is correct if they
are found both on the device and on the last partition.

So if the device is a partition, refuse to read the metadata.

Signed-off-by: NeilBrown <neilb at suse.de>


---

 mdadm.h       |    1 +
 super-ddf.c   |    4 ++++
 super-intel.c |    4 ++++
 util.c        |   25 +++++++++++++++++++++++++
 4 files changed, 34 insertions(+), 0 deletions(-)

diff --git a/mdadm.h b/mdadm.h
index 1bf5ac0..d9d17b0 100644
--- a/mdadm.h
+++ b/mdadm.h
@@ -876,6 +876,7 @@ extern int enough(int level, int raid_disks, int layout, int clean,
 extern int ask(char *mesg);
 extern unsigned long long get_component_size(int fd);
 extern void remove_partitions(int fd);
+extern int test_partition(int fd);
 extern unsigned long long calc_array_size(int level, int raid_disks, int layout,
 				   int chunksize, unsigned long long devsize);
 extern int flush_metadata_updates(struct supertype *st);
diff --git a/super-ddf.c b/super-ddf.c
index 3feea57..0e6f1e5 100644
--- a/super-ddf.c
+++ b/super-ddf.c
@@ -783,6 +783,10 @@ static int load_super_ddf(struct supertype *st, int fd,
 	if (get_dev_size(fd, devname, &dsize) == 0)
 		return 1;
 
+	if (test_partition(fd))
+		/* DDF is not allowed on partitions */
+		return 1;
+
 	/* 32M is a lower bound */
 	if (dsize <= 32*1024*1024) {
 		if (devname)
diff --git a/super-intel.c b/super-intel.c
index 677396c..bdd7a96 100644
--- a/super-intel.c
+++ b/super-intel.c
@@ -2798,6 +2798,10 @@ static int load_super_imsm(struct supertype *st, int fd, char *devname)
 		return 0;
 #endif
 
+	if (test_partition(fd))
+		/* IMSM not allowed on partitions */
+		return 1;
+
 	free_super_imsm(st);
 
 	super = alloc_super();
diff --git a/util.c b/util.c
index 79d2b0f..25f1e56 100644
--- a/util.c
+++ b/util.c
@@ -302,6 +302,31 @@ void remove_partitions(int fd)
 #endif
 }
 
+int test_partition(int fd)
+{
+	/* Check if fd is a whole-disk or a partition.
+	 * BLKPG will return EINVAL on a partition, and BLKPG_DEL_PARTITION
+	 * will return ENXIO on an invalid partition number.
+	 */
+	struct blkpg_ioctl_arg a;
+	struct blkpg_partition p;
+	a.op = BLKPG_DEL_PARTITION;
+	a.data = (void*)&p;
+	a.datalen = sizeof(p);
+	a.flags = 0;
+	memset(a.data, 0, a.datalen);
+	p.pno = 1<<30;
+	if (ioctl(fd, BLKPG, &a) == 0)
+		/* Very unlikely, but not a partition */
+		return 0;
+	if (errno == ENXIO)
+		/* not a partition */
+		return 0;
+
+	return 1;
+}
+
+
 int enough(int level, int raid_disks, int layout, int clean,
 	   char *avail, int avail_disks)
 {




More information about the pkg-mdadm-commits mailing list