mercurial/revlog.py
changeset 43525 845e5b313783
parent 43524 a7c0c5b5a50f
child 43526 e258ad110488
equal deleted inserted replaced
43524:a7c0c5b5a50f 43525:845e5b313783
   203 indexformatv0_pack = indexformatv0.pack
   203 indexformatv0_pack = indexformatv0.pack
   204 indexformatv0_unpack = indexformatv0.unpack
   204 indexformatv0_unpack = indexformatv0.unpack
   205 
   205 
   206 
   206 
   207 class revlogoldindex(list):
   207 class revlogoldindex(list):
       
   208     @util.propertycache
       
   209     def nodemap(self):
       
   210         nodemap = revlogutils.NodeMap({nullid: nullrev})
       
   211         for r in range(0, len(self)):
       
   212             n = self[r][7]
       
   213             nodemap[n] = r
       
   214         return nodemap
       
   215 
       
   216     def clearcaches(self):
       
   217         self.__dict__.pop('nodemap', None)
       
   218 
   208     def __getitem__(self, i):
   219     def __getitem__(self, i):
   209         if i == -1:
   220         if i == -1:
   210             return (0, 0, 0, -1, -1, -1, -1, nullid)
   221             return (0, 0, 0, -1, -1, -1, -1, nullid)
   211         return list.__getitem__(self, i)
   222         return list.__getitem__(self, i)
   212 
   223 
   238             )
   249             )
   239             index.append(e2)
   250             index.append(e2)
   240             nodemap[e[6]] = n
   251             nodemap[e[6]] = n
   241             n += 1
   252             n += 1
   242 
   253 
   243         return revlogoldindex(index), nodemap, None
   254         index = revlogoldindex(index)
       
   255         return index, index.nodemap, None
   244 
   256 
   245     def packentry(self, entry, node, version, rev):
   257     def packentry(self, entry, node, version, rev):
   246         if gettype(entry[0]):
   258         if gettype(entry[0]):
   247             raise error.RevlogError(
   259             raise error.RevlogError(
   248                 _(b'index entry flags need revlog version 1')
   260                 _(b'index entry flags need revlog version 1')
   285         self.size = indexformatng.size
   297         self.size = indexformatng.size
   286 
   298 
   287     def parseindex(self, data, inline):
   299     def parseindex(self, data, inline):
   288         # call the C implementation to parse the index data
   300         # call the C implementation to parse the index data
   289         index, cache = parsers.parse_index2(data, inline)
   301         index, cache = parsers.parse_index2(data, inline)
   290         return index, getattr(index, 'nodemap', None), cache
   302         return index, index.nodemap, cache
   291 
   303 
   292     def packentry(self, entry, node, version, rev):
   304     def packentry(self, entry, node, version, rev):
   293         p = indexformatng_pack(*entry)
   305         p = indexformatng_pack(*entry)
   294         if rev == 0:
   306         if rev == 0:
   295             p = versionformat_pack(version) + p[4:]
   307             p = versionformat_pack(version) + p[4:]
   370         self._chunkcache = (0, b'')
   382         self._chunkcache = (0, b'')
   371         # How much data to read and cache into the raw revlog data cache.
   383         # How much data to read and cache into the raw revlog data cache.
   372         self._chunkcachesize = 65536
   384         self._chunkcachesize = 65536
   373         self._maxchainlen = None
   385         self._maxchainlen = None
   374         self._deltabothparents = True
   386         self._deltabothparents = True
   375         self.index = []
   387         self.index = None
   376         # Mapping of partial identifiers to full nodes.
   388         # Mapping of partial identifiers to full nodes.
   377         self._pcache = {}
   389         self._pcache = {}
   378         # Mapping of revision integer to full node.
   390         # Mapping of revision integer to full node.
   379         self._nodecache = revlogutils.NodeMap({nullid: nullrev})
   391         self._nodecache = None
   380         self._nodepos = None
   392         self._nodepos = None
   381         self._compengine = b'zlib'
   393         self._compengine = b'zlib'
   382         self._compengineopts = {}
   394         self._compengineopts = {}
   383         self._maxdeltachainspan = -1
   395         self._maxdeltachainspan = -1
   384         self._withsparseread = False
   396         self._withsparseread = False
   539         except (ValueError, IndexError):
   551         except (ValueError, IndexError):
   540             raise error.RevlogError(
   552             raise error.RevlogError(
   541                 _(b"index %s is corrupted") % self.indexfile
   553                 _(b"index %s is corrupted") % self.indexfile
   542             )
   554             )
   543         self.index, nodemap, self._chunkcache = d
   555         self.index, nodemap, self._chunkcache = d
   544         if nodemap is not None:
   556         self.nodemap = self._nodecache = nodemap
   545             self.nodemap = self._nodecache = nodemap
       
   546         if not self._chunkcache:
   557         if not self._chunkcache:
   547             self._chunkclear()
   558             self._chunkclear()
   548         # revnum -> (chain-length, sum-delta-length)
   559         # revnum -> (chain-length, sum-delta-length)
   549         self._chaininfocache = {}
   560         self._chaininfocache = {}
   550         # revlog header -> revlog compressor
   561         # revlog header -> revlog compressor
   644     def clearcaches(self):
   655     def clearcaches(self):
   645         self._revisioncache = None
   656         self._revisioncache = None
   646         self._chainbasecache.clear()
   657         self._chainbasecache.clear()
   647         self._chunkcache = (0, b'')
   658         self._chunkcache = (0, b'')
   648         self._pcache = {}
   659         self._pcache = {}
   649 
   660         self.index.clearcaches()
   650         try:
       
   651             # If we are using the native C version, you are in a fun case
       
   652             # where self.index, self.nodemap and self._nodecaches is the same
       
   653             # object.
       
   654             self._nodecache.clearcaches()
       
   655         except AttributeError:
       
   656             self._nodecache = revlogutils.NodeMap({nullid: nullrev})
       
   657             self._nodepos = None
       
   658 
   661 
   659     def rev(self, node):
   662     def rev(self, node):
   660         try:
   663         try:
   661             return self._nodecache[node]
   664             return self._nodecache[node]
   662         except TypeError:
   665         except TypeError:
   663             raise
   666             raise
   664         except error.RevlogError:
   667         except error.RevlogError:
   665             if not isinstance(self._nodecache, revlogutils.NodeMap):
   668             # parsers.c radix tree lookup failed
   666                 # parsers.c radix tree lookup failed
   669             if node == wdirid or node in wdirfilenodeids:
   667                 if node == wdirid or node in wdirfilenodeids:
   670                 raise error.WdirUnsupported
   668                     raise error.WdirUnsupported
   671             raise error.LookupError(node, self.indexfile, _(b'no node'))
   669                 raise error.LookupError(node, self.indexfile, _(b'no node'))
       
   670             else:
       
   671                 # pure python cache lookup failed
       
   672                 n = self._nodecache
       
   673                 i = self.index
       
   674                 p = self._nodepos
       
   675                 if p is None:
       
   676                     p = len(i) - 1
       
   677                 else:
       
   678                     assert p < len(i)
       
   679                 for r in pycompat.xrange(p, -1, -1):
       
   680                     v = i[r][7]
       
   681                     n[v] = r
       
   682                     if v == node:
       
   683                         self._nodepos = r - 1
       
   684                         return r
       
   685                 if node == wdirid or node in wdirfilenodeids:
       
   686                     raise error.WdirUnsupported
       
   687                 raise error.LookupError(node, self.indexfile, _(b'no node'))
       
   688 
   672 
   689     # Accessors for index entries.
   673     # Accessors for index entries.
   690 
   674 
   691     # First tuple entry is 8 bytes. First 6 bytes are offset. Last 2 bytes
   675     # First tuple entry is 8 bytes. First 6 bytes are offset. Last 2 bytes
   692     # are flags.
   676     # are flags.