annotate mercurial/hbisect.py @ 45059:79f6f9fa18c1

documentation: add some internals documentation about bid merge This is an important algorithm that was only documented on the wiki so far. Some update to the algorithm (and associated doc) is to expected in the future since the bid merge algorithm is bug-ridden when it comes to file deletion comes to play. Differential Revision: https://phab.mercurial-scm.org/D8711
author Pierre-Yves David <pierre-yves.david@octobus.net>
date Mon, 22 Jun 2020 13:32:20 +0200
parents 9d2b2df2c2ba
children e641bb2a6159
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
5775
2dd202a6e15b bisect: make bisect a built-in command
Matt Mackall <mpm@selenic.com>
parents: 5774
diff changeset
1 # changelog bisection for mercurial
1367
a7678cbd7c28 bisect extension for mercurial
Benoit Boissinot <benoit.boissinot@ens-lyon.org>
parents:
diff changeset
2 #
5775
2dd202a6e15b bisect: make bisect a built-in command
Matt Mackall <mpm@selenic.com>
parents: 5774
diff changeset
3 # Copyright 2007 Matt Mackall
1861
65949d1c9bf7 Added copyright information to hbisect.py
Thomas Arendsen Hein <thomas@intevation.de>
parents: 1856
diff changeset
4 # Copyright 2005, 2006 Benoit Boissinot <benoit.boissinot@ens-lyon.org>
8228
eee2319c5895 add blank line after copyright notices and after header
Martin Geisler <mg@lazybytes.net>
parents: 8225
diff changeset
5 #
1861
65949d1c9bf7 Added copyright information to hbisect.py
Thomas Arendsen Hein <thomas@intevation.de>
parents: 1856
diff changeset
6 # Inspired by git bisect, extension skeleton taken from mq.py.
65949d1c9bf7 Added copyright information to hbisect.py
Thomas Arendsen Hein <thomas@intevation.de>
parents: 1856
diff changeset
7 #
8225
46293a0c7e9f updated license to be explicit about GPL version 2
Martin Geisler <mg@lazybytes.net>
parents: 8152
diff changeset
8 # This software may be used and distributed according to the terms of the
10263
25e572394f5c Update license to GPLv2+
Matt Mackall <mpm@selenic.com>
parents: 9583
diff changeset
9 # GNU General Public License version 2 or any later version.
1367
a7678cbd7c28 bisect extension for mercurial
Benoit Boissinot <benoit.boissinot@ens-lyon.org>
parents:
diff changeset
10
25952
f0ad094db832 hbisect: use absolute_import
Gregory Szorc <gregory.szorc@gmail.com>
parents: 25113
diff changeset
11 from __future__ import absolute_import
f0ad094db832 hbisect: use absolute_import
Gregory Szorc <gregory.szorc@gmail.com>
parents: 25113
diff changeset
12
25113
0ca8410ea345 util: drop alias for collections.deque
Martin von Zweigbergk <martinvonz@google.com>
parents: 23877
diff changeset
13 import collections
43665
f37da59a36d9 bisect: replace try:/finally: by a "restore_state" context manager
Denis Laxalde <denis.laxalde@logilab.fr>
parents: 43077
diff changeset
14 import contextlib
25952
f0ad094db832 hbisect: use absolute_import
Gregory Szorc <gregory.szorc@gmail.com>
parents: 25113
diff changeset
15
f0ad094db832 hbisect: use absolute_import
Gregory Szorc <gregory.szorc@gmail.com>
parents: 25113
diff changeset
16 from .i18n import _
f0ad094db832 hbisect: use absolute_import
Gregory Szorc <gregory.szorc@gmail.com>
parents: 25113
diff changeset
17 from .node import (
f0ad094db832 hbisect: use absolute_import
Gregory Szorc <gregory.szorc@gmail.com>
parents: 25113
diff changeset
18 hex,
f0ad094db832 hbisect: use absolute_import
Gregory Szorc <gregory.szorc@gmail.com>
parents: 25113
diff changeset
19 short,
f0ad094db832 hbisect: use absolute_import
Gregory Szorc <gregory.szorc@gmail.com>
parents: 25113
diff changeset
20 )
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 42310
diff changeset
21 from . import error
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 42310
diff changeset
22
1367
a7678cbd7c28 bisect extension for mercurial
Benoit Boissinot <benoit.boissinot@ens-lyon.org>
parents:
diff changeset
23
35128
fd8b6b183073 hbisect: pass repo into hbisect.bisect
David Soria Parra <davidsp@fb.com>
parents: 30389
diff changeset
24 def bisect(repo, state):
6858
8f256bf98219 Add support for multiple possible bisect results (issue1228, issue1182)
Bernhard Leiner <bleiner@gmail.com>
parents: 6217
diff changeset
25 """find the next node (if any) for testing during a bisect search.
8f256bf98219 Add support for multiple possible bisect results (issue1228, issue1182)
Bernhard Leiner <bleiner@gmail.com>
parents: 6217
diff changeset
26 returns a (nodes, number, good) tuple.
8f256bf98219 Add support for multiple possible bisect results (issue1228, issue1182)
Bernhard Leiner <bleiner@gmail.com>
parents: 6217
diff changeset
27
8f256bf98219 Add support for multiple possible bisect results (issue1228, issue1182)
Bernhard Leiner <bleiner@gmail.com>
parents: 6217
diff changeset
28 'nodes' is the final result of the bisect if 'number' is 0.
8f256bf98219 Add support for multiple possible bisect results (issue1228, issue1182)
Bernhard Leiner <bleiner@gmail.com>
parents: 6217
diff changeset
29 Otherwise 'number' indicates the remaining possible candidates for
8f256bf98219 Add support for multiple possible bisect results (issue1228, issue1182)
Bernhard Leiner <bleiner@gmail.com>
parents: 6217
diff changeset
30 the search and 'nodes' contains the next bisect target.
8f256bf98219 Add support for multiple possible bisect results (issue1228, issue1182)
Bernhard Leiner <bleiner@gmail.com>
parents: 6217
diff changeset
31 'good' is True if bisect is searching for a first good changeset, False
8f256bf98219 Add support for multiple possible bisect results (issue1228, issue1182)
Bernhard Leiner <bleiner@gmail.com>
parents: 6217
diff changeset
32 if searching for a first bad one.
8f256bf98219 Add support for multiple possible bisect results (issue1228, issue1182)
Bernhard Leiner <bleiner@gmail.com>
parents: 6217
diff changeset
33 """
8f256bf98219 Add support for multiple possible bisect results (issue1228, issue1182)
Bernhard Leiner <bleiner@gmail.com>
parents: 6217
diff changeset
34
42310
21eda240be07 bisect: do not crash with rewritten commits
timeless <timeless@mozdev.org>
parents: 42057
diff changeset
35 repo = repo.unfiltered()
35128
fd8b6b183073 hbisect: pass repo into hbisect.bisect
David Soria Parra <davidsp@fb.com>
parents: 30389
diff changeset
36 changelog = repo.changelog
5737
6c8df073c3ee bisect: remove class
Matt Mackall <mpm@selenic.com>
parents: 5736
diff changeset
37 clparents = changelog.parentrevs
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
38 skip = {changelog.rev(n) for n in state[b'skip']}
1367
a7678cbd7c28 bisect extension for mercurial
Benoit Boissinot <benoit.boissinot@ens-lyon.org>
parents:
diff changeset
39
5776
35ec669cdd43 bisect: handle search for bad to good transitions
Matt Mackall <mpm@selenic.com>
parents: 5775
diff changeset
40 def buildancestors(bad, good):
35ec669cdd43 bisect: handle search for bad to good transitions
Matt Mackall <mpm@selenic.com>
parents: 5775
diff changeset
41 badrev = min([changelog.rev(n) for n in bad])
35130
8287df8b7be5 hbisect: use a defaultdict to avoid large allocations for a large changelogs
David Soria Parra <davidsp@fb.com>
parents: 35129
diff changeset
42 ancestors = collections.defaultdict(lambda: None)
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
43 for rev in repo.revs(b"descendants(%ln) - ancestors(%ln)", good, good):
14895
a35d6f822e3e hbisect: do not assume that min(good) is an ancestor of min(bad)
Alexander Krauss <krauss@in.tum.de>
parents: 14894
diff changeset
44 ancestors[rev] = []
5776
35ec669cdd43 bisect: handle search for bad to good transitions
Matt Mackall <mpm@selenic.com>
parents: 5775
diff changeset
45 if ancestors[badrev] is None:
5777
51776e50bc8c bisect: improve tests
Matt Mackall <mpm@selenic.com>
parents: 5776
diff changeset
46 return badrev, None
5776
35ec669cdd43 bisect: handle search for bad to good transitions
Matt Mackall <mpm@selenic.com>
parents: 5775
diff changeset
47 return badrev, ancestors
35ec669cdd43 bisect: handle search for bad to good transitions
Matt Mackall <mpm@selenic.com>
parents: 5775
diff changeset
48
14215
e5a59d31bb04 hbisect: use real Booleans instead of 0/1
Martin Geisler <mg@aragost.com>
parents: 12067
diff changeset
49 good = False
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
50 badrev, ancestors = buildancestors(state[b'bad'], state[b'good'])
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 42310
diff changeset
51 if not ancestors: # looking for bad to good transition?
14215
e5a59d31bb04 hbisect: use real Booleans instead of 0/1
Martin Geisler <mg@aragost.com>
parents: 12067
diff changeset
52 good = True
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
53 badrev, ancestors = buildancestors(state[b'good'], state[b'bad'])
5777
51776e50bc8c bisect: improve tests
Matt Mackall <mpm@selenic.com>
parents: 5776
diff changeset
54 bad = changelog.node(badrev)
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 42310
diff changeset
55 if not ancestors: # now we're confused
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 42310
diff changeset
56 if (
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
57 len(state[b'bad']) == 1
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
58 and len(state[b'good']) == 1
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
59 and state[b'bad'] != state[b'good']
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 42310
diff changeset
60 ):
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
61 raise error.Abort(_(b"starting revisions are not directly related"))
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 42310
diff changeset
62 raise error.Abort(
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
63 _(b"inconsistent state, %d:%s is good and bad")
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 42310
diff changeset
64 % (badrev, short(bad))
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 42310
diff changeset
65 )
5723
e3b09819496b bisect: switch to rev-based calculation
Matt Mackall <mpm@selenic.com>
parents: 5722
diff changeset
66
5768
78d14403bdc7 bisect: use a dict for children
Matt Mackall <mpm@selenic.com>
parents: 5767
diff changeset
67 # build children dict
78d14403bdc7 bisect: use a dict for children
Matt Mackall <mpm@selenic.com>
parents: 5767
diff changeset
68 children = {}
25113
0ca8410ea345 util: drop alias for collections.deque
Martin von Zweigbergk <martinvonz@google.com>
parents: 23877
diff changeset
69 visit = collections.deque([badrev])
5769
49809f4a38d8 bisect: calculate candidate set while finding children
Matt Mackall <mpm@selenic.com>
parents: 5768
diff changeset
70 candidates = []
5768
78d14403bdc7 bisect: use a dict for children
Matt Mackall <mpm@selenic.com>
parents: 5767
diff changeset
71 while visit:
16803
107a3270a24a cleanup: use the deque type where appropriate
Bryan O'Sullivan <bryano@fb.com>
parents: 16647
diff changeset
72 rev = visit.popleft()
5767
dd5f8ed31057 bisect: propagate ancestor lists directly to children
Matt Mackall <mpm@selenic.com>
parents: 5766
diff changeset
73 if ancestors[rev] == []:
5769
49809f4a38d8 bisect: calculate candidate set while finding children
Matt Mackall <mpm@selenic.com>
parents: 5768
diff changeset
74 candidates.append(rev)
5767
dd5f8ed31057 bisect: propagate ancestor lists directly to children
Matt Mackall <mpm@selenic.com>
parents: 5766
diff changeset
75 for prev in clparents(rev):
5768
78d14403bdc7 bisect: use a dict for children
Matt Mackall <mpm@selenic.com>
parents: 5767
diff changeset
76 if prev != -1:
78d14403bdc7 bisect: use a dict for children
Matt Mackall <mpm@selenic.com>
parents: 5767
diff changeset
77 if prev in children:
78d14403bdc7 bisect: use a dict for children
Matt Mackall <mpm@selenic.com>
parents: 5767
diff changeset
78 children[prev].append(rev)
78d14403bdc7 bisect: use a dict for children
Matt Mackall <mpm@selenic.com>
parents: 5767
diff changeset
79 else:
78d14403bdc7 bisect: use a dict for children
Matt Mackall <mpm@selenic.com>
parents: 5767
diff changeset
80 children[prev] = [rev]
78d14403bdc7 bisect: use a dict for children
Matt Mackall <mpm@selenic.com>
parents: 5767
diff changeset
81 visit.append(prev)
5767
dd5f8ed31057 bisect: propagate ancestor lists directly to children
Matt Mackall <mpm@selenic.com>
parents: 5766
diff changeset
82
5769
49809f4a38d8 bisect: calculate candidate set while finding children
Matt Mackall <mpm@selenic.com>
parents: 5768
diff changeset
83 candidates.sort()
5770
f5b858fc8067 bisect: find best node in ancestor collection pass
Matt Mackall <mpm@selenic.com>
parents: 5769
diff changeset
84 # have we narrowed it down to one entry?
6858
8f256bf98219 Add support for multiple possible bisect results (issue1228, issue1182)
Bernhard Leiner <bleiner@gmail.com>
parents: 6217
diff changeset
85 # or have all other possible candidates besides 'bad' have been skipped?
5770
f5b858fc8067 bisect: find best node in ancestor collection pass
Matt Mackall <mpm@selenic.com>
parents: 5769
diff changeset
86 tot = len(candidates)
6858
8f256bf98219 Add support for multiple possible bisect results (issue1228, issue1182)
Bernhard Leiner <bleiner@gmail.com>
parents: 6217
diff changeset
87 unskipped = [c for c in candidates if (c not in skip) and (c != badrev)]
8f256bf98219 Add support for multiple possible bisect results (issue1228, issue1182)
Bernhard Leiner <bleiner@gmail.com>
parents: 6217
diff changeset
88 if tot == 1 or not unskipped:
30389
e124e83fd159 hbisect: avoid shadowing a variable in a list comprehension
Augie Fackler <augie@google.com>
parents: 30126
diff changeset
89 return ([changelog.node(c) for c in candidates], 0, good)
7902
afddc32b2b3f bisect: use integer division
Benoit Boissinot <benoit.boissinot@ens-lyon.org>
parents: 7557
diff changeset
90 perfect = tot // 2
5769
49809f4a38d8 bisect: calculate candidate set while finding children
Matt Mackall <mpm@selenic.com>
parents: 5768
diff changeset
91
5770
f5b858fc8067 bisect: find best node in ancestor collection pass
Matt Mackall <mpm@selenic.com>
parents: 5769
diff changeset
92 # find the best node to test
f5b858fc8067 bisect: find best node in ancestor collection pass
Matt Mackall <mpm@selenic.com>
parents: 5769
diff changeset
93 best_rev = None
f5b858fc8067 bisect: find best node in ancestor collection pass
Matt Mackall <mpm@selenic.com>
parents: 5769
diff changeset
94 best_len = -1
8463
43186df4bb8e bisect: use set instead of dict
Benoit Boissinot <benoit.boissinot@ens-lyon.org>
parents: 8228
diff changeset
95 poison = set()
5769
49809f4a38d8 bisect: calculate candidate set while finding children
Matt Mackall <mpm@selenic.com>
parents: 5768
diff changeset
96 for rev in candidates:
5772
4c46636eafe5 bisect: skip calculations on candidates with too many ancestors
Matt Mackall <mpm@selenic.com>
parents: 5771
diff changeset
97 if rev in poison:
8482
fc27c91fff2c hbisect: use set.update for bulk updates
Martin Geisler <mg@lazybytes.net>
parents: 8463
diff changeset
98 # poison children
fc27c91fff2c hbisect: use set.update for bulk updates
Martin Geisler <mg@lazybytes.net>
parents: 8463
diff changeset
99 poison.update(children.get(rev, []))
5772
4c46636eafe5 bisect: skip calculations on candidates with too many ancestors
Matt Mackall <mpm@selenic.com>
parents: 5771
diff changeset
100 continue
5773
2f6105ab4c54 bisect: merge ancestor lists when pushing to children
Matt Mackall <mpm@selenic.com>
parents: 5772
diff changeset
101
2f6105ab4c54 bisect: merge ancestor lists when pushing to children
Matt Mackall <mpm@selenic.com>
parents: 5772
diff changeset
102 a = ancestors[rev] or [rev]
5770
f5b858fc8067 bisect: find best node in ancestor collection pass
Matt Mackall <mpm@selenic.com>
parents: 5769
diff changeset
103 ancestors[rev] = None
5773
2f6105ab4c54 bisect: merge ancestor lists when pushing to children
Matt Mackall <mpm@selenic.com>
parents: 5772
diff changeset
104
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 42310
diff changeset
105 x = len(a) # number of ancestors
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 42310
diff changeset
106 y = tot - x # number of non-ancestors
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 42310
diff changeset
107 value = min(x, y) # how good is this test?
5773
2f6105ab4c54 bisect: merge ancestor lists when pushing to children
Matt Mackall <mpm@selenic.com>
parents: 5772
diff changeset
108 if value > best_len and rev not in skip:
2f6105ab4c54 bisect: merge ancestor lists when pushing to children
Matt Mackall <mpm@selenic.com>
parents: 5772
diff changeset
109 best_len = value
2f6105ab4c54 bisect: merge ancestor lists when pushing to children
Matt Mackall <mpm@selenic.com>
parents: 5772
diff changeset
110 best_rev = rev
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 42310
diff changeset
111 if value == perfect: # found a perfect candidate? quit early
5773
2f6105ab4c54 bisect: merge ancestor lists when pushing to children
Matt Mackall <mpm@selenic.com>
parents: 5772
diff changeset
112 break
5772
4c46636eafe5 bisect: skip calculations on candidates with too many ancestors
Matt Mackall <mpm@selenic.com>
parents: 5771
diff changeset
113
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 42310
diff changeset
114 if y < perfect and rev not in skip: # all downhill from here?
8482
fc27c91fff2c hbisect: use set.update for bulk updates
Martin Geisler <mg@lazybytes.net>
parents: 8463
diff changeset
115 # poison children
fc27c91fff2c hbisect: use set.update for bulk updates
Martin Geisler <mg@lazybytes.net>
parents: 8463
diff changeset
116 poison.update(children.get(rev, []))
5773
2f6105ab4c54 bisect: merge ancestor lists when pushing to children
Matt Mackall <mpm@selenic.com>
parents: 5772
diff changeset
117 continue
5772
4c46636eafe5 bisect: skip calculations on candidates with too many ancestors
Matt Mackall <mpm@selenic.com>
parents: 5771
diff changeset
118
5773
2f6105ab4c54 bisect: merge ancestor lists when pushing to children
Matt Mackall <mpm@selenic.com>
parents: 5772
diff changeset
119 for c in children.get(rev, []):
2f6105ab4c54 bisect: merge ancestor lists when pushing to children
Matt Mackall <mpm@selenic.com>
parents: 5772
diff changeset
120 if ancestors[c]:
8152
08e1baf924ca replace set-like dictionaries with real sets
Martin Geisler <mg@lazybytes.net>
parents: 8109
diff changeset
121 ancestors[c] = list(set(ancestors[c] + a))
5773
2f6105ab4c54 bisect: merge ancestor lists when pushing to children
Matt Mackall <mpm@selenic.com>
parents: 5772
diff changeset
122 else:
2f6105ab4c54 bisect: merge ancestor lists when pushing to children
Matt Mackall <mpm@selenic.com>
parents: 5772
diff changeset
123 ancestors[c] = a + [c]
5734
944b231fa0e7 bisect: move reporting out of core bisect function
Matt Mackall <mpm@selenic.com>
parents: 5733
diff changeset
124
5737
6c8df073c3ee bisect: remove class
Matt Mackall <mpm@selenic.com>
parents: 5736
diff changeset
125 assert best_rev is not None
6c8df073c3ee bisect: remove class
Matt Mackall <mpm@selenic.com>
parents: 5736
diff changeset
126 best_node = changelog.node(best_rev)
1367
a7678cbd7c28 bisect extension for mercurial
Benoit Boissinot <benoit.boissinot@ens-lyon.org>
parents:
diff changeset
127
6858
8f256bf98219 Add support for multiple possible bisect results (issue1228, issue1182)
Bernhard Leiner <bleiner@gmail.com>
parents: 6217
diff changeset
128 return ([best_node], tot, good)
7227
e1afb50ec2aa bisect: ability to check revision with command
Alexander Solovyov <piranha@piranha.org.ua>
parents: 6861
diff changeset
129
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 42310
diff changeset
130
30066
5f93737d0ba8 bisect: move the 'extendrange' to the 'hbisect' module
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 30065
diff changeset
131 def extendrange(repo, state, nodes, good):
5f93737d0ba8 bisect: move the 'extendrange' to the 'hbisect' module
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 30065
diff changeset
132 # bisect is incomplete when it ends on a merge node and
5f93737d0ba8 bisect: move the 'extendrange' to the 'hbisect' module
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 30065
diff changeset
133 # one of the parent was not checked.
5f93737d0ba8 bisect: move the 'extendrange' to the 'hbisect' module
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 30065
diff changeset
134 parents = repo[nodes[0]].parents()
5f93737d0ba8 bisect: move the 'extendrange' to the 'hbisect' module
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 30065
diff changeset
135 if len(parents) > 1:
5f93737d0ba8 bisect: move the 'extendrange' to the 'hbisect' module
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 30065
diff changeset
136 if good:
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
137 side = state[b'bad']
30066
5f93737d0ba8 bisect: move the 'extendrange' to the 'hbisect' module
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 30065
diff changeset
138 else:
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
139 side = state[b'good']
44452
9d2b2df2c2ba cleanup: run pyupgrade on our source tree to clean up varying things
Augie Fackler <augie@google.com>
parents: 43665
diff changeset
140 num = len({i.node() for i in parents} & set(side))
30066
5f93737d0ba8 bisect: move the 'extendrange' to the 'hbisect' module
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 30065
diff changeset
141 if num == 1:
5f93737d0ba8 bisect: move the 'extendrange' to the 'hbisect' module
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 30065
diff changeset
142 return parents[0].ancestor(parents[1])
5f93737d0ba8 bisect: move the 'extendrange' to the 'hbisect' module
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 30065
diff changeset
143 return None
7227
e1afb50ec2aa bisect: ability to check revision with command
Alexander Solovyov <piranha@piranha.org.ua>
parents: 6861
diff changeset
144
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 42310
diff changeset
145
7227
e1afb50ec2aa bisect: ability to check revision with command
Alexander Solovyov <piranha@piranha.org.ua>
parents: 6861
diff changeset
146 def load_state(repo):
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
147 state = {b'current': [], b'good': [], b'bad': [], b'skip': []}
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
148 for l in repo.vfs.tryreadlines(b"bisect.state"):
27525
cba62f996780 hbisect: use tryreadlines to load state
Bryan O'Sullivan <bos@serpentine.com>
parents: 26587
diff changeset
149 kind, node = l[:-1].split()
42310
21eda240be07 bisect: do not crash with rewritten commits
timeless <timeless@mozdev.org>
parents: 42057
diff changeset
150 node = repo.unfiltered().lookup(node)
27525
cba62f996780 hbisect: use tryreadlines to load state
Bryan O'Sullivan <bos@serpentine.com>
parents: 26587
diff changeset
151 if kind not in state:
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
152 raise error.Abort(_(b"unknown bisect kind %s") % kind)
27525
cba62f996780 hbisect: use tryreadlines to load state
Bryan O'Sullivan <bos@serpentine.com>
parents: 26587
diff changeset
153 state[kind].append(node)
7227
e1afb50ec2aa bisect: ability to check revision with command
Alexander Solovyov <piranha@piranha.org.ua>
parents: 6861
diff changeset
154 return state
e1afb50ec2aa bisect: ability to check revision with command
Alexander Solovyov <piranha@piranha.org.ua>
parents: 6861
diff changeset
155
e1afb50ec2aa bisect: ability to check revision with command
Alexander Solovyov <piranha@piranha.org.ua>
parents: 6861
diff changeset
156
e1afb50ec2aa bisect: ability to check revision with command
Alexander Solovyov <piranha@piranha.org.ua>
parents: 6861
diff changeset
157 def save_state(repo, state):
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
158 f = repo.vfs(b"bisect.state", b"w", atomictemp=True)
27853
9b8a5c6ac176 with: use context manager in bisect save_state
Bryan O'Sullivan <bryano@fb.com>
parents: 27525
diff changeset
159 with repo.wlock():
18358
93293813d753 bisect: store state sorted
Mads Kiilerich <mads@kiilerich.com>
parents: 17537
diff changeset
160 for kind in sorted(state):
7227
e1afb50ec2aa bisect: ability to check revision with command
Alexander Solovyov <piranha@piranha.org.ua>
parents: 6861
diff changeset
161 for node in state[kind]:
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
162 f.write(b"%s %s\n" % (kind, hex(node)))
15057
774da7121fc9 atomictempfile: make close() consistent with other file-like objects.
Greg Ward <greg@gerg.ca>
parents: 14895
diff changeset
163 f.close()
7227
e1afb50ec2aa bisect: ability to check revision with command
Alexander Solovyov <piranha@piranha.org.ua>
parents: 6861
diff changeset
164
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 42310
diff changeset
165
30065
ee21ed7fc7a2 bisect: extract the 'reset' logic into its own function
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 27853
diff changeset
166 def resetstate(repo):
ee21ed7fc7a2 bisect: extract the 'reset' logic into its own function
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 27853
diff changeset
167 """remove any bisect state from the repository"""
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
168 if repo.vfs.exists(b"bisect.state"):
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
169 repo.vfs.unlink(b"bisect.state")
30065
ee21ed7fc7a2 bisect: extract the 'reset' logic into its own function
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 27853
diff changeset
170
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 42310
diff changeset
171
30126
755730fc1e48 bisect: move check_state into the bisect module
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 30067
diff changeset
172 def checkstate(state):
755730fc1e48 bisect: move check_state into the bisect module
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 30067
diff changeset
173 """check we have both 'good' and 'bad' to define a range
755730fc1e48 bisect: move check_state into the bisect module
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 30067
diff changeset
174
755730fc1e48 bisect: move check_state into the bisect module
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 30067
diff changeset
175 Raise Abort exception otherwise."""
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
176 if state[b'good'] and state[b'bad']:
30126
755730fc1e48 bisect: move check_state into the bisect module
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 30067
diff changeset
177 return True
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
178 if not state[b'good']:
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
179 raise error.Abort(_(b'cannot bisect (no known good revisions)'))
30126
755730fc1e48 bisect: move check_state into the bisect module
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 30067
diff changeset
180 else:
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
181 raise error.Abort(_(b'cannot bisect (no known bad revisions)'))
30126
755730fc1e48 bisect: move check_state into the bisect module
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 30067
diff changeset
182
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 42310
diff changeset
183
43665
f37da59a36d9 bisect: replace try:/finally: by a "restore_state" context manager
Denis Laxalde <denis.laxalde@logilab.fr>
parents: 43077
diff changeset
184 @contextlib.contextmanager
f37da59a36d9 bisect: replace try:/finally: by a "restore_state" context manager
Denis Laxalde <denis.laxalde@logilab.fr>
parents: 43077
diff changeset
185 def restore_state(repo, state, node):
f37da59a36d9 bisect: replace try:/finally: by a "restore_state" context manager
Denis Laxalde <denis.laxalde@logilab.fr>
parents: 43077
diff changeset
186 try:
f37da59a36d9 bisect: replace try:/finally: by a "restore_state" context manager
Denis Laxalde <denis.laxalde@logilab.fr>
parents: 43077
diff changeset
187 yield
f37da59a36d9 bisect: replace try:/finally: by a "restore_state" context manager
Denis Laxalde <denis.laxalde@logilab.fr>
parents: 43077
diff changeset
188 finally:
f37da59a36d9 bisect: replace try:/finally: by a "restore_state" context manager
Denis Laxalde <denis.laxalde@logilab.fr>
parents: 43077
diff changeset
189 state[b'current'] = [node]
f37da59a36d9 bisect: replace try:/finally: by a "restore_state" context manager
Denis Laxalde <denis.laxalde@logilab.fr>
parents: 43077
diff changeset
190 save_state(repo, state)
f37da59a36d9 bisect: replace try:/finally: by a "restore_state" context manager
Denis Laxalde <denis.laxalde@logilab.fr>
parents: 43077
diff changeset
191
f37da59a36d9 bisect: replace try:/finally: by a "restore_state" context manager
Denis Laxalde <denis.laxalde@logilab.fr>
parents: 43077
diff changeset
192
15135
f19de58af225 revset.bisect: move bisect() code to hbisect.py
"Yann E. MORIN" <yann.morin.1998@anciens.enib.fr>
parents: 15057
diff changeset
193 def get(repo, status):
f19de58af225 revset.bisect: move bisect() code to hbisect.py
"Yann E. MORIN" <yann.morin.1998@anciens.enib.fr>
parents: 15057
diff changeset
194 """
f19de58af225 revset.bisect: move bisect() code to hbisect.py
"Yann E. MORIN" <yann.morin.1998@anciens.enib.fr>
parents: 15057
diff changeset
195 Return a list of revision(s) that match the given status:
f19de58af225 revset.bisect: move bisect() code to hbisect.py
"Yann E. MORIN" <yann.morin.1998@anciens.enib.fr>
parents: 15057
diff changeset
196
15153
fa0a464e4ca5 hbisect: add two new revset descriptions: 'goods' and 'bads'
"Yann E. MORIN" <yann.morin.1998@anciens.enib.fr>
parents: 15147
diff changeset
197 - ``good``, ``bad``, ``skip``: csets explicitly marked as good/bad/skip
17424
e7cfe3587ea4 fix trivial spelling errors
Mads Kiilerich <mads@kiilerich.com>
parents: 16834
diff changeset
198 - ``goods``, ``bads`` : csets topologically good/bad
15153
fa0a464e4ca5 hbisect: add two new revset descriptions: 'goods' and 'bads'
"Yann E. MORIN" <yann.morin.1998@anciens.enib.fr>
parents: 15147
diff changeset
199 - ``range`` : csets taking part in the bisection
fa0a464e4ca5 hbisect: add two new revset descriptions: 'goods' and 'bads'
"Yann E. MORIN" <yann.morin.1998@anciens.enib.fr>
parents: 15147
diff changeset
200 - ``pruned`` : csets that are goods, bads or skipped
15138
883d28233a4d revset.bisect: add new 'untested' set to the bisect keyword
"Yann E. MORIN" <yann.morin.1998@anciens.enib.fr>
parents: 15137
diff changeset
201 - ``untested`` : csets whose fate is yet unknown
15147
395ca8cd2669 revset.bisect: add 'ignored' set to the bisect keyword
"Yann E. MORIN" <yann.morin.1998@anciens.enib.fr>
parents: 15146
diff changeset
202 - ``ignored`` : csets ignored due to DAG topology
16647
14913fcb30c6 bisect: track the current changeset (issue3382)
Bryan O'Sullivan <bryano@fb.com>
parents: 15406
diff changeset
203 - ``current`` : the cset currently being bisected
15135
f19de58af225 revset.bisect: move bisect() code to hbisect.py
"Yann E. MORIN" <yann.morin.1998@anciens.enib.fr>
parents: 15057
diff changeset
204 """
f19de58af225 revset.bisect: move bisect() code to hbisect.py
"Yann E. MORIN" <yann.morin.1998@anciens.enib.fr>
parents: 15057
diff changeset
205 state = load_state(repo)
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
206 if status in (b'good', b'bad', b'skip', b'current'):
42310
21eda240be07 bisect: do not crash with rewritten commits
timeless <timeless@mozdev.org>
parents: 42057
diff changeset
207 return map(repo.unfiltered().changelog.rev, state[status])
15135
f19de58af225 revset.bisect: move bisect() code to hbisect.py
"Yann E. MORIN" <yann.morin.1998@anciens.enib.fr>
parents: 15057
diff changeset
208 else:
17493
d057e92dadfc spelling: following
timeless@mozdev.org
parents: 16834
diff changeset
209 # In the following sets, we do *not* call 'bisect()' with more
17509
f7767f52e9eb spelling: recursion
timeless@mozdev.org
parents: 17493
diff changeset
210 # than one level of recursion, because that can be very, very
15146
b39d85be78a8 hbisect.get: use simpler code with repo.set(), fix 'pruned' set
"Yann E. MORIN" <yann.morin.1998@anciens.enib.fr>
parents: 15138
diff changeset
211 # time consuming. Instead, we always develop the expression as
b39d85be78a8 hbisect.get: use simpler code with repo.set(), fix 'pruned' set
"Yann E. MORIN" <yann.morin.1998@anciens.enib.fr>
parents: 15138
diff changeset
212 # much as possible.
b39d85be78a8 hbisect.get: use simpler code with repo.set(), fix 'pruned' set
"Yann E. MORIN" <yann.morin.1998@anciens.enib.fr>
parents: 15138
diff changeset
213
b39d85be78a8 hbisect.get: use simpler code with repo.set(), fix 'pruned' set
"Yann E. MORIN" <yann.morin.1998@anciens.enib.fr>
parents: 15138
diff changeset
214 # 'range' is all csets that make the bisection:
b39d85be78a8 hbisect.get: use simpler code with repo.set(), fix 'pruned' set
"Yann E. MORIN" <yann.morin.1998@anciens.enib.fr>
parents: 15138
diff changeset
215 # - have a good ancestor and a bad descendant, or conversely
b39d85be78a8 hbisect.get: use simpler code with repo.set(), fix 'pruned' set
"Yann E. MORIN" <yann.morin.1998@anciens.enib.fr>
parents: 15138
diff changeset
216 # that's because the bisection can go either way
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
217 range = b'( bisect(bad)::bisect(good) | bisect(good)::bisect(bad) )'
15136
18219c0789ae revset.bisect: add new 'range' set to the bisect keyword
"Yann E. MORIN" <yann.morin.1998@anciens.enib.fr>
parents: 15135
diff changeset
218
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
219 _t = repo.revs(b'bisect(good)::bisect(bad)')
15153
fa0a464e4ca5 hbisect: add two new revset descriptions: 'goods' and 'bads'
"Yann E. MORIN" <yann.morin.1998@anciens.enib.fr>
parents: 15147
diff changeset
220 # The sets of topologically good or bad csets
fa0a464e4ca5 hbisect: add two new revset descriptions: 'goods' and 'bads'
"Yann E. MORIN" <yann.morin.1998@anciens.enib.fr>
parents: 15147
diff changeset
221 if len(_t) == 0:
fa0a464e4ca5 hbisect: add two new revset descriptions: 'goods' and 'bads'
"Yann E. MORIN" <yann.morin.1998@anciens.enib.fr>
parents: 15147
diff changeset
222 # Goods are topologically after bads
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
223 goods = b'bisect(good)::' # Pruned good csets
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
224 bads = b'::bisect(bad)' # Pruned bad csets
15153
fa0a464e4ca5 hbisect: add two new revset descriptions: 'goods' and 'bads'
"Yann E. MORIN" <yann.morin.1998@anciens.enib.fr>
parents: 15147
diff changeset
225 else:
fa0a464e4ca5 hbisect: add two new revset descriptions: 'goods' and 'bads'
"Yann E. MORIN" <yann.morin.1998@anciens.enib.fr>
parents: 15147
diff changeset
226 # Goods are topologically before bads
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
227 goods = b'::bisect(good)' # Pruned good csets
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
228 bads = b'bisect(bad)::' # Pruned bad csets
15153
fa0a464e4ca5 hbisect: add two new revset descriptions: 'goods' and 'bads'
"Yann E. MORIN" <yann.morin.1998@anciens.enib.fr>
parents: 15147
diff changeset
229
fa0a464e4ca5 hbisect: add two new revset descriptions: 'goods' and 'bads'
"Yann E. MORIN" <yann.morin.1998@anciens.enib.fr>
parents: 15147
diff changeset
230 # 'pruned' is all csets whose fate is already known: good, bad, skip
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
231 skips = b'bisect(skip)' # Pruned skipped csets
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
232 pruned = b'( (%s) | (%s) | (%s) )' % (goods, bads, skips)
15136
18219c0789ae revset.bisect: add new 'range' set to the bisect keyword
"Yann E. MORIN" <yann.morin.1998@anciens.enib.fr>
parents: 15135
diff changeset
233
15146
b39d85be78a8 hbisect.get: use simpler code with repo.set(), fix 'pruned' set
"Yann E. MORIN" <yann.morin.1998@anciens.enib.fr>
parents: 15138
diff changeset
234 # 'untested' is all cset that are- in 'range', but not in 'pruned'
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
235 untested = b'( (%s) - (%s) )' % (range, pruned)
15136
18219c0789ae revset.bisect: add new 'range' set to the bisect keyword
"Yann E. MORIN" <yann.morin.1998@anciens.enib.fr>
parents: 15135
diff changeset
236
15147
395ca8cd2669 revset.bisect: add 'ignored' set to the bisect keyword
"Yann E. MORIN" <yann.morin.1998@anciens.enib.fr>
parents: 15146
diff changeset
237 # 'ignored' is all csets that were not used during the bisection
395ca8cd2669 revset.bisect: add 'ignored' set to the bisect keyword
"Yann E. MORIN" <yann.morin.1998@anciens.enib.fr>
parents: 15146
diff changeset
238 # due to DAG topology, but may however have had an impact.
17424
e7cfe3587ea4 fix trivial spelling errors
Mads Kiilerich <mads@kiilerich.com>
parents: 16834
diff changeset
239 # E.g., a branch merged between bads and goods, but whose branch-
15147
395ca8cd2669 revset.bisect: add 'ignored' set to the bisect keyword
"Yann E. MORIN" <yann.morin.1998@anciens.enib.fr>
parents: 15146
diff changeset
240 # point is out-side of the range.
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
241 iba = b'::bisect(bad) - ::bisect(good)' # Ignored bads' ancestors
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
242 iga = b'::bisect(good) - ::bisect(bad)' # Ignored goods' ancestors
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
243 ignored = b'( ( (%s) | (%s) ) - (%s) )' % (iba, iga, range)
15147
395ca8cd2669 revset.bisect: add 'ignored' set to the bisect keyword
"Yann E. MORIN" <yann.morin.1998@anciens.enib.fr>
parents: 15146
diff changeset
244
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
245 if status == b'range':
15404
c1eb8398fe82 localrepo: convert various repo.set() users to repo.revs()
Matt Mackall <mpm@selenic.com>
parents: 15308
diff changeset
246 return repo.revs(range)
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
247 elif status == b'pruned':
15404
c1eb8398fe82 localrepo: convert various repo.set() users to repo.revs()
Matt Mackall <mpm@selenic.com>
parents: 15308
diff changeset
248 return repo.revs(pruned)
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
249 elif status == b'untested':
15404
c1eb8398fe82 localrepo: convert various repo.set() users to repo.revs()
Matt Mackall <mpm@selenic.com>
parents: 15308
diff changeset
250 return repo.revs(untested)
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
251 elif status == b'ignored':
15404
c1eb8398fe82 localrepo: convert various repo.set() users to repo.revs()
Matt Mackall <mpm@selenic.com>
parents: 15308
diff changeset
252 return repo.revs(ignored)
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
253 elif status == b"goods":
15404
c1eb8398fe82 localrepo: convert various repo.set() users to repo.revs()
Matt Mackall <mpm@selenic.com>
parents: 15308
diff changeset
254 return repo.revs(goods)
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
255 elif status == b"bads":
15404
c1eb8398fe82 localrepo: convert various repo.set() users to repo.revs()
Matt Mackall <mpm@selenic.com>
parents: 15308
diff changeset
256 return repo.revs(bads)
15136
18219c0789ae revset.bisect: add new 'range' set to the bisect keyword
"Yann E. MORIN" <yann.morin.1998@anciens.enib.fr>
parents: 15135
diff changeset
257 else:
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
258 raise error.ParseError(_(b'invalid bisect state'))
15154
aa2e908c521e hbisect: add functions to return a label for a cset bisection status
"Yann E. MORIN" <yann.morin.1998@anciens.enib.fr>
parents: 15153
diff changeset
259
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 42310
diff changeset
260
15406
1f677c7e494d bisect: remove superfluous parameter in label()
"Yann E. MORIN" <yann.morin.1998@anciens.enib.fr>
parents: 15404
diff changeset
261 def label(repo, node):
15154
aa2e908c521e hbisect: add functions to return a label for a cset bisection status
"Yann E. MORIN" <yann.morin.1998@anciens.enib.fr>
parents: 15153
diff changeset
262 rev = repo.changelog.rev(node)
aa2e908c521e hbisect: add functions to return a label for a cset bisection status
"Yann E. MORIN" <yann.morin.1998@anciens.enib.fr>
parents: 15153
diff changeset
263
aa2e908c521e hbisect: add functions to return a label for a cset bisection status
"Yann E. MORIN" <yann.morin.1998@anciens.enib.fr>
parents: 15153
diff changeset
264 # Try explicit sets
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
265 if rev in get(repo, b'good'):
15308
ab341fbb05b1 bisect: add i18n contexts
Wagner Bruna <wbruna@softwareexpress.com.br>
parents: 15154
diff changeset
266 # i18n: bisect changeset status
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
267 return _(b'good')
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
268 if rev in get(repo, b'bad'):
15308
ab341fbb05b1 bisect: add i18n contexts
Wagner Bruna <wbruna@softwareexpress.com.br>
parents: 15154
diff changeset
269 # i18n: bisect changeset status
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
270 return _(b'bad')
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
271 if rev in get(repo, b'skip'):
15308
ab341fbb05b1 bisect: add i18n contexts
Wagner Bruna <wbruna@softwareexpress.com.br>
parents: 15154
diff changeset
272 # i18n: bisect changeset status
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
273 return _(b'skipped')
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
274 if rev in get(repo, b'untested') or rev in get(repo, b'current'):
15308
ab341fbb05b1 bisect: add i18n contexts
Wagner Bruna <wbruna@softwareexpress.com.br>
parents: 15154
diff changeset
275 # i18n: bisect changeset status
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
276 return _(b'untested')
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
277 if rev in get(repo, b'ignored'):
15308
ab341fbb05b1 bisect: add i18n contexts
Wagner Bruna <wbruna@softwareexpress.com.br>
parents: 15154
diff changeset
278 # i18n: bisect changeset status
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
279 return _(b'ignored')
15154
aa2e908c521e hbisect: add functions to return a label for a cset bisection status
"Yann E. MORIN" <yann.morin.1998@anciens.enib.fr>
parents: 15153
diff changeset
280
aa2e908c521e hbisect: add functions to return a label for a cset bisection status
"Yann E. MORIN" <yann.morin.1998@anciens.enib.fr>
parents: 15153
diff changeset
281 # Try implicit sets
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
282 if rev in get(repo, b'goods'):
15308
ab341fbb05b1 bisect: add i18n contexts
Wagner Bruna <wbruna@softwareexpress.com.br>
parents: 15154
diff changeset
283 # i18n: bisect changeset status
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
284 return _(b'good (implicit)')
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
285 if rev in get(repo, b'bads'):
15308
ab341fbb05b1 bisect: add i18n contexts
Wagner Bruna <wbruna@softwareexpress.com.br>
parents: 15154
diff changeset
286 # i18n: bisect changeset status
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
287 return _(b'bad (implicit)')
15154
aa2e908c521e hbisect: add functions to return a label for a cset bisection status
"Yann E. MORIN" <yann.morin.1998@anciens.enib.fr>
parents: 15153
diff changeset
288
aa2e908c521e hbisect: add functions to return a label for a cset bisection status
"Yann E. MORIN" <yann.morin.1998@anciens.enib.fr>
parents: 15153
diff changeset
289 return None
aa2e908c521e hbisect: add functions to return a label for a cset bisection status
"Yann E. MORIN" <yann.morin.1998@anciens.enib.fr>
parents: 15153
diff changeset
290
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 42310
diff changeset
291
30067
6e88cd060ba2 bisect: move 'printresult' in the 'hbisect' module
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 30066
diff changeset
292 def printresult(ui, repo, state, displayer, nodes, good):
42310
21eda240be07 bisect: do not crash with rewritten commits
timeless <timeless@mozdev.org>
parents: 42057
diff changeset
293 repo = repo.unfiltered()
30067
6e88cd060ba2 bisect: move 'printresult' in the 'hbisect' module
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 30066
diff changeset
294 if len(nodes) == 1:
6e88cd060ba2 bisect: move 'printresult' in the 'hbisect' module
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 30066
diff changeset
295 # narrowed it down to a single revision
6e88cd060ba2 bisect: move 'printresult' in the 'hbisect' module
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 30066
diff changeset
296 if good:
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
297 ui.write(_(b"The first good revision is:\n"))
30067
6e88cd060ba2 bisect: move 'printresult' in the 'hbisect' module
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 30066
diff changeset
298 else:
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
299 ui.write(_(b"The first bad revision is:\n"))
30067
6e88cd060ba2 bisect: move 'printresult' in the 'hbisect' module
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 30066
diff changeset
300 displayer.show(repo[nodes[0]])
6e88cd060ba2 bisect: move 'printresult' in the 'hbisect' module
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 30066
diff changeset
301 extendnode = extendrange(repo, state, nodes, good)
6e88cd060ba2 bisect: move 'printresult' in the 'hbisect' module
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 30066
diff changeset
302 if extendnode is not None:
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 42310
diff changeset
303 ui.write(
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 42310
diff changeset
304 _(
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
305 b'Not all ancestors of this changeset have been'
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
306 b' checked.\nUse bisect --extend to continue the '
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
307 b'bisection from\nthe common ancestor, %s.\n'
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 42310
diff changeset
308 )
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 42310
diff changeset
309 % extendnode
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 42310
diff changeset
310 )
30067
6e88cd060ba2 bisect: move 'printresult' in the 'hbisect' module
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 30066
diff changeset
311 else:
6e88cd060ba2 bisect: move 'printresult' in the 'hbisect' module
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 30066
diff changeset
312 # multiple possible revisions
6e88cd060ba2 bisect: move 'printresult' in the 'hbisect' module
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 30066
diff changeset
313 if good:
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 42310
diff changeset
314 ui.write(
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 42310
diff changeset
315 _(
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
316 b"Due to skipped revisions, the first "
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
317 b"good revision could be any of:\n"
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 42310
diff changeset
318 )
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 42310
diff changeset
319 )
30067
6e88cd060ba2 bisect: move 'printresult' in the 'hbisect' module
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 30066
diff changeset
320 else:
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 42310
diff changeset
321 ui.write(
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 42310
diff changeset
322 _(
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
323 b"Due to skipped revisions, the first "
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
324 b"bad revision could be any of:\n"
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 42310
diff changeset
325 )
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 42310
diff changeset
326 )
30067
6e88cd060ba2 bisect: move 'printresult' in the 'hbisect' module
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 30066
diff changeset
327 for n in nodes:
6e88cd060ba2 bisect: move 'printresult' in the 'hbisect' module
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 30066
diff changeset
328 displayer.show(repo[n])
6e88cd060ba2 bisect: move 'printresult' in the 'hbisect' module
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 30066
diff changeset
329 displayer.close()