mirror of
https://github.com/facebook/sapling.git
synced 2024-10-07 15:27:13 +03:00
hg: improve perf interactions with treedirstate
Summary: There are a couple of ways that dirstate and fsmonitor interact with treedirstate that are sub-optimal. When iterating over all files in the dirstate map, use the iterator of keys (`__iter__` rather than `iteritems`) to hit the treedirstate fastpath that doesn't build the dirstate tuples. Use `__getitem__` and catch the `KeyError` rather than `__contains__` followed by `__getitem__`, as the latter involves two look-ups in the tree. Skip the indirect call to `hastrackedfile` and `hasremovedfile` as these add noticable overhead when called many times. Also fix up the `test-check-code` failure for treedirstate. Reviewed By: ryanmce Differential Revision: D6818952 fbshipit-source-id: d49907c282a1b97c66a3d24257bdf54800d7da70
This commit is contained in:
parent
d942f5a88e
commit
4b7dab149a
@ -420,13 +420,11 @@ def overridewalk(orig, self, match, subrepos, unknown, ignored, full=True):
|
||||
if f not in results and matchfn(f))
|
||||
else:
|
||||
if matchalways:
|
||||
visit.update(f for f, st in dmap.iteritems() if f not in results)
|
||||
visit.update(f for f in dmap if f not in results)
|
||||
visit.update(f for f in copymap if f not in results)
|
||||
else:
|
||||
visit.update(f for f, st in dmap.iteritems()
|
||||
if f not in results and matchfn(f))
|
||||
visit.update(f for f in copymap
|
||||
if f not in results and matchfn(f))
|
||||
visit.update(f for f in dmap if f not in results and matchfn(f))
|
||||
visit.update(f for f in copymap if f not in results and matchfn(f))
|
||||
|
||||
audit = pathutil.pathauditor(self._root, cached=True).check
|
||||
auditpass = [f for f in visit if audit(f)]
|
||||
|
@ -237,7 +237,8 @@ class treedirstatemap(object):
|
||||
return self._rmap.hasremovedfile(filename)
|
||||
|
||||
def __contains__(self, filename):
|
||||
return self.hastrackedfile(filename) or self.hasremovedfile(filename)
|
||||
return (self._rmap.hastrackedfile(filename) or
|
||||
self._rmap.hasremovedfile(filename))
|
||||
|
||||
def trackedfiles(self):
|
||||
"""Returns a list of all filenames tracked by the dirstate."""
|
||||
@ -671,7 +672,7 @@ def wrapclose(orig, self):
|
||||
invocations that involve writing to treedirstate.
|
||||
"""
|
||||
# For chg, do not clean up on the "serve" command
|
||||
if 'CHGINTERNALMARK' in os.environ:
|
||||
if 'CHGINTERNALMARK' in encoding.environ:
|
||||
return orig(self)
|
||||
|
||||
try:
|
||||
|
@ -1025,7 +1025,6 @@ class dirstate(object):
|
||||
|
||||
dmap = self._map
|
||||
dmap.preload()
|
||||
dcontains = dmap.__contains__
|
||||
dget = dmap.__getitem__
|
||||
ladd = lookup.append # aka "unsure"
|
||||
madd = modified.append
|
||||
@ -1048,7 +1047,9 @@ class dirstate(object):
|
||||
full = listclean or match.traversedir is not None
|
||||
for fn, st in self.walk(match, subrepos, listunknown, listignored,
|
||||
full=full).iteritems():
|
||||
if not dcontains(fn):
|
||||
try:
|
||||
t = dget(fn)
|
||||
except KeyError:
|
||||
if (listignored or mexact(fn)) and dirignore(fn):
|
||||
if listignored:
|
||||
iadd(fn)
|
||||
@ -1063,7 +1064,6 @@ class dirstate(object):
|
||||
# a list, but falls back to creating a full-fledged iterator in
|
||||
# general. That is much slower than simply accessing and storing the
|
||||
# tuple members one by one.
|
||||
t = dget(fn)
|
||||
state = t[0]
|
||||
mode = t[1]
|
||||
size = t[2]
|
||||
|
@ -129,9 +129,6 @@ New errors are not allowed. Warnings are strongly discouraged.
|
||||
hgext/phabstatus.py:78:
|
||||
> repodir=os.getcwd(), ca_bundle=ca_certs, repo=repo)
|
||||
use pycompat.getcwd instead (py3)
|
||||
hgext/treedirstate.py:674:
|
||||
> if 'CHGINTERNALMARK' in os.environ:
|
||||
use encoding.environ instead (py3)
|
||||
hgext/tweakdefaults.py:275:
|
||||
> if pipei_bufsize != 4096 and os.name == 'nt':
|
||||
use pycompat.osname instead (py3)
|
||||
|
Loading…
Reference in New Issue
Block a user