diff options
-rw-r--r-- | .gitignore | 1 | ||||
-rw-r--r-- | src/reset.c | 66 | ||||
-rw-r--r-- | tests-clar/reset/soft.c | 25 |
3 files changed, 50 insertions, 42 deletions
diff --git a/.gitignore b/.gitignore index b81a1b13c..0289813c8 100644 --- a/.gitignore +++ b/.gitignore @@ -1,4 +1,5 @@ /tests-clar/clar.suite +/tests-clar/clar.suite.rule /tests-clar/.clarcache /apidocs /trash-*.exe diff --git a/src/reset.c b/src/reset.c index 784094a1f..04b0863b9 100644 --- a/src/reset.c +++ b/src/reset.c @@ -15,12 +15,6 @@ #define ERROR_MSG "Cannot perform reset" -static int reset_error_invalid(const char *msg) -{ - giterr_set(GITERR_INVALID, "%s - %s", ERROR_MSG, msg); - return -1; -} - static int update_head(git_repository *repo, git_object *commit) { int error; @@ -68,7 +62,7 @@ int git_reset( git_object *commit = NULL; git_index *index = NULL; git_tree *tree = NULL; - int error = -1; + int error; git_checkout_opts opts = GIT_CHECKOUT_OPTS_INIT; assert(repo && target); @@ -76,29 +70,33 @@ int git_reset( || reset_type == GIT_RESET_MIXED || reset_type == GIT_RESET_HARD); - if (git_object_owner(target) != repo) - return reset_error_invalid("The given target does not belong to this repository."); + if (git_object_owner(target) != repo) { + giterr_set(GITERR_OBJECT, + "%s - The given target does not belong to this repository.", ERROR_MSG); + return -1; + } if (reset_type != GIT_RESET_SOFT - && git_repository__ensure_not_bare( + && (error = git_repository__ensure_not_bare( repo, - reset_type == GIT_RESET_MIXED ? "reset mixed" : "reset hard") < 0) - return GIT_EBAREREPO; + reset_type == GIT_RESET_MIXED ? "reset mixed" : "reset hard")) < 0) + return error; - if (git_object_peel(&commit, target, GIT_OBJ_COMMIT) < 0) { - reset_error_invalid("The given target does not resolve to a commit"); + if ((error = git_object_peel(&commit, target, GIT_OBJ_COMMIT)) < 0) goto cleanup; - } - if (reset_type == GIT_RESET_SOFT && (git_repository_state(repo) == GIT_REPOSITORY_STATE_MERGE)) { - giterr_set(GITERR_OBJECT, "%s (soft) while in the middle of a merge.", ERROR_MSG); - error = GIT_EUNMERGED; + if ((error = git_repository_index(&index, repo)) < 0) goto cleanup; - } - //TODO: Check for unmerged entries + if (reset_type == GIT_RESET_SOFT && + (git_repository_state(repo) == GIT_REPOSITORY_STATE_MERGE || + git_index_has_conflicts(index))) { + giterr_set(GITERR_OBJECT, "%s (soft) while in the middle of a merge.", ERROR_MSG); + error = GIT_EUNMERGED; + goto cleanup; + } - if (update_head(repo, commit) < 0) + if ((error = update_head(repo, commit)) < 0) goto cleanup; if (reset_type == GIT_RESET_SOFT) { @@ -106,28 +104,17 @@ int git_reset( goto cleanup; } - if (git_commit_tree(&tree, (git_commit *)commit) < 0) { - giterr_set(GITERR_OBJECT, "%s - Failed to retrieve the commit tree.", ERROR_MSG); + if ((error = git_commit_tree(&tree, (git_commit *)commit)) < 0) goto cleanup; - } - if (git_repository_index(&index, repo) < 0) { - giterr_set(GITERR_OBJECT, "%s - Failed to retrieve the index.", ERROR_MSG); + if ((error = git_index_read_tree(index, tree)) < 0) goto cleanup; - } - if (git_index_read_tree(index, tree) < 0) { - giterr_set(GITERR_INDEX, "%s - Failed to update the index.", ERROR_MSG); + if ((error = git_index_write(index)) < 0) goto cleanup; - } - - if (git_index_write(index) < 0) { - giterr_set(GITERR_INDEX, "%s - Failed to write the index.", ERROR_MSG); - goto cleanup; - } if ((error = git_repository_merge_cleanup(repo)) < 0) { - giterr_set(GITERR_INDEX, "%s - Failed to clean up merge data.", ERROR_MSG); + giterr_set(GITERR_REPOSITORY, "%s - Failed to clean up merge data.", ERROR_MSG); goto cleanup; } @@ -138,12 +125,7 @@ int git_reset( opts.checkout_strategy = GIT_CHECKOUT_FORCE; - if (git_checkout_index(repo, NULL, &opts) < 0) { - giterr_set(GITERR_INDEX, "%s - Failed to checkout the index.", ERROR_MSG); - goto cleanup; - } - - error = 0; + error = git_checkout_index(repo, NULL, &opts); cleanup: git_object_free(commit); diff --git a/tests-clar/reset/soft.c b/tests-clar/reset/soft.c index 9ebd63763..884697c91 100644 --- a/tests-clar/reset/soft.c +++ b/tests-clar/reset/soft.c @@ -130,3 +130,28 @@ void test_reset_soft__fails_when_merging(void) git_buf_free(&merge_head_path); } + +void test_reset_soft__fails_when_index_contains_conflicts_independently_of_MERGE_HEAD_file_existence(void) +{ + git_index *index; + git_reference *head; + git_buf merge_head_path = GIT_BUF_INIT; + + cl_git_sandbox_cleanup(); + + repo = cl_git_sandbox_init("mergedrepo"); + + cl_git_pass(git_buf_joinpath(&merge_head_path, git_repository_path(repo), "MERGE_HEAD")); + cl_git_pass(p_unlink(git_buf_cstr(&merge_head_path))); + git_buf_free(&merge_head_path); + + cl_git_pass(git_repository_index(&index, repo)); + cl_assert_equal_i(true, git_index_has_conflicts(index)); + git_index_free(index); + + cl_git_pass(git_repository_head(&head, repo)); + cl_git_pass(git_reference_peel(&target, head, GIT_OBJ_COMMIT)); + git_reference_free(head); + + cl_assert_equal_i(GIT_EUNMERGED, git_reset(repo, target, GIT_RESET_SOFT)); +} |