Mercurial > hg
changeset 20885:f49d60fa40a5
fncache: clean up fncache during strips
Previously the fncache was cleaned up at read time by noticing when it was out
of sync. This caused writes to happen outside the scope of transactions and
could have caused race conditions. With this change, we'll keep the fncache
up-to-date as we go by removing old entries during repair.strip.
author | Durham Goode <durham@fb.com> |
---|---|
date | Mon, 24 Mar 2014 15:43:15 -0700 |
parents | 2efdd186925d |
children | 203908968644 |
files | mercurial/repair.py mercurial/store.py tests/test-strip.t |
diffstat | 3 files changed, 30 insertions(+), 0 deletions(-) [+] |
line wrap: on
line diff
--- a/mercurial/repair.py Mon Mar 24 15:35:07 2014 -0700 +++ b/mercurial/repair.py Mon Mar 24 15:43:15 2014 -0700 @@ -134,6 +134,8 @@ for i in xrange(offset, len(tr.entries)): file, troffset, ignore = tr.entries[i] repo.sopener(file, 'a').truncate(troffset) + if troffset == 0: + repo.store.markremoved(file) tr.close() except: # re-raises tr.abort()
--- a/mercurial/store.py Mon Mar 24 15:35:07 2014 -0700 +++ b/mercurial/store.py Mon Mar 24 15:43:15 2014 -0700 @@ -343,6 +343,9 @@ def invalidatecaches(self): pass + def markremoved(self, fn): + pass + def __contains__(self, path): '''Checks if the store contains path''' path = "/".join(("data", path)) @@ -421,6 +424,15 @@ self._dirty = True self.entries.add(fn) + def remove(self, fn): + if self.entries is None: + self._load() + try: + self.entries.remove(fn) + self._dirty = True + except KeyError: + pass + def __contains__(self, fn): if self.entries is None: self._load() @@ -495,6 +507,9 @@ def invalidatecaches(self): self.fncache.entries = None + def markremoved(self, fn): + self.fncache.remove(fn) + def _exists(self, f): ef = self.encode(f) try:
--- a/tests/test-strip.t Mon Mar 24 15:35:07 2014 -0700 +++ b/tests/test-strip.t Mon Mar 24 15:43:15 2014 -0700 @@ -336,6 +336,19 @@ saved backup bundle to $TESTTMP/test/.hg/strip-backup/*-backup.hg (glob) $ restore +verify fncache is kept up-to-date + + $ touch a + $ hg ci -qAm a + $ cat .hg/store/fncache | sort + data/a.i + data/bar.i + $ hg strip tip + 0 files updated, 0 files merged, 1 files removed, 0 files unresolved + saved backup bundle to $TESTTMP/test/.hg/strip-backup/*-backup.hg (glob) + $ cat .hg/store/fncache + data/bar.i + stripping an empty revset $ hg strip "1 and not 1"