]> git.proxmox.com Git - libgit2.git/commitdiff
rebase: take `checkout_options` where appropriate
authorEdward Thomson <ethomson@microsoft.com>
Tue, 17 Mar 2015 15:47:16 +0000 (11:47 -0400)
committerEdward Thomson <ethomson@microsoft.com>
Mon, 20 Apr 2015 20:22:49 +0000 (16:22 -0400)
include/git2/rebase.h
src/rebase.c
tests/rebase/abort.c
tests/rebase/iterator.c
tests/rebase/merge.c
tests/rebase/setup.c

index 3d8d180a51852e09165e5e39c032c08a48c43472..8171682e401d6823ecbe89a929da71da83337d5b 100644 (file)
@@ -143,6 +143,8 @@ GIT_EXTERN(int) git_rebase_init_options(
  * @param onto The branch to rebase onto, or NULL to rebase onto the given
  *             upstream
  * @param opts Options to specify how rebase is performed
+ * @param checkout_opts Options to specify how the checkout to the `onto`
+ *                      branch is performed
  * @return Zero on success; -1 on failure.
  */
 GIT_EXTERN(int) git_rebase_init(
@@ -151,7 +153,8 @@ GIT_EXTERN(int) git_rebase_init(
        const git_annotated_commit *branch,
        const git_annotated_commit *upstream,
        const git_annotated_commit *onto,
-       const git_rebase_options *opts);
+       const git_rebase_options *opts,
+       const git_checkout_options *checkout_opts);
 
 /**
  * Opens an existing rebase that was previously started by either an
@@ -245,10 +248,14 @@ GIT_EXTERN(int) git_rebase_commit(
  * and working directory to their state before rebase began.
  *
  * @param rebase The rebase that is in-progress
+ * @param checkout_opts The checkout options that will be used to influence a
+ *                      hard reset of the working directory.
  * @return Zero on success; GIT_ENOTFOUND if a rebase is not in progress,
  *         -1 on other errors.
  */
-GIT_EXTERN(int) git_rebase_abort(git_rebase *rebase);
+GIT_EXTERN(int) git_rebase_abort(
+       git_rebase *rebase,
+       const git_checkout_options *checkout_opts);
 
 /**
  * Finishes a rebase that is currently in progress once all patches have
index f8f4a1b339b34b7ba793758b09d03fadf357ffa8..c51bf6094ae4a8e1ae406a116372cf79c4352e30 100644 (file)
@@ -658,19 +658,37 @@ done:
        return error;
 }
 
+static void normalize_checkout_opts(
+       git_checkout_options *checkout_opts,
+       const git_checkout_options *given_checkout_opts)
+{
+       if (given_checkout_opts != NULL)
+               memcpy(checkout_opts, given_checkout_opts, sizeof(git_checkout_options));
+       else {
+               git_checkout_options default_checkout_opts = GIT_CHECKOUT_OPTIONS_INIT;
+               default_checkout_opts.checkout_strategy =  GIT_CHECKOUT_SAFE;
+
+               memcpy(checkout_opts, &default_checkout_opts, sizeof(git_checkout_options));
+       }
+
+       if (! (checkout_opts->checkout_strategy & (GIT_CHECKOUT_SAFE | GIT_CHECKOUT_FORCE)))
+               checkout_opts->checkout_strategy |= GIT_CHECKOUT_SAFE;
+}
+
 int git_rebase_init(
        git_rebase **out,
        git_repository *repo,
        const git_annotated_commit *branch,
        const git_annotated_commit *upstream,
        const git_annotated_commit *onto,
-       const git_rebase_options *given_opts)
+       const git_rebase_options *given_opts,
+       const git_checkout_options *given_checkout_opts)
 {
        git_rebase *rebase = NULL;
        git_rebase_options opts;
        git_buf reflog = GIT_BUF_INIT;
        git_commit *onto_commit = NULL;
-       git_checkout_options checkout_opts = GIT_CHECKOUT_OPTIONS_INIT;
+       git_checkout_options checkout_opts;
        git_reference *head_ref = NULL;
        int error;
 
@@ -679,11 +697,12 @@ int git_rebase_init(
        *out = NULL;
 
        GITERR_CHECK_VERSION(given_opts, GIT_REBASE_OPTIONS_VERSION, "git_rebase_options");
+       GITERR_CHECK_VERSION(given_checkout_opts, GIT_CHECKOUT_OPTIONS_VERSION, "git_checkout_options");
 
        if (!onto)
                onto = upstream;
 
-       checkout_opts.checkout_strategy = GIT_CHECKOUT_SAFE;
+       normalize_checkout_opts(&checkout_opts, given_checkout_opts);
 
        if ((error = rebase_normalize_opts(repo, &opts, given_opts)) < 0 ||
                (error = git_repository__ensure_not_bare(repo, "rebase")) < 0 ||
@@ -723,20 +742,13 @@ done:
        return error;
 }
 
-static void normalize_checkout_opts(
+static void normalize_checkout_opts_for_apply(
        git_rebase *rebase,
        git_commit *current_commit,
        git_checkout_options *checkout_opts,
        const git_checkout_options *given_checkout_opts)
 {
-       if (given_checkout_opts != NULL)
-               memcpy(checkout_opts, given_checkout_opts, sizeof(git_checkout_options));
-       else {
-               git_checkout_options default_checkout_opts = GIT_CHECKOUT_OPTIONS_INIT;
-               default_checkout_opts.checkout_strategy =  GIT_CHECKOUT_SAFE;
-
-               memcpy(checkout_opts, &default_checkout_opts, sizeof(git_checkout_options));
-       }
+       normalize_checkout_opts(checkout_opts, given_checkout_opts);
 
        if (!checkout_opts->ancestor_label)
                checkout_opts->ancestor_label = "ancestor";
@@ -805,7 +817,7 @@ static int rebase_next_merge(
 
        git_oid_fmt(current_idstr, &operation->id);
 
-       normalize_checkout_opts(rebase, current_commit, &checkout_opts, given_checkout_opts);
+       normalize_checkout_opts_for_apply(rebase, current_commit, &checkout_opts, given_checkout_opts);
 
        if ((error = git_indexwriter_init_for_operation(&indexwriter, rebase->repo, &checkout_opts.checkout_strategy)) < 0 ||
                (error = rebase_setupfile(rebase, MSGNUM_FILE, -1, "%d\n", rebase->current+1)) < 0 ||
@@ -960,7 +972,9 @@ int git_rebase_commit(
        return error;
 }
 
-int git_rebase_abort(git_rebase *rebase)
+int git_rebase_abort(
+       git_rebase *rebase,
+       const git_checkout_options *checkout_opts)
 {
        git_reference *orig_head_ref = NULL;
        git_commit *orig_head_commit = NULL;
@@ -981,7 +995,7 @@ int git_rebase_abort(git_rebase *rebase)
        if ((error = git_commit_lookup(
                        &orig_head_commit, rebase->repo, &rebase->orig_head_id)) < 0 ||
                (error = git_reset(rebase->repo, (git_object *)orig_head_commit,
-                       GIT_RESET_HARD, NULL)) < 0)
+                       GIT_RESET_HARD, checkout_opts)) < 0)
                goto done;
 
        error = rebase_cleanup(rebase);
index 24af2d140573726a7638c1535e360fd561e61b14..a04a34b5c03787d1d3c7f544b51d761154824835 100644 (file)
@@ -28,7 +28,7 @@ static void test_abort(git_annotated_commit *branch, git_annotated_commit *onto)
        const git_reflog_entry *reflog_entry;
 
        cl_git_pass(git_rebase_open(&rebase, repo));
-       cl_git_pass(git_rebase_abort(rebase));
+       cl_git_pass(git_rebase_abort(rebase, NULL));
 
        cl_assert_equal_i(GIT_REPOSITORY_STATE_NONE, git_repository_state(repo));
 
@@ -73,7 +73,7 @@ void test_rebase_abort__merge(void)
        cl_git_pass(git_annotated_commit_from_ref(&branch_head, repo, branch_ref));
        cl_git_pass(git_annotated_commit_from_ref(&onto_head, repo, onto_ref));
 
-       cl_git_pass(git_rebase_init(&rebase, repo, branch_head, NULL, onto_head, NULL));
+       cl_git_pass(git_rebase_init(&rebase, repo, branch_head, NULL, onto_head, NULL, NULL));
        cl_assert_equal_i(GIT_REPOSITORY_STATE_REBASE_MERGE, git_repository_state(repo));
 
        test_abort(branch_head, onto_head);
@@ -102,7 +102,7 @@ void test_rebase_abort__detached_head(void)
 
        cl_git_pass(git_signature_new(&signature, "Rebaser", "rebaser@example.com", 1404157834, -400));
 
-       cl_git_pass(git_rebase_init(&rebase, repo, branch_head, NULL, onto_head, NULL));
+       cl_git_pass(git_rebase_init(&rebase, repo, branch_head, NULL, onto_head, NULL, NULL));
        cl_assert_equal_i(GIT_REPOSITORY_STATE_REBASE_MERGE, git_repository_state(repo));
 
        test_abort(branch_head, onto_head);
@@ -131,7 +131,7 @@ void test_rebase_abort__old_style_head_file(void)
 
        cl_git_pass(git_signature_new(&signature, "Rebaser", "rebaser@example.com", 1404157834, -400));
 
-       cl_git_pass(git_rebase_init(&rebase, repo, branch_head, NULL, onto_head, NULL));
+       cl_git_pass(git_rebase_init(&rebase, repo, branch_head, NULL, onto_head, NULL, NULL));
        cl_assert_equal_i(GIT_REPOSITORY_STATE_REBASE_MERGE, git_repository_state(repo));
 
        p_rename("rebase-merge/.git/rebase-merge/orig-head",
index 23272d51c2aa3652b372311917d7150a95c8bde2..d2f4278ccc5b6944df0468867c1f1030a2d281f0 100644 (file)
@@ -64,7 +64,7 @@ void test_rebase_iterator__iterates(void)
        cl_git_pass(git_annotated_commit_from_ref(&branch_head, repo, branch_ref));
        cl_git_pass(git_annotated_commit_from_ref(&upstream_head, repo, upstream_ref));
 
-       cl_git_pass(git_rebase_init(&rebase, repo, branch_head, upstream_head, NULL, NULL));
+       cl_git_pass(git_rebase_init(&rebase, repo, branch_head, upstream_head, NULL, NULL, NULL));
        test_operations(rebase, GIT_REBASE_NO_OPERATION);
        git_rebase_free(rebase);
 
index 02c39609e1db59423e9d3a7de35b5b91441db549..ade6f5cf67f402c5c87bdd8af8a6f1fcbcded1c9 100644 (file)
@@ -53,7 +53,7 @@ void test_rebase_merge__next(void)
        cl_git_pass(git_annotated_commit_from_ref(&branch_head, repo, branch_ref));
        cl_git_pass(git_annotated_commit_from_ref(&upstream_head, repo, upstream_ref));
 
-       cl_git_pass(git_rebase_init(&rebase, repo, branch_head, upstream_head, NULL, NULL));
+       cl_git_pass(git_rebase_init(&rebase, repo, branch_head, upstream_head, NULL, NULL, NULL));
 
        cl_git_pass(git_rebase_next(&rebase_operation, rebase, &checkout_opts));
 
@@ -120,7 +120,7 @@ void test_rebase_merge__next_with_conflicts(void)
        cl_git_pass(git_annotated_commit_from_ref(&branch_head, repo, branch_ref));
        cl_git_pass(git_annotated_commit_from_ref(&upstream_head, repo, upstream_ref));
 
-       cl_git_pass(git_rebase_init(&rebase, repo, branch_head, upstream_head, NULL, NULL));
+       cl_git_pass(git_rebase_init(&rebase, repo, branch_head, upstream_head, NULL, NULL, NULL));
 
        cl_git_pass(git_rebase_next(&rebase_operation, rebase, &checkout_opts));
 
@@ -167,7 +167,7 @@ void test_rebase_merge__next_stops_with_iterover(void)
        cl_git_pass(git_annotated_commit_from_ref(&branch_head, repo, branch_ref));
        cl_git_pass(git_annotated_commit_from_ref(&upstream_head, repo, upstream_ref));
 
-       cl_git_pass(git_rebase_init(&rebase, repo, branch_head, upstream_head, NULL, NULL));
+       cl_git_pass(git_rebase_init(&rebase, repo, branch_head, upstream_head, NULL, NULL, NULL));
 
        cl_git_pass(git_rebase_next(&rebase_operation, rebase, &checkout_opts));
        cl_git_pass(git_rebase_commit(&commit_id, rebase, NULL, signature,
@@ -223,7 +223,7 @@ void test_rebase_merge__commit(void)
        cl_git_pass(git_annotated_commit_from_ref(&branch_head, repo, branch_ref));
        cl_git_pass(git_annotated_commit_from_ref(&upstream_head, repo, upstream_ref));
 
-       cl_git_pass(git_rebase_init(&rebase, repo, branch_head, upstream_head, NULL, NULL));
+       cl_git_pass(git_rebase_init(&rebase, repo, branch_head, upstream_head, NULL, NULL, NULL));
 
        cl_git_pass(git_rebase_next(&rebase_operation, rebase, &checkout_opts));
        cl_git_pass(git_rebase_commit(&commit_id, rebase, NULL, signature,
@@ -316,7 +316,7 @@ void test_rebase_merge__commit_updates_rewritten(void)
        cl_git_pass(git_annotated_commit_from_ref(&branch_head, repo, branch_ref));
        cl_git_pass(git_annotated_commit_from_ref(&upstream_head, repo, upstream_ref));
 
-       cl_git_pass(git_rebase_init(&rebase, repo, branch_head, upstream_head, NULL, NULL));
+       cl_git_pass(git_rebase_init(&rebase, repo, branch_head, upstream_head, NULL, NULL, NULL));
 
        cl_git_pass(git_rebase_next(&rebase_operation, rebase, &checkout_opts));
        cl_git_pass(git_rebase_commit(&commit_id, rebase, NULL, signature,
@@ -356,7 +356,7 @@ void test_rebase_merge__commit_drops_already_applied(void)
        cl_git_pass(git_annotated_commit_from_ref(&branch_head, repo, branch_ref));
        cl_git_pass(git_annotated_commit_from_ref(&upstream_head, repo, upstream_ref));
 
-       cl_git_pass(git_rebase_init(&rebase, repo, branch_head, upstream_head, NULL, NULL));
+       cl_git_pass(git_rebase_init(&rebase, repo, branch_head, upstream_head, NULL, NULL, NULL));
 
        cl_git_pass(git_rebase_next(&rebase_operation, rebase, &checkout_opts));
        cl_git_fail(error = git_rebase_commit(&commit_id, rebase, NULL, signature,
@@ -399,7 +399,7 @@ void test_rebase_merge__finish(void)
        cl_git_pass(git_annotated_commit_from_ref(&branch_head, repo, branch_ref));
        cl_git_pass(git_annotated_commit_from_ref(&upstream_head, repo, upstream_ref));
 
-       cl_git_pass(git_rebase_init(&rebase, repo, branch_head, upstream_head, NULL, NULL));
+       cl_git_pass(git_rebase_init(&rebase, repo, branch_head, upstream_head, NULL, NULL, NULL));
 
        cl_git_pass(git_rebase_next(&rebase_operation, rebase, &checkout_opts));
        cl_git_pass(git_rebase_commit(&commit_id, rebase, NULL, signature,
@@ -470,7 +470,7 @@ static void test_copy_note(
                git_commit_id(branch_commit),
                "This is a commit note.", 0));
 
-       cl_git_pass(git_rebase_init(&rebase, repo, branch_head, upstream_head, NULL, opts));
+       cl_git_pass(git_rebase_init(&rebase, repo, branch_head, upstream_head, NULL, opts, NULL));
 
        cl_git_pass(git_rebase_next(&rebase_operation, rebase, &checkout_opts));
        cl_git_pass(git_rebase_commit(&commit_id, rebase, NULL, signature,
index 627d3b9de47008d087a5b79fbfdc94915afddd03..61d886978b28bba9d356a54271b3a1dfaaa1011c 100644 (file)
@@ -39,12 +39,12 @@ void test_rebase_setup__blocked_when_in_progress(void)
        cl_git_pass(git_annotated_commit_from_ref(&branch_head, repo, branch_ref));
        cl_git_pass(git_annotated_commit_from_ref(&upstream_head, repo, upstream_ref));
 
-       cl_git_pass(git_rebase_init(&rebase, repo, branch_head, upstream_head, NULL, NULL));
+       cl_git_pass(git_rebase_init(&rebase, repo, branch_head, upstream_head, NULL, NULL, NULL));
        git_rebase_free(rebase);
 
        cl_assert_equal_i(GIT_REPOSITORY_STATE_REBASE_MERGE, git_repository_state(repo));
 
-       cl_git_fail(git_rebase_init(&rebase, repo, branch_head, upstream_head, NULL, NULL));
+       cl_git_fail(git_rebase_init(&rebase, repo, branch_head, upstream_head, NULL, NULL, NULL));
 
        git_annotated_commit_free(branch_head);
        git_annotated_commit_free(upstream_head);
@@ -70,7 +70,7 @@ void test_rebase_setup__merge(void)
        cl_git_pass(git_annotated_commit_from_ref(&branch_head, repo, branch_ref));
        cl_git_pass(git_annotated_commit_from_ref(&upstream_head, repo, upstream_ref));
 
-       cl_git_pass(git_rebase_init(&rebase, repo, branch_head, upstream_head, NULL, NULL));
+       cl_git_pass(git_rebase_init(&rebase, repo, branch_head, upstream_head, NULL, NULL, NULL));
 
        cl_assert_equal_i(GIT_REPOSITORY_STATE_REBASE_MERGE, git_repository_state(repo));
 
@@ -118,7 +118,7 @@ void test_rebase_setup__merge_root(void)
        cl_git_pass(git_annotated_commit_from_ref(&branch_head, repo, branch_ref));
        cl_git_pass(git_annotated_commit_from_ref(&onto_head, repo, onto_ref));
 
-       cl_git_pass(git_rebase_init(&rebase, repo, branch_head, NULL, onto_head, NULL));
+       cl_git_pass(git_rebase_init(&rebase, repo, branch_head, NULL, onto_head, NULL, NULL));
 
        git_oid_fromstr(&head_id, "efad0b11c47cb2f0220cbd6f5b0f93bb99064b00");
        cl_git_pass(git_repository_head(&head, repo));
@@ -168,7 +168,7 @@ void test_rebase_setup__merge_onto_and_upstream(void)
        cl_git_pass(git_annotated_commit_from_ref(&branch2_head, repo, branch2_ref));
        cl_git_pass(git_annotated_commit_from_ref(&onto_head, repo, onto_ref));
 
-       cl_git_pass(git_rebase_init(&rebase, repo, branch1_head, branch2_head, onto_head, NULL));
+       cl_git_pass(git_rebase_init(&rebase, repo, branch1_head, branch2_head, onto_head, NULL, NULL));
 
        git_oid_fromstr(&head_id, "efad0b11c47cb2f0220cbd6f5b0f93bb99064b00");
        cl_git_pass(git_repository_head(&head, repo));
@@ -215,7 +215,7 @@ void test_rebase_setup__branch_with_merges(void)
        cl_git_pass(git_annotated_commit_from_ref(&branch_head, repo, branch_ref));
        cl_git_pass(git_annotated_commit_from_ref(&upstream_head, repo, upstream_ref));
 
-       cl_git_pass(git_rebase_init(&rebase, repo, branch_head, upstream_head, NULL, NULL));
+       cl_git_pass(git_rebase_init(&rebase, repo, branch_head, upstream_head, NULL, NULL, NULL));
 
        cl_assert_equal_i(GIT_REPOSITORY_STATE_REBASE_MERGE, git_repository_state(repo));
 
@@ -263,7 +263,7 @@ void test_rebase_setup__orphan_branch(void)
        cl_git_pass(git_annotated_commit_from_ref(&branch_head, repo, branch_ref));
        cl_git_pass(git_annotated_commit_from_ref(&upstream_head, repo, upstream_ref));
 
-       cl_git_pass(git_rebase_init(&rebase, repo, branch_head, upstream_head, NULL, NULL));
+       cl_git_pass(git_rebase_init(&rebase, repo, branch_head, upstream_head, NULL, NULL, NULL));
 
        cl_assert_equal_i(GIT_REPOSITORY_STATE_REBASE_MERGE, git_repository_state(repo));
 
@@ -314,7 +314,7 @@ void test_rebase_setup__merge_null_branch_uses_HEAD(void)
        cl_git_pass(git_reference_lookup(&upstream_ref, repo, "refs/heads/master"));
        cl_git_pass(git_annotated_commit_from_ref(&upstream_head, repo, upstream_ref));
 
-       cl_git_pass(git_rebase_init(&rebase, repo, NULL, upstream_head, NULL, NULL));
+       cl_git_pass(git_rebase_init(&rebase, repo, NULL, upstream_head, NULL, NULL, NULL));
 
        cl_assert_equal_i(GIT_REPOSITORY_STATE_REBASE_MERGE, git_repository_state(repo));
 
@@ -358,7 +358,7 @@ static int rebase_is_blocked(void)
        cl_git_pass(git_annotated_commit_from_ref(&branch_head, repo, branch_ref));
        cl_git_pass(git_annotated_commit_from_ref(&upstream_head, repo, upstream_ref));
                                                                                                    
-       error = git_rebase_init(&rebase, repo, branch_head, upstream_head, NULL, NULL);
+       error = git_rebase_init(&rebase, repo, branch_head, upstream_head, NULL, NULL, NULL);
 
        git_annotated_commit_free(branch_head);
        git_annotated_commit_free(upstream_head);