[PATCH 3 of 5] merge: include obsolete calculation for branchtips

Sean Farley sean.michael.farley at gmail.com
Wed Nov 27 15:59:28 CST 2013


# HG changeset patch
# User Sean Farley <sean.michael.farley at gmail.com>
# Date 1383779296 21600
#      Wed Nov 06 17:08:16 2013 -0600
# Node ID 0043392ae4bbb546a9c0a14ca35d76c0f299e2f1
# Parent  38f0fd90e66237b2b3395605e3ef23516ecebae7
merge: include obsolete calculation for branchtips

This logic was initially done by Pierre-Yves David in a59e575c6ff8 but
branchtips, which are calculated at the beginning of the function, were not
included. This patch moves that logic forward and preserves the no-op update
clause added by Siddharth Agarwal in ab2362e1672e.

Tests will be updated in the next patch because it requires a non-obvious fix
to the test case.

diff --git a/mercurial/merge.py b/mercurial/merge.py
--- a/mercurial/merge.py
+++ b/mercurial/merge.py
@@ -695,10 +695,26 @@
             except error.RepoLookupError:
                 if wc.branch() == "default": # no default branch!
                     node = repo.lookup("tip") # update to tip
                 else:
                     raise util.Abort(_("branch %s not found") % wc.branch())
+
+            # We only check for foreground (successor) changesets if the node
+            # found by the above logic is obsolete
+            if repo[node].obsolete():
+                # Branching is a bit strange to ensure we do the minimal
+                # amount of call to obsolete.background.
+                foreground = obsolete.foreground(repo, [p1.node()])
+                # note: the <node> variable contains a random identifier
+
+                # allow updating to successors
+                if repo[node].node() in foreground:
+                    # get the max revision for the given foreground set
+                    unfil = [repo.unfiltered()[n].rev() for n in foreground]
+                    node = repo[max(unfil)].node()
+                    pa = p1
+
         overwrite = force and not branchmerge
 
         p2 = repo[node]
         if pa is None:
             pa = p1.ancestor(p2)
@@ -724,23 +740,23 @@
                 if wc.sub(s).dirty():
                     raise util.Abort(_("uncommitted changes in "
                                        "subrepository '%s'") % s)
 
         elif not overwrite:
-            if p1 == p2: # no-op update
+            # no-op update
+            if (p1 == p2 and
+                not (foreground and foreground != set([p1.node()]))):
                 # call the hooks and exit early
                 repo.hook('preupdate', throw=True, parent1=xp2, parent2='')
                 repo.hook('update', parent1=xp2, parent2='', error=0)
                 return 0, 0, 0, 0
 
             if pa not in (p1, p2):  # nonlinear
                 dirty = wc.dirty(missing=True)
                 if dirty or onode is None:
-                    # Branching is a bit strange to ensure we do the minimal
-                    # amount of call to obsolete.background.
-                    foreground = obsolete.foreground(repo, [p1.node()])
-                    # note: the <node> variable contains a random identifier
+                    if foreground is None:
+                        foreground = obsolete.foreground(repo, [p1.node()])
                     if repo[node].node() in foreground:
                         pa = p1  # allow updating to successors
                     elif dirty:
                         msg = _("uncommitted changes")
                         if onode is None:


More information about the Mercurial-devel mailing list