##// END OF EJS Templates
verify: drop "revlog" from warning message...
Gregory Szorc -
r37428:a6651f5e default
parent child Browse files
Show More
@@ -1,487 +1,487 b''
1 # verify.py - repository integrity checking for Mercurial
1 # verify.py - repository integrity checking for Mercurial
2 #
2 #
3 # Copyright 2006, 2007 Matt Mackall <mpm@selenic.com>
3 # Copyright 2006, 2007 Matt Mackall <mpm@selenic.com>
4 #
4 #
5 # This software may be used and distributed according to the terms of the
5 # This software may be used and distributed according to the terms of the
6 # GNU General Public License version 2 or any later version.
6 # GNU General Public License version 2 or any later version.
7
7
8 from __future__ import absolute_import
8 from __future__ import absolute_import
9
9
10 import os
10 import os
11
11
12 from .i18n import _
12 from .i18n import _
13 from .node import (
13 from .node import (
14 nullid,
14 nullid,
15 short,
15 short,
16 )
16 )
17
17
18 from . import (
18 from . import (
19 error,
19 error,
20 pycompat,
20 pycompat,
21 revlog,
21 revlog,
22 scmutil,
22 scmutil,
23 util,
23 util,
24 )
24 )
25
25
26 def verify(repo):
26 def verify(repo):
27 with repo.lock():
27 with repo.lock():
28 return verifier(repo).verify()
28 return verifier(repo).verify()
29
29
30 def _normpath(f):
30 def _normpath(f):
31 # under hg < 2.4, convert didn't sanitize paths properly, so a
31 # under hg < 2.4, convert didn't sanitize paths properly, so a
32 # converted repo may contain repeated slashes
32 # converted repo may contain repeated slashes
33 while '//' in f:
33 while '//' in f:
34 f = f.replace('//', '/')
34 f = f.replace('//', '/')
35 return f
35 return f
36
36
37 class verifier(object):
37 class verifier(object):
38 # The match argument is always None in hg core, but e.g. the narrowhg
38 # The match argument is always None in hg core, but e.g. the narrowhg
39 # extension will pass in a matcher here.
39 # extension will pass in a matcher here.
40 def __init__(self, repo, match=None):
40 def __init__(self, repo, match=None):
41 self.repo = repo.unfiltered()
41 self.repo = repo.unfiltered()
42 self.ui = repo.ui
42 self.ui = repo.ui
43 self.match = match or scmutil.matchall(repo)
43 self.match = match or scmutil.matchall(repo)
44 self.badrevs = set()
44 self.badrevs = set()
45 self.errors = 0
45 self.errors = 0
46 self.warnings = 0
46 self.warnings = 0
47 self.havecl = len(repo.changelog) > 0
47 self.havecl = len(repo.changelog) > 0
48 self.havemf = len(repo.manifestlog._revlog) > 0
48 self.havemf = len(repo.manifestlog._revlog) > 0
49 self.revlogv1 = repo.changelog.version != revlog.REVLOGV0
49 self.revlogv1 = repo.changelog.version != revlog.REVLOGV0
50 self.lrugetctx = util.lrucachefunc(repo.__getitem__)
50 self.lrugetctx = util.lrucachefunc(repo.__getitem__)
51 self.refersmf = False
51 self.refersmf = False
52 self.fncachewarned = False
52 self.fncachewarned = False
53 # developer config: verify.skipflags
53 # developer config: verify.skipflags
54 self.skipflags = repo.ui.configint('verify', 'skipflags')
54 self.skipflags = repo.ui.configint('verify', 'skipflags')
55
55
56 def warn(self, msg):
56 def warn(self, msg):
57 self.ui.warn(msg + "\n")
57 self.ui.warn(msg + "\n")
58 self.warnings += 1
58 self.warnings += 1
59
59
60 def err(self, linkrev, msg, filename=None):
60 def err(self, linkrev, msg, filename=None):
61 if linkrev is not None:
61 if linkrev is not None:
62 self.badrevs.add(linkrev)
62 self.badrevs.add(linkrev)
63 linkrev = "%d" % linkrev
63 linkrev = "%d" % linkrev
64 else:
64 else:
65 linkrev = '?'
65 linkrev = '?'
66 msg = "%s: %s" % (linkrev, msg)
66 msg = "%s: %s" % (linkrev, msg)
67 if filename:
67 if filename:
68 msg = "%s@%s" % (filename, msg)
68 msg = "%s@%s" % (filename, msg)
69 self.ui.warn(" " + msg + "\n")
69 self.ui.warn(" " + msg + "\n")
70 self.errors += 1
70 self.errors += 1
71
71
72 def exc(self, linkrev, msg, inst, filename=None):
72 def exc(self, linkrev, msg, inst, filename=None):
73 fmsg = pycompat.bytestr(inst)
73 fmsg = pycompat.bytestr(inst)
74 if not fmsg:
74 if not fmsg:
75 fmsg = pycompat.byterepr(inst)
75 fmsg = pycompat.byterepr(inst)
76 self.err(linkrev, "%s: %s" % (msg, fmsg), filename)
76 self.err(linkrev, "%s: %s" % (msg, fmsg), filename)
77
77
78 def checklog(self, obj, name, linkrev):
78 def checklog(self, obj, name, linkrev):
79 if not len(obj) and (self.havecl or self.havemf):
79 if not len(obj) and (self.havecl or self.havemf):
80 self.err(linkrev, _("empty or missing %s") % name)
80 self.err(linkrev, _("empty or missing %s") % name)
81 return
81 return
82
82
83 d = obj.checksize()
83 d = obj.checksize()
84 if d[0]:
84 if d[0]:
85 self.err(None, _("data length off by %d bytes") % d[0], name)
85 self.err(None, _("data length off by %d bytes") % d[0], name)
86 if d[1]:
86 if d[1]:
87 self.err(None, _("index contains %d extra bytes") % d[1], name)
87 self.err(None, _("index contains %d extra bytes") % d[1], name)
88
88
89 if obj.version != revlog.REVLOGV0:
89 if obj.version != revlog.REVLOGV0:
90 if not self.revlogv1:
90 if not self.revlogv1:
91 self.warn(_("warning: `%s' uses revlog format 1") % name)
91 self.warn(_("warning: `%s' uses revlog format 1") % name)
92 elif self.revlogv1:
92 elif self.revlogv1:
93 self.warn(_("warning: `%s' uses revlog format 0") % name)
93 self.warn(_("warning: `%s' uses revlog format 0") % name)
94
94
95 def checkentry(self, obj, i, node, seen, linkrevs, f):
95 def checkentry(self, obj, i, node, seen, linkrevs, f):
96 lr = obj.linkrev(obj.rev(node))
96 lr = obj.linkrev(obj.rev(node))
97 if lr < 0 or (self.havecl and lr not in linkrevs):
97 if lr < 0 or (self.havecl and lr not in linkrevs):
98 if lr < 0 or lr >= len(self.repo.changelog):
98 if lr < 0 or lr >= len(self.repo.changelog):
99 msg = _("rev %d points to nonexistent changeset %d")
99 msg = _("rev %d points to nonexistent changeset %d")
100 else:
100 else:
101 msg = _("rev %d points to unexpected changeset %d")
101 msg = _("rev %d points to unexpected changeset %d")
102 self.err(None, msg % (i, lr), f)
102 self.err(None, msg % (i, lr), f)
103 if linkrevs:
103 if linkrevs:
104 if f and len(linkrevs) > 1:
104 if f and len(linkrevs) > 1:
105 try:
105 try:
106 # attempt to filter down to real linkrevs
106 # attempt to filter down to real linkrevs
107 linkrevs = [l for l in linkrevs
107 linkrevs = [l for l in linkrevs
108 if self.lrugetctx(l)[f].filenode() == node]
108 if self.lrugetctx(l)[f].filenode() == node]
109 except Exception:
109 except Exception:
110 pass
110 pass
111 self.warn(_(" (expected %s)") % " ".join
111 self.warn(_(" (expected %s)") % " ".join
112 (map(pycompat.bytestr, linkrevs)))
112 (map(pycompat.bytestr, linkrevs)))
113 lr = None # can't be trusted
113 lr = None # can't be trusted
114
114
115 try:
115 try:
116 p1, p2 = obj.parents(node)
116 p1, p2 = obj.parents(node)
117 if p1 not in seen and p1 != nullid:
117 if p1 not in seen and p1 != nullid:
118 self.err(lr, _("unknown parent 1 %s of %s") %
118 self.err(lr, _("unknown parent 1 %s of %s") %
119 (short(p1), short(node)), f)
119 (short(p1), short(node)), f)
120 if p2 not in seen and p2 != nullid:
120 if p2 not in seen and p2 != nullid:
121 self.err(lr, _("unknown parent 2 %s of %s") %
121 self.err(lr, _("unknown parent 2 %s of %s") %
122 (short(p2), short(node)), f)
122 (short(p2), short(node)), f)
123 except Exception as inst:
123 except Exception as inst:
124 self.exc(lr, _("checking parents of %s") % short(node), inst, f)
124 self.exc(lr, _("checking parents of %s") % short(node), inst, f)
125
125
126 if node in seen:
126 if node in seen:
127 self.err(lr, _("duplicate revision %d (%d)") % (i, seen[node]), f)
127 self.err(lr, _("duplicate revision %d (%d)") % (i, seen[node]), f)
128 seen[node] = i
128 seen[node] = i
129 return lr
129 return lr
130
130
131 def verify(self):
131 def verify(self):
132 repo = self.repo
132 repo = self.repo
133
133
134 ui = repo.ui
134 ui = repo.ui
135
135
136 if not repo.url().startswith('file:'):
136 if not repo.url().startswith('file:'):
137 raise error.Abort(_("cannot verify bundle or remote repos"))
137 raise error.Abort(_("cannot verify bundle or remote repos"))
138
138
139 if os.path.exists(repo.sjoin("journal")):
139 if os.path.exists(repo.sjoin("journal")):
140 ui.warn(_("abandoned transaction found - run hg recover\n"))
140 ui.warn(_("abandoned transaction found - run hg recover\n"))
141
141
142 if ui.verbose or not self.revlogv1:
142 if ui.verbose or not self.revlogv1:
143 ui.status(_("repository uses revlog format %d\n") %
143 ui.status(_("repository uses revlog format %d\n") %
144 (self.revlogv1 and 1 or 0))
144 (self.revlogv1 and 1 or 0))
145
145
146 mflinkrevs, filelinkrevs = self._verifychangelog()
146 mflinkrevs, filelinkrevs = self._verifychangelog()
147
147
148 filenodes = self._verifymanifest(mflinkrevs)
148 filenodes = self._verifymanifest(mflinkrevs)
149 del mflinkrevs
149 del mflinkrevs
150
150
151 self._crosscheckfiles(filelinkrevs, filenodes)
151 self._crosscheckfiles(filelinkrevs, filenodes)
152
152
153 totalfiles, filerevisions = self._verifyfiles(filenodes, filelinkrevs)
153 totalfiles, filerevisions = self._verifyfiles(filenodes, filelinkrevs)
154
154
155 ui.status(_("%d files, %d changesets, %d total revisions\n") %
155 ui.status(_("%d files, %d changesets, %d total revisions\n") %
156 (totalfiles, len(repo.changelog), filerevisions))
156 (totalfiles, len(repo.changelog), filerevisions))
157 if self.warnings:
157 if self.warnings:
158 ui.warn(_("%d warnings encountered!\n") % self.warnings)
158 ui.warn(_("%d warnings encountered!\n") % self.warnings)
159 if self.fncachewarned:
159 if self.fncachewarned:
160 ui.warn(_('hint: run "hg debugrebuildfncache" to recover from '
160 ui.warn(_('hint: run "hg debugrebuildfncache" to recover from '
161 'corrupt fncache\n'))
161 'corrupt fncache\n'))
162 if self.errors:
162 if self.errors:
163 ui.warn(_("%d integrity errors encountered!\n") % self.errors)
163 ui.warn(_("%d integrity errors encountered!\n") % self.errors)
164 if self.badrevs:
164 if self.badrevs:
165 ui.warn(_("(first damaged changeset appears to be %d)\n")
165 ui.warn(_("(first damaged changeset appears to be %d)\n")
166 % min(self.badrevs))
166 % min(self.badrevs))
167 return 1
167 return 1
168
168
169 def _verifychangelog(self):
169 def _verifychangelog(self):
170 ui = self.ui
170 ui = self.ui
171 repo = self.repo
171 repo = self.repo
172 match = self.match
172 match = self.match
173 cl = repo.changelog
173 cl = repo.changelog
174
174
175 ui.status(_("checking changesets\n"))
175 ui.status(_("checking changesets\n"))
176 mflinkrevs = {}
176 mflinkrevs = {}
177 filelinkrevs = {}
177 filelinkrevs = {}
178 seen = {}
178 seen = {}
179 self.checklog(cl, "changelog", 0)
179 self.checklog(cl, "changelog", 0)
180 total = len(repo)
180 total = len(repo)
181 for i in repo:
181 for i in repo:
182 ui.progress(_('checking'), i, total=total, unit=_('changesets'))
182 ui.progress(_('checking'), i, total=total, unit=_('changesets'))
183 n = cl.node(i)
183 n = cl.node(i)
184 self.checkentry(cl, i, n, seen, [i], "changelog")
184 self.checkentry(cl, i, n, seen, [i], "changelog")
185
185
186 try:
186 try:
187 changes = cl.read(n)
187 changes = cl.read(n)
188 if changes[0] != nullid:
188 if changes[0] != nullid:
189 mflinkrevs.setdefault(changes[0], []).append(i)
189 mflinkrevs.setdefault(changes[0], []).append(i)
190 self.refersmf = True
190 self.refersmf = True
191 for f in changes[3]:
191 for f in changes[3]:
192 if match(f):
192 if match(f):
193 filelinkrevs.setdefault(_normpath(f), []).append(i)
193 filelinkrevs.setdefault(_normpath(f), []).append(i)
194 except Exception as inst:
194 except Exception as inst:
195 self.refersmf = True
195 self.refersmf = True
196 self.exc(i, _("unpacking changeset %s") % short(n), inst)
196 self.exc(i, _("unpacking changeset %s") % short(n), inst)
197 ui.progress(_('checking'), None)
197 ui.progress(_('checking'), None)
198 return mflinkrevs, filelinkrevs
198 return mflinkrevs, filelinkrevs
199
199
200 def _verifymanifest(self, mflinkrevs, dir="", storefiles=None,
200 def _verifymanifest(self, mflinkrevs, dir="", storefiles=None,
201 progress=None):
201 progress=None):
202 repo = self.repo
202 repo = self.repo
203 ui = self.ui
203 ui = self.ui
204 match = self.match
204 match = self.match
205 mfl = self.repo.manifestlog
205 mfl = self.repo.manifestlog
206 mf = mfl._revlog.dirlog(dir)
206 mf = mfl._revlog.dirlog(dir)
207
207
208 if not dir:
208 if not dir:
209 self.ui.status(_("checking manifests\n"))
209 self.ui.status(_("checking manifests\n"))
210
210
211 filenodes = {}
211 filenodes = {}
212 subdirnodes = {}
212 subdirnodes = {}
213 seen = {}
213 seen = {}
214 label = "manifest"
214 label = "manifest"
215 if dir:
215 if dir:
216 label = dir
216 label = dir
217 revlogfiles = mf.files()
217 revlogfiles = mf.files()
218 storefiles.difference_update(revlogfiles)
218 storefiles.difference_update(revlogfiles)
219 if progress: # should be true since we're in a subdirectory
219 if progress: # should be true since we're in a subdirectory
220 progress()
220 progress()
221 if self.refersmf:
221 if self.refersmf:
222 # Do not check manifest if there are only changelog entries with
222 # Do not check manifest if there are only changelog entries with
223 # null manifests.
223 # null manifests.
224 self.checklog(mf, label, 0)
224 self.checklog(mf, label, 0)
225 total = len(mf)
225 total = len(mf)
226 for i in mf:
226 for i in mf:
227 if not dir:
227 if not dir:
228 ui.progress(_('checking'), i, total=total, unit=_('manifests'))
228 ui.progress(_('checking'), i, total=total, unit=_('manifests'))
229 n = mf.node(i)
229 n = mf.node(i)
230 lr = self.checkentry(mf, i, n, seen, mflinkrevs.get(n, []), label)
230 lr = self.checkentry(mf, i, n, seen, mflinkrevs.get(n, []), label)
231 if n in mflinkrevs:
231 if n in mflinkrevs:
232 del mflinkrevs[n]
232 del mflinkrevs[n]
233 elif dir:
233 elif dir:
234 self.err(lr, _("%s not in parent-directory manifest") %
234 self.err(lr, _("%s not in parent-directory manifest") %
235 short(n), label)
235 short(n), label)
236 else:
236 else:
237 self.err(lr, _("%s not in changesets") % short(n), label)
237 self.err(lr, _("%s not in changesets") % short(n), label)
238
238
239 try:
239 try:
240 mfdelta = mfl.get(dir, n).readdelta(shallow=True)
240 mfdelta = mfl.get(dir, n).readdelta(shallow=True)
241 for f, fn, fl in mfdelta.iterentries():
241 for f, fn, fl in mfdelta.iterentries():
242 if not f:
242 if not f:
243 self.err(lr, _("entry without name in manifest"))
243 self.err(lr, _("entry without name in manifest"))
244 elif f == "/dev/null": # ignore this in very old repos
244 elif f == "/dev/null": # ignore this in very old repos
245 continue
245 continue
246 fullpath = dir + _normpath(f)
246 fullpath = dir + _normpath(f)
247 if fl == 't':
247 if fl == 't':
248 if not match.visitdir(fullpath):
248 if not match.visitdir(fullpath):
249 continue
249 continue
250 subdirnodes.setdefault(fullpath + '/', {}).setdefault(
250 subdirnodes.setdefault(fullpath + '/', {}).setdefault(
251 fn, []).append(lr)
251 fn, []).append(lr)
252 else:
252 else:
253 if not match(fullpath):
253 if not match(fullpath):
254 continue
254 continue
255 filenodes.setdefault(fullpath, {}).setdefault(fn, lr)
255 filenodes.setdefault(fullpath, {}).setdefault(fn, lr)
256 except Exception as inst:
256 except Exception as inst:
257 self.exc(lr, _("reading delta %s") % short(n), inst, label)
257 self.exc(lr, _("reading delta %s") % short(n), inst, label)
258 if not dir:
258 if not dir:
259 ui.progress(_('checking'), None)
259 ui.progress(_('checking'), None)
260
260
261 if self.havemf:
261 if self.havemf:
262 for c, m in sorted([(c, m) for m in mflinkrevs
262 for c, m in sorted([(c, m) for m in mflinkrevs
263 for c in mflinkrevs[m]]):
263 for c in mflinkrevs[m]]):
264 if dir:
264 if dir:
265 self.err(c, _("parent-directory manifest refers to unknown "
265 self.err(c, _("parent-directory manifest refers to unknown "
266 "revision %s") % short(m), label)
266 "revision %s") % short(m), label)
267 else:
267 else:
268 self.err(c, _("changeset refers to unknown revision %s") %
268 self.err(c, _("changeset refers to unknown revision %s") %
269 short(m), label)
269 short(m), label)
270
270
271 if not dir and subdirnodes:
271 if not dir and subdirnodes:
272 self.ui.status(_("checking directory manifests\n"))
272 self.ui.status(_("checking directory manifests\n"))
273 storefiles = set()
273 storefiles = set()
274 subdirs = set()
274 subdirs = set()
275 revlogv1 = self.revlogv1
275 revlogv1 = self.revlogv1
276 for f, f2, size in repo.store.datafiles():
276 for f, f2, size in repo.store.datafiles():
277 if not f:
277 if not f:
278 self.err(None, _("cannot decode filename '%s'") % f2)
278 self.err(None, _("cannot decode filename '%s'") % f2)
279 elif (size > 0 or not revlogv1) and f.startswith('meta/'):
279 elif (size > 0 or not revlogv1) and f.startswith('meta/'):
280 storefiles.add(_normpath(f))
280 storefiles.add(_normpath(f))
281 subdirs.add(os.path.dirname(f))
281 subdirs.add(os.path.dirname(f))
282 subdircount = len(subdirs)
282 subdircount = len(subdirs)
283 currentsubdir = [0]
283 currentsubdir = [0]
284 def progress():
284 def progress():
285 currentsubdir[0] += 1
285 currentsubdir[0] += 1
286 ui.progress(_('checking'), currentsubdir[0], total=subdircount,
286 ui.progress(_('checking'), currentsubdir[0], total=subdircount,
287 unit=_('manifests'))
287 unit=_('manifests'))
288
288
289 for subdir, linkrevs in subdirnodes.iteritems():
289 for subdir, linkrevs in subdirnodes.iteritems():
290 subdirfilenodes = self._verifymanifest(linkrevs, subdir, storefiles,
290 subdirfilenodes = self._verifymanifest(linkrevs, subdir, storefiles,
291 progress)
291 progress)
292 for f, onefilenodes in subdirfilenodes.iteritems():
292 for f, onefilenodes in subdirfilenodes.iteritems():
293 filenodes.setdefault(f, {}).update(onefilenodes)
293 filenodes.setdefault(f, {}).update(onefilenodes)
294
294
295 if not dir and subdirnodes:
295 if not dir and subdirnodes:
296 ui.progress(_('checking'), None)
296 ui.progress(_('checking'), None)
297 for f in sorted(storefiles):
297 for f in sorted(storefiles):
298 self.warn(_("warning: orphan revlog '%s'") % f)
298 self.warn(_("warning: orphan data file '%s'") % f)
299
299
300 return filenodes
300 return filenodes
301
301
302 def _crosscheckfiles(self, filelinkrevs, filenodes):
302 def _crosscheckfiles(self, filelinkrevs, filenodes):
303 repo = self.repo
303 repo = self.repo
304 ui = self.ui
304 ui = self.ui
305 ui.status(_("crosschecking files in changesets and manifests\n"))
305 ui.status(_("crosschecking files in changesets and manifests\n"))
306
306
307 total = len(filelinkrevs) + len(filenodes)
307 total = len(filelinkrevs) + len(filenodes)
308 count = 0
308 count = 0
309 if self.havemf:
309 if self.havemf:
310 for f in sorted(filelinkrevs):
310 for f in sorted(filelinkrevs):
311 count += 1
311 count += 1
312 ui.progress(_('crosschecking'), count, total=total)
312 ui.progress(_('crosschecking'), count, total=total)
313 if f not in filenodes:
313 if f not in filenodes:
314 lr = filelinkrevs[f][0]
314 lr = filelinkrevs[f][0]
315 self.err(lr, _("in changeset but not in manifest"), f)
315 self.err(lr, _("in changeset but not in manifest"), f)
316
316
317 if self.havecl:
317 if self.havecl:
318 for f in sorted(filenodes):
318 for f in sorted(filenodes):
319 count += 1
319 count += 1
320 ui.progress(_('crosschecking'), count, total=total)
320 ui.progress(_('crosschecking'), count, total=total)
321 if f not in filelinkrevs:
321 if f not in filelinkrevs:
322 try:
322 try:
323 fl = repo.file(f)
323 fl = repo.file(f)
324 lr = min([fl.linkrev(fl.rev(n)) for n in filenodes[f]])
324 lr = min([fl.linkrev(fl.rev(n)) for n in filenodes[f]])
325 except Exception:
325 except Exception:
326 lr = None
326 lr = None
327 self.err(lr, _("in manifest but not in changeset"), f)
327 self.err(lr, _("in manifest but not in changeset"), f)
328
328
329 ui.progress(_('crosschecking'), None)
329 ui.progress(_('crosschecking'), None)
330
330
331 def _verifyfiles(self, filenodes, filelinkrevs):
331 def _verifyfiles(self, filenodes, filelinkrevs):
332 repo = self.repo
332 repo = self.repo
333 ui = self.ui
333 ui = self.ui
334 lrugetctx = self.lrugetctx
334 lrugetctx = self.lrugetctx
335 revlogv1 = self.revlogv1
335 revlogv1 = self.revlogv1
336 havemf = self.havemf
336 havemf = self.havemf
337 ui.status(_("checking files\n"))
337 ui.status(_("checking files\n"))
338
338
339 storefiles = set()
339 storefiles = set()
340 for f, f2, size in repo.store.datafiles():
340 for f, f2, size in repo.store.datafiles():
341 if not f:
341 if not f:
342 self.err(None, _("cannot decode filename '%s'") % f2)
342 self.err(None, _("cannot decode filename '%s'") % f2)
343 elif (size > 0 or not revlogv1) and f.startswith('data/'):
343 elif (size > 0 or not revlogv1) and f.startswith('data/'):
344 storefiles.add(_normpath(f))
344 storefiles.add(_normpath(f))
345
345
346 files = sorted(set(filenodes) | set(filelinkrevs))
346 files = sorted(set(filenodes) | set(filelinkrevs))
347 total = len(files)
347 total = len(files)
348 revisions = 0
348 revisions = 0
349 for i, f in enumerate(files):
349 for i, f in enumerate(files):
350 ui.progress(_('checking'), i, item=f, total=total, unit=_('files'))
350 ui.progress(_('checking'), i, item=f, total=total, unit=_('files'))
351 try:
351 try:
352 linkrevs = filelinkrevs[f]
352 linkrevs = filelinkrevs[f]
353 except KeyError:
353 except KeyError:
354 # in manifest but not in changelog
354 # in manifest but not in changelog
355 linkrevs = []
355 linkrevs = []
356
356
357 if linkrevs:
357 if linkrevs:
358 lr = linkrevs[0]
358 lr = linkrevs[0]
359 else:
359 else:
360 lr = None
360 lr = None
361
361
362 try:
362 try:
363 fl = repo.file(f)
363 fl = repo.file(f)
364 except error.RevlogError as e:
364 except error.RevlogError as e:
365 self.err(lr, _("broken revlog! (%s)") % e, f)
365 self.err(lr, _("broken revlog! (%s)") % e, f)
366 continue
366 continue
367
367
368 for ff in fl.files():
368 for ff in fl.files():
369 try:
369 try:
370 storefiles.remove(ff)
370 storefiles.remove(ff)
371 except KeyError:
371 except KeyError:
372 self.warn(_(" warning: revlog '%s' not in fncache!") % ff)
372 self.warn(_(" warning: revlog '%s' not in fncache!") % ff)
373 self.fncachewarned = True
373 self.fncachewarned = True
374
374
375 self.checklog(fl, f, lr)
375 self.checklog(fl, f, lr)
376 seen = {}
376 seen = {}
377 rp = None
377 rp = None
378 for i in fl:
378 for i in fl:
379 revisions += 1
379 revisions += 1
380 n = fl.node(i)
380 n = fl.node(i)
381 lr = self.checkentry(fl, i, n, seen, linkrevs, f)
381 lr = self.checkentry(fl, i, n, seen, linkrevs, f)
382 if f in filenodes:
382 if f in filenodes:
383 if havemf and n not in filenodes[f]:
383 if havemf and n not in filenodes[f]:
384 self.err(lr, _("%s not in manifests") % (short(n)), f)
384 self.err(lr, _("%s not in manifests") % (short(n)), f)
385 else:
385 else:
386 del filenodes[f][n]
386 del filenodes[f][n]
387
387
388 # Verify contents. 4 cases to care about:
388 # Verify contents. 4 cases to care about:
389 #
389 #
390 # common: the most common case
390 # common: the most common case
391 # rename: with a rename
391 # rename: with a rename
392 # meta: file content starts with b'\1\n', the metadata
392 # meta: file content starts with b'\1\n', the metadata
393 # header defined in filelog.py, but without a rename
393 # header defined in filelog.py, but without a rename
394 # ext: content stored externally
394 # ext: content stored externally
395 #
395 #
396 # More formally, their differences are shown below:
396 # More formally, their differences are shown below:
397 #
397 #
398 # | common | rename | meta | ext
398 # | common | rename | meta | ext
399 # -------------------------------------------------------
399 # -------------------------------------------------------
400 # flags() | 0 | 0 | 0 | not 0
400 # flags() | 0 | 0 | 0 | not 0
401 # renamed() | False | True | False | ?
401 # renamed() | False | True | False | ?
402 # rawtext[0:2]=='\1\n'| False | True | True | ?
402 # rawtext[0:2]=='\1\n'| False | True | True | ?
403 #
403 #
404 # "rawtext" means the raw text stored in revlog data, which
404 # "rawtext" means the raw text stored in revlog data, which
405 # could be retrieved by "revision(rev, raw=True)". "text"
405 # could be retrieved by "revision(rev, raw=True)". "text"
406 # mentioned below is "revision(rev, raw=False)".
406 # mentioned below is "revision(rev, raw=False)".
407 #
407 #
408 # There are 3 different lengths stored physically:
408 # There are 3 different lengths stored physically:
409 # 1. L1: rawsize, stored in revlog index
409 # 1. L1: rawsize, stored in revlog index
410 # 2. L2: len(rawtext), stored in revlog data
410 # 2. L2: len(rawtext), stored in revlog data
411 # 3. L3: len(text), stored in revlog data if flags==0, or
411 # 3. L3: len(text), stored in revlog data if flags==0, or
412 # possibly somewhere else if flags!=0
412 # possibly somewhere else if flags!=0
413 #
413 #
414 # L1 should be equal to L2. L3 could be different from them.
414 # L1 should be equal to L2. L3 could be different from them.
415 # "text" may or may not affect commit hash depending on flag
415 # "text" may or may not affect commit hash depending on flag
416 # processors (see revlog.addflagprocessor).
416 # processors (see revlog.addflagprocessor).
417 #
417 #
418 # | common | rename | meta | ext
418 # | common | rename | meta | ext
419 # -------------------------------------------------
419 # -------------------------------------------------
420 # rawsize() | L1 | L1 | L1 | L1
420 # rawsize() | L1 | L1 | L1 | L1
421 # size() | L1 | L2-LM | L1(*) | L1 (?)
421 # size() | L1 | L2-LM | L1(*) | L1 (?)
422 # len(rawtext) | L2 | L2 | L2 | L2
422 # len(rawtext) | L2 | L2 | L2 | L2
423 # len(text) | L2 | L2 | L2 | L3
423 # len(text) | L2 | L2 | L2 | L3
424 # len(read()) | L2 | L2-LM | L2-LM | L3 (?)
424 # len(read()) | L2 | L2-LM | L2-LM | L3 (?)
425 #
425 #
426 # LM: length of metadata, depending on rawtext
426 # LM: length of metadata, depending on rawtext
427 # (*): not ideal, see comment in filelog.size
427 # (*): not ideal, see comment in filelog.size
428 # (?): could be "- len(meta)" if the resolved content has
428 # (?): could be "- len(meta)" if the resolved content has
429 # rename metadata
429 # rename metadata
430 #
430 #
431 # Checks needed to be done:
431 # Checks needed to be done:
432 # 1. length check: L1 == L2, in all cases.
432 # 1. length check: L1 == L2, in all cases.
433 # 2. hash check: depending on flag processor, we may need to
433 # 2. hash check: depending on flag processor, we may need to
434 # use either "text" (external), or "rawtext" (in revlog).
434 # use either "text" (external), or "rawtext" (in revlog).
435 try:
435 try:
436 skipflags = self.skipflags
436 skipflags = self.skipflags
437 if skipflags:
437 if skipflags:
438 skipflags &= fl.flags(i)
438 skipflags &= fl.flags(i)
439 if not skipflags:
439 if not skipflags:
440 fl.read(n) # side effect: read content and do checkhash
440 fl.read(n) # side effect: read content and do checkhash
441 rp = fl.renamed(n)
441 rp = fl.renamed(n)
442 # the "L1 == L2" check
442 # the "L1 == L2" check
443 l1 = fl.rawsize(i)
443 l1 = fl.rawsize(i)
444 l2 = len(fl.revision(n, raw=True))
444 l2 = len(fl.revision(n, raw=True))
445 if l1 != l2:
445 if l1 != l2:
446 self.err(lr, _("unpacked size is %s, %s expected") %
446 self.err(lr, _("unpacked size is %s, %s expected") %
447 (l2, l1), f)
447 (l2, l1), f)
448 except error.CensoredNodeError:
448 except error.CensoredNodeError:
449 # experimental config: censor.policy
449 # experimental config: censor.policy
450 if ui.config("censor", "policy") == "abort":
450 if ui.config("censor", "policy") == "abort":
451 self.err(lr, _("censored file data"), f)
451 self.err(lr, _("censored file data"), f)
452 except Exception as inst:
452 except Exception as inst:
453 self.exc(lr, _("unpacking %s") % short(n), inst, f)
453 self.exc(lr, _("unpacking %s") % short(n), inst, f)
454
454
455 # check renames
455 # check renames
456 try:
456 try:
457 if rp:
457 if rp:
458 if lr is not None and ui.verbose:
458 if lr is not None and ui.verbose:
459 ctx = lrugetctx(lr)
459 ctx = lrugetctx(lr)
460 if not any(rp[0] in pctx for pctx in ctx.parents()):
460 if not any(rp[0] in pctx for pctx in ctx.parents()):
461 self.warn(_("warning: copy source of '%s' not"
461 self.warn(_("warning: copy source of '%s' not"
462 " in parents of %s") % (f, ctx))
462 " in parents of %s") % (f, ctx))
463 fl2 = repo.file(rp[0])
463 fl2 = repo.file(rp[0])
464 if not len(fl2):
464 if not len(fl2):
465 self.err(lr, _("empty or missing copy source "
465 self.err(lr, _("empty or missing copy source "
466 "revlog %s:%s") % (rp[0], short(rp[1])), f)
466 "revlog %s:%s") % (rp[0], short(rp[1])), f)
467 elif rp[1] == nullid:
467 elif rp[1] == nullid:
468 ui.note(_("warning: %s@%s: copy source"
468 ui.note(_("warning: %s@%s: copy source"
469 " revision is nullid %s:%s\n")
469 " revision is nullid %s:%s\n")
470 % (f, lr, rp[0], short(rp[1])))
470 % (f, lr, rp[0], short(rp[1])))
471 else:
471 else:
472 fl2.rev(rp[1])
472 fl2.rev(rp[1])
473 except Exception as inst:
473 except Exception as inst:
474 self.exc(lr, _("checking rename of %s") % short(n), inst, f)
474 self.exc(lr, _("checking rename of %s") % short(n), inst, f)
475
475
476 # cross-check
476 # cross-check
477 if f in filenodes:
477 if f in filenodes:
478 fns = [(v, k) for k, v in filenodes[f].iteritems()]
478 fns = [(v, k) for k, v in filenodes[f].iteritems()]
479 for lr, node in sorted(fns):
479 for lr, node in sorted(fns):
480 self.err(lr, _("manifest refers to unknown revision %s") %
480 self.err(lr, _("manifest refers to unknown revision %s") %
481 short(node), f)
481 short(node), f)
482 ui.progress(_('checking'), None)
482 ui.progress(_('checking'), None)
483
483
484 for f in sorted(storefiles):
484 for f in sorted(storefiles):
485 self.warn(_("warning: orphan revlog '%s'") % f)
485 self.warn(_("warning: orphan data file '%s'") % f)
486
486
487 return len(files), revisions
487 return len(files), revisions
@@ -1,139 +1,139 b''
1 #require unix-permissions no-root
1 #require unix-permissions no-root
2
2
3 $ cat > $TESTTMP/dumpjournal.py <<EOF
3 $ cat > $TESTTMP/dumpjournal.py <<EOF
4 > import sys
4 > import sys
5 > for entry in sys.stdin.read().split('\n'):
5 > for entry in sys.stdin.read().split('\n'):
6 > if entry:
6 > if entry:
7 > print(entry.split('\x00')[0])
7 > print(entry.split('\x00')[0])
8 > EOF
8 > EOF
9
9
10 $ echo "[extensions]" >> $HGRCPATH
10 $ echo "[extensions]" >> $HGRCPATH
11 $ echo "mq=">> $HGRCPATH
11 $ echo "mq=">> $HGRCPATH
12
12
13 $ teststrip() {
13 $ teststrip() {
14 > hg -q up -C $1
14 > hg -q up -C $1
15 > echo % before update $1, strip $2
15 > echo % before update $1, strip $2
16 > hg parents
16 > hg parents
17 > chmod -$3 $4
17 > chmod -$3 $4
18 > hg strip $2 2>&1 | sed 's/\(bundle\).*/\1/' | sed 's/Permission denied.*\.hg\/store\/\(.*\)/Permission denied \.hg\/store\/\1/'
18 > hg strip $2 2>&1 | sed 's/\(bundle\).*/\1/' | sed 's/Permission denied.*\.hg\/store\/\(.*\)/Permission denied \.hg\/store\/\1/'
19 > echo % after update $1, strip $2
19 > echo % after update $1, strip $2
20 > chmod +$3 $4
20 > chmod +$3 $4
21 > hg verify
21 > hg verify
22 > echo % journal contents
22 > echo % journal contents
23 > if [ -f .hg/store/journal ]; then
23 > if [ -f .hg/store/journal ]; then
24 > cat .hg/store/journal | $PYTHON $TESTTMP/dumpjournal.py
24 > cat .hg/store/journal | $PYTHON $TESTTMP/dumpjournal.py
25 > else
25 > else
26 > echo "(no journal)"
26 > echo "(no journal)"
27 > fi
27 > fi
28 > ls .hg/store/journal >/dev/null 2>&1 && hg recover
28 > ls .hg/store/journal >/dev/null 2>&1 && hg recover
29 > ls .hg/strip-backup/* >/dev/null 2>&1 && hg unbundle -q .hg/strip-backup/*
29 > ls .hg/strip-backup/* >/dev/null 2>&1 && hg unbundle -q .hg/strip-backup/*
30 > rm -rf .hg/strip-backup
30 > rm -rf .hg/strip-backup
31 > }
31 > }
32
32
33 $ hg init test
33 $ hg init test
34 $ cd test
34 $ cd test
35 $ echo a > a
35 $ echo a > a
36 $ hg -q ci -m "a" -A
36 $ hg -q ci -m "a" -A
37 $ echo b > b
37 $ echo b > b
38 $ hg -q ci -m "b" -A
38 $ hg -q ci -m "b" -A
39 $ echo b2 >> b
39 $ echo b2 >> b
40 $ hg -q ci -m "b2" -A
40 $ hg -q ci -m "b2" -A
41 $ echo c > c
41 $ echo c > c
42 $ hg -q ci -m "c" -A
42 $ hg -q ci -m "c" -A
43 $ teststrip 0 2 w .hg/store/data/b.i
43 $ teststrip 0 2 w .hg/store/data/b.i
44 % before update 0, strip 2
44 % before update 0, strip 2
45 changeset: 0:cb9a9f314b8b
45 changeset: 0:cb9a9f314b8b
46 user: test
46 user: test
47 date: Thu Jan 01 00:00:00 1970 +0000
47 date: Thu Jan 01 00:00:00 1970 +0000
48 summary: a
48 summary: a
49
49
50 saved backup bundle
50 saved backup bundle
51 transaction abort!
51 transaction abort!
52 failed to truncate data/b.i
52 failed to truncate data/b.i
53 rollback failed - please run hg recover
53 rollback failed - please run hg recover
54 strip failed, backup bundle
54 strip failed, backup bundle
55 abort: Permission denied .hg/store/data/b.i
55 abort: Permission denied .hg/store/data/b.i
56 % after update 0, strip 2
56 % after update 0, strip 2
57 abandoned transaction found - run hg recover
57 abandoned transaction found - run hg recover
58 checking changesets
58 checking changesets
59 checking manifests
59 checking manifests
60 crosschecking files in changesets and manifests
60 crosschecking files in changesets and manifests
61 checking files
61 checking files
62 b@?: rev 1 points to nonexistent changeset 2
62 b@?: rev 1 points to nonexistent changeset 2
63 (expected 1)
63 (expected 1)
64 b@?: 736c29771fba not in manifests
64 b@?: 736c29771fba not in manifests
65 warning: orphan revlog 'data/c.i'
65 warning: orphan data file 'data/c.i'
66 2 files, 2 changesets, 3 total revisions
66 2 files, 2 changesets, 3 total revisions
67 2 warnings encountered!
67 2 warnings encountered!
68 2 integrity errors encountered!
68 2 integrity errors encountered!
69 % journal contents
69 % journal contents
70 00changelog.i
70 00changelog.i
71 00manifest.i
71 00manifest.i
72 data/b.i
72 data/b.i
73 data/c.i
73 data/c.i
74 rolling back interrupted transaction
74 rolling back interrupted transaction
75 checking changesets
75 checking changesets
76 checking manifests
76 checking manifests
77 crosschecking files in changesets and manifests
77 crosschecking files in changesets and manifests
78 checking files
78 checking files
79 2 files, 2 changesets, 2 total revisions
79 2 files, 2 changesets, 2 total revisions
80 $ teststrip 0 2 r .hg/store/data/b.i
80 $ teststrip 0 2 r .hg/store/data/b.i
81 % before update 0, strip 2
81 % before update 0, strip 2
82 changeset: 0:cb9a9f314b8b
82 changeset: 0:cb9a9f314b8b
83 user: test
83 user: test
84 date: Thu Jan 01 00:00:00 1970 +0000
84 date: Thu Jan 01 00:00:00 1970 +0000
85 summary: a
85 summary: a
86
86
87 abort: Permission denied .hg/store/data/b.i
87 abort: Permission denied .hg/store/data/b.i
88 % after update 0, strip 2
88 % after update 0, strip 2
89 checking changesets
89 checking changesets
90 checking manifests
90 checking manifests
91 crosschecking files in changesets and manifests
91 crosschecking files in changesets and manifests
92 checking files
92 checking files
93 3 files, 4 changesets, 4 total revisions
93 3 files, 4 changesets, 4 total revisions
94 % journal contents
94 % journal contents
95 (no journal)
95 (no journal)
96 $ teststrip 0 2 w .hg/store/00manifest.i
96 $ teststrip 0 2 w .hg/store/00manifest.i
97 % before update 0, strip 2
97 % before update 0, strip 2
98 changeset: 0:cb9a9f314b8b
98 changeset: 0:cb9a9f314b8b
99 user: test
99 user: test
100 date: Thu Jan 01 00:00:00 1970 +0000
100 date: Thu Jan 01 00:00:00 1970 +0000
101 summary: a
101 summary: a
102
102
103 saved backup bundle
103 saved backup bundle
104 transaction abort!
104 transaction abort!
105 failed to truncate 00manifest.i
105 failed to truncate 00manifest.i
106 rollback failed - please run hg recover
106 rollback failed - please run hg recover
107 strip failed, backup bundle
107 strip failed, backup bundle
108 abort: Permission denied .hg/store/00manifest.i
108 abort: Permission denied .hg/store/00manifest.i
109 % after update 0, strip 2
109 % after update 0, strip 2
110 abandoned transaction found - run hg recover
110 abandoned transaction found - run hg recover
111 checking changesets
111 checking changesets
112 checking manifests
112 checking manifests
113 manifest@?: rev 2 points to nonexistent changeset 2
113 manifest@?: rev 2 points to nonexistent changeset 2
114 manifest@?: 3362547cdf64 not in changesets
114 manifest@?: 3362547cdf64 not in changesets
115 manifest@?: rev 3 points to nonexistent changeset 3
115 manifest@?: rev 3 points to nonexistent changeset 3
116 manifest@?: 265a85892ecb not in changesets
116 manifest@?: 265a85892ecb not in changesets
117 crosschecking files in changesets and manifests
117 crosschecking files in changesets and manifests
118 c@3: in manifest but not in changeset
118 c@3: in manifest but not in changeset
119 checking files
119 checking files
120 b@?: rev 1 points to nonexistent changeset 2
120 b@?: rev 1 points to nonexistent changeset 2
121 (expected 1)
121 (expected 1)
122 c@?: rev 0 points to nonexistent changeset 3
122 c@?: rev 0 points to nonexistent changeset 3
123 3 files, 2 changesets, 4 total revisions
123 3 files, 2 changesets, 4 total revisions
124 1 warnings encountered!
124 1 warnings encountered!
125 7 integrity errors encountered!
125 7 integrity errors encountered!
126 (first damaged changeset appears to be 3)
126 (first damaged changeset appears to be 3)
127 % journal contents
127 % journal contents
128 00changelog.i
128 00changelog.i
129 00manifest.i
129 00manifest.i
130 data/b.i
130 data/b.i
131 data/c.i
131 data/c.i
132 rolling back interrupted transaction
132 rolling back interrupted transaction
133 checking changesets
133 checking changesets
134 checking manifests
134 checking manifests
135 crosschecking files in changesets and manifests
135 crosschecking files in changesets and manifests
136 checking files
136 checking files
137 2 files, 2 changesets, 2 total revisions
137 2 files, 2 changesets, 2 total revisions
138
138
139 $ cd ..
139 $ cd ..
@@ -1,876 +1,876 b''
1 #require killdaemons
1 #require killdaemons
2
2
3 $ cat << EOF >> $HGRCPATH
3 $ cat << EOF >> $HGRCPATH
4 > [ui]
4 > [ui]
5 > ssh=$PYTHON "$TESTDIR/dummyssh"
5 > ssh=$PYTHON "$TESTDIR/dummyssh"
6 > EOF
6 > EOF
7
7
8 Set up repo
8 Set up repo
9
9
10 $ hg --config experimental.treemanifest=True init repo
10 $ hg --config experimental.treemanifest=True init repo
11 $ cd repo
11 $ cd repo
12
12
13 Requirements get set on init
13 Requirements get set on init
14
14
15 $ grep treemanifest .hg/requires
15 $ grep treemanifest .hg/requires
16 treemanifest
16 treemanifest
17
17
18 Without directories, looks like any other repo
18 Without directories, looks like any other repo
19
19
20 $ echo 0 > a
20 $ echo 0 > a
21 $ echo 0 > b
21 $ echo 0 > b
22 $ hg ci -Aqm initial
22 $ hg ci -Aqm initial
23 $ hg debugdata -m 0
23 $ hg debugdata -m 0
24 a\x00362fef284ce2ca02aecc8de6d5e8a1c3af0556fe (esc)
24 a\x00362fef284ce2ca02aecc8de6d5e8a1c3af0556fe (esc)
25 b\x00362fef284ce2ca02aecc8de6d5e8a1c3af0556fe (esc)
25 b\x00362fef284ce2ca02aecc8de6d5e8a1c3af0556fe (esc)
26
26
27 Submanifest is stored in separate revlog
27 Submanifest is stored in separate revlog
28
28
29 $ mkdir dir1
29 $ mkdir dir1
30 $ echo 1 > dir1/a
30 $ echo 1 > dir1/a
31 $ echo 1 > dir1/b
31 $ echo 1 > dir1/b
32 $ echo 1 > e
32 $ echo 1 > e
33 $ hg ci -Aqm 'add dir1'
33 $ hg ci -Aqm 'add dir1'
34 $ hg debugdata -m 1
34 $ hg debugdata -m 1
35 a\x00362fef284ce2ca02aecc8de6d5e8a1c3af0556fe (esc)
35 a\x00362fef284ce2ca02aecc8de6d5e8a1c3af0556fe (esc)
36 b\x00362fef284ce2ca02aecc8de6d5e8a1c3af0556fe (esc)
36 b\x00362fef284ce2ca02aecc8de6d5e8a1c3af0556fe (esc)
37 dir1\x008b3ffd73f901e83304c83d33132c8e774ceac44et (esc)
37 dir1\x008b3ffd73f901e83304c83d33132c8e774ceac44et (esc)
38 e\x00b8e02f6433738021a065f94175c7cd23db5f05be (esc)
38 e\x00b8e02f6433738021a065f94175c7cd23db5f05be (esc)
39 $ hg debugdata --dir dir1 0
39 $ hg debugdata --dir dir1 0
40 a\x00b8e02f6433738021a065f94175c7cd23db5f05be (esc)
40 a\x00b8e02f6433738021a065f94175c7cd23db5f05be (esc)
41 b\x00b8e02f6433738021a065f94175c7cd23db5f05be (esc)
41 b\x00b8e02f6433738021a065f94175c7cd23db5f05be (esc)
42
42
43 Can add nested directories
43 Can add nested directories
44
44
45 $ mkdir dir1/dir1
45 $ mkdir dir1/dir1
46 $ echo 2 > dir1/dir1/a
46 $ echo 2 > dir1/dir1/a
47 $ echo 2 > dir1/dir1/b
47 $ echo 2 > dir1/dir1/b
48 $ mkdir dir1/dir2
48 $ mkdir dir1/dir2
49 $ echo 2 > dir1/dir2/a
49 $ echo 2 > dir1/dir2/a
50 $ echo 2 > dir1/dir2/b
50 $ echo 2 > dir1/dir2/b
51 $ hg ci -Aqm 'add dir1/dir1'
51 $ hg ci -Aqm 'add dir1/dir1'
52 $ hg files -r .
52 $ hg files -r .
53 a
53 a
54 b
54 b
55 dir1/a
55 dir1/a
56 dir1/b
56 dir1/b
57 dir1/dir1/a
57 dir1/dir1/a
58 dir1/dir1/b
58 dir1/dir1/b
59 dir1/dir2/a
59 dir1/dir2/a
60 dir1/dir2/b
60 dir1/dir2/b
61 e
61 e
62
62
63 The manifest command works
63 The manifest command works
64
64
65 $ hg manifest
65 $ hg manifest
66 a
66 a
67 b
67 b
68 dir1/a
68 dir1/a
69 dir1/b
69 dir1/b
70 dir1/dir1/a
70 dir1/dir1/a
71 dir1/dir1/b
71 dir1/dir1/b
72 dir1/dir2/a
72 dir1/dir2/a
73 dir1/dir2/b
73 dir1/dir2/b
74 e
74 e
75
75
76 Revision is not created for unchanged directory
76 Revision is not created for unchanged directory
77
77
78 $ mkdir dir2
78 $ mkdir dir2
79 $ echo 3 > dir2/a
79 $ echo 3 > dir2/a
80 $ hg add dir2
80 $ hg add dir2
81 adding dir2/a
81 adding dir2/a
82 $ hg debugindex --dir dir1 > before
82 $ hg debugindex --dir dir1 > before
83 $ hg ci -qm 'add dir2'
83 $ hg ci -qm 'add dir2'
84 $ hg debugindex --dir dir1 > after
84 $ hg debugindex --dir dir1 > after
85 $ diff before after
85 $ diff before after
86 $ rm before after
86 $ rm before after
87
87
88 Removing directory does not create an revlog entry
88 Removing directory does not create an revlog entry
89
89
90 $ hg rm dir1/dir1
90 $ hg rm dir1/dir1
91 removing dir1/dir1/a
91 removing dir1/dir1/a
92 removing dir1/dir1/b
92 removing dir1/dir1/b
93 $ hg debugindex --dir dir1/dir1 > before
93 $ hg debugindex --dir dir1/dir1 > before
94 $ hg ci -qm 'remove dir1/dir1'
94 $ hg ci -qm 'remove dir1/dir1'
95 $ hg debugindex --dir dir1/dir1 > after
95 $ hg debugindex --dir dir1/dir1 > after
96 $ diff before after
96 $ diff before after
97 $ rm before after
97 $ rm before after
98
98
99 Check that hg files (calls treemanifest.walk()) works
99 Check that hg files (calls treemanifest.walk()) works
100 without loading all directory revlogs
100 without loading all directory revlogs
101
101
102 $ hg co 'desc("add dir2")'
102 $ hg co 'desc("add dir2")'
103 2 files updated, 0 files merged, 0 files removed, 0 files unresolved
103 2 files updated, 0 files merged, 0 files removed, 0 files unresolved
104 $ mv .hg/store/meta/dir2 .hg/store/meta/dir2-backup
104 $ mv .hg/store/meta/dir2 .hg/store/meta/dir2-backup
105 $ hg files -r . dir1
105 $ hg files -r . dir1
106 dir1/a
106 dir1/a
107 dir1/b
107 dir1/b
108 dir1/dir1/a
108 dir1/dir1/a
109 dir1/dir1/b
109 dir1/dir1/b
110 dir1/dir2/a
110 dir1/dir2/a
111 dir1/dir2/b
111 dir1/dir2/b
112
112
113 Check that status between revisions works (calls treemanifest.matches())
113 Check that status between revisions works (calls treemanifest.matches())
114 without loading all directory revlogs
114 without loading all directory revlogs
115
115
116 $ hg status --rev 'desc("add dir1")' --rev . dir1
116 $ hg status --rev 'desc("add dir1")' --rev . dir1
117 A dir1/dir1/a
117 A dir1/dir1/a
118 A dir1/dir1/b
118 A dir1/dir1/b
119 A dir1/dir2/a
119 A dir1/dir2/a
120 A dir1/dir2/b
120 A dir1/dir2/b
121 $ mv .hg/store/meta/dir2-backup .hg/store/meta/dir2
121 $ mv .hg/store/meta/dir2-backup .hg/store/meta/dir2
122
122
123 Merge creates 2-parent revision of directory revlog
123 Merge creates 2-parent revision of directory revlog
124
124
125 $ echo 5 > dir1/a
125 $ echo 5 > dir1/a
126 $ hg ci -Aqm 'modify dir1/a'
126 $ hg ci -Aqm 'modify dir1/a'
127 $ hg co '.^'
127 $ hg co '.^'
128 1 files updated, 0 files merged, 0 files removed, 0 files unresolved
128 1 files updated, 0 files merged, 0 files removed, 0 files unresolved
129 $ echo 6 > dir1/b
129 $ echo 6 > dir1/b
130 $ hg ci -Aqm 'modify dir1/b'
130 $ hg ci -Aqm 'modify dir1/b'
131 $ hg merge 'desc("modify dir1/a")'
131 $ hg merge 'desc("modify dir1/a")'
132 1 files updated, 0 files merged, 0 files removed, 0 files unresolved
132 1 files updated, 0 files merged, 0 files removed, 0 files unresolved
133 (branch merge, don't forget to commit)
133 (branch merge, don't forget to commit)
134 $ hg ci -m 'conflict-free merge involving dir1/'
134 $ hg ci -m 'conflict-free merge involving dir1/'
135 $ cat dir1/a
135 $ cat dir1/a
136 5
136 5
137 $ cat dir1/b
137 $ cat dir1/b
138 6
138 6
139 $ hg debugindex --dir dir1
139 $ hg debugindex --dir dir1
140 rev linkrev nodeid p1 p2
140 rev linkrev nodeid p1 p2
141 0 1 8b3ffd73f901 000000000000 000000000000
141 0 1 8b3ffd73f901 000000000000 000000000000
142 1 2 68e9d057c5a8 8b3ffd73f901 000000000000
142 1 2 68e9d057c5a8 8b3ffd73f901 000000000000
143 2 4 4698198d2624 68e9d057c5a8 000000000000
143 2 4 4698198d2624 68e9d057c5a8 000000000000
144 3 5 44844058ccce 68e9d057c5a8 000000000000
144 3 5 44844058ccce 68e9d057c5a8 000000000000
145 4 6 bf3d9b744927 68e9d057c5a8 000000000000
145 4 6 bf3d9b744927 68e9d057c5a8 000000000000
146 5 7 dde7c0af2a03 bf3d9b744927 44844058ccce
146 5 7 dde7c0af2a03 bf3d9b744927 44844058ccce
147
147
148 Merge keeping directory from parent 1 does not create revlog entry. (Note that
148 Merge keeping directory from parent 1 does not create revlog entry. (Note that
149 dir1's manifest does change, but only because dir1/a's filelog changes.)
149 dir1's manifest does change, but only because dir1/a's filelog changes.)
150
150
151 $ hg co 'desc("add dir2")'
151 $ hg co 'desc("add dir2")'
152 2 files updated, 0 files merged, 0 files removed, 0 files unresolved
152 2 files updated, 0 files merged, 0 files removed, 0 files unresolved
153 $ echo 8 > dir2/a
153 $ echo 8 > dir2/a
154 $ hg ci -m 'modify dir2/a'
154 $ hg ci -m 'modify dir2/a'
155 created new head
155 created new head
156
156
157 $ hg debugindex --dir dir2 > before
157 $ hg debugindex --dir dir2 > before
158 $ hg merge 'desc("modify dir1/a")'
158 $ hg merge 'desc("modify dir1/a")'
159 1 files updated, 0 files merged, 0 files removed, 0 files unresolved
159 1 files updated, 0 files merged, 0 files removed, 0 files unresolved
160 (branch merge, don't forget to commit)
160 (branch merge, don't forget to commit)
161 $ hg revert -r 'desc("modify dir2/a")' .
161 $ hg revert -r 'desc("modify dir2/a")' .
162 reverting dir1/a
162 reverting dir1/a
163 $ hg ci -m 'merge, keeping parent 1'
163 $ hg ci -m 'merge, keeping parent 1'
164 $ hg debugindex --dir dir2 > after
164 $ hg debugindex --dir dir2 > after
165 $ diff before after
165 $ diff before after
166 $ rm before after
166 $ rm before after
167
167
168 Merge keeping directory from parent 2 does not create revlog entry. (Note that
168 Merge keeping directory from parent 2 does not create revlog entry. (Note that
169 dir2's manifest does change, but only because dir2/a's filelog changes.)
169 dir2's manifest does change, but only because dir2/a's filelog changes.)
170
170
171 $ hg co 'desc("modify dir2/a")'
171 $ hg co 'desc("modify dir2/a")'
172 1 files updated, 0 files merged, 0 files removed, 0 files unresolved
172 1 files updated, 0 files merged, 0 files removed, 0 files unresolved
173 $ hg debugindex --dir dir1 > before
173 $ hg debugindex --dir dir1 > before
174 $ hg merge 'desc("modify dir1/a")'
174 $ hg merge 'desc("modify dir1/a")'
175 1 files updated, 0 files merged, 0 files removed, 0 files unresolved
175 1 files updated, 0 files merged, 0 files removed, 0 files unresolved
176 (branch merge, don't forget to commit)
176 (branch merge, don't forget to commit)
177 $ hg revert -r 'desc("modify dir1/a")' .
177 $ hg revert -r 'desc("modify dir1/a")' .
178 reverting dir2/a
178 reverting dir2/a
179 $ hg ci -m 'merge, keeping parent 2'
179 $ hg ci -m 'merge, keeping parent 2'
180 created new head
180 created new head
181 $ hg debugindex --dir dir1 > after
181 $ hg debugindex --dir dir1 > after
182 $ diff before after
182 $ diff before after
183 $ rm before after
183 $ rm before after
184
184
185 Create flat source repo for tests with mixed flat/tree manifests
185 Create flat source repo for tests with mixed flat/tree manifests
186
186
187 $ cd ..
187 $ cd ..
188 $ hg init repo-flat
188 $ hg init repo-flat
189 $ cd repo-flat
189 $ cd repo-flat
190
190
191 Create a few commits with flat manifest
191 Create a few commits with flat manifest
192
192
193 $ echo 0 > a
193 $ echo 0 > a
194 $ echo 0 > b
194 $ echo 0 > b
195 $ echo 0 > e
195 $ echo 0 > e
196 $ for d in dir1 dir1/dir1 dir1/dir2 dir2
196 $ for d in dir1 dir1/dir1 dir1/dir2 dir2
197 > do
197 > do
198 > mkdir $d
198 > mkdir $d
199 > echo 0 > $d/a
199 > echo 0 > $d/a
200 > echo 0 > $d/b
200 > echo 0 > $d/b
201 > done
201 > done
202 $ hg ci -Aqm initial
202 $ hg ci -Aqm initial
203
203
204 $ echo 1 > a
204 $ echo 1 > a
205 $ echo 1 > dir1/a
205 $ echo 1 > dir1/a
206 $ echo 1 > dir1/dir1/a
206 $ echo 1 > dir1/dir1/a
207 $ hg ci -Aqm 'modify on branch 1'
207 $ hg ci -Aqm 'modify on branch 1'
208
208
209 $ hg co 0
209 $ hg co 0
210 3 files updated, 0 files merged, 0 files removed, 0 files unresolved
210 3 files updated, 0 files merged, 0 files removed, 0 files unresolved
211 $ echo 2 > b
211 $ echo 2 > b
212 $ echo 2 > dir1/b
212 $ echo 2 > dir1/b
213 $ echo 2 > dir1/dir1/b
213 $ echo 2 > dir1/dir1/b
214 $ hg ci -Aqm 'modify on branch 2'
214 $ hg ci -Aqm 'modify on branch 2'
215
215
216 $ hg merge 1
216 $ hg merge 1
217 3 files updated, 0 files merged, 0 files removed, 0 files unresolved
217 3 files updated, 0 files merged, 0 files removed, 0 files unresolved
218 (branch merge, don't forget to commit)
218 (branch merge, don't forget to commit)
219 $ hg ci -m 'merge of flat manifests to new flat manifest'
219 $ hg ci -m 'merge of flat manifests to new flat manifest'
220
220
221 $ hg serve -p $HGPORT -d --pid-file=hg.pid --errorlog=errors.log
221 $ hg serve -p $HGPORT -d --pid-file=hg.pid --errorlog=errors.log
222 $ cat hg.pid >> $DAEMON_PIDS
222 $ cat hg.pid >> $DAEMON_PIDS
223
223
224 Create clone with tree manifests enabled
224 Create clone with tree manifests enabled
225
225
226 $ cd ..
226 $ cd ..
227 $ hg clone --config experimental.treemanifest=1 \
227 $ hg clone --config experimental.treemanifest=1 \
228 > http://localhost:$HGPORT repo-mixed -r 1
228 > http://localhost:$HGPORT repo-mixed -r 1
229 adding changesets
229 adding changesets
230 adding manifests
230 adding manifests
231 adding file changes
231 adding file changes
232 added 2 changesets with 14 changes to 11 files
232 added 2 changesets with 14 changes to 11 files
233 new changesets 5b02a3e8db7e:581ef6037d8b
233 new changesets 5b02a3e8db7e:581ef6037d8b
234 updating to branch default
234 updating to branch default
235 11 files updated, 0 files merged, 0 files removed, 0 files unresolved
235 11 files updated, 0 files merged, 0 files removed, 0 files unresolved
236 $ cd repo-mixed
236 $ cd repo-mixed
237 $ test -d .hg/store/meta
237 $ test -d .hg/store/meta
238 [1]
238 [1]
239 $ grep treemanifest .hg/requires
239 $ grep treemanifest .hg/requires
240 treemanifest
240 treemanifest
241
241
242 Should be possible to push updates from flat to tree manifest repo
242 Should be possible to push updates from flat to tree manifest repo
243
243
244 $ hg -R ../repo-flat push ssh://user@dummy/repo-mixed
244 $ hg -R ../repo-flat push ssh://user@dummy/repo-mixed
245 pushing to ssh://user@dummy/repo-mixed
245 pushing to ssh://user@dummy/repo-mixed
246 searching for changes
246 searching for changes
247 remote: adding changesets
247 remote: adding changesets
248 remote: adding manifests
248 remote: adding manifests
249 remote: adding file changes
249 remote: adding file changes
250 remote: added 2 changesets with 3 changes to 3 files
250 remote: added 2 changesets with 3 changes to 3 files
251
251
252 Commit should store revlog per directory
252 Commit should store revlog per directory
253
253
254 $ hg co 1
254 $ hg co 1
255 0 files updated, 0 files merged, 0 files removed, 0 files unresolved
255 0 files updated, 0 files merged, 0 files removed, 0 files unresolved
256 $ echo 3 > a
256 $ echo 3 > a
257 $ echo 3 > dir1/a
257 $ echo 3 > dir1/a
258 $ echo 3 > dir1/dir1/a
258 $ echo 3 > dir1/dir1/a
259 $ hg ci -m 'first tree'
259 $ hg ci -m 'first tree'
260 created new head
260 created new head
261 $ find .hg/store/meta | sort
261 $ find .hg/store/meta | sort
262 .hg/store/meta
262 .hg/store/meta
263 .hg/store/meta/dir1
263 .hg/store/meta/dir1
264 .hg/store/meta/dir1/00manifest.i
264 .hg/store/meta/dir1/00manifest.i
265 .hg/store/meta/dir1/dir1
265 .hg/store/meta/dir1/dir1
266 .hg/store/meta/dir1/dir1/00manifest.i
266 .hg/store/meta/dir1/dir1/00manifest.i
267 .hg/store/meta/dir1/dir2
267 .hg/store/meta/dir1/dir2
268 .hg/store/meta/dir1/dir2/00manifest.i
268 .hg/store/meta/dir1/dir2/00manifest.i
269 .hg/store/meta/dir2
269 .hg/store/meta/dir2
270 .hg/store/meta/dir2/00manifest.i
270 .hg/store/meta/dir2/00manifest.i
271
271
272 Merge of two trees
272 Merge of two trees
273
273
274 $ hg co 2
274 $ hg co 2
275 6 files updated, 0 files merged, 0 files removed, 0 files unresolved
275 6 files updated, 0 files merged, 0 files removed, 0 files unresolved
276 $ hg merge 1
276 $ hg merge 1
277 3 files updated, 0 files merged, 0 files removed, 0 files unresolved
277 3 files updated, 0 files merged, 0 files removed, 0 files unresolved
278 (branch merge, don't forget to commit)
278 (branch merge, don't forget to commit)
279 $ hg ci -m 'merge of flat manifests to new tree manifest'
279 $ hg ci -m 'merge of flat manifests to new tree manifest'
280 created new head
280 created new head
281 $ hg diff -r 3
281 $ hg diff -r 3
282
282
283 Parent of tree root manifest should be flat manifest, and two for merge
283 Parent of tree root manifest should be flat manifest, and two for merge
284
284
285 $ hg debugindex -m
285 $ hg debugindex -m
286 rev linkrev nodeid p1 p2
286 rev linkrev nodeid p1 p2
287 0 0 40536115ed9e 000000000000 000000000000
287 0 0 40536115ed9e 000000000000 000000000000
288 1 1 f3376063c255 40536115ed9e 000000000000
288 1 1 f3376063c255 40536115ed9e 000000000000
289 2 2 5d9b9da231a2 40536115ed9e 000000000000
289 2 2 5d9b9da231a2 40536115ed9e 000000000000
290 3 3 d17d663cbd8a 5d9b9da231a2 f3376063c255
290 3 3 d17d663cbd8a 5d9b9da231a2 f3376063c255
291 4 4 51e32a8c60ee f3376063c255 000000000000
291 4 4 51e32a8c60ee f3376063c255 000000000000
292 5 5 cc5baa78b230 5d9b9da231a2 f3376063c255
292 5 5 cc5baa78b230 5d9b9da231a2 f3376063c255
293
293
294
294
295 Status across flat/tree boundary should work
295 Status across flat/tree boundary should work
296
296
297 $ hg status --rev '.^' --rev .
297 $ hg status --rev '.^' --rev .
298 M a
298 M a
299 M dir1/a
299 M dir1/a
300 M dir1/dir1/a
300 M dir1/dir1/a
301
301
302
302
303 Turning off treemanifest config has no effect
303 Turning off treemanifest config has no effect
304
304
305 $ hg debugindex --dir dir1
305 $ hg debugindex --dir dir1
306 rev linkrev nodeid p1 p2
306 rev linkrev nodeid p1 p2
307 0 4 064927a0648a 000000000000 000000000000
307 0 4 064927a0648a 000000000000 000000000000
308 1 5 25ecb8cb8618 000000000000 000000000000
308 1 5 25ecb8cb8618 000000000000 000000000000
309 $ echo 2 > dir1/a
309 $ echo 2 > dir1/a
310 $ hg --config experimental.treemanifest=False ci -qm 'modify dir1/a'
310 $ hg --config experimental.treemanifest=False ci -qm 'modify dir1/a'
311 $ hg debugindex --dir dir1
311 $ hg debugindex --dir dir1
312 rev linkrev nodeid p1 p2
312 rev linkrev nodeid p1 p2
313 0 4 064927a0648a 000000000000 000000000000
313 0 4 064927a0648a 000000000000 000000000000
314 1 5 25ecb8cb8618 000000000000 000000000000
314 1 5 25ecb8cb8618 000000000000 000000000000
315 2 6 5b16163a30c6 25ecb8cb8618 000000000000
315 2 6 5b16163a30c6 25ecb8cb8618 000000000000
316
316
317 Stripping and recovering changes should work
317 Stripping and recovering changes should work
318
318
319 $ hg st --change tip
319 $ hg st --change tip
320 M dir1/a
320 M dir1/a
321 $ hg --config extensions.strip= strip tip
321 $ hg --config extensions.strip= strip tip
322 1 files updated, 0 files merged, 0 files removed, 0 files unresolved
322 1 files updated, 0 files merged, 0 files removed, 0 files unresolved
323 saved backup bundle to $TESTTMP/repo-mixed/.hg/strip-backup/51cfd7b1e13b-78a2f3ed-backup.hg
323 saved backup bundle to $TESTTMP/repo-mixed/.hg/strip-backup/51cfd7b1e13b-78a2f3ed-backup.hg
324 $ hg debugindex --dir dir1
324 $ hg debugindex --dir dir1
325 rev linkrev nodeid p1 p2
325 rev linkrev nodeid p1 p2
326 0 4 064927a0648a 000000000000 000000000000
326 0 4 064927a0648a 000000000000 000000000000
327 1 5 25ecb8cb8618 000000000000 000000000000
327 1 5 25ecb8cb8618 000000000000 000000000000
328
328
329 #if repobundlerepo
329 #if repobundlerepo
330 $ hg incoming .hg/strip-backup/*
330 $ hg incoming .hg/strip-backup/*
331 comparing with .hg/strip-backup/*-backup.hg (glob)
331 comparing with .hg/strip-backup/*-backup.hg (glob)
332 searching for changes
332 searching for changes
333 changeset: 6:51cfd7b1e13b
333 changeset: 6:51cfd7b1e13b
334 tag: tip
334 tag: tip
335 user: test
335 user: test
336 date: Thu Jan 01 00:00:00 1970 +0000
336 date: Thu Jan 01 00:00:00 1970 +0000
337 summary: modify dir1/a
337 summary: modify dir1/a
338
338
339 #endif
339 #endif
340
340
341 $ hg unbundle .hg/strip-backup/*
341 $ hg unbundle .hg/strip-backup/*
342 adding changesets
342 adding changesets
343 adding manifests
343 adding manifests
344 adding file changes
344 adding file changes
345 added 1 changesets with 1 changes to 1 files
345 added 1 changesets with 1 changes to 1 files
346 new changesets 51cfd7b1e13b
346 new changesets 51cfd7b1e13b
347 (run 'hg update' to get a working copy)
347 (run 'hg update' to get a working copy)
348 $ hg --config extensions.strip= strip tip
348 $ hg --config extensions.strip= strip tip
349 saved backup bundle to $TESTTMP/repo-mixed/.hg/strip-backup/*-backup.hg (glob)
349 saved backup bundle to $TESTTMP/repo-mixed/.hg/strip-backup/*-backup.hg (glob)
350 $ hg unbundle -q .hg/strip-backup/*
350 $ hg unbundle -q .hg/strip-backup/*
351 $ hg debugindex --dir dir1
351 $ hg debugindex --dir dir1
352 rev linkrev nodeid p1 p2
352 rev linkrev nodeid p1 p2
353 0 4 064927a0648a 000000000000 000000000000
353 0 4 064927a0648a 000000000000 000000000000
354 1 5 25ecb8cb8618 000000000000 000000000000
354 1 5 25ecb8cb8618 000000000000 000000000000
355 2 6 5b16163a30c6 25ecb8cb8618 000000000000
355 2 6 5b16163a30c6 25ecb8cb8618 000000000000
356 $ hg st --change tip
356 $ hg st --change tip
357 M dir1/a
357 M dir1/a
358
358
359 Shelving and unshelving should work
359 Shelving and unshelving should work
360
360
361 $ echo foo >> dir1/a
361 $ echo foo >> dir1/a
362 $ hg --config extensions.shelve= shelve
362 $ hg --config extensions.shelve= shelve
363 shelved as default
363 shelved as default
364 1 files updated, 0 files merged, 0 files removed, 0 files unresolved
364 1 files updated, 0 files merged, 0 files removed, 0 files unresolved
365 $ hg --config extensions.shelve= unshelve
365 $ hg --config extensions.shelve= unshelve
366 unshelving change 'default'
366 unshelving change 'default'
367 $ hg diff --nodates
367 $ hg diff --nodates
368 diff -r 708a273da119 dir1/a
368 diff -r 708a273da119 dir1/a
369 --- a/dir1/a
369 --- a/dir1/a
370 +++ b/dir1/a
370 +++ b/dir1/a
371 @@ -1,1 +1,2 @@
371 @@ -1,1 +1,2 @@
372 1
372 1
373 +foo
373 +foo
374
374
375 Pushing from treemanifest repo to an empty repo makes that a treemanifest repo
375 Pushing from treemanifest repo to an empty repo makes that a treemanifest repo
376
376
377 $ cd ..
377 $ cd ..
378 $ hg init empty-repo
378 $ hg init empty-repo
379 $ cat << EOF >> empty-repo/.hg/hgrc
379 $ cat << EOF >> empty-repo/.hg/hgrc
380 > [experimental]
380 > [experimental]
381 > changegroup3=yes
381 > changegroup3=yes
382 > EOF
382 > EOF
383 $ grep treemanifest empty-repo/.hg/requires
383 $ grep treemanifest empty-repo/.hg/requires
384 [1]
384 [1]
385 $ hg push -R repo -r 0 empty-repo
385 $ hg push -R repo -r 0 empty-repo
386 pushing to empty-repo
386 pushing to empty-repo
387 searching for changes
387 searching for changes
388 adding changesets
388 adding changesets
389 adding manifests
389 adding manifests
390 adding file changes
390 adding file changes
391 added 1 changesets with 2 changes to 2 files
391 added 1 changesets with 2 changes to 2 files
392 $ grep treemanifest empty-repo/.hg/requires
392 $ grep treemanifest empty-repo/.hg/requires
393 treemanifest
393 treemanifest
394
394
395 Pushing to an empty repo works
395 Pushing to an empty repo works
396
396
397 $ hg --config experimental.treemanifest=1 init clone
397 $ hg --config experimental.treemanifest=1 init clone
398 $ grep treemanifest clone/.hg/requires
398 $ grep treemanifest clone/.hg/requires
399 treemanifest
399 treemanifest
400 $ hg push -R repo clone
400 $ hg push -R repo clone
401 pushing to clone
401 pushing to clone
402 searching for changes
402 searching for changes
403 adding changesets
403 adding changesets
404 adding manifests
404 adding manifests
405 adding file changes
405 adding file changes
406 added 11 changesets with 15 changes to 10 files (+3 heads)
406 added 11 changesets with 15 changes to 10 files (+3 heads)
407 $ grep treemanifest clone/.hg/requires
407 $ grep treemanifest clone/.hg/requires
408 treemanifest
408 treemanifest
409 $ hg -R clone verify
409 $ hg -R clone verify
410 checking changesets
410 checking changesets
411 checking manifests
411 checking manifests
412 checking directory manifests
412 checking directory manifests
413 crosschecking files in changesets and manifests
413 crosschecking files in changesets and manifests
414 checking files
414 checking files
415 10 files, 11 changesets, 15 total revisions
415 10 files, 11 changesets, 15 total revisions
416
416
417 Create deeper repo with tree manifests.
417 Create deeper repo with tree manifests.
418
418
419 $ hg --config experimental.treemanifest=True init deeprepo
419 $ hg --config experimental.treemanifest=True init deeprepo
420 $ cd deeprepo
420 $ cd deeprepo
421
421
422 $ mkdir .A
422 $ mkdir .A
423 $ mkdir b
423 $ mkdir b
424 $ mkdir b/bar
424 $ mkdir b/bar
425 $ mkdir b/bar/orange
425 $ mkdir b/bar/orange
426 $ mkdir b/bar/orange/fly
426 $ mkdir b/bar/orange/fly
427 $ mkdir b/foo
427 $ mkdir b/foo
428 $ mkdir b/foo/apple
428 $ mkdir b/foo/apple
429 $ mkdir b/foo/apple/bees
429 $ mkdir b/foo/apple/bees
430
430
431 $ touch .A/one.txt
431 $ touch .A/one.txt
432 $ touch .A/two.txt
432 $ touch .A/two.txt
433 $ touch b/bar/fruits.txt
433 $ touch b/bar/fruits.txt
434 $ touch b/bar/orange/fly/gnat.py
434 $ touch b/bar/orange/fly/gnat.py
435 $ touch b/bar/orange/fly/housefly.txt
435 $ touch b/bar/orange/fly/housefly.txt
436 $ touch b/foo/apple/bees/flower.py
436 $ touch b/foo/apple/bees/flower.py
437 $ touch c.txt
437 $ touch c.txt
438 $ touch d.py
438 $ touch d.py
439
439
440 $ hg ci -Aqm 'initial'
440 $ hg ci -Aqm 'initial'
441
441
442 $ echo >> .A/one.txt
442 $ echo >> .A/one.txt
443 $ echo >> .A/two.txt
443 $ echo >> .A/two.txt
444 $ echo >> b/bar/fruits.txt
444 $ echo >> b/bar/fruits.txt
445 $ echo >> b/bar/orange/fly/gnat.py
445 $ echo >> b/bar/orange/fly/gnat.py
446 $ echo >> b/bar/orange/fly/housefly.txt
446 $ echo >> b/bar/orange/fly/housefly.txt
447 $ echo >> b/foo/apple/bees/flower.py
447 $ echo >> b/foo/apple/bees/flower.py
448 $ echo >> c.txt
448 $ echo >> c.txt
449 $ echo >> d.py
449 $ echo >> d.py
450 $ hg ci -Aqm 'second'
450 $ hg ci -Aqm 'second'
451
451
452 We'll see that visitdir works by removing some treemanifest revlogs and running
452 We'll see that visitdir works by removing some treemanifest revlogs and running
453 the files command with various parameters.
453 the files command with various parameters.
454
454
455 Test files from the root.
455 Test files from the root.
456
456
457 $ hg files -r .
457 $ hg files -r .
458 .A/one.txt
458 .A/one.txt
459 .A/two.txt
459 .A/two.txt
460 b/bar/fruits.txt
460 b/bar/fruits.txt
461 b/bar/orange/fly/gnat.py
461 b/bar/orange/fly/gnat.py
462 b/bar/orange/fly/housefly.txt
462 b/bar/orange/fly/housefly.txt
463 b/foo/apple/bees/flower.py
463 b/foo/apple/bees/flower.py
464 c.txt
464 c.txt
465 d.py
465 d.py
466
466
467 Excludes with a glob should not exclude everything from the glob's root
467 Excludes with a glob should not exclude everything from the glob's root
468
468
469 $ hg files -r . -X 'b/fo?' b
469 $ hg files -r . -X 'b/fo?' b
470 b/bar/fruits.txt
470 b/bar/fruits.txt
471 b/bar/orange/fly/gnat.py
471 b/bar/orange/fly/gnat.py
472 b/bar/orange/fly/housefly.txt
472 b/bar/orange/fly/housefly.txt
473 $ cp -R .hg/store .hg/store-copy
473 $ cp -R .hg/store .hg/store-copy
474
474
475 Test files for a subdirectory.
475 Test files for a subdirectory.
476
476
477 $ rm -r .hg/store/meta/~2e_a
477 $ rm -r .hg/store/meta/~2e_a
478 $ hg files -r . b
478 $ hg files -r . b
479 b/bar/fruits.txt
479 b/bar/fruits.txt
480 b/bar/orange/fly/gnat.py
480 b/bar/orange/fly/gnat.py
481 b/bar/orange/fly/housefly.txt
481 b/bar/orange/fly/housefly.txt
482 b/foo/apple/bees/flower.py
482 b/foo/apple/bees/flower.py
483 $ hg diff -r '.^' -r . --stat b
483 $ hg diff -r '.^' -r . --stat b
484 b/bar/fruits.txt | 1 +
484 b/bar/fruits.txt | 1 +
485 b/bar/orange/fly/gnat.py | 1 +
485 b/bar/orange/fly/gnat.py | 1 +
486 b/bar/orange/fly/housefly.txt | 1 +
486 b/bar/orange/fly/housefly.txt | 1 +
487 b/foo/apple/bees/flower.py | 1 +
487 b/foo/apple/bees/flower.py | 1 +
488 4 files changed, 4 insertions(+), 0 deletions(-)
488 4 files changed, 4 insertions(+), 0 deletions(-)
489 $ cp -R .hg/store-copy/. .hg/store
489 $ cp -R .hg/store-copy/. .hg/store
490
490
491 Test files with just includes and excludes.
491 Test files with just includes and excludes.
492
492
493 $ rm -r .hg/store/meta/~2e_a
493 $ rm -r .hg/store/meta/~2e_a
494 $ rm -r .hg/store/meta/b/bar/orange/fly
494 $ rm -r .hg/store/meta/b/bar/orange/fly
495 $ rm -r .hg/store/meta/b/foo/apple/bees
495 $ rm -r .hg/store/meta/b/foo/apple/bees
496 $ hg files -r . -I path:b/bar -X path:b/bar/orange/fly -I path:b/foo -X path:b/foo/apple/bees
496 $ hg files -r . -I path:b/bar -X path:b/bar/orange/fly -I path:b/foo -X path:b/foo/apple/bees
497 b/bar/fruits.txt
497 b/bar/fruits.txt
498 $ hg diff -r '.^' -r . --stat -I path:b/bar -X path:b/bar/orange/fly -I path:b/foo -X path:b/foo/apple/bees
498 $ hg diff -r '.^' -r . --stat -I path:b/bar -X path:b/bar/orange/fly -I path:b/foo -X path:b/foo/apple/bees
499 b/bar/fruits.txt | 1 +
499 b/bar/fruits.txt | 1 +
500 1 files changed, 1 insertions(+), 0 deletions(-)
500 1 files changed, 1 insertions(+), 0 deletions(-)
501 $ cp -R .hg/store-copy/. .hg/store
501 $ cp -R .hg/store-copy/. .hg/store
502
502
503 Test files for a subdirectory, excluding a directory within it.
503 Test files for a subdirectory, excluding a directory within it.
504
504
505 $ rm -r .hg/store/meta/~2e_a
505 $ rm -r .hg/store/meta/~2e_a
506 $ rm -r .hg/store/meta/b/foo
506 $ rm -r .hg/store/meta/b/foo
507 $ hg files -r . -X path:b/foo b
507 $ hg files -r . -X path:b/foo b
508 b/bar/fruits.txt
508 b/bar/fruits.txt
509 b/bar/orange/fly/gnat.py
509 b/bar/orange/fly/gnat.py
510 b/bar/orange/fly/housefly.txt
510 b/bar/orange/fly/housefly.txt
511 $ hg diff -r '.^' -r . --stat -X path:b/foo b
511 $ hg diff -r '.^' -r . --stat -X path:b/foo b
512 b/bar/fruits.txt | 1 +
512 b/bar/fruits.txt | 1 +
513 b/bar/orange/fly/gnat.py | 1 +
513 b/bar/orange/fly/gnat.py | 1 +
514 b/bar/orange/fly/housefly.txt | 1 +
514 b/bar/orange/fly/housefly.txt | 1 +
515 3 files changed, 3 insertions(+), 0 deletions(-)
515 3 files changed, 3 insertions(+), 0 deletions(-)
516 $ cp -R .hg/store-copy/. .hg/store
516 $ cp -R .hg/store-copy/. .hg/store
517
517
518 Test files for a sub directory, including only a directory within it, and
518 Test files for a sub directory, including only a directory within it, and
519 including an unrelated directory.
519 including an unrelated directory.
520
520
521 $ rm -r .hg/store/meta/~2e_a
521 $ rm -r .hg/store/meta/~2e_a
522 $ rm -r .hg/store/meta/b/foo
522 $ rm -r .hg/store/meta/b/foo
523 $ hg files -r . -I path:b/bar/orange -I path:a b
523 $ hg files -r . -I path:b/bar/orange -I path:a b
524 b/bar/orange/fly/gnat.py
524 b/bar/orange/fly/gnat.py
525 b/bar/orange/fly/housefly.txt
525 b/bar/orange/fly/housefly.txt
526 $ hg diff -r '.^' -r . --stat -I path:b/bar/orange -I path:a b
526 $ hg diff -r '.^' -r . --stat -I path:b/bar/orange -I path:a b
527 b/bar/orange/fly/gnat.py | 1 +
527 b/bar/orange/fly/gnat.py | 1 +
528 b/bar/orange/fly/housefly.txt | 1 +
528 b/bar/orange/fly/housefly.txt | 1 +
529 2 files changed, 2 insertions(+), 0 deletions(-)
529 2 files changed, 2 insertions(+), 0 deletions(-)
530 $ cp -R .hg/store-copy/. .hg/store
530 $ cp -R .hg/store-copy/. .hg/store
531
531
532 Test files for a pattern, including a directory, and excluding a directory
532 Test files for a pattern, including a directory, and excluding a directory
533 within that.
533 within that.
534
534
535 $ rm -r .hg/store/meta/~2e_a
535 $ rm -r .hg/store/meta/~2e_a
536 $ rm -r .hg/store/meta/b/foo
536 $ rm -r .hg/store/meta/b/foo
537 $ rm -r .hg/store/meta/b/bar/orange
537 $ rm -r .hg/store/meta/b/bar/orange
538 $ hg files -r . glob:**.txt -I path:b/bar -X path:b/bar/orange
538 $ hg files -r . glob:**.txt -I path:b/bar -X path:b/bar/orange
539 b/bar/fruits.txt
539 b/bar/fruits.txt
540 $ hg diff -r '.^' -r . --stat glob:**.txt -I path:b/bar -X path:b/bar/orange
540 $ hg diff -r '.^' -r . --stat glob:**.txt -I path:b/bar -X path:b/bar/orange
541 b/bar/fruits.txt | 1 +
541 b/bar/fruits.txt | 1 +
542 1 files changed, 1 insertions(+), 0 deletions(-)
542 1 files changed, 1 insertions(+), 0 deletions(-)
543 $ cp -R .hg/store-copy/. .hg/store
543 $ cp -R .hg/store-copy/. .hg/store
544
544
545 Add some more changes to the deep repo
545 Add some more changes to the deep repo
546 $ echo narf >> b/bar/fruits.txt
546 $ echo narf >> b/bar/fruits.txt
547 $ hg ci -m narf
547 $ hg ci -m narf
548 $ echo troz >> b/bar/orange/fly/gnat.py
548 $ echo troz >> b/bar/orange/fly/gnat.py
549 $ hg ci -m troz
549 $ hg ci -m troz
550
550
551 Verify works
551 Verify works
552 $ hg verify
552 $ hg verify
553 checking changesets
553 checking changesets
554 checking manifests
554 checking manifests
555 checking directory manifests
555 checking directory manifests
556 crosschecking files in changesets and manifests
556 crosschecking files in changesets and manifests
557 checking files
557 checking files
558 8 files, 4 changesets, 18 total revisions
558 8 files, 4 changesets, 18 total revisions
559
559
560 Dirlogs are included in fncache
560 Dirlogs are included in fncache
561 $ grep meta/.A/00manifest.i .hg/store/fncache
561 $ grep meta/.A/00manifest.i .hg/store/fncache
562 meta/.A/00manifest.i
562 meta/.A/00manifest.i
563
563
564 Rebuilt fncache includes dirlogs
564 Rebuilt fncache includes dirlogs
565 $ rm .hg/store/fncache
565 $ rm .hg/store/fncache
566 $ hg debugrebuildfncache
566 $ hg debugrebuildfncache
567 adding data/.A/one.txt.i
567 adding data/.A/one.txt.i
568 adding data/.A/two.txt.i
568 adding data/.A/two.txt.i
569 adding data/b/bar/fruits.txt.i
569 adding data/b/bar/fruits.txt.i
570 adding data/b/bar/orange/fly/gnat.py.i
570 adding data/b/bar/orange/fly/gnat.py.i
571 adding data/b/bar/orange/fly/housefly.txt.i
571 adding data/b/bar/orange/fly/housefly.txt.i
572 adding data/b/foo/apple/bees/flower.py.i
572 adding data/b/foo/apple/bees/flower.py.i
573 adding data/c.txt.i
573 adding data/c.txt.i
574 adding data/d.py.i
574 adding data/d.py.i
575 adding meta/.A/00manifest.i
575 adding meta/.A/00manifest.i
576 adding meta/b/00manifest.i
576 adding meta/b/00manifest.i
577 adding meta/b/bar/00manifest.i
577 adding meta/b/bar/00manifest.i
578 adding meta/b/bar/orange/00manifest.i
578 adding meta/b/bar/orange/00manifest.i
579 adding meta/b/bar/orange/fly/00manifest.i
579 adding meta/b/bar/orange/fly/00manifest.i
580 adding meta/b/foo/00manifest.i
580 adding meta/b/foo/00manifest.i
581 adding meta/b/foo/apple/00manifest.i
581 adding meta/b/foo/apple/00manifest.i
582 adding meta/b/foo/apple/bees/00manifest.i
582 adding meta/b/foo/apple/bees/00manifest.i
583 16 items added, 0 removed from fncache
583 16 items added, 0 removed from fncache
584
584
585 Finish first server
585 Finish first server
586 $ killdaemons.py
586 $ killdaemons.py
587
587
588 Back up the recently added revlogs
588 Back up the recently added revlogs
589 $ cp -R .hg/store .hg/store-newcopy
589 $ cp -R .hg/store .hg/store-newcopy
590
590
591 Verify reports missing dirlog
591 Verify reports missing dirlog
592 $ rm .hg/store/meta/b/00manifest.*
592 $ rm .hg/store/meta/b/00manifest.*
593 $ hg verify
593 $ hg verify
594 checking changesets
594 checking changesets
595 checking manifests
595 checking manifests
596 checking directory manifests
596 checking directory manifests
597 0: empty or missing b/
597 0: empty or missing b/
598 b/@0: parent-directory manifest refers to unknown revision 67688a370455
598 b/@0: parent-directory manifest refers to unknown revision 67688a370455
599 b/@1: parent-directory manifest refers to unknown revision f065da70369e
599 b/@1: parent-directory manifest refers to unknown revision f065da70369e
600 b/@2: parent-directory manifest refers to unknown revision ac0d30948e0b
600 b/@2: parent-directory manifest refers to unknown revision ac0d30948e0b
601 b/@3: parent-directory manifest refers to unknown revision 367152e6af28
601 b/@3: parent-directory manifest refers to unknown revision 367152e6af28
602 warning: orphan revlog 'meta/b/bar/00manifest.i'
602 warning: orphan data file 'meta/b/bar/00manifest.i'
603 warning: orphan revlog 'meta/b/bar/orange/00manifest.i'
603 warning: orphan data file 'meta/b/bar/orange/00manifest.i'
604 warning: orphan revlog 'meta/b/bar/orange/fly/00manifest.i'
604 warning: orphan data file 'meta/b/bar/orange/fly/00manifest.i'
605 warning: orphan revlog 'meta/b/foo/00manifest.i'
605 warning: orphan data file 'meta/b/foo/00manifest.i'
606 warning: orphan revlog 'meta/b/foo/apple/00manifest.i'
606 warning: orphan data file 'meta/b/foo/apple/00manifest.i'
607 warning: orphan revlog 'meta/b/foo/apple/bees/00manifest.i'
607 warning: orphan data file 'meta/b/foo/apple/bees/00manifest.i'
608 crosschecking files in changesets and manifests
608 crosschecking files in changesets and manifests
609 b/bar/fruits.txt@0: in changeset but not in manifest
609 b/bar/fruits.txt@0: in changeset but not in manifest
610 b/bar/orange/fly/gnat.py@0: in changeset but not in manifest
610 b/bar/orange/fly/gnat.py@0: in changeset but not in manifest
611 b/bar/orange/fly/housefly.txt@0: in changeset but not in manifest
611 b/bar/orange/fly/housefly.txt@0: in changeset but not in manifest
612 b/foo/apple/bees/flower.py@0: in changeset but not in manifest
612 b/foo/apple/bees/flower.py@0: in changeset but not in manifest
613 checking files
613 checking files
614 8 files, 4 changesets, 18 total revisions
614 8 files, 4 changesets, 18 total revisions
615 6 warnings encountered!
615 6 warnings encountered!
616 9 integrity errors encountered!
616 9 integrity errors encountered!
617 (first damaged changeset appears to be 0)
617 (first damaged changeset appears to be 0)
618 [1]
618 [1]
619 $ cp -R .hg/store-newcopy/. .hg/store
619 $ cp -R .hg/store-newcopy/. .hg/store
620
620
621 Verify reports missing dirlog entry
621 Verify reports missing dirlog entry
622 $ mv -f .hg/store-copy/meta/b/00manifest.* .hg/store/meta/b/
622 $ mv -f .hg/store-copy/meta/b/00manifest.* .hg/store/meta/b/
623 $ hg verify
623 $ hg verify
624 checking changesets
624 checking changesets
625 checking manifests
625 checking manifests
626 checking directory manifests
626 checking directory manifests
627 b/@2: parent-directory manifest refers to unknown revision ac0d30948e0b
627 b/@2: parent-directory manifest refers to unknown revision ac0d30948e0b
628 b/@3: parent-directory manifest refers to unknown revision 367152e6af28
628 b/@3: parent-directory manifest refers to unknown revision 367152e6af28
629 b/bar/@?: rev 2 points to unexpected changeset 2
629 b/bar/@?: rev 2 points to unexpected changeset 2
630 b/bar/@?: 44d7e1146e0d not in parent-directory manifest
630 b/bar/@?: 44d7e1146e0d not in parent-directory manifest
631 b/bar/@?: rev 3 points to unexpected changeset 3
631 b/bar/@?: rev 3 points to unexpected changeset 3
632 b/bar/@?: 70b10c6b17b7 not in parent-directory manifest
632 b/bar/@?: 70b10c6b17b7 not in parent-directory manifest
633 b/bar/orange/@?: rev 2 points to unexpected changeset 3
633 b/bar/orange/@?: rev 2 points to unexpected changeset 3
634 (expected None)
634 (expected None)
635 b/bar/orange/fly/@?: rev 2 points to unexpected changeset 3
635 b/bar/orange/fly/@?: rev 2 points to unexpected changeset 3
636 (expected None)
636 (expected None)
637 crosschecking files in changesets and manifests
637 crosschecking files in changesets and manifests
638 checking files
638 checking files
639 8 files, 4 changesets, 18 total revisions
639 8 files, 4 changesets, 18 total revisions
640 2 warnings encountered!
640 2 warnings encountered!
641 8 integrity errors encountered!
641 8 integrity errors encountered!
642 (first damaged changeset appears to be 2)
642 (first damaged changeset appears to be 2)
643 [1]
643 [1]
644 $ cp -R .hg/store-newcopy/. .hg/store
644 $ cp -R .hg/store-newcopy/. .hg/store
645
645
646 Test cloning a treemanifest repo over http.
646 Test cloning a treemanifest repo over http.
647 $ hg serve -p $HGPORT -d --pid-file=hg.pid --errorlog=errors.log
647 $ hg serve -p $HGPORT -d --pid-file=hg.pid --errorlog=errors.log
648 $ cat hg.pid >> $DAEMON_PIDS
648 $ cat hg.pid >> $DAEMON_PIDS
649 $ cd ..
649 $ cd ..
650 We can clone even with the knob turned off and we'll get a treemanifest repo.
650 We can clone even with the knob turned off and we'll get a treemanifest repo.
651 $ hg clone --config experimental.treemanifest=False \
651 $ hg clone --config experimental.treemanifest=False \
652 > --config experimental.changegroup3=True \
652 > --config experimental.changegroup3=True \
653 > http://localhost:$HGPORT deepclone
653 > http://localhost:$HGPORT deepclone
654 requesting all changes
654 requesting all changes
655 adding changesets
655 adding changesets
656 adding manifests
656 adding manifests
657 adding file changes
657 adding file changes
658 added 4 changesets with 18 changes to 8 files
658 added 4 changesets with 18 changes to 8 files
659 new changesets 775704be6f52:523e5c631710
659 new changesets 775704be6f52:523e5c631710
660 updating to branch default
660 updating to branch default
661 8 files updated, 0 files merged, 0 files removed, 0 files unresolved
661 8 files updated, 0 files merged, 0 files removed, 0 files unresolved
662 No server errors.
662 No server errors.
663 $ cat deeprepo/errors.log
663 $ cat deeprepo/errors.log
664 requires got updated to include treemanifest
664 requires got updated to include treemanifest
665 $ cat deepclone/.hg/requires | grep treemanifest
665 $ cat deepclone/.hg/requires | grep treemanifest
666 treemanifest
666 treemanifest
667 Tree manifest revlogs exist.
667 Tree manifest revlogs exist.
668 $ find deepclone/.hg/store/meta | sort
668 $ find deepclone/.hg/store/meta | sort
669 deepclone/.hg/store/meta
669 deepclone/.hg/store/meta
670 deepclone/.hg/store/meta/b
670 deepclone/.hg/store/meta/b
671 deepclone/.hg/store/meta/b/00manifest.i
671 deepclone/.hg/store/meta/b/00manifest.i
672 deepclone/.hg/store/meta/b/bar
672 deepclone/.hg/store/meta/b/bar
673 deepclone/.hg/store/meta/b/bar/00manifest.i
673 deepclone/.hg/store/meta/b/bar/00manifest.i
674 deepclone/.hg/store/meta/b/bar/orange
674 deepclone/.hg/store/meta/b/bar/orange
675 deepclone/.hg/store/meta/b/bar/orange/00manifest.i
675 deepclone/.hg/store/meta/b/bar/orange/00manifest.i
676 deepclone/.hg/store/meta/b/bar/orange/fly
676 deepclone/.hg/store/meta/b/bar/orange/fly
677 deepclone/.hg/store/meta/b/bar/orange/fly/00manifest.i
677 deepclone/.hg/store/meta/b/bar/orange/fly/00manifest.i
678 deepclone/.hg/store/meta/b/foo
678 deepclone/.hg/store/meta/b/foo
679 deepclone/.hg/store/meta/b/foo/00manifest.i
679 deepclone/.hg/store/meta/b/foo/00manifest.i
680 deepclone/.hg/store/meta/b/foo/apple
680 deepclone/.hg/store/meta/b/foo/apple
681 deepclone/.hg/store/meta/b/foo/apple/00manifest.i
681 deepclone/.hg/store/meta/b/foo/apple/00manifest.i
682 deepclone/.hg/store/meta/b/foo/apple/bees
682 deepclone/.hg/store/meta/b/foo/apple/bees
683 deepclone/.hg/store/meta/b/foo/apple/bees/00manifest.i
683 deepclone/.hg/store/meta/b/foo/apple/bees/00manifest.i
684 deepclone/.hg/store/meta/~2e_a
684 deepclone/.hg/store/meta/~2e_a
685 deepclone/.hg/store/meta/~2e_a/00manifest.i
685 deepclone/.hg/store/meta/~2e_a/00manifest.i
686 Verify passes.
686 Verify passes.
687 $ cd deepclone
687 $ cd deepclone
688 $ hg verify
688 $ hg verify
689 checking changesets
689 checking changesets
690 checking manifests
690 checking manifests
691 checking directory manifests
691 checking directory manifests
692 crosschecking files in changesets and manifests
692 crosschecking files in changesets and manifests
693 checking files
693 checking files
694 8 files, 4 changesets, 18 total revisions
694 8 files, 4 changesets, 18 total revisions
695 $ cd ..
695 $ cd ..
696
696
697 Create clones using old repo formats to use in later tests
697 Create clones using old repo formats to use in later tests
698 $ hg clone --config format.usestore=False \
698 $ hg clone --config format.usestore=False \
699 > --config experimental.changegroup3=True \
699 > --config experimental.changegroup3=True \
700 > http://localhost:$HGPORT deeprepo-basicstore
700 > http://localhost:$HGPORT deeprepo-basicstore
701 requesting all changes
701 requesting all changes
702 adding changesets
702 adding changesets
703 adding manifests
703 adding manifests
704 adding file changes
704 adding file changes
705 added 4 changesets with 18 changes to 8 files
705 added 4 changesets with 18 changes to 8 files
706 new changesets 775704be6f52:523e5c631710
706 new changesets 775704be6f52:523e5c631710
707 updating to branch default
707 updating to branch default
708 8 files updated, 0 files merged, 0 files removed, 0 files unresolved
708 8 files updated, 0 files merged, 0 files removed, 0 files unresolved
709 $ cd deeprepo-basicstore
709 $ cd deeprepo-basicstore
710 $ grep store .hg/requires
710 $ grep store .hg/requires
711 [1]
711 [1]
712 $ hg serve -p $HGPORT1 -d --pid-file=hg.pid --errorlog=errors.log
712 $ hg serve -p $HGPORT1 -d --pid-file=hg.pid --errorlog=errors.log
713 $ cat hg.pid >> $DAEMON_PIDS
713 $ cat hg.pid >> $DAEMON_PIDS
714 $ cd ..
714 $ cd ..
715 $ hg clone --config format.usefncache=False \
715 $ hg clone --config format.usefncache=False \
716 > --config experimental.changegroup3=True \
716 > --config experimental.changegroup3=True \
717 > http://localhost:$HGPORT deeprepo-encodedstore
717 > http://localhost:$HGPORT deeprepo-encodedstore
718 requesting all changes
718 requesting all changes
719 adding changesets
719 adding changesets
720 adding manifests
720 adding manifests
721 adding file changes
721 adding file changes
722 added 4 changesets with 18 changes to 8 files
722 added 4 changesets with 18 changes to 8 files
723 new changesets 775704be6f52:523e5c631710
723 new changesets 775704be6f52:523e5c631710
724 updating to branch default
724 updating to branch default
725 8 files updated, 0 files merged, 0 files removed, 0 files unresolved
725 8 files updated, 0 files merged, 0 files removed, 0 files unresolved
726 $ cd deeprepo-encodedstore
726 $ cd deeprepo-encodedstore
727 $ grep fncache .hg/requires
727 $ grep fncache .hg/requires
728 [1]
728 [1]
729 $ hg serve -p $HGPORT2 -d --pid-file=hg.pid --errorlog=errors.log
729 $ hg serve -p $HGPORT2 -d --pid-file=hg.pid --errorlog=errors.log
730 $ cat hg.pid >> $DAEMON_PIDS
730 $ cat hg.pid >> $DAEMON_PIDS
731 $ cd ..
731 $ cd ..
732
732
733 Local clone with basicstore
733 Local clone with basicstore
734 $ hg clone -U deeprepo-basicstore local-clone-basicstore
734 $ hg clone -U deeprepo-basicstore local-clone-basicstore
735 $ hg -R local-clone-basicstore verify
735 $ hg -R local-clone-basicstore verify
736 checking changesets
736 checking changesets
737 checking manifests
737 checking manifests
738 checking directory manifests
738 checking directory manifests
739 crosschecking files in changesets and manifests
739 crosschecking files in changesets and manifests
740 checking files
740 checking files
741 8 files, 4 changesets, 18 total revisions
741 8 files, 4 changesets, 18 total revisions
742
742
743 Local clone with encodedstore
743 Local clone with encodedstore
744 $ hg clone -U deeprepo-encodedstore local-clone-encodedstore
744 $ hg clone -U deeprepo-encodedstore local-clone-encodedstore
745 $ hg -R local-clone-encodedstore verify
745 $ hg -R local-clone-encodedstore verify
746 checking changesets
746 checking changesets
747 checking manifests
747 checking manifests
748 checking directory manifests
748 checking directory manifests
749 crosschecking files in changesets and manifests
749 crosschecking files in changesets and manifests
750 checking files
750 checking files
751 8 files, 4 changesets, 18 total revisions
751 8 files, 4 changesets, 18 total revisions
752
752
753 Local clone with fncachestore
753 Local clone with fncachestore
754 $ hg clone -U deeprepo local-clone-fncachestore
754 $ hg clone -U deeprepo local-clone-fncachestore
755 $ hg -R local-clone-fncachestore verify
755 $ hg -R local-clone-fncachestore verify
756 checking changesets
756 checking changesets
757 checking manifests
757 checking manifests
758 checking directory manifests
758 checking directory manifests
759 crosschecking files in changesets and manifests
759 crosschecking files in changesets and manifests
760 checking files
760 checking files
761 8 files, 4 changesets, 18 total revisions
761 8 files, 4 changesets, 18 total revisions
762
762
763 Stream clone with basicstore
763 Stream clone with basicstore
764 $ hg clone --config experimental.changegroup3=True --stream -U \
764 $ hg clone --config experimental.changegroup3=True --stream -U \
765 > http://localhost:$HGPORT1 stream-clone-basicstore
765 > http://localhost:$HGPORT1 stream-clone-basicstore
766 streaming all changes
766 streaming all changes
767 18 files to transfer, * of data (glob)
767 18 files to transfer, * of data (glob)
768 transferred * in * seconds (*) (glob)
768 transferred * in * seconds (*) (glob)
769 searching for changes
769 searching for changes
770 no changes found
770 no changes found
771 $ hg -R stream-clone-basicstore verify
771 $ hg -R stream-clone-basicstore verify
772 checking changesets
772 checking changesets
773 checking manifests
773 checking manifests
774 checking directory manifests
774 checking directory manifests
775 crosschecking files in changesets and manifests
775 crosschecking files in changesets and manifests
776 checking files
776 checking files
777 8 files, 4 changesets, 18 total revisions
777 8 files, 4 changesets, 18 total revisions
778
778
779 Stream clone with encodedstore
779 Stream clone with encodedstore
780 $ hg clone --config experimental.changegroup3=True --stream -U \
780 $ hg clone --config experimental.changegroup3=True --stream -U \
781 > http://localhost:$HGPORT2 stream-clone-encodedstore
781 > http://localhost:$HGPORT2 stream-clone-encodedstore
782 streaming all changes
782 streaming all changes
783 18 files to transfer, * of data (glob)
783 18 files to transfer, * of data (glob)
784 transferred * in * seconds (*) (glob)
784 transferred * in * seconds (*) (glob)
785 searching for changes
785 searching for changes
786 no changes found
786 no changes found
787 $ hg -R stream-clone-encodedstore verify
787 $ hg -R stream-clone-encodedstore verify
788 checking changesets
788 checking changesets
789 checking manifests
789 checking manifests
790 checking directory manifests
790 checking directory manifests
791 crosschecking files in changesets and manifests
791 crosschecking files in changesets and manifests
792 checking files
792 checking files
793 8 files, 4 changesets, 18 total revisions
793 8 files, 4 changesets, 18 total revisions
794
794
795 Stream clone with fncachestore
795 Stream clone with fncachestore
796 $ hg clone --config experimental.changegroup3=True --stream -U \
796 $ hg clone --config experimental.changegroup3=True --stream -U \
797 > http://localhost:$HGPORT stream-clone-fncachestore
797 > http://localhost:$HGPORT stream-clone-fncachestore
798 streaming all changes
798 streaming all changes
799 18 files to transfer, * of data (glob)
799 18 files to transfer, * of data (glob)
800 transferred * in * seconds (*) (glob)
800 transferred * in * seconds (*) (glob)
801 searching for changes
801 searching for changes
802 no changes found
802 no changes found
803 $ hg -R stream-clone-fncachestore verify
803 $ hg -R stream-clone-fncachestore verify
804 checking changesets
804 checking changesets
805 checking manifests
805 checking manifests
806 checking directory manifests
806 checking directory manifests
807 crosschecking files in changesets and manifests
807 crosschecking files in changesets and manifests
808 checking files
808 checking files
809 8 files, 4 changesets, 18 total revisions
809 8 files, 4 changesets, 18 total revisions
810
810
811 Packed bundle
811 Packed bundle
812 $ hg -R deeprepo debugcreatestreamclonebundle repo-packed.hg
812 $ hg -R deeprepo debugcreatestreamclonebundle repo-packed.hg
813 writing 5330 bytes for 18 files
813 writing 5330 bytes for 18 files
814 bundle requirements: generaldelta, revlogv1, treemanifest
814 bundle requirements: generaldelta, revlogv1, treemanifest
815 $ hg debugbundle --spec repo-packed.hg
815 $ hg debugbundle --spec repo-packed.hg
816 none-packed1;requirements%3Dgeneraldelta%2Crevlogv1%2Ctreemanifest
816 none-packed1;requirements%3Dgeneraldelta%2Crevlogv1%2Ctreemanifest
817
817
818 Bundle with changegroup2 is not supported
818 Bundle with changegroup2 is not supported
819
819
820 $ hg -R deeprepo bundle --all -t v2 deeprepo.bundle
820 $ hg -R deeprepo bundle --all -t v2 deeprepo.bundle
821 abort: repository does not support bundle version 02
821 abort: repository does not support bundle version 02
822 [255]
822 [255]
823
823
824 Pull does not include changegroup for manifest the client already has from
824 Pull does not include changegroup for manifest the client already has from
825 other branch
825 other branch
826
826
827 $ mkdir grafted-dir-repo
827 $ mkdir grafted-dir-repo
828 $ cd grafted-dir-repo
828 $ cd grafted-dir-repo
829 $ hg --config experimental.treemanifest=1 init
829 $ hg --config experimental.treemanifest=1 init
830 $ mkdir dir
830 $ mkdir dir
831 $ echo a > dir/file
831 $ echo a > dir/file
832 $ echo a > file
832 $ echo a > file
833 $ hg ci -Am initial
833 $ hg ci -Am initial
834 adding dir/file
834 adding dir/file
835 adding file
835 adding file
836 $ echo b > dir/file
836 $ echo b > dir/file
837 $ hg ci -m updated
837 $ hg ci -m updated
838 $ hg co '.^'
838 $ hg co '.^'
839 1 files updated, 0 files merged, 0 files removed, 0 files unresolved
839 1 files updated, 0 files merged, 0 files removed, 0 files unresolved
840 $ hg revert -r tip dir/
840 $ hg revert -r tip dir/
841 reverting dir/file
841 reverting dir/file
842 $ echo b > file # to make sure root manifest is sent
842 $ echo b > file # to make sure root manifest is sent
843 $ hg ci -m grafted
843 $ hg ci -m grafted
844 created new head
844 created new head
845 $ cd ..
845 $ cd ..
846
846
847 $ hg --config experimental.treemanifest=1 clone --pull -r 1 \
847 $ hg --config experimental.treemanifest=1 clone --pull -r 1 \
848 > grafted-dir-repo grafted-dir-repo-clone
848 > grafted-dir-repo grafted-dir-repo-clone
849 adding changesets
849 adding changesets
850 adding manifests
850 adding manifests
851 adding file changes
851 adding file changes
852 added 2 changesets with 3 changes to 2 files
852 added 2 changesets with 3 changes to 2 files
853 new changesets d84f4c419457:09ab742f3b0f
853 new changesets d84f4c419457:09ab742f3b0f
854 updating to branch default
854 updating to branch default
855 2 files updated, 0 files merged, 0 files removed, 0 files unresolved
855 2 files updated, 0 files merged, 0 files removed, 0 files unresolved
856 $ cd grafted-dir-repo-clone
856 $ cd grafted-dir-repo-clone
857 $ hg pull -r 2
857 $ hg pull -r 2
858 pulling from $TESTTMP/grafted-dir-repo
858 pulling from $TESTTMP/grafted-dir-repo
859 searching for changes
859 searching for changes
860 adding changesets
860 adding changesets
861 adding manifests
861 adding manifests
862 adding file changes
862 adding file changes
863 added 1 changesets with 1 changes to 1 files (+1 heads)
863 added 1 changesets with 1 changes to 1 files (+1 heads)
864 new changesets 73699489fb7c
864 new changesets 73699489fb7c
865 (run 'hg heads' to see heads, 'hg merge' to merge)
865 (run 'hg heads' to see heads, 'hg merge' to merge)
866
866
867 Committing a empty commit does not duplicate root treemanifest
867 Committing a empty commit does not duplicate root treemanifest
868 $ echo z >> z
868 $ echo z >> z
869 $ hg commit -Aqm 'pre-empty commit'
869 $ hg commit -Aqm 'pre-empty commit'
870 $ hg rm z
870 $ hg rm z
871 $ hg commit --amend -m 'empty commit'
871 $ hg commit --amend -m 'empty commit'
872 saved backup bundle to $TESTTMP/grafted-dir-repo-clone/.hg/strip-backup/cb99d5717cea-9e3b6b02-amend.hg
872 saved backup bundle to $TESTTMP/grafted-dir-repo-clone/.hg/strip-backup/cb99d5717cea-9e3b6b02-amend.hg
873 $ hg log -r 'tip + tip^' -T '{manifest}\n'
873 $ hg log -r 'tip + tip^' -T '{manifest}\n'
874 1:678d3574b88c
874 1:678d3574b88c
875 1:678d3574b88c
875 1:678d3574b88c
876 $ hg --config extensions.strip= strip -r . -q
876 $ hg --config extensions.strip= strip -r . -q
@@ -1,363 +1,363 b''
1 prepare repo
1 prepare repo
2
2
3 $ hg init a
3 $ hg init a
4 $ cd a
4 $ cd a
5 $ echo "some text" > FOO.txt
5 $ echo "some text" > FOO.txt
6 $ echo "another text" > bar.txt
6 $ echo "another text" > bar.txt
7 $ echo "more text" > QUICK.txt
7 $ echo "more text" > QUICK.txt
8 $ hg add
8 $ hg add
9 adding FOO.txt
9 adding FOO.txt
10 adding QUICK.txt
10 adding QUICK.txt
11 adding bar.txt
11 adding bar.txt
12 $ hg ci -mtest1
12 $ hg ci -mtest1
13
13
14 verify
14 verify
15
15
16 $ hg verify
16 $ hg verify
17 checking changesets
17 checking changesets
18 checking manifests
18 checking manifests
19 crosschecking files in changesets and manifests
19 crosschecking files in changesets and manifests
20 checking files
20 checking files
21 3 files, 1 changesets, 3 total revisions
21 3 files, 1 changesets, 3 total revisions
22
22
23 verify with journal
23 verify with journal
24
24
25 $ touch .hg/store/journal
25 $ touch .hg/store/journal
26 $ hg verify
26 $ hg verify
27 abandoned transaction found - run hg recover
27 abandoned transaction found - run hg recover
28 checking changesets
28 checking changesets
29 checking manifests
29 checking manifests
30 crosschecking files in changesets and manifests
30 crosschecking files in changesets and manifests
31 checking files
31 checking files
32 3 files, 1 changesets, 3 total revisions
32 3 files, 1 changesets, 3 total revisions
33 $ rm .hg/store/journal
33 $ rm .hg/store/journal
34
34
35 introduce some bugs in repo
35 introduce some bugs in repo
36
36
37 $ cd .hg/store/data
37 $ cd .hg/store/data
38 $ mv _f_o_o.txt.i X_f_o_o.txt.i
38 $ mv _f_o_o.txt.i X_f_o_o.txt.i
39 $ mv bar.txt.i xbar.txt.i
39 $ mv bar.txt.i xbar.txt.i
40 $ rm _q_u_i_c_k.txt.i
40 $ rm _q_u_i_c_k.txt.i
41
41
42 $ hg verify
42 $ hg verify
43 checking changesets
43 checking changesets
44 checking manifests
44 checking manifests
45 crosschecking files in changesets and manifests
45 crosschecking files in changesets and manifests
46 checking files
46 checking files
47 warning: revlog 'data/FOO.txt.i' not in fncache!
47 warning: revlog 'data/FOO.txt.i' not in fncache!
48 0: empty or missing FOO.txt
48 0: empty or missing FOO.txt
49 FOO.txt@0: manifest refers to unknown revision f62022d3d590
49 FOO.txt@0: manifest refers to unknown revision f62022d3d590
50 warning: revlog 'data/QUICK.txt.i' not in fncache!
50 warning: revlog 'data/QUICK.txt.i' not in fncache!
51 0: empty or missing QUICK.txt
51 0: empty or missing QUICK.txt
52 QUICK.txt@0: manifest refers to unknown revision 88b857db8eba
52 QUICK.txt@0: manifest refers to unknown revision 88b857db8eba
53 warning: revlog 'data/bar.txt.i' not in fncache!
53 warning: revlog 'data/bar.txt.i' not in fncache!
54 0: empty or missing bar.txt
54 0: empty or missing bar.txt
55 bar.txt@0: manifest refers to unknown revision 256559129457
55 bar.txt@0: manifest refers to unknown revision 256559129457
56 3 files, 1 changesets, 0 total revisions
56 3 files, 1 changesets, 0 total revisions
57 3 warnings encountered!
57 3 warnings encountered!
58 hint: run "hg debugrebuildfncache" to recover from corrupt fncache
58 hint: run "hg debugrebuildfncache" to recover from corrupt fncache
59 6 integrity errors encountered!
59 6 integrity errors encountered!
60 (first damaged changeset appears to be 0)
60 (first damaged changeset appears to be 0)
61 [1]
61 [1]
62
62
63 $ cd ../../..
63 $ cd ../../..
64 $ cd ..
64 $ cd ..
65
65
66 Set up a repo for testing missing revlog entries
66 Set up a repo for testing missing revlog entries
67
67
68 $ hg init missing-entries
68 $ hg init missing-entries
69 $ cd missing-entries
69 $ cd missing-entries
70 $ echo 0 > file
70 $ echo 0 > file
71 $ hg ci -Aqm0
71 $ hg ci -Aqm0
72 $ cp -R .hg/store .hg/store-partial
72 $ cp -R .hg/store .hg/store-partial
73 $ echo 1 > file
73 $ echo 1 > file
74 $ hg ci -Aqm1
74 $ hg ci -Aqm1
75 $ cp -R .hg/store .hg/store-full
75 $ cp -R .hg/store .hg/store-full
76
76
77 Entire changelog missing
77 Entire changelog missing
78
78
79 $ rm .hg/store/00changelog.*
79 $ rm .hg/store/00changelog.*
80 $ hg verify -q
80 $ hg verify -q
81 0: empty or missing changelog
81 0: empty or missing changelog
82 manifest@0: d0b6632564d4 not in changesets
82 manifest@0: d0b6632564d4 not in changesets
83 manifest@1: 941fc4534185 not in changesets
83 manifest@1: 941fc4534185 not in changesets
84 3 integrity errors encountered!
84 3 integrity errors encountered!
85 (first damaged changeset appears to be 0)
85 (first damaged changeset appears to be 0)
86 [1]
86 [1]
87 $ cp -R .hg/store-full/. .hg/store
87 $ cp -R .hg/store-full/. .hg/store
88
88
89 Entire manifest log missing
89 Entire manifest log missing
90
90
91 $ rm .hg/store/00manifest.*
91 $ rm .hg/store/00manifest.*
92 $ hg verify -q
92 $ hg verify -q
93 0: empty or missing manifest
93 0: empty or missing manifest
94 1 integrity errors encountered!
94 1 integrity errors encountered!
95 (first damaged changeset appears to be 0)
95 (first damaged changeset appears to be 0)
96 [1]
96 [1]
97 $ cp -R .hg/store-full/. .hg/store
97 $ cp -R .hg/store-full/. .hg/store
98
98
99 Entire filelog missing
99 Entire filelog missing
100
100
101 $ rm .hg/store/data/file.*
101 $ rm .hg/store/data/file.*
102 $ hg verify -q
102 $ hg verify -q
103 warning: revlog 'data/file.i' not in fncache!
103 warning: revlog 'data/file.i' not in fncache!
104 0: empty or missing file
104 0: empty or missing file
105 file@0: manifest refers to unknown revision 362fef284ce2
105 file@0: manifest refers to unknown revision 362fef284ce2
106 file@1: manifest refers to unknown revision c10f2164107d
106 file@1: manifest refers to unknown revision c10f2164107d
107 1 warnings encountered!
107 1 warnings encountered!
108 hint: run "hg debugrebuildfncache" to recover from corrupt fncache
108 hint: run "hg debugrebuildfncache" to recover from corrupt fncache
109 3 integrity errors encountered!
109 3 integrity errors encountered!
110 (first damaged changeset appears to be 0)
110 (first damaged changeset appears to be 0)
111 [1]
111 [1]
112 $ cp -R .hg/store-full/. .hg/store
112 $ cp -R .hg/store-full/. .hg/store
113
113
114 Entire changelog and manifest log missing
114 Entire changelog and manifest log missing
115
115
116 $ rm .hg/store/00changelog.*
116 $ rm .hg/store/00changelog.*
117 $ rm .hg/store/00manifest.*
117 $ rm .hg/store/00manifest.*
118 $ hg verify -q
118 $ hg verify -q
119 warning: orphan revlog 'data/file.i'
119 warning: orphan data file 'data/file.i'
120 1 warnings encountered!
120 1 warnings encountered!
121 $ cp -R .hg/store-full/. .hg/store
121 $ cp -R .hg/store-full/. .hg/store
122
122
123 Entire changelog and filelog missing
123 Entire changelog and filelog missing
124
124
125 $ rm .hg/store/00changelog.*
125 $ rm .hg/store/00changelog.*
126 $ rm .hg/store/data/file.*
126 $ rm .hg/store/data/file.*
127 $ hg verify -q
127 $ hg verify -q
128 0: empty or missing changelog
128 0: empty or missing changelog
129 manifest@0: d0b6632564d4 not in changesets
129 manifest@0: d0b6632564d4 not in changesets
130 manifest@1: 941fc4534185 not in changesets
130 manifest@1: 941fc4534185 not in changesets
131 warning: revlog 'data/file.i' not in fncache!
131 warning: revlog 'data/file.i' not in fncache!
132 ?: empty or missing file
132 ?: empty or missing file
133 file@0: manifest refers to unknown revision 362fef284ce2
133 file@0: manifest refers to unknown revision 362fef284ce2
134 file@1: manifest refers to unknown revision c10f2164107d
134 file@1: manifest refers to unknown revision c10f2164107d
135 1 warnings encountered!
135 1 warnings encountered!
136 hint: run "hg debugrebuildfncache" to recover from corrupt fncache
136 hint: run "hg debugrebuildfncache" to recover from corrupt fncache
137 6 integrity errors encountered!
137 6 integrity errors encountered!
138 (first damaged changeset appears to be 0)
138 (first damaged changeset appears to be 0)
139 [1]
139 [1]
140 $ cp -R .hg/store-full/. .hg/store
140 $ cp -R .hg/store-full/. .hg/store
141
141
142 Entire manifest log and filelog missing
142 Entire manifest log and filelog missing
143
143
144 $ rm .hg/store/00manifest.*
144 $ rm .hg/store/00manifest.*
145 $ rm .hg/store/data/file.*
145 $ rm .hg/store/data/file.*
146 $ hg verify -q
146 $ hg verify -q
147 0: empty or missing manifest
147 0: empty or missing manifest
148 warning: revlog 'data/file.i' not in fncache!
148 warning: revlog 'data/file.i' not in fncache!
149 0: empty or missing file
149 0: empty or missing file
150 1 warnings encountered!
150 1 warnings encountered!
151 hint: run "hg debugrebuildfncache" to recover from corrupt fncache
151 hint: run "hg debugrebuildfncache" to recover from corrupt fncache
152 2 integrity errors encountered!
152 2 integrity errors encountered!
153 (first damaged changeset appears to be 0)
153 (first damaged changeset appears to be 0)
154 [1]
154 [1]
155 $ cp -R .hg/store-full/. .hg/store
155 $ cp -R .hg/store-full/. .hg/store
156
156
157 Changelog missing entry
157 Changelog missing entry
158
158
159 $ cp -f .hg/store-partial/00changelog.* .hg/store
159 $ cp -f .hg/store-partial/00changelog.* .hg/store
160 $ hg verify -q
160 $ hg verify -q
161 manifest@?: rev 1 points to nonexistent changeset 1
161 manifest@?: rev 1 points to nonexistent changeset 1
162 manifest@?: 941fc4534185 not in changesets
162 manifest@?: 941fc4534185 not in changesets
163 file@?: rev 1 points to nonexistent changeset 1
163 file@?: rev 1 points to nonexistent changeset 1
164 (expected 0)
164 (expected 0)
165 1 warnings encountered!
165 1 warnings encountered!
166 3 integrity errors encountered!
166 3 integrity errors encountered!
167 [1]
167 [1]
168 $ cp -R .hg/store-full/. .hg/store
168 $ cp -R .hg/store-full/. .hg/store
169
169
170 Manifest log missing entry
170 Manifest log missing entry
171
171
172 $ cp -f .hg/store-partial/00manifest.* .hg/store
172 $ cp -f .hg/store-partial/00manifest.* .hg/store
173 $ hg verify -q
173 $ hg verify -q
174 manifest@1: changeset refers to unknown revision 941fc4534185
174 manifest@1: changeset refers to unknown revision 941fc4534185
175 file@1: c10f2164107d not in manifests
175 file@1: c10f2164107d not in manifests
176 2 integrity errors encountered!
176 2 integrity errors encountered!
177 (first damaged changeset appears to be 1)
177 (first damaged changeset appears to be 1)
178 [1]
178 [1]
179 $ cp -R .hg/store-full/. .hg/store
179 $ cp -R .hg/store-full/. .hg/store
180
180
181 Filelog missing entry
181 Filelog missing entry
182
182
183 $ cp -f .hg/store-partial/data/file.* .hg/store/data
183 $ cp -f .hg/store-partial/data/file.* .hg/store/data
184 $ hg verify -q
184 $ hg verify -q
185 file@1: manifest refers to unknown revision c10f2164107d
185 file@1: manifest refers to unknown revision c10f2164107d
186 1 integrity errors encountered!
186 1 integrity errors encountered!
187 (first damaged changeset appears to be 1)
187 (first damaged changeset appears to be 1)
188 [1]
188 [1]
189 $ cp -R .hg/store-full/. .hg/store
189 $ cp -R .hg/store-full/. .hg/store
190
190
191 Changelog and manifest log missing entry
191 Changelog and manifest log missing entry
192
192
193 $ cp -f .hg/store-partial/00changelog.* .hg/store
193 $ cp -f .hg/store-partial/00changelog.* .hg/store
194 $ cp -f .hg/store-partial/00manifest.* .hg/store
194 $ cp -f .hg/store-partial/00manifest.* .hg/store
195 $ hg verify -q
195 $ hg verify -q
196 file@?: rev 1 points to nonexistent changeset 1
196 file@?: rev 1 points to nonexistent changeset 1
197 (expected 0)
197 (expected 0)
198 file@?: c10f2164107d not in manifests
198 file@?: c10f2164107d not in manifests
199 1 warnings encountered!
199 1 warnings encountered!
200 2 integrity errors encountered!
200 2 integrity errors encountered!
201 [1]
201 [1]
202 $ cp -R .hg/store-full/. .hg/store
202 $ cp -R .hg/store-full/. .hg/store
203
203
204 Changelog and filelog missing entry
204 Changelog and filelog missing entry
205
205
206 $ cp -f .hg/store-partial/00changelog.* .hg/store
206 $ cp -f .hg/store-partial/00changelog.* .hg/store
207 $ cp -f .hg/store-partial/data/file.* .hg/store/data
207 $ cp -f .hg/store-partial/data/file.* .hg/store/data
208 $ hg verify -q
208 $ hg verify -q
209 manifest@?: rev 1 points to nonexistent changeset 1
209 manifest@?: rev 1 points to nonexistent changeset 1
210 manifest@?: 941fc4534185 not in changesets
210 manifest@?: 941fc4534185 not in changesets
211 file@?: manifest refers to unknown revision c10f2164107d
211 file@?: manifest refers to unknown revision c10f2164107d
212 3 integrity errors encountered!
212 3 integrity errors encountered!
213 [1]
213 [1]
214 $ cp -R .hg/store-full/. .hg/store
214 $ cp -R .hg/store-full/. .hg/store
215
215
216 Manifest and filelog missing entry
216 Manifest and filelog missing entry
217
217
218 $ cp -f .hg/store-partial/00manifest.* .hg/store
218 $ cp -f .hg/store-partial/00manifest.* .hg/store
219 $ cp -f .hg/store-partial/data/file.* .hg/store/data
219 $ cp -f .hg/store-partial/data/file.* .hg/store/data
220 $ hg verify -q
220 $ hg verify -q
221 manifest@1: changeset refers to unknown revision 941fc4534185
221 manifest@1: changeset refers to unknown revision 941fc4534185
222 1 integrity errors encountered!
222 1 integrity errors encountered!
223 (first damaged changeset appears to be 1)
223 (first damaged changeset appears to be 1)
224 [1]
224 [1]
225 $ cp -R .hg/store-full/. .hg/store
225 $ cp -R .hg/store-full/. .hg/store
226
226
227 Corrupt changelog base node to cause failure to read revision
227 Corrupt changelog base node to cause failure to read revision
228
228
229 $ printf abcd | dd conv=notrunc of=.hg/store/00changelog.i bs=1 seek=16 \
229 $ printf abcd | dd conv=notrunc of=.hg/store/00changelog.i bs=1 seek=16 \
230 > 2> /dev/null
230 > 2> /dev/null
231 $ hg verify -q
231 $ hg verify -q
232 0: unpacking changeset 08b1860757c2: * (glob)
232 0: unpacking changeset 08b1860757c2: * (glob)
233 manifest@?: rev 0 points to unexpected changeset 0
233 manifest@?: rev 0 points to unexpected changeset 0
234 manifest@?: d0b6632564d4 not in changesets
234 manifest@?: d0b6632564d4 not in changesets
235 file@?: rev 0 points to unexpected changeset 0
235 file@?: rev 0 points to unexpected changeset 0
236 (expected 1)
236 (expected 1)
237 1 warnings encountered!
237 1 warnings encountered!
238 4 integrity errors encountered!
238 4 integrity errors encountered!
239 (first damaged changeset appears to be 0)
239 (first damaged changeset appears to be 0)
240 [1]
240 [1]
241 $ cp -R .hg/store-full/. .hg/store
241 $ cp -R .hg/store-full/. .hg/store
242
242
243 Corrupt manifest log base node to cause failure to read revision
243 Corrupt manifest log base node to cause failure to read revision
244
244
245 $ printf abcd | dd conv=notrunc of=.hg/store/00manifest.i bs=1 seek=16 \
245 $ printf abcd | dd conv=notrunc of=.hg/store/00manifest.i bs=1 seek=16 \
246 > 2> /dev/null
246 > 2> /dev/null
247 $ hg verify -q
247 $ hg verify -q
248 manifest@0: reading delta d0b6632564d4: * (glob)
248 manifest@0: reading delta d0b6632564d4: * (glob)
249 file@0: 362fef284ce2 not in manifests
249 file@0: 362fef284ce2 not in manifests
250 2 integrity errors encountered!
250 2 integrity errors encountered!
251 (first damaged changeset appears to be 0)
251 (first damaged changeset appears to be 0)
252 [1]
252 [1]
253 $ cp -R .hg/store-full/. .hg/store
253 $ cp -R .hg/store-full/. .hg/store
254
254
255 Corrupt filelog base node to cause failure to read revision
255 Corrupt filelog base node to cause failure to read revision
256
256
257 $ printf abcd | dd conv=notrunc of=.hg/store/data/file.i bs=1 seek=16 \
257 $ printf abcd | dd conv=notrunc of=.hg/store/data/file.i bs=1 seek=16 \
258 > 2> /dev/null
258 > 2> /dev/null
259 $ hg verify -q
259 $ hg verify -q
260 file@0: unpacking 362fef284ce2: * (glob)
260 file@0: unpacking 362fef284ce2: * (glob)
261 1 integrity errors encountered!
261 1 integrity errors encountered!
262 (first damaged changeset appears to be 0)
262 (first damaged changeset appears to be 0)
263 [1]
263 [1]
264 $ cp -R .hg/store-full/. .hg/store
264 $ cp -R .hg/store-full/. .hg/store
265
265
266 $ cd ..
266 $ cd ..
267
267
268 test changelog without a manifest
268 test changelog without a manifest
269
269
270 $ hg init b
270 $ hg init b
271 $ cd b
271 $ cd b
272 $ hg branch foo
272 $ hg branch foo
273 marked working directory as branch foo
273 marked working directory as branch foo
274 (branches are permanent and global, did you want a bookmark?)
274 (branches are permanent and global, did you want a bookmark?)
275 $ hg ci -m branchfoo
275 $ hg ci -m branchfoo
276 $ hg verify
276 $ hg verify
277 checking changesets
277 checking changesets
278 checking manifests
278 checking manifests
279 crosschecking files in changesets and manifests
279 crosschecking files in changesets and manifests
280 checking files
280 checking files
281 0 files, 1 changesets, 0 total revisions
281 0 files, 1 changesets, 0 total revisions
282
282
283 test revlog corruption
283 test revlog corruption
284
284
285 $ touch a
285 $ touch a
286 $ hg add a
286 $ hg add a
287 $ hg ci -m a
287 $ hg ci -m a
288
288
289 $ echo 'corrupted' > b
289 $ echo 'corrupted' > b
290 $ dd if=.hg/store/data/a.i of=start bs=1 count=20 2>/dev/null
290 $ dd if=.hg/store/data/a.i of=start bs=1 count=20 2>/dev/null
291 $ cat start b > .hg/store/data/a.i
291 $ cat start b > .hg/store/data/a.i
292
292
293 $ hg verify
293 $ hg verify
294 checking changesets
294 checking changesets
295 checking manifests
295 checking manifests
296 crosschecking files in changesets and manifests
296 crosschecking files in changesets and manifests
297 checking files
297 checking files
298 a@1: broken revlog! (index data/a.i is corrupted)
298 a@1: broken revlog! (index data/a.i is corrupted)
299 warning: orphan revlog 'data/a.i'
299 warning: orphan data file 'data/a.i'
300 1 files, 2 changesets, 0 total revisions
300 1 files, 2 changesets, 0 total revisions
301 1 warnings encountered!
301 1 warnings encountered!
302 1 integrity errors encountered!
302 1 integrity errors encountered!
303 (first damaged changeset appears to be 1)
303 (first damaged changeset appears to be 1)
304 [1]
304 [1]
305
305
306 $ cd ..
306 $ cd ..
307
307
308 test revlog format 0
308 test revlog format 0
309
309
310 $ revlog-formatv0.py
310 $ revlog-formatv0.py
311 $ cd formatv0
311 $ cd formatv0
312 $ hg verify
312 $ hg verify
313 repository uses revlog format 0
313 repository uses revlog format 0
314 checking changesets
314 checking changesets
315 checking manifests
315 checking manifests
316 crosschecking files in changesets and manifests
316 crosschecking files in changesets and manifests
317 checking files
317 checking files
318 1 files, 1 changesets, 1 total revisions
318 1 files, 1 changesets, 1 total revisions
319 $ cd ..
319 $ cd ..
320
320
321 test flag processor and skipflags
321 test flag processor and skipflags
322
322
323 $ hg init skipflags
323 $ hg init skipflags
324 $ cd skipflags
324 $ cd skipflags
325 $ cat >> .hg/hgrc <<EOF
325 $ cat >> .hg/hgrc <<EOF
326 > [extensions]
326 > [extensions]
327 > flagprocessor=$RUNTESTDIR/flagprocessorext.py
327 > flagprocessor=$RUNTESTDIR/flagprocessorext.py
328 > EOF
328 > EOF
329 $ echo '[BASE64]content' > base64
329 $ echo '[BASE64]content' > base64
330 $ hg commit -Aqm 'flag processor content' base64
330 $ hg commit -Aqm 'flag processor content' base64
331 $ hg verify
331 $ hg verify
332 checking changesets
332 checking changesets
333 checking manifests
333 checking manifests
334 crosschecking files in changesets and manifests
334 crosschecking files in changesets and manifests
335 checking files
335 checking files
336 1 files, 1 changesets, 1 total revisions
336 1 files, 1 changesets, 1 total revisions
337
337
338 $ cat >> $TESTTMP/break-base64.py <<EOF
338 $ cat >> $TESTTMP/break-base64.py <<EOF
339 > from __future__ import absolute_import
339 > from __future__ import absolute_import
340 > import base64
340 > import base64
341 > base64.b64decode=lambda x: x
341 > base64.b64decode=lambda x: x
342 > EOF
342 > EOF
343 $ cat >> .hg/hgrc <<EOF
343 $ cat >> .hg/hgrc <<EOF
344 > breakbase64=$TESTTMP/break-base64.py
344 > breakbase64=$TESTTMP/break-base64.py
345 > EOF
345 > EOF
346
346
347 $ hg verify
347 $ hg verify
348 checking changesets
348 checking changesets
349 checking manifests
349 checking manifests
350 crosschecking files in changesets and manifests
350 crosschecking files in changesets and manifests
351 checking files
351 checking files
352 base64@0: unpacking 794cee7777cb: integrity check failed on data/base64.i:0
352 base64@0: unpacking 794cee7777cb: integrity check failed on data/base64.i:0
353 1 files, 1 changesets, 1 total revisions
353 1 files, 1 changesets, 1 total revisions
354 1 integrity errors encountered!
354 1 integrity errors encountered!
355 (first damaged changeset appears to be 0)
355 (first damaged changeset appears to be 0)
356 [1]
356 [1]
357 $ hg verify --config verify.skipflags=2147483647
357 $ hg verify --config verify.skipflags=2147483647
358 checking changesets
358 checking changesets
359 checking manifests
359 checking manifests
360 crosschecking files in changesets and manifests
360 crosschecking files in changesets and manifests
361 checking files
361 checking files
362 1 files, 1 changesets, 1 total revisions
362 1 files, 1 changesets, 1 total revisions
363
363
General Comments 0
You need to be logged in to leave comments. Login now