# HG changeset patch # User Pierre-Yves David # Date 2021-09-22 13:17:12 # Node ID 5d68c4eedd66559f9f7d3fc395fcb5ad44e1fb0e # Parent 40dd560860560960a4ad413c604716b1e2c771d1 dirstate: move parent state handling in the dirstatemap This involves dirstatemap data mostly. Moving this one level down will remove the needs for the dirstatemap to expose some of its internals. This will help us to simplify more code further. Differential Revision: https://phab.mercurial-scm.org/D11505 diff --git a/mercurial/dirstate.py b/mercurial/dirstate.py --- a/mercurial/dirstate.py +++ b/mercurial/dirstate.py @@ -381,39 +381,10 @@ class dirstate(object): oldp2 = self._pl[1] if self._origpl is None: self._origpl = self._pl - self._map.setparents(p1, p2) - copies = {} nullid = self._nodeconstants.nullid - if oldp2 != nullid and p2 == nullid: - candidatefiles = self._map.non_normal_or_other_parent_paths() - - for f in candidatefiles: - s = self._map.get(f) - if s is None: - continue - - # Discard "merged" markers when moving away from a merge state - if s.merged: - source = self._map.copymap.get(f) - if source: - copies[f] = source - self._map.reset_state( - f, - wc_tracked=True, - p1_tracked=True, - possibly_dirty=True, - ) - # Also fix up otherparent markers - elif s.from_p2: - source = self._map.copymap.get(f) - if source: - copies[f] = source - self._map.reset_state( - f, - p1_tracked=False, - wc_tracked=True, - ) - return copies + # True if we need to fold p2 related state back to a linear case + fold_p2 = oldp2 != nullid and p2 == nullid + return self._map.setparents(p1, p2, fold_p2=fold_p2) def setbranch(self, branch): self.__class__._branch.set(self, encoding.fromlocal(branch)) diff --git a/mercurial/dirstatemap.py b/mercurial/dirstatemap.py --- a/mercurial/dirstatemap.py +++ b/mercurial/dirstatemap.py @@ -428,9 +428,40 @@ class dirstatemap(object): return self._parents - def setparents(self, p1, p2): + def setparents(self, p1, p2, fold_p2=False): self._parents = (p1, p2) self._dirtyparents = True + copies = {} + if fold_p2: + candidatefiles = self.non_normal_or_other_parent_paths() + + for f in candidatefiles: + s = self.get(f) + if s is None: + continue + + # Discard "merged" markers when moving away from a merge state + if s.merged: + source = self.copymap.get(f) + if source: + copies[f] = source + self.reset_state( + f, + wc_tracked=True, + p1_tracked=True, + possibly_dirty=True, + ) + # Also fix up otherparent markers + elif s.from_p2: + source = self.copymap.get(f) + if source: + copies[f] = source + self.reset_state( + f, + p1_tracked=False, + wc_tracked=True, + ) + return copies def read(self): # ignore HG_PENDING because identity is used only for writing @@ -769,9 +800,40 @@ if rustmod is not None: # File doesn't exist, so the current state is empty return b'' - def setparents(self, p1, p2): + def setparents(self, p1, p2, fold_p2=False): self._parents = (p1, p2) self._dirtyparents = True + copies = {} + if fold_p2: + candidatefiles = self.non_normal_or_other_parent_paths() + + for f in candidatefiles: + s = self.get(f) + if s is None: + continue + + # Discard "merged" markers when moving away from a merge state + if s.merged: + source = self.copymap.get(f) + if source: + copies[f] = source + self.reset_state( + f, + wc_tracked=True, + p1_tracked=True, + possibly_dirty=True, + ) + # Also fix up otherparent markers + elif s.from_p2: + source = self.copymap.get(f) + if source: + copies[f] = source + self.reset_state( + f, + p1_tracked=False, + wc_tracked=True, + ) + return copies def parents(self): if not self._parents: