tests/test-parseindex.t
author Gregory Szorc <gregory.szorc@gmail.com>
Sat, 18 Jul 2015 10:57:20 -0700
changeset 25823 2406e2baa937
parent 25810 82d6a35cf432
child 25859 1619563959b3
permissions -rw-r--r--
changegroup: compute seen files as changesets are added (issue4750) Before this patch, addchangegroup() would walk the changelog and compute the set of seen files between applying changesets and applying manifests. When cloning large repositories such as mozilla-central, this consumed a non-trivial amount of time. On my MBP, this walk takes ~10s. On a dainty EC2 instance, this was measured to take ~125s! On the latter machine, this delay was enough for the Mercurial server to disconnect the client, thinking it had timed out, thus causing a clone to abort. This patch enables the changelog to compute the set of changed files as new revisions are added. By doing so, we: * avoid a potentially heavy computation between changelog and manifest processing by spreading the computation across all changelog additions * avoid extra reads from the changelog by operating on the data as it is added The downside of this is that the add revision callback does result in extra I/O. Before, we would perform a flush (and subsequent read to construct the full revision) when new delta chains were created. For changelogs, this is typically every 2-4 revisions. Using the callback guarantees there will be a flush after every added revision *and* an open + read of the changelog to obtain the full revision in order to read the added files. So, this increases the frequency of these operations by the average chain length. In the future, the revlog should be smart enough to know how to read revisions that haven't been flushed yet, thus eliminating this extra I/O. On my MBP, the total CPU times for an `hg unbundle` with a local mozilla-central gzip bundle containing 251,934 changesets and 211,065 files did not have a statistically significant change with this patch, holding steady around 360s. So, the increased revlog flushing did not have an effect. With this patch, there is no longer a visible pause between applying changeset and manifest data. Before, it sure felt like Mercurial was lethargic making this transition. Now, the transition is nearly instantaneous, giving the impression that Mercurial is faster. Of course, eliminating this pause means that the potential for network disconnect due to channel inactivity during the changelog walk is eliminated as well. And that is the impetus behind this change.
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
12476
4cce5194c307 tests: unify test-parseindex
Matt Mackall <mpm@selenic.com>
parents: 12156
diff changeset
     1
revlog.parseindex must be able to parse the index file even if
4cce5194c307 tests: unify test-parseindex
Matt Mackall <mpm@selenic.com>
parents: 12156
diff changeset
     2
an index entry is split between two 64k blocks.  The ideal test
4cce5194c307 tests: unify test-parseindex
Matt Mackall <mpm@selenic.com>
parents: 12156
diff changeset
     3
would be to create an index file with inline data where
4cce5194c307 tests: unify test-parseindex
Matt Mackall <mpm@selenic.com>
parents: 12156
diff changeset
     4
64k < size < 64k + 64 (64k is the size of the read buffer, 64 is
4cce5194c307 tests: unify test-parseindex
Matt Mackall <mpm@selenic.com>
parents: 12156
diff changeset
     5
the size of an index entry) and with an index entry starting right
4cce5194c307 tests: unify test-parseindex
Matt Mackall <mpm@selenic.com>
parents: 12156
diff changeset
     6
before the 64k block boundary, and try to read it.
4cce5194c307 tests: unify test-parseindex
Matt Mackall <mpm@selenic.com>
parents: 12156
diff changeset
     7
We approximate that by reducing the read buffer to 1 byte.
2290
6563438219e3 add test for revlog.parseindex
Alexis S. L. Carvalho <alexis@cecm.usp.br>
parents:
diff changeset
     8
12476
4cce5194c307 tests: unify test-parseindex
Matt Mackall <mpm@selenic.com>
parents: 12156
diff changeset
     9
  $ hg init a
4cce5194c307 tests: unify test-parseindex
Matt Mackall <mpm@selenic.com>
parents: 12156
diff changeset
    10
  $ cd a
4cce5194c307 tests: unify test-parseindex
Matt Mackall <mpm@selenic.com>
parents: 12156
diff changeset
    11
  $ echo abc > foo
4cce5194c307 tests: unify test-parseindex
Matt Mackall <mpm@selenic.com>
parents: 12156
diff changeset
    12
  $ hg add foo
4cce5194c307 tests: unify test-parseindex
Matt Mackall <mpm@selenic.com>
parents: 12156
diff changeset
    13
  $ hg commit -m 'add foo'
4cce5194c307 tests: unify test-parseindex
Matt Mackall <mpm@selenic.com>
parents: 12156
diff changeset
    14
  $ echo >> foo
4cce5194c307 tests: unify test-parseindex
Matt Mackall <mpm@selenic.com>
parents: 12156
diff changeset
    15
  $ hg commit -m 'change foo'
4cce5194c307 tests: unify test-parseindex
Matt Mackall <mpm@selenic.com>
parents: 12156
diff changeset
    16
  $ hg log -r 0:
4cce5194c307 tests: unify test-parseindex
Matt Mackall <mpm@selenic.com>
parents: 12156
diff changeset
    17
  changeset:   0:7c31755bf9b5
4cce5194c307 tests: unify test-parseindex
Matt Mackall <mpm@selenic.com>
parents: 12156
diff changeset
    18
  user:        test
4cce5194c307 tests: unify test-parseindex
Matt Mackall <mpm@selenic.com>
parents: 12156
diff changeset
    19
  date:        Thu Jan 01 00:00:00 1970 +0000
4cce5194c307 tests: unify test-parseindex
Matt Mackall <mpm@selenic.com>
parents: 12156
diff changeset
    20
  summary:     add foo
4cce5194c307 tests: unify test-parseindex
Matt Mackall <mpm@selenic.com>
parents: 12156
diff changeset
    21
  
4cce5194c307 tests: unify test-parseindex
Matt Mackall <mpm@selenic.com>
parents: 12156
diff changeset
    22
  changeset:   1:26333235a41c
4cce5194c307 tests: unify test-parseindex
Matt Mackall <mpm@selenic.com>
parents: 12156
diff changeset
    23
  tag:         tip
4cce5194c307 tests: unify test-parseindex
Matt Mackall <mpm@selenic.com>
parents: 12156
diff changeset
    24
  user:        test
4cce5194c307 tests: unify test-parseindex
Matt Mackall <mpm@selenic.com>
parents: 12156
diff changeset
    25
  date:        Thu Jan 01 00:00:00 1970 +0000
4cce5194c307 tests: unify test-parseindex
Matt Mackall <mpm@selenic.com>
parents: 12156
diff changeset
    26
  summary:     change foo
4cce5194c307 tests: unify test-parseindex
Matt Mackall <mpm@selenic.com>
parents: 12156
diff changeset
    27
  
4cce5194c307 tests: unify test-parseindex
Matt Mackall <mpm@selenic.com>
parents: 12156
diff changeset
    28
  $ cat >> test.py << EOF
13970
d13913355390 move opener from util to scmutil
Adrian Buehlmann <adrian@cadifra.com>
parents: 12476
diff changeset
    29
  > from mercurial import changelog, scmutil
12476
4cce5194c307 tests: unify test-parseindex
Matt Mackall <mpm@selenic.com>
parents: 12156
diff changeset
    30
  > from mercurial.node import *
4cce5194c307 tests: unify test-parseindex
Matt Mackall <mpm@selenic.com>
parents: 12156
diff changeset
    31
  > 
4cce5194c307 tests: unify test-parseindex
Matt Mackall <mpm@selenic.com>
parents: 12156
diff changeset
    32
  > class singlebyteread(object):
4cce5194c307 tests: unify test-parseindex
Matt Mackall <mpm@selenic.com>
parents: 12156
diff changeset
    33
  >     def __init__(self, real):
4cce5194c307 tests: unify test-parseindex
Matt Mackall <mpm@selenic.com>
parents: 12156
diff changeset
    34
  >         self.real = real
4cce5194c307 tests: unify test-parseindex
Matt Mackall <mpm@selenic.com>
parents: 12156
diff changeset
    35
  > 
4cce5194c307 tests: unify test-parseindex
Matt Mackall <mpm@selenic.com>
parents: 12156
diff changeset
    36
  >     def read(self, size=-1):
4cce5194c307 tests: unify test-parseindex
Matt Mackall <mpm@selenic.com>
parents: 12156
diff changeset
    37
  >         if size == 65536:
4cce5194c307 tests: unify test-parseindex
Matt Mackall <mpm@selenic.com>
parents: 12156
diff changeset
    38
  >             size = 1
