connect: detect algorithm when fetching refs
If we're fetching refs, detect the hash algorithm and parse the refs using that algorithm. As mentioned in the documentation, if multiple versions of the object-format capability are provided, we use the first. No known implementation supports multiple algorithms now, but they may in the future. Signed-off-by: brian m. carlson <sandals@crustytoothpaste.net> Signed-off-by: Junio C Hamano <gitster@pobox.com>
brian m. carlson committed
May 25, 2020 at 19:59 UTC
7c601dc333b6cd86a84e77f41c968a3bb773ba36
1 file changed
+17
-4
connect.c
+17
-4
@@ -220,12 +220,25 @@ static void annotate_refs_with_symref_info(struct ref *ref)
220
221
static void process_capabilities(struct packet_reader *reader, int *linelen)
222
{
223
+ const char *feat_val;
224
+ int feat_len;
225
const char *line = reader->line;
226
int nul_location = strlen(line);
227
if (nul_location == *linelen)
228
return;
229
server_capabilities_v1 = xstrdup(line + nul_location + 1);
230
*linelen = nul_location;
231
+
232
+ feat_val = server_feature_value("object-format", &feat_len);
233
+ if (feat_val) {
234
+ char *hash_name = xstrndup(feat_val, feat_len);
235
+ int hash_algo = hash_algo_by_name(hash_name);
236
+ if (hash_algo != GIT_HASH_UNKNOWN)
237
+ reader->hash_algo = &hash_algos[hash_algo];
238
+ free(hash_name);
239
+ } else {
240
+ reader->hash_algo = &hash_algos[GIT_HASH_SHA1];
241
+ }
242
}
243
244
static int process_dummy_ref(const struct packet_reader *reader)
@@ -234,7 +247,7 @@ static int process_dummy_ref(const struct packet_reader *reader)
247
struct object_id oid;
248
const char *name;
249
237
- if (parse_oid_hex(line, &oid, &name))
250
+ if (parse_oid_hex_algop(line, &oid, &name, reader->hash_algo))
251
return 0;
252
if (*name != ' ')
253
return 0;
@@ -258,7 +271,7 @@ static int process_ref(const struct packet_reader *reader, int len,
271
struct object_id old_oid;
272
const char *name;
273
261
- if (parse_oid_hex(line, &old_oid, &name))
274
+ if (parse_oid_hex_algop(line, &old_oid, &name, reader->hash_algo))
275
return 0;
276
if (*name != ' ')
277
return 0;
@@ -270,7 +283,7 @@ static int process_ref(const struct packet_reader *reader, int len,
283
die(_("protocol error: unexpected capabilities^{}"));
284
} else if (check_ref(name, flags)) {
285
struct ref *ref = alloc_ref(name);
273
- oidcpy(&ref->old_oid, &old_oid);
286
+ memcpy(ref->old_oid.hash, old_oid.hash, reader->hash_algo->rawsz);
287
**list = ref;
288
*list = &ref->next;
289
}
@@ -288,7 +301,7 @@ static int process_shallow(const struct packet_reader *reader, int len,
301
if (!skip_prefix(line, "shallow ", &arg))
302
return 0;
303
291
- if (get_oid_hex(arg, &old_oid))
304
+ if (get_oid_hex_algop(arg, &old_oid, reader->hash_algo))
305
die(_("protocol error: expected shallow sha-1, got '%s'"), arg);
306
if (!shallow_points)
307
die(_("repository on the other end cannot be shallow"));