From 20bc377dcdb0fab8a37cb5ae9230c0ea38534063 Mon Sep 17 00:00:00 2001
From: David Lehman <dlehman@redhat.com>
Date: Fri, 2 Aug 2013 11:08:21 -0500
Subject: [PATCH 5/7] Use name of active md array when possible during
 populate. (#868182)

---
 storage/devicetree.py | 82 +++++++++++++++++++++++++++++++++++----------------
 1 file changed, 56 insertions(+), 26 deletions(-)

diff --git a/storage/devicetree.py b/storage/devicetree.py
index c4e925d..f59b366 100644
--- a/storage/devicetree.py
+++ b/storage/devicetree.py
@@ -1707,37 +1707,67 @@ class DeviceTree(object):
                 log.warning("invalid data for %s: %s" % (name, e))
                 return
 
-            # try to name the array based on the preferred minor
-            md_info = devicelibs.mdraid.mdexamine(device.path)
-            md_path = md_info.get("device", "")
-            md_metadata = md_info.get("metadata")
-            md_name = devicePathToName(md_info.get("device", ""))
-            if md_name:
+            # check the list of devices udev knows about to see if the array
+            # this device belongs to is already active
+            for dev in udev_get_block_devices():
+                if not udev_device_is_md(dev):
+                    continue
+
                 try:
-                    # md_name can be either md# or md/#
-                    if md_name.startswith("md/"):
-                        minor = int(md_name[3:])     # strip off leading "md/"
-                        md_name = "md%d" % minor     # use a regular md# name
-                    else:
-                        minor = int(md_name[2:])     # strip off leading "md"
-                except (IndexError, ValueError):
-                    minor = None
-                    md_name = None
-                else:
-                    array = self.getDeviceByName(md_name)
-                    if array and array.uuid != md_uuid:
-                        md_name = None
+                    dev_uuid = udev_device_get_md_uuid(dev)
+                    dev_level = udev_device_get_md_level(dev)
+                except KeyError:
+                    continue
+
+                if dev_uuid is None or dev_level is None:
+                    continue
+
+                if dev_uuid == md_uuid and dev_level == md_level:
+                    md_name = udev_device_get_md_name(dev)
+                    md_metadata = dev.get("MD_METADATA")
+                    if not md_name:
+                        # containers don't typically have names and they also
+                        # don't have a symlink in /dev/md
+                        md_name = udev_device_get_name(dev)
+                        if md_level != "container" and \
+                           re.match(r'md\d+$', md_name):
+                            # md0 -> 0
+                            md_name = md_name[2:]
+
+                    break
 
             if not md_name:
-                # if we don't have a name yet, find the first unused minor
-                minor = 0
-                while True:
-                    if self.getDeviceByName("md%d" % minor):
-                        minor += 1
+                # try to name the array based on the preferred minor
+                md_info = devicelibs.mdraid.mdexamine(device.path)
+                md_path = md_info.get("device", "")
+                md_metadata = md_info.get("metadata")
+                md_name = devicePathToName(md_info.get("device", ""))
+                if md_name:
+                    try:
+                        # md_name can be either md# or md/#
+                        if md_name.startswith("md/"):
+                            minor = int(md_name[3:])# strip off leading "md/"
+                            md_name = "md%d" % minor# use a regular md# name
+                        else:
+                            minor = int(md_name[2:])# strip off leading "md"
+                    except (IndexError, ValueError):
+                        minor = None
+                        md_name = None
                     else:
-                        break
+                        array = self.getDeviceByName(md_name)
+                        if array and array.uuid != md_uuid:
+                            md_name = None
+
+                if not md_name:
+                    # if we don't have a name yet, find the first unused minor
+                    minor = 0
+                    while True:
+                        if self.getDeviceByName("md%d" % minor):
+                            minor += 1
+                        else:
+                            break
 
-                md_name = "md%d" % minor
+                    md_name = "md%d" % minor
 
             log.debug("using name %s for md array containing member %s"
                         % (md_name, device.name))
-- 
1.8.1.4

