3 USAGE='[help|start|bad|good|skip|next|reset|visualize|replay|log|run]'
4 LONG_USAGE='git bisect help
5 print this long help message.
6 git bisect start [--no-checkout] [<bad> [<good>...]] [--] [<pathspec>...]
7 reset bisect state and start bisection.
9 mark <rev> a known-bad revision.
10 git bisect good [<rev>...]
11 mark <rev>... known-good revisions.
12 git bisect skip [(<rev>|<range>)...]
13 mark <rev>... untestable revisions.
15 find next bisection to test and check it out.
16 git bisect reset [<commit>]
17 finish bisection search and go back to commit.
19 show bisect status in gitk.
20 git bisect replay <logfile>
24 git bisect run <cmd>...
25 use <cmd>... to automatically bisect.
27 Please use "git help bisect" to get the full man page.'
33 _x40='[0-9a-f][0-9a-f][0-9a-f][0-9a-f][0-9a-f]'
34 _x40="$_x40$_x40$_x40$_x40$_x40$_x40$_x40$_x40"
38 if test -f "$GIT_DIR/BISECT_HEAD"
47 test -s "$GIT_DIR/BISECT_START" || {
48 gettextln "You need to start by \"git bisect start\"" >&2
51 # TRANSLATORS: Make sure to include [Y] and [n] in your
52 # translation. The program will only accept English input
54 gettext "Do you want me to do it for you [Y/n]? " >&2
69 # Check for one bad and then some good revisions.
73 case "$arg" in --) has_double_dash=1; break ;; esac
75 orig_args=$(git rev-parse --sq-quote "$@")
78 if test "z$(git rev-parse --is-bare-repository)" != zfalse
84 while [ $# -gt 0 ]; do
95 die "$(eval_gettext "unrecognised option: '\$arg'")" ;;
97 rev=$(git rev-parse -q --verify "$arg^{commit}") || {
98 test $has_double_dash -eq 1 &&
99 die "$(eval_gettext "'\$arg' does not appear to be a valid revision")"
103 0) state='bad' ; bad_seen=1 ;;
106 eval="$eval bisect_write '$state' '$rev' 'nolog' &&"
115 head=$(GIT_DIR="$GIT_DIR" git symbolic-ref -q HEAD) ||
116 head=$(GIT_DIR="$GIT_DIR" git rev-parse --verify HEAD) ||
117 die "$(gettext "Bad HEAD - I need a HEAD")"
120 # Check if we are bisecting.
123 if test -s "$GIT_DIR/BISECT_START"
125 # Reset to the rev from where we started.
126 start_head=$(cat "$GIT_DIR/BISECT_START")
127 if test "z$mode" != "z--no-checkout"
129 git checkout "$start_head" --
132 # Get rev from where we start.
135 # This error message should only be triggered by
136 # cogito usage, and cogito users should understand
137 # it relates to cg-seek.
138 [ -s "$GIT_DIR/head-name" ] &&
139 die "$(gettext "won't bisect on seeked tree")"
140 start_head="${head#refs/heads/}"
143 die "$(gettext "Bad HEAD - strange symbolic ref")"
149 # Get rid of any old bisect state.
151 bisect_clean_state || exit
155 # In case of mistaken revs or checkout error, or signals received,
156 # "bisect_auto_next" below may exit or misbehave.
157 # We have to trap this to be able to clean up using
158 # "bisect_clean_state".
160 trap 'bisect_clean_state' 0
161 trap 'exit 255' 1 2 3 15
164 # Write new start state.
166 echo "$start_head" >"$GIT_DIR/BISECT_START" && {
167 test "z$mode" != "z--no-checkout" ||
168 git update-ref --no-deref BISECT_HEAD "$start_head"
170 git rev-parse --sq-quote "$@" >"$GIT_DIR/BISECT_NAMES" &&
172 echo "git bisect start$orig_args" >>"$GIT_DIR/BISECT_LOG" || exit
174 # Check if we can proceed to the next bisect state.
187 good|skip) tag="$state"-"$rev" ;;
188 *) die "$(eval_gettext "Bad bisect_write argument: \$state")" ;;
190 git update-ref "refs/bisect/$tag" "$rev" || exit
191 echo "# $state: $(git show-branch $rev)" >>"$GIT_DIR/BISECT_LOG"
192 test -n "$nolog" || echo "git bisect $state $rev" >>"$GIT_DIR/BISECT_LOG"
196 test -f "$GIT_DIR/BISECT_EXPECTED_REV" &&
197 test "$1" = $(cat "$GIT_DIR/BISECT_EXPECTED_REV")
200 check_expected_revs() {
202 if ! is_expected_rev "$_rev"
204 rm -f "$GIT_DIR/BISECT_ANCESTORS_OK"
205 rm -f "$GIT_DIR/BISECT_EXPECTED_REV"
217 revs=$(git rev-list "$arg") || die "$(eval_gettext "Bad rev input: \$arg")" ;;
219 revs=$(git rev-parse --sq-quote "$arg") ;;
223 eval bisect_state 'skip' $all
231 die "$(gettext "Please call 'bisect_state' with at least one argument.")" ;;
233 rev=$(git rev-parse --verify $(bisect_head)) ||
234 die "$(gettext "Bad rev input: $(bisect_head)")"
235 bisect_write "$state" "$rev"
236 check_expected_revs "$rev" ;;
242 sha=$(git rev-parse --verify "$rev^{commit}") ||
243 die "$(eval_gettext "Bad rev input: \$rev")"
244 eval="$eval bisect_write '$state' '$sha'; "
247 check_expected_revs "$@" ;;
249 die "$(gettext "'git bisect bad' can take only one argument.")" ;;
256 bisect_next_check() {
257 missing_good= missing_bad=
258 git show-ref -q --verify refs/bisect/bad || missing_bad=t
259 test -n "$(git for-each-ref "refs/bisect/good-*")" || missing_good=t
261 case "$missing_good,$missing_bad,$1" in
263 : have both good and bad - ok
266 # do not have both but not asked to fail - just report.
270 # have bad but not good. we could bisect although
271 # this is less optimum.
272 gettextln "Warning: bisecting only with a bad commit." >&2
275 # TRANSLATORS: Make sure to include [Y] and [n] in your
276 # translation. The program will only accept English input
278 gettext "Are you sure [Y/n]? " >&2
280 case "$yesno" in [Nn]*) exit 1 ;; esac
282 : bisect without good...
286 if test -s "$GIT_DIR/BISECT_START"
288 gettextln "You need to give me at least one good and one bad revisions.
289 (You can use \"git bisect bad\" and \"git bisect good\" for that.)" >&2
291 gettextln "You need to start by \"git bisect start\".
292 You then need to give me at least one good and one bad revisions.
293 (You can use \"git bisect bad\" and \"git bisect good\" for that.)" >&2
300 bisect_next_check && bisect_next || :
304 case "$#" in 0) ;; *) usage ;; esac
306 bisect_next_check good
308 # Perform all bisection computation, display and checkout
309 git bisect--helper --next-all $(test -f "$GIT_DIR/BISECT_HEAD" && echo --no-checkout)
312 # Check if we should exit because bisection is finished
313 test $res -eq 10 && exit 0
315 # Check for an error in the bisection process
316 test $res -ne 0 && exit $res
322 bisect_next_check fail
326 if test -n "${DISPLAY+set}${SESSIONNAME+set}${MSYSTEM+set}${SECURITYSESSIONID+set}" &&
327 type gitk >/dev/null 2>&1
336 -*) set git log "$@" ;;
341 eval '"$@"' --bisect -- $(cat "$GIT_DIR/BISECT_NAMES")
345 test -s "$GIT_DIR/BISECT_START" || {
346 gettextln "We are not bisecting."
350 0) branch=$(cat "$GIT_DIR/BISECT_START") ;;
351 1) git rev-parse --quiet --verify "$1^{commit}" > /dev/null || {
353 die "$(eval_gettext "'\$invalid' is not a valid commit")"
360 if ! test -f "$GIT_DIR/BISECT_HEAD" && ! git checkout "$branch" --
362 die "$(eval_gettext "Could not check out original HEAD '\$branch'.
363 Try 'git bisect reset <commit>'.")"
368 bisect_clean_state() {
369 # There may be some refs packed during bisection.
370 git for-each-ref --format='%(refname) %(objectname)' refs/bisect/\* |
373 git update-ref -d $ref $hash || exit
375 rm -f "$GIT_DIR/BISECT_EXPECTED_REV" &&
376 rm -f "$GIT_DIR/BISECT_ANCESTORS_OK" &&
377 rm -f "$GIT_DIR/BISECT_LOG" &&
378 rm -f "$GIT_DIR/BISECT_NAMES" &&
379 rm -f "$GIT_DIR/BISECT_RUN" &&
380 # Cleanup head-name if it got left by an old version of git-bisect
381 rm -f "$GIT_DIR/head-name" &&
382 git update-ref -d --no-deref BISECT_HEAD &&
383 # clean up BISECT_START last
384 rm -f "$GIT_DIR/BISECT_START"
389 test "$#" -eq 1 || die "$(gettext "No logfile given")"
390 test -r "$file" || die "$(eval_gettext "cannot read \$file for replaying")"
392 while read git bisect command rev
394 test "$git $bisect" = "git bisect" -o "$git" = "git-bisect" || continue
395 if test "$git" = "git-bisect"
402 cmd="bisect_start $rev"
405 bisect_write "$command" "$rev" ;;
407 die "$(gettext "?? what are you talking about?")" ;;
414 bisect_next_check fail
419 eval_gettextln "running \$command"
423 # Check for really bad run error.
424 if [ $res -lt 0 -o $res -ge 128 ]
426 eval_gettextln "bisect run failed:
427 exit code \$res from '\$command' is < 0 or >= 128" >&2
431 # Find current state depending on run success or failure.
432 # A special exit code of 125 means cannot test.
443 # We have to use a subshell because "bisect_state" can exit.
444 ( bisect_state $state > "$GIT_DIR/BISECT_RUN" )
447 cat "$GIT_DIR/BISECT_RUN"
449 if sane_grep "first bad commit could be any of" "$GIT_DIR/BISECT_RUN" \
452 gettextln "bisect run cannot continue any more" >&2
458 eval_gettextln "bisect run failed:
459 'bisect_state \$state' exited with error code \$res" >&2
463 if sane_grep "is the first bad commit" "$GIT_DIR/BISECT_RUN" > /dev/null
465 gettextln "bisect run success"
473 test -s "$GIT_DIR/BISECT_LOG" || die "$(gettext "We are not bisecting.")"
474 cat "$GIT_DIR/BISECT_LOG"
489 bisect_state "$cmd" "$@" ;;
493 # Not sure we want "next" at the UI level anymore.
496 bisect_visualize "$@" ;;
500 bisect_replay "$@" ;;