Hash :
9094d30b
Author :
Date :
2012-11-23T11:41:56
Reset all static variables to NULL in clar's __cleanup Without this change, any failed assertion in the second (or a later) test inside a test suite has a chance of double deleting memory, resulting in a heap corruption. See #1096 for details. This leaves alone the test cases where we "just" use cl_git_sandbox_init() and cl_git_sandbox_cleanup(). These methods already take good care to not double delete a repository. Fixes #1096
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196
#include "clar_libgit2.h"
#include "refs.h"
#include "repo_helpers.h"
#include "posix.h"
static git_repository *repo;
void test_repo_head__initialize(void)
{
repo = cl_git_sandbox_init("testrepo.git");
}
void test_repo_head__cleanup(void)
{
cl_git_sandbox_cleanup();
}
void test_repo_head__head_detached(void)
{
git_reference *ref;
cl_git_pass(git_repository_head_detached(repo));
cl_git_pass(git_repository_detach_head(repo));
cl_assert_equal_i(true, git_repository_head_detached(repo));
/* take the reop back to it's original state */
cl_git_pass(git_reference_create_symbolic(&ref, repo, "HEAD", "refs/heads/master", 1));
git_reference_free(ref);
cl_assert_equal_i(false, git_repository_head_detached(repo));
}
void test_repo_head__head_orphan(void)
{
git_reference *ref;
cl_git_pass(git_repository_head_detached(repo));
make_head_orphaned(repo, NON_EXISTING_HEAD);
cl_assert(git_repository_head_orphan(repo) == 1);
/* take the repo back to it's original state */
cl_git_pass(git_reference_create_symbolic(&ref, repo, "HEAD", "refs/heads/master", 1));
cl_assert(git_repository_head_orphan(repo) == 0);
git_reference_free(ref);
}
void test_repo_head__set_head_Attaches_HEAD_to_un_unborn_branch_when_the_branch_doesnt_exist(void)
{
git_reference *head;
cl_git_pass(git_repository_set_head(repo, "refs/heads/doesnt/exist/yet"));
cl_assert_equal_i(false, git_repository_head_detached(repo));
cl_assert_equal_i(GIT_EORPHANEDHEAD, git_repository_head(&head, repo));
}
void test_repo_head__set_head_Returns_ENOTFOUND_when_the_reference_doesnt_exist(void)
{
cl_assert_equal_i(GIT_ENOTFOUND, git_repository_set_head(repo, "refs/tags/doesnt/exist/yet"));
}
void test_repo_head__set_head_Fails_when_the_reference_points_to_a_non_commitish(void)
{
cl_git_fail(git_repository_set_head(repo, "refs/tags/point_to_blob"));
}
void test_repo_head__set_head_Attaches_HEAD_when_the_reference_points_to_a_branch(void)
{
git_reference *head;
cl_git_pass(git_repository_set_head(repo, "refs/heads/br2"));
cl_assert_equal_i(false, git_repository_head_detached(repo));
cl_git_pass(git_repository_head(&head, repo));
cl_assert_equal_s("refs/heads/br2", git_reference_name(head));
git_reference_free(head);
}
static void assert_head_is_correctly_detached(void)
{
git_reference *head;
git_object *commit;
cl_assert_equal_i(true, git_repository_head_detached(repo));
cl_git_pass(git_repository_head(&head, repo));
cl_git_pass(git_object_lookup(&commit, repo, git_reference_oid(head), GIT_OBJ_COMMIT));
git_object_free(commit);
git_reference_free(head);
}
void test_repo_head__set_head_Detaches_HEAD_when_the_reference_doesnt_point_to_a_branch(void)
{
cl_git_pass(git_repository_set_head(repo, "refs/tags/test"));
cl_assert_equal_i(true, git_repository_head_detached(repo));
assert_head_is_correctly_detached();
}
void test_repo_head__set_head_detached_Return_ENOTFOUND_when_the_object_doesnt_exist(void)
{
git_oid oid;
cl_git_pass(git_oid_fromstr(&oid, "deadbeefdeadbeefdeadbeefdeadbeefdeadbeef"));
cl_assert_equal_i(GIT_ENOTFOUND, git_repository_set_head_detached(repo, &oid));
}
void test_repo_head__set_head_detached_Fails_when_the_object_isnt_a_commitish(void)
{
git_object *blob;
cl_git_pass(git_revparse_single(&blob, repo, "point_to_blob"));
cl_git_fail(git_repository_set_head_detached(repo, git_object_id(blob)));
git_object_free(blob);
}
void test_repo_head__set_head_detached_Detaches_HEAD_and_make_it_point_to_the_peeled_commit(void)
{
git_object *tag;
cl_git_pass(git_revparse_single(&tag, repo, "tags/test"));
cl_assert_equal_i(GIT_OBJ_TAG, git_object_type(tag));
cl_git_pass(git_repository_set_head_detached(repo, git_object_id(tag)));
assert_head_is_correctly_detached();
git_object_free(tag);
}
void test_repo_head__detach_head_Detaches_HEAD_and_make_it_point_to_the_peeled_commit(void)
{
cl_assert_equal_i(false, git_repository_head_detached(repo));
cl_git_pass(git_repository_detach_head(repo));
assert_head_is_correctly_detached();
}
void test_repo_head__detach_head_Fails_if_HEAD_and_point_to_a_non_commitish(void)
{
git_reference *head;
cl_git_pass(git_reference_create_symbolic(&head, repo, GIT_HEAD_FILE, "refs/tags/point_to_blob", 1));
cl_git_fail(git_repository_detach_head(repo));
git_reference_free(head);
}
void test_repo_head__detaching_an_orphaned_head_returns_GIT_EORPHANEDHEAD(void)
{
make_head_orphaned(repo, NON_EXISTING_HEAD);
cl_assert_equal_i(GIT_EORPHANEDHEAD, git_repository_detach_head(repo));
}
void test_repo_head__retrieving_an_orphaned_head_returns_GIT_EORPHANEDHEAD(void)
{
git_reference *head;
make_head_orphaned(repo, NON_EXISTING_HEAD);
cl_assert_equal_i(GIT_EORPHANEDHEAD, git_repository_head(&head, repo));
}
void test_repo_head__retrieving_a_missing_head_returns_GIT_ENOTFOUND(void)
{
git_reference *head;
delete_head(repo);
cl_assert_equal_i(GIT_ENOTFOUND, git_repository_head(&head, repo));
}
void test_repo_head__can_tell_if_an_orphaned_head_is_detached(void)
{
make_head_orphaned(repo, NON_EXISTING_HEAD);
cl_assert_equal_i(false, git_repository_head_detached(repo));
}