##// END OF EJS Templates
fix issue 322....
Vadim Gelfer -
r2953:3d554784 default
parent child Browse files
Show More
@@ -0,0 +1,34 b''
1 # strutil.py - string utilities for Mercurial
2 #
3 # Copyright 2006 Vadim Gelfer <vadim.gelfer@gmail.com>
4 #
5 # This software may be used and distributed according to the terms
6 # of the GNU General Public License, incorporated herein by reference.
7
8 def findall(haystack, needle, start=0, end=None):
9 if end is None:
10 end = len(haystack)
11 if end < 0:
12 end += len(haystack)
13 if start < 0:
14 start += len(haystack)
15 while start < end:
16 c = haystack.find(needle, start, end)
17 if c == -1:
18 break
19 yield c
20 start = c + 1
21
22 def rfindall(haystack, needle, start=0, end=None):
23 if end is None:
24 end = len(haystack)
25 if end < 0:
26 end += len(haystack)
27 if start < 0:
28 start += len(haystack)
29 while end >= 0:
30 c = haystack.rfind(needle, start, end)
31 if c == -1:
32 break
33 yield c
34 end = c - 1
@@ -0,0 +1,12 b''
1 % file replaced with directory
2 adding a
3 % should fail - would corrupt dirstate
4 abort: file named 'a' already in dirstate
5 % directory replaced with file
6 adding a/a
7 % should fail - would corrupt dirstate
8 abort: directory named 'a' already in dirstate
9 % directory replaced with file
10 adding b/c/d
11 % should fail - would corrupt dirstate
12 abort: directory named 'b' already in dirstate
@@ -10,7 +10,7 b' of the GNU General Public License, incor'
10 from node import *
10 from node import *
11 from i18n import gettext as _
11 from i18n import gettext as _
12 from demandload import *
12 from demandload import *
13 demandload(globals(), "struct os time bisect stat util re errno")
13 demandload(globals(), "struct os time bisect stat strutil util re errno")
14
14
15 class dirstate(object):
15 class dirstate(object):
16 format = ">cllll"
16 format = ">cllll"
@@ -22,6 +22,7 b' class dirstate(object):'
22 self.ui = ui
22 self.ui = ui
23 self.map = None
23 self.map = None
24 self.pl = None
24 self.pl = None
25 self.dirs = None
25 self.copies = {}
26 self.copies = {}
26 self.ignorefunc = None
27 self.ignorefunc = None
27 self.blockignore = False
28 self.blockignore = False
@@ -197,6 +198,38 b' class dirstate(object):'
197 def copied(self, file):
198 def copied(self, file):
198 return self.copies.get(file, None)
199 return self.copies.get(file, None)
199
200
201 def initdirs(self):
202 if self.dirs is None:
203 self.dirs = {}
204 for f in self.map:
205 self.updatedirs(f, 1)
206
207 def updatedirs(self, path, delta):
208 if self.dirs is not None:
209 for c in strutil.findall(path, '/'):
210 pc = path[:c]
211 self.dirs.setdefault(pc, 0)
212 self.dirs[pc] += delta
213
214 def checkshadows(self, files):
215 def prefixes(f):
216 for c in strutil.rfindall(f, '/'):
217 yield f[:c]
218 self.lazyread()
219 self.initdirs()
220 seendirs = {}
221 for f in files:
222 if self.dirs.get(f):
223 raise util.Abort(_('directory named %r already in dirstate') %
224 f)
225 for d in prefixes(f):
226 if d in seendirs:
227 break
228 if d in self.map:
229 raise util.Abort(_('file named %r already in dirstate') %
230 d)
231 seendirs[d] = True
232
200 def update(self, files, state, **kw):
233 def update(self, files, state, **kw):
201 ''' current states:
234 ''' current states:
202 n normal
235 n normal
@@ -207,10 +240,16 b' class dirstate(object):'
207 if not files: return
240 if not files: return
208 self.lazyread()
241 self.lazyread()
209 self.markdirty()
242 self.markdirty()
243 if state == "a":
244 self.initdirs()
245 self.checkshadows(files)
210 for f in files:
246 for f in files:
211 if state == "r":
247 if state == "r":
212 self.map[f] = ('r', 0, 0, 0)
248 self.map[f] = ('r', 0, 0, 0)
249 self.updatedirs(f, -1)
213 else:
250 else:
251 if state == "a":
252 self.updatedirs(f, 1)
214 s = os.lstat(self.wjoin(f))
253 s = os.lstat(self.wjoin(f))
215 st_size = kw.get('st_size', s.st_size)
254 st_size = kw.get('st_size', s.st_size)
216 st_mtime = kw.get('st_mtime', s.st_mtime)
255 st_mtime = kw.get('st_mtime', s.st_mtime)
@@ -222,9 +261,11 b' class dirstate(object):'
222 if not files: return
261 if not files: return
223 self.lazyread()
262 self.lazyread()
224 self.markdirty()
263 self.markdirty()
264 self.initdirs()
225 for f in files:
265 for f in files:
226 try:
266 try:
227 del self.map[f]
267 del self.map[f]
268 self.updatedirs(f, -1)
228 except KeyError:
269 except KeyError:
229 self.ui.warn(_("not in dirstate: %s!\n") % f)
270 self.ui.warn(_("not in dirstate: %s!\n") % f)
230 pass
271 pass
@@ -232,6 +273,7 b' class dirstate(object):'
232 def clear(self):
273 def clear(self):
233 self.map = {}
274 self.map = {}
234 self.copies = {}
275 self.copies = {}
276 self.dirs = None
235 self.markdirty()
277 self.markdirty()
236
278
237 def rebuild(self, parent, files):
279 def rebuild(self, parent, files):
@@ -995,4 +995,3 b' def drop_scheme(scheme, path):'
995 if path.startswith('//'):
995 if path.startswith('//'):
996 path = path[2:]
996 path = path[2:]
997 return path
997 return path
998
@@ -14,15 +14,7 b' echo a > a/a'
14 echo % should fail - would corrupt dirstate
14 echo % should fail - would corrupt dirstate
15 hg add a/a
15 hg add a/a
16
16
17 echo % should fail - if add succeeded, would corrupt manifest
18 hg commit -mb
19
20 echo % should fail if commit succeeded - manifest is corrupt
21 hg verify
22
23 cd ..
17 cd ..
24 echo % should succeed, but manifest is corrupt
25 hg --debug --traceback clone a b
26
18
27 echo % directory replaced with file
19 echo % directory replaced with file
28
20
@@ -38,8 +30,20 b' echo a > a'
38 echo % should fail - would corrupt dirstate
30 echo % should fail - would corrupt dirstate
39 hg add a
31 hg add a
40
32
41 echo % should fail - if add succeeded, would corrupt manifest
33 cd ..
42 hg commit -mb a
34
35 echo % directory replaced with file
43
36
44 echo % should fail if commit succeeded - manifest is corrupt
37 hg init d
45 hg verify
38 cd d
39 mkdir b
40 mkdir b/c
41 echo a > b/c/d
42 hg commit -Ama
43 rm -rf b
44 echo a > b
45
46 echo % should fail - would corrupt dirstate
47 hg add b
48
49 exit 0
General Comments 0
You need to be logged in to leave comments. Login now