Commit 79fd42301e80c1f787ee9e9b83dc5159ae12854a

nulltoken 2012-04-06T15:23:18

transport/local: Fix peeling of nested tags

diff --git a/src/transports/local.c b/src/transports/local.c
index eb24db0..6cf8ed9 100644
--- a/src/transports/local.c
+++ b/src/transports/local.c
@@ -27,7 +27,7 @@ static int add_ref(transport_local *t, const char *name)
 	const char peeled[] = "^{}";
 	git_remote_head *head;
 	git_reference *ref, *resolved_ref;
-	git_object *obj = NULL;
+	git_object *obj = NULL, *peeled_tag_target = NULL;
 	int error = GIT_SUCCESS, peel_len, ret;
 
 	head = git__malloc(sizeof(git_remote_head));
@@ -78,7 +78,11 @@ static int add_ref(transport_local *t, const char *name)
 	assert(ret < peel_len + 1);
 	(void)ret;
 
-	git_oid_cpy(&head->oid, git_tag_target_oid((git_tag *) obj));
+	error = git_tag_peel(&peeled_tag_target, (git_tag *) obj);
+	if (error < 0)
+		goto out;
+
+	git_oid_cpy(&head->oid, git_object_id(peeled_tag_target));
 
 	error = git_vector_insert(&t->refs, head);
 	if (error < GIT_SUCCESS)
@@ -89,6 +93,7 @@ static int add_ref(transport_local *t, const char *name)
 	git_reference_free(resolved_ref);
 
 	git_object_free(obj);
+	git_object_free(peeled_tag_target);
 	if (head && error < GIT_SUCCESS) {
 		git__free(head->name);
 		git__free(head);
diff --git a/tests-clar/network/remotelocal.c b/tests-clar/network/remotelocal.c
index 74a0b57..e154226 100644
--- a/tests-clar/network/remotelocal.c
+++ b/tests-clar/network/remotelocal.c
@@ -71,6 +71,16 @@ static int count_ref__cb(git_remote_head *head, void *payload)
 	return GIT_SUCCESS;
 }
 
+static int ensure_peeled__cb(git_remote_head *head, void *payload)
+{
+	GIT_UNUSED(payload);
+
+	if(strcmp(head->name, "refs/tags/test^{}") != 0)
+		return 0;
+
+	return git_oid_streq(&head->oid, "e90810b8df3e80c413d903f631643c716887138d");
+}
+
 static void connect_to_local_repository(const char *local_repository)
 {
 	build_local_file_url(&file_path_buf, local_repository);
@@ -104,5 +114,15 @@ void test_network_remotelocal__retrieve_advertised_references_from_spaced_reposi
 
 	cl_assert(how_many_refs == 14); /* 1 HEAD + 6 heads + 1 lightweight tag + 3 annotated tags + 3 peeled target */
 
+	git_remote_free(remote);	/* Disconnect from the "spaced repo" before the cleanup */
+	remote = NULL;
+
 	cl_fixture_cleanup("spaced testrepo.git");
 }
+
+void test_network_remotelocal__nested_tags_are_completely_peeled(void)
+{
+	connect_to_local_repository(cl_fixture("testrepo.git"));
+
+	cl_git_pass(git_remote_ls(remote, &ensure_peeled__cb, NULL));
+}