summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorMark Hatle <mark.hatle@windriver.com>2015-01-22 16:10:34 -0600
committerDan McGregor <dan.mcgregor@usask.ca>2015-02-05 08:51:16 -0600
commitc2258bfabd6057ce58275e72188dad5e1372d6cc (patch)
treed10103916f938aec2fe7e7952678743c507f6bc1
parentf512c196cc80ae46b29c7956d9a97a4fe055141e (diff)
downloadopenembedded-core-contrib-c2258bfabd6057ce58275e72188dad5e1372d6cc.tar.gz
openembedded-core-contrib-c2258bfabd6057ce58275e72188dad5e1372d6cc.tar.bz2
openembedded-core-contrib-c2258bfabd6057ce58275e72188dad5e1372d6cc.zip
python-smartpm: Fix attemptonly builds when file conflicts occur
[YOCTO #7299] When file conflicts occur, the RPM transaction aborts. Instead of simply accepting the failure, we now identify, capture, and remove the offending package(s) from the transaction and retry. Signed-off-by: Mark Hatle <mark.hatle@windriver.com> Signed-off-by: Ross Burton <ross.burton@intel.com>
-rw-r--r--meta/recipes-devtools/python/python-smartpm/smart-attempt.patch97
1 files changed, 66 insertions, 31 deletions
diff --git a/meta/recipes-devtools/python/python-smartpm/smart-attempt.patch b/meta/recipes-devtools/python/python-smartpm/smart-attempt.patch
index 45f794787c..82d2e6cf31 100644
--- a/meta/recipes-devtools/python/python-smartpm/smart-attempt.patch
+++ b/meta/recipes-devtools/python/python-smartpm/smart-attempt.patch
@@ -9,40 +9,24 @@ failures (usually conflicts).
This option only works for the install operation.
+If a complementary install fails, an actual error occurred, one that
+we can't ignore without losing the entire attempted transaction. Keep
+this as an error so that we can catch these cases in the futre.
+
Upstream-Status: Pending
Signed-off-by: Mark Hatle <mark.hatle@windriver.com>
Signed-off-by: Paul Eggleton <paul.eggleton@linux.intel.com>
-
-For complementary and 'attemptonly' package processing, we should
-make sure the warn rather than error reported.
-Signed-off-by: Hongxu Jia <hongxu.jia@windriver.com>
---
smart.py | 5 +++-
smart/commands/install.py | 5 ++++
smart/transaction.py | 65 +++++++++++++++++++++++++++++++++++------------
3 files changed, 58 insertions(+), 17 deletions(-)
-diff --git a/smart.py b/smart.py
-index c5c7a02..7e7fd34 100755
---- a/smart.py
-+++ b/smart.py
-@@ -179,7 +179,10 @@ def main(argv):
- if opts and opts.log_level == "debug":
- import traceback
- traceback.print_exc()
-- if iface.object:
-+ if iface.object and sysconf.has("attempt-install", soft=True):
-+ iface.warning(unicode(e))
-+ exitcode = 0
-+ elif iface.object:
- iface.error(unicode(e))
- else:
- sys.stderr.write(_("error: %s\n") % e)
-diff --git a/smart/commands/install.py b/smart/commands/install.py
-index 590222c..6ef9682 100644
---- a/smart/commands/install.py
-+++ b/smart/commands/install.py
+Index: smart-1.4.1/smart/commands/install.py
+===================================================================
+--- smart-1.4.1.orig/smart/commands/install.py
++++ smart-1.4.1/smart/commands/install.py
@@ -50,6 +50,8 @@ def option_parser():
parser = OptionParser(usage=USAGE,
description=DESCRIPTION,
@@ -62,10 +46,10 @@ index 590222c..6ef9682 100644
if opts.explain:
sysconf.set("explain-changesets", True, soft=True)
-diff --git a/smart/transaction.py b/smart/transaction.py
-index 5730a42..e3e61c6 100644
---- a/smart/transaction.py
-+++ b/smart/transaction.py
+Index: smart-1.4.1/smart/transaction.py
+===================================================================
+--- smart-1.4.1.orig/smart/transaction.py
++++ smart-1.4.1/smart/transaction.py
@@ -555,6 +555,8 @@ class Transaction(object):
changeset.set(pkg, INSTALL)
isinst = changeset.installed
@@ -183,6 +167,57 @@ index 5730a42..e3e61c6 100644
elif op is REMOVE:
self._remove(pkg, changeset, locked, pending)
elif op is UPGRADE:
---
-1.9.1
-
+Index: smart-1.4.1/smart/backends/rpm/pm.py
+===================================================================
+--- smart-1.4.1.orig/smart/backends/rpm/pm.py
++++ smart-1.4.1/smart/backends/rpm/pm.py
+@@ -243,15 +253,48 @@ class RPMPackageManager(PackageManager):
+ cb = RPMCallback(prog, upgradednames)
+ cb.grabOutput(True)
+ probs = None
++ retry = 0
+ try:
+ probs = ts.run(cb, None)
+ finally:
+ del getTS.ts
+ cb.grabOutput(False)
++ if probs and sysconf.has("attempt-install", soft=True):
++ def remove_conflict(pkgNEVR):
++ for key in changeset.keys():
++ if pkgNEVR == str(key):
++ del changeset[key]
++ del pkgpaths[key]
++ iface.warning("Removing %s due to file %s conflicting with %s" % (pkgNEVR, fname, altNEVR))
++ break
++
++ retry = 1
++ for prob in probs:
++ if prob[1][0] == rpm.RPMPROB_NEW_FILE_CONFLICT:
++ msg = prob[0].split()
++ fname = msg[1]
++ pkgNEVR = msg[7]
++ altNEVR = msg[9]
++ pkgNEVR = pkgNEVR.rsplit('.', 1)[0] + '@' + pkgNEVR.rsplit('.', 1)[1]
++ altNEVR = altNEVR.rsplit('.', 1)[0] + '@' + altNEVR.rsplit('.', 1)[1]
++ remove_conflict(pkgNEVR)
++ elif prob[1][0] == rpm.RPMPROB_FILE_CONFLICT:
++ msg = prob[0].split()
++ fname = msg[1]
++ pkgNEVR = msg[5]
++ altNEVR = msg[11]
++ pkgNEVR = pkgNEVR.rsplit('.', 1)[0] + '@' + pkgNEVR.rsplit('.', 1)[1]
++ altNEVR = altNEVR.rsplit('.', 1)[0] + '@' + altNEVR.rsplit('.', 1)[1]
++ remove_conflict(pkgNEVR)
++ else:
++ retry = 0
++
+ prog.setDone()
+- if probs:
++ if probs and (not retry):
+ raise Error, "\n".join([x[0] for x in probs])
+ prog.stop()
++ if retry and len(changeset):
++ self.commit(changeset, pkgpaths)
+
+ class RPMCallback:
+ def __init__(self, prog, upgradednames):