# HG changeset patch # User Thomas Arendsen Hein # Date 2006-02-18 05:50:22 # Node ID 813f9f5fe837edbf50025e4579eaed25217ddcab # Parent 1e5bb6c929cd6ec919a42b32c816b752e670a8d3 # Parent 57de7e1a81d266d294429b3c7507ac34d9ab382f Merge with upstream diff --git a/mercurial/commands.py b/mercurial/commands.py --- a/mercurial/commands.py +++ b/mercurial/commands.py @@ -2580,17 +2580,20 @@ norepo = ("clone init version help debug def find(cmd): """Return (aliases, command table entry) for command string.""" choice = None + count = 0 for e in table.keys(): aliases = e.lstrip("^").split("|") if cmd in aliases: return aliases, table[e] for a in aliases: if a.startswith(cmd): - if choice: - raise AmbiguousCommand(cmd) - else: - choice = aliases, table[e] - break + count += 1 + choice = aliases, table[e] + break + + if count > 1: + raise AmbiguousCommand(cmd) + if choice: return choice diff --git a/mercurial/localrepo.py b/mercurial/localrepo.py --- a/mercurial/localrepo.py +++ b/mercurial/localrepo.py @@ -274,6 +274,25 @@ class localrepository(object): self.dirstate.read() return wlock + def checkfilemerge(self, filename, text, filelog, manifest1, manifest2): + "determine whether a new filenode is needed" + fp1 = manifest1.get(filename, nullid) + fp2 = manifest2.get(filename, nullid) + + if fp2 != nullid: + # is one parent an ancestor of the other? + fpa = filelog.ancestor(fp1, fp2) + if fpa == fp1: + fp1, fp2 = fp2, nullid + elif fpa == fp2: + fp2 = nullid + + # is the file unmodified from the parent? report existing entry + if fp2 == nullid and text == filelog.read(fp1): + return (fp1, None, None) + + return (None, fp1, fp2) + def rawcommit(self, files, text, user, date, p1=None, p2=None, wlock=None): orig_parent = self.dirstate.parents()[0] or nullid p1 = p1 or self.dirstate.parents()[0] or nullid @@ -304,27 +323,10 @@ class localrepository(object): r = self.file(f) mfm[f] = tm - fp1 = m1.get(f, nullid) - fp2 = m2.get(f, nullid) - - # is the same revision on two branches of a merge? - if fp2 == fp1: - fp2 = nullid - - if fp2 != nullid: - # is one parent an ancestor of the other? - fpa = r.ancestor(fp1, fp2) - if fpa == fp1: - fp1, fp2 = fp2, nullid - elif fpa == fp2: - fp2 = nullid - - # is the file unmodified from the parent? - if t == r.read(fp1): - # record the proper existing parent in manifest - # no need to add a revision - mm[f] = fp1 - continue + (entry, fp1, fp2) = self.checkfilemerge(f, t, r, m1, m2) + if entry: + mm[f] = entry + continue mm[f] = r.add(t, {}, tr, linkrev, fp1, fp2) changed.append(f) @@ -412,22 +414,9 @@ class localrepository(object): self.ui.debug(_(" %s: copy %s:%s\n") % (f, cp, meta["copyrev"])) fp1, fp2 = nullid, nullid else: - fp1 = m1.get(f, nullid) - fp2 = m2.get(f, nullid) - - if fp2 != nullid: - # is one parent an ancestor of the other? - fpa = r.ancestor(fp1, fp2) - if fpa == fp1: - fp1, fp2 = fp2, nullid - elif fpa == fp2: - fp2 = nullid - - # is the file unmodified from the parent? - if not meta and t == r.read(fp1) and fp2 == nullid: - # record the proper existing parent in manifest - # no need to add a revision - new[f] = fp1 + entry, fp1, fp2 = self.checkfilemerge(f, t, r, m1, m2) + if entry: + new[f] = entry continue new[f] = r.add(t, meta, tr, linkrev, fp1, fp2) diff --git a/tests/test-excessive-merge b/tests/test-excessive-merge new file mode 100755 --- /dev/null +++ b/tests/test-excessive-merge @@ -0,0 +1,46 @@ +#!/bin/sh + +hg init + +echo foo > a +echo foo > b +hg add a b + +hg ci -m "test" -d "0 0" + +echo blah > a + +hg ci -m "branch a" -d "0 0" + +hg co 0 + +echo blah > b + +hg ci -m "branch b" -d "0 0" +HGMERGE=true hg up -m 1 + +hg ci -m "merge b/a -> blah" -d "0 0" + +hg co 1 +HGMERGE=true hg up -m 2 +hg ci -m "merge a/b -> blah" -d "0 0" + +hg log +hg debugindex .hg/00changelog.i + +echo + +echo 1 +hg manifest 1 +echo 2 +hg manifest 2 +echo 3 +hg manifest 3 +echo 4 +hg manifest 4 + +echo + +hg debugindex .hg/data/a.i + +hg verify \ No newline at end of file diff --git a/tests/test-excessive-merge.out b/tests/test-excessive-merge.out new file mode 100644 --- /dev/null +++ b/tests/test-excessive-merge.out @@ -0,0 +1,59 @@ +changeset: 4:2ee31f665a86 +tag: tip +parent: 1:96155394af80 +parent: 2:92cc4c306b19 +user: test +date: Thu Jan 1 00:00:00 1970 +0000 +summary: merge a/b -> blah + +changeset: 3:e16a66a37edd +parent: 2:92cc4c306b19 +parent: 1:96155394af80 +user: test +date: Thu Jan 1 00:00:00 1970 +0000 +summary: merge b/a -> blah + +changeset: 2:92cc4c306b19 +parent: 0:5e0375449e74 +user: test +date: Thu Jan 1 00:00:00 1970 +0000 +summary: branch b + +changeset: 1:96155394af80 +user: test +date: Thu Jan 1 00:00:00 1970 +0000 +summary: branch a + +changeset: 0:5e0375449e74 +user: test +date: Thu Jan 1 00:00:00 1970 +0000 +summary: test + + rev offset length base linkrev nodeid p1 p2 + 0 0 60 0 0 5e0375449e74 000000000000 000000000000 + 1 60 62 1 1 96155394af80 5e0375449e74 000000000000 + 2 122 62 2 2 92cc4c306b19 5e0375449e74 000000000000 + 3 184 69 3 3 e16a66a37edd 92cc4c306b19 96155394af80 + 4 253 29 3 4 2ee31f665a86 96155394af80 92cc4c306b19 + +1 +79d7492df40aa0fa093ec4209be78043c181f094 644 a +2ed2a3912a0b24502043eae84ee4b279c18b90dd 644 b +2 +2ed2a3912a0b24502043eae84ee4b279c18b90dd 644 a +79d7492df40aa0fa093ec4209be78043c181f094 644 b +3 +79d7492df40aa0fa093ec4209be78043c181f094 644 a +79d7492df40aa0fa093ec4209be78043c181f094 644 b +4 +79d7492df40aa0fa093ec4209be78043c181f094 644 a +79d7492df40aa0fa093ec4209be78043c181f094 644 b + + rev offset length base linkrev nodeid p1 p2 + 0 0 5 0 0 2ed2a3912a0b 000000000000 000000000000 + 1 5 6 1 1 79d7492df40a 2ed2a3912a0b 000000000000 +checking changesets +checking manifests +crosschecking files in changesets and manifests +checking files +2 files, 5 changesets, 4 total revisions diff --git a/tests/test-ro-message b/tests/test-ro-message --- a/tests/test-ro-message +++ b/tests/test-ro-message @@ -14,4 +14,4 @@ echo 'stationary' >>b/vehicle "$HG" commit -m 'Clarifying the vehicle.' "$HG" update -C 1 chmod a-w b/vehicle -"$HG" update -m 2 2>&1 | sed 's|^\(.*[ ]\)/tmp/[^/]*/\(.*\)$|\1\2|g' +"$HG" update -m 2 2>&1 | sed 's|^\(.*[ ]\).*/\([^/]*/[^/]*/[^/]*\)$|\1\2|g'