Reimplement `bisect_reset` shell function in C and add a `--bisect-reset`
subcommand to `git bisect--helper` to call it from git-bisect.sh .
Using `bisect_reset` subcommand is a temporary measure to port shell
functions to C so as to use the existing test suite. As more functions
are ported, this subcommand would be retired and will be called by some
other method.
Note: --bisect-clean-state subcommand has not been retired as there are
still a function namely `bisect_start()` which still uses this
subcommand.
Mentored-by: Lars Schneider
Mentored-by: Christian Couder
Signed-off-by: Pranit Bauva
---
builtin/bisect--helper.c | 48 +++-
git-bisect.sh| 28 ++--
2 files changed, 49 insertions(+), 27 deletions(-)
diff --git a/builtin/bisect--helper.c b/builtin/bisect--helper.c
index 3e4a458..14043a8 100644
--- a/builtin/bisect--helper.c
+++ b/builtin/bisect--helper.c
@@ -4,6 +4,8 @@
#include "bisect.h"
#include "refs.h"
#include "dir.h"
+#include "argv-array.h"
+#include "run-command.h"
static GIT_PATH_FUNC(git_path_bisect_write_terms, "BISECT_TERMS")
static GIT_PATH_FUNC(git_path_bisect_expected_rev, "BISECT_EXPECTED_REV")
@@ -13,11 +15,13 @@ static GIT_PATH_FUNC(git_path_bisect_names, "BISECT_NAMES")
static GIT_PATH_FUNC(git_path_bisect_run, "BISECT_RUN")
static GIT_PATH_FUNC(git_path_head_name, "head-name")
static GIT_PATH_FUNC(git_path_bisect_start, "BISECT_START")
+static GIT_PATH_FUNC(git_path_bisect_head, "BISECT_HEAD")
static const char * const git_bisect_helper_usage[] = {
N_("git bisect--helper --next-all [--no-checkout]"),
N_("git bisect--helper --write-terms "),
N_("git bisect--helper --bisect-clean-state"),
+ N_("git bisect--helper --bisect-reset []"),
NULL
};
@@ -123,12 +127,48 @@ static int bisect_clean_state(void)
return result;
}
+static int bisect_reset(const char *commit)
+{
+ struct strbuf branch = STRBUF_INIT;
+
+ if (!commit) {
+ if (strbuf_read_file(&branch, git_path_bisect_start(), 0) < 1) {
+ printf("We are not bisecting.\n");
+ return 0;
+ }
+ strbuf_rtrim(&branch);
+
+ } else {
+ struct object_id oid;
+ if (get_oid(commit, &oid))
+ return error(_("'%s' is not a valid commit"), commit);
+ strbuf_addf(&branch, "%s", commit);
+ }
+
+ if (!file_exists(git_path_bisect_head())) {
+ struct argv_array argv = ARGV_ARRAY_INIT;
+ argv_array_pushl(&argv, "checkout", branch.buf, "--", NULL);
+ if (run_command_v_opt(argv.argv, RUN_GIT_CMD)) {
+ error(_("Could not check out original HEAD '%s'. Try"
+ "'git bisect reset '."),
branch.buf);
+ strbuf_release(&branch);
+ argv_array_clear(&argv);
+ return -1;
+ }
+ argv_array_clear(&argv);
+ }
+
+ strbuf_release(&branch);
+ return bisect_clean_state();
+}
+
int cmd_bisect__helper(int argc, const char **argv, const char *prefix)
{
enum {
NEXT_ALL = 1,
WRITE_TERMS,
- BISECT_CLEAN_STATE
+ BISECT_CLEAN_STATE,
+ BISECT_RESET
} cmdmode = 0;
int no_checkout = 0;
struct option options[] = {
@@ -138,6 +178,8 @@ int cmd_bisect__helper(int argc, const char **argv, const
char *prefix)
N_("write the terms to .git/BISECT_TERMS"),
WRITE_TERMS),
OPT_CMDMODE(0, "bisect-clean-state", &cmdmode,
N_("cleanup the bisection state"), BISECT_CLEAN_STATE),
+ OPT_CMDMODE(0, "bisect-reset", &cmdmode,
+N_("reset the bisection state"), BISECT_RESET),
OPT_BOOL(0, "no-checkout", &no_checkout,
N_("update BISECT_HEAD instead of checking out the
current commit")),
OPT_END()
@@ -160,6 +202,10 @@ int cmd_bisect__helper(int argc, const char **argv, const
char *prefix)
if (argc != 0)
die(_("--bisect-clean-state requires no arguments"));
return bisect_clean_state();
+ case BISECT_RESET:
+ if (argc > 1)
+ die(_("--bisect-reset requires either zero or one
arguments"));
+ return bisect_reset(argc ? argv[0] : NULL);
default:
die("BUG: unknown subcommand '%d'", cmdmode);
}
diff --git a/git-bisect.sh b/git-bisect.sh
index bbc57d2..18580b7 100755
--- a/git-bisect.sh
+++ b/git-bisect.sh
@@ -409,35 +409,11 @@ bisect_visualize() {
eval '"$@"' --bisect -- $(cat "$GIT_DIR/BISECT_NAMES")
}
-bisect_reset() {
- test -s "$GIT_DIR/BISECT_START" || {