D11203: revlog: recommit 49fd21f32695 with a fix for issue6528
joerg.sonnenberger (Joerg Sonnenberger)
phabricator at mercurial-scm.org
Tue Jul 20 13:58:49 UTC 2021
joerg.sonnenberger created this revision.
Herald added a reviewer: durin42.
Herald added a reviewer: hg-reviewers.
Herald added a subscriber: mercurial-patches.
REVISION SUMMARY
`filelog.size` currently special cases two forms of metadata encoding:
- copy data via the parent order as flag bit
- censor data by peaking into the raw delta
All other forms of metadata encoding including the empty metadata block
are mishandled. In `basefilectx.cmp` the empty metadata block is
explicitly checked to compensate for this.
Restore 49fd21f32695 <https://phab.mercurial-scm.org/rHG49fd21f32695d885d730b56d91707c9059c6bd54>, but disable it for filelog, so that the original
flag bit use contines to work. Document all this mess for now in
preparation of a proper rework.
REPOSITORY
rHG Mercurial
BRANCH
stable
REVISION DETAIL
https://phab.mercurial-scm.org/D11203
AFFECTED FILES
mercurial/context.py
mercurial/filelog.py
mercurial/revlog.py
tests/test-narrow-shallow-merges.t
CHANGE DETAILS
diff --git a/tests/test-narrow-shallow-merges.t b/tests/test-narrow-shallow-merges.t
--- a/tests/test-narrow-shallow-merges.t
+++ b/tests/test-narrow-shallow-merges.t
@@ -179,7 +179,7 @@
$ hg log -T '{if(ellipsis,"...")}{node|short} {p1node|short} {p2node|short} {desc}\n' | sort
- ...2a20009de83e 000000000000 3ac1f5779de3 outside 10
+ ...2a20009de83e 3ac1f5779de3 000000000000 outside 10
...3ac1f5779de3 bb96a08b062a 465567bdfb2d merge a/b/c/d 9
...8d874d57adea 7ef88b4dd4fa 000000000000 outside 12
...b844052e7b3b 000000000000 000000000000 outside 2c
diff --git a/mercurial/revlog.py b/mercurial/revlog.py
--- a/mercurial/revlog.py
+++ b/mercurial/revlog.py
@@ -434,6 +434,7 @@
upperboundcomp=None,
persistentnodemap=False,
concurrencychecker=None,
+ canonical_parent_order=True,
):
"""
create a revlog object
@@ -491,6 +492,13 @@
self._concurrencychecker = concurrencychecker
+ # parent order is supposed to be semantically irrelevant, so we
+ # normally resort parents to ensure that the first parent is non-null,
+ # if there is a non-null parent at all.
+ # filelog obuses the parent order as flag to mark some instances of
+ # meta-encoded files, so allow it to disable this behavior.
+ self.canonical_parent_order = canonical_parent_order
+
def _loadindex(self):
mmapindexthreshold = None
opts = self.opener.options
@@ -885,7 +893,10 @@
raise error.WdirUnsupported
raise
- return entry[5], entry[6]
+ if self.canonical_parent_order and entry[5] == nullrev:
+ return entry[6], entry[5]
+ else:
+ return entry[5], entry[6]
# fast parentrevs(rev) where rev isn't filtered
_uncheckedparentrevs = parentrevs
@@ -907,6 +918,11 @@
i = self.index
d = i[self.rev(node)]
return i[d[5]][7], i[d[6]][7] # map revisions to nodes inline
+ # inline node() to avoid function call overhead
+ if self.canonical_parent_order and d[5] == nullid:
+ return i[d[6]][7], i[d[5]][7]
+ else:
+ return i[d[5]][7], i[d[6]][7]
def chainlen(self, rev):
return self._chaininfo(rev)[0]
diff --git a/mercurial/filelog.py b/mercurial/filelog.py
--- a/mercurial/filelog.py
+++ b/mercurial/filelog.py
@@ -27,7 +27,10 @@
class filelog(object):
def __init__(self, opener, path):
self._revlog = revlog.revlog(
- opener, b'/'.join((b'data', path + b'.i')), censorable=True
+ opener,
+ b'/'.join((b'data', path + b'.i')),
+ censorable=True,
+ canonical_parent_order=False, # see comment in revlog.py
)
# Full name of the user visible file, relative to the repository root.
# Used by LFS.
@@ -197,6 +200,7 @@
return 0
# XXX if self.read(node).startswith("\1\n"), this returns (size+4)
+ # XXX See also basefilectx.cmp.
return self._revlog.size(rev)
def cmp(self, node, text):
diff --git a/mercurial/context.py b/mercurial/context.py
--- a/mercurial/context.py
+++ b/mercurial/context.py
@@ -988,6 +988,16 @@
if self._repo._encodefilterpats:
# can't rely on size() because wdir content may be decoded
return self._filelog.cmp(self._filenode, fctx.data())
+ # filelog.size() has two special cases:
+ # - censored metadata
+ # - copy/rename tracking
+ # The first is detected by peaking into the delta,
+ # the second is detected by abusing parent order
+ # in the revlog index as flag bit. This leaves files using
+ # the dummy encoding and non-standard meta attributes.
+ # The following check is a special case for the empty
+ # metadata block used if the raw file content starts with '\1\n'.
+ # Cases of arbitrary metadata flags are currently mishandled.
if self.size() - 4 == fctx.size():
# size() can match:
# if file data starts with '\1\n', empty metadata block is
To: joerg.sonnenberger, durin42, #hg-reviewers
Cc: mercurial-patches, mercurial-devel
More information about the Mercurial-devel
mailing list