4cce5194c307 tests: unify test-parseindex
Matt Mackall <mpm@selenic.com>
parents: 12156
diff changeset
    39
  >         return self.real.read(size)
4cce5194c307 tests: unify test-parseindex
Matt Mackall <mpm@selenic.com>
parents: 12156
diff changeset
    40
  > 
4cce5194c307 tests: unify test-parseindex
Matt Mackall <mpm@selenic.com>
parents: 12156
diff changeset
    41
  >     def __getattr__(self, key):
4cce5194c307 tests: unify test-parseindex
Matt Mackall <mpm@selenic.com>
parents: 12156
diff changeset
    42
  >         return getattr(self.real, key)
4cce5194c307 tests: unify test-parseindex
Matt Mackall <mpm@selenic.com>
parents: 12156
diff changeset
    43
  > 
4cce5194c307 tests: unify test-parseindex
Matt Mackall <mpm@selenic.com>
parents: 12156
diff changeset
    44
  > def opener(*args):
13970
d13913355390 move opener from util to scmutil
Adrian Buehlmann <adrian@cadifra.com>
parents: 12476
diff changeset
    45
  >     o = scmutil.opener(*args)
12476
4cce5194c307 tests: unify test-parseindex
Matt Mackall <mpm@selenic.com>
parents: 12156
diff changeset
    46
  >     def wrapper(*a):
4cce5194c307 tests: unify test-parseindex
Matt Mackall <mpm@selenic.com>
parents: 12156
diff changeset
    47
  >         f = o(*a)
4cce5194c307 tests: unify test-parseindex
Matt Mackall <mpm@selenic.com>
parents: 12156
diff changeset
    48
  >         return singlebyteread(f)
4cce5194c307 tests: unify test-parseindex
Matt Mackall <mpm@selenic.com>
parents: 12156
diff changeset
    49
  >     return wrapper
4cce5194c307 tests: unify test-parseindex
Matt Mackall <mpm@selenic.com>
parents: 12156
diff changeset
    50
  > 
4cce5194c307 tests: unify test-parseindex
Matt Mackall <mpm@selenic.com>
parents: 12156
diff changeset
    51
  > cl = changelog.changelog(opener('.hg/store'))
4cce5194c307 tests: unify test-parseindex
Matt Mackall <mpm@selenic.com>
parents: 12156
diff changeset
    52
  > print len(cl), 'revisions:'
4cce5194c307 tests: unify test-parseindex
Matt Mackall <mpm@selenic.com>
parents: 12156
diff changeset
    53
  > for r in cl:
4cce5194c307 tests: unify test-parseindex
Matt Mackall <mpm@selenic.com>
parents: 12156
diff changeset
    54
  >     print short(cl.node(r))
4cce5194c307 tests: unify test-parseindex
Matt Mackall <mpm@selenic.com>
parents: 12156
diff changeset
    55
  > EOF
4cce5194c307 tests: unify test-parseindex
Matt Mackall <mpm@selenic.com>
parents: 12156
diff changeset
    56
  $ python test.py
4cce5194c307 tests: unify test-parseindex
Matt Mackall <mpm@selenic.com>
parents: 12156
diff changeset
    57
  2 revisions:
4cce5194c307 tests: unify test-parseindex
Matt Mackall <mpm@selenic.com>
parents: 12156
diff changeset
    58
  7c31755bf9b5
4cce5194c307 tests: unify test-parseindex
Matt Mackall <mpm@selenic.com>
parents: 12156
diff changeset
    59
  26333235a41c
16913
f2719b387380 tests: add missing trailing 'cd ..'
Mads Kiilerich <mads@kiilerich.com>
parents: 13970
diff changeset
    60
f2719b387380 tests: add missing trailing 'cd ..'
Mads Kiilerich <mads@kiilerich.com>
parents: 13970
diff changeset
    61
  $ cd ..
25810
82d6a35cf432 parsers: fix buffer overflow by invalid parent revision read from revlog
Yuya Nishihara <yuya@tcha.org>
parents: 16913
diff changeset
    62
82d6a35cf432 parsers: fix buffer overflow by invalid parent revision read from revlog
Yuya Nishihara <yuya@tcha.org>
parents: 16913
diff changeset
    63
