[PATCH 2 of 2] revert: special case 'hg revert --all'
Augie Fackler
raf at durin42.com
Mon Sep 29 14:09:10 CDT 2014
On Fri, Sep 19, 2014 at 06:53:11PM -0700, Durham Goode wrote:
> # HG changeset patch
> # User Durham Goode <durham at fb.com>
> # Date 1411177433 25200
> # Fri Sep 19 18:43:53 2014 -0700
> # Node ID 4ba21a38b9dc7d351e88cc575516443046f6d913
> # Parent b74b7d5f46d5d8ad13ca74e6b740970129090529
> revert: special case 'hg revert --all'
Queued for crew. Sorry for delay.
(Thanks to Pierre-Yves for reminding me.)
>
> On large repos, hg revert --all can take over 13 seconds. This is mainly due to
> it walking the tree three times: once to find the list of files in the
> dirstate, once to find the list of files in the target, and once to compute the
> status from the dirstate to the target.
>
> This optimizes the hg revert --all case to only require the final status. This
> speeds it up to 1.3 seconds or so (with hgwatchman enabled).
>
> Further optimizations could be done for the -r NODE and pattern cases, but they
> are significantly more complex.
>
> diff --git a/mercurial/cmdutil.py b/mercurial/cmdutil.py
> --- a/mercurial/cmdutil.py
> +++ b/mercurial/cmdutil.py
> @@ -2480,34 +2480,43 @@
> # walk dirstate to fill `names`
>
> m = scmutil.match(repo[None], pats, opts)
> - m.bad = lambda x, y: False
> - for abs in repo.walk(m):
> - names[abs] = m.rel(abs), m.exact(abs)
> -
> - # walk target manifest to fill `names`
> -
> - def badfn(path, msg):
> - if path in names:
> - return
> - if path in ctx.substate:
> - return
> - path_ = path + '/'
> - for f in names:
> - if f.startswith(path_):
> + if not m.always() or node != parent:
> + m.bad = lambda x, y: False
> + for abs in repo.walk(m):
> + names[abs] = m.rel(abs), m.exact(abs)
> +
> + # walk target manifest to fill `names`
> +
> + def badfn(path, msg):
> + if path in names:
> return
> - ui.warn("%s: %s\n" % (m.rel(path), msg))
> -
> - m = scmutil.match(ctx, pats, opts)
> - m.bad = badfn
> - for abs in ctx.walk(m):
> - if abs not in names:
> - names[abs] = m.rel(abs), m.exact(abs)
> -
> - # Find status of all file in `names`.
> - m = scmutil.matchfiles(repo, names)
> -
> - changes = repo.status(node1=node, match=m,
> - unknown=True, ignored=True, clean=True)
> + if path in ctx.substate:
> + return
> + path_ = path + '/'
> + for f in names:
> + if f.startswith(path_):
> + return
> + ui.warn("%s: %s\n" % (m.rel(path), msg))
> +
> + m = scmutil.match(ctx, pats, opts)
> + m.bad = badfn
> + for abs in ctx.walk(m):
> + if abs not in names:
> + names[abs] = m.rel(abs), m.exact(abs)
> +
> + # Find status of all file in `names`.
> + m = scmutil.matchfiles(repo, names)
> +
> + changes = repo.status(node1=node, match=m,
> + unknown=True, ignored=True, clean=True)
> + else:
> + changes = repo.status(match=m)
> + for kind in changes:
> + for abs in kind:
> + names[abs] = m.rel(abs), m.exact(abs)
> +
> + m = scmutil.matchfiles(repo, names)
> +
> modified = set(changes[0])
> added = set(changes[1])
> removed = set(changes[2])
> _______________________________________________
> Mercurial-devel mailing list
> Mercurial-devel at selenic.com
> http://selenic.com/mailman/listinfo/mercurial-devel
More information about the Mercurial-devel
mailing list