dirstate: ignore stat data for files that were updated too recently
This should fix the race where
hg commit foo
<change foo without changing its size>
happens in the same second and status is fooled into thinking foo
is clean.
A configuration item is used to determine the timeout, since different
filesystems may have different requirements (I think VFAT needs 3s,
while most Unix filesystems are fine with 1s).
--- a/mercurial/dirstate.py Thu Mar 20 11:12:35 2008 -0500
+++ b/mercurial/dirstate.py Wed Mar 19 17:55:21 2008 -0300
@@ -10,7 +10,7 @@
from node import nullid
from i18n import _
import struct, os, bisect, stat, strutil, util, errno, ignore
-import cStringIO, osutil
+import cStringIO, osutil, sys
_unknown = ('?', 0, 0, 0)
_format = ">cllll"
@@ -66,6 +66,12 @@
elif name == '_checkexec':
self._checkexec = util.checkexec(self._root)
return self._checkexec
+ elif name == '_limit':
+ try:
+ self._limit = int(self._ui.config('ui', 'limit', 1))
+ except ValueError:
+ self._limit = 1
+ return self._limit
else:
raise AttributeError, name
@@ -335,6 +341,11 @@
def write(self):
if not self._dirty:
return
+ st = self._opener("dirstate", "w", atomictemp=True)
+ if self._limit > 0:
+ limit = util.fstat(st).st_mtime - self._limit
+ else:
+ limit = sys.maxint
cs = cStringIO.StringIO()
copymap = self._copymap
pack = struct.pack
@@ -343,10 +354,11 @@
for f, e in self._map.iteritems():
if f in copymap:
f = "%s\0%s" % (f, copymap[f])
+ if e[3] > limit and e[0] == 'n':
+ e = (e[0], 0, -1, -1, 0)
e = pack(_format, e[0], e[1], e[2], e[3], len(f))
write(e)
write(f)
- st = self._opener("dirstate", "w", atomictemp=True)
st.write(cs.getvalue())
st.rename()
self._dirty = self._dirtypl = False
--- a/tests/test-filebranch.out Thu Mar 20 11:12:35 2008 -0500
+++ b/tests/test-filebranch.out Wed Mar 19 17:55:21 2008 -0300
@@ -3,10 +3,10 @@
creating branch a
creating branch b
we shouldn't have anything but n state here
-n 644 2 bar
-n 644 3 baz
-n 644 3 foo
-n 644 2 quux
+n 0 -1 bar
+n 0 -1 baz
+n 0 -1 foo
+n 0 -1 quux
merging
pulling from ../a
searching for changes
--- a/tests/test-rebuildstate.out Thu Mar 20 11:12:35 2008 -0500
+++ b/tests/test-rebuildstate.out Wed Mar 19 17:55:21 2008 -0300
@@ -2,7 +2,7 @@
adding foo
% state dump
a 0 -1 baz
-n 644 0 foo
+n 0 -1 foo
r 0 0 bar
% status
A baz