Test corrupted p1/p2 fields that could cause SEGV at parsers.c:
82d6a35cf432 parsers: fix buffer overflow by invalid parent revision read from revlog
Yuya Nishihara <yuya@tcha.org>
parents: 16913
diff changeset
    64
82d6a35cf432 parsers: fix buffer overflow by invalid parent revision read from revlog
Yuya Nishihara <yuya@tcha.org>
parents: 16913
diff changeset
    65
  $ mkdir invalidparent
82d6a35cf432 parsers: fix buffer overflow by invalid parent revision read from revlog
Yuya Nishihara <yuya@tcha.org>
parents: 16913
diff changeset
    66
  $ cd invalidparent
82d6a35cf432 parsers: fix buffer overflow by invalid parent revision read from revlog
Yuya Nishihara <yuya@tcha.org>
parents: 16913
diff changeset
    67
82d6a35cf432 parsers: fix buffer overflow by invalid parent revision read from revlog
Yuya Nishihara <yuya@tcha.org>
parents: 16913
diff changeset
    68
  $ hg clone --pull -q --config phases.publish=False ../a limit
82d6a35cf432 parsers: fix buffer overflow by invalid parent revision read from revlog
Yuya Nishihara <yuya@tcha.org>
parents: 16913
diff changeset
    69
  $ hg clone --pull -q --config phases.publish=False ../a segv
82d6a35cf432 parsers: fix buffer overflow by invalid parent revision read from revlog
Yuya Nishihara <yuya@tcha.org>
parents: 16913
diff changeset
    70
  $ rm -R limit/.hg/cache segv/.hg/cache
82d6a35cf432 parsers: fix buffer overflow by invalid parent revision read from revlog
Yuya Nishihara <yuya@tcha.org>
parents: 16913
diff changeset
    71
82d6a35cf432 parsers: fix buffer overflow by invalid parent revision read from revlog
Yuya Nishihara <yuya@tcha.org>
parents: 16913
diff changeset
    72
  $ python <<EOF
82d6a35cf432 parsers: fix buffer overflow by invalid parent revision read from revlog
Yuya Nishihara <yuya@tcha.org>
parents: 16913
diff changeset
    73
  > data = open("limit/.hg/store/00changelog.i", "rb").read()
82d6a35cf432 parsers: fix buffer overflow by invalid parent revision read from revlog
Yuya Nishihara <yuya@tcha.org>
parents: 16913
diff changeset
    74
  > for n, p in [('limit', '\0\0\0\x02'), ('segv', '\0\x01\0\0')]:
82d6a35cf432 parsers: fix buffer overflow by invalid parent revision read from revlog
Yuya Nishihara <yuya@tcha.org>
parents: 16913
diff changeset
    75
  >     # corrupt p1 at rev0 and p2 at rev1
82d6a35cf432 parsers: fix buffer overflow by invalid parent revision read from revlog
Yuya Nishihara <yuya@tcha.org>
parents: 16913
diff changeset
    76
  >     d = data[:24] + p + data[28:127 + 28] + p + data[127 + 32:]
82d6a35cf432 parsers: fix buffer overflow by invalid parent revision read from revlog
Yuya Nishihara <yuya@tcha.org>
parents: 16913
diff changeset
    77
  >     open(n + "/.hg/store/00changelog.i", "wb").write(d)
82d6a35cf432 parsers: fix buffer overflow by invalid parent revision read from revlog
Yuya Nishihara <yuya@tcha.org>
parents: 16913
diff changeset
    78
  > EOF
82d6a35cf432 parsers: fix buffer overflow by invalid parent revision read from revlog
Yuya Nishihara <yuya@tcha.org>
parents: 16913
diff changeset
    79
82d6a35cf432 parsers: fix buffer overflow by invalid parent revision read from revlog
Yuya Nishihara <yuya@tcha.org>
parents: 16913
diff changeset
    80
  $ hg debugindex -f1 limit/.hg/store/00changelog.i
82d6a35cf432 parsers: fix buffer overflow by invalid parent revision read from revlog
Yuya Nishihara <yuya@tcha.org>
parents: 16913
diff changeset
    81
     rev flag   offset   length     size   base   link     p1     p2       nodeid
82d6a35cf432 parsers: fix buffer overflow by invalid parent revision read from revlog
Yuya Nishihara <yuya@tcha.org>
parents: 16913
diff changeset
    82
       0 0000        0       63       62      0      0      2     -1 7c31755bf9b5
