aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--hash.c18
-rw-r--r--hash.h3
-rw-r--r--object-name.c23
3 files changed, 24 insertions, 20 deletions
diff --git a/hash.c b/hash.c
index 553f2008ea..e925b9754e 100644
--- a/hash.c
+++ b/hash.c
@@ -317,3 +317,21 @@ const struct git_hash_algo *unsafe_hash_algo(const struct git_hash_algo *algop)
/* Otherwise use the default one. */
return algop;
}
+
+unsigned oid_common_prefix_hexlen(const struct object_id *a,
+ const struct object_id *b)
+{
+ unsigned rawsz = hash_algos[a->algo].rawsz;
+
+ for (unsigned i = 0; i < rawsz; i++) {
+ if (a->hash[i] == b->hash[i])
+ continue;
+
+ if ((a->hash[i] ^ b->hash[i]) & 0xf0)
+ return i * 2;
+ else
+ return i * 2 + 1;
+ }
+
+ return rawsz * 2;
+}
diff --git a/hash.h b/hash.h
index d51efce1d3..c082a53c9a 100644
--- a/hash.h
+++ b/hash.h
@@ -396,6 +396,9 @@ static inline int oideq(const struct object_id *oid1, const struct object_id *oi
return !memcmp(oid1->hash, oid2->hash, GIT_MAX_RAWSZ);
}
+unsigned oid_common_prefix_hexlen(const struct object_id *a,
+ const struct object_id *b);
+
static inline void oidcpy(struct object_id *dst, const struct object_id *src)
{
memcpy(dst->hash, src->hash, GIT_MAX_RAWSZ);
diff --git a/object-name.c b/object-name.c
index d82fb49f39..32e9c23e40 100644
--- a/object-name.c
+++ b/object-name.c
@@ -585,32 +585,16 @@ static unsigned msb(unsigned long val)
struct min_abbrev_data {
unsigned int init_len;
unsigned int cur_len;
- char *hex;
struct repository *repo;
const struct object_id *oid;
};
-static inline char get_hex_char_from_oid(const struct object_id *oid,
- unsigned int pos)
-{
- static const char hex[] = "0123456789abcdef";
-
- if ((pos & 1) == 0)
- return hex[oid->hash[pos >> 1] >> 4];
- else
- return hex[oid->hash[pos >> 1] & 0xf];
-}
-
static int extend_abbrev_len(const struct object_id *oid,
struct min_abbrev_data *mad)
{
- unsigned int i = mad->init_len;
- while (mad->hex[i] && mad->hex[i] == get_hex_char_from_oid(oid, i))
- i++;
-
- if (mad->hex[i] && i >= mad->cur_len)
- mad->cur_len = i + 1;
-
+ unsigned len = oid_common_prefix_hexlen(oid, mad->oid);
+ if (len != hash_algos[oid->algo].hexsz && len >= mad->cur_len)
+ mad->cur_len = len + 1;
return 0;
}
@@ -785,7 +769,6 @@ int repo_find_unique_abbrev_r(struct repository *r, char *hex,
mad.repo = r;
mad.init_len = len;
mad.cur_len = len;
- mad.hex = hex;
mad.oid = oid;
find_abbrev_len_packed(&mad);