sha1_name.c: refactor find_short_packed_object()

Extract the logic to find object(s) that match a given prefix inside
a single pack into a separate helper function, and give it a bit more
comment.

Signed-off-by: Junio C Hamano <gitster@pobox.com>
This commit is contained in:
Junio C Hamano 2012-06-18 13:10:38 -07:00
parent 1b27c2f01a
commit f703e6ea5e

View File

@ -78,16 +78,15 @@ static int match_sha(unsigned len, const unsigned char *a, const unsigned char *
return 1; return 1;
} }
static int find_short_packed_object(int len, const unsigned char *match, unsigned char *sha1) static int unique_in_pack(int len,
const unsigned char *match,
struct packed_git *p,
const unsigned char **found_sha1,
int seen_so_far)
{ {
struct packed_git *p; uint32_t num, last, i, first = 0;
const unsigned char *found_sha1 = NULL; const unsigned char *current = NULL;
int found = 0;
prepare_packed_git();
for (p = packed_git; p && found < 2; p = p->next) {
uint32_t num, last;
uint32_t first = 0;
open_pack_index(p); open_pack_index(p);
num = p->num_objects; num = p->num_objects;
last = num; last = num;
@ -108,30 +107,40 @@ static int find_short_packed_object(int len, const unsigned char *match, unsigne
} }
last = mid; last = mid;
} }
if (first < num) {
const unsigned char *current, *next; /*
* At this point, "first" is the location of the lowest object
* with an object name that could match "match". See if we have
* 0, 1 or more objects that actually match(es).
*/
for (i = first; i < num; i++) {
current = nth_packed_object_sha1(p, first); current = nth_packed_object_sha1(p, first);
if (match_sha(len, match, current)) { if (!match_sha(len, match, current))
next = nth_packed_object_sha1(p, first+1);
if (!next|| !match_sha(len, match, next)) {
/* unique within this pack */
if (!found) {
found_sha1 = current;
found++;
}
else if (hashcmp(found_sha1, current)) {
found = 2;
break; break;
/* current matches */
if (!seen_so_far) {
*found_sha1 = current;
seen_so_far++;
} else if (seen_so_far) {
/* is it the same as the one previously found elsewhere? */
if (hashcmp(*found_sha1, current))
return 2; /* definitely not unique */
} }
} }
else { return seen_so_far;
/* not even unique within this pack */
found = 2;
break;
}
}
}
} }
static int find_short_packed_object(int len, const unsigned char *match, unsigned char *sha1)
{
struct packed_git *p;
const unsigned char *found_sha1 = NULL;
int found = 0;
prepare_packed_git();
for (p = packed_git; p && found < 2; p = p->next)
found = unique_in_pack(len, match, p, &found_sha1, found);
if (found == 1) if (found == 1)
hashcpy(sha1, found_sha1); hashcpy(sha1, found_sha1);
return found; return found;