82d6a35cf432 parsers: fix buffer overflow by invalid parent revision read from revlog
Yuya Nishihara <yuya@tcha.org>
parents: 16913
diff changeset
    83
       1 0000       63       66       65      1      1      0      2 26333235a41c
82d6a35cf432 parsers: fix buffer overflow by invalid parent revision read from revlog
Yuya Nishihara <yuya@tcha.org>
parents: 16913
diff changeset
    84
  $ hg debugindex -f1 segv/.hg/store/00changelog.i
82d6a35cf432 parsers: fix buffer overflow by invalid parent revision read from revlog
Yuya Nishihara <yuya@tcha.org>
parents: 16913
diff changeset
    85
     rev flag   offset   length     size   base   link     p1     p2       nodeid
82d6a35cf432 parsers: fix buffer overflow by invalid parent revision read from revlog
Yuya Nishihara <yuya@tcha.org>
parents: 16913
diff changeset
    86
       0 0000        0       63       62      0      0  65536     -1 7c31755bf9b5
82d6a35cf432 parsers: fix buffer overflow by invalid parent revision read from revlog
Yuya Nishihara <yuya@tcha.org>
parents: 16913
diff changeset
    87
       1 0000       63       66       65      1      1      0  65536 26333235a41c
82d6a35cf432 parsers: fix buffer overflow by invalid parent revision read from revlog
Yuya Nishihara <yuya@tcha.org>
parents: 16913
diff changeset
    88
82d6a35cf432 parsers: fix buffer overflow by invalid parent revision read from revlog
Yuya Nishihara <yuya@tcha.org>
parents: 16913
diff changeset
    89
  $ cat <<EOF > test.py
82d6a35cf432 parsers: fix buffer overflow by invalid parent revision read from revlog
Yuya Nishihara <yuya@tcha.org>
parents: 16913
diff changeset
    90
  > import sys
82d6a35cf432 parsers: fix buffer overflow by invalid parent revision read from revlog
Yuya Nishihara <yuya@tcha.org>
parents: 16913
diff changeset
    91
  > from mercurial import changelog, scmutil
82d6a35cf432 parsers: fix buffer overflow by invalid parent revision read from revlog
Yuya Nishihara <yuya@tcha.org>
parents: 16913
diff changeset
    92
  > cl = changelog.changelog(scmutil.vfs(sys.argv[1]))
82d6a35cf432 parsers: fix buffer overflow by invalid parent revision read from revlog
Yuya Nishihara <yuya@tcha.org>
parents: 16913
diff changeset
    93
  > n0, n1 = cl.node(0), cl.node(1)
82d6a35cf432 parsers: fix buffer overflow by invalid parent revision read from revlog
Yuya Nishihara <yuya@tcha.org>
parents: 16913
diff changeset
    94
  > ops = [
82d6a35cf432 parsers: fix buffer overflow by invalid parent revision read from revlog
Yuya Nishihara <yuya@tcha.org>
parents: 16913
diff changeset
    95
  >     ('compute_phases_map_sets', lambda: cl.computephases([[0], []])),
82d6a35cf432 parsers: fix buffer overflow by invalid parent revision read from revlog
Yuya Nishihara <yuya@tcha.org>
parents: 16913
diff changeset
    96
  >     ('index_headrevs', lambda: cl.headrevs()),
82d6a35cf432 parsers: fix buffer overflow by invalid parent revision read from revlog
Yuya Nishihara <yuya@tcha.org>
parents: 16913
diff changeset
    97
  >     ('find_gca_candidates', lambda: cl.commonancestorsheads(n0, n1)),
82d6a35cf432 parsers: fix buffer overflow by invalid parent revision read from revlog
Yuya Nishihara <yuya@tcha.org>
parents: 16913
diff changeset
    98
  >     ('find_deepest', lambda: cl.ancestor(n0, n1)),
82d6a35cf432 parsers: fix buffer overflow by invalid parent revision read from revlog
Yuya Nishihara <yuya@tcha.org>
parents: 16913
diff changeset
    99
  >     ]
82d6a35cf432 parsers: fix buffer overflow by invalid parent revision read from revlog
Yuya Nishihara <yuya@tcha.org>
parents: 16913
diff changeset
   100
  > for l, f in ops:
