mirror of
https://git.proxmox.com/git/libgit2
synced 2025-06-18 06:59:07 +00:00
Add git_merge_bases_many.
This commit is contained in:
parent
9f57fd6443
commit
eca07bcd83
@ -58,3 +58,6 @@ v0.21 + 1
|
||||
|
||||
* Introduce git_merge_bases() and the git_oidarray type to expose all
|
||||
merge bases between two commits.
|
||||
|
||||
* Introduce git_merge_bases_many() to expose all merge bases between
|
||||
multiple commits.
|
||||
|
@ -351,6 +351,21 @@ GIT_EXTERN(int) git_merge_base_many(
|
||||
size_t length,
|
||||
const git_oid input_array[]);
|
||||
|
||||
/**
|
||||
* Find all merge bases given a list of commits
|
||||
*
|
||||
* @param out array in which to store the resulting ids
|
||||
* @param repo the repository where the commits exist
|
||||
* @param length The number of commits in the provided `input_array`
|
||||
* @param input_array oids of the commits
|
||||
* @return Zero on success; GIT_ENOTFOUND or -1 on failure.
|
||||
*/
|
||||
GIT_EXTERN(int) git_merge_bases_many(
|
||||
git_oidarray *out,
|
||||
git_repository *repo,
|
||||
size_t length,
|
||||
const git_oid input_array[]);
|
||||
|
||||
/**
|
||||
* Find a merge base in preparation for an octopus merge
|
||||
*
|
||||
|
67
src/merge.c
67
src/merge.c
@ -116,6 +116,73 @@ cleanup:
|
||||
return error;
|
||||
}
|
||||
|
||||
int git_merge_bases_many(git_oidarray *out, git_repository *repo, size_t length, const git_oid input_array[])
|
||||
{
|
||||
git_revwalk *walk;
|
||||
git_vector list;
|
||||
git_commit_list *current, *result = NULL;
|
||||
int error = -1;
|
||||
unsigned int i;
|
||||
git_commit_list_node *commit;
|
||||
git_array_oid_t array;
|
||||
|
||||
assert(out && repo && input_array);
|
||||
|
||||
if (length < 2) {
|
||||
giterr_set(GITERR_INVALID, "At least two commits are required to find an ancestor. Provided 'length' was %u.", length);
|
||||
return -1;
|
||||
}
|
||||
|
||||
if (git_vector_init(&list, length - 1, NULL) < 0)
|
||||
return -1;
|
||||
|
||||
if (git_revwalk_new(&walk, repo) < 0)
|
||||
goto cleanup;
|
||||
|
||||
for (i = 1; i < length; i++) {
|
||||
commit = git_revwalk__commit_lookup(walk, &input_array[i]);
|
||||
if (commit == NULL)
|
||||
goto cleanup;
|
||||
|
||||
git_vector_insert(&list, commit);
|
||||
}
|
||||
|
||||
commit = git_revwalk__commit_lookup(walk, &input_array[0]);
|
||||
if (commit == NULL)
|
||||
goto cleanup;
|
||||
|
||||
if (git_merge__bases_many(&result, walk, commit, &list) < 0)
|
||||
goto cleanup;
|
||||
|
||||
if (!result) {
|
||||
giterr_set(GITERR_MERGE, "No merge base found");
|
||||
error = GIT_ENOTFOUND;
|
||||
goto cleanup;
|
||||
}
|
||||
|
||||
git_array_init(array);
|
||||
|
||||
current = result;
|
||||
while (current) {
|
||||
git_oid *id = git_array_alloc(array);
|
||||
if (id == NULL)
|
||||
goto cleanup;
|
||||
|
||||
git_oid_cpy(id, ¤t->item->oid);
|
||||
current = current->next;
|
||||
}
|
||||
|
||||
git_oidarray__from_array(out, &array);
|
||||
|
||||
error = 0;
|
||||
|
||||
cleanup:
|
||||
git_commit_list_free(&result);
|
||||
git_revwalk_free(walk);
|
||||
git_vector_free(&list);
|
||||
return error;
|
||||
}
|
||||
|
||||
int git_merge_base_octopus(git_oid *out, git_repository *repo, size_t length, const git_oid input_array[])
|
||||
{
|
||||
git_oid result;
|
||||
|
@ -127,7 +127,7 @@ void test_revwalk_mergebase__prefer_youngest_merge_base(void)
|
||||
{
|
||||
git_oid result, one, two, expected;
|
||||
|
||||
cl_git_pass(git_oid_fromstr(&one, "a4a7dce85cf63874e984719f4fdd239f5145052f "));
|
||||
cl_git_pass(git_oid_fromstr(&one, "a4a7dce85cf63874e984719f4fdd239f5145052f"));
|
||||
cl_git_pass(git_oid_fromstr(&two, "be3563ae3f795b2b4353bcce3a527ad0a4f7f644"));
|
||||
cl_git_pass(git_oid_fromstr(&expected, "c47800c7266a2be04c571c04d5a6614691ea99bd"));
|
||||
|
||||
@ -140,7 +140,7 @@ void test_revwalk_mergebase__multiple_merge_bases(void)
|
||||
git_oid one, two, expected1, expected2;
|
||||
git_oidarray result = {NULL, 0};
|
||||
|
||||
cl_git_pass(git_oid_fromstr(&one, "a4a7dce85cf63874e984719f4fdd239f5145052f "));
|
||||
cl_git_pass(git_oid_fromstr(&one, "a4a7dce85cf63874e984719f4fdd239f5145052f"));
|
||||
cl_git_pass(git_oid_fromstr(&two, "be3563ae3f795b2b4353bcce3a527ad0a4f7f644"));
|
||||
cl_git_pass(git_oid_fromstr(&expected1, "c47800c7266a2be04c571c04d5a6614691ea99bd"));
|
||||
cl_git_pass(git_oid_fromstr(&expected2, "9fd738e8f7967c078dceed8190330fc8648ee56a"));
|
||||
@ -153,6 +153,26 @@ void test_revwalk_mergebase__multiple_merge_bases(void)
|
||||
git_oidarray_free(&result);
|
||||
}
|
||||
|
||||
void test_revwalk_mergebase__multiple_merge_bases_many_commits(void)
|
||||
{
|
||||
git_oid expected1, expected2;
|
||||
git_oidarray result = {NULL, 0};
|
||||
|
||||
git_oid *input = git__malloc(sizeof(git_oid) * 2);
|
||||
|
||||
cl_git_pass(git_oid_fromstr(&input[0], "a4a7dce85cf63874e984719f4fdd239f5145052f"));
|
||||
cl_git_pass(git_oid_fromstr(&input[1], "be3563ae3f795b2b4353bcce3a527ad0a4f7f644"));
|
||||
cl_git_pass(git_oid_fromstr(&expected1, "c47800c7266a2be04c571c04d5a6614691ea99bd"));
|
||||
cl_git_pass(git_oid_fromstr(&expected2, "9fd738e8f7967c078dceed8190330fc8648ee56a"));
|
||||
|
||||
cl_git_pass(git_merge_bases_many(&result, _repo, 2, input));
|
||||
cl_assert_equal_i(2, result.count);
|
||||
cl_assert_equal_oid(&expected1, &result.ids[0]);
|
||||
cl_assert_equal_oid(&expected2, &result.ids[1]);
|
||||
|
||||
git_oidarray_free(&result);
|
||||
}
|
||||
|
||||
void test_revwalk_mergebase__no_off_by_one_missing(void)
|
||||
{
|
||||
git_oid result, one, two;
|
||||
|
Loading…
Reference in New Issue
Block a user