# HG changeset patch # User Vadim Gelfer # Date 1155931300 25200 # Node ID f4fc0575e8fa2e0ae565791579ede185fc0183c6 # Parent d77022db1bca49eb479257dce6e510f2da7323c0# Parent d32df6452323a6177e291c2b8fdf2e2819dcc05d merge with brendan. diff -r d77022db1bca -r f4fc0575e8fa hgext/mq.py --- a/hgext/mq.py Fri Aug 18 10:24:04 2006 -0700 +++ b/hgext/mq.py Fri Aug 18 13:01:40 2006 -0700 @@ -252,6 +252,9 @@ for line in file(pf): line = line.rstrip() + if line.startswith('diff --git'): + diffstart = 2 + break if diffstart: if line.startswith('+++ '): diffstart = 2 @@ -298,8 +301,10 @@ return (message, comments, user, date, diffstart > 1) def printdiff(self, repo, node1, node2=None, files=None, - fp=None, changes=None, opts=None): - patch.diff(repo, node1, node2, files, + fp=None, changes=None, opts={}): + fns, matchfn, anypats = cmdutil.matchpats(repo, files, opts) + + patch.diff(repo, node1, node2, fns, match=matchfn, fp=fp, changes=changes, opts=self.diffopts()) def mergeone(self, repo, mergeq, head, patch, rev, wlock): @@ -408,7 +413,7 @@ self.ui.warn("patch failed, unable to continue (try -v)\n") return (False, [], False) - return (True, files.keys(), fuzz) + return (True, files, fuzz) def apply(self, repo, series, list=False, update_status=True, strict=False, patchdir=None, merge=None, wlock=None): @@ -421,42 +426,37 @@ lock = repo.lock() tr = repo.transaction() n = None - for patch in series: - pushable, reason = self.pushable(patch) + for patchname in series: + pushable, reason = self.pushable(patchname) if not pushable: - self.explain_pushable(patch, all_patches=True) + self.explain_pushable(patchname, all_patches=True) continue - self.ui.warn("applying %s\n" % patch) - pf = os.path.join(patchdir, patch) + self.ui.warn("applying %s\n" % patchname) + pf = os.path.join(patchdir, patchname) try: - message, comments, user, date, patchfound = self.readheaders(patch) + message, comments, user, date, patchfound = self.readheaders(patchname) except: - self.ui.warn("Unable to read %s\n" % pf) + self.ui.warn("Unable to read %s\n" % patchname) err = 1 break if not message: - message = "imported patch %s\n" % patch + message = "imported patch %s\n" % patchname else: if list: - message.append("\nimported patch %s" % patch) + message.append("\nimported patch %s" % patchname) message = '\n'.join(message) (patcherr, files, fuzz) = self.patch(repo, pf) patcherr = not patcherr - if merge and len(files) > 0: + if merge and files: # Mark as merged and update dirstate parent info - repo.dirstate.update(repo.dirstate.filterfiles(files), 'm') + repo.dirstate.update(repo.dirstate.filterfiles(files.keys()), 'm') p1, p2 = repo.dirstate.parents() repo.dirstate.setparents(p1, merge) - if len(files) > 0: - cwd = repo.getcwd() - cfiles = files - if cwd: - cfiles = [util.pathto(cwd, f) for f in files] - cmdutil.addremove(repo, cfiles, wlock=wlock) + files = patch.updatedir(self.ui, repo, files, wlock=wlock) n = repo.commit(files, message, user, date, force=1, lock=lock, wlock=wlock) @@ -464,11 +464,11 @@ raise util.Abort(_("repo commit failed")) if update_status: - self.applied.append(statusentry(revlog.hex(n), patch)) + self.applied.append(statusentry(revlog.hex(n), patchname)) if patcherr: if not patchfound: - self.ui.warn("patch %s is empty\n" % patch) + self.ui.warn("patch %s is empty\n" % patchname) err = 0 else: self.ui.warn("patch failed, rejects left in working dir\n") @@ -904,15 +904,15 @@ else: self.ui.write("Patch queue now empty\n") - def diff(self, repo, files): + def diff(self, repo, pats, opts): top = self.check_toppatch(repo) if not top: self.ui.write("No patches applied\n") return qp = self.qparents(repo, top) - self.printdiff(repo, qp, files=files) + self.printdiff(repo, qp, files=pats, opts=opts) - def refresh(self, repo, msg='', short=False): + def refresh(self, repo, pats=None, **opts): if len(self.applied) == 0: self.ui.write("No patches applied\n") return @@ -925,7 +925,7 @@ message, comments, user, date, patchfound = self.readheaders(patch) patchf = self.opener(patch, "w") - msg = msg.rstrip() + msg = opts.get('msg', '').rstrip() if msg: if comments: # Remove existing message. @@ -939,6 +939,7 @@ comments = "\n".join(comments) + '\n\n' patchf.write(comments) + fns, matchfn, anypats = cmdutil.matchpats(repo, pats, opts) tip = repo.changelog.tip() if top == tip: # if the top of our patch queue is also the tip, there is an @@ -956,7 +957,7 @@ # caching against the next repo.status call # mm, aa, dd, aa2, uu = repo.status(patchparent, tip)[:5] - if short: + if opts.get('short'): filelist = mm + aa + dd else: filelist = None @@ -992,16 +993,27 @@ m = list(util.unique(mm)) r = list(util.unique(dd)) a = list(util.unique(aa)) - filelist = list(util.unique(m + r + a)) + filelist = filter(matchfn, util.unique(m + r + a)) self.printdiff(repo, patchparent, files=filelist, changes=(m, a, r, [], u), fp=patchf) patchf.close() changes = repo.changelog.read(tip) repo.dirstate.setparents(*cparents) + copies = [(f, repo.dirstate.copied(f)) for f in a] repo.dirstate.update(a, 'a') + for dst, src in copies: + repo.dirstate.copy(src, dst) repo.dirstate.update(r, 'r') + # if the patch excludes a modified file, mark that file with mtime=0 + # so status can see it. + mm = [] + for i in range(len(m)-1, -1, -1): + if not matchfn(m[i]): + mm.append(m[i]) + del m[i] repo.dirstate.update(m, 'n') + repo.dirstate.update(mm, 'n', st_mtime=0) repo.dirstate.forget(forget) if not msg: @@ -1216,7 +1228,7 @@ if not self.ui.verbose: p = pname else: - p = str(self.series.index(pname)) + " " + p + p = str(self.series.index(pname)) + " " + pname return p def top(self, repo): @@ -1411,17 +1423,24 @@ changes unless -f is specified, in which case the patch will be initialised with them. - -m or -l set the patch header as well as the commit message. - If neither is specified, the patch header is empty and the + -e, -m or -l set the patch header as well as the commit message. + If none is specified, the patch header is empty and the commit message is 'New patch: PATCH'""" q = repo.mq message = commands.logmessage(opts) + if opts['edit']: + message = ui.edit(message, ui.username()) q.new(repo, patch, msg=message, force=opts['force']) q.save_dirty() return 0 -def refresh(ui, repo, **opts): - """update the current patch""" +def refresh(ui, repo, *pats, **opts): + """update the current patch + + If any file patterns are provided, the refreshed patch will contain only + the modifications that match those patterns; the remaining modifications + will remain in the working directory. + """ q = repo.mq message = commands.logmessage(opts) if opts['edit']: @@ -1430,14 +1449,13 @@ patch = q.applied[-1].name (message, comment, user, date, hasdiff) = q.readheaders(patch) message = ui.edit('\n'.join(message), user or ui.username()) - q.refresh(repo, msg=message, short=opts['short']) + q.refresh(repo, pats, msg=message, **opts) q.save_dirty() return 0 -def diff(ui, repo, *files, **opts): +def diff(ui, repo, *pats, **opts): """diff of the current patch""" - # deep in the dirstate code, the walkhelper method wants a list, not a tuple - repo.mq.diff(repo, list(files)) + repo.mq.diff(repo, pats, opts) return 0 def fold(ui, repo, *files, **opts): @@ -1469,20 +1487,21 @@ patches = [] messages = [] for f in files: - patch = q.lookup(f) - if patch in patches or patch == parent: - ui.warn(_('Skipping already folded patch %s') % patch) - if q.isapplied(patch): - raise util.Abort(_('qfold cannot fold already applied patch %s') % patch) - patches.append(patch) + p = q.lookup(f) + if p in patches or p == parent: + ui.warn(_('Skipping already folded patch %s') % p) + if q.isapplied(p): + raise util.Abort(_('qfold cannot fold already applied patch %s') % p) + patches.append(p) - for patch in patches: + for p in patches: if not message: - messages.append(q.readheaders(patch)[0]) - pf = q.join(patch) + messages.append(q.readheaders(p)[0]) + pf = q.join(p) (patchsuccess, files, fuzz) = q.patch(repo, pf) if not patchsuccess: - raise util.Abort(_('Error folding patch %s') % patch) + raise util.Abort(_('Error folding patch %s') % p) + patch.updatedir(ui, repo, files) if not message: message, comments, user = q.readheaders(parent)[0:3] @@ -1495,29 +1514,26 @@ message = ui.edit(message, user or ui.username()) q.refresh(repo, msg=message) - - for patch in patches: - q.delete(repo, patch, keep=opts['keep']) - + q.delete(repo, patches, keep=opts['keep']) q.save_dirty() def guard(ui, repo, *args, **opts): '''set or print guards for a patch - guards control whether a patch can be pushed. a patch with no - guards is aways pushed. a patch with posative guard ("+foo") is - pushed only if qselect command enables guard "foo". a patch with - nagative guard ("-foo") is never pushed if qselect command enables - guard "foo". + Guards control whether a patch can be pushed. A patch with no + guards is always pushed. A patch with a positive guard ("+foo") is + pushed only if the qselect command has activated it. A patch with + a negative guard ("-foo") is never pushed if the qselect command + has activated it. - with no arguments, default is to print current active guards. - with arguments, set active guards for patch. + With no arguments, print the currently active guards. + With arguments, set guards for the named patch. - to set nagative guard "-foo" on topmost patch ("--" is needed so - hg will not interpret "-foo" as argument): + To set a negative guard "-foo" on topmost patch ("--" is needed so + hg will not interpret "-foo" as an option): hg qguard -- -foo - to set guards on other patch: + To set guards on another patch: hg qguard other.patch +2.6.17 -stable ''' def status(idx): @@ -1723,32 +1739,34 @@ def select(ui, repo, *args, **opts): '''set or print guarded patches to push - use qguard command to set or print guards on patch. then use - qselect to tell mq which guards to use. example: + Use the qguard command to set or print guards on patch, then use + qselect to tell mq which guards to use. A patch will be pushed if it + has no guards or any positive guards match the currently selected guard, + but will not be pushed if any negative guards match the current guard. + For example: - qguard foo.patch -stable (nagative guard) - qguard bar.patch +stable (posative guard) + qguard foo.patch -stable (negative guard) + qguard bar.patch +stable (positive guard) qselect stable - this sets "stable" guard. mq will skip foo.patch (because it has - nagative match) but push bar.patch (because it has posative - match). patch is pushed if any posative guards match and no - nagative guards match. + This activates the "stable" guard. mq will skip foo.patch (because + it has a negative match) but push bar.patch (because it + has a positive match). - with no arguments, default is to print current active guards. - with arguments, set active guards as given. + With no arguments, prints the currently active guards. + With one argument, sets the active guard. - use -n/--none to deactivate guards (no other arguments needed). - when no guards active, patches with posative guards are skipped, - patches with nagative guards are pushed. + Use -n/--none to deactivate guards (no other arguments needed). + When no guards are active, patches with positive guards are skipped + and patches with negative guards are pushed. - qselect can change guards of applied patches. it does not pop - guarded patches by default. use --pop to pop back to last applied - patch that is not guarded. use --reapply (implies --pop) to push - back to current patch afterwards, but skip guarded patches. + qselect can change the guards on applied patches. It does not pop + guarded patches by default. Use --pop to pop back to the last applied + patch that is not guarded. Use --reapply (which implies --pop) to push + back to the current patch afterwards, but skip guarded patches. - use -s/--series to print list of all guards in series file (no - other arguments needed). use -v for more information.''' + Use -s/--series to print a list of all guards in the series file (no + other arguments needed). Use -v for more information.''' q = repo.mq guards = q.active() @@ -1885,7 +1903,10 @@ (commit, commands.table["^commit|ci"][1], 'hg qcommit [OPTION]... [FILE]...'), - "^qdiff": (diff, [], 'hg qdiff [FILE]...'), + "^qdiff": (diff, + [('I', 'include', [], _('include names matching the given patterns')), + ('X', 'exclude', [], _('exclude names matching the given patterns'))], + 'hg qdiff [-I] [-X] [FILE]...'), "qdelete|qremove|qrm": (delete, [('k', 'keep', None, _('keep patch file'))], @@ -1914,10 +1935,11 @@ 'hg qinit [-c]'), "qnew": (new, - [('m', 'message', '', _('use as commit message')), + [('e', 'edit', None, _('edit commit message')), + ('m', 'message', '', _('use as commit message')), ('l', 'logfile', '', _('read the commit message from ')), ('f', 'force', None, _('import uncommitted changes into patch'))], - 'hg qnew [-m TEXT] [-l FILE] [-f] PATCH'), + 'hg qnew [-e] [-m TEXT] [-l FILE] [-f] PATCH'), "qnext": (next, [], 'hg qnext'), "qprev": (prev, [], 'hg qprev'), "^qpop": @@ -1939,8 +1961,10 @@ [('e', 'edit', None, _('edit commit message')), ('m', 'message', '', _('change commit message with ')), ('l', 'logfile', '', _('change commit message with content')), - ('s', 'short', None, 'short refresh')], - 'hg qrefresh [-e] [-m TEXT] [-l FILE] [-s]'), + ('s', 'short', None, 'short refresh'), + ('I', 'include', [], _('include names matching the given patterns')), + ('X', 'exclude', [], _('exclude names matching the given patterns'))], + 'hg qrefresh [-I] [-X] [-e] [-m TEXT] [-l FILE] [-s] FILES...'), 'qrename|qmv': (rename, [], 'hg qrename PATCH1 [PATCH2]'), "qrestore": diff -r d77022db1bca -r f4fc0575e8fa mercurial/commands.py --- a/mercurial/commands.py Fri Aug 18 10:24:04 2006 -0700 +++ b/mercurial/commands.py Fri Aug 18 13:01:40 2006 -0700 @@ -1681,44 +1681,7 @@ ui.debug(_('message:\n%s\n') % message) files, fuzz = patch.patch(tmpname, ui, strip=strip, cwd=repo.root) - removes = [] - if len(files) > 0: - cfiles = files.keys() - copies = [] - copts = {'after': False, 'force': False} - cwd = repo.getcwd() - if cwd: - cfiles = [util.pathto(cwd, f) for f in files.keys()] - for f in files: - ctype, gp = files[f] - if ctype == 'RENAME': - copies.append((gp.oldpath, gp.path, gp.copymod)) - removes.append(gp.oldpath) - elif ctype == 'COPY': - copies.append((gp.oldpath, gp.path, gp.copymod)) - elif ctype == 'DELETE': - removes.append(gp.path) - for src, dst, after in copies: - absdst = os.path.join(repo.root, dst) - if not after and os.path.exists(absdst): - raise util.Abort(_('patch creates existing file %s') % dst) - if cwd: - src, dst = [util.pathto(cwd, f) for f in (src, dst)] - copts['after'] = after - errs, copied = docopy(ui, repo, (src, dst), copts, wlock=wlock) - if errs: - raise util.Abort(errs) - if removes: - repo.remove(removes, True, wlock=wlock) - for f in files: - ctype, gp = files[f] - if gp and gp.mode: - x = gp.mode & 0100 != 0 - dst = os.path.join(repo.root, gp.path) - util.set_exec(dst, x) - cmdutil.addremove(repo, cfiles, wlock=wlock) - files = files.keys() - files.extend([r for r in removes if r not in files]) + files = patch.updatedir(ui, repo, files, wlock=wlock) repo.commit(files, message, user, date, wlock=wlock, lock=lock) finally: os.unlink(tmpname) diff -r d77022db1bca -r f4fc0575e8fa mercurial/patch.py --- a/mercurial/patch.py Fri Aug 18 10:24:04 2006 -0700 +++ b/mercurial/patch.py Fri Aug 18 13:01:40 2006 -0700 @@ -11,6 +11,28 @@ demandload(globals(), "cmdutil mdiff util") demandload(globals(), "cStringIO email.Parser os re shutil sys tempfile") +# helper functions + +def copyfile(src, dst, basedir=None): + if not basedir: + basedir = os.getcwd() + + abssrc, absdst = [os.path.join(basedir, n) for n in (src, dst)] + if os.path.exists(absdst): + raise util.Abort(_("cannot create %s: destination already exists") % + dst) + + targetdir = os.path.dirname(absdst) + if not os.path.isdir(targetdir): + os.makedirs(targetdir) + try: + shutil.copyfile(abssrc, absdst) + shutil.copymode(abssrc, absdst) + except shutil.Error, inst: + raise util.Abort(str(inst)) + +# public functions + def extract(ui, fileobj): '''extract patch from data read from fileobj. @@ -174,21 +196,7 @@ if not p.copymod: continue - if os.path.exists(p.path): - raise util.Abort(_("cannot create %s: destination already exists") % - p.path) - - (src, dst) = [os.path.join(os.getcwd(), n) - for n in (p.oldpath, p.path)] - - targetdir = os.path.dirname(dst) - if not os.path.isdir(targetdir): - os.makedirs(targetdir) - try: - shutil.copyfile(src, dst) - shutil.copymode(src, dst) - except shutil.Error, inst: - raise util.Abort(str(inst)) + copyfile(p.oldpath, p.path) # rewrite patch hunk while pfline < p.lineno: @@ -281,6 +289,45 @@ ignoreblanklines=(opts.get('ignore_blank_lines') or ui.configbool('diff', 'ignoreblanklines', None))) +def updatedir(ui, repo, patches, wlock=None): + '''Update dirstate after patch application according to metadata''' + if not patches: + return + copies = [] + removes = [] + cfiles = patches.keys() + copts = {'after': False, 'force': False} + cwd = repo.getcwd() + if cwd: + cfiles = [util.pathto(cwd, f) for f in patches.keys()] + for f in patches: + ctype, gp = patches[f] + if ctype == 'RENAME': + copies.append((gp.oldpath, gp.path, gp.copymod)) + removes.append(gp.oldpath) + elif ctype == 'COPY': + copies.append((gp.oldpath, gp.path, gp.copymod)) + elif ctype == 'DELETE': + removes.append(gp.path) + for src, dst, after in copies: + if not after: + copyfile(src, dst, repo.root) + repo.copy(src, dst, wlock=wlock) + if removes: + repo.remove(removes, True, wlock=wlock) + for f in patches: + ctype, gp = patches[f] + if gp and gp.mode: + x = gp.mode & 0100 != 0 + dst = os.path.join(repo.root, gp.path) + util.set_exec(dst, x) + cmdutil.addremove(repo, cfiles, wlock=wlock) + files = patches.keys() + files.extend([r for r in removes if r not in files]) + files.sort() + + return files + def diff(repo, node1=None, node2=None, files=None, match=util.always, fp=None, changes=None, opts=None): '''print diff of changes to files between two nodes, or node and @@ -296,10 +343,27 @@ if not node1: node1 = repo.dirstate.parents()[0] + + clcache = {} + def getchangelog(n): + if n not in clcache: + clcache[n] = repo.changelog.read(n) + return clcache[n] + mcache = {} + def getmanifest(n): + if n not in mcache: + mcache[n] = repo.manifest.read(n) + return mcache[n] + fcache = {} + def getfile(f): + if f not in fcache: + fcache[f] = repo.file(f) + return fcache[f] + # reading the data for node1 early allows it to play nicely # with repo.status and the revlog cache. - change = repo.changelog.read(node1) - mmap = repo.manifest.read(change[0]) + change = getchangelog(node1) + mmap = getmanifest(change[0]) date1 = util.datestr(change[2]) if not changes: @@ -320,17 +384,32 @@ if not modified and not added and not removed: return + def renamedbetween(f, n1, n2): + r1, r2 = map(repo.changelog.rev, (n1, n2)) + src = None + while r2 > r1: + cl = getchangelog(n2)[0] + m = getmanifest(cl) + try: + src = getfile(f).renamed(m[f]) + except KeyError: + return None + if src: + f = src[0] + n2 = repo.changelog.parents(n2)[0] + r2 = repo.changelog.rev(n2) + return src + if node2: - change = repo.changelog.read(node2) - mmap2 = repo.manifest.read(change[0]) + change = getchangelog(node2) + mmap2 = getmanifest(change[0]) _date2 = util.datestr(change[2]) def date2(f): return _date2 def read(f): - return repo.file(f).read(mmap2[f]) + return getfile(f).read(mmap2[f]) def renamed(f): - src = repo.file(f).renamed(mmap2[f]) - return src and src[0] or None + return renamedbetween(f, node1, node2) else: tz = util.makedate()[1] _date2 = util.datestr() @@ -343,7 +422,18 @@ def read(f): return repo.wread(f) def renamed(f): - return repo.dirstate.copies.get(f) + src = repo.dirstate.copies.get(f) + parent = repo.dirstate.parents()[0] + if src: + f = src[0] + of = renamedbetween(f, node1, parent) + if of: + return of + elif src: + cl = getchangelog(parent)[0] + return (src, getmanifest(cl)[src]) + else: + return None if repo.ui.quiet: r = None @@ -357,7 +447,7 @@ src = renamed(f) if src: copied[f] = src - srcs = [x[1] for x in copied.items()] + srcs = [x[1][0] for x in copied.items()] all = modified + added + removed all.sort() @@ -366,7 +456,7 @@ tn = None dodiff = True if f in mmap: - to = repo.file(f).read(mmap[f]) + to = getfile(f).read(mmap[f]) if f not in removed: tn = read(f) if opts.git: @@ -385,13 +475,13 @@ else: mode = gitmode(util.is_exec(repo.wjoin(f), None)) if f in copied: - a = copied[f] + a, arev = copied[f] omode = gitmode(mmap.execf(a)) addmodehdr(header, omode, mode) op = a in removed and 'rename' or 'copy' header.append('%s from %s\n' % (op, a)) header.append('%s to %s\n' % (op, f)) - to = repo.file(a).read(mmap[a]) + to = getfile(a).read(arev) else: header.append('new file mode %s\n' % mode) elif f in removed: diff -r d77022db1bca -r f4fc0575e8fa tests/README --- a/tests/README Fri Aug 18 10:24:04 2006 -0700 +++ b/tests/README Fri Aug 18 13:01:40 2006 -0700 @@ -28,6 +28,6 @@ - diff will show the current time - use hg diff | sed "s/\(\(---\|+++\) [a-zA-Z0-9_/.-]*\).*/\1/" to strip - dates - + use hg diff | sed -e "s/\(+++ [a-zA-Z0-9_/.-]*\).*/\1/" \ + -e "s/\(--- [a-zA-Z0-9_/.-]*\).*/\1/" + to strip dates diff -r d77022db1bca -r f4fc0575e8fa tests/test-git-export --- a/tests/test-git-export Fri Aug 18 10:24:04 2006 -0700 +++ b/tests/test-git-export Fri Aug 18 13:01:40 2006 -0700 @@ -8,22 +8,26 @@ echo new > new hg ci -Amnew -d '0 0' echo '% new file' -hg diff --git -r 0 | sed "s/\(\(---\|+++\) [a-zA-Z0-9_/.-]*\).*/\1/" +hg diff --git -r 0 | sed -e "s/\(+++ [a-zA-Z0-9_/.-]*\).*/\1/" \ + -e "s/\(--- [a-zA-Z0-9_/.-]*\).*/\1/" hg cp new copy hg ci -mcopy -d '0 0' echo '% copy' -hg diff --git -r 1:tip | sed "s/\(\(---\|+++\) [a-zA-Z0-9_/.-]*\).*/\1/" +hg diff --git -r 1:tip | sed -e "s/\(+++ [a-zA-Z0-9_/.-]*\).*/\1/" \ + -e "s/\(--- [a-zA-Z0-9_/.-]*\).*/\1/" hg mv copy rename hg ci -mrename -d '0 0' echo '% rename' -hg diff --git -r 2:tip | sed "s/\(\(---\|+++\) [a-zA-Z0-9_/.-]*\).*/\1/" +hg diff --git -r 2:tip | sed -e "s/\(+++ [a-zA-Z0-9_/.-]*\).*/\1/" \ + -e "s/\(--- [a-zA-Z0-9_/.-]*\).*/\1/" hg rm rename hg ci -mdelete -d '0 0' echo '% delete' -hg diff --git -r 3:tip | sed "s/\(\(---\|+++\) [a-zA-Z0-9_/.-]*\).*/\1/" +hg diff --git -r 3:tip | sed -e "s/\(+++ [a-zA-Z0-9_/.-]*\).*/\1/" \ + -e "s/\(--- [a-zA-Z0-9_/.-]*\).*/\1/" cat > src <> dst hg ci -mrenamemod -d '0 0' echo '% rename+mod+chmod' -hg diff --git -r 6:tip | sed "s/\(\(---\|+++\) [a-zA-Z0-9_/.-]*\).*/\1/" +hg diff --git -r 6:tip | sed -e "s/\(+++ [a-zA-Z0-9_/.-]*\).*/\1/" \ + -e "s/\(--- [a-zA-Z0-9_/.-]*\).*/\1/" diff -r d77022db1bca -r f4fc0575e8fa tests/test-mq --- a/tests/test-mq Fri Aug 18 10:24:04 2006 -0700 +++ b/tests/test-mq Fri Aug 18 13:01:40 2006 -0700 @@ -126,3 +126,30 @@ hg ci -Ama hg strip tip 2>&1 | sed 's/\(saving bundle to \).*/\1/' hg unbundle .hg/strip-backup/* + +cat >>$HGTMP/.hgrc < new +chmod +x new +hg add new +hg qrefresh +sed -e "s/\(+++ [a-zA-Z0-9_/.-]*\).*/\1/" \ + -e "s/\(--- [a-zA-Z0-9_/.-]*\).*/\1/" .hg/patches/new + +hg qnew -m'copy file' copy +hg cp new copy +hg qrefresh +sed -e "s/\(+++ [a-zA-Z0-9_/.-]*\).*/\1/" \ + -e "s/\(--- [a-zA-Z0-9_/.-]*\).*/\1/" .hg/patches/copy + +hg qpop +hg qpush +hg qdiff diff -r d77022db1bca -r f4fc0575e8fa tests/test-mq.out --- a/tests/test-mq.out Fri Aug 18 10:24:04 2006 -0700 +++ b/tests/test-mq.out Fri Aug 18 13:01:40 2006 -0700 @@ -127,3 +127,22 @@ adding file changes added 1 changesets with 1 changes to 1 files (run 'hg update' to get a working copy) +new file + +diff --git a/new b/new +new file mode 100755 +--- /dev/null ++++ b/new +@@ -0,0 +1,1 @@ ++foo +copy file + +diff --git a/new b/copy +copy from new +copy to copy +Now at: new +applying copy +Now at: copy +diff --git a/new b/copy +copy from new +copy to copy