Mercurial > public > mercurial-scm > hg-stable
diff mercurial/phases.py @ 45131:61e7464477ac
phases: sparsify phaseroots and phasesets
As final step of dealing with the holes in the phase numbers, make
phaseroots and phasesets both dictionaries indexed by the phase number.
Further adjust the interface of the C module by pushing the node to
revision mapping down as it is cheaper on the C side to deal with
revision numbers.
Overall, the patch series improves a no-change "hg up" for my NetBSD test
repository from 4.7s to 1.3s.
Differential Revision: https://phab.mercurial-scm.org/D8698
author | Joerg Sonnenberger <joerg@bec.de> |
---|---|
date | Wed, 08 Jul 2020 00:36:36 +0200 |
parents | b1e51ef4e536 |
children | f025b97f3758 |
line wrap: on
line diff
--- a/mercurial/phases.py Tue Jul 07 14:01:12 2020 +0530 +++ b/mercurial/phases.py Wed Jul 08 00:36:36 2020 +0200 @@ -170,7 +170,7 @@ """ repo = repo.unfiltered() dirty = False - roots = [set() for i in range(max(allphases) + 1)] + roots = {i: set() for i in allphases} try: f, pending = txnutil.trypending(repo.root, repo.svfs, b'phaseroots') try: @@ -333,7 +333,11 @@ if len(cl) >= self._loadedrevslen: self.invalidate() self.loadphaserevs(repo) - return any(self.phaseroots[1:]) + return any( + revs + for phase, revs in pycompat.iteritems(self.phaseroots) + if phase != public + ) def nonpublicphaseroots(self, repo): """returns the roots of all non-public phases @@ -346,7 +350,13 @@ if len(cl) >= self._loadedrevslen: self.invalidate() self.loadphaserevs(repo) - return set().union(*[roots for roots in self.phaseroots[1:] if roots]) + return set().union( + *[ + revs + for phase, revs in pycompat.iteritems(self.phaseroots) + if phase != public + ] + ) def getrevset(self, repo, phases, subset=None): """return a smartset for the given phases""" @@ -405,7 +415,7 @@ # Shallow copy meant to ensure isolation in # advance/retractboundary(), nothing more. ph = self.__class__(None, None, _load=False) - ph.phaseroots = self.phaseroots[:] + ph.phaseroots = self.phaseroots.copy() ph.dirty = self.dirty ph.opener = self.opener ph._loadedrevslen = self._loadedrevslen @@ -425,21 +435,12 @@ def _getphaserevsnative(self, repo): repo = repo.unfiltered() - nativeroots = [] - for phase in trackedphases: - nativeroots.append( - pycompat.maplist(repo.changelog.rev, self.phaseroots[phase]) - ) - revslen, phasesets = repo.changelog.computephases(nativeroots) - phasesets2 = [set() for phase in range(max(allphases) + 1)] - for phase, phaseset in zip(allphases, phasesets): - phasesets2[phase] = phaseset - return revslen, phasesets2 + return repo.changelog.computephases(self.phaseroots) def _computephaserevspure(self, repo): repo = repo.unfiltered() cl = repo.changelog - self._phasesets = [set() for phase in range(max(allphases) + 1)] + self._phasesets = {phase: set() for phase in allphases} lowerroots = set() for phase in reversed(trackedphases): roots = pycompat.maplist(cl.rev, self.phaseroots[phase]) @@ -493,7 +494,7 @@ f.close() def _write(self, fp): - for phase, roots in enumerate(self.phaseroots): + for phase, roots in pycompat.iteritems(self.phaseroots): for h in sorted(roots): fp.write(b'%i %s\n' % (phase, hex(h))) self.dirty = False @@ -575,7 +576,11 @@ return changes def retractboundary(self, repo, tr, targetphase, nodes): - oldroots = self.phaseroots[: targetphase + 1] + oldroots = { + phase: revs + for phase, revs in pycompat.iteritems(self.phaseroots) + if phase <= targetphase + } if tr is None: phasetracking = None else: @@ -594,7 +599,7 @@ # find the phase of the affected revision for phase in pycompat.xrange(targetphase, -1, -1): if phase: - roots = oldroots[phase] + roots = oldroots.get(phase, []) revs = set(repo.revs(b'%ln::%ld', roots, affected)) affected -= revs else: # public phase @@ -648,7 +653,7 @@ """ filtered = False has_node = repo.changelog.index.has_node # to filter unknown nodes - for phase, nodes in enumerate(self.phaseroots): + for phase, nodes in pycompat.iteritems(self.phaseroots): missing = sorted(node for node in nodes if not has_node(node)) if missing: for mnode in missing: