merge with stable
authorMatt Mackall <mpm@selenic.com>
Thu, 17 Nov 2011 16:53:17 -0600
changeset 15513 646759147717
parent 15510 5414b56cfad6 (diff)
parent 15512 8b011ededfb2 (current diff)
child 15523 f9da84a950d0
merge with stable
mercurial/commands.py
mercurial/discovery.py
mercurial/dispatch.py
mercurial/mdiff.py
mercurial/subrepo.py
mercurial/util.py
tests/test-graft.t
tests/test-url.py
--- a/contrib/check-code.py	Wed Nov 16 08:34:36 2011 +0100
+++ b/contrib/check-code.py	Thu Nov 17 16:53:17 2011 -0600
@@ -131,7 +131,8 @@
     (r'[^\n]\Z', "no trailing newline"),
     (r'(\S[ \t]+|^[ \t]+)\n', "trailing whitespace"),
 #    (r'^\s+[^_ \n][^_. \n]+_[^_\n]+\s*=', "don't use underbars in identifiers"),
-#    (r'\w*[a-z][A-Z]\w*\s*=', "don't use camelcase in identifiers"),
+    (r'^\s+(self\.)?[A-za-z][a-z0-9]+[A-Z]\w* = ',
+     "don't use camelcase in identifiers"),
     (r'^\s*(if|while|def|class|except|try)\s[^[\n]*:\s*[^\\n]#\s]+',
      "linebreak after :"),
     (r'class\s[^( \n]+:', "old-style class, use class foo(object)"),
@@ -301,7 +302,7 @@
     return lines
 
 def checkfile(f, logfunc=_defaultlogger.log, maxerr=None, warnings=False,
-              blame=False, debug=False):
+              blame=False, debug=False, lineno=True):
     """checks style and portability of a given file
 
     :f: filepath
@@ -384,7 +385,7 @@
                         bl, bu, br = blamecache[n]
                         if bl == l:
                             bd = '%s@%s' % (bu, br)
-                errors.append((f, n + 1, l, msg, bd))
+                errors.append((f, lineno and n + 1, l, msg, bd))
                 result = False
 
         errors.sort()
@@ -407,8 +408,11 @@
                       help="use annotate to generate blame info")
     parser.add_option("", "--debug", action="store_true",
                       help="show debug information")
+    parser.add_option("", "--nolineno", action="store_false",
+                      dest='lineno', help="don't show line numbers")
 
-    parser.set_defaults(per_file=15, warnings=False, blame=False, debug=False)
+    parser.set_defaults(per_file=15, warnings=False, blame=False, debug=False,
+                        lineno=True)
     (options, args) = parser.parse_args()
 
     if len(args) == 0:
@@ -419,6 +423,7 @@
     for f in check:
         ret = 0
         if not checkfile(f, maxerr=options.per_file, warnings=options.warnings,
-                         blame=options.blame, debug=options.debug):
+                         blame=options.blame, debug=options.debug,
+                         lineno=options.lineno):
             ret = 1
     sys.exit(ret)
--- a/hgext/convert/darcs.py	Wed Nov 16 08:34:36 2011 +0100
+++ b/hgext/convert/darcs.py	Thu Nov 17 16:53:17 2011 -0600
@@ -24,7 +24,7 @@
             try:
                 from elementtree.ElementTree import ElementTree, XMLParser
             except ImportError:
-                ElementTree = None
+                pass
 
 class darcs_source(converter_source, commandline):
     def __init__(self, ui, path, rev=None):
@@ -42,7 +42,7 @@
             raise util.Abort(_('darcs version 2.1 or newer needed (found %r)') %
                              version)
 
-        if ElementTree is None:
+        if "ElementTree" not in globals():
             raise util.Abort(_("Python ElementTree module is not available"))
 
         self.path = os.path.realpath(path)
--- a/hgext/mq.py	Wed Nov 16 08:34:36 2011 +0100
+++ b/hgext/mq.py	Thu Nov 17 16:53:17 2011 -0600
@@ -2915,6 +2915,9 @@
         return 0
 
     revs = scmutil.revrange(repo, revrange)
+    if repo['.'].rev() in revs and repo[None].files():
+        ui.warn(_('warning: uncommitted changes in the working directory\n'))
+
     q.finish(repo, revs)
     q.savedirty()
     return 0
--- a/hgext/rebase.py	Wed Nov 16 08:34:36 2011 +0100
+++ b/hgext/rebase.py	Thu Nov 17 16:53:17 2011 -0600
@@ -185,21 +185,19 @@
                 dest = repo[destf]
 
             if revf:
-                revgen = repo.set('%lr', revf)
+                rebaseset = repo.revs('%lr', revf)
             elif srcf:
-                revgen = repo.set('(%r)::', srcf)
+                rebaseset = repo.revs('(%r)::', srcf)
             else:
                 base = basef or '.'
-                revgen = repo.set('(children(ancestor(%r, %d)) and ::(%r))::',
-                                  base, dest, base)
-
-            rebaseset = [c.rev() for c in revgen]
+                rebaseset = repo.revs('(children(ancestor(%r, %d)) & ::%r)::',
+                    base, dest, base)
 
             if not rebaseset:
                 repo.ui.debug('base is ancestor of destination')
                 result = None
-            elif not keepf and list(repo.set('first(children(%ld) - %ld)',
-                                            rebaseset, rebaseset)):
+            elif not keepf and list(repo.revs('first(children(%ld) - %ld)',
+                                              rebaseset, rebaseset)):
                 raise util.Abort(
                     _("can't remove original changesets with"
                       " unrebased descendants"),
@@ -589,8 +587,7 @@
         # rebase on ancestor, force detach
         detach = True
     if detach:
-        detachset = [c.rev() for c in repo.set('::%d - ::%d - %d',
-                                                root, commonbase, root)]
+        detachset = repo.revs('::%d - ::%d - %d', root, commonbase, root)
 
     repo.ui.debug('rebase onto %d starting from %d\n' % (dest, root))
     state = dict.fromkeys(rebaseset, nullrev)
--- a/mercurial/cmdutil.py	Wed Nov 16 08:34:36 2011 +0100
+++ b/mercurial/cmdutil.py	Thu Nov 17 16:53:17 2011 -0600
@@ -1165,15 +1165,19 @@
             if ui.verbose or not exact:
                 ui.status(_('adding %s\n') % match.rel(join(f)))
 
-    if listsubrepos:
-        for subpath in wctx.substate:
-            sub = wctx.sub(subpath)
-            try:
-                submatch = matchmod.narrowmatcher(subpath, match)
+    for subpath in wctx.substate:
+        sub = wctx.sub(subpath)
+        try:
+            submatch = matchmod.narrowmatcher(subpath, match)
+            if listsubrepos:
                 bad.extend(sub.add(ui, submatch, dryrun, prefix))
-            except error.LookupError:
-                ui.status(_("skipping missing subrepository: %s\n")
-                               % join(subpath))
+            else:
+                for f in sub.walk(submatch):
+                    if submatch.exact(f):
+                        bad.extend(sub.add(ui, submatch, dryrun, prefix))
+        except error.LookupError:
+            ui.status(_("skipping missing subrepository: %s\n")
+                           % join(subpath))
 
     if not dryrun:
         rejected = wctx.add(names, prefix)
--- a/mercurial/commands.py	Wed Nov 16 08:34:36 2011 +0100
+++ b/mercurial/commands.py	Thu Nov 17 16:53:17 2011 -0600
@@ -13,6 +13,7 @@
 import patch, help, url, encoding, templatekw, discovery
 import archival, changegroup, cmdutil, hbisect
 import sshserver, hgweb, hgweb.server, commandserver
+import match as matchmod
 import merge as mergemod
 import minirst, revset, fileset
 import dagparser, context, simplemerge
@@ -738,6 +739,17 @@
     marks = repo._bookmarks
     cur   = repo.changectx('.').node()
 
+    if delete:
+        if mark is None:
+            raise util.Abort(_("bookmark name required"))
+        if mark not in marks:
+            raise util.Abort(_("bookmark '%s' does not exist") % mark)
+        if mark == repo._bookmarkcurrent:
+            bookmarks.setcurrent(repo, None)
+        del marks[mark]
+        bookmarks.write(repo)
+        return
+
     if rename:
         if rename not in marks:
             raise util.Abort(_("bookmark '%s' does not exist") % rename)
@@ -753,17 +765,6 @@
         bookmarks.write(repo)
         return
 
-    if delete:
-        if mark is None:
-            raise util.Abort(_("bookmark name required"))
-        if mark not in marks:
-            raise util.Abort(_("bookmark '%s' does not exist") % mark)
-        if mark == repo._bookmarkcurrent:
-            bookmarks.setcurrent(repo, None)
-        del marks[mark]
-        bookmarks.write(repo)
-        return
-
     if mark is not None:
         if "\n" in mark:
             raise util.Abort(_("bookmark name cannot contain newlines"))
@@ -784,8 +785,8 @@
         if rev:
             marks[mark] = repo.lookup(rev)
         else:
-            marks[mark] = repo.changectx('.').node()
-        if not inactive and repo.changectx('.').node() == marks[mark]:
+            marks[mark] = cur
+        if not inactive and cur == marks[mark]:
             bookmarks.setcurrent(repo, mark)
         bookmarks.write(repo)
         return
@@ -2189,7 +2190,7 @@
         if ent[1] & 020000:
             mode = 'lnk'
         else:
-            mode = '%3o' % (ent[1] & 0777)
+            mode = '%3o' % (ent[1] & 0777 & ~util.umask)
         ui.write("%c %s %10d %s%s\n" % (ent[0], mode, ent[2], timestr, file_))
     for f in repo.dirstate.copies():
         ui.write(_("copy: %s -> %s\n") % (repo.dirstate.copied(f), f))
@@ -2432,23 +2433,45 @@
     if not pats:
         raise util.Abort(_('no files specified'))
 
-    m = scmutil.match(repo[None], pats, opts)
+    wctx = repo[None]
+    m = scmutil.match(wctx, pats, opts)
     s = repo.status(match=m, clean=True)
     forget = sorted(s[0] + s[1] + s[3] + s[6])
+    subforget = {}
     errs = 0
 
+    for subpath in wctx.substate:
+        sub = wctx.sub(subpath)
+        try:
+            submatch = matchmod.narrowmatcher(subpath, m)
+            for fsub in sub.walk(submatch):
+                if submatch.exact(fsub):
+                    subforget[subpath + '/' + fsub] = (fsub, sub)
+        except error.LookupError:
+            ui.status(_("skipping missing subrepository: %s\n") % subpath)
+
     for f in m.files():
         if f not in repo.dirstate and not os.path.isdir(m.rel(f)):
-            if os.path.exists(m.rel(f)):
-                ui.warn(_('not removing %s: file is already untracked\n')
-                        % m.rel(f))
-            errs = 1
+            if f not in subforget:
+                if os.path.exists(m.rel(f)):
+                    ui.warn(_('not removing %s: file is already untracked\n')
+                            % m.rel(f))
+                errs = 1
 
     for f in forget:
         if ui.verbose or not m.exact(f):
             ui.status(_('removing %s\n') % m.rel(f))
 
-    repo[None].forget(forget)
+    if ui.verbose:
+        for f in sorted(subforget.keys()):
+            ui.status(_('removing %s\n') % m.rel(f))
+
+    wctx.forget(forget)
+
+    for f in sorted(subforget.keys()):
+        fsub, sub = subforget[f]
+        sub.forget([fsub])
+
     return errs
 
 @command(
@@ -2534,16 +2557,16 @@
         revs = scmutil.revrange(repo, revs)
 
     # check for merges
-    for ctx in repo.set('%ld and merge()', revs):
-        ui.warn(_('skipping ungraftable merge revision %s\n') % ctx.rev())
-        revs.remove(ctx.rev())
+    for rev in repo.revs('%ld and merge()', revs):
+        ui.warn(_('skipping ungraftable merge revision %s\n') % rev)
+        revs.remove(rev)
     if not revs:
         return -1
 
     # check for ancestors of dest branch
-    for ctx in repo.set('::. and %ld', revs):
-        ui.warn(_('skipping ancestor revision %s\n') % ctx.rev())
-        revs.remove(ctx.rev())
+    for rev in repo.revs('::. and %ld', revs):
+        ui.warn(_('skipping ancestor revision %s\n') % rev)
+        revs.remove(rev)
     if not revs:
         return -1
 
@@ -3734,14 +3757,14 @@
     [('f', 'follow', None,
      _('follow changeset history, or file history across copies and renames')),
     ('', 'follow-first', None,
-     _('only follow the first parent of merge changesets')),
+     _('only follow the first parent of merge changesets (DEPRECATED)')),
     ('d', 'date', '', _('show revisions matching date spec'), _('DATE')),
     ('C', 'copies', None, _('show copied files')),
     ('k', 'keyword', [],
      _('do case-insensitive search for a given text'), _('TEXT')),
     ('r', 'rev', [], _('show the specified revision or range'), _('REV')),
     ('', 'removed', None, _('include revisions where files were removed')),
-    ('m', 'only-merges', None, _('show only merges')),
+    ('m', 'only-merges', None, _('show only merges (DEPRECATED)')),
     ('u', 'user', [], _('revisions committed by user'), _('USER')),
     ('', 'only-branch', [],
      _('show only changesets within the given named branch (DEPRECATED)'),
@@ -3750,7 +3773,7 @@
      _('show changesets within the given named branch'), _('BRANCH')),
     ('P', 'prune', [],
      _('do not display revision or any of its ancestors'), _('REV')),
-    ('', 'hidden', False, _('show hidden changesets')),
+    ('', 'hidden', False, _('show hidden changesets (DEPRECATED)')),
     ] + logopts + walkopts,
     _('[OPTION]... [FILE]'))
 def log(ui, repo, *pats, **opts):
--- a/mercurial/context.py	Wed Nov 16 08:34:36 2011 +0100
+++ b/mercurial/context.py	Thu Nov 17 16:53:17 2011 -0600
@@ -117,6 +117,13 @@
         return self._repo.nodetags(self._node)
     def bookmarks(self):
         return self._repo.nodebookmarks(self._node)
+    def phase(self):
+        if self._rev == -1:
+            return 0
+        if self._rev >= len(self._repo._phaserev):
+            # outdated cache
+            del self._repo._phaserev
+        return self._repo._phaserev[self._rev]
     def hidden(self):
         return self._rev in self._repo.changelog.hiddenrevs
 
--- a/mercurial/discovery.py	Wed Nov 16 08:34:36 2011 +0100
+++ b/mercurial/discovery.py	Thu Nov 17 16:53:17 2011 -0600
@@ -67,14 +67,18 @@
     on circumstances:
 
     If we are not going to push anything, return a tuple (None,
-    outgoing) where outgoing is 0 if there are no outgoing
+    outgoing, common) where outgoing is 0 if there are no outgoing
     changesets and 1 if there are, but we refuse to push them
-    (e.g. would create new remote heads).
+    (e.g. would create new remote heads). The third element "common"
+    is the list of heads of the common set between local and remote.
 
-    Otherwise, return a tuple (changegroup, remoteheads), where
-    changegroup is a readable file-like object whose read() returns
-    successive changegroup chunks ready to be sent over the wire and
-    remoteheads is the list of remote heads.'''
+    Otherwise, return a tuple (changegroup, remoteheads, futureheads),
+    where changegroup is a readable file-like object whose read()
+    returns successive changegroup chunks ready to be sent over the
+    wire, remoteheads is the list of remote heads and futureheads is
+    the list of heads of the common set between local and remote to
+    be after push completion.
+    '''
     commoninc = findcommonincoming(repo, remote, force=force)
     common, revs = findcommonoutgoing(repo, remote, onlyheads=revs,
                                       commoninc=commoninc, force=force)
@@ -85,7 +89,7 @@
 
     if not outg:
         repo.ui.status(_("no changes found\n"))
-        return None, 1
+        return None, 1, common
 
     if not force and remoteheads != [nullid]:
         if remote.capable('branchmap'):
@@ -189,4 +193,10 @@
         cg = repo._changegroup(outg, 'push')
     else:
         cg = repo.getbundle('push', heads=revs, common=common)
-    return cg, remoteheads
+    # no need to compute outg ancestor. All node in outg have either:
+    # - parents in outg
+    # - parents in common
+    # - nullid parent
+    rset = repo.set('heads(%ln + %ln)', common, outg)
+    futureheads = [ctx.node() for ctx in rset]
+    return cg, remoteheads, futureheads
--- a/mercurial/dispatch.py	Wed Nov 16 08:34:36 2011 +0100
+++ b/mercurial/dispatch.py	Thu Nov 17 16:53:17 2011 -0600
@@ -24,7 +24,7 @@
 
 def run():
     "run the command in sys.argv"
-    sys.exit(dispatch(request(sys.argv[1:])))
+    sys.exit((dispatch(request(sys.argv[1:])) or 0) & 255)
 
 def dispatch(req):
     "run the command specified in req.args"
--- a/mercurial/filemerge.py	Wed Nov 16 08:34:36 2011 +0100
+++ b/mercurial/filemerge.py	Thu Nov 17 16:53:17 2011 -0600
@@ -262,7 +262,11 @@
         _matcheol(repo.wjoin(fd), back)
 
     if r:
-        ui.warn(_("merging %s failed!\n") % fd)
+        if tool == "internal:merge":
+            ui.warn(_("merging %s incomplete! "
+                      "(edit conflicts, then use 'hg resolve --mark')\n") % fd)
+        else:
+            ui.warn(_("merging %s failed!\n") % fd)
     else:
         os.unlink(back)
 
--- a/mercurial/hbisect.py	Wed Nov 16 08:34:36 2011 +0100
+++ b/mercurial/hbisect.py	Thu Nov 17 16:53:17 2011 -0600
@@ -179,7 +179,7 @@
         # that's because the bisection can go either way
         range = '( bisect(bad)::bisect(good) | bisect(good)::bisect(bad) )'
 
-        _t = [c.rev() for c in repo.set('bisect(good)::bisect(bad)')]
+        _t = repo.revs('bisect(good)::bisect(bad)')
         # The sets of topologically good or bad csets
         if len(_t) == 0:
             # Goods are topologically after bads
@@ -206,22 +206,21 @@
         ignored = '( ( (%s) | (%s) ) - (%s) )' % (iba, iga, range)
 
         if status == 'range':
-            return [c.rev() for c in repo.set(range)]
+            return repo.revs(range)
         elif status == 'pruned':
-            return [c.rev() for c in repo.set(pruned)]
+            return repo.revs(pruned)
         elif status == 'untested':
-            return [c.rev() for c in repo.set(untested)]
+            return repo.revs(untested)
         elif status == 'ignored':
-            return [c.rev() for c in repo.set(ignored)]
+            return repo.revs(ignored)
         elif status == "goods":
-            return [c.rev() for c in repo.set(goods)]
+            return repo.revs(goods)
         elif status == "bads":
-            return [c.rev() for c in repo.set(bads)]
-
+            return repo.revs(bads)
         else:
             raise error.ParseError(_('invalid bisect state'))
 
-def label(repo, node, short=False):
+def label(repo, node):
     rev = repo.changelog.rev(node)
 
     # Try explicit sets
--- a/mercurial/help/subrepos.txt	Wed Nov 16 08:34:36 2011 +0100
+++ b/mercurial/help/subrepos.txt	Thu Nov 17 16:53:17 2011 -0600
@@ -73,8 +73,10 @@
 -----------------------------------
 
 :add: add does not recurse in subrepos unless -S/--subrepos is
-    specified. Git and Subversion subrepositories are currently
-    silently ignored.
+    specified.  However, if you specify the full path of a file in a
+    subrepo, it will be added even without -S/--subrepos specified.
+    Git and Subversion subrepositories are currently silently
+    ignored.
 
 :archive: archive does not recurse in subrepositories unless
     -S/--subrepos is specified.
@@ -93,6 +95,9 @@
     elements. Git and Subversion subrepositories are currently
     silently ignored.
 
+:forget: forget currently only handles exact file matches in subrepos.
+    Git and Subversion subrepositories are currently silently ignored.
+
 :incoming: incoming does not recurse in subrepos unless -S/--subrepos
     is specified. Git and Subversion subrepositories are currently
     silently ignored.
--- a/mercurial/localrepo.py	Wed Nov 16 08:34:36 2011 +0100
+++ b/mercurial/localrepo.py	Thu Nov 17 16:53:17 2011 -0600
@@ -8,7 +8,7 @@
 from node import bin, hex, nullid, nullrev, short
 from i18n import _
 import repo, changegroup, subrepo, discovery, pushkey
-import changelog, dirstate, filelog, manifest, context, bookmarks
+import changelog, dirstate, filelog, manifest, context, bookmarks, phases
 import lock, transaction, store, encoding
 import scmutil, util, extensions, hook, error, revset
 import match as matchmod
@@ -36,6 +36,7 @@
         self.wopener = scmutil.opener(self.root)
         self.baseui = baseui
         self.ui = baseui.copy()
+        self._dirtyphases = False
 
         try:
             self.ui.readconfig(self.join("hgrc"), self.root)
@@ -170,6 +171,25 @@
     def _writebookmarks(self, marks):
       bookmarks.write(self)
 
+    @filecache('phaseroots')
+    def _phaseroots(self):
+        self._dirtyphases = False
+        phaseroots = phases.readroots(self)
+        phases.filterunknown(self, phaseroots)
+        return phaseroots
+
+    @propertycache
+    def _phaserev(self):
+        cache = [0] * len(self)
+        for phase in phases.trackedphases:
+            roots = map(self.changelog.rev, self._phaseroots[phase])
+            if roots:
+                for rev in roots:
+                    cache[rev] = phase
+                for rev in self.changelog.descendants(*roots):
+                    cache[rev] = phase
+        return cache
+
     @filecache('00changelog.i', True)
     def changelog(self):
         c = changelog.changelog(self.sopener)
@@ -220,15 +240,18 @@
         for i in xrange(len(self)):
             yield i
 
+    def revs(self, expr, *args):
+        '''Return a list of revisions matching the given revset'''
+        expr = revset.formatspec(expr, *args)
+        m = revset.match(None, expr)
+        return [r for r in m(self, range(len(self)))]
+
     def set(self, expr, *args):
         '''
         Yield a context for each matching revision, after doing arg
         replacement via revset.formatspec
         '''
-
-        expr = revset.formatspec(expr, *args)
-        m = revset.match(None, expr)
-        for r in m(self, range(len(self))):
+        for r in self.revs(expr, *args):
             yield self[r]
 
     def url(self):
@@ -737,10 +760,16 @@
             util.copyfile(bkname, self.join('journal.bookmarks'))
         else:
             self.opener.write('journal.bookmarks', '')
+        phasesname = self.sjoin('phaseroots')
+        if os.path.exists(phasesname):
+            util.copyfile(phasesname, self.sjoin('journal.phaseroots'))
+        else:
+            self.sopener.write('journal.phaseroots', '')
 
         return (self.sjoin('journal'), self.join('journal.dirstate'),
                 self.join('journal.branch'), self.join('journal.desc'),
-                self.join('journal.bookmarks'))
+                self.join('journal.bookmarks'),
+                self.sjoin('journal.phaseroots'))
 
     def recover(self):
         lock = self.lock()
@@ -805,6 +834,9 @@
         if os.path.exists(self.join('undo.bookmarks')):
             util.rename(self.join('undo.bookmarks'),
                         self.join('bookmarks'))
+        if os.path.exists(self.sjoin('undo.phaseroots')):
+            util.rename(self.sjoin('undo.phaseroots'),
+                        self.sjoin('phaseroots'))
         self.invalidate()
 
         parentgone = (parents[0] not in self.changelog.nodemap or
@@ -891,6 +923,8 @@
 
         def unlock():
             self.store.write()
+            if self._dirtyphases:
+                phases.writeroots(self)
             for k, ce in self._filecache.items():
                 if k == 'dirstate':
                     continue
@@ -1209,6 +1243,8 @@
             self.hook('pretxncommit', throw=True, node=hex(n), parent1=xp1,
                       parent2=xp2, pending=p)
             self.changelog.finalize(trp)
+            # ensure the new commit is 1-phase
+            phases.retractboundary(self, 1, [n])
             tr.close()
 
             if self._branchcache:
@@ -1484,6 +1520,7 @@
                     cg = remote.changegroupsubset(fetch, heads, 'pull')
                 result = self.addchangegroup(cg, 'pull', remote.url(),
                                              lock=lock)
+            phases.advanceboundary(self, 0, common)
         finally:
             lock.release()
 
@@ -1518,24 +1555,32 @@
         if not unbundle:
             lock = remote.lock()
         try:
-            cg, remote_heads = discovery.prepush(self, remote, force, revs,
-                                                 newbranch)
-            ret = remote_heads
-            if cg is not None:
-                if unbundle:
-                    # local repo finds heads on server, finds out what
-                    # revs it must push. once revs transferred, if server
-                    # finds it has different heads (someone else won
-                    # commit/push race), server aborts.
-                    if force:
-                        remote_heads = ['force']
-                    # ssh: return remote's addchangegroup()
-                    # http: return remote's addchangegroup() or 0 for error
-                    ret = remote.unbundle(cg, remote_heads, 'push')
-                else:
-                    # we return an integer indicating remote head count change
-                    ret = remote.addchangegroup(cg, 'push', self.url(),
-                                                lock=lock)
+            # get local lock as we might write phase data
+            locallock = self.lock()
+            try:
+                cg, remote_heads, fut = discovery.prepush(self, remote, force,
+                                                           revs, newbranch)
+                ret = remote_heads
+                if cg is not None:
+                    if unbundle:
+                        # local repo finds heads on server, finds out what
+                        # revs it must push. once revs transferred, if server
+                        # finds it has different heads (someone else won
+                        # commit/push race), server aborts.
+                        if force:
+                            remote_heads = ['force']
+                        # ssh: return remote's addchangegroup()
+                        # http: return remote's addchangegroup() or 0 for error
+                        ret = remote.unbundle(cg, remote_heads, 'push')
+                    else:
+                        # we return an integer indicating remote head count change
+                        ret = remote.addchangegroup(cg, 'push', self.url(),
+                                                    lock=lock)
+                # if we don't push, the common data is already useful
+                # everything exchange is public for now
+                phases.advanceboundary(self, 0, fut)
+            finally:
+                locallock.release()
         finally:
             if lock is not None:
                 lock.release()
@@ -1942,6 +1987,9 @@
                           node=hex(cl.node(clstart)), source=srctype,
                           url=url, pending=p)
 
+            added = [cl.node(r) for r in xrange(clstart, clend)]
+            if srctype != 'strip':
+                phases.advanceboundary(self, 0, added)
             # make changelog see real files again
             cl.finalize(trp)
 
@@ -1958,9 +2006,8 @@
             self.hook("changegroup", node=hex(cl.node(clstart)),
                       source=srctype, url=url)
 
-            for i in xrange(clstart, clend):
-                self.hook("incoming", node=hex(cl.node(i)),
-                          source=srctype, url=url)
+            for n in added:
+                self.hook("incoming", node=hex(n), source=srctype, url=url)
 
         # never return 0 here:
         if dh < 0:
--- a/mercurial/mdiff.py	Wed Nov 16 08:34:36 2011 +0100
+++ b/mercurial/mdiff.py	Thu Nov 17 16:53:17 2011 -0600
@@ -100,6 +100,9 @@
         return ""
     epoch = util.datestr((0, 0))
 
+    fn1 = util.pconvert(fn1)
+    fn2 = util.pconvert(fn2)
+
     if not opts.text and (util.binary(a) or util.binary(b)):
         if a and b and len(a) == len(b) and a == b:
             return ""
--- a/mercurial/patch.py	Wed Nov 16 08:34:36 2011 +0100
+++ b/mercurial/patch.py	Thu Nov 17 16:53:17 2011 -0600
@@ -566,8 +566,8 @@
         return self.changed | self.removed
 
 # @@ -start,len +start,len @@ or @@ -start +start @@ if len is 1
-unidesc = re.compile('@@ -(\d+)(,(\d+))? \+(\d+)(,(\d+))? @@')
-contextdesc = re.compile('(---|\*\*\*) (\d+)(,(\d+))? (---|\*\*\*)')
+unidesc = re.compile('@@ -(\d+)(?:,(\d+))? \+(\d+)(?:,(\d+))? @@')
+contextdesc = re.compile('(?:---|\*\*\*) (\d+)(?:,(\d+))? (?:---|\*\*\*)')
 eolmodes = ['strict', 'crlf', 'lf', 'auto']
 
 class patchfile(object):
@@ -830,7 +830,7 @@
         m = unidesc.match(self.desc)
         if not m:
             raise PatchError(_("bad hunk #%d") % self.number)
-        self.starta, foo, self.lena, self.startb, foo2, self.lenb = m.groups()
+        self.starta, self.lena, self.startb, self.lenb = m.groups()
         if self.lena is None:
             self.lena = 1
         else:
@@ -857,7 +857,7 @@
         m = contextdesc.match(self.desc)
         if not m:
             raise PatchError(_("bad hunk #%d") % self.number)
-        foo, self.starta, foo2, aend, foo3 = m.groups()
+        self.starta, aend = m.groups()
         self.starta = int(self.starta)
         if aend is None:
             aend = self.starta
@@ -890,7 +890,7 @@
         m = contextdesc.match(l)
         if not m:
             raise PatchError(_("bad hunk #%d") % self.number)
-        foo, self.startb, foo2, bend, foo3 = m.groups()
+        self.startb, bend = m.groups()
         self.startb = int(self.startb)
         if bend is None:
             bend = self.startb
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/mercurial/phases.py	Thu Nov 17 16:53:17 2011 -0600
@@ -0,0 +1,102 @@
+# Mercurial phases support code
+#
+# Copyright 2011 Pierre-Yves David <pierre-yves.david@ens-lyon.org>
+#                Logilab SA        <contact@logilab.fr>
+#                Augie Fackler     <durin42@gmail.com>
+#
+# This software may be used and distributed according to the terms of the
+# GNU General Public License version 2 or any later version.
+
+import errno
+from node import nullid, bin, hex, short
+from i18n import _
+
+allphases = range(2)
+trackedphases = allphases[1:]
+
+def readroots(repo):
+    """Read phase roots from disk"""
+    roots = [set() for i in allphases]
+    roots[0].add(nullid)
+    try:
+        f = repo.sopener('phaseroots')
+        try:
+            for line in f:
+                phase, nh = line.strip().split()
+                roots[int(phase)].add(bin(nh))
+        finally:
+            f.close()
+    except IOError, inst:
+        if inst.errno != errno.ENOENT:
+            raise
+    return roots
+
+def writeroots(repo):
+    """Write phase roots from disk"""
+    f = repo.sopener('phaseroots', 'w', atomictemp=True)
+    try:
+        for phase, roots in enumerate(repo._phaseroots):
+            for h in roots:
+                f.write('%i %s\n' % (phase, hex(h)))
+        repo._dirtyphases = False
+    finally:
+        f.close()
+
+def filterunknown(repo, phaseroots=None):
+    """remove unknown nodes from the phase boundary
+
+    no data is lost as unknown node only old data for their descentants
+    """
+    if phaseroots is None:
+        phaseroots = repo._phaseroots
+    for phase, nodes in enumerate(phaseroots):
+        missing = [node for node in nodes if node not in repo]
+        if missing:
+            for mnode in missing:
+                msg = _('Removing unknown node %(n)s from %(p)i-phase boundary')
+                repo.ui.debug(msg, {'n': short(mnode), 'p': phase})
+            nodes.symmetric_difference_update(missing)
+            repo._dirtyphases = True
+
+def advanceboundary(repo, targetphase, nodes):
+    """Add nodes to a phase changing other nodes phases if necessary.
+
+    This function move boundary *forward* this means that all nodes are set
+    in the target phase or kept in a *lower* phase.
+
+    Simplify boundary to contains phase roots only."""
+    for phase in xrange(targetphase + 1, len(allphases)):
+        # filter nodes that are not in a compatible phase already
+        # XXX rev phase cache might have been invalidated by a previous loop
+        # XXX we need to be smarter here
+        nodes = [n for n in nodes if repo[n].phase() >= phase]
+        if not nodes:
+            break # no roots to move anymore
+        roots = repo._phaseroots[phase]
+        olds = roots.copy()
+        ctxs = list(repo.set('roots((%ln::) - (%ln::%ln))', olds, olds, nodes))
+        roots.clear()
+        roots.update(ctx.node() for ctx in ctxs)
+        if olds != roots:
+            # invalidate cache (we probably could be smarter here
+            if '_phaserev' in vars(repo):
+                del repo._phaserev
+            repo._dirtyphases = True
+
+def retractboundary(repo, targetphase, nodes):
+    """Set nodes back to a phase changing other nodes phases if necessary.
+
+    This function move boundary *backward* this means that all nodes are set
+    in the target phase or kept in a *higher* phase.
+
+    Simplify boundary to contains phase roots only."""
+    currentroots = repo._phaseroots[targetphase]
+    newroots = [n for n in nodes if repo[n].phase() < targetphase]
+    if newroots:
+        currentroots.update(newroots)
+        ctxs = repo.set('roots(%ln::)', currentroots)
+        currentroots.intersection_update(ctx.node() for ctx in ctxs)
+        if '_phaserev' in vars(repo):
+            del repo._phaserev
+        repo._dirtyphases = True
+
--- a/mercurial/repair.py	Wed Nov 16 08:34:36 2011 +0100
+++ b/mercurial/repair.py	Thu Nov 17 16:53:17 2011 -0600
@@ -6,7 +6,7 @@
 # This software may be used and distributed according to the terms of the
 # GNU General Public License version 2 or any later version.
 
-from mercurial import changegroup, bookmarks
+from mercurial import changegroup, bookmarks, phases
 from mercurial.node import short
 from mercurial.i18n import _
 import os
@@ -145,7 +145,9 @@
         for m in updatebm:
             bm[m] = repo['.'].node()
         bookmarks.write(repo)
-
+        # remove potential unknown phase
+        # XXX using to_strip data would be faster
+        phases.filterunknown(repo)
     except:
         if backupfile:
             ui.warn(_("strip failed, full bundle stored in '%s'\n")
--- a/mercurial/scmutil.py	Wed Nov 16 08:34:36 2011 +0100
+++ b/mercurial/scmutil.py	Thu Nov 17 16:53:17 2011 -0600
@@ -98,7 +98,7 @@
                 if p in lparts[1:]:
                     pos = lparts.index(p)
                     base = os.path.join(*parts[:pos])
-                    raise util.Abort(_('path %r is inside nested repo %r')
+                    raise util.Abort(_("path '%s' is inside nested repo %r")
                                      % (path, base))
 
         parts.pop()
@@ -123,7 +123,7 @@
                 elif (stat.S_ISDIR(st.st_mode) and
                       os.path.isdir(os.path.join(curpath, '.hg'))):
                     if not self.callback or not self.callback(curpath):
-                        raise util.Abort(_('path %r is inside nested repo %r') %
+                        raise util.Abort(_("path '%s' is inside nested repo %r") %
                                          (path, prefix))
             prefixes.append(prefix)
             parts.pop()
--- a/mercurial/subrepo.py	Wed Nov 16 08:34:36 2011 +0100
+++ b/mercurial/subrepo.py	Thu Nov 17 16:53:17 2011 -0600
@@ -353,6 +353,15 @@
                         unit=_('files'), total=total)
         ui.progress(_('archiving (%s)') % relpath, None)
 
+    def walk(self, match):
+        '''
+        walk recursively through the directory tree, finding all files
+        matched by the match function
+        '''
+        pass
+
+    def forget(self, files):
+        pass
 
 class hgsubrepo(abstractsubrepo):
     def __init__(self, ctx, path, state):
@@ -543,6 +552,13 @@
         ctx = self._repo[rev]
         return ctx.flags(name)
 
+    def walk(self, match):
+        ctx = self._repo[None]
+        return ctx.walk(match)
+
+    def forget(self, files):
+        ctx = self._repo[None]
+        ctx.forget(files)
 
 class svnsubrepo(abstractsubrepo):
     def __init__(self, ctx, path, state):
--- a/mercurial/templatekw.py	Wed Nov 16 08:34:36 2011 +0100
+++ b/mercurial/templatekw.py	Thu Nov 17 16:53:17 2011 -0600
@@ -275,6 +275,10 @@
     """
     return ctx.hex()
 
