D7888: nodemap: track the maximum revision tracked in the nodemap

marmoute (Pierre-Yves David) phabricator at mercurial-scm.org
Fri Jan 31 18:02:10 EST 2020


marmoute updated this revision to Diff 19796.

REPOSITORY
  rHG Mercurial

CHANGES SINCE LAST UPDATE
  https://phab.mercurial-scm.org/D7888?vs=19769&id=19796

CHANGES SINCE LAST ACTION
  https://phab.mercurial-scm.org/D7888/new/

REVISION DETAIL
  https://phab.mercurial-scm.org/D7888

AFFECTED FILES
  mercurial/debugcommands.py
  mercurial/pure/parsers.py
  mercurial/revlog.py
  mercurial/revlogutils/nodemap.py
  tests/test-persistent-nodemap.t

CHANGE DETAILS

diff --git a/tests/test-persistent-nodemap.t b/tests/test-persistent-nodemap.t
--- a/tests/test-persistent-nodemap.t
+++ b/tests/test-persistent-nodemap.t
@@ -14,8 +14,9 @@
   $ hg debugbuilddag .+5000
   $ hg debugnodemap --metadata
   uid: ???????????????? (glob)
+  tip-rev: 5000
   $ f --size .hg/store/00changelog.n
-  .hg/store/00changelog.n: size=18
+  .hg/store/00changelog.n: size=26
   $ f --sha256 .hg/store/00changelog-*.nd
   .hg/store/00changelog-????????????????.nd: sha256=bc400bf49f11e83bbd25630439feee6628a80a8602d2e38972eac44cc3efe10c (glob)
   $ hg debugnodemap --dump-new | f --sha256 --size
@@ -51,8 +52,9 @@
   $ hg ci -m 'foo'
   $ hg debugnodemap --metadata
   uid: ???????????????? (glob)
+  tip-rev: 5001
   $ f --size .hg/store/00changelog.n
-  .hg/store/00changelog.n: size=18
+  .hg/store/00changelog.n: size=26
 
 (The pure code use the debug code that perform incremental update, the C code reencode from scratch)
 
diff --git a/mercurial/revlogutils/nodemap.py b/mercurial/revlogutils/nodemap.py
--- a/mercurial/revlogutils/nodemap.py
+++ b/mercurial/revlogutils/nodemap.py
@@ -36,9 +36,11 @@
     if version != ONDISK_VERSION:
         return None
     offset += S_VERSION.size
-    (uid_size,) = S_HEADER.unpack(pdata[offset : offset + S_HEADER.size])
+    headers = S_HEADER.unpack(pdata[offset : offset + S_HEADER.size])
+    uid_size, tip_rev = headers
     offset += S_HEADER.size
     docket = NodeMapDocket(pdata[offset : offset + uid_size])
+    docket.tip_rev = tip_rev
 
     filename = _rawdata_filepath(revlog, docket)
     return docket, revlog.opener.tryread(filename)
@@ -94,6 +96,7 @@
         # store vfs
         with revlog.opener(datafile, b'w') as fd:
             fd.write(data)
+    target_docket.tip_rev = revlog.tiprev()
     # EXP-TODO: if this is a cache, this should use a cache vfs, not a
     # store vfs
     with revlog.opener(revlog.nodemap_file, b'w', atomictemp=True) as fp:
@@ -142,7 +145,7 @@
 ONDISK_VERSION = 0
 
 S_VERSION = struct.Struct(">B")
-S_HEADER = struct.Struct(">B")
+S_HEADER = struct.Struct(">BQ")
 
 ID_SIZE = 8
 
@@ -164,15 +167,19 @@
         if uid is None:
             uid = _make_uid()
         self.uid = uid
+        self.tip_rev = None
 
     def copy(self):
-        return NodeMapDocket(uid=self.uid)
+        new = NodeMapDocket(uid=self.uid)
+        new.tip_rev = self.tip_rev
+        return new
 
     def serialize(self):
         """return serialized bytes for a docket using the passed uid"""
         data = []
         data.append(S_VERSION.pack(ONDISK_VERSION))
-        data.append(S_HEADER.pack(len(self.uid)))
+        headers = (len(self.uid), self.tip_rev)
+        data.append(S_HEADER.pack(*headers))
         data.append(self.uid)
         return b''.join(data)
 
diff --git a/mercurial/revlog.py b/mercurial/revlog.py
--- a/mercurial/revlog.py
+++ b/mercurial/revlog.py
@@ -639,7 +639,7 @@
             if use_nodemap:
                 nodemap_data = nodemaputil.persisted_data(self)
                 if nodemap_data is not None:
-                    index.update_nodemap_data(nodemap_data[1])
+                    index.update_nodemap_data(*nodemap_data)
         except (ValueError, IndexError):
             raise error.RevlogError(
                 _(b"index %s is corrupted") % self.indexfile
diff --git a/mercurial/pure/parsers.py b/mercurial/pure/parsers.py
--- a/mercurial/pure/parsers.py
+++ b/mercurial/pure/parsers.py
@@ -170,15 +170,15 @@
         self._nm_root = self._nm_max_idx = self._nm_rev = None
         return data
 
-    def update_nodemap_data(self, nm_data):
-        """provide full blokc of persisted binary data for a nodemap
+    def update_nodemap_data(self, docket, nm_data):
+        """provide full block of persisted binary data for a nodemap
 
         The data are expected to come from disk. See `nodemap_data_all` for a
         produceur of such data."""
         if nm_data is not None:
             self._nm_root, self._nm_max_idx = nodemaputil.parse_data(nm_data)
             if self._nm_root:
-                self._nm_rev = len(self) - 1
+                self._nm_rev = docket.tip_rev
             else:
                 self._nm_root = self._nm_max_idx = self._nm_rev = None
 
diff --git a/mercurial/debugcommands.py b/mercurial/debugcommands.py
--- a/mercurial/debugcommands.py
+++ b/mercurial/debugcommands.py
@@ -2136,6 +2136,7 @@
         if nm_data is not None:
             docket, data = nm_data
             ui.write((b"uid: %s\n") % docket.uid)
+            ui.write((b"tip-rev: %d\n") % docket.tip_rev)
 
 
 @command(



To: marmoute, indygreg, #hg-reviewers
Cc: mercurial-devel


More information about the Mercurial-devel mailing list