82d6a35cf432 parsers: fix buffer overflow by invalid parent revision read from revlog
Yuya Nishihara <yuya@tcha.org>
parents: 16913
diff changeset
   101
  >     print l + ':',
82d6a35cf432 parsers: fix buffer overflow by invalid parent revision read from revlog
Yuya Nishihara <yuya@tcha.org>
parents: 16913
diff changeset
   102
  >     try:
82d6a35cf432 parsers: fix buffer overflow by invalid parent revision read from revlog
Yuya Nishihara <yuya@tcha.org>
parents: 16913
diff changeset
   103
  >         f()
82d6a35cf432 parsers: fix buffer overflow by invalid parent revision read from revlog
Yuya Nishihara <yuya@tcha.org>
parents: 16913
diff changeset
   104
  >         print 'uncaught buffer overflow?'
82d6a35cf432 parsers: fix buffer overflow by invalid parent revision read from revlog
Yuya Nishihara <yuya@tcha.org>
parents: 16913
diff changeset
   105
  >     except ValueError, inst:
82d6a35cf432 parsers: fix buffer overflow by invalid parent revision read from revlog
Yuya Nishihara <yuya@tcha.org>
parents: 16913
diff changeset
   106
  >         print inst
82d6a35cf432 parsers: fix buffer overflow by invalid parent revision read from revlog
Yuya Nishihara <yuya@tcha.org>
parents: 16913
diff changeset
   107
  > EOF
82d6a35cf432 parsers: fix buffer overflow by invalid parent revision read from revlog
Yuya Nishihara <yuya@tcha.org>
parents: 16913
diff changeset
   108
82d6a35cf432 parsers: fix buffer overflow by invalid parent revision read from revlog
Yuya Nishihara <yuya@tcha.org>
parents: 16913
diff changeset
   109
  $ python test.py limit/.hg/store
82d6a35cf432 parsers: fix buffer overflow by invalid parent revision read from revlog
Yuya Nishihara <yuya@tcha.org>
parents: 16913
diff changeset
   110
  compute_phases_map_sets: parent out of range
82d6a35cf432 parsers: fix buffer overflow by invalid parent revision read from revlog
Yuya Nishihara <yuya@tcha.org>
parents: 16913
diff changeset
   111
  index_headrevs: parent out of range
82d6a35cf432 parsers: fix buffer overflow by invalid parent revision read from revlog
Yuya Nishihara <yuya@tcha.org>
parents: 16913
diff changeset
   112
  find_gca_candidates: parent out of range
82d6a35cf432 parsers: fix buffer overflow by invalid parent revision read from revlog
Yuya Nishihara <yuya@tcha.org>
parents: 16913
diff changeset
   113
  find_deepest: parent out of range
82d6a35cf432 parsers: fix buffer overflow by invalid parent revision read from revlog
Yuya Nishihara <yuya@tcha.org>
parents: 16913
diff changeset
   114
  $ python test.py segv/.hg/store
82d6a35cf432 parsers: fix buffer overflow by invalid parent revision read from revlog
Yuya Nishihara <yuya@tcha.org>
parents: 16913
diff changeset
   115
  compute_phases_map_sets: parent out of range
82d6a35cf432 parsers: fix buffer overflow by invalid parent revision read from revlog
Yuya Nishihara <yuya@tcha.org>
parents: 16913
diff changeset
   116
  index_headrevs: parent out of range
82d6a35cf432 parsers: fix buffer overflow by invalid parent revision read from revlog
Yuya Nishihara <yuya@tcha.org>
parents: 16913
diff changeset
   117
  find_gca_candidates: parent out of range
82d6a35cf432 parsers: fix buffer overflow by invalid parent revision read from revlog
Yuya Nishihara <yuya@tcha.org>
parents: 16913
diff changeset
   118
  find_deepest: parent out of range
82d6a35cf432 parsers: fix buffer overflow by invalid parent revision read from revlog
Yuya Nishihara <yuya@tcha.org>
parents: 16913
diff changeset
   119
82d6a35cf432 parsers: fix buffer overflow by invalid parent revision read from revlog
Yuya Nishihara <yuya@tcha.org>
parents: 16913
diff changeset
   120
  $ cd ..