summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorLibravatar Pratik Karki <predatoramigo@gmail.com>2018-09-04 14:59:49 -0700
committerLibravatar Junio C Hamano <gitster@pobox.com>2018-09-06 11:56:19 -0700
commit361badd3933c5c319229896f2ad2d546d95cd8a7 (patch)
tree537849d53088af6762afaf508ac37340af5ad5dd
parentbuiltin rebase: stop if `git am` is in progress (diff)
downloadtgif-361badd3933c5c319229896f2ad2d546d95cd8a7.tar.xz
builtin rebase: allow selecting the rebase "backend"
With this commit the builtin rebase supports selecting the "rebase backends" (or "type") `interactive`, `preserve-merges`, and `merge`. The `state_dir` was already handled according to the rebase type in a previous commit. Note that there is one quirk in the shell script: `--interactive` followed by `--merge` won't reset the type to "merge" but keeps the type as "interactive". And as t3418 tests this explicitly, we have to support it in the builtin rebase, too. Likewise, `--interactive` followed by `--preserve-merges` makes it an "explicitly interactive" rebase, i.e. a rebase that should show the todo list, while `--preserve-merges` alone is not interactive (and t5520 tests for this via `git pull --rebase=preserve`). Signed-off-by: Pratik Karki <predatoramigo@gmail.com> Signed-off-by: Johannes Schindelin <johannes.schindelin@gmx.de> Signed-off-by: Junio C Hamano <gitster@pobox.com>
-rw-r--r--builtin/rebase.c37
1 files changed, 37 insertions, 0 deletions
diff --git a/builtin/rebase.c b/builtin/rebase.c
index 2165656ae2..61695ac7b9 100644
--- a/builtin/rebase.c
+++ b/builtin/rebase.c
@@ -452,6 +452,29 @@ static int can_fast_forward(struct commit *onto, struct object_id *head_oid,
return res && is_linear_history(onto, head);
}
+/* -i followed by -m is still -i */
+static int parse_opt_merge(const struct option *opt, const char *arg, int unset)
+{
+ struct rebase_options *opts = opt->value;
+
+ if (!is_interactive(opts))
+ opts->type = REBASE_MERGE;
+
+ return 0;
+}
+
+/* -i followed by -p is still explicitly interactive, but -p alone is not */
+static int parse_opt_interactive(const struct option *opt, const char *arg,
+ int unset)
+{
+ struct rebase_options *opts = opt->value;
+
+ opts->type = REBASE_INTERACTIVE;
+ opts->flags |= REBASE_INTERACTIVE_EXPLICIT;
+
+ return 0;
+}
+
int cmd_rebase(int argc, const char **argv, const char *prefix)
{
struct rebase_options options = {
@@ -510,6 +533,17 @@ int cmd_rebase(int argc, const char **argv, const char *prefix)
OPT_CMDMODE(0, "show-current-patch", &action,
N_("show the patch file being applied or merged"),
ACTION_SHOW_CURRENT_PATCH),
+ { OPTION_CALLBACK, 'm', "merge", &options, NULL,
+ N_("use merging strategies to rebase"),
+ PARSE_OPT_NOARG | PARSE_OPT_NONEG,
+ parse_opt_merge },
+ { OPTION_CALLBACK, 'i', "interactive", &options, NULL,
+ N_("let the user edit the list of commits to rebase"),
+ PARSE_OPT_NOARG | PARSE_OPT_NONEG,
+ parse_opt_interactive },
+ OPT_SET_INT('p', "preserve-merges", &options.type,
+ N_("try to recreate merges instead of ignoring "
+ "them"), REBASE_PRESERVE_MERGES),
OPT_END(),
};
@@ -884,6 +918,9 @@ int cmd_rebase(int argc, const char **argv, const char *prefix)
diff_flush(&opts);
}
+ if (is_interactive(&options))
+ goto run_rebase;
+
/* Detach HEAD and reset the tree */
if (options.flags & REBASE_NO_QUIET)
printf(_("First, rewinding head to replay your work on top of "