Mandriva Linux Archives: cooker@mandrivalinux.org

Mandriva Linux: cooker@mandrivalinux.org


[Date Prev] [Date Next] [Thread Prev] [Thread Next] [Date Index] [Thread Index]

  • From: Andreas Hasenack
  • Subject: [Cooker] [PATCH REVIEW] mkinitrd, lvm, UUID
  • Date: 4 Jan 2008 17:50:49 -0000

This is about https://bugzilla.mandriva.com/show_bug.cgi?id=36457

Summary:
a) lvm tools don't work on UUID=... style devices
  -> "lvdisplay UUID=c52cc68a-fcff-4a11-b034-31023bf5025c" won't work

b) lvm tools don't work with devices outside /dev/mapper/* or
  /dev/<volumegroupname>/*
  -> "lvdisplay /dev/dm-5" won't work, even if /dev/dm-5 is a literal
      copy of /dev/mapper/vg0-root for example

c) nash's mount command, used in the initrd, doesn't do mount by UUIDs
  -> "mount -t ext3 -o ro UUID=c52cc68a-fcff-4a11-b034-31023bf5025c /sysroot" won't work

d) mkinitrd was doing stat(1) on some UUID=... "devices" instead of the
   real device. stat(1) doesn't support UUID.


[b] is working as intended, according to the #lvm IRC channel:
<agk_>   dmsetup uses the device-mapper namespace to refer to devices
<agk_>   it does not use /dev
<ahasenack>      ok, that's why "dmsetup info vg0-root" works
<ahasenack>      but not /dev/vg0/root, at most only /dev/mapper/vg0-root
<agk_>   if someone sent me a patch to enhance dmsetup to accept /dev names, I'd accept it
<agk_>   but noboduy has yet
<agk_>   it would involve looking up the major/minor of the supplied /dev/dm-5 inode
<ahasenack>      and searching for a match in the device-mapper namespace
<agk_>   then changing the command into 'dmsetup -j <major> -m <minor> ...'
<ahasenack>      is this namespace the same issue why lvdisplay doesn't work on /dev/dm-5?
<agk_>   lvdisplay uses a different namespace agin
<agk_>     vg/lv
<agk_>   "/dev" is an optional prefix that lvm2 simply deletes
<agk_>   so lvdisplay /dev/vg/lv  becomes lvdisplay vg/lv  which is processed
<agk_>   - the arg is not treated as a file
<ahasenack>      and since dm-5 is not a logical volume name, it fails
<agk_>   we added special processing so /dev/mapper/* would work


Bottom line: if you use LVM on / and mount by UUID (new with 2008.1),
your system won't boot.


Attached are patches to try to workaround this:

- nash-mount-by-uuid.patch: adds mount-by-uuid to nash's builtin mount
  command (fixing [c])
- mkinitrd-4.2.17-uuid_lvm.patch: deals with [a], [b] and [d]

The good: my system boots again, and a plain installation (without lvm)
works too.
The bad: didn't test RAID on / yet, nor LVM1 (and I won't test LVM1).
The ugly: feels sort of hackish, we should find a way to deal with all these
"dm"s in one good way. Who knows what other surprises are there.
--- mkinitrd-4.2.17/mkinitrd.uuid_lvm	2008-01-04 12:16:55.000000000 -0500
+++ mkinitrd-4.2.17/mkinitrd	2008-01-04 12:18:34.000000000 -0500
@@ -717,10 +717,14 @@
 
 # check if the root fs is on a logical volume or md device
 root_major=$((0x$(stat -L -c '%t' $rootdev)))
+root_minor=$((0x$(stat -L -c '%T' $rootdev)))
 [ -f /sbin/lvm1-vgdisplay ] && lvmprefix="lvm1-"
 dm_major=`awk '$2 == "device-mapper" {print $1}' /proc/devices`
 if [ "$root_major" = "$dm_major" ]; then
-    if [ -x /sbin/lvm2 ] && /sbin/lvm2 lvdisplay $fstabrootdev > /dev/null 2>&1; then
+    [ -x /sbin/lvs ] && \
+        lv=`/sbin/lvs --noheadings -o vg_name,lv_name,lv_kernel_major,lv_kernel_minor \
+        --separator : | grep "$root_major:$root_minor"`
+    if [ -n "$lv" ]; then
     # trick to support making initrd for kernel that has a different version of lvm
     # unless forced by --lvmver
 	case x$lvmver in
@@ -744,10 +748,12 @@
 	esac
 	# root is on an LVM2 LV
 	root_lvm=1
-	rootvg=`/sbin/lvm2 lvdisplay $fstabrootdev | /bin/awk '/VG Name/ { print $NF }'`
+        rootvg=`echo $lv | cut -d : -f 1`
+        # now we can use lvm tools with this rootdev
+        rootdev=/dev/mapper/$rootvg-`echo $lv | cut -d : -f 2`
 	pvs=$(/sbin/lvm2 vgdisplay -v ${rootvg} | /bin/awk '/PV Name/ { print $NF }')
     else
-	dmraidev ${fstabrootdev}
+	dmraidev ${rootdev}
     fi
     if [ -z "$pvs" -a -x /sbin/evms_query  ]; then
 	if /sbin/evms_query info ${fstabrootdev} > /dev/null 2>&1; then
@@ -812,6 +818,8 @@
             need_dmnod=1
 	fi
     fi
+# XXX - lvm1, dont know how to handle it with UUIDs, so lets
+# just use the device name and hope for the best
 elif [ $root_major = 58 ]; then
     case x$lvmver in
 	x1) findmodule -lvm-mod;;
@@ -834,7 +842,7 @@
     esac
     # root is on an LVM LV
     root_lvm=1
-    rootvg=`/sbin/${lvmprefix}lvdisplay $fstabrootdev | /bin/awk '/VG Name/ { print $NF }'`
+    rootvg=`/sbin/${lvmprefix}lvdisplay $rootdev | /bin/awk '/VG Name/ { print $NF }'`
     pvs=$(/sbin/${lvmprefix}vgdisplay -v ${rootvg} | /bin/awk '/PV Name/ { print $(NF-1) }')
 fi
 
Index: nash/nash.c
===================================================================
--- nash/nash.c
+++ nash/nash.c	2008-01-04 08:50:52.000000000 -0500
@@ -286,6 +286,19 @@
 	return device;
 }
 
+static char *getpathbyuuid(const char *uuid)
+{
+	char *device;
+	int major, minor;
+
+	if ((device = get_spec_by_uuid(uuid, &major, &minor)) == NULL)
+		return NULL;
+	if (smartmknod(device, S_IFBLK | 0600, makedev(major, minor)) < 0)
+		return NULL;
+
+	return device;
+}
+
 static char *getpathbyrdev(const char *rdevstr)
 {
 	FILE *fp;
@@ -336,6 +349,8 @@
 
 	if (strncmp(spec, "LABEL=", 6) == 0)
 		path = getpathbylabel(spec + 6);
+	else if (strncmp(spec, "UUID=", 5) == 0)
+		path = getpathbyuuid(spec + 5);
 	else if (isxdigit(spec[0]))
 		path = getpathbyrdev(spec);
 	else
@@ -476,13 +491,16 @@
     if (rdonly)
 	flags |= MS_RDONLY;
 
-    if (!strncmp("LABEL=", device, 6)) {
+    if ((!strncmp("LABEL=", device, 6)) || (!strncmp("UUID=", device, 5))) {
 	int major, minor;
 	char * devName;
 	char * ptr;
 	int i;
 
-	devName = get_spec_by_volume_label(device + 6, &major, &minor);
+	if (!strncmp("LABEL=", device, 6))
+		devName = get_spec_by_volume_label(device + 6, &major, &minor);
+	else
+		devName = get_spec_by_uuid(device + 5, &major, &minor);
 
 	if (devName) {
 	    device = devName;

Attachment: pgp00019.pgp
Description: PGP signature



Date Index | Thread Index

Search the archive:



To (un)subscribe from/to the lists:

Sympa mailing lists server.





Fund the Mandriva Linux project

Looking for a job?