Show More
@@ -290,6 +290,16 b' class revlog:' | |||
|
290 | 290 | |
|
291 | 291 | _flagserrorclass = error.RevlogError |
|
292 | 292 | |
|
293 | @staticmethod | |
|
294 | def is_inline_index(header_bytes): | |
|
295 | header = INDEX_HEADER.unpack(header_bytes)[0] | |
|
296 | ||
|
297 | _format_flags = header & ~0xFFFF | |
|
298 | _format_version = header & 0xFFFF | |
|
299 | ||
|
300 | features = FEATURES_BY_VERSION[_format_version] | |
|
301 | return features[b'inline'](_format_flags) | |
|
302 | ||
|
293 | 303 | def __init__( |
|
294 | 304 | self, |
|
295 | 305 | opener, |
@@ -16,6 +16,9 b' from .i18n import _' | |||
|
16 | 16 | from .pycompat import getattr |
|
17 | 17 | from .thirdparty import attr |
|
18 | 18 | from .node import hex |
|
19 | from .revlogutils.constants import ( | |
|
20 | INDEX_HEADER, | |
|
21 | ) | |
|
19 | 22 | from . import ( |
|
20 | 23 | changelog, |
|
21 | 24 | error, |
@@ -23,6 +26,7 b' from . import (' | |||
|
23 | 26 | manifest, |
|
24 | 27 | policy, |
|
25 | 28 | pycompat, |
|
29 | revlog as revlogmod, | |
|
26 | 30 | util, |
|
27 | 31 | vfs as vfsmod, |
|
28 | 32 | ) |
@@ -619,44 +623,70 b' class RevlogStoreEntry(BaseStoreEntry):' | |||
|
619 | 623 | copies=None, |
|
620 | 624 | max_changeset=None, |
|
621 | 625 | ): |
|
622 | if repo is None or max_changeset is None: | |
|
623 | return super().get_streams( | |
|
624 | repo=repo, | |
|
625 | vfs=vfs, | |
|
626 | copies=copies, | |
|
627 | max_changeset=max_changeset, | |
|
628 | ) | |
|
629 | if any(k.endswith(b'.idx') for k in self._details.keys()): | |
|
626 | if ( | |
|
627 | repo is None | |
|
628 | or max_changeset is None | |
|
630 | 629 | # This use revlog-v2, ignore for now |
|
630 | or any(k.endswith(b'.idx') for k in self._details.keys()) | |
|
631 | # This is not inline, no race expected | |
|
632 | or b'.d' in self._details | |
|
633 | ): | |
|
631 | 634 | return super().get_streams( |
|
632 | 635 | repo=repo, |
|
633 | 636 | vfs=vfs, |
|
634 | 637 | copies=copies, |
|
635 | 638 | max_changeset=max_changeset, |
|
636 | 639 | ) |
|
637 | name_to_ext = {} | |
|
638 | for ext in self._details.keys(): | |
|
639 | name_to_ext[self._path_prefix + ext] = ext | |
|
640 | ||
|
640 | 641 | name_to_size = {} |
|
641 | 642 | for f in self.files(): |
|
642 | 643 | name_to_size[f.unencoded_path] = f.file_size(None) |
|
644 | ||
|
643 | 645 | stream = [ |
|
644 | 646 | f.get_stream(vfs, copies) |
|
645 | 647 | for f in self.files() |
|
646 |
if n |
|
|
648 | if not f.unencoded_path.endswith(b'.i') | |
|
647 | 649 | ] |
|
648 | 650 | |
|
649 | is_inline = b'.d' not in self._details | |
|
651 | index_path = self._path_prefix + b'.i' | |
|
650 | 652 | |
|
651 | rl = self.get_revlog_instance(repo).get_revlog() | |
|
652 | rl_stream = rl.get_streams(max_changeset, force_inline=is_inline) | |
|
653 | index_file = None | |
|
654 | try: | |
|
655 | index_file = vfs(index_path) | |
|
656 | header = index_file.read(INDEX_HEADER.size) | |
|
657 | if revlogmod.revlog.is_inline_index(header): | |
|
658 | size = name_to_size[index_path] | |
|
653 | 659 | |
|
654 | for name, s, size in rl_stream: | |
|
655 | if name_to_size.get(name, 0) != size: | |
|
656 | msg = _(b"expected %d bytes but %d provided for %s") | |
|
657 | msg %= name_to_size.get(name, 0), size, name | |
|
658 | raise error.Abort(msg) | |
|
659 | stream.extend(rl_stream) | |
|
660 | # no split underneath, just return the stream | |
|
661 | def get_stream(): | |
|
662 | fp = index_file | |
|
663 | try: | |
|
664 | fp.seek(0) | |
|
665 | yield None | |
|
666 | if size <= 65536: | |
|
667 | yield fp.read(size) | |
|
668 | else: | |
|
669 | yield from util.filechunkiter(fp, limit=size) | |
|
670 | finally: | |
|
671 | fp.close() | |
|
672 | ||
|
673 | s = get_stream() | |
|
674 | next(s) | |
|
675 | index_file = None | |
|
676 | stream.append((index_path, s, size)) | |
|
677 | else: | |
|
678 | rl = self.get_revlog_instance(repo).get_revlog() | |
|
679 | rl_stream = rl.get_streams(max_changeset, force_inline=True) | |
|
680 | for name, s, size in rl_stream: | |
|
681 | if name_to_size.get(name, 0) != size: | |
|
682 | msg = _(b"expected %d bytes but %d provided for %s") | |
|
683 | msg %= name_to_size.get(name, 0), size, name | |
|
684 | raise error.Abort(msg) | |
|
685 | stream.extend(rl_stream) | |
|
686 | finally: | |
|
687 | if index_file is not None: | |
|
688 | index_file.close() | |
|
689 | ||
|
660 | 690 | files = self.files() |
|
661 | 691 | assert len(stream) == len(files), ( |
|
662 | 692 | stream, |
General Comments 0
You need to be logged in to leave comments.
Login now