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

[PATCH] Encode our upgrade policy in productMatches/versionMatches and enforce it.



For Fedora, this means we will not allow upgrades of detected root filesystems
more than two releases old, or "upgrading" a newer install with an older one.
For RHEL, we don't yet know what to do so just allow things to continue as they
always have.  Using "upgradeany" still circumvents this check.
---
 installclass.py          |    9 +++++
 installclasses/fedora.py |   30 ++++++++++++++++++
 installclasses/rhel.py   |   37 ++++++++++++++++++++++
 partedUtils.py           |   75 +++++++++++++---------------------------------
 upgrade.py               |    6 +--
 5 files changed, 99 insertions(+), 58 deletions(-)

diff --git a/installclass.py b/installclass.py
index c36e9e9..a3a97ae 100644
--- a/installclass.py
+++ b/installclass.py
@@ -213,6 +213,15 @@ class BaseInstallClass(object):
 	anaconda.id.reset()
 	anaconda.id.instClass = self
 
+    def versionMatches(self, oldver):
+        pass
+
+    def productMatches(self, oldprod):
+        pass
+
+    def productUpgradable(self, oldprod, oldver):
+        return self.productMatches(oldprod) and self.versionMatches(oldver)
+
     def __init__(self):
 	pass
 
diff --git a/installclasses/fedora.py b/installclasses/fedora.py
index 3e529c5..7c22697 100644
--- a/installclasses/fedora.py
+++ b/installclasses/fedora.py
@@ -19,6 +19,7 @@
 
 from installclass import BaseInstallClass
 from constants import *
+from product import *
 from filer import *
 from flags import flags
 import os, types
@@ -76,5 +77,34 @@ class InstallClass(BaseInstallClass):
         else:
             return yuminstall.YumBackend
 
+    def productMatches(self, oldprod):
+        if oldprod.startswith(productName):
+            return True
+
+        productUpgrades = {
+                "Fedora Core": ("Red Hat Linux", ),
+                "Fedora": ("Fedora Core", )
+        }
+
+        if productUpgrades.has_key(productName):
+            acceptable = productUpgrades[productName]
+        else:
+            acceptable = ()
+
+        for p in acceptable:
+            if oldprod.startswith(p):
+                return True
+
+        return False
+
+    def versionMatches(self, oldver):
+        try:
+            oldVer = float(oldver)
+            newVer = float(productVersion)
+        except ValueError:
+            return True
+
+        return newVer > oldVer and newVer - oldVer <= 2
+
     def __init__(self):
 	BaseInstallClass.__init__(self)
diff --git a/installclasses/rhel.py b/installclasses/rhel.py
index 668e9cb..ddfb897 100644
--- a/installclasses/rhel.py
+++ b/installclasses/rhel.py
@@ -19,6 +19,7 @@
 
 from installclass import BaseInstallClass
 from constants import *
+from product import *
 from filer import *
 from flags import flags
 import os
@@ -177,6 +178,42 @@ class InstallClass(BaseInstallClass):
     def getBackend(self):
         return yuminstall.YumBackend
 
+    def productMatches(self, oldprod):
+        if oldprod.startswith(productName):
+            return True
+
+        productUpgrades = {
+            "Red Hat Enterprise Linux AS": ("Red Hat Linux Advanced Server", ),
+            "Red Hat Enterprise Linux WS": ("Red Hat Linux Advanced Workstation",),
+            # FIXME: this probably shouldn't be in a release...
+            "Red Hat Enterprise Linux": ("Red Hat Linux Advanced Server",
+                                         "Red Hat Linux Advanced Workstation",
+                                         "Red Hat Enterprise Linux AS",
+                                         "Red Hat Enterprise Linux ES",
+                                         "Red Hat Enterprise Linux WS"),
+            "Red Hat Enterprise Linux Server": ("Red Hat Enterprise Linux AS",
+                                                "Red Hat Enterprise Linux ES",
+                                                "Red Hat Enterprise Linux WS",
+                                                "Red Hat Enterprise Linux"),
+            "Red Hat Enterprise Linux Client": ("Red Hat Enterprise Linux WS",
+                                                "Red Hat Enterprise Linux Desktop",
+                                                "Red Hat Enterprise Linux"),
+        }
+
+        if productUpgrades.has_key(productName):
+            acceptable = productUpgrades[productName]
+        else:
+            acceptable = ()
+
+        for p in acceptable:
+            if oldprod.startswith(p):
+                return True
+
+        return False
+
+    def versionMatches(self, oldver):
+        return True
+
     def __init__(self):
 	BaseInstallClass.__init__(self)
 
diff --git a/partedUtils.py b/partedUtils.py
index 7d40805..80ada25 100644
--- a/partedUtils.py
+++ b/partedUtils.py
@@ -311,6 +311,9 @@ def isLinuxNative(part):
         return False
 
 def getReleaseString(mountpoint):
+    relName = None
+    relVer = None
+
     if os.access(mountpoint + "/etc/redhat-release", os.R_OK):
         f = open(mountpoint + "/etc/redhat-release", "r")
         try:
@@ -320,11 +323,14 @@ def getReleaseString(mountpoint):
                 f.close()
             except:
                 pass
-            return ""
+            return (relName, relVer)
+
         f.close()
+
         # return the first line with the newline at the end stripped
         if len(lines) == 0:
-            return ""
+            return (relName, relVer)
+
         relstr = string.strip(lines[0][:-1])
 
         # get the release name and version
@@ -333,56 +339,20 @@ def getReleaseString(mountpoint):
         if relstr.find("release") != -1:
             try:
                 idx = relstr.find("release")
-                prod = relstr[:idx - 1]
+                relName = relstr[:idx - 1]
+                relVer = ""
 
