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
#include "clar_libgit2.h"
#include "odb.h"
#include "hash.h"
void test_object_raw_short__oid_shortener_no_duplicates(void)
{
git_oid_shorten *os;
int min_len;
os = git_oid_shorten_new(0);
cl_assert(os != NULL);
git_oid_shorten_add(os, "22596363b3de40b06f981fb85d82312e8c0ed511");
git_oid_shorten_add(os, "ce08fe4884650f067bd5703b6a59a8b3b3c99a09");
git_oid_shorten_add(os, "16a0123456789abcdef4b775213c23a8bd74f5e0");
min_len = git_oid_shorten_add(os, "ce08fe4884650f067bd5703b6a59a8b3b3c99a09");
cl_assert(min_len == GIT_OID_HEXSZ + 1);
git_oid_shorten_free(os);
}
static int insert_sequential_oids(
char ***out, git_oid_shorten *os, int n, int fail)
{
int i, min_len = 0;
char numbuf[16];
git_oid oid;
char **oids = git__calloc(n, sizeof(char *));
cl_assert(oids != NULL);
for (i = 0; i < n; ++i) {
p_snprintf(numbuf, sizeof(numbuf), "%u", (unsigned int)i);
git_hash_buf(&oid, numbuf, strlen(numbuf));
oids[i] = git__malloc(GIT_OID_HEXSZ + 1);
cl_assert(oids[i]);
git_oid_nfmt(oids[i], GIT_OID_HEXSZ + 1, &oid);
min_len = git_oid_shorten_add(os, oids[i]);
/* After "fail", we expect git_oid_shorten_add to fail */
if (fail >= 0 && i >= fail)
cl_assert(min_len < 0);
else
cl_assert(min_len >= 0);
}
*out = oids;
return min_len;
}
static void free_oids(int n, char **oids)
{
int i;
for (i = 0; i < n; ++i) {
git__free(oids[i]);
}
git__free(oids);
}
void test_object_raw_short__oid_shortener_stresstest_git_oid_shorten(void)
{
#define MAX_OIDS 1000
git_oid_shorten *os;
size_t i, j;
int min_len = 0, found_collision;
char **oids;
os = git_oid_shorten_new(0);
cl_assert(os != NULL);
/*
* Insert in the shortener 1000 unique SHA1 ids
*/
min_len = insert_sequential_oids(&oids, os, MAX_OIDS, MAX_OIDS);
cl_assert(min_len > 0);
/*
* Compare the first `min_char - 1` characters of each
* SHA1 OID. If the minimizer worked, we should find at
* least one collision
*/
found_collision = 0;
for (i = 0; i < MAX_OIDS; ++i) {
for (j = i + 1; j < MAX_OIDS; ++j) {
if (memcmp(oids[i], oids[j], min_len - 1) == 0)
found_collision = 1;
}
}
cl_assert_equal_b(true, found_collision);
/*
* Compare the first `min_char` characters of each
* SHA1 OID. If the minimizer worked, every single preffix
* should be unique.
*/
found_collision = 0;
for (i = 0; i < MAX_OIDS; ++i) {
for (j = i + 1; j < MAX_OIDS; ++j) {
if (memcmp(oids[i], oids[j], min_len) == 0)
found_collision = 1;
}
}
cl_assert_equal_b(false, found_collision);
/* cleanup */
free_oids(MAX_OIDS, oids);
git_oid_shorten_free(os);
#undef MAX_OIDS
}
void test_object_raw_short__oid_shortener_too_much_oids(void)
{
/* The magic number of oids at which an oid_shortener will fail.
* This was experimentally established. */
#define MAX_OIDS 24556
git_oid_shorten *os;
char **oids;
os = git_oid_shorten_new(0);
cl_assert(os != NULL);
cl_assert(insert_sequential_oids(&oids, os, MAX_OIDS, MAX_OIDS - 1) < 0);
free_oids(MAX_OIDS, oids);
git_oid_shorten_free(os);
#undef MAX_OIDS
}