#!/usr/bin/env python
-import sys
+import sys, struct
from bup import options, git, _helpers
from bup.helpers import *
optspec = """
bup margin
+--
+predict Guess object offsets and report the maximum deviation
+ignore-midx Don't use midx files; use only plain pack idx files.
"""
o = options.Options('bup margin', optspec)
(opt, flags, extra) = o.parse(sys.argv[1:])
o.fatal("no arguments expected")
git.check_repo_or_die()
-#git.ignore_midx = 1
+git.ignore_midx = opt.ignore_midx
mi = git.PackIdxList(git.repo('objects/pack'))
-last = '\0'*20
-longmatch = 0
-for i in mi:
- if i == last:
- continue
- #assert(str(i) >= last)
- pm = _helpers.bitmatch(last, i)
- longmatch = max(longmatch, pm)
- last = i
-print longmatch
+
+def do_predict(ix):
+ total = len(ix)
+ maxdiff = 0
+ for count,i in enumerate(ix):
+ prefix = struct.unpack('!Q', i[:8])[0]
+ expected = prefix * total / (1<<64)
+ diff = count - expected
+ maxdiff = max(maxdiff, abs(diff))
+ print '%d of %d (%.3f%%) ' % (maxdiff, len(ix), maxdiff*100.0/len(ix))
+ sys.stdout.flush()
+ assert(count+1 == len(ix))
+
+if opt.predict:
+ if opt.ignore_midx:
+ for pack in mi.packs:
+ do_predict(pack)
+ else:
+ do_predict(mi)
+else:
+ # default mode: find longest matching prefix
+ last = '\0'*20
+ longmatch = 0
+ for i in mi:
+ if i == last:
+ continue
+ #assert(str(i) >= last)
+ pm = _helpers.bitmatch(last, i)
+ longmatch = max(longmatch, pm)
+ last = i
+ print longmatch
def __iter__(self):
return iter(idxmerge(self.packs))
+ def __len__(self):
+ return sum(len(pack) for pack in self.packs)
+
def exists(self, hash):
"""Return nonempty if the object exists in the index files."""
if hash in self.also:
self.close()
def _make_objcache(self):
- if not self.objcache:
+ if self.objcache == None:
if self.objcache_maker:
self.objcache = self.objcache_maker()
else: