mirror of
https://git.proxmox.com/git/libgit2
synced 2025-07-17 17:48:15 +00:00
Merge pull request #2178 from libgit2/rb/fix-short-id
Fix git_odb_short_id and git_odb_exists_prefix bugs
This commit is contained in:
commit
3ab5781601
24
src/odb.c
24
src/odb.c
@ -640,7 +640,7 @@ int git_odb_exists_prefix(
|
|||||||
{
|
{
|
||||||
int error = GIT_ENOTFOUND, num_found = 0;
|
int error = GIT_ENOTFOUND, num_found = 0;
|
||||||
size_t i;
|
size_t i;
|
||||||
git_oid last_found = {{0}}, found;
|
git_oid key = {{0}}, last_found = {{0}}, found;
|
||||||
|
|
||||||
assert(db && short_id);
|
assert(db && short_id);
|
||||||
|
|
||||||
@ -659,6 +659,11 @@ int git_odb_exists_prefix(
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* just copy valid part of short_id */
|
||||||
|
memcpy(&key.id, short_id->id, (len + 1) / 2);
|
||||||
|
if (len & 1)
|
||||||
|
key.id[len / 2] &= 0xF0;
|
||||||
|
|
||||||
for (i = 0; i < db->backends.length; ++i) {
|
for (i = 0; i < db->backends.length; ++i) {
|
||||||
backend_internal *internal = git_vector_get(&db->backends, i);
|
backend_internal *internal = git_vector_get(&db->backends, i);
|
||||||
git_odb_backend *b = internal->backend;
|
git_odb_backend *b = internal->backend;
|
||||||
@ -666,7 +671,7 @@ int git_odb_exists_prefix(
|
|||||||
if (!b->exists_prefix)
|
if (!b->exists_prefix)
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
error = b->exists_prefix(&found, b, short_id, len);
|
error = b->exists_prefix(&found, b, &key, len);
|
||||||
if (error == GIT_ENOTFOUND || error == GIT_PASSTHROUGH)
|
if (error == GIT_ENOTFOUND || error == GIT_PASSTHROUGH)
|
||||||
continue;
|
continue;
|
||||||
if (error)
|
if (error)
|
||||||
@ -683,11 +688,11 @@ int git_odb_exists_prefix(
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (!num_found)
|
if (!num_found)
|
||||||
return git_odb__error_notfound("no match for id prefix", short_id);
|
return git_odb__error_notfound("no match for id prefix", &key);
|
||||||
if (out)
|
if (out)
|
||||||
git_oid_cpy(out, &last_found);
|
git_oid_cpy(out, &last_found);
|
||||||
|
|
||||||
return error;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
int git_odb_read_header(size_t *len_p, git_otype *type_p, git_odb *db, const git_oid *id)
|
int git_odb_read_header(size_t *len_p, git_otype *type_p, git_odb *db, const git_oid *id)
|
||||||
@ -790,7 +795,7 @@ int git_odb_read_prefix(
|
|||||||
{
|
{
|
||||||
size_t i;
|
size_t i;
|
||||||
int error = GIT_ENOTFOUND;
|
int error = GIT_ENOTFOUND;
|
||||||
git_oid found_full_oid = {{0}};
|
git_oid key = {{0}}, found_full_oid = {{0}};
|
||||||
git_rawobj raw;
|
git_rawobj raw;
|
||||||
void *data = NULL;
|
void *data = NULL;
|
||||||
bool found = false;
|
bool found = false;
|
||||||
@ -809,13 +814,18 @@ int git_odb_read_prefix(
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* just copy valid part of short_id */
|
||||||
|
memcpy(&key.id, short_id->id, (len + 1) / 2);
|
||||||
|
if (len & 1)
|
||||||
|
key.id[len / 2] &= 0xF0;
|
||||||
|
|
||||||
for (i = 0; i < db->backends.length; ++i) {
|
for (i = 0; i < db->backends.length; ++i) {
|
||||||
backend_internal *internal = git_vector_get(&db->backends, i);
|
backend_internal *internal = git_vector_get(&db->backends, i);
|
||||||
git_odb_backend *b = internal->backend;
|
git_odb_backend *b = internal->backend;
|
||||||
|
|
||||||
if (b->read_prefix != NULL) {
|
if (b->read_prefix != NULL) {
|
||||||
git_oid full_oid;
|
git_oid full_oid;
|
||||||
error = b->read_prefix(&full_oid, &raw.data, &raw.len, &raw.type, b, short_id, len);
|
error = b->read_prefix(&full_oid, &raw.data, &raw.len, &raw.type, b, &key, len);
|
||||||
if (error == GIT_ENOTFOUND || error == GIT_PASSTHROUGH)
|
if (error == GIT_ENOTFOUND || error == GIT_PASSTHROUGH)
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
@ -836,7 +846,7 @@ int git_odb_read_prefix(
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (!found)
|
if (!found)
|
||||||
return git_odb__error_notfound("no match for prefix", short_id);
|
return git_odb__error_notfound("no match for prefix", &key);
|
||||||
|
|
||||||
if ((object = odb_object__alloc(&found_full_oid, &raw)) == NULL)
|
if ((object = odb_object__alloc(&found_full_oid, &raw)) == NULL)
|
||||||
return -1;
|
return -1;
|
||||||
|
@ -26,6 +26,13 @@ void test_object_shortid__select(void)
|
|||||||
cl_assert_equal_s("ce01362", shorty.ptr);
|
cl_assert_equal_s("ce01362", shorty.ptr);
|
||||||
git_object_free(obj);
|
git_object_free(obj);
|
||||||
|
|
||||||
|
git_oid_fromstr(&full, "038d718da6a1ebbc6a7780a96ed75a70cc2ad6e2");
|
||||||
|
cl_git_pass(git_object_lookup(&obj, _repo, &full, GIT_OBJ_ANY));
|
||||||
|
cl_git_pass(git_object_short_id(&shorty, obj));
|
||||||
|
cl_assert_equal_i(7, shorty.size);
|
||||||
|
cl_assert_equal_s("038d718", shorty.ptr);
|
||||||
|
git_object_free(obj);
|
||||||
|
|
||||||
git_oid_fromstr(&full, "dea509d097ce692e167dfc6a48a7a280cc5e877e");
|
git_oid_fromstr(&full, "dea509d097ce692e167dfc6a48a7a280cc5e877e");
|
||||||
cl_git_pass(git_object_lookup(&obj, _repo, &full, GIT_OBJ_ANY));
|
cl_git_pass(git_object_lookup(&obj, _repo, &full, GIT_OBJ_ANY));
|
||||||
cl_git_pass(git_object_short_id(&shorty, obj));
|
cl_git_pass(git_object_short_id(&shorty, obj));
|
||||||
|
@ -66,23 +66,25 @@ void test_odb_loose__cleanup(void)
|
|||||||
|
|
||||||
void test_odb_loose__exists(void)
|
void test_odb_loose__exists(void)
|
||||||
{
|
{
|
||||||
git_oid id, id2;
|
git_oid id, id2;
|
||||||
git_odb *odb;
|
git_odb *odb;
|
||||||
|
|
||||||
write_object_files(&one);
|
write_object_files(&one);
|
||||||
cl_git_pass(git_odb_open(&odb, "test-objects"));
|
cl_git_pass(git_odb_open(&odb, "test-objects"));
|
||||||
|
|
||||||
cl_git_pass(git_oid_fromstr(&id, one.id));
|
cl_git_pass(git_oid_fromstr(&id, one.id));
|
||||||
|
cl_assert(git_odb_exists(odb, &id));
|
||||||
|
|
||||||
cl_assert(git_odb_exists(odb, &id));
|
cl_git_pass(git_oid_fromstrp(&id, "8b137891"));
|
||||||
|
cl_git_pass(git_odb_exists_prefix(&id2, odb, &id, 8));
|
||||||
|
cl_assert_equal_i(0, git_oid_streq(&id2, one.id));
|
||||||
|
|
||||||
cl_assert(git_odb_exists_prefix(&id2, odb, &id, 8));
|
/* Test for a missing object */
|
||||||
cl_assert(git_oid_equal(&id, &id2));
|
cl_git_pass(git_oid_fromstr(&id, "8b137891791fe96927ad78e64b0aad7bded08baa"));
|
||||||
|
cl_assert(!git_odb_exists(odb, &id));
|
||||||
|
|
||||||
/* Test for a non-existant object */
|
cl_git_pass(git_oid_fromstrp(&id, "8b13789a"));
|
||||||
cl_git_pass(git_oid_fromstr(&id2, "8b137891791fe96927ad78e64b0aad7bded08baa"));
|
cl_assert_equal_i(GIT_ENOTFOUND, git_odb_exists_prefix(&id2, odb, &id, 8));
|
||||||
cl_assert(!git_odb_exists(odb, &id2));
|
|
||||||
cl_assert_equal_i(GIT_ENOTFOUND, git_odb_exists_prefix(NULL, odb, &id2, 8));
|
|
||||||
|
|
||||||
git_odb_free(odb);
|
git_odb_free(odb);
|
||||||
}
|
}
|
||||||
|
Binary file not shown.
Loading…
Reference in New Issue
Block a user