1 #ifndef HASH_H
2 #define HASH_H
3
4 #if defined(SHA1_APPLE)
5 #define SHA1_BACKEND "SHA1_APPLE (No collision detection)"
6 #include <CommonCrypto/CommonDigest.h>
7 #elif defined(SHA1_OPENSSL)
8 # define SHA1_BACKEND "SHA1_OPENSSL (No collision detection)"
9 # include <openssl/sha.h>
10 # if defined(OPENSSL_API_LEVEL) && OPENSSL_API_LEVEL >= 3
11 # define SHA1_NEEDS_CLONE_HELPER
12 # include "sha1/openssl.h"
13 # endif
14 #elif defined(SHA1_DC)
15 #define SHA1_BACKEND "SHA1_DC"
16 #include "sha1dc_git.h"
17 #else /* SHA1_BLK */
18 #define SHA1_BACKEND "SHA1_BLK (No collision detection)"
19 #include "block-sha1/sha1.h"
20 #endif
21
22 #if defined(SHA1_APPLE_UNSAFE)
23 # define SHA1_UNSAFE_BACKEND "SHA1_APPLE_UNSAFE"
24 # include <CommonCrypto/CommonDigest.h>
25 # define platform_SHA_CTX_unsafe CC_SHA1_CTX
26 # define platform_SHA1_Init_unsafe CC_SHA1_Init
27 # define platform_SHA1_Update_unsafe CC_SHA1_Update
28 # define platform_SHA1_Final_unsafe CC_SHA1_Final
29 #elif defined(SHA1_OPENSSL_UNSAFE)
30 # define SHA1_UNSAFE_BACKEND "SHA1_OPENSSL_UNSAFE"
31 # include <openssl/sha.h>
32 # if defined(OPENSSL_API_LEVEL) && OPENSSL_API_LEVEL >= 3
33 # define SHA1_NEEDS_CLONE_HELPER_UNSAFE
34 # include "sha1/openssl.h"
35 # define platform_SHA_CTX_unsafe openssl_SHA1_CTX
36 # define platform_SHA1_Init_unsafe openssl_SHA1_Init
37 # define platform_SHA1_Clone_unsafe openssl_SHA1_Clone
38 # define platform_SHA1_Update_unsafe openssl_SHA1_Update
39 # define platform_SHA1_Final_unsafe openssl_SHA1_Final
40 # define platform_SHA1_Discard_unsafe openssl_SHA1_Discard
41 # else
42 # define platform_SHA_CTX_unsafe SHA_CTX
43 # define platform_SHA1_Init_unsafe SHA1_Init
44 # define platform_SHA1_Update_unsafe SHA1_Update
45 # define platform_SHA1_Final_unsafe SHA1_Final
46 # endif
47 #elif defined(SHA1_BLK_UNSAFE)
48 # define SHA1_UNSAFE_BACKEND "SHA1_BLK_UNSAFE"
49 # include "block-sha1/sha1.h"
50 # define platform_SHA_CTX_unsafe blk_SHA_CTX
51 # define platform_SHA1_Init_unsafe blk_SHA1_Init
52 # define platform_SHA1_Update_unsafe blk_SHA1_Update
53 # define platform_SHA1_Final_unsafe blk_SHA1_Final
54 #endif
55
56 #if defined(SHA256_NETTLE)
57 #define SHA256_BACKEND "SHA256_NETTLE"
58 #include "sha256/nettle.h"
59 #elif defined(SHA256_GCRYPT)
60 #define SHA256_BACKEND "SHA256_GCRYPT"
61 #define SHA256_NEEDS_CLONE_HELPER
62 #include "sha256/gcrypt.h"
63 #elif defined(SHA256_OPENSSL)
64 # define SHA256_BACKEND "SHA256_OPENSSL"
65 # include <openssl/sha.h>
66 # if defined(OPENSSL_API_LEVEL) && OPENSSL_API_LEVEL >= 3
67 # define SHA256_NEEDS_CLONE_HELPER
68 # include "sha256/openssl.h"
69 # endif
70 #else
71 #define SHA256_BACKEND "SHA256_BLK"
72 #include "sha256/block/sha256.h"
73 #endif
74
75 #ifndef platform_SHA_CTX
76 /*
77 * platform's underlying implementation of SHA-1; could be OpenSSL,
78 * blk_SHA, Apple CommonCrypto, etc... Note that the relevant
79 * SHA-1 header may have already defined platform_SHA_CTX for our
80 * own implementations like block-sha1, so we list
81 * the default for OpenSSL compatible SHA-1 implementations here.
82 */
83 #define platform_SHA_CTX SHA_CTX
84 #define platform_SHA1_Init SHA1_Init
85 #define platform_SHA1_Update SHA1_Update
86 #define platform_SHA1_Final SHA1_Final
87 #endif
88
89 #ifndef platform_SHA_CTX_unsafe
90 # define platform_SHA_CTX_unsafe platform_SHA_CTX
91 # define platform_SHA1_Init_unsafe platform_SHA1_Init
92 # define platform_SHA1_Update_unsafe platform_SHA1_Update
93 # define platform_SHA1_Final_unsafe platform_SHA1_Final
94 # ifdef platform_SHA1_Clone
95 # define platform_SHA1_Clone_unsafe platform_SHA1_Clone
96 # define platform_SHA1_Discard_unsafe platform_SHA1_Discard
97 # endif
98 # ifdef SHA1_NEEDS_CLONE_HELPER
99 # define SHA1_NEEDS_CLONE_HELPER_UNSAFE
100 # endif
101 #endif
102
103 #define git_SHA_CTX platform_SHA_CTX
104 #define git_SHA1_Init platform_SHA1_Init
105 #define git_SHA1_Update platform_SHA1_Update
106 #define git_SHA1_Final platform_SHA1_Final
107
108 #define git_SHA_CTX_unsafe platform_SHA_CTX_unsafe
109 #define git_SHA1_Init_unsafe platform_SHA1_Init_unsafe
110 #define git_SHA1_Update_unsafe platform_SHA1_Update_unsafe
111 #define git_SHA1_Final_unsafe platform_SHA1_Final_unsafe
112
113 #ifdef platform_SHA1_Clone
114 #define git_SHA1_Clone platform_SHA1_Clone
115 #define git_SHA1_Discard platform_SHA1_Discard
116 #endif
117 #ifdef platform_SHA1_Clone_unsafe
118 # define git_SHA1_Clone_unsafe platform_SHA1_Clone_unsafe
119 # define git_SHA1_Discard_unsafe platform_SHA1_Discard_unsafe
120 #endif
121
122 #ifndef platform_SHA256_CTX
123 #define platform_SHA256_CTX SHA256_CTX
124 #define platform_SHA256_Init SHA256_Init
125 #define platform_SHA256_Update SHA256_Update
126 #define platform_SHA256_Final SHA256_Final
127 #endif
128
129 #define git_SHA256_CTX platform_SHA256_CTX
130 #define git_SHA256_Init platform_SHA256_Init
131 #define git_SHA256_Update platform_SHA256_Update
132 #define git_SHA256_Final platform_SHA256_Final
133
134 #ifdef platform_SHA256_Clone
135 #define git_SHA256_Clone platform_SHA256_Clone
136 #define git_SHA256_Discard platform_SHA256_Discard
137 #endif
138
139 #ifdef SHA1_MAX_BLOCK_SIZE
140 #include "compat/sha1-chunked.h"
141 #undef git_SHA1_Update
142 #define git_SHA1_Update git_SHA1_Update_Chunked
143 #endif
144
145 #ifndef SHA1_NEEDS_CLONE_HELPER
146 static inline void git_SHA1_Clone(git_SHA_CTX *dst, const git_SHA_CTX *src)
147 {
148 memcpy(dst, src, sizeof(*dst));
149 }
150 static inline void git_SHA1_Discard(git_SHA_CTX *ctx UNUSED)
151 {
152 /* noop */
153 }
154 #endif
155 #ifndef SHA1_NEEDS_CLONE_HELPER_UNSAFE
156 static inline void git_SHA1_Clone_unsafe(git_SHA_CTX_unsafe *dst,
157 const git_SHA_CTX_unsafe *src)
158 {
159 memcpy(dst, src, sizeof(*dst));
160 }
161 static inline void git_SHA1_Discard_unsafe(git_SHA_CTX_unsafe *ctx UNUSED)
162 {
163 /* noop */
164 }
165 #endif
166
167 #ifndef SHA256_NEEDS_CLONE_HELPER
168 static inline void git_SHA256_Clone(git_SHA256_CTX *dst, const git_SHA256_CTX *src)
169 {
170 memcpy(dst, src, sizeof(*dst));
171 }
172 static inline void git_SHA256_Discard(git_SHA256_CTX *ctx UNUSED)
173 {
174 /* noop */
175 }
176 #endif
177
178 /*
179 * Note that these constants are suitable for indexing the hash_algos array and
180 * comparing against each other, but are otherwise arbitrary, so they should not
181 * be exposed to the user or serialized to disk. To know whether a
182 * git_hash_algo struct points to some usable hash function, test the format_id
183 * field for being non-zero. Use the name field for user-visible situations and
184 * the format_id field for fixed-length fields on disk.
185 */
186 /* An unknown hash function. */
187 #define GIT_HASH_UNKNOWN 0
188 /* SHA-1 */
189 #define GIT_HASH_SHA1 1
190 /* SHA-256 */
191 #define GIT_HASH_SHA256 2
192 /* Number of algorithms supported (including unknown). */
193 #define GIT_HASH_NALGOS (GIT_HASH_SHA256 + 1)
194
195 /* Default hash algorithm if unspecified. */
196 #ifdef WITH_BREAKING_CHANGES
197 # define GIT_HASH_DEFAULT GIT_HASH_SHA256
198 #else
199 # define GIT_HASH_DEFAULT GIT_HASH_SHA1
200 #endif
201
202 /* Legacy hash algorithm. Implied for older data formats which don't specify. */
203 #define GIT_HASH_SHA1_LEGACY GIT_HASH_SHA1
204
205 /* "sha1", big-endian */
206 #define GIT_SHA1_FORMAT_ID 0x73686131
207
208 /* The length in bytes and in hex digits of an object name (SHA-1 value). */
209 #define GIT_SHA1_RAWSZ 20
210 #define GIT_SHA1_HEXSZ (2 * GIT_SHA1_RAWSZ)
211 /* The block size of SHA-1. */
212 #define GIT_SHA1_BLKSZ 64
213
214 /* "s256", big-endian */
215 #define GIT_SHA256_FORMAT_ID 0x73323536
216
217 /* The length in bytes and in hex digits of an object name (SHA-256 value). */
218 #define GIT_SHA256_RAWSZ 32
219 #define GIT_SHA256_HEXSZ (2 * GIT_SHA256_RAWSZ)
220 /* The block size of SHA-256. */
221 #define GIT_SHA256_BLKSZ 64
222
223 /* The length in byte and in hex digits of the largest possible hash value. */
224 #define GIT_MAX_RAWSZ GIT_SHA256_RAWSZ
225 #define GIT_MAX_HEXSZ GIT_SHA256_HEXSZ
226 /* The largest possible block size for any supported hash. */
227 #define GIT_MAX_BLKSZ GIT_SHA256_BLKSZ
228
229 struct object_id {
230 unsigned char hash[GIT_MAX_RAWSZ];
231 uint32_t algo; /* XXX requires 4-byte alignment */
232 };
233
234 #define GET_OID_QUIETLY 01
235 #define GET_OID_COMMIT 02
236 #define GET_OID_COMMITTISH 04
237 #define GET_OID_TREE 010
238 #define GET_OID_TREEISH 020
239 #define GET_OID_BLOB 040
240 #define GET_OID_FOLLOW_SYMLINKS 0100
241 #define GET_OID_RECORD_PATH 0200
242 #define GET_OID_ONLY_TO_DIE 04000
243 #define GET_OID_REQUIRE_PATH 010000
244 #define GET_OID_HASH_ANY 020000
245 #define GET_OID_SKIP_AMBIGUITY_CHECK 040000
246 #define GET_OID_GENTLY 0100000
247
248 #define GET_OID_DISAMBIGUATORS \
249 (GET_OID_COMMIT | GET_OID_COMMITTISH | \
250 GET_OID_TREE | GET_OID_TREEISH | \
251 GET_OID_BLOB)
252
253 enum get_oid_result {
254 FOUND = 0,
255 MISSING_OBJECT = -1, /* The requested object is missing */
256 SHORT_NAME_AMBIGUOUS = -2,
257 /* The following only apply when symlinks are followed */
258 DANGLING_SYMLINK = -4, /*
259 * The initial symlink is there, but
260 * (transitively) points to a missing
261 * in-tree file
262 */
263 SYMLINK_LOOP = -5,
264 NOT_DIR = -6, /*
265 * Somewhere along the symlink chain, a path is
266 * requested which contains a file as a
267 * non-final element.
268 */
269 };
270
271 #ifdef USE_THE_REPOSITORY_VARIABLE
272 # include "repository.h"
273 # define the_hash_algo the_repository->hash_algo
274 #endif
275
276 /* A suitably aligned type for stack allocations of hash contexts. */
277 struct git_hash_ctx {
278 const struct git_hash_algo *algop;
279 union {
280 git_SHA_CTX sha1;
281 git_SHA_CTX_unsafe sha1_unsafe;
282 git_SHA256_CTX sha256;
283 } state;
284 bool active;
285 };
286
287 typedef void (*git_hash_init_fn)(struct git_hash_ctx *ctx);
288 typedef void (*git_hash_clone_fn)(struct git_hash_ctx *dst, const struct git_hash_ctx *src);
289 typedef void (*git_hash_update_fn)(struct git_hash_ctx *ctx, const void *in, size_t len);
290 typedef void (*git_hash_final_fn)(unsigned char *hash, struct git_hash_ctx *ctx);
291 typedef void (*git_hash_final_oid_fn)(struct object_id *oid, struct git_hash_ctx *ctx);
292 typedef void (*git_hash_discard_fn)(struct git_hash_ctx *ctx);
293
294 struct git_hash_algo {
295 /*
296 * The name of the algorithm, as appears in the config file and in
297 * messages.
298 */
299 const char *name;
300
301 /* A four-byte version identifier, used in pack indices. */
302 uint32_t format_id;
303
304 /* The length of the hash in binary. */
305 size_t rawsz;
306
307 /* The length of the hash in hex characters. */
308 size_t hexsz;
309
310 /* The block size of the hash. */
311 size_t blksz;
312
313 /*
314 * Low-level implementation hooks. Callers should use the git_hash_*
315 * wrappers below rather than invoking these directly.
316 */
317 git_hash_init_fn init_fn;
318 git_hash_clone_fn clone_fn;
319 git_hash_update_fn update_fn;
320 git_hash_final_fn final_fn;
321 git_hash_final_oid_fn final_oid_fn;
322 git_hash_discard_fn discard_fn;
323
324 /* The OID of the empty tree. */
325 const struct object_id *empty_tree;
326
327 /* The OID of the empty blob. */
328 const struct object_id *empty_blob;
329
330 /* The all-zeros OID. */
331 const struct object_id *null_oid;
332
333 /* The unsafe variant of this hash function, if one exists. */
334 const struct git_hash_algo *unsafe;
335 };
336 extern const struct git_hash_algo hash_algos[GIT_HASH_NALGOS];
337
338 /*
339 * Prepare an uninitialized hash context for use. You must eventually release
340 * the context with git_hash_final() (or final_oid()) or by calling
341 * git_hash_discard().
342 */
343 void git_hash_init(struct git_hash_ctx *ctx, const struct git_hash_algo *algop);
344
345 /*
346 * Clone the state of a hash. Both src and dst must have been initialized with
347 * git_hash_init().
348 */
349 void git_hash_clone(struct git_hash_ctx *dst, const struct git_hash_ctx *src);
350
351 /*
352 * Add more data to an initialized hash context.
353 */
354 void git_hash_update(struct git_hash_ctx *ctx, const void *in, size_t len);
355
356 /*
357 * Retrieve the final hash value from a context, releasing any resources.
358 */
359 void git_hash_final(unsigned char *hash, struct git_hash_ctx *ctx);
360
361 /*
362 * Like git_hash_final(), but write the result into an object_id.
363 */
364 void git_hash_final_oid(struct object_id *oid, struct git_hash_ctx *ctx);
365
366 /*
367 * Discard a hash context without computing the final value, but still
368 * releasing any resources.
369 */
370 void git_hash_discard(struct git_hash_ctx *ctx);
371
372 const struct git_hash_algo *hash_algo_ptr_by_number(uint32_t algo);
373 struct git_hash_ctx *git_hash_alloc(void);
374 void git_hash_free(struct git_hash_ctx *ctx);
375 /*
376 * Return a GIT_HASH_* constant based on the name. Returns GIT_HASH_UNKNOWN if
377 * the name doesn't match a known algorithm.
378 */
379 uint32_t hash_algo_by_name(const char *name);
380 /* Identical, except based on the format ID. */
381 uint32_t hash_algo_by_id(uint32_t format_id);
382 /* Identical, except based on the length. */
383 uint32_t hash_algo_by_length(size_t len);
384 /* Identical, except for a pointer to struct git_hash_algo. */
385 static inline uint32_t hash_algo_by_ptr(const struct git_hash_algo *p)
386 {
387 size_t i;
388 for (i = 0; i < GIT_HASH_NALGOS; i++) {
389 const struct git_hash_algo *algop = &hash_algos[i];
390 if (p == algop)
391 return i;
392 }
393 return GIT_HASH_UNKNOWN;
394 }
395
396 const struct git_hash_algo *unsafe_hash_algo(const struct git_hash_algo *algop);
397
398 const struct object_id *null_oid(const struct git_hash_algo *algop);
399
400 static inline int hashcmp(const unsigned char *sha1, const unsigned char *sha2, const struct git_hash_algo *algop)
401 {
402 /*
403 * Teach the compiler that there are only two possibilities of hash size
404 * here, so that it can optimize for this case as much as possible.
405 */
406 if (algop->rawsz == GIT_MAX_RAWSZ)
407 return memcmp(sha1, sha2, GIT_MAX_RAWSZ);
408 return memcmp(sha1, sha2, GIT_SHA1_RAWSZ);
409 }
410
411 static inline int hasheq(const unsigned char *sha1, const unsigned char *sha2, const struct git_hash_algo *algop)
412 {
413 /*
414 * We write this here instead of deferring to hashcmp so that the
415 * compiler can properly inline it and avoid calling memcmp.
416 */
417 if (algop->rawsz == GIT_MAX_RAWSZ)
418 return !memcmp(sha1, sha2, GIT_MAX_RAWSZ);
419 return !memcmp(sha1, sha2, GIT_SHA1_RAWSZ);
420 }
421
422 static inline void hashcpy(unsigned char *sha_dst, const unsigned char *sha_src,
423 const struct git_hash_algo *algop)
424 {
425 memcpy(sha_dst, sha_src, algop->rawsz);
426 }
427
428 static inline void hashclr(unsigned char *hash, const struct git_hash_algo *algop)
429 {
430 memset(hash, 0, algop->rawsz);
431 }
432
433 static inline int oidcmp(const struct object_id *oid1, const struct object_id *oid2)
434 {
435 return memcmp(oid1->hash, oid2->hash, GIT_MAX_RAWSZ);
436 }
437
438 static inline int oideq(const struct object_id *oid1, const struct object_id *oid2)
439 {
440 return !memcmp(oid1->hash, oid2->hash, GIT_MAX_RAWSZ);
441 }
442
443 unsigned oid_common_prefix_hexlen(const struct object_id *a,
444 const struct object_id *b);
445
446 static inline void oidcpy(struct object_id *dst, const struct object_id *src)
447 {
448 memcpy(dst->hash, src->hash, GIT_MAX_RAWSZ);
449 dst->algo = src->algo;
450 }
451
452 static inline void oidread(struct object_id *oid, const unsigned char *hash,
453 const struct git_hash_algo *algop)
454 {
455 memcpy(oid->hash, hash, algop->rawsz);
456 if (algop->rawsz < GIT_MAX_RAWSZ)
457 memset(oid->hash + algop->rawsz, 0, GIT_MAX_RAWSZ - algop->rawsz);
458 oid->algo = hash_algo_by_ptr(algop);
459 }
460
461 static inline void oidclr(struct object_id *oid,
462 const struct git_hash_algo *algop)
463 {
464 memset(oid->hash, 0, GIT_MAX_RAWSZ);
465 oid->algo = hash_algo_by_ptr(algop);
466 }
467
468 static inline struct object_id *oiddup(const struct object_id *src)
469 {
470 struct object_id *dst = xmalloc(sizeof(struct object_id));
471 oidcpy(dst, src);
472 return dst;
473 }
474
475 static inline void oid_set_algo(struct object_id *oid, const struct git_hash_algo *algop)
476 {
477 oid->algo = hash_algo_by_ptr(algop);
478 }
479
480 /*
481 * Converts a cryptographic hash (e.g. SHA-1) into an int-sized hash code
482 * for use in hash tables. Cryptographic hashes are supposed to have
483 * uniform distribution, so in contrast to `memhash()`, this just copies
484 * the first `sizeof(int)` bytes without shuffling any bits. Note that
485 * the results will be different on big-endian and little-endian
486 * platforms, so they should not be stored or transferred over the net.
487 */
488 static inline unsigned int oidhash(const struct object_id *oid)
489 {
490 /*
491 * Equivalent to 'return *(unsigned int *)oid->hash;', but safe on
492 * platforms that don't support unaligned reads.
493 */
494 unsigned int hash;
495 memcpy(&hash, oid->hash, sizeof(hash));
496 return hash;
497 }
498
499 static inline int is_null_oid(const struct object_id *oid)
500 {
501 static const unsigned char null_hash[GIT_MAX_RAWSZ];
502 return !memcmp(oid->hash, null_hash, GIT_MAX_RAWSZ);
503 }
504
505 const char *empty_tree_oid_hex(const struct git_hash_algo *algop);
506
507 static inline int is_empty_blob_oid(const struct object_id *oid,
508 const struct git_hash_algo *algop)
509 {
510 return oideq(oid, algop->empty_blob);
511 }
512
513 static inline int is_empty_tree_oid(const struct object_id *oid,
514 const struct git_hash_algo *algop)
515 {
516 return oideq(oid, algop->empty_tree);
517 }
518
519 #endif