+def showphase(repo, ctx, templ, **args):
+    """:rev: Integer. The changeset phase."""
+    return ctx.phase()
+
 def showrev(repo, ctx, templ, **args):
     """:rev: Integer. The repository-local changeset revision number."""
     return ctx.rev()
@@ -312,6 +316,7 @@
     'latesttagdistance': showlatesttagdistance,
     'manifest': showmanifest,
     'node': shownode,
+    'phase': showphase,
     'rev': showrev,
     'tags': showtags,
 }
--- a/mercurial/util.py	Wed Nov 16 08:34:36 2011 +0100
+++ b/mercurial/util.py	Thu Nov 17 16:53:17 2011 -0600
@@ -1495,7 +1495,7 @@
     """
 
     _safechars = "!~*'()+"
-    _safepchars = "/!~*'()+"
+    _safepchars = "/!~*'()+:"
     _matchscheme = re.compile(r'^[a-zA-Z0-9+.\-]+:').match
 
     def __init__(self, path, parsequery=True, parsefragment=True):
@@ -1607,8 +1607,8 @@
 
         Examples:
 
-        >>> str(url('http://user:pw@host:80/?foo#bar'))
-        'http://user:pw@host:80/?foo#bar'
+        >>> str(url('http://user:pw@host:80/c:/bob?fo:oo#ba:ar'))
+        'http://user:pw@host:80/c:/bob?fo:oo#ba:ar'
         >>> str(url('http://user:pw@host:80/?foo=bar&baz=42'))
         'http://user:pw@host:80/?foo=bar&baz=42'
         >>> str(url('http://user:pw@host:80/?foo=bar%3dbaz'))
--- a/mercurial/windows.py	Wed Nov 16 08:34:36 2011 +0100
+++ b/mercurial/windows.py	Thu Nov 17 16:53:17 2011 -0600
@@ -26,7 +26,7 @@
 unlink = win32.unlink
 
 nulldev = 'NUL:'
-umask = 002
+umask = 0022
 
 # wrap osutil.posixfile to provide friendlier exceptions
 def posixfile(name, mode='r', buffering=-1):
--- a/setup.py	Wed Nov 16 08:34:36 2011 +0100
+++ b/setup.py	Thu Nov 17 16:53:17 2011 -0600
@@ -44,7 +44,7 @@
     pass
 
 if isironpython:
-    print "warning: IronPython detected (no bz2 support)"
+    sys.stderr.write("warning: IronPython detected (no bz2 support)\n")
 else:
     try:
         import bz2
@@ -68,6 +68,19 @@
 from distutils.sysconfig import get_python_inc
 from distutils.version import StrictVersion
 
+convert2to3 = '--c2to3' in sys.argv
+if convert2to3:
+    try:
+        from distutils.command.build_py import build_py_2to3 as build_py
+        from lib2to3.refactor import get_fixers_from_package as getfixers
+    except ImportError:
+        if sys.version_info[0] < 3:
+            raise SystemExit("--c2to3 is only compatible with python3.")
+        raise
+    sys.path.append('contrib')
+elif sys.version_info[0] >= 3:
+    raise SystemExit("setup.py with python3 needs --c2to3 (experimental)")
+
 scripts = ['hg']
 if os.name == 'nt':
     scripts.append('contrib/win32/hg.bat')
@@ -186,7 +199,18 @@
 except ImportError:
     version = 'unknown'
 
-class hgbuildmo(build):
+class hgbuild(build):
+    # Insert hgbuildmo first so that files in mercurial/locale/ are found
+    # when build_py is run next.
+    sub_commands = [('build_mo', None),
+    # We also need build_ext before build_py. Otherwise, when 2to3 is called (in
+    # build_py), it will not find osutil & friends, thinking that those modules are
+    # global and, consequently, making a mess, now that all module imports are
+    # global.
+                    ('build_ext', build.has_ext_modules),
+                   ] + build.sub_commands
+
+class hgbuildmo(Command):
 
     description = "build translations (.mo files)"
 
@@ -216,14 +240,27 @@
             self.mkpath(join('mercurial', modir))
             self.make_file([pofile], mobuildfile, spawn, (cmd,))
 
+    def initialize_options(self):
+        pass
 
-# Insert hgbuildmo first so that files in mercurial/locale/ are found
-# when build_py is run next.
-build.sub_commands.insert(0, ('build_mo', None))
+    def finalize_options(self):
+        pass
+
+
+class hgdist(Distribution):
+    pure = 0
 
-Distribution.pure = 0
-Distribution.global_options.append(('pure', None, "use pure (slow) Python "
-                                    "code instead of C extensions"))
+    global_options = Distribution.global_options + \
+                     [('pure', None, "use pure (slow) Python "
+                        "code instead of C extensions"),
+                      ('c2to3', None, "(experimental!) convert "
+                        "code with 2to3"),
+                     ]
+
+    def has_ext_modules(self):
+        # self.ext_modules is emptied in hgbuildpy.finalize_options which is
+        # too late for some cases
+        return not self.pure and Distribution.has_ext_modules(self)
 
 class hgbuildext(build_ext):
 
@@ -237,6 +274,9 @@
                      ext.name)
 
 class hgbuildpy(build_py):
+    if convert2to3:
+        fixer_names = sorted(set(getfixers("lib2to3.fixes") +
+                                 getfixers("hgfixes")))
 
     def finalize_options(self):
         build_py.finalize_options(self)
@@ -327,7 +367,7 @@
             fp.close()
 
             # skip binary files
-            if '\0' in data:
+            if b('\0') in data:
                 continue
 
             data = data.replace('@LIBDIR@', libdir.encode('string_escape'))
@@ -335,7 +375,8 @@
             fp.write(data)
             fp.close()
 
-cmdclass = {'build_mo': hgbuildmo,
+cmdclass = {'build': hgbuild,
+            'build_mo': hgbuildmo,
             'build_ext': hgbuildext,
             'build_py': hgbuildpy,
             'build_hgextindex': buildhgextindex,
@@ -435,6 +476,7 @@
       data_files=datafiles,
       package_data=packagedata,
       cmdclass=cmdclass,
+      distclass=hgdist,
       options=dict(py2exe=dict(packages=['hgext', 'email']),
                    bdist_mpkg=dict(zipdist=True,
                                    license='COPYING',
--- a/tests/heredoctest.py	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/heredoctest.py	Thu Nov 17 16:53:17 2011 -0600
@@ -1,16 +1,19 @@
-import doctest, tempfile, os, sys
-
-if __name__ == "__main__":
-    if 'TERM' in os.environ:
-        del os.environ['TERM']
-
-    fd, name = tempfile.mkstemp(suffix='hg-tst')
+import sys
 
-    try:
-        os.write(fd, sys.stdin.read())
-        os.close(fd)
-        failures, _ = doctest.testfile(name, module_relative=False)
-        if failures:
-            sys.exit(1)
-    finally:
-        os.remove(name)
+globalvars = {}
+localvars = {}
+lines = sys.stdin.readlines()
+while lines:
+    l = lines.pop(0)
+    if l.startswith('SALT'):
+        print l[:-1]
+    elif l.startswith('>>> '):
+        snippet = l[4:]
+        while lines and lines[0].startswith('... '):
+            l = lines.pop(0)
+            snippet += "\n" + l[4:]
+        c = compile(snippet, '<heredoc>', 'single')
+        try:
+            exec c in globalvars, localvars
+        except Exception, inst:
+            print repr(inst)
--- a/tests/hghave	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/hghave	Thu Nov 17 16:53:17 2011 -0600
@@ -161,7 +161,7 @@
     return matchoutput('p4 -V', r'Rev\. P4/') and matchoutput('p4d -V', r'Rev\. P4D/')
 
 def has_symlink():
-    return hasattr(os, "symlink")
+    return hasattr(os, "symlink") # FIXME: should also check file system and os
 
 def has_tla():
     return matchoutput('tla --version 2>&1', r'The GNU Arch Revision')
@@ -209,6 +209,15 @@
     except ImportError:
         return False
 
+def has_windows():
+    return os.name == 'nt'
+
+def has_system_sh():
+    return os.name != 'nt'
+
+def has_serve():
+    return os.name != 'nt' # gross approximation
+
 checks = {
     "baz": (has_baz, "GNU Arch baz client"),
     "bzr": (has_bzr, "Canonical's Bazaar client"),
@@ -231,14 +240,17 @@
     "p4": (has_p4, "Perforce server and client"),
     "pyflakes": (has_pyflakes, "Pyflakes python linter"),
     "pygments": (has_pygments, "Pygments source highlighting library"),
+    "serve": (has_serve, "platform and python can manage 'hg serve -d'"),
     "ssl": (has_ssl, "python >= 2.6 ssl module and python OpenSSL"),
     "svn": (has_svn, "subversion client and admin tools"),
     "svn13": (has_svn13, "subversion client and admin tools >= 1.3"),
     "svn15": (has_svn15, "subversion client and admin tools >= 1.5"),
     "svn-bindings": (has_svn_bindings, "subversion python bindings"),
     "symlink": (has_symlink, "symbolic links"),
+    "system-sh": (has_system_sh, "system() uses sh"),
     "tla": (has_tla, "GNU Arch tla client"),
     "unix-permissions": (has_unix_permissions, "unix-style permissions"),
+    "windows": (has_windows, "Windows"),
 }
 
 def list_features():
--- a/tests/run-tests.py	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/run-tests.py	Thu Nov 17 16:53:17 2011 -0600
@@ -87,7 +87,7 @@
 SKIPPED_STATUS = 80
 SKIPPED_PREFIX = 'skipped: '
 FAILED_PREFIX  = 'hghave check failed: '
-PYTHON = sys.executable
+PYTHON = sys.executable.replace('\\', '/')
 IMPL_PATH = 'PYTHONPATH'
 if 'java' in sys.platform:
     IMPL_PATH = 'JYTHONPATH'
@@ -521,43 +521,103 @@
 def stringescape(s):
     return escapesub(escapef, s)
 
-def transformtst(lines):
-    inblock = False
-    for l in lines:
-        if inblock:
-            if l.startswith('  $ ') or not l.startswith('  '):
-                inblock = False
-                yield '  > EOF\n'
-                yield l
-            else:
-                yield '  > ' + l[2:]
+def rematch(el, l):
+    try:
+        # ensure that the regex matches to the end of the string
+        return re.match(el + r'\Z', l)
+    except re.error:
+        # el is an invalid regex
+        return False
+
+def globmatch(el, l):
+    # The only supported special characters are * and ? plus / which also
+    # matches \ on windows. Escaping of these caracters is supported.
+    i, n = 0, len(el)
+    res = ''
+    while i < n:
+        c = el[i]
+        i += 1
+        if c == '\\' and el[i] in '*?\\/':
+            res += el[i - 1:i + 1]
+            i += 1
+        elif c == '*':
+            res += '.*'
+        elif c == '?':
+            res += '.'
+        elif c == '/' and os.name == 'nt':
+            res += '[/\\\\]'
         else:
-            if l.startswith('  >>> '):
-                inblock = True
-                yield '  $ %s -m heredoctest <<EOF\n' % PYTHON
-                yield '  > ' + l[2:]
-            else:
-                yield l
-    if inblock:
-        yield '  > EOF\n'
+            res += re.escape(c)
+    return rematch(res, l)
+
+def linematch(el, l):
+    if el == l: # perfect match (fast)
+        return True
+    if (el and
+        (el.endswith(" (re)\n") and rematch(el[:-6] + '\n', l) or
+         el.endswith(" (glob)\n") and globmatch(el[:-8] + '\n', l) or
+         el.endswith(" (esc)\n") and
+             (el[:-7].decode('string-escape') + '\n' == l or
+              el[:-7].decode('string-escape').replace('\r', '') +
+                  '\n' == l and os.name == 'nt'))):
+        return True
+    return False
 
 def tsttest(test, wd, options, replacements):
-    t = open(test)
-    out = []
-    script = []
+    # We generate a shell script which outputs unique markers to line
+    # up script results with our source. These markers include input
+    # line number and the last return code
     salt = "SALT" + str(time.time())
+    def addsalt(line, inpython):
+        if inpython:
+            script.append('%s %d 0\n' % (salt, line))
+        else:
+            script.append('echo %s %s $?\n' % (salt, line))
 
-    pos = prepos = -1
+    # After we run the shell script, we re-unify the script output
+    # with non-active parts of the source, with synchronization by our
+    # SALT line number markers. The after table contains the
+    # non-active components, ordered by line number
     after = {}
+    pos = prepos = -1
+
+    # Expected shellscript output
     expected = {}
-    for n, l in enumerate(transformtst(t)):
+
+    # We keep track of whether or not we're in a Python block so we
+    # can generate the surrounding doctest magic
+    inpython = False
+
+    f = open(test)
+    t = f.readlines()
+    f.close()
+
+    script = []
+    for n, l in enumerate(t):
         if not l.endswith('\n'):
             l += '\n'
-        if l.startswith('  $ '): # commands
+        if l.startswith('  >>> '): # python inlines
             after.setdefault(pos, []).append(l)
             prepos = pos
             pos = n
-            script.append('echo %s %s $?\n' % (salt, n))
+            if not inpython:
+                # we've just entered a Python block, add the header
+                inpython = True
+                addsalt(prepos, False) # make sure we report the exit code
+                script.append('%s -m heredoctest <<EOF\n' % PYTHON)
+            addsalt(n, True)
+            script.append(l[2:])
+        if l.startswith('  ... '): # python inlines
+            after.setdefault(prepos, []).append(l)
+            script.append(l[2:])
+        elif l.startswith('  $ '): # commands
+            if inpython:
+                script.append("EOF\n")
+                inpython = False
+            after.setdefault(pos, []).append(l)
+            prepos = pos
+            pos = n
+            addsalt(n, False)
             script.append(l[4:])
         elif l.startswith('  > '): # continuations
             after.setdefault(prepos, []).append(l)
@@ -566,21 +626,24 @@
             # queue up a list of expected results
             expected.setdefault(pos, []).append(l[2:])
         else:
+            if inpython:
+                script.append("EOF\n")
+                inpython = False
             # non-command/result - queue up for merged output
             after.setdefault(pos, []).append(l)
 
-    t.close()
+    if inpython:
+        script.append("EOF\n")
+    addsalt(n + 1, False)
 
-    script.append('echo %s %s $?\n' % (salt, n + 1))
-
+    # Write out the script and execute it
     fd, name = tempfile.mkstemp(suffix='hg-tst')
-
     try:
         for l in script:
             os.write(fd, l)
         os.close(fd)
 
-        cmd = '"%s" "%s"' % (options.shell, name)
+        cmd = '%s "%s"' % (options.shell, name)
         vlog("# Running", cmd)
         exitcode, output = run(cmd, wd, options, replacements)
         # do not merge output if skipped, return hghave message instead
@@ -590,32 +653,7 @@
     finally:
         os.remove(name)
 
-    def rematch(el, l):
-        try:
-            # ensure that the regex matches to the end of the string
-            return re.match(el + r'\Z', l)
-        except re.error:
-            # el is an invalid regex
-            return False
-
-    def globmatch(el, l):
-        # The only supported special characters are * and ?. Escaping is
-        # supported.
-        i, n = 0, len(el)
-        res = ''
-        while i < n:
-            c = el[i]
-            i += 1
-            if c == '\\' and el[i] in '*?\\':
-                res += el[i - 1:i + 1]
-                i += 1
-            elif c == '*':
-                res += '.*'
-            elif c == '?':
-                res += '.'
-            else:
-                res += re.escape(c)
-        return rematch(res, l)
+    # Merge the script output back into a unified test
 
     pos = -1
     postout = []
@@ -627,20 +665,16 @@
 
         if lout:
             if lcmd:
+                # output block had no trailing newline, clean up
                 lout += ' (no-eol)\n'
 
+            # find the expected output at the current position
             el = None
             if pos in expected and expected[pos]:
                 el = expected[pos].pop(0)
 
-            if el == lout: # perfect match (fast)
-                postout.append("  " + lout)
-            elif (el and
-                  (el.endswith(" (re)\n") and rematch(el[:-6] + '\n', lout) or
-                   el.endswith(" (glob)\n") and globmatch(el[:-8] + '\n', lout)
-                   or el.endswith(" (esc)\n") and
-                      el.decode('string-escape') == l)):
-                postout.append("  " + el) # fallback regex/glob/esc match
+            if linematch(el, lout):
+                postout.append("  " + el)
             else:
                 if needescape(lout):
                     lout = stringescape(lout.rstrip('\n')) + " (esc)\n"
@@ -652,6 +686,7 @@
             if ret != 0:
                 postout.append("  [%s]\n" % ret)
             if pos in after:
+                # merge in non-active test bits
                 postout += after.pop(pos)
             pos = int(lcmd.split()[0])
 
@@ -832,15 +867,26 @@
 
     # Make a tmp subdirectory to work in
     testtmp = os.environ["TESTTMP"] = os.environ["HOME"] = \
-        os.path.join(HGTMP, os.path.basename(test))
+        os.path.join(HGTMP, os.path.basename(test)).replace('\\', '/')
 
-    os.mkdir(testtmp)
-    ret, out = runner(testpath, testtmp, options, [
-        (re.escape(testtmp), '$TESTTMP'),
+    replacements = [
         (r':%s\b' % options.port, ':$HGPORT'),
         (r':%s\b' % (options.port + 1), ':$HGPORT1'),
         (r':%s\b' % (options.port + 2), ':$HGPORT2'),
-        ])
+        ]
+    if os.name == 'nt':
+        replacements.append((r'\r\n', '\n'))
+        replacements.append(
+            (''.join(c.isalpha() and '[%s%s]' % (c.lower(), c.upper()) or
+                     c in '/\\' and r'[/\\]' or
+                     c.isdigit() and c or
+                     '\\' + c
+                     for c in testtmp), '$TESTTMP'))
+    else:
+        replacements.append((re.escape(testtmp), '$TESTTMP'))
+
+    os.mkdir(testtmp)
+    ret, out = runner(testpath, testtmp, options, replacements)
     vlog("# Ret was:", ret)
 
     mark = '.'
@@ -853,7 +899,7 @@
         refout = None                   # to match "out is None"
     elif os.path.exists(ref):
         f = open(ref, "r")
-        refout = list(transformtst(splitnewlines(f.read())))
+        refout = list(splitnewlines(f.read()))
         f.close()
     else:
         refout = []
--- a/tests/test-add.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-add.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,5 @@
+  $ "$TESTDIR/hghave" no-windows || exit 80
+
   $ hg init a
   $ cd a
   $ echo a > a
@@ -86,7 +88,7 @@
   $ hg merge
   merging a
   warning: conflicts during merge.
-  merging a failed!
+  merging a incomplete! (edit conflicts, then use 'hg resolve --mark')
   0 files updated, 0 files merged, 0 files removed, 1 files unresolved
   use 'hg resolve' to retry unresolved file merges or 'hg update -C .' to abandon
   [1]
--- a/tests/test-addremove-similar.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-addremove-similar.t	Thu Nov 17 16:53:17 2011 -0600
@@ -81,7 +81,7 @@
   $ hg addremove -s80
   removing d/a
   adding d/b
-  recording removal of d/a as rename to d/b (100% similar)
+  recording removal of d/a as rename to d/b (100% similar) (glob)
   $ hg debugstate
   r   0          0 1970-01-01 00:00:00 d/a
   a   0         -1 unset               d/b
@@ -91,10 +91,10 @@
 no copies found here (since the target isn't in d
 
   $ hg addremove -s80 d
-  removing d/b
+  removing d/b (glob)
 
 copies here
 
   $ hg addremove -s80
   adding c
-  recording removal of d/a as rename to c (100% similar)
+  recording removal of d/a as rename to c (100% similar) (glob)
--- a/tests/test-addremove.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-addremove.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,5 @@
+  $ "$TESTDIR/hghave" no-windows || exit 80
+
   $ hg init rep
   $ cd rep
   $ mkdir dir
--- a/tests/test-alias.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-alias.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,5 @@
+  $ "$TESTDIR/hghave" system-sh || exit 80
+
   $ HGFOO=BAR; export HGFOO
   $ cat >> $HGRCPATH <<EOF
   > [extensions]
--- a/tests/test-archive.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-archive.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,5 @@
+  $ "$TESTDIR/hghave" serve || exit 80
+
   $ hg init test
   $ cd test
   $ echo foo>foo
--- a/tests/test-audit-path.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-audit-path.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,9 +1,11 @@
+  $ "$TESTDIR/hghave" symlink || exit 80
+
   $ hg init
 
 should fail
 
   $ hg add .hg/00changelog.i
-  abort: path contains illegal component: .hg/00changelog.i
+  abort: path contains illegal component: .hg/00changelog.i (glob)
   [255]
 
   $ mkdir a
@@ -16,7 +18,7 @@
 should fail
 
   $ hg add b/b
-  abort: path 'b/b' traverses symbolic link 'b'
+  abort: path 'b/b' traverses symbolic link 'b' (glob)
   [255]
 
 should succeed
@@ -26,7 +28,7 @@
 should still fail - maybe
 
   $ hg add b/b
-  abort: path 'b/b' traverses symbolic link 'b'
+  abort: path 'b/b' traverses symbolic link 'b' (glob)
   [255]
 
 unbundle tampered bundle
--- a/tests/test-bad-pull.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-bad-pull.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,5 @@
+  $ "$TESTDIR/hghave" serve || exit 80
+
   $ hg clone http://localhost:$HGPORT/ copy
   abort: error: Connection refused
   [255]
--- a/tests/test-bisect3.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-bisect3.t	Thu Nov 17 16:53:17 2011 -0600
@@ -14,15 +14,15 @@
   $ hg add a
   $ hg ci -u test -d '0 0' -m '0'
   $ echo '1' >a
-  $ hg ci -u test -d '0 1' -m '1'
+  $ hg ci -u test -d '1 0' -m '1'
 
 branch 2-3
 
   $ echo '2' >b
   $ hg add b
-  $ hg ci -u test -d '0 2' -m '2'
+  $ hg ci -u test -d '2 0' -m '2'
   $ echo '3' >b
-  $ hg ci -u test -d '0 3' -m '3'
+  $ hg ci -u test -d '3 0' -m '3'
 
 branch 4-8
 
@@ -30,30 +30,30 @@
   0 files updated, 0 files merged, 1 files removed, 0 files unresolved
   $ echo '4' >c
   $ hg add c
-  $ hg ci -u test -d '0 4' -m '4'
+  $ hg ci -u test -d '4 0' -m '4'
   created new head
   $ echo '5' >c
-  $ hg ci -u test -d '0 5' -m '5'
+  $ hg ci -u test -d '5 0' -m '5'
   $ echo '6' >c
-  $ hg ci -u test -d '0 6' -m '6'
+  $ hg ci -u test -d '6 0' -m '6'
   $ echo '7' >c
-  $ hg ci -u test -d '0 7' -m '7'
+  $ hg ci -u test -d '7 0' -m '7'
   $ echo '8' >c
-  $ hg ci -u test -d '0 8' -m '8'
+  $ hg ci -u test -d '8 0' -m '8'
 
 merge
 
   $ hg merge -r 3
   1 files updated, 0 files merged, 0 files removed, 0 files unresolved
   (branch merge, don't forget to commit)
-  $ hg ci -u test -d '0 9' -m '9=8+3'
+  $ hg ci -u test -d '9 0' -m '9=8+3'
 
   $ echo '10' >a
-  $ hg ci -u test -d '0 10' -m '10'
+  $ hg ci -u test -d '10 0' -m '10'
   $ echo '11' >a
-  $ hg ci -u test -d '0 11' -m '11'
+  $ hg ci -u test -d '11 0' -m '11'
   $ echo '12' >a
-  $ hg ci -u test -d '0 12' -m '12'
+  $ hg ci -u test -d '12 0' -m '12'
 
 unrelated branch
 
@@ -61,10 +61,10 @@
   1 files updated, 0 files merged, 1 files removed, 0 files unresolved
   $ echo '13' >d
   $ hg add d
-  $ hg ci -u test -d '0 13' -m '13'
+  $ hg ci -u test -d '13 0' -m '13'
   created new head
   $ echo '14' >d
-  $ hg ci -u test -d '0 14' -m '14'
+  $ hg ci -u test -d '14 0' -m '14'
 
 mark changesets
 
@@ -72,140 +72,140 @@
   $ hg bisect --good 4
   $ hg bisect --good 6
   $ hg bisect --bad 12
-  Testing changeset 9:8bcbdb072033 (6 changesets remaining, ~2 tests)
+  Testing changeset 9:2197c557e14c (6 changesets remaining, ~2 tests)
   1 files updated, 0 files merged, 1 files removed, 0 files unresolved
   $ hg bisect --bad 10
-  Testing changeset 8:3cd112f87d77 (4 changesets remaining, ~2 tests)
+  Testing changeset 8:e74a86251f58 (4 changesets remaining, ~2 tests)
   0 files updated, 0 files merged, 1 files removed, 0 files unresolved
   $ hg bisect --skip 7
-  Testing changeset 8:3cd112f87d77 (4 changesets remaining, ~2 tests)
+  Testing changeset 8:e74a86251f58 (4 changesets remaining, ~2 tests)
   0 files updated, 0 files merged, 0 files removed, 0 files unresolved
 
 test template
 
   $ hg log --template '{rev}:{node|short} {bisect}\n'
-  14:cecd84203acc 
-  13:86f7c8cdb6df 
-  12:a76089b5f47c bad
-  11:5c3eb122d29c bad (implicit)
-  10:b097cef2be03 bad
-  9:8bcbdb072033 untested
-  8:3cd112f87d77 untested
-  7:577e237a73bd skipped
-  6:e597fa2707c5 good
-  5:b9cea37a76bc good (implicit)
-  4:da6b357259d7 good
-  3:e7f031aee8ca ignored
-  2:b1ad1b6bcc5c ignored
-  1:37f42ae8b45e good (implicit)
+  14:cbf2f3105bbf 
+  13:e07efca37c43 
+  12:98c6b56349c0 bad
+  11:03f491376e63 bad (implicit)
+  10:c012b15e2409 bad
+  9:2197c557e14c untested
+  8:e74a86251f58 untested
+  7:a5f87041c899 skipped
+  6:7d997bedcd8d good
+  5:2dd1875f1028 good (implicit)
+  4:2a1daef14cd4 good
+  3:8417d459b90c ignored
+  2:e1355ee1f23e ignored
+  1:ce7c85e06a9f good (implicit)
   0:b4e73ffab476 good (implicit)
   $ hg log --template '{bisect|shortbisect} {rev}:{node|short}\n'
-    14:cecd84203acc
-    13:86f7c8cdb6df
-  B 12:a76089b5f47c
-  B 11:5c3eb122d29c
-  B 10:b097cef2be03
-  U 9:8bcbdb072033
-  U 8:3cd112f87d77
-  S 7:577e237a73bd
-  G 6:e597fa2707c5
-  G 5:b9cea37a76bc
-  G 4:da6b357259d7
-  I 3:e7f031aee8ca
-  I 2:b1ad1b6bcc5c
-  G 1:37f42ae8b45e
+    14:cbf2f3105bbf
+    13:e07efca37c43
+  B 12:98c6b56349c0
+  B 11:03f491376e63
+  B 10:c012b15e2409
+  U 9:2197c557e14c
+  U 8:e74a86251f58
+  S 7:a5f87041c899
+  G 6:7d997bedcd8d
+  G 5:2dd1875f1028
+  G 4:2a1daef14cd4
+  I 3:8417d459b90c
+  I 2:e1355ee1f23e
+  G 1:ce7c85e06a9f
   G 0:b4e73ffab476
 
 test style
 
   $ hg log --style bisect
-  changeset:   14:cecd84203acc
+  changeset:   14:cbf2f3105bbf
   bisect:      
   tag:         tip
   user:        test
-  date:        Wed Dec 31 23:59:46 1969 -0000
+  date:        Thu Jan 01 00:00:14 1970 +0000
   summary:     14
   
-  changeset:   13:86f7c8cdb6df
+  changeset:   13:e07efca37c43
   bisect:      
-  parent:      3:e7f031aee8ca
+  parent:      3:8417d459b90c
   user:        test
-  date:        Wed Dec 31 23:59:47 1969 -0000
+  date:        Thu Jan 01 00:00:13 1970 +0000
   summary:     13
   
-  changeset:   12:a76089b5f47c
+  changeset:   12:98c6b56349c0
   bisect:      bad
   user:        test
-  date:        Wed Dec 31 23:59:48 1969 -0000
+  date:        Thu Jan 01 00:00:12 1970 +0000
   summary:     12
   
-  changeset:   11:5c3eb122d29c
+  changeset:   11:03f491376e63
   bisect:      bad (implicit)
   user:        test
-  date:        Wed Dec 31 23:59:49 1969 -0000
+  date:        Thu Jan 01 00:00:11 1970 +0000
   summary:     11
   
-  changeset:   10:b097cef2be03
+  changeset:   10:c012b15e2409
   bisect:      bad
   user:        test
-  date:        Wed Dec 31 23:59:50 1969 -0000
+  date:        Thu Jan 01 00:00:10 1970 +0000
   summary:     10
   
-  changeset:   9:8bcbdb072033
+  changeset:   9:2197c557e14c
   bisect:      untested
-  parent:      8:3cd112f87d77
-  parent:      3:e7f031aee8ca
+  parent:      8:e74a86251f58
+  parent:      3:8417d459b90c
   user:        test
-  date:        Wed Dec 31 23:59:51 1969 -0000
+  date:        Thu Jan 01 00:00:09 1970 +0000
   summary:     9=8+3
   
-  changeset:   8:3cd112f87d77
+  changeset:   8:e74a86251f58
   bisect:      untested
   user:        test
-  date:        Wed Dec 31 23:59:52 1969 -0000
+  date:        Thu Jan 01 00:00:08 1970 +0000
   summary:     8
   
-  changeset:   7:577e237a73bd
+  changeset:   7:a5f87041c899
   bisect:      skipped
   user:        test
-  date:        Wed Dec 31 23:59:53 1969 -0000
+  date:        Thu Jan 01 00:00:07 1970 +0000
   summary:     7
   
-  changeset:   6:e597fa2707c5
+  changeset:   6:7d997bedcd8d
   bisect:      good
   user:        test
-  date:        Wed Dec 31 23:59:54 1969 -0000
+  date:        Thu Jan 01 00:00:06 1970 +0000
   summary:     6
   
-  changeset:   5:b9cea37a76bc
+  changeset:   5:2dd1875f1028
   bisect:      good (implicit)
   user:        test
-  date:        Wed Dec 31 23:59:55 1969 -0000
+  date:        Thu Jan 01 00:00:05 1970 +0000
   summary:     5
   
-  changeset:   4:da6b357259d7
+  changeset:   4:2a1daef14cd4
   bisect:      good
-  parent:      1:37f42ae8b45e
+  parent:      1:ce7c85e06a9f
   user:        test
-  date:        Wed Dec 31 23:59:56 1969 -0000
+  date:        Thu Jan 01 00:00:04 1970 +0000
   summary:     4
   
-  changeset:   3:e7f031aee8ca
+  changeset:   3:8417d459b90c
   bisect:      ignored
   user:        test
-  date:        Wed Dec 31 23:59:57 1969 -0000
+  date:        Thu Jan 01 00:00:03 1970 +0000
   summary:     3
   
-  changeset:   2:b1ad1b6bcc5c
+  changeset:   2:e1355ee1f23e
   bisect:      ignored
   user:        test
-  date:        Wed Dec 31 23:59:58 1969 -0000
+  date:        Thu Jan 01 00:00:02 1970 +0000
   summary:     2
   
-  changeset:   1:37f42ae8b45e
+  changeset:   1:ce7c85e06a9f
   bisect:      good (implicit)
   user:        test
-  date:        Wed Dec 31 23:59:59 1969 -0000
+  date:        Thu Jan 01 00:00:01 1970 +0000
   summary:     1
   
   changeset:   0:b4e73ffab476
@@ -215,18 +215,18 @@
   summary:     0
   
   $ hg log --quiet --style bisect
-    14:cecd84203acc
-    13:86f7c8cdb6df
-  B 12:a76089b5f47c
-  B 11:5c3eb122d29c
-  B 10:b097cef2be03
-  U 9:8bcbdb072033
-  U 8:3cd112f87d77
-  S 7:577e237a73bd
-  G 6:e597fa2707c5
-  G 5:b9cea37a76bc
-  G 4:da6b357259d7
-  I 3:e7f031aee8ca
-  I 2:b1ad1b6bcc5c
-  G 1:37f42ae8b45e
+    14:cbf2f3105bbf
+    13:e07efca37c43
+  B 12:98c6b56349c0
+  B 11:03f491376e63
+  B 10:c012b15e2409
+  U 9:2197c557e14c
+  U 8:e74a86251f58
+  S 7:a5f87041c899
+  G 6:7d997bedcd8d
+  G 5:2dd1875f1028
+  G 4:2a1daef14cd4
+  I 3:8417d459b90c
+  I 2:e1355ee1f23e
+  G 1:ce7c85e06a9f
   G 0:b4e73ffab476
--- a/tests/test-bookmarks-pushpull.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-bookmarks-pushpull.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,5 @@
+  $ "$TESTDIR/hghave" serve || exit 80
+
 initialize
 
   $ hg init a
--- a/tests/test-check-code.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-check-code.t	Thu Nov 17 16:53:17 2011 -0600
@@ -132,3 +132,11 @@
    object comparison with literal
   [1]
 
+  $ cat > warning.py <<EOF
+  > except:
+  > EOF
+  $ "$check_code" warning.py --warning --nolineno
+  warning.py:0:
+   > except:
+   warning: naked except clause
+  [1]
--- a/tests/test-clone-failure.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-clone-failure.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,5 @@
+  $ "$TESTDIR/hghave" unix-permissions || exit 80
+
 No local source
 
   $ hg clone a b
--- a/tests/test-clone-pull-corruption.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-clone-pull-corruption.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,5 @@
+  $ "$TESTDIR/hghave" system-sh || exit 80
+
 Corrupt an hg repo with a pull started during an aborted commit
 Create two repos, so that one of them can pull from the other one.
 
--- a/tests/test-command-template.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-command-template.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,5 @@
+  $ "$TESTDIR/hghave" unix-permissions || exit 80
+
   $ hg init a
   $ cd a
   $ echo a > a
--- a/tests/test-commit-unresolved.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-commit-unresolved.t	Thu Nov 17 16:53:17 2011 -0600
@@ -29,7 +29,7 @@
   $ hg merge
   merging A
   warning: conflicts during merge.
-  merging A failed!
+  merging A incomplete! (edit conflicts, then use 'hg resolve --mark')
   1 files updated, 0 files merged, 0 files removed, 1 files unresolved
   use 'hg resolve' to retry unresolved file merges or 'hg update -C .' to abandon
   [1]
--- a/tests/test-commit.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-commit.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,5 @@
+  $ "$TESTDIR/hghave" symlink || exit 80
+
 commit date test
 
   $ hg init test
@@ -43,7 +45,7 @@
   $ mkdir dir
   $ echo boo > dir/file
   $ hg add
-  adding dir/file
+  adding dir/file (glob)
   $ hg -v commit -m commit-9 dir
   dir/file
   committed changeset 2:d2a76177cb42
@@ -113,8 +115,8 @@
   $ mkdir bar
   $ echo bar > bar/bar
   $ hg add
-  adding bar/bar
-  adding foo/foo
+  adding bar/bar (glob)
+  adding foo/foo (glob)
   $ hg ci -m commit-subdir-1 foo
   $ hg ci -m commit-subdir-2 bar
 
--- a/tests/test-conflict.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-conflict.t	Thu Nov 17 16:53:17 2011 -0600
@@ -13,7 +13,7 @@
   $ hg merge 1
   merging a
   warning: conflicts during merge.
-  merging a failed!
+  merging a incomplete! (edit conflicts, then use 'hg resolve --mark')
   0 files updated, 0 files merged, 0 files removed, 1 files unresolved
   use 'hg resolve' to retry unresolved file merges or 'hg update -C .' to abandon
   [1]
--- a/tests/test-contrib.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-contrib.t	Thu Nov 17 16:53:17 2011 -0600
@@ -107,7 +107,7 @@
 Test shrink-revlog:
   $ cd repo-a
   $ hg --config extensions.shrink=$CONTRIBDIR/shrink-revlog.py shrink
-  shrinking $TESTTMP/repo-a/.hg/store/00manifest.i
+  shrinking $TESTTMP/repo-a/.hg/store/00manifest.i (glob)
   reading revs
   sorting revs
   writing revs
@@ -115,8 +115,8 @@
   new file size:          324 bytes (   0.0 MiB)
   shrinkage: 0.0% (1.0x)
   note: old revlog saved in:
-    $TESTTMP/repo-a/.hg/store/00manifest.i.old
-    $TESTTMP/repo-a/.hg/store/00manifest.d.old
+    $TESTTMP/repo-a/.hg/store/00manifest.i.old (glob)
+    $TESTTMP/repo-a/.hg/store/00manifest.d.old (glob)
   (You can delete those files when you are satisfied that your
   repository is still sane.  Running 'hg verify' is strongly recommended.)
   $ hg verify
--- a/tests/test-convert-authormap.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-convert-authormap.t	Thu Nov 17 16:53:17 2011 -0600
@@ -27,7 +27,7 @@
   sorting...
   converting...
   0 foo
-  Writing author map file $TESTTMP/new/.hg/authormap
+  Writing author map file $TESTTMP/new/.hg/authormap (glob)
   $ cat new/.hg/authormap
   user name=Long User Name
   $ hg -Rnew log
@@ -44,7 +44,7 @@
   $ hg init new
   $ mv authormap.txt new/.hg/authormap
   $ hg convert orig new
-  Ignoring bad line in author map file $TESTTMP/new/.hg/authormap: this line is ignored
+  Ignoring bad line in author map file $TESTTMP/new/.hg/authormap: this line is ignored (glob)
   scanning source...
   sorting...
   converting...
--- a/tests/test-convert-bzr.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-convert-bzr.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,4 @@
+  $ "$TESTDIR/hghave" symlink execbit || exit 80
 
   $ . "$TESTDIR/bzr-definitions"
 
--- a/tests/test-convert-hg-source.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-convert-hg-source.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,4 @@
+  $ "$TESTDIR/hghave" execbit || exit 80
 
   $ cat >> $HGRCPATH <<EOF
   > [extensions]
--- a/tests/test-convert-svn-sink.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-convert-svn-sink.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,5 +1,4 @@
-
-  $ "$TESTDIR/hghave" svn13 no-outer-repo || exit 80
+  $ "$TESTDIR/hghave" svn13 no-outer-repo symlink execbit || exit 80
 
   $ fixpath()
   > {
@@ -417,7 +416,7 @@
   $ hg --cwd b merge
   merging b
   warning: conflicts during merge.
-  merging b failed!
+  merging b incomplete! (edit conflicts, then use 'hg resolve --mark')
   2 files updated, 0 files merged, 0 files removed, 1 files unresolved
   use 'hg resolve' to retry unresolved file merges or 'hg update -C .' to abandon
   [1]
--- a/tests/test-convert-tla.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-convert-tla.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,5 +1,5 @@
 
-  $ "$TESTDIR/hghave" tla || exit 80
+  $ "$TESTDIR/hghave" tla symlink || exit 80
   $ tla my-id "mercurial <mercurial@selenic.com>"
   $ echo "[extensions]" >> $HGRCPATH
   $ echo "convert=" >> $HGRCPATH
--- a/tests/test-convert.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-convert.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,4 @@
+  $ "$TESTDIR/hghave" unix-permissions || exit 80
 
   $ cat >> $HGRCPATH <<EOF
   > [extensions]
--- a/tests/test-default-push.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-default-push.t	Thu Nov 17 16:53:17 2011 -0600
@@ -18,7 +18,7 @@
 Push should push to 'default' when 'default-push' not set:
 
   $ hg --cwd b push
-  pushing to $TESTTMP/a
+  pushing to $TESTTMP/a (glob)
   searching for changes
   adding changesets
   adding manifests
@@ -29,7 +29,7 @@
 
   $ echo 'default-push = ../c' >> b/.hg/hgrc
   $ hg --cwd b push
-  pushing to $TESTTMP/c
+  pushing to $TESTTMP/c (glob)
   searching for changes
   adding changesets
   adding manifests
--- a/tests/test-diff-color.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-diff-color.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,5 @@
+  $ "$TESTDIR/hghave" execbit || exit 80
+
 Setup
 
   $ echo "[color]" >> $HGRCPATH
@@ -74,7 +76,7 @@
 
 record
 
-  $ chmod 0755 a
+  $ chmod +x a
   $ hg record --color=always -m moda a <<EOF
   > y
   > y
--- a/tests/test-diff-upgrade.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-diff-upgrade.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,4 @@
+  $ "$TESTDIR/hghave" execbit || exit 80
 
   $ echo "[extensions]" >> $HGRCPATH
   $ echo "autodiff=$TESTDIR/autodiff.py" >> $HGRCPATH
--- a/tests/test-dirstate.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-dirstate.t	Thu Nov 17 16:53:17 2011 -0600
@@ -11,9 +11,9 @@
   adding a/b/c/d/y
   adding a/b/c/d/z
   $ hg mv a z
-  moving a/b/c/d/x to z/b/c/d/x
-  moving a/b/c/d/y to z/b/c/d/y
-  moving a/b/c/d/z to z/b/c/d/z
+  moving a/b/c/d/x to z/b/c/d/x (glob)
+  moving a/b/c/d/y to z/b/c/d/y (glob)
+  moving a/b/c/d/z to z/b/c/d/z (glob)
   $ cd ..
 
 Issue1790: dirstate entry locked into unset if file mtime is set into
--- a/tests/test-eol.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-eol.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,5 @@
+  $ "$TESTDIR/hghave" unix-permissions || exit 80
+
 Test EOL extension
 
   $ cat >> $HGRCPATH <<EOF
--- a/tests/test-extdiff.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-extdiff.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,5 @@
+  $ "$TESTDIR/hghave" symlink execbit || exit 80
+
   $ echo "[extensions]" >> $HGRCPATH
   $ echo "extdiff=" >> $HGRCPATH
 
--- a/tests/test-extension.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-extension.t	Thu Nov 17 16:53:17 2011 -0600
@@ -473,7 +473,7 @@
   > cmdtable = None
   > EOF
   $ hg --config extensions.path=./path.py help foo > /dev/null
-  warning: error finding commands in $TESTTMP/hgext/forest.py
+  warning: error finding commands in $TESTTMP/hgext/forest.py (glob)
   hg: unknown command 'foo'
-  warning: error finding commands in $TESTTMP/hgext/forest.py
+  warning: error finding commands in $TESTTMP/hgext/forest.py (glob)
   [255]
--- a/tests/test-fetch.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-fetch.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,5 @@
+  $ "$TESTDIR/hghave" serve || exit 80
+
   $ echo "[extensions]" >> $HGRCPATH
   $ echo "fetch=" >> $HGRCPATH
 
--- a/tests/test-flags.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-flags.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,5 @@
+  $ "$TESTDIR/hghave" execbit || exit 80
+
   $ umask 027
 
   $ hg init test1
--- a/tests/test-fncache.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-fncache.t	Thu Nov 17 16:53:17 2011 -0600
@@ -14,7 +14,7 @@
   $ mkdir a.i
   $ echo "some other text" > a.i/b
   $ hg add
-  adding a.i/b
+  adding a.i/b (glob)
   $ hg ci -m second
   $ cat .hg/store/fncache | sort
   data/a.i
@@ -25,7 +25,7 @@
   $ mkdir a.i.hg
   $ echo "yet another text" > a.i.hg/c
   $ hg add
-  adding a.i.hg/c
+  adding a.i.hg/c (glob)
   $ hg ci -m third
   $ cat .hg/store/fncache | sort
   data/a.i
@@ -74,12 +74,14 @@
   .hg/data/tst.d.hg/foo.i
   .hg/dirstate
   .hg/last-message.txt
+  .hg/phaseroots
   .hg/requires
   .hg/undo
   .hg/undo.bookmarks
   .hg/undo.branch
   .hg/undo.desc
   .hg/undo.dirstate
+  .hg/undo.phaseroots
   $ cd ..
 
 Non fncache repo:
@@ -102,7 +104,9 @@
   .hg/store/data
   .hg/store/data/tst.d.hg
   .hg/store/data/tst.d.hg/_foo.i
+  .hg/store/phaseroots
   .hg/store/undo
+  .hg/store/undo.phaseroots
   .hg/undo.bookmarks
   .hg/undo.branch
   .hg/undo.desc
--- a/tests/test-getbundle.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-getbundle.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,4 @@
+  $ "$TESTDIR/hghave" serve || exit 80
 
 = Test the getbundle() protocol function =
 
--- a/tests/test-git-export.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-git-export.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,5 @@
+  $ "$TESTDIR/hghave" execbit || exit 80
+
   $ hg init
   $ echo start > start
   $ hg ci -Amstart
--- a/tests/test-graft.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-graft.t	Thu Nov 17 16:53:17 2011 -0600
@@ -151,7 +151,7 @@
   merging e
   my e@77eb504366ab+ other e@9c233e8e184d ancestor e@68795b066622
   warning: conflicts during merge.
-  merging e failed!
+  merging e incomplete! (edit conflicts, then use 'hg resolve --mark')
     searching for copies back to rev 1
     unmatched files in local:
      c
--- a/tests/test-hardlinks.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-hardlinks.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,5 @@
+  $ "$TESTDIR/hghave" no-windows || exit 80
+
   $ cat > nlinks.py <<EOF
   > import os, sys
   > for f in sorted(sys.stdin.readlines()):
@@ -45,7 +47,9 @@
   1 r1/.hg/store/data/d1/f2.i
   1 r1/.hg/store/data/f1.i
   1 r1/.hg/store/fncache
+  1 r1/.hg/store/phaseroots
   1 r1/.hg/store/undo
+  1 r1/.hg/store/undo.phaseroots
 
 
 Create hardlinked clone r2:
@@ -73,7 +77,9 @@
   2 r1/.hg/store/data/d1/f2.i
   2 r1/.hg/store/data/f1.i
   2 r1/.hg/store/fncache
+  1 r1/.hg/store/phaseroots
   1 r1/.hg/store/undo
+  1 r1/.hg/store/undo.phaseroots
 
   $ nlinksdir r2/.hg/store
   2 r2/.hg/store/00changelog.i
@@ -91,6 +97,7 @@
   1 r3/.hg/store/data/f1.i
   1 r3/.hg/store/fncache
   1 r3/.hg/store/undo
+  1 r3/.hg/store/undo.phaseroots
 
 
 Create a non-inlined filelog in r3:
@@ -110,7 +117,9 @@
   1 r3/.hg/store/data/d1/f2.i
   1 r3/.hg/store/data/f1.i
   1 r3/.hg/store/fncache
+  1 r3/.hg/store/phaseroots
   1 r3/.hg/store/undo
+  1 r3/.hg/store/undo.phaseroots
 
 Push to repo r1 should break up most hardlinks in r2:
 
@@ -193,7 +202,9 @@
   2 r4/.hg/store/data/d1/f2.i
   2 r4/.hg/store/data/f1.i
   2 r4/.hg/store/fncache
+  2 r4/.hg/store/phaseroots
   2 r4/.hg/store/undo
+  2 r4/.hg/store/undo.phaseroots
   2 r4/.hg/undo.bookmarks
   2 r4/.hg/undo.branch
   2 r4/.hg/undo.desc
@@ -222,7 +233,9 @@
   2 r4/.hg/store/data/d1/f2.i
   2 r4/.hg/store/data/f1.i
   2 r4/.hg/store/fncache
+  2 r4/.hg/store/phaseroots
   2 r4/.hg/store/undo
+  2 r4/.hg/store/undo.phaseroots
   2 r4/.hg/undo.bookmarks
   2 r4/.hg/undo.branch
   2 r4/.hg/undo.desc
--- a/tests/test-hgignore.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-hgignore.t	Thu Nov 17 16:53:17 2011 -0600
@@ -44,7 +44,7 @@
 
   $ echo "*.o" > .hgignore
   $ hg status
-  abort: $TESTTMP/.hgignore: invalid pattern (relre): *.o
+  abort: $TESTTMP/.hgignore: invalid pattern (relre): *.o (glob)
   [255]
 
   $ echo ".*\.o" > .hgignore
@@ -88,7 +88,7 @@
 
   $ echo "syntax: invalid" > .hgignore
   $ hg status
-  $TESTTMP/.hgignore: ignoring invalid syntax 'invalid'
+  $TESTTMP/.hgignore: ignoring invalid syntax 'invalid' (glob)
   A dir/b.o
   ? .hgignore
   ? a.c
--- a/tests/test-hgrc.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-hgrc.t	Thu Nov 17 16:53:17 2011 -0600
@@ -26,12 +26,12 @@
   $ cd foobar
   $ cat .hg/hgrc
   [paths]
-  default = $TESTTMP/foo%bar
+  default = $TESTTMP/foo%bar (glob)
   $ hg paths
-  default = $TESTTMP/foo%bar
+  default = $TESTTMP/foo%bar (glob)
   $ hg showconfig
-  bundle.mainreporoot=$TESTTMP/foobar
-  paths.default=$TESTTMP/foo%bar
+  bundle.mainreporoot=$TESTTMP/foobar (glob)
+  paths.default=$TESTTMP/foo%bar (glob)
   $ cd ..
 
 issue1829: wrong indentation
--- a/tests/test-hgweb-commands.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-hgweb-commands.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,5 @@
+  $ "$TESTDIR/hghave" serve || exit 80
+
 An attempt at more fully testing the hgweb web interface.
 The following things are tested elsewhere and are therefore omitted:
 - archive, tested in test-archive
--- a/tests/test-hgweb-descend-empties.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-hgweb-descend-empties.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,5 @@
+  $ "$TESTDIR/hghave" serve || exit 80
+
 Test chains of near empty directories, terminating 3 different ways:
 - a1: file at level 4 (deepest)
 - b1: two dirs at level 3
--- a/tests/test-hgweb-diffs.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-hgweb-diffs.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,5 @@
+  $ "$TESTDIR/hghave" serve execbit || exit 80
+
 setting up repo
 
   $ hg init test
@@ -10,7 +12,7 @@
 
 change permissions for git diffs
 
-  $ chmod 755 a
+  $ chmod +x a
   $ hg ci -Amb
 
 set up hgweb
--- a/tests/test-hgweb-empty.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-hgweb-empty.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,5 @@
+  $ "$TESTDIR/hghave" serve || exit 80
+
 Some tests for hgweb in an empty repository
 
   $ hg init test
--- a/tests/test-hgweb-filelog.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-hgweb-filelog.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,4 @@
+  $ "$TESTDIR/hghave" serve || exit 80
 
   $ hg init test
   $ cd test
--- a/tests/test-hgweb-raw.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-hgweb-raw.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,5 @@
+  $ "$TESTDIR/hghave" serve || exit 80
+
 Test raw style of hgweb
 
   $ hg init test
--- a/tests/test-hgweb-removed.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-hgweb-removed.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,5 @@
+  $ "$TESTDIR/hghave" serve || exit 80
+
 setting up repo
 
   $ hg init test
--- a/tests/test-hgweb.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-hgweb.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,5 @@
+  $ "$TESTDIR/hghave" serve || exit 80
+
 Some tests for hgweb. Tests static files, plain files and different 404's.
 
   $ hg init test
--- a/tests/test-hgwebdir.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-hgwebdir.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,5 @@
+  $ "$TESTDIR/hghave" serve || exit 80
+
 Tests some basic hgwebdir functionality. Tests setting up paths and
 collection, different forms of 404s and the subdirectory support.
 
--- a/tests/test-hgwebdirsym.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-hgwebdirsym.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,6 +1,6 @@
 Tests whether or not hgwebdir properly handles various symlink topologies.
 
-  $ "$TESTDIR/hghave" symlink || exit 80
+  $ "$TESTDIR/hghave" serve symlink || exit 80
   $ hg init a
   $ echo a > a/a
   $ hg --cwd a ci -Ama -d'1 0'
--- a/tests/test-highlight.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-highlight.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,5 +1,5 @@
 
-  $ "$TESTDIR/hghave" pygments || exit 80
+  $ "$TESTDIR/hghave" pygments serve || exit 80
   $ cat <<EOF >> $HGRCPATH
   > [extensions]
   > highlight =
--- a/tests/test-hook.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-hook.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,5 @@
+  $ "$TESTDIR/hghave" system-sh || exit 80
+
 commit hooks can see env vars
 
   $ hg init a
--- a/tests/test-http-branchmap.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-http-branchmap.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,4 @@
+  $ "$TESTDIR/hghave" serve || exit 80
 
   $ hgserve() {
   >     hg serve -a localhost -p $HGPORT1 -d --pid-file=hg.pid -E errors.log -v $@
--- a/tests/test-http-clone-r.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-http-clone-r.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,5 @@
+  $ "$TESTDIR/hghave" serve || exit 80
+
 creating 'remote
 
   $ hg init remote
--- a/tests/test-http-proxy.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-http-proxy.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,4 @@
+  $ "$TESTDIR/hghave" serve || exit 80
 
   $ hg init a
   $ cd a
--- a/tests/test-http.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-http.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,4 @@
+  $ "$TESTDIR/hghave" serve || exit 80
 
   $ hg init test
   $ cd test
--- a/tests/test-https.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-https.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,6 +1,6 @@
 Proper https client requires the built-in ssl from Python 2.6.
 
-  $ "$TESTDIR/hghave" ssl || exit 80
+  $ "$TESTDIR/hghave" serve ssl || exit 80
 
 Certificates created with:
  printf '.\n.\n.\n.\n.\nlocalhost\nhg@localhost\n' | \
--- a/tests/test-hup.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-hup.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,6 +1,6 @@
 Test hangup signal in the middle of transaction
 
-  $ "$TESTDIR/hghave" fifo || exit 80
+  $ "$TESTDIR/hghave" serve fifo || exit 80
   $ hg init
   $ mkfifo p
   $ hg serve --stdio < p &
@@ -17,4 +17,4 @@
   rollback completed
   killed!
   $ echo .hg/* .hg/store/*
-  .hg/00changelog.i .hg/journal.bookmarks .hg/journal.branch .hg/journal.desc .hg/journal.dirstate .hg/requires .hg/store .hg/store/00changelog.i .hg/store/00changelog.i.a
+  .hg/00changelog.i .hg/journal.bookmarks .hg/journal.branch .hg/journal.desc .hg/journal.dirstate .hg/requires .hg/store .hg/store/00changelog.i .hg/store/00changelog.i.a .hg/store/journal.phaseroots
--- a/tests/test-identify.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-identify.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,4 +1,4 @@
-  $ "$TESTDIR/hghave" no-outer-repo || exit 80
+  $ "$TESTDIR/hghave" no-outer-repo serve || exit 80
 
 no repo
 
--- a/tests/test-import-bypass.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-import-bypass.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,5 @@
+  $ "$TESTDIR/hghave" symlink execbit || exit 80
+
   $ echo "[extensions]" >> $HGRCPATH
   $ echo "purge=" >> $HGRCPATH
   $ echo "graphlog=" >> $HGRCPATH
--- a/tests/test-import-git.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-import-git.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,4 @@
+  $ "$TESTDIR/hghave" symlink || exit 80
 
   $ hg init
 
--- a/tests/test-incoming-outgoing.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-incoming-outgoing.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,5 @@
+  $ "$TESTDIR/hghave" serve || exit 80
+
   $ hg init test
   $ cd test
   $ for i in 0 1 2 3 4 5 6 7 8; do
--- a/tests/test-inherit-mode.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-inherit-mode.t	Thu Nov 17 16:53:17 2011 -0600
@@ -76,7 +76,9 @@
   00660 ./.hg/store/data/dir/bar.i
   00660 ./.hg/store/data/foo.i
   00660 ./.hg/store/fncache
+  00660 ./.hg/store/phaseroots
   00660 ./.hg/store/undo
+  00660 ./.hg/store/undo.phaseroots
   00660 ./.hg/undo.bookmarks
   00660 ./.hg/undo.branch
   00660 ./.hg/undo.desc
@@ -118,6 +120,7 @@
   00660 ../push/.hg/store/data/foo.i
   00660 ../push/.hg/store/fncache
   00660 ../push/.hg/store/undo
+  00660 ../push/.hg/store/undo.phaseroots
   00660 ../push/.hg/undo.bookmarks
   00660 ../push/.hg/undo.branch
   00660 ../push/.hg/undo.desc
--- a/tests/test-init.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-init.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,5 @@
+  $ "$TESTDIR/hghave" no-windows || exit 80
+
 This test tries to exercise the ssh functionality with a dummy script
 
   $ checknewrepo()
--- a/tests/test-install.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-install.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,8 +1,8 @@
 hg debuginstall
   $ hg debuginstall
   Checking encoding (ascii)...
-  Checking installed modules (*/mercurial)... (glob)
-  Checking templates (*/mercurial/templates)... (glob)
+  Checking installed modules (*mercurial)... (glob)
+  Checking templates (*mercurial?templates)... (glob)
   Checking commit editor...
   Checking username...
   No problems detected
@@ -10,8 +10,8 @@
 hg debuginstall with no username
   $ HGUSER= hg debuginstall
   Checking encoding (ascii)...
-  Checking installed modules (*/mercurial)... (glob)
-  Checking templates (*/mercurial/templates)... (glob)
+  Checking installed modules (*mercurial)... (glob)
+  Checking templates (*mercurial?templates)... (glob)
   Checking commit editor...
   Checking username...
    no username supplied (see "hg help config")
--- a/tests/test-interhg.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-interhg.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,5 @@
+  $ "$TESTDIR/hghave" serve || exit 80
+
   $ hg init test
   $ cd test
 
--- a/tests/test-issue1089.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-issue1089.t	Thu Nov 17 16:53:17 2011 -0600
@@ -7,7 +7,7 @@
   adding a/b
 
   $ hg rm a
-  removing a/b
+  removing a/b (glob)
   $ hg ci -m m a
 
   $ mkdir a b
@@ -16,7 +16,7 @@
   adding a/b
 
   $ hg rm a
-  removing a/b
+  removing a/b (glob)
   $ cd b
 
 Relative delete:
--- a/tests/test-issue1502.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-issue1502.t	Thu Nov 17 16:53:17 2011 -0600
@@ -13,7 +13,7 @@
   $ echo "bar" > foo1/a && hg -R foo1 commit -m "edit a in foo1"
   $ echo "hi" > foo/a && hg -R foo commit -m "edited a foo"
   $ hg -R foo1 pull -u
-  pulling from $TESTTMP/foo
+  pulling from $TESTTMP/foo (glob)
   searching for changes
   adding changesets
   adding manifests
@@ -29,7 +29,7 @@
 
   $ echo "there" >> foo/a && hg -R foo commit -m "edited a again"
   $ hg -R foo1 pull
-  pulling from $TESTTMP/foo
+  pulling from $TESTTMP/foo (glob)
   searching for changes
   adding changesets
   adding manifests
--- a/tests/test-issue1802.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-issue1802.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,5 @@
+  $ "$TESTDIR/hghave" execbit || exit 80
+
 Create extension that can disable exec checks:
 
   $ cat > noexec.py <<EOF
--- a/tests/test-issue612.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-issue612.t	Thu Nov 17 16:53:17 2011 -0600
@@ -7,7 +7,7 @@
   adding src/a.c
 
   $ hg mv src source
-  moving src/a.c to source/a.c
+  moving src/a.c to source/a.c (glob)
 
   $ hg ci -Ammove
 
--- a/tests/test-issue660.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-issue660.t	Thu Nov 17 16:53:17 2011 -0600
@@ -67,9 +67,9 @@
 
   $ hg revert --all
   undeleting a
-  forgetting a/a
+  forgetting a/a (glob)
   forgetting b
-  undeleting b/b
+  undeleting b/b (glob)
 
   $ hg st
 
--- a/tests/test-journal-exists.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-journal-exists.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,5 @@
+  $ "$TESTDIR/hghave" unix-permissions || exit 80
+
   $ hg init
   $ echo a > a
   $ hg ci -Am0
--- a/tests/test-keyword.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-keyword.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,5 @@
+  $ "$TESTDIR/hghave" symlink unix-permissions serve || exit 80
+
   $ cat <<EOF >> $HGRCPATH
   > [extensions]
   > keyword =
@@ -208,7 +210,7 @@
   Message-Id: <hg.a2392c293916*> (glob)
   To: Test
   
-  changeset a2392c293916 in $TESTTMP/Test
+  changeset a2392c293916 in $TESTTMP/Test (glob)
   details: $TESTTMP/Test?cmd=changeset;node=a2392c293916
   description:
   	addsym
@@ -231,7 +233,7 @@
   Message-Id: <hg.ef63ca68695b*> (glob)
   To: Test
   
-  changeset ef63ca68695b in $TESTTMP/Test
+  changeset ef63ca68695b in $TESTTMP/Test (glob)
   details: $TESTTMP/Test?cmd=changeset;node=ef63ca68695b
   description:
   	absym
@@ -797,7 +799,7 @@
   > default = ../Test
   > EOF
   $ hg incoming
-  comparing with $TESTTMP/Test
+  comparing with $TESTTMP/Test (glob)
   searching for changes
   changeset:   2:bb948857c743
   tag:         tip
@@ -974,7 +976,7 @@
   $ hg merge
   merging m
   warning: conflicts during merge.
-  merging m failed!
+  merging m incomplete! (edit conflicts, then use 'hg resolve --mark')
   0 files updated, 0 files merged, 0 files removed, 1 files unresolved
   use 'hg resolve' to retry unresolved file merges or 'hg update -C .' to abandon
   [1]
--- a/tests/test-known.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-known.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,4 @@
+  $ "$TESTDIR/hghave" serve || exit 80
 
 = Test the known() protocol function =
 
--- a/tests/test-largefiles.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-largefiles.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,5 @@
+  $ "$TESTDIR/hghave" symlink unix-permissions serve || exit 80
+
   $ cat >> $HGRCPATH <<EOF
   > [extensions]
   > largefiles=
@@ -183,8 +185,8 @@
   $ echo large6 > sub2/large6
   $ echo large7 > sub2/large7
   $ hg add --large sub2
-  adding sub2/large6 as a largefile
-  adding sub2/large7 as a largefile
+  adding sub2/large6 as a largefile (glob)
+  adding sub2/large7 as a largefile (glob)
   $ hg st
   M large3
   A large5
@@ -348,7 +350,7 @@
   added 1 changesets with 2 changes to 2 files (+1 heads)
   getting changed largefiles
   1 largefiles updated, 0 removed
-  saved backup bundle to $TESTTMP/d/.hg/strip-backup/f574fb32bb45-backup.hg
+  saved backup bundle to $TESTTMP/d/.hg/strip-backup/f574fb32bb45-backup.hg (glob)
   nothing to rebase
   $ hg log --template '{rev}:{node|short}  {desc|firstline}\n'
   9:598410d3eb9a  modify normal file largefile in repo d
@@ -383,7 +385,7 @@
   $ hg rebase
   getting changed largefiles
   1 largefiles updated, 0 removed
-  saved backup bundle to $TESTTMP/e/.hg/strip-backup/f574fb32bb45-backup.hg
+  saved backup bundle to $TESTTMP/e/.hg/strip-backup/f574fb32bb45-backup.hg (glob)
   $ hg log
   changeset:   9:598410d3eb9a
   tag:         tip
@@ -553,8 +555,8 @@
 # XXX we don't really want to report that we're reverting the standin;
 # that's just an implementation detail. But I don't see an obvious fix. ;-(
   $ hg revert sub
-  reverting .hglf/sub/large4
-  reverting sub/normal4
+  reverting .hglf/sub/large4 (glob)
+  reverting sub/normal4 (glob)
   $ hg status
   M normal3
   A sub2/large8
@@ -566,8 +568,8 @@
   $ cat sub/large4
   large4-modified
   $ hg revert -a --no-backup
-  undeleting .hglf/sub2/large6
-  forgetting .hglf/sub2/large8
+  undeleting .hglf/sub2/large6 (glob)
+  forgetting .hglf/sub2/large8 (glob)
   reverting normal3
   $ hg status
   ? sub/large4.orig
@@ -581,11 +583,11 @@
 
 revert some files to an older revision
   $ hg revert --no-backup -r 8 sub2
-  reverting .hglf/sub2/large6
+  reverting .hglf/sub2/large6 (glob)
   $ cat sub2/large6
   large6
   $ hg revert --no-backup sub2
-  reverting .hglf/sub2/large6
+  reverting .hglf/sub2/large6 (glob)
   $ hg status
 
 "verify --large" actually verifies largefiles
--- a/tests/test-lfconvert.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-lfconvert.t	Thu Nov 17 16:53:17 2011 -0600
@@ -83,8 +83,8 @@
   $ hg commit -q -m"remove large, normal3"
   $ hg merge
   merging sub/maybelarge.dat and stuff/maybelarge.dat to stuff/maybelarge.dat
-  warning: $TESTTMP/bigfile-repo/stuff/maybelarge.dat looks like a binary file.
-  merging stuff/maybelarge.dat failed!
+  warning: $TESTTMP/bigfile-repo/stuff/maybelarge.dat looks like a binary file. (glob)
+  merging stuff/maybelarge.dat incomplete! (edit conflicts, then use 'hg resolve --mark')
   merging sub/normal2 and stuff/normal2 to stuff/normal2
   0 files updated, 1 files merged, 0 files removed, 1 files unresolved
   use 'hg resolve' to retry unresolved file merges or 'hg update -C .' to abandon
@@ -170,7 +170,7 @@
   $ hg share -q -U bigfile-repo shared
   $ printf 'bogus' > shared/.hg/sharedpath
   $ hg lfconvert shared foo
-  abort: .hg/sharedpath points to nonexistent directory $TESTTMP/bogus!
+  abort: .hg/sharedpath points to nonexistent directory $TESTTMP/bogus! (glob)
   [255]
   $ hg lfconvert bigfile-repo largefiles-repo
   initializing destination largefiles-repo
--- a/tests/test-locate.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-locate.t	Thu Nov 17 16:53:17 2011 -0600
@@ -88,33 +88,33 @@
   $ rm -r t
 
   $ hg locate 't/**'
-  t/b
-  t/e.h
-  t/x
+  t/b (glob)
+  t/e.h (glob)
+  t/x (glob)
 
   $ mkdir otherdir
   $ cd otherdir
 
   $ hg locate b
-  ../b
-  ../t/b
+  ../b (glob)
+  ../t/b (glob)
   $ hg locate '*.h'
-  ../t.h
-  ../t/e.h
+  ../t.h (glob)
+  ../t/e.h (glob)
   $ hg locate path:t/x
-  ../t/x
+  ../t/x (glob)
   $ hg locate 're:.*\.h$'
-  ../t.h
-  ../t/e.h
+  ../t.h (glob)
+  ../t/e.h (glob)
   $ hg locate -r 0 b
-  ../b
-  ../t/b
+  ../b (glob)
+  ../t/b (glob)
   $ hg locate -r 0 '*.h'
-  ../t.h
-  ../t/e.h
+  ../t.h (glob)
+  ../t/e.h (glob)
   $ hg locate -r 0 path:t/x
-  ../t/x
+  ../t/x (glob)
   $ hg locate -r 0 're:.*\.h$'
-  ../t.h
-  ../t/e.h
+  ../t.h (glob)
+  ../t/e.h (glob)
 
--- a/tests/test-lock-badness.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-lock-badness.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,5 @@
+  $ "$TESTDIR/hghave" unix-permissions || exit 80
+
   $ hg init a
   $ echo a > a/a
   $ hg -R a ci -A -m a
--- a/tests/test-log.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-log.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,5 @@
+  $ "$TESTDIR/hghave" execbit || exit 80
+
   $ hg init a
 
   $ cd a
@@ -920,7 +922,7 @@
   $ hg merge 7
   merging foo
   warning: conflicts during merge.
-  merging foo failed!
+  merging foo incomplete! (edit conflicts, then use 'hg resolve --mark')
   0 files updated, 0 files merged, 0 files removed, 1 files unresolved
   use 'hg resolve' to retry unresolved file merges or 'hg update -C .' to abandon
   [1]
@@ -931,7 +933,7 @@
   $ hg merge 4
   merging foo
   warning: conflicts during merge.
-  merging foo failed!
+  merging foo incomplete! (edit conflicts, then use 'hg resolve --mark')
   1 files updated, 0 files merged, 0 files removed, 1 files unresolved
   use 'hg resolve' to retry unresolved file merges or 'hg update -C .' to abandon
   [1]
--- a/tests/test-manifest.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-manifest.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,5 @@
+  $ "$TESTDIR/hghave" symlink || exit 80
+
 Source bundle was generated with the following script:
 
 # hg init
--- a/tests/test-merge-local.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-merge-local.t	Thu Nov 17 16:53:17 2011 -0600
@@ -63,7 +63,7 @@
   merging zzz1_merge_ok
   merging zzz2_merge_bad
   warning: conflicts during merge.
-  merging zzz2_merge_bad failed!
+  merging zzz2_merge_bad incomplete! (edit conflicts, then use 'hg resolve --mark')
   2 files updated, 1 files merged, 3 files removed, 1 files unresolved
   use 'hg resolve' to retry unresolved file merges
   [1]
@@ -88,7 +88,7 @@
   merging zzz1_merge_ok
   merging zzz2_merge_bad
   warning: conflicts during merge.
-  merging zzz2_merge_bad failed!
+  merging zzz2_merge_bad incomplete! (edit conflicts, then use 'hg resolve --mark')
   3 files updated, 1 files merged, 2 files removed, 1 files unresolved
   use 'hg resolve' to retry unresolved file merges
   [1]
@@ -97,7 +97,7 @@
   merging zzz1_merge_ok
   merging zzz2_merge_bad
   warning: conflicts during merge.
-  merging zzz2_merge_bad failed!
+  merging zzz2_merge_bad incomplete! (edit conflicts, then use 'hg resolve --mark')
   2 files updated, 1 files merged, 3 files removed, 1 files unresolved
   use 'hg resolve' to retry unresolved file merges
   [1]
--- a/tests/test-merge-revert2.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-merge-revert2.t	Thu Nov 17 16:53:17 2011 -0600
@@ -45,7 +45,7 @@
   $ hg update
   merging file1
   warning: conflicts during merge.
-  merging file1 failed!
+  merging file1 incomplete! (edit conflicts, then use 'hg resolve --mark')
   0 files updated, 0 files merged, 0 files removed, 1 files unresolved
   use 'hg resolve' to retry unresolved file merges
   [1]
--- a/tests/test-merge-symlinks.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-merge-symlinks.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,4 @@
+  $ "$TESTDIR/hghave" symlink || exit 80
 
   $ cat > echo.py <<EOF
   > #!/usr/bin/env python
--- a/tests/test-merge-tools.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-merge-tools.t	Thu Nov 17 16:53:17 2011 -0600
@@ -66,7 +66,7 @@
   $ PATH="$BINDIR" $PYTHON "$BINDIR"/hg merge -r 2
   merging f
   warning: conflicts during merge.
-  merging f failed!
+  merging f incomplete! (edit conflicts, then use 'hg resolve --mark')
   0 files updated, 0 files merged, 0 files removed, 1 files unresolved
   use 'hg resolve' to retry unresolved file merges or 'hg update -C .' to abandon
   [1]
--- a/tests/test-merge-types.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-merge-types.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,5 @@
+  $ "$TESTDIR/hghave" symlink execbit || exit 80
+
   $ hg init
 
   $ echo a > a
--- a/tests/test-merge7.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-merge7.t	Thu Nov 17 16:53:17 2011 -0600
@@ -45,7 +45,7 @@
   $ hg merge
   merging test.txt
   warning: conflicts during merge.
-  merging test.txt failed!
+  merging test.txt incomplete! (edit conflicts, then use 'hg resolve --mark')
   0 files updated, 0 files merged, 0 files removed, 1 files unresolved
   use 'hg resolve' to retry unresolved file merges or 'hg update -C .' to abandon
   [1]
@@ -90,7 +90,7 @@
   merging test.txt
   my test.txt@50c3a7e29886+ other test.txt@40d11a4173a8 ancestor test.txt@96b70246a118
   warning: conflicts during merge.
-  merging test.txt failed!
+  merging test.txt incomplete! (edit conflicts, then use 'hg resolve --mark')
   0 files updated, 0 files merged, 0 files removed, 1 files unresolved
   use 'hg resolve' to retry unresolved file merges or 'hg update -C .' to abandon
   [1]
--- a/tests/test-merge9.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-merge9.t	Thu Nov 17 16:53:17 2011 -0600
@@ -83,7 +83,7 @@
   $ hg resolve -a
   merging bar
   warning: conflicts during merge.
-  merging bar failed!
+  merging bar incomplete! (edit conflicts, then use 'hg resolve --mark')
   [1]
 
 after
--- a/tests/test-mq-merge.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-mq-merge.t	Thu Nov 17 16:53:17 2011 -0600
@@ -56,7 +56,7 @@
 Save the patch queue so we can merge it later:
 
   $ hg qsave -c -e
-  copy $TESTTMP/t/.hg/patches to $TESTTMP/t/.hg/patches.1
+  copy $TESTTMP/t/.hg/patches to $TESTTMP/t/.hg/patches.1 (glob)
   $ checkundo
 
 Update b and commit in an "update" changeset:
@@ -76,7 +76,7 @@
   b
 
   $ hg qpush -a -m
-  merging with queue at: $TESTTMP/t/.hg/patches.1
+  merging with queue at: $TESTTMP/t/.hg/patches.1 (glob)
   applying rm_a
   now at: rm_a
 
@@ -115,14 +115,14 @@
 Create the reference queue:
 
   $ hg qsave -c -e -n refqueue
-  copy $TESTTMP/t2/.hg/patches to $TESTTMP/t2/.hg/refqueue
+  copy $TESTTMP/t2/.hg/patches to $TESTTMP/t2/.hg/refqueue (glob)
   $ hg up -C 1
   1 files updated, 0 files merged, 1 files removed, 0 files unresolved
 
 Merge:
 
   $ HGMERGE=internal:other hg qpush -a -m -n refqueue
-  merging with queue at: $TESTTMP/t2/.hg/refqueue
+  merging with queue at: $TESTTMP/t2/.hg/refqueue (glob)
   applying patcha
   patching file a
   Hunk #1 FAILED at 0
--- a/tests/test-mq-qclone-http.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-mq-qclone-http.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,4 @@
+  $ "$TESTDIR/hghave" serve || exit 80
 
   $ echo "[extensions]" >> $HGRCPATH
   $ echo "mq=" >> $HGRCPATH
--- a/tests/test-mq-qdelete.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-mq-qdelete.t	Thu Nov 17 16:53:17 2011 -0600
@@ -188,7 +188,9 @@
   $ echo > .hg/patches/series # remove 4.diff and 5.diff from series to confuse mq
   $ echo hup >>  base
   $ hg qnew -f -d '1 0' -m 6 6.diff
+  $ echo pup > base
   $ hg qfinish -a
+  warning: uncommitted changes in the working directory
   revision 2b1c98802260 refers to unknown patches: 5.diff
   revision 33a6861311c0 refers to unknown patches: 4.diff
 
--- a/tests/test-mq-qimport.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-mq-qimport.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,4 @@
+  $ "$TESTDIR/hghave" serve || exit 80
 
   $ cat > writelines.py <<EOF
   > import sys
--- a/tests/test-mq-qnew.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-mq-qnew.t	Thu Nov 17 16:53:17 2011 -0600
@@ -155,7 +155,7 @@
   created new head
   merging a
   warning: conflicts during merge.
-  merging a failed!
+  merging a incomplete! (edit conflicts, then use 'hg resolve --mark')
   0 files updated, 0 files merged, 0 files removed, 1 files unresolved
   use 'hg resolve' to retry unresolved file merges or 'hg update -C .' to abandon
   abort: cannot manage merge changesets
@@ -228,7 +228,7 @@
   created new head
   merging a
   warning: conflicts during merge.
-  merging a failed!
+  merging a incomplete! (edit conflicts, then use 'hg resolve --mark')
   0 files updated, 0 files merged, 0 files removed, 1 files unresolved
   use 'hg resolve' to retry unresolved file merges or 'hg update -C .' to abandon
   abort: cannot manage merge changesets
--- a/tests/test-mq-safety.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-mq-safety.t	Thu Nov 17 16:53:17 2011 -0600
@@ -39,7 +39,7 @@
   abort: popping would remove a revision not managed by this patch queue
   [255]
   $ hg qpop -n patches
-  using patch queue: $TESTTMP/repo/.hg/patches
+  using patch queue: $TESTTMP/repo/.hg/patches (glob)
   abort: popping would remove a revision not managed by this patch queue
   [255]
   $ hg qrefresh
--- a/tests/test-mq.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-mq.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,5 @@
+  $ "$TESTDIR/hghave" execbit || exit 80
+
   $ checkundo()
   > {
   >     if [ -f .hg/store/undo ]; then
@@ -135,7 +137,7 @@
   guards
   $ cat .hg/patches/series
   $ hg qinit -c
-  abort: repository $TESTTMP/d/.hg/patches already exists!
+  abort: repository $TESTTMP/d/.hg/patches already exists! (glob)
   [255]
   $ cd ..
 
@@ -154,8 +156,8 @@
   $ echo status >> .hg/patches/.hgignore
   $ echo bleh >> .hg/patches/.hgignore
   $ hg qinit -c
-  adding .hg/patches/A
-  adding .hg/patches/B
+  adding .hg/patches/A (glob)
+  adding .hg/patches/B (glob)
   $ hg -R .hg/patches status
   A .hgignore
   A A
@@ -1191,7 +1193,7 @@
 
   $ cd qclonesource
   $ hg qinit -c
-  adding .hg/patches/patch1
+  adding .hg/patches/patch1 (glob)
   $ hg qci -m checkpoint
   $ qlog
   main repo:
--- a/tests/test-mv-cp-st-diff.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-mv-cp-st-diff.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1138,7 +1138,7 @@
   updating to branch default
   3 files updated, 0 files merged, 0 files removed, 0 files unresolved
   created new head
-  moving x/x to y/x
+  moving x/x to y/x (glob)
   ** directory move **
   ** hg mv x y / add y/x x1 / add y/x x2
   - working to parent: 
--- a/tests/test-nested-repo.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-nested-repo.t	Thu Nov 17 16:53:17 2011 -0600
@@ -11,16 +11,16 @@
 Should fail:
 
   $ hg st b/x
-  abort: path 'b/x' is inside nested repo 'b'
+  abort: path 'b/x' is inside nested repo 'b' (glob)
   [255]
   $ hg add b/x
-  abort: path 'b/x' is inside nested repo 'b'
+  abort: path 'b/x' is inside nested repo 'b' (glob)
   [255]
 
 Should fail:
 
   $ hg add b b/x
-  abort: path 'b/x' is inside nested repo 'b'
+  abort: path 'b/x' is inside nested repo 'b' (glob)
   [255]
   $ hg st
 
@@ -34,7 +34,7 @@
 Should fail:
 
   $ hg mv a b
-  abort: path 'b/a' is inside nested repo 'b'
+  abort: path 'b/a' is inside nested repo 'b' (glob)
   [255]
   $ hg st
 
--- a/tests/test-notify-changegroup.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-notify-changegroup.t	Thu Nov 17 16:53:17 2011 -0600
@@ -56,11 +56,11 @@
   Message-Id: <*> (glob)
   To: baz, foo@bar
   
-  changeset cb9a9f314b8b in $TESTTMP/a
+  changeset cb9a9f314b8b in $TESTTMP/a (glob)
   details: $TESTTMP/a?cmd=changeset;node=cb9a9f314b8b
   summary: a
   
-  changeset ba677d0156c1 in $TESTTMP/a
+  changeset ba677d0156c1 in $TESTTMP/a (glob)
   details: $TESTTMP/a?cmd=changeset;node=ba677d0156c1
   summary: b
   
@@ -107,11 +107,11 @@
   Message-Id: <*> (glob)
   To: baz, foo@bar
   
-  changeset cb9a9f314b8b in $TESTTMP/a
+  changeset cb9a9f314b8b in $TESTTMP/a (glob)
   details: $TESTTMP/a?cmd=changeset;node=cb9a9f314b8b
   summary: a
   
-  changeset ba677d0156c1 in $TESTTMP/a
+  changeset ba677d0156c1 in $TESTTMP/a (glob)
   details: $TESTTMP/a?cmd=changeset;node=ba677d0156c1
   summary: b
   
--- a/tests/test-notify.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-notify.t	Thu Nov 17 16:53:17 2011 -0600
@@ -173,7 +173,7 @@
   Message-Id: <*> (glob)
   To: baz, foo@bar
   
-  changeset 0647d048b600 in $TESTTMP/b
+  changeset 0647d048b600 in $TESTTMP/b (glob)
   details: $TESTTMP/b?cmd=changeset;node=0647d048b600
   description: b
   
--- a/tests/test-paths.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-paths.t	Thu Nov 17 16:53:17 2011 -0600
@@ -7,29 +7,29 @@
   $ echo 'dupe = ../b' >> .hg/hgrc
   $ echo 'expand = $SOMETHING/bar' >> .hg/hgrc
   $ hg in dupe
-  comparing with $TESTTMP/b
+  comparing with $TESTTMP/b (glob)
   no changes found
   [1]
   $ cd ..
   $ hg -R a in dupe
-  comparing with $TESTTMP/b
+  comparing with $TESTTMP/b (glob)
   no changes found
   [1]
   $ cd a
   $ hg paths
-  dupe = $TESTTMP/b
-  expand = $TESTTMP/a/$SOMETHING/bar
+  dupe = $TESTTMP/b (glob)
+  expand = $TESTTMP/a/$SOMETHING/bar (glob)
   $ SOMETHING=foo hg paths
-  dupe = $TESTTMP/b
-  expand = $TESTTMP/a/foo/bar
+  dupe = $TESTTMP/b (glob)
+  expand = $TESTTMP/a/foo/bar (glob)
   $ SOMETHING=/foo hg paths
-  dupe = $TESTTMP/b
+  dupe = $TESTTMP/b (glob)
   expand = /foo/bar
   $ hg paths -q
   dupe
   expand
   $ hg paths dupe
-  $TESTTMP/b
+  $TESTTMP/b (glob)
   $ hg paths -q dupe
   $ hg paths unknown
   not found!
--- a/tests/test-permissions.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-permissions.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,5 @@
+  $ "$TESTDIR/hghave" unix-permissions || exit 80
+
   $ hg init t
   $ cd t
 
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/tests/test-phases-exchange.t	Thu Nov 17 16:53:17 2011 -0600
@@ -0,0 +1,112 @@
+  $ cat >> $HGRCPATH <<EOF
+  > [extensions]
+  > graphlog=
+  > EOF
+  $ alias hgph='hg log --template "{rev} {phase} {desc}\n"'
+
+  $ mkcommit() {
+  >    echo "$1" > "$1"
+  >    hg add "$1"
+  >    hg ci -m "$1"
+  > }
+
+  $ hg init alpha
+  $ cd alpha
+  $ mkcommit a-A
+  $ mkcommit a-B
+  $ mkcommit a-C
+  $ mkcommit a-D
+  $ hgph
+  3 1 a-D
+  2 1 a-C
+  1 1 a-B
+  0 1 a-A
+
+  $ hg init ../beta
+  $ hg push -r 1 ../beta
+  pushing to ../beta
+  searching for changes
+  adding changesets
+  adding manifests
+  adding file changes
+  added 2 changesets with 2 changes to 2 files
+  $ hgph
+  3 1 a-D
+  2 1 a-C
+  1 0 a-B
+  0 0 a-A
+
+  $ cd ../beta
+  $ hgph
+  1 0 a-B
+  0 0 a-A
+  $ hg up -q
+  $ mkcommit b-A
+  $ hgph
+  2 1 b-A
+  1 0 a-B
+  0 0 a-A
+  $ hg pull ../alpha
+  pulling from ../alpha
+  searching for changes
+  adding changesets
+  adding manifests
+  adding file changes
+  added 2 changesets with 2 changes to 2 files (+1 heads)
+  (run 'hg heads' to see heads, 'hg merge' to merge)
+  $ hgph
+  4 0 a-D
+  3 0 a-C
+  2 1 b-A
+  1 0 a-B
+  0 0 a-A
+
+pull did not updated ../alpha state.
+push from alpha to beta should update phase even if nothing is transfered
+
+  $ cd ../alpha
+  $ hgph # not updated by remote pull
+  3 1 a-D
+  2 1 a-C
+  1 0 a-B
+  0 0 a-A
+  $ hg push ../beta
+  pushing to ../beta
+  searching for changes
+  no changes found
+  $ hgph
+  3 0 a-D
+  2 0 a-C
+  1 0 a-B
+  0 0 a-A
+
+update must update phase of common changeset too
+
+  $ hg pull ../beta # getting b-A
+  pulling from ../beta
+  searching for changes
+  adding changesets
+  adding manifests
+  adding file changes
+  added 1 changesets with 1 changes to 1 files (+1 heads)
+  (run 'hg heads' to see heads, 'hg merge' to merge)
+
+  $ cd ../beta
+  $ hgph # not updated by remote pull
+  4 0 a-D
+  3 0 a-C
+  2 1 b-A
+  1 0 a-B
+  0 0 a-A
+  $ hg pull ../alpha
+  pulling from ../alpha
+  searching for changes
+  no changes found
+  $ hgph
+  4 0 a-D
+  3 0 a-C
+  2 0 b-A
+  1 0 a-B
+  0 0 a-A
+
+
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/tests/test-phases.t	Thu Nov 17 16:53:17 2011 -0600
@@ -0,0 +1,10 @@
+  $ alias hglog='hg log --template "{rev} {phase} {desc}\n"'
+
+  $ hg init initialrepo
+  $ cd initialrepo
+  $ touch sam
+  $ hg add sam
+  $ hg ci -m 'first'
+
+  $ hglog
+  0 1 first
--- a/tests/test-pull-http.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-pull-http.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,4 @@
+  $ "$TESTDIR/hghave" serve || exit 80
 
   $ hg init test
   $ cd test
--- a/tests/test-pull-r.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-pull-r.t	Thu Nov 17 16:53:17 2011 -0600
@@ -43,7 +43,7 @@
   2:effea6de0384
   1:ed1b79f46b9a
   $ hg pull
-  pulling from $TESTTMP/repo2
+  pulling from $TESTTMP/repo2 (glob)
   searching for changes
   adding changesets
   adding manifests
--- a/tests/test-pull.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-pull.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,5 @@
+  $ "$TESTDIR/hghave" serve || exit 80
+
   $ hg init test
   $ cd test
 
--- a/tests/test-push-http.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-push-http.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,4 @@
+  $ "$TESTDIR/hghave" serve || exit 80
 
   $ hg init test
   $ cd test
--- a/tests/test-push-validation.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-push-validation.t	Thu Nov 17 16:53:17 2011 -0600
@@ -40,7 +40,7 @@
 Expected to fail:
 
   $ hg push
-  pushing to $TESTTMP/test
+  pushing to $TESTTMP/test (glob)
   searching for changes
   adding changesets
   adding manifests
--- a/tests/test-rebase-abort.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-rebase-abort.t	Thu Nov 17 16:53:17 2011 -0600
@@ -49,7 +49,7 @@
   $ hg rebase -s 3 -d 2
   merging common
   warning: conflicts during merge.
-  merging common failed!
+  merging common incomplete! (edit conflicts, then use 'hg resolve --mark')
   abort: unresolved conflicts (see hg resolve, then hg rebase --continue)
   [255]
 
@@ -117,7 +117,7 @@
   $ hg rebase -b 4 -d 2
   merging c
   warning: conflicts during merge.
-  merging c failed!
+  merging c incomplete! (edit conflicts, then use 'hg resolve --mark')
   abort: unresolved conflicts (see hg resolve, then hg rebase --continue)
   [255]
 
--- a/tests/test-rebase-check-restore.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-rebase-check-restore.t	Thu Nov 17 16:53:17 2011 -0600
@@ -63,7 +63,7 @@
   $ hg rebase -s 1 -d 4 --keep
   merging A
   warning: conflicts during merge.
-  merging A failed!
+  merging A incomplete! (edit conflicts, then use 'hg resolve --mark')
   abort: unresolved conflicts (see hg resolve, then hg rebase --continue)
   [255]
 
@@ -115,7 +115,7 @@
   $ hg rebase -s 5 -d 4 --keepbranches
   merging A
   warning: conflicts during merge.
-  merging A failed!
+  merging A incomplete! (edit conflicts, then use 'hg resolve --mark')
   abort: unresolved conflicts (see hg resolve, then hg rebase --continue)
   [255]
 
--- a/tests/test-rebase-conflicts.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-rebase-conflicts.t	Thu Nov 17 16:53:17 2011 -0600
@@ -58,7 +58,7 @@
   $ hg rebase -s 3 -d 2
   merging common
   warning: conflicts during merge.
-  merging common failed!
+  merging common incomplete! (edit conflicts, then use 'hg resolve --mark')
   abort: unresolved conflicts (see hg resolve, then hg rebase --continue)
   [255]
 
--- a/tests/test-rebase-detach.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-rebase-detach.t	Thu Nov 17 16:53:17 2011 -0600
@@ -283,7 +283,7 @@
   
 
   $ hg rebase -d 5 -s 7
-  saved backup bundle to $TESTTMP/a5/.hg/strip-backup/13547172c9c0-backup.hg
+  saved backup bundle to $TESTTMP/a5/.hg/strip-backup/13547172c9c0-backup.hg (glob)
   $ hg tglog
   @  8: 'D'
   |
@@ -367,7 +367,7 @@
   $ hg rebase -s 8 -d 7 --detach --config ui.merge=internal:fail
   merging H
   warning: conflicts during merge.
-  merging H failed!
+  merging H incomplete! (edit conflicts, then use 'hg resolve --mark')
   abort: unresolved conflicts (see hg resolve, then hg rebase --continue)
   [255]
   $ hg resolve --all -t internal:local
--- a/tests/test-rebase-interruptions.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-rebase-interruptions.t	Thu Nov 17 16:53:17 2011 -0600
@@ -56,7 +56,7 @@
   $ hg rebase -s 1 -d 4
   merging A
   warning: conflicts during merge.
-  merging A failed!
+  merging A incomplete! (edit conflicts, then use 'hg resolve --mark')
   abort: unresolved conflicts (see hg resolve, then hg rebase --continue)
   [255]
 
@@ -88,7 +88,7 @@
   $ hg rebase --continue
   merging A
   warning: conflicts during merge.
-  merging A failed!
+  merging A incomplete! (edit conflicts, then use 'hg resolve --mark')
   abort: unresolved conflicts (see hg resolve, then hg rebase --continue)
   [255]
 
@@ -142,7 +142,7 @@
   $ hg rebase -s 1 -d 4
   merging A
   warning: conflicts during merge.
-  merging A failed!
+  merging A incomplete! (edit conflicts, then use 'hg resolve --mark')
   abort: unresolved conflicts (see hg resolve, then hg rebase --continue)
   [255]
 
--- a/tests/test-rebase-mq.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-rebase-mq.t	Thu Nov 17 16:53:17 2011 -0600
@@ -62,7 +62,7 @@
   $ hg rebase -s 2 -d 1
   merging f
   warning: conflicts during merge.
-  merging f failed!
+  merging f incomplete! (edit conflicts, then use 'hg resolve --mark')
   abort: unresolved conflicts (see hg resolve, then hg rebase --continue)
   [255]
 
@@ -73,7 +73,7 @@
   $ hg rebase -c
   merging f
   warning: conflicts during merge.
-  merging f failed!
+  merging f incomplete! (edit conflicts, then use 'hg resolve --mark')
   abort: unresolved conflicts (see hg resolve, then hg rebase --continue)
   [255]
 
--- a/tests/test-rebase-pull.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-rebase-pull.t	Thu Nov 17 16:53:17 2011 -0600
@@ -48,7 +48,7 @@
 Now b has one revision to be pulled from a:
 
   $ hg pull --rebase
-  pulling from $TESTTMP/a
+  pulling from $TESTTMP/a (glob)
   searching for changes
   adding changesets
   adding manifests
@@ -68,7 +68,7 @@
 Re-run:
 
   $ hg pull --rebase
-  pulling from $TESTTMP/a
+  pulling from $TESTTMP/a (glob)
   searching for changes
   no changes found
 
@@ -78,7 +78,7 @@
   $ cd ../c
 
   $ hg pull --rebase
-  pulling from $TESTTMP/a
+  pulling from $TESTTMP/a (glob)
   searching for changes
   adding changesets
   adding manifests
@@ -94,7 +94,7 @@
 pull --rebase --update should ignore --update:
 
   $ hg pull --rebase --update
-  pulling from $TESTTMP/a
+  pulling from $TESTTMP/a (glob)
   searching for changes
   no changes found
 
@@ -103,7 +103,7 @@
   $ hg up -q 1
 
   $ hg pull --rebase
-  pulling from $TESTTMP/a
+  pulling from $TESTTMP/a (glob)
   searching for changes
   no changes found
 
--- a/tests/test-rebase-scenario-global.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-rebase-scenario-global.t	Thu Nov 17 16:53:17 2011 -0600
@@ -251,7 +251,7 @@
 C onto A - rebase onto an ancestor:
 
   $ hg rebase -d 0 -s 2
-  saved backup bundle to $TESTTMP/a7/.hg/strip-backup/5fddd98957c8-backup.hg
+  saved backup bundle to $TESTTMP/a7/.hg/strip-backup/5fddd98957c8-backup.hg (glob)
   $ hg tglog
   @  7: 'D'
   |
@@ -473,7 +473,7 @@
   $ hg clone -q -u . ah ah5
   $ cd ah5
   $ hg rebase -r '6::' -d 2
-  saved backup bundle to $TESTTMP/ah5/.hg/strip-backup/3d8a618087a7-backup.hg
+  saved backup bundle to $TESTTMP/ah5/.hg/strip-backup/3d8a618087a7-backup.hg (glob)
   $ hg tglog
   @  8: 'I'
   |
--- a/tests/test-rebuildstate.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-rebuildstate.t	Thu Nov 17 16:53:17 2011 -0600
@@ -17,8 +17,8 @@
 state dump after
 
   $ hg debugstate --nodates | sort
-  n 666         -1 bar
-  n 666         -1 foo
+  n 644         -1 bar
+  n 644         -1 foo
 
 status
 
--- a/tests/test-record.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-record.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,5 @@
+  $ "$TESTDIR/hghave" execbit || exit 80
+
 Set up a repo
 
   $ echo "[ui]" >> $HGRCPATH
--- a/tests/test-relink.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-relink.t	Thu Nov 17 16:53:17 2011 -0600
@@ -39,7 +39,7 @@
 don't sit forever trying to double-lock the source repo
 
   $ hg relink .
-  relinking $TESTTMP/repo/.hg/store to $TESTTMP/repo/.hg/store
+  relinking $TESTTMP/repo/.hg/store to $TESTTMP/repo/.hg/store (glob)
   there is nothing to relink
 
 
--- a/tests/test-remove.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-remove.t	Thu Nov 17 16:53:17 2011 -0600
@@ -196,8 +196,8 @@
 
   $ rm test/bar
   $ remove test
-  removing test/bar
-  removing test/foo
+  removing test/bar (glob)
+  removing test/foo (glob)
   exit code: 0
   R test/bar
   R test/foo
@@ -208,8 +208,8 @@
 
   $ rm test/bar
   $ remove -f test
-  removing test/bar
-  removing test/foo
+  removing test/bar (glob)
+  removing test/foo (glob)
   exit code: 0
   R test/bar
   R test/foo
@@ -220,8 +220,8 @@
 
   $ rm test/bar
   $ remove -A test
-  not removing test/foo: file still exists (use -f to force removal)
-  removing test/bar
+  not removing test/foo: file still exists (use -f to force removal) (glob)
+  removing test/bar (glob)
   exit code: 1
   R test/bar
   ./foo
@@ -232,8 +232,8 @@
 
   $ rm test/bar
   $ remove -Af test
-  removing test/bar
-  removing test/foo
+  removing test/bar (glob)
+  removing test/foo (glob)
   exit code: 0
   R test/bar
   R test/foo
@@ -250,7 +250,7 @@
   adding issue1861/b/c/y
   adding issue1861/x
   $ hg rm issue1861/b
-  removing issue1861/b/c/y
+  removing issue1861/b/c/y (glob)
   $ hg ci -m remove
   $ ls issue1861
   x
--- a/tests/test-rename-dir-merge.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-rename-dir-merge.t	Thu Nov 17 16:53:17 2011 -0600
@@ -11,8 +11,8 @@
   $ hg co -C 0
   0 files updated, 0 files merged, 0 files removed, 0 files unresolved
   $ hg mv a b
-  moving a/a to b/a
-  moving a/b to b/b
+  moving a/a to b/a (glob)
+  moving a/b to b/b (glob)
   $ hg ci -m "1 mv a/ b/"
 
   $ hg co -C 0
@@ -75,7 +75,7 @@
   ? b/d
   $ hg ci -m "3 merge 2+1"
   $ hg debugrename b/c
-  b/c renamed from a/c:354ae8da6e890359ef49ade27b68bbc361f3ca88
+  b/c renamed from a/c:354ae8da6e890359ef49ade27b68bbc361f3ca88 (glob)
 
   $ hg co -C 1
   0 files updated, 0 files merged, 1 files removed, 0 files unresolved
@@ -111,7 +111,7 @@
   $ hg ci -m "4 merge 1+2"
   created new head
   $ hg debugrename b/c
-  b/c renamed from a/c:354ae8da6e890359ef49ade27b68bbc361f3ca88
+  b/c renamed from a/c:354ae8da6e890359ef49ade27b68bbc361f3ca88 (glob)
 
 
 Second scenario with two repos:
@@ -122,7 +122,7 @@
   $ mkdir a
   $ echo foo > a/f
   $ hg add a
-  adding a/f
+  adding a/f (glob)
   $ hg ci -m "a/f == foo"
   $ cd ..
 
@@ -131,7 +131,7 @@
   1 files updated, 0 files merged, 0 files removed, 0 files unresolved
   $ cd r2
   $ hg mv a b
-  moving a/f to b/f
+  moving a/f to b/f (glob)
   $ echo foo1 > b/f
   $ hg ci -m" a -> b, b/f == foo1"
   $ cd ..
@@ -140,7 +140,7 @@
   $ mkdir a/aa
   $ echo bar > a/aa/g
   $ hg add a/aa
-  adding a/aa/g
+  adding a/aa/g (glob)
   $ hg ci -m "a/aa/g"
   $ hg pull ../r2
   pulling from ../r2
--- a/tests/test-rename.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-rename.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,5 @@
+  $ "$TESTDIR/hghave" symlink || exit 80
+
   $ hg init
   $ mkdir d1 d1/d11 d2
   $ echo d1/a > d1/a
@@ -69,7 +71,7 @@
 rename --after a single file to a nonexistant target filename
 
   $ hg rename --after d1/a dummy
-  d1/a: not recording move - dummy does not exist
+  d1/a: not recording move - dummy does not exist (glob)
 
 move a single file to an existing directory
 
@@ -119,10 +121,10 @@
 rename directory d1 as d3
 
   $ hg rename d1/ d3
-  moving d1/a to d3/a
-  moving d1/b to d3/b
-  moving d1/ba to d3/ba
-  moving d1/d11/a1 to d3/d11/a1
+  moving d1/a to d3/a (glob)
+  moving d1/b to d3/b (glob)
+  moving d1/ba to d3/ba (glob)
+  moving d1/d11/a1 to d3/d11/a1 (glob)
   $ hg status -C
   A d3/a
     d1/a
@@ -144,10 +146,10 @@
 
   $ mv d1 d3
   $ hg rename --after d1 d3
-  moving d1/a to d3/a
-  moving d1/b to d3/b
-  moving d1/ba to d3/ba
-  moving d1/d11/a1 to d3/d11/a1
+  moving d1/a to d3/a (glob)
+  moving d1/b to d3/b (glob)
+  moving d1/ba to d3/ba (glob)
+  moving d1/d11/a1 to d3/d11/a1 (glob)
   $ hg status -C
   A d3/a
     d1/a
@@ -168,7 +170,7 @@
 move a directory using a relative path
 
   $ (cd d2; mkdir d3; hg rename ../d1/d11 d3)
-  moving ../d1/d11/a1 to d3/d11/a1
+  moving ../d1/d11/a1 to d3/d11/a1 (glob)
   $ hg status -C
   A d2/d3/d11/a1
     d1/d11/a1
@@ -180,7 +182,7 @@
 move --after a directory using a relative path
 
   $ (cd d2; mkdir d3; mv ../d1/d11 d3; hg rename --after ../d1/d11 d3)
-  moving ../d1/d11/a1 to d3/d11/a1
+  moving ../d1/d11/a1 to d3/d11/a1 (glob)
   $ hg status -C
   A d2/d3/d11/a1
     d1/d11/a1
@@ -192,7 +194,7 @@
 move directory d1/d11 to an existing directory d2 (removes empty d1)
 
   $ hg rename d1/d11/ d2
-  moving d1/d11/a1 to d2/d11/a1
+  moving d1/d11/a1 to d2/d11/a1 (glob)
   $ hg status -C
   A d2/d11/a1
     d1/d11/a1
@@ -205,11 +207,11 @@
 
   $ mkdir d3
   $ hg rename d1 d2 d3
-  moving d1/a to d3/d1/a
-  moving d1/b to d3/d1/b
-  moving d1/ba to d3/d1/ba
-  moving d1/d11/a1 to d3/d1/d11/a1
-  moving d2/b to d3/d2/b
+  moving d1/a to d3/d1/a (glob)
+  moving d1/b to d3/d1/b (glob)
+  moving d1/ba to d3/d1/ba (glob)
+  moving d1/d11/a1 to d3/d1/d11/a1 (glob)
+  moving d2/b to d3/d2/b (glob)
   $ hg status -C
   A d3/d1/a
     d1/a
@@ -235,11 +237,11 @@
   $ mkdir d3
   $ mv d1 d2 d3
   $ hg rename --after d1 d2 d3
-  moving d1/a to d3/d1/a
-  moving d1/b to d3/d1/b
-  moving d1/ba to d3/d1/ba
-  moving d1/d11/a1 to d3/d1/d11/a1
-  moving d2/b to d3/d2/b
+  moving d1/a to d3/d1/a (glob)
+  moving d1/b to d3/d1/b (glob)
+  moving d1/ba to d3/d1/ba (glob)
+  moving d1/d11/a1 to d3/d1/d11/a1 (glob)
+  moving d2/b to d3/d2/b (glob)
   $ hg status -C
   A d3/d1/a
     d1/a
@@ -265,7 +267,7 @@
 
   $ hg rename d1/* d2
   d2/b: not overwriting - file exists
-  moving d1/d11/a1 to d2/d11/a1
+  moving d1/d11/a1 to d2/d11/a1 (glob)
   $ hg status -C
   A d2/a
     d1/a
@@ -306,10 +308,10 @@
 
   $ mkdir d2/d21
   $ hg rename 'glob:d1/**' d2/d21
-  moving d1/a to d2/d21/a
-  moving d1/b to d2/d21/b
-  moving d1/ba to d2/d21/ba
-  moving d1/d11/a1 to d2/d21/a1
+  moving d1/a to d2/d21/a (glob)
+  moving d1/b to d2/d21/b (glob)
+  moving d1/ba to d2/d21/ba (glob)
+  moving d1/d11/a1 to d2/d21/a1 (glob)
   $ hg status -C
   A d2/d21/a
     d1/a
@@ -332,10 +334,10 @@
   $ mkdir d2/d21
   $ mv d1/a d1/d11/a1 d2/d21
   $ hg rename --after 'glob:d1/**' d2/d21
-  moving d1/a to d2/d21/a
-  d1/b: not recording move - d2/d21/b does not exist
-  d1/ba: not recording move - d2/d21/ba does not exist
-  moving d1/d11/a1 to d2/d21/a1
+  moving d1/a to d2/d21/a (glob)
+  d1/b: not recording move - d2/d21/b does not exist (glob)
+  d1/ba: not recording move - d2/d21/ba does not exist (glob)
+  moving d1/d11/a1 to d2/d21/a1 (glob)
   $ hg status -C
   A d2/d21/a
     d1/a
@@ -351,8 +353,8 @@
 
   $ mkdir d2/d21
   $ hg rename 're:d1/([^a][^/]*/)*a.*' d2/d21
-  moving d1/a to d2/d21/a
-  moving d1/d11/a1 to d2/d21/a1
+  moving d1/a to d2/d21/a (glob)
+  moving d1/d11/a1 to d2/d21/a1 (glob)
   $ hg status -C
   A d2/d21/a
     d1/a
@@ -413,7 +415,7 @@
 
   $ mkdir d3
   $ hg rename d1/* d2/* d3
-  moving d1/d11/a1 to d3/d11/a1
+  moving d1/d11/a1 to d3/d11/a1 (glob)
   d3/b: not overwriting - d2/b collides with d1/b
   $ hg status -C
   A d3/a
@@ -439,7 +441,7 @@
   moving a to ../d3/d1/a
   moving b to ../d3/d1/b
   moving ba to ../d3/d1/ba
-  moving d11/a1 to ../d3/d1/d11/a1
+  moving d11/a1 to ../d3/d1/d11/a1 (glob)
   $ hg status -C
   A d3/d1/a
     d1/a
@@ -465,7 +467,7 @@
   moving a to ../d3/a
   moving b to ../d3/b
   moving ba to ../d3/ba
-  moving d11/a1 to ../d3/d11/a1
+  moving d11/a1 to ../d3/d11/a1 (glob)
   $ hg status -C
   A d3/a
     d1/a
@@ -486,9 +488,9 @@
 move the parent tree with "hg rename .."
 
   $ (cd d1/d11; hg rename .. ../../d3)
-  moving ../a to ../../d3/a
-  moving ../b to ../../d3/b
-  moving ../ba to ../../d3/ba
+  moving ../a to ../../d3/a (glob)
+  moving ../b to ../../d3/b (glob)
+  moving ../ba to ../../d3/ba (glob)
   moving a1 to ../../d3/d11/a1
   $ hg status -C
   A d3/a
@@ -511,9 +513,9 @@
 
   $ hg remove d1/b
   $ hg rename d1 d3
-  moving d1/a to d3/a
-  moving d1/ba to d3/ba
-  moving d1/d11/a1 to d3/d11/a1
+  moving d1/a to d3/a (glob)
+  moving d1/ba to d3/ba (glob)
+  moving d1/d11/a1 to d3/d11/a1 (glob)
   $ hg status -C
   A d3/a
     d1/a
@@ -587,7 +589,7 @@
 check illegal path components
 
   $ hg rename d1/d11/a1 .hg/foo
-  abort: path contains illegal component: .hg/foo
+  abort: path contains illegal component: .hg/foo (glob)
   [255]
   $ hg status -C
   $ hg rename d1/d11/a1 ../foo
@@ -597,7 +599,7 @@
 
   $ mv d1/d11/a1 .hg/foo
   $ hg rename --after d1/d11/a1 .hg/foo
-  abort: path contains illegal component: .hg/foo
+  abort: path contains illegal component: .hg/foo (glob)
   [255]
   $ hg status -C
   ! d1/d11/a1
@@ -606,17 +608,17 @@
   $ rm .hg/foo
 
   $ hg rename d1/d11/a1 .hg
-  abort: path contains illegal component: .hg/a1
+  abort: path contains illegal component: .hg/a1 (glob)
   [255]
   $ hg status -C
   $ hg rename d1/d11/a1 ..
-  abort: ../a1 not under root
+  abort: ../a1 not under root (glob)
   [255]
   $ hg status -C
 
   $ mv d1/d11/a1 .hg
   $ hg rename --after d1/d11/a1 .hg
-  abort: path contains illegal component: .hg/a1
+  abort: path contains illegal component: .hg/a1 (glob)
   [255]
   $ hg status -C
   ! d1/d11/a1
@@ -625,7 +627,7 @@
   $ rm .hg/a1
 
   $ (cd d1/d11; hg rename ../../d2/b ../../.hg/foo)
-  abort: path contains illegal component: .hg/foo
+  abort: path contains illegal component: .hg/foo (glob)
   [255]
   $ hg status -C
   $ (cd d1/d11; hg rename ../../d2/b ../../../foo)
--- a/tests/test-repair-strip.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-repair-strip.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,4 @@
+  $ "$TESTDIR/hghave" unix-permissions || exit 80
 
   $ echo "[extensions]" >> $HGRCPATH
   $ echo "mq=">> $HGRCPATH
--- a/tests/test-revert.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-revert.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,5 @@
+  $ "$TESTDIR/hghave" execbit || exit 80
+
   $ hg init repo
   $ cd repo
   $ echo 123 > a
@@ -214,11 +216,11 @@
   $ echo foo > newdir/newfile
   $ hg add newdir/newfile
   $ hg revert b newdir
-  reverting b/b
-  forgetting newdir/newfile
+  reverting b/b (glob)
+  forgetting newdir/newfile (glob)
   $ echo foobar > b/b
   $ hg revert .
-  reverting b/b
+  reverting b/b (glob)
 
 
 reverting a rename target should revert the source
@@ -259,8 +261,8 @@
 
   $ hg revert -a --no-backup
   reverting ignored
-  reverting ignoreddir/file
-  undeleting ignoreddir/removed
+  reverting ignoreddir/file (glob)
+  undeleting ignoreddir/removed (glob)
   undeleting removed
   $ hg st -mardi
 
--- a/tests/test-revset-outgoing.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-revset-outgoing.t	Thu Nov 17 16:53:17 2011 -0600
@@ -39,7 +39,7 @@
   $ cd b
   $ cat .hg/hgrc
   [paths]
-  default = $TESTTMP/a#stable
+  default = $TESTTMP/a#stable (glob)
 
   $ echo red >> a
   $ hg ci -qm3
@@ -60,7 +60,7 @@
   
 
   $ hg tout
-  comparing with $TESTTMP/a
+  comparing with $TESTTMP/a (glob)
   searching for changes
   2:1d4099801a4e: '3' stable
 
@@ -79,11 +79,11 @@
 
   $ cat .hg/hgrc
   [paths]
-  default = $TESTTMP/a#stable
+  default = $TESTTMP/a#stable (glob)
   green = ../a#default
 
   $ hg tout green
-  comparing with $TESTTMP/a
+  comparing with $TESTTMP/a (glob)
   searching for changes
   3:f0461977a3db: '4' 
 
--- a/tests/test-rollback.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-rollback.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,5 @@
+  $ "$TESTDIR/hghave" serve || exit 80
+
 setup repo
   $ hg init t
   $ cd t
--- a/tests/test-run-tests.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-run-tests.t	Thu Nov 17 16:53:17 2011 -0600
@@ -16,6 +16,11 @@
   $ foo
   bar
 
+Return codes before inline python:
+
+  $ false
+  [1]
+
 Doctest commands:
 
   >>> print 'foo'
@@ -28,7 +33,7 @@
   y
   z
   >>> print
-  <BLANKLINE>
+  
 
 Regular expressions:
 
--- a/tests/test-schemes.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-schemes.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,4 @@
+  $ "$TESTDIR/hghave" serve || exit 80
 
   $ cat <<EOF >> $HGRCPATH
   > [extensions]
--- a/tests/test-serve.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-serve.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,4 @@
+  $ "$TESTDIR/hghave" serve || exit 80
 
   $ hgserve()
   > {
--- a/tests/test-share.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-share.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,4 @@
+  $ "$TESTDIR/hghave" serve || exit 80
 
   $ echo "[extensions]"      >> $HGRCPATH
   $ echo "share = "          >> $HGRCPATH
@@ -26,14 +27,14 @@
 Some sed versions appends newline, some don't, and some just fails
 
   $ cat .hg/sharedpath; echo
-  $TESTTMP/repo1/.hg
+  $TESTTMP/repo1/.hg (glob)
 
 trailing newline on .hg/sharedpath is ok
   $ hg tip -q
   0:d3873e73d99e
   $ echo '' >> .hg/sharedpath
   $ cat .hg/sharedpath
-  $TESTTMP/repo1/.hg
+  $TESTTMP/repo1/.hg (glob)
   $ hg tip -q
   0:d3873e73d99e
 
--- a/tests/test-static-http.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-static-http.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,4 @@
+  $ "$TESTDIR/hghave" serve || exit 80
 
   $ hg clone http://localhost:$HGPORT/ copy
   abort: error: Connection refused
--- a/tests/test-status-color.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-status-color.t	Thu Nov 17 16:53:17 2011 -0600
@@ -280,10 +280,10 @@
   $ hg merge
   merging a
   warning: conflicts during merge.
-  merging a failed!
+  merging a incomplete! (edit conflicts, then use 'hg resolve --mark')
   merging b
   warning: conflicts during merge.
-  merging b failed!
+  merging b incomplete! (edit conflicts, then use 'hg resolve --mark')
   0 files updated, 0 files merged, 0 files removed, 2 files unresolved
   use 'hg resolve' to retry unresolved file merges or 'hg update -C .' to abandon
   [1]
--- a/tests/test-subrepo-deep-nested-change.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-subrepo-deep-nested-change.t	Thu Nov 17 16:53:17 2011 -0600
@@ -3,7 +3,7 @@
   $ hg init sub2
   $ echo sub2 > sub2/sub2
   $ hg add -R sub2
-  adding sub2/sub2
+  adding sub2/sub2 (glob)
   $ hg commit -R sub2 -m "sub2 import"
 
 Preparing the 'sub1' repo which depends on the subrepo 'sub2'
@@ -15,8 +15,8 @@
   updating to branch default
   1 files updated, 0 files merged, 0 files removed, 0 files unresolved
   $ hg add -R sub1
-  adding sub1/.hgsub
-  adding sub1/sub1
+  adding sub1/.hgsub (glob)
+  adding sub1/sub1 (glob)
   $ hg commit -R sub1 -m "sub1 import"
   committing subrepository sub2
 
@@ -30,8 +30,8 @@
   cloning subrepo sub2 from $TESTTMP/sub2
   3 files updated, 0 files merged, 0 files removed, 0 files unresolved
   $ hg add -R main
-  adding main/.hgsub
-  adding main/main
+  adding main/.hgsub (glob)
+  adding main/main (glob)
   $ hg commit -R main -m "main import"
   committing subrepository sub1
 
@@ -51,7 +51,7 @@
   $ hg clone main cloned
   updating to branch default
   cloning subrepo sub1 from $TESTTMP/sub1
-  cloning subrepo sub1/sub2 from $TESTTMP/sub2
+  cloning subrepo sub1/sub2 from $TESTTMP/sub2 (glob)
   3 files updated, 0 files merged, 0 files removed, 0 files unresolved
 
 Checking cloned repo ids
@@ -79,7 +79,7 @@
   $ echo modified > cloned/sub1/sub2/sub2
   $ hg commit --subrepos -m "deep nested modif should trigger a commit" -R cloned
   committing subrepository sub1
-  committing subrepository sub1/sub2
+  committing subrepository sub1/sub2 (glob)
 
 Checking modified node ids
 
--- a/tests/test-subrepo-paths.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-subrepo-paths.t	Thu Nov 17 16:53:17 2011 -0600
@@ -55,5 +55,5 @@
   > .* = \1
   > EOF
   $ hg debugsub
-  abort: bad subrepository pattern in $TESTTMP/outer/.hg/hgrc:2: invalid group reference
+  abort: bad subrepository pattern in $TESTTMP/outer/.hg/hgrc:2: invalid group reference (glob)
   [255]
--- a/tests/test-subrepo-recursion.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-subrepo-recursion.t	Thu Nov 17 16:53:17 2011 -0600
@@ -265,10 +265,10 @@
   archiving (foo) [====================================>] 3/3
   archiving (foo) [====================================>] 3/3
                                                               
-  archiving (foo/bar) [                                 ] 0/1
-  archiving (foo/bar) [                                 ] 0/1
-  archiving (foo/bar) [================================>] 1/1
-  archiving (foo/bar) [================================>] 1/1
+  archiving (foo/bar) [                                 ] 0/1 (glob)
+  archiving (foo/bar) [                                 ] 0/1 (glob)
+  archiving (foo/bar) [================================>] 1/1 (glob)
+  archiving (foo/bar) [================================>] 1/1 (glob)
                                                               \r (esc)
   $ find ../archive | sort
   ../archive
@@ -305,10 +305,10 @@
   archiving (foo) [====================================>] 3/3
   archiving (foo) [====================================>] 3/3
                                                               
-  archiving (foo/bar) [                                 ] 0/1
-  archiving (foo/bar) [                                 ] 0/1
-  archiving (foo/bar) [================================>] 1/1
-  archiving (foo/bar) [================================>] 1/1
+  archiving (foo/bar) [                                 ] 0/1 (glob)
+  archiving (foo/bar) [                                 ] 0/1 (glob)
+  archiving (foo/bar) [================================>] 1/1 (glob)
+  archiving (foo/bar) [================================>] 1/1 (glob)
                                                               \r (esc)
 
 Test archiving a revision that references a subrepo that is not yet
@@ -336,10 +336,10 @@
   archiving (foo) [====================================>] 3/3
   archiving (foo) [====================================>] 3/3
                                                               
-  archiving (foo/bar) [                                 ] 0/1
-  archiving (foo/bar) [                                 ] 0/1
-  archiving (foo/bar) [================================>] 1/1
-  archiving (foo/bar) [================================>] 1/1
+  archiving (foo/bar) [                                 ] 0/1 (glob)
+  archiving (foo/bar) [                                 ] 0/1 (glob)
+  archiving (foo/bar) [================================>] 1/1 (glob)
+  archiving (foo/bar) [================================>] 1/1 (glob)
                                                               
   cloning subrepo foo from $TESTTMP/repo/foo
   cloning subrepo foo/bar from $TESTTMP/repo/foo/bar
--- a/tests/test-subrepo-relative-path.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-subrepo-relative-path.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,9 +1,11 @@
+  $ "$TESTDIR/hghave" serve || exit 80
+
 Preparing the subrepository 'sub'
 
   $ hg init sub
   $ echo sub > sub/sub
   $ hg add -R sub
-  adding sub/sub
+  adding sub/sub (glob)
   $ hg commit -R sub -m "sub import"
 
 Preparing the 'main' repo which depends on the subrepo 'sub'
@@ -15,8 +17,8 @@
   updating to branch default
   1 files updated, 0 files merged, 0 files removed, 0 files unresolved
   $ hg add -R main
-  adding main/.hgsub
-  adding main/main
+  adding main/.hgsub (glob)
+  adding main/main (glob)
   $ hg commit -R main -m "main import"
   committing subrepository sub
 
--- a/tests/test-subrepo.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-subrepo.t	Thu Nov 17 16:53:17 2011 -0600
@@ -49,7 +49,7 @@
 
   $ hg revert -a
   $ hg revert -R s -a -C
-  reverting s/a
+  reverting s/a (glob)
 
 Issue2022: update -C
 
@@ -92,7 +92,7 @@
   update: (current)
   $ hg ci -m2
   committing subrepository s
-  committing subrepository s/ss
+  committing subrepository s/ss (glob)
   $ hg sum
   parent: 2:df30734270ae tip
    2
@@ -147,7 +147,7 @@
   $ hg init t
   $ echo t > t/t
   $ hg -R t add t
-  adding t/t
+  adding t/t (glob)
 
 5
 
@@ -245,7 +245,7 @@
   merging t
   my t@20a0db6fbf6c+ other t@7af322bc1198 ancestor t@6747d179aa9a
   warning: conflicts during merge.
-  merging t failed!
+  merging t incomplete! (edit conflicts, then use 'hg resolve --mark')
   0 files updated, 0 files merged, 0 files removed, 1 files unresolved
   use 'hg resolve' to retry unresolved file merges or 'hg update -C .' to abandon
   0 files updated, 0 files merged, 0 files removed, 0 files unresolved
@@ -265,9 +265,9 @@
   $ cd ..
   $ hg clone t tc
   updating to branch default
-  cloning subrepo s from $TESTTMP/sub/t/s
-  cloning subrepo s/ss from $TESTTMP/sub/t/s/ss
-  cloning subrepo t from $TESTTMP/sub/t/t
+  cloning subrepo s from $TESTTMP/sub/t/s (glob)
+  cloning subrepo s/ss from $TESTTMP/sub/t/s/ss (glob)
+  cloning subrepo t from $TESTTMP/sub/t/t (glob)
   3 files updated, 0 files merged, 0 files removed, 0 files unresolved
   $ cd tc
   $ hg debugsub
@@ -284,14 +284,14 @@
   $ hg ci -m11
   committing subrepository t
   $ hg push
-  pushing to $TESTTMP/sub/t
-  pushing subrepo s/ss to $TESTTMP/sub/t/s/ss
+  pushing to $TESTTMP/sub/t (glob)
+  pushing subrepo s/ss to $TESTTMP/sub/t/s/ss (glob)
   searching for changes
   no changes found
-  pushing subrepo s to $TESTTMP/sub/t/s
+  pushing subrepo s to $TESTTMP/sub/t/s (glob)
   searching for changes
   no changes found
-  pushing subrepo t to $TESTTMP/sub/t/t
+  pushing subrepo t to $TESTTMP/sub/t/t (glob)
   searching for changes
   adding changesets
   adding manifests
@@ -309,27 +309,27 @@
   $ hg ci -m12
   committing subrepository s
   $ hg push
-  pushing to $TESTTMP/sub/t
-  pushing subrepo s/ss to $TESTTMP/sub/t/s/ss
+  pushing to $TESTTMP/sub/t (glob)
+  pushing subrepo s/ss to $TESTTMP/sub/t/s/ss (glob)
   searching for changes
   no changes found
-  pushing subrepo s to $TESTTMP/sub/t/s
+  pushing subrepo s to $TESTTMP/sub/t/s (glob)
   searching for changes
   abort: push creates new remote head 12a213df6fa9!
   (did you forget to merge? use push -f to force)
   [255]
   $ hg push -f
-  pushing to $TESTTMP/sub/t
-  pushing subrepo s/ss to $TESTTMP/sub/t/s/ss
+  pushing to $TESTTMP/sub/t (glob)
+  pushing subrepo s/ss to $TESTTMP/sub/t/s/ss (glob)
   searching for changes
   no changes found
-  pushing subrepo s to $TESTTMP/sub/t/s
+  pushing subrepo s to $TESTTMP/sub/t/s (glob)
   searching for changes
   adding changesets
   adding manifests
   adding file changes
   added 1 changesets with 1 changes to 1 files (+1 heads)
-  pushing subrepo t to $TESTTMP/sub/t/t
+  pushing subrepo t to $TESTTMP/sub/t/t (glob)
   searching for changes
   no changes found
   searching for changes
@@ -351,7 +351,7 @@
 
   $ cd ../tc
   $ hg pull
-  pulling from $TESTTMP/sub/t
+  pulling from $TESTTMP/sub/t (glob)
   searching for changes
   adding changesets
   adding manifests
@@ -362,7 +362,7 @@
 should pull t
 
   $ hg up
-  pulling subrepo t from $TESTTMP/sub/t/t
+  pulling subrepo t from $TESTTMP/sub/t/t (glob)
   searching for changes
   adding changesets
   adding manifests
@@ -507,15 +507,15 @@
   $ echo test > testdelete/nested/foo
   $ echo test > testdelete/nested2/foo
   $ hg -R testdelete/nested add
-  adding testdelete/nested/foo
+  adding testdelete/nested/foo (glob)
   $ hg -R testdelete/nested2 add
-  adding testdelete/nested2/foo
+  adding testdelete/nested2/foo (glob)
   $ hg -R testdelete/nested ci -m test
   $ hg -R testdelete/nested2 ci -m test
   $ echo nested = nested > testdelete/.hgsub
   $ echo nested2 = nested2 >> testdelete/.hgsub
   $ hg -R testdelete add
-  adding testdelete/.hgsub
+  adding testdelete/.hgsub (glob)
   $ hg -R testdelete ci -m "nested 1 & 2 added"
   committing subrepository nested
   committing subrepository nested2
@@ -534,19 +534,19 @@
   $ hg init nested_absolute
   $ echo test > nested_absolute/foo
   $ hg -R nested_absolute add
-  adding nested_absolute/foo
+  adding nested_absolute/foo (glob)
   $ hg -R nested_absolute ci -mtest
   $ cd mercurial
   $ hg init nested_relative
   $ echo test2 > nested_relative/foo2
   $ hg -R nested_relative add
-  adding nested_relative/foo2
+  adding nested_relative/foo2 (glob)
   $ hg -R nested_relative ci -mtest2
   $ hg init main
   $ echo "nested_relative = ../nested_relative" > main/.hgsub
   $ echo "nested_absolute = `pwd`/nested_absolute" >> main/.hgsub
   $ hg -R main add
-  adding main/.hgsub
+  adding main/.hgsub (glob)
   $ hg -R main ci -m "add subrepos"
   committing subrepository nested_absolute
   committing subrepository nested_relative
@@ -575,7 +575,7 @@
   committing subrepository s
   $ hg clone repo repo2
   updating to branch default
-  cloning subrepo s from $TESTTMP/sub/repo/s
+  cloning subrepo s from $TESTTMP/sub/repo/s (glob)
   2 files updated, 0 files merged, 0 files removed, 0 files unresolved
   $ hg -q -R repo2 pull -u
   $ echo 1 > repo2/s/a
@@ -609,10 +609,10 @@
   $ echo sub/repo = sub/repo > .hgsub
   $ hg add .hgsub
   $ hg ci -mtest
-  committing subrepository sub/repo
+  committing subrepository sub/repo (glob)
   $ echo test >> sub/repo/foo
   $ hg ci -mtest
-  committing subrepository sub/repo
+  committing subrepository sub/repo (glob)
   $ cd ..
 
 Create repo without default path, pull top repo, and see what happens on update
@@ -627,7 +627,7 @@
   added 2 changesets with 3 changes to 2 files
   (run 'hg update' to get a working copy)
   $ hg -R issue1852b update
-  abort: default path for subrepository sub/repo not found
+  abort: default path for subrepository sub/repo not found (glob)
   [255]
 
 Pull -u now doesn't help
@@ -646,14 +646,14 @@
   adding manifests
   adding file changes
   added 1 changesets with 2 changes to 2 files
-  cloning subrepo sub/repo from issue1852a/sub/repo
+  cloning subrepo sub/repo from issue1852a/sub/repo (glob)
   2 files updated, 0 files merged, 0 files removed, 0 files unresolved
 
 Try to push from the other side
 
   $ hg -R issue1852a push `pwd`/issue1852c
   pushing to $TESTTMP/sub/issue1852c
-  pushing subrepo sub/repo to $TESTTMP/sub/issue1852c/sub/repo
+  pushing subrepo sub/repo to $TESTTMP/sub/issue1852c/sub/repo (glob)
   searching for changes
   no changes found
   searching for changes
@@ -883,3 +883,135 @@
   rm2
   
   
+Test behavior of add for explicit path in subrepo:
+  $ cd ..
+  $ hg init explicit
+  $ cd explicit
+  $ echo s = s > .hgsub
+  $ hg add .hgsub
+  $ hg init s
+  $ hg ci -m0
+  committing subrepository s
+Adding with an explicit path in a subrepo adds the file
+  $ echo c1 > f1
+  $ echo c2 > s/f2
+  $ hg st -S
+  ? f1
+  ? s/f2
+  $ hg add s/f2
+  $ hg st -S
+  A s/f2
+  ? f1
+  $ hg ci -R s -m0
+  $ hg ci -Am1
+  adding f1
+  committing subrepository s
+Adding with an explicit path in a subrepo with -S has the same behavior
+  $ echo c3 > f3
+  $ echo c4 > s/f4
+  $ hg st -S
+  ? f3
+  ? s/f4
+  $ hg add -S s/f4
+  $ hg st -S
+  A s/f4
+  ? f3
+  $ hg ci -R s -m1
+  $ hg ci -Ama2
+  adding f3
+  committing subrepository s
+Adding without a path or pattern silently ignores subrepos
+  $ echo c5 > f5
+  $ echo c6 > s/f6
+  $ echo c7 > s/f7
+  $ hg st -S
+  ? f5
+  ? s/f6
+  ? s/f7
+  $ hg add
+  adding f5
+  $ hg st -S
+  A f5
+  ? s/f6
+  ? s/f7
+  $ hg ci -R s -Am2
+  adding f6
+  adding f7
+  $ hg ci -m3
+  committing subrepository s
+Adding without a path or pattern with -S also adds files in subrepos
+  $ echo c8 > f8
+  $ echo c9 > s/f9
+  $ echo c10 > s/f10
+  $ hg st -S
+  ? f8
+  ? s/f10
+  ? s/f9
+  $ hg add -S
+  adding f8
+  adding s/f10
+  adding s/f9
+  $ hg st -S
+  A f8
+  A s/f10
+  A s/f9
+  $ hg ci -R s -m3
+  $ hg ci -m4
+  committing subrepository s
+Adding with a pattern silently ignores subrepos
+  $ echo c11 > fm11
+  $ echo c12 > fn12
+  $ echo c13 > s/fm13
+  $ echo c14 > s/fn14
+  $ hg st -S
+  ? fm11
+  ? fn12
+  ? s/fm13
+  ? s/fn14
+  $ hg add 'glob:**fm*'
+  adding fm11
+  $ hg st -S
+  A fm11
+  ? fn12
+  ? s/fm13
+  ? s/fn14
+  $ hg ci -R s -Am4
+  adding fm13
+  adding fn14
+  $ hg ci -Am5
+  adding fn12
+  committing subrepository s
+Adding with a pattern with -S also adds matches in subrepos
+  $ echo c15 > fm15
+  $ echo c16 > fn16
+  $ echo c17 > s/fm17
+  $ echo c18 > s/fn18
+  $ hg st -S
+  ? fm15
+  ? fn16
+  ? s/fm17
+  ? s/fn18
+  $ hg add -S 'glob:**fm*'
+  adding fm15
+  adding s/fm17
+  $ hg st -S
+  A fm15
+  A s/fm17
+  ? fn16
+  ? s/fn18
+  $ hg ci -R s -Am5
+  adding fn18
+  $ hg ci -Am6
+  adding fn16
+  committing subrepository s
+
+Test behavior of forget for explicit path in subrepo:
+Forgetting an explicit path in a subrepo untracks the file
+  $ echo c19 > s/f19
+  $ hg add s/f19
+  $ hg st -S
+  A s/f19
+  $ hg forget s/f19
+  $ hg st -S
+  ? s/f19
+  $ rm s/f19
--- a/tests/test-symlink-placeholder.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-symlink-placeholder.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,5 @@
+  $ "$TESTDIR/hghave" symlink || exit 80
+
 Create extension that can disable symlink support:
 
   $ cat > nolink.py <<EOF
--- a/tests/test-tags.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-tags.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,5 @@
+  $ "$TESTDIR/hghave" unix-permissions || exit 80
+
 Helper functions:
 
   $ cacheexists() {
--- a/tests/test-transplant.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-transplant.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,5 @@
+  $ "$TESTDIR/hghave" serve || exit 80
+
   $ cat <<EOF >> $HGRCPATH
   > [extensions]
   > transplant=
--- a/tests/test-treediscovery-legacy.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-treediscovery-legacy.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,5 @@
+  $ "$TESTDIR/hghave" serve || exit 80
+
 Tests discovery against servers without getbundle support:
 
   $ cat >> $HGRCPATH <<EOF
--- a/tests/test-treediscovery.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-treediscovery.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,5 @@
+  $ "$TESTDIR/hghave" serve || exit 80
+
 Tests discovery against servers without getbundle support:
 
   $ CAP=getbundle
--- a/tests/test-unbundlehash.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-unbundlehash.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,4 @@
+  $ "$TESTDIR/hghave" serve || exit 80
 
 Test wire protocol unbundle with hashed heads (capability: unbundlehash)
 
--- a/tests/test-update-issue1456.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-update-issue1456.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,5 @@
+  $ "$TESTDIR/hghave" execbit || exit 80
+
   $ rm -rf a
   $ hg init a
   $ cd a
--- a/tests/test-update-renames.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-update-renames.t	Thu Nov 17 16:53:17 2011 -0600
@@ -21,7 +21,7 @@
   $ hg up
   merging a and b to b
   warning: conflicts during merge.
-  merging b failed!
+  merging b incomplete! (edit conflicts, then use 'hg resolve --mark')
   0 files updated, 0 files merged, 0 files removed, 1 files unresolved
   use 'hg resolve' to retry unresolved file merges
   [1]
--- a/tests/test-url-rev.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-url-rev.t	Thu Nov 17 16:53:17 2011 -0600
@@ -41,7 +41,7 @@
   
   $ cat clone/.hg/hgrc
   [paths]
-  default = $TESTTMP/repo#foo
+  default = $TESTTMP/repo#foo (glob)
 
 Changing original repo:
 
--- a/tests/test-url.py	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-url.py	Thu Nov 17 16:53:17 2011 -0600
@@ -219,7 +219,7 @@
     >>> u
     <url scheme: 'file', path: 'f:oo/bar/baz'>
     >>> str(u)
-    'file:f%3Aoo/bar/baz'
+    'file:f:oo/bar/baz'
     >>> u.localpath()
     'f:oo/bar/baz'
 
@@ -227,7 +227,7 @@
     >>> u
     <url scheme: 'file', host: 'localhost', path: 'f:oo/bar/baz'>
     >>> str(u)
-    'file://localhost/f%3Aoo/bar/baz'
+    'file://localhost/f:oo/bar/baz'
     >>> u.localpath()
     'f:oo/bar/baz'
 
--- a/tests/test-walk.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-walk.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,5 @@
+  $ "$TESTDIR/hghave" no-windows || exit 80
+
   $ hg init t
   $ cd t
   $ mkdir -p beans
--- a/tests/test-win32text.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-win32text.t	Thu Nov 17 16:53:17 2011 -0600
@@ -385,7 +385,7 @@
   WARNING: f4.bat already has CRLF line endings
   and does not need EOL conversion by the win32text plugin.
   Before your next commit, please reconsider your encode/decode settings in 
-  Mercurial.ini or $TESTTMP/t/.hg/hgrc.
+  Mercurial.ini or $TESTTMP/t/.hg/hgrc. (glob)
   3 files updated, 0 files merged, 0 files removed, 0 files unresolved
   $ cat bin
   hello\x00\r (esc)
--- a/tests/test-wireproto.t	Wed Nov 16 08:34:36 2011 +0100
+++ b/tests/test-wireproto.t	Thu Nov 17 16:53:17 2011 -0600
@@ -1,3 +1,4 @@
+  $ "$TESTDIR/hghave" serve || exit 80
 
 Test wire protocol argument passing