[RFC/PATCH] Bisect: implement "git bisect run <cmd>..." to automatically bisect.

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



This idea was suggested by Bill Lear
(Message-ID: <17920.38942.364466.642979@xxxxxxxxxxxxxxx>)
and I think it is a very good one.

This patch adds a new test file for "git bisect run", but there
is currently only one basic test.

Signed-off-by: Christian Couder <chriscool@xxxxxxxxxxxxx>
---
 git-bisect.sh         |   54 +++++++++++++++++++++++++++++++++++++++++++--
 t/t6030-bisect-run.sh |   57 +++++++++++++++++++++++++++++++++++++++++++++++++
 2 files changed, 108 insertions(+), 3 deletions(-)
 create mode 100755 t/t6030-bisect-run.sh

diff --git a/git-bisect.sh b/git-bisect.sh
index b1c3a6b..53dff7d 100755
--- a/git-bisect.sh
+++ b/git-bisect.sh
@@ -1,14 +1,15 @@
 #!/bin/sh
 
-USAGE='[start|bad|good|next|reset|visualize|replay|log]'
+USAGE='[start|bad|good|next|reset|visualize|replay|log|run]'
 LONG_USAGE='git bisect start [<pathspec>]	reset bisect state and start bisection.
 git bisect bad [<rev>]		mark <rev> a known-bad revision.
 git bisect good [<rev>...]	mark <rev>... known-good revisions.
 git bisect next			find next bisection to test and check it out.
 git bisect reset [<branch>]	finish bisection search and go back to branch.
 git bisect visualize            show bisect status in gitk.
-git bisect replay <logfile>	replay bisection log
-git bisect log			show bisect log.'
+git bisect replay <logfile>	replay bisection log.
+git bisect log			show bisect log.
+git bisect run <cmd>... 	use <cmd>... to automatically bisect.'
 
 . git-sh-setup
 require_work_tree
@@ -185,6 +186,7 @@ bisect_reset() {
 		rm -f "$GIT_DIR/refs/heads/bisect" "$GIT_DIR/head-name"
 		rm -f "$GIT_DIR/BISECT_LOG"
 		rm -f "$GIT_DIR/BISECT_NAMES"
+		rm -f "$GIT_DIR/BISECT_RUN"
 	fi
 }
 
@@ -220,6 +222,50 @@ bisect_replay () {
 	bisect_auto_next
 }
 
+bisect_run () {
+    while true
+    do
+      echo "running $@"
+      "$@"
+      res=$?
+
+      # Check for really bad run error.
+      if [ $res -lt 0 -o $res -ge 128 ]; then
+	  echo >&2 "bisect run failed:"
+	  echo >&2 "exit code $res from '$@' is < 0 or >= 128"
+	  exit $res
+      fi
+
+      # Use "git-bisect good" or "git-bisect bad"
+      # depending on run success or failure.
+      # We cannot use bisect_good or bisect_bad functions
+      # because they can exit.
+      if [ $res -gt 0 ]; then
+	  next_bisect='git-bisect bad'
+      else
+	  next_bisect='git-bisect good'
+      fi
+
+      $next_bisect > "$GIT_DIR/BISECT_RUN"
+      res=$?
+
+      cat "$GIT_DIR/BISECT_RUN"
+
+      if [ $res -ne 0 ]; then
+	  echo >&2 "bisect run failed:"
+	  echo >&2 "$next_bisect exited with error code $res"
+	  exit $res
+      fi
+
+      if grep "is first bad commit" "$GIT_DIR/BISECT_RUN" > /dev/null; then
+	  echo "bisect run success"
+	  exit 0;
+      fi
+
+    done
+}
+
+
 case "$#" in
 0)
     usage ;;
@@ -244,6 +290,8 @@ case "$#" in
 	bisect_replay "$@" ;;
     log)
 	cat "$GIT_DIR/BISECT_LOG" ;;
+    run)
+        bisect_run "$@" ;;
     *)
         usage ;;
     esac
diff --git a/t/t6030-bisect-run.sh b/t/t6030-bisect-run.sh
new file mode 100755
index 0000000..39c7228
--- /dev/null
+++ b/t/t6030-bisect-run.sh
@@ -0,0 +1,57 @@
+#!/bin/sh
+#
+# Copyright (c) 2007 Christian Couder
+#
+test_description='Tests git-bisect run functionality'
+
+. ./test-lib.sh
+
+add_line_into_file()
+{
+    _line=$1
+    _file=$2
+
+    if [ -f "$_file" ]; then
+        echo "$_line" >> $_file || return $?
+        MSG="Add <$_line> into <$_file>."
+    else
+        echo "$_line" > $_file || return $?
+        git add $_file || return $?
+        MSG="Create file <$_file> with <$_line> inside."
+    fi
+
+    git-commit -m "$MSG" $_file
+}
+
+HASH1=
+HASH3=
+HASH4=
+
+test_expect_success \
+    'set up basic repo with 1 file (hello) and 4 commits' \
+    'add_line_into_file "1: Hello World" hello &&
+     add_line_into_file "2: A new day for git" hello &&
+     add_line_into_file "3: Another new day for git" hello &&
+     add_line_into_file "4: Ciao for now" hello &&
+     HASH1=$(git rev-list HEAD | tail -1) &&
+     HASH3=$(git rev-list HEAD | head -2 | tail -1) &&
+     HASH4=$(git rev-list HEAD | head -1)'
+
+# We want to automatically find the commit that
+# introduced "Another" into hello.
+test_expect_success \
+    'git bisect run simple case' \
+    'echo "#!/bin/sh" > test_script.sh &&
+     echo "grep Another hello > /dev/null" >> test_script.sh &&
+     echo "test \$? -ne 0" >> test_script.sh &&
+     chmod +x test_script.sh &&
+     git bisect start &&
+     git bisect good $HASH1 &&
+     git bisect bad $HASH4 &&
+     git bisect run ./test_script.sh > my_bisect_log.txt &&
+     grep "$HASH3 is first bad commit" my_bisect_log.txt'
+
+#
+#
+test_done
+
-- 
1.5.1.rc1.13.g0872-dirty
-
To unsubscribe from this list: send the line "unsubscribe git" in
the body of a message to majordomo@xxxxxxxxxxxxxxx
More majordomo info at  http://vger.kernel.org/majordomo-info.html

[Index of Archives]     [Linux Kernel Development]     [Gcc Help]     [IETF Annouce]     [DCCP]     [Netdev]     [Networking]     [Security]     [V4L]     [Bugtraq]     [Yosemite]     [MIPS Linux]     [ARM Linux]     [Linux Security]     [Linux RAID]     [Linux SCSI]     [Fedora Users]