-                ver = ""
                 for a in relstr[idx + 8:]:
                     if a in string.digits + ".":
-                        ver = ver + a
+                        relVer += a
                     else:
                         break
 
                     relstr = prod + " " + ver
             except:
                 pass # don't worry, just use the relstr as we have it
-        return relstr
-    return ""
-
-def productMatches(oldproduct, newproduct):
-    """Determine if this is a reasonable product to upgrade old product"""
-    if oldproduct.startswith(newproduct):
-        return 1
-
-    productUpgrades = {
-        "Red Hat Enterprise Linux AS": ("Red Hat Linux Advanced Server", ),
-        "Red Hat Enterprise Linux WS": ("Red Hat Linux Advanced Workstation",),
-        # FIXME: this probably shouldn't be in a release...
-        "Red Hat Enterprise Linux": ("Red Hat Linux Advanced Server",
-                                     "Red Hat Linux Advanced Workstation",
-                                     "Red Hat Enterprise Linux AS",
-                                     "Red Hat Enterprise Linux ES",
-                                     "Red Hat Enterprise Linux WS"),
-        "Red Hat Enterprise Linux Server": ("Red Hat Enterprise Linux AS",
-                                            "Red Hat Enterprise Linux ES",
-                                            "Red Hat Enterprise Linux WS",
-                                            "Red Hat Enterprise Linux"),
-        "Red Hat Enterprise Linux Client": ("Red Hat Enterprise Linux WS",
-                                            "Red Hat Enterprise Linux Desktop",
-                                            "Red Hat Enterprise Linux"),
-        "Fedora Core": ("Red Hat Linux",),
-        "Fedora": ("Fedora Core",)
-        }
-
-    if productUpgrades.has_key(newproduct):
-        acceptable = productUpgrades[newproduct]
-    else:
-        acceptable = ()
-
-    for p in acceptable:
-        if oldproduct.startswith(p):
-            return 1
 
-    return 0
+    return (relName, relVer)
 
 class DiskSet:
     """The disks in the system."""
@@ -619,10 +589,9 @@ class DiskSet:
 
             if found:
                 if os.access (self.anaconda.rootPath + '/etc/fstab', os.R_OK):
-                    relstr = getReleaseString(self.anaconda.rootPath)
+                    (prod, ver) = getReleaseString(self.anaconda.rootPath)
 
-                    if ((upgradeany == 1) or
-                        (productMatches(relstr, productName))):
+                    if upgradeany == 1 or self.anaconda.id.instClass.productUpgradable(prod, ver):
                         try:
                             label = isys.readFSLabel(theDev)
                         except:
@@ -630,7 +599,7 @@ class DiskSet:
 
                         uuid = isys.readFSUuid(theDev)
                         # XXX we could add the "raw" dev and let caller decrypt
-                        rootparts.append ((theDev, fs, relstr, label, uuid))
+                        rootparts.append ((theDev, fs, prod+" "+ver, label, uuid))
                 isys.umount(self.anaconda.rootPath)
 
         # now, look for candidate lvm roots
@@ -666,17 +635,16 @@ class DiskSet:
 
             if found:
                 if os.access (self.anaconda.rootPath + '/etc/fstab', os.R_OK):
-                    relstr = getReleaseString(self.anaconda.rootPath)
+                    (prod, ver) = getReleaseString(self.anaconda.rootPath)
 
-                    if ((upgradeany == 1) or
-                        (productMatches(relstr, productName))):
+                    if upgradeany == 1 or self.anaconda.id.instClass.productUpgradable(prod, ver):
                         try:
                             label = isys.readFSLabel(theDev)
                         except:
                             label = None
 
                         uuid = isys.readFSUuid(theDev)
-                        rootparts.append ((theDev, fs, relstr, label, uuid))
+                        rootparts.append ((theDev, fs, prod+" "+ver, label, uuid))
                 isys.umount(self.anaconda.rootPath)
 
         lvm.vgdeactivate()
@@ -726,10 +694,9 @@ class DiskSet:
                         continue
 
                     if os.access (checkRoot + '/etc/fstab', os.R_OK):
-                        relstr = getReleaseString(checkRoot)
+                        (prod, ver) = getReleaseString(checkRoot)
 
-                        if ((upgradeany == 1) or
-                            (productMatches(relstr, productName))):
+                        if upgradeany == 1 or self.anaconda.id.instClass.productUpgradable(prod, ver):
                             try:
                                 label = isys.readFSLabel("/dev/%s" % theDev)
                             except:
@@ -737,7 +704,7 @@ class DiskSet:
 
                             uuid = isys.readFSUuid("/dev/%s" % (theDev,))
                             rootparts.append (("/dev/%s" % (theDev,),
-                                              fstype, relstr, label, uuid))
+                                              fstype, prod+" "+ver, label, uuid))
 
                     isys.umount(self.anaconda.rootPath)
 
diff --git a/upgrade.py b/upgrade.py
index 1c4685d..a554d3b 100644
--- a/upgrade.py
+++ b/upgrade.py
@@ -153,10 +153,8 @@ def findExistingRoots(anaconda, upgradeany = 0):
     anaconda.id.iscsi.startup(anaconda.intf)
 
     if not flags.setupFilesystems:
-        relstr = partedUtils.getReleaseString (anaconda.rootPath)
-        if ((flags.cmdline.has_key("upgradeany")) or
-            (upgradeany == 1) or
-            (partedUtils.productMatches(relstr, productName))):
+        (prod, ver) = partedUtils.getReleaseString (anaconda.rootPath)
+        if flags.cmdline.has_key("upgradeany") or upgradeany == 1 or anaconda.id.instClass.productUpgradable(prod, ver):
             return [(anaconda.rootPath, 'ext2', "")]
         return []
 
-- 
1.6.0.3


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