fast-import: make hash-size independent

Replace several uses of GIT_SHA1_HEXSZ and 40-based constants with references to the_hash_algo. Update the note handling code here to compute path sizes based on GIT_MAX_RAWSZ as well. Signed-off-by: brian m. carlson <sandals@crustytoothpaste.net> Signed-off-by: Junio C Hamano <gitster@pobox.com>

brian m. carlson committed Feb 19, 2019 at 00:05 UTC 28d055bde9436dc1180d58aec2406579ab6d6307
1 file changed +29 -16
fast-import.c
+29 -16
@@ -29,6 +29,13 @@
29 */
30 #define NO_DELTA S_ISUID
31
32 +/*
33 + * The amount of additional space required in order to write an object into the
34 + * current pack. This is the hash lengths at the end of the pack, plus the
35 + * length of one object ID.
36 + */
37 +#define PACK_SIZE_THRESHOLD (the_hash_algo->rawsz * 3)
38 +
39 struct object_entry {
40 struct pack_idx_entry idx;
41 struct object_entry *next;
@@ -949,8 +956,9 @@ static int store_object(
956 git_deflate_end(&s);
957
958 /* Determine if we should auto-checkpoint. */
952 - if ((max_packsize && (pack_size + 60 + s.total_out) > max_packsize)
953 - || (pack_size + 60 + s.total_out) < pack_size) {
959 + if ((max_packsize
960 + && (pack_size + PACK_SIZE_THRESHOLD + s.total_out) > max_packsize)
961 + || (pack_size + PACK_SIZE_THRESHOLD + s.total_out) < pack_size) {
962
963 /* This new object needs to *not* have the current pack_id. */
964 e->pack_id = pack_id + 1;
@@ -1045,8 +1053,9 @@ static void stream_blob(uintmax_t len, struct object_id *oidout, uintmax_t mark)
1053 int status = Z_OK;
1054
1055 /* Determine if we should auto-checkpoint. */
1048 - if ((max_packsize && (pack_size + 60 + len) > max_packsize)
1049 - || (pack_size + 60 + len) < pack_size)
1056 + if ((max_packsize
1057 + && (pack_size + PACK_SIZE_THRESHOLD + len) > max_packsize)
1058 + || (pack_size + PACK_SIZE_THRESHOLD + len) < pack_size)
1059 cycle_packfile();
1060
1061 hashfile_checkpoint(pack_file, &checkpoint);
@@ -1241,7 +1250,7 @@ static void load_tree(struct tree_entry *root)
1250 c += e->name->str_len + 1;
1251 hashcpy(e->versions[0].oid.hash, (unsigned char *)c);
1252 hashcpy(e->versions[1].oid.hash, (unsigned char *)c);
1244 - c += GIT_SHA1_RAWSZ;
1253 + c += the_hash_algo->rawsz;
1254 }
1255 free(buf);
1256 }
@@ -1288,7 +1297,7 @@ static void mktree(struct tree_content *t, int v, struct strbuf *b)
1297 strbuf_addf(b, "%o %s%c",
1298 (unsigned int)(e->versions[v].mode & ~NO_DELTA),
1299 e->name->str_dat, '\0');
1291 - strbuf_add(b, e->versions[v].oid.hash, GIT_SHA1_RAWSZ);
1300 + strbuf_add(b, e->versions[v].oid.hash, the_hash_algo->rawsz);
1301 }
1302 }
1303
@@ -2047,7 +2056,9 @@ static uintmax_t do_change_note_fanout(
2056 unsigned int i, tmp_hex_oid_len, tmp_fullpath_len;
2057 uintmax_t num_notes = 0;
2058 struct object_id oid;
2050 - char realpath[60];
2059 + /* hex oid + '/' between each pair of hex digits + NUL */
2060 + char realpath[GIT_MAX_HEXSZ + ((GIT_MAX_HEXSZ / 2) - 1) + 1];
2061 + const unsigned hexsz = the_hash_algo->hexsz;
2062
2063 if (!root->tree)
2064 load_tree(root);
@@ -2067,7 +2078,7 @@ static uintmax_t do_change_note_fanout(
2078 * of 2 chars.
2079 */
2080 if (!e->versions[1].mode ||
2070 - tmp_hex_oid_len > GIT_SHA1_HEXSZ ||
2081 + tmp_hex_oid_len > hexsz ||
2082 e->name->str_len % 2)
2083 continue;
2084
@@ -2081,7 +2092,7 @@ static uintmax_t do_change_note_fanout(
2092 tmp_fullpath_len += e->name->str_len;
2093 fullpath[tmp_fullpath_len] = '\0';
2094
2084 - if (tmp_hex_oid_len == GIT_SHA1_HEXSZ && !get_oid_hex(hex_oid, &oid)) {
2095 + if (tmp_hex_oid_len == hexsz && !get_oid_hex(hex_oid, &oid)) {
2096 /* This is a note entry */
2097 if (fanout == 0xff) {
2098 /* Counting mode, no rename */
@@ -2352,7 +2363,7 @@ static void note_change_n(const char *p, struct branch *b, unsigned char *old_fa
2363 struct object_entry *oe;
2364 struct branch *s;
2365 struct object_id oid, commit_oid;
2355 - char path[60];
2366 + char path[GIT_MAX_RAWSZ * 3];
2367 uint16_t inline_data = 0;
2368 unsigned char new_fanout;
2369
@@ -2405,7 +2416,7 @@ static void note_change_n(const char *p, struct branch *b, unsigned char *old_fa
2416 char *buf = read_object_with_reference(&commit_oid,
2417 commit_type, &size,
2418 &commit_oid);
2408 - if (!buf || size < 46)
2419 + if (!buf || size < the_hash_algo->hexsz + 6)
2420 die("Not a valid commit: %s", p);
2421 free(buf);
2422 } else
@@ -2456,7 +2467,7 @@ static void file_change_deleteall(struct branch *b)
2467
2468 static void parse_from_commit(struct branch *b, char *buf, unsigned long size)
2469 {
2459 - if (!buf || size < GIT_SHA1_HEXSZ + 6)
2470 + if (!buf || size < the_hash_algo->hexsz + 6)
2471 die("Not a valid commit: %s", oid_to_hex(&b->oid));
2472 if (memcmp("tree ", buf, 5)
2473 || get_oid_hex(buf + 5, &b->branch_tree.versions[1].oid))
@@ -2555,7 +2566,7 @@ static struct hash_list *parse_merge(unsigned int *count)
2566 char *buf = read_object_with_reference(&n->oid,
2567 commit_type,
2568 &size, &n->oid);
2558 - if (!buf || size < 46)
2569 + if (!buf || size < the_hash_algo->hexsz + 6)
2570 die("Not a valid commit: %s", from);
2571 free(buf);
2572 } else
@@ -2842,7 +2853,7 @@ static void parse_get_mark(const char *p)
2853 die("Unknown mark: %s", command_buf.buf);
2854
2855 xsnprintf(output, sizeof(output), "%s\n", oid_to_hex(&oe->idx.oid));
2845 - cat_blob_write(output, GIT_SHA1_HEXSZ + 1);
2856 + cat_blob_write(output, the_hash_algo->hexsz + 1);
2857 }
2858
2859 static void parse_cat_blob(const char *p)
@@ -2872,6 +2883,8 @@ static struct object_entry *dereference(struct object_entry *oe,
2883 {
2884 unsigned long size;
2885 char *buf = NULL;
2886 + const unsigned hexsz = the_hash_algo->hexsz;
2887 +
2888 if (!oe) {
2889 enum object_type type = oid_object_info(the_repository, oid,
2890 NULL);
@@ -2905,12 +2918,12 @@ static struct object_entry *dereference(struct object_entry *oe,
2918 /* Peel one layer. */
2919 switch (oe->type) {
2920 case OBJ_TAG:
2908 - if (size < GIT_SHA1_HEXSZ + strlen("object ") ||
2921 + if (size < hexsz + strlen("object ") ||
2922 get_oid_hex(buf + strlen("object "), oid))
2923 die("Invalid SHA1 in tag: %s", command_buf.buf);
2924 break;
2925 case OBJ_COMMIT:
2913 - if (size < GIT_SHA1_HEXSZ + strlen("tree ") ||
2926 + if (size < hexsz + strlen("tree ") ||
2927 get_oid_hex(buf + strlen("tree "), oid))
2928 die("Invalid SHA1 in commit: %s", command_buf.buf);
2929 }