Git fork
at reftables-rust 215 lines 7.1 kB view raw
1#ifndef COMMIT_GRAPH_H 2#define COMMIT_GRAPH_H 3 4#include "odb.h" 5#include "oidset.h" 6 7#define GIT_TEST_COMMIT_GRAPH "GIT_TEST_COMMIT_GRAPH" 8#define GIT_TEST_COMMIT_GRAPH_DIE_ON_PARSE "GIT_TEST_COMMIT_GRAPH_DIE_ON_PARSE" 9#define GIT_TEST_COMMIT_GRAPH_CHANGED_PATHS "GIT_TEST_COMMIT_GRAPH_CHANGED_PATHS" 10 11/* 12 * This environment variable controls whether commits looked up via the 13 * commit graph will be double checked to exist in the object database. 14 */ 15#define GIT_COMMIT_GRAPH_PARANOIA "GIT_COMMIT_GRAPH_PARANOIA" 16 17/* 18 * This method is only used to enhance coverage of the commit-graph 19 * feature in the test suite with the GIT_TEST_COMMIT_GRAPH and 20 * GIT_TEST_COMMIT_GRAPH_CHANGED_PATHS environment variables. Do not 21 * call this method oustide of a builtin, and only if you know what 22 * you are doing! 23 */ 24void git_test_write_commit_graph_or_die(struct odb_source *source); 25 26struct commit; 27struct bloom_filter_settings; 28struct repository; 29struct object_database; 30struct string_list; 31 32char *get_commit_graph_filename(struct odb_source *source); 33char *get_commit_graph_chain_filename(struct odb_source *source); 34int open_commit_graph(const char *graph_file, int *fd, struct stat *st); 35int open_commit_graph_chain(const char *chain_file, int *fd, struct stat *st, 36 const struct git_hash_algo *hash_algo); 37 38/* 39 * Given a commit struct, try to fill the commit struct info, including: 40 * 1. tree object 41 * 2. date 42 * 3. parents. 43 * 44 * Returns 1 if and only if the commit was found in the packed graph. 45 * 46 * See parse_commit_buffer() for the fallback after this call. 47 */ 48int parse_commit_in_graph(struct repository *r, struct commit *item); 49 50/* 51 * Fills `*pos` with the graph position of `c`, and returns the graph `c` is 52 * found in, or NULL otherwise. Initializes the commit-graphs belonging to 53 * `r` if it hasn't been already. 54 * 55 * Note: this is a low-level helper that does not alter any slab data 56 * associated with `c`. Useful in circumstances where the slab data is 57 * already being modified (e.g., writing the commit-graph itself). 58 * 59 * In most cases, callers should use `parse_commit_in_graph()` instead. 60 */ 61struct commit_graph *repo_find_commit_pos_in_graph(struct repository *r, 62 struct commit *c, 63 uint32_t *pos); 64 65/* 66 * Look up the given commit ID in the commit-graph. This will only return a 67 * commit if the ID exists both in the graph and in the object database such 68 * that we don't return commits whose object has been pruned. Otherwise, this 69 * function returns `NULL`. 70 */ 71struct commit *lookup_commit_in_graph(struct repository *repo, const struct object_id *id); 72 73/* 74 * It is possible that we loaded commit contents from the commit buffer, 75 * but we also want to ensure the commit-graph content is correctly 76 * checked and filled. Fill the graph_pos and generation members of 77 * the given commit. 78 */ 79void load_commit_graph_info(struct repository *r, struct commit *item); 80 81struct tree *get_commit_tree_in_graph(struct repository *r, 82 const struct commit *c); 83 84struct commit_graph { 85 const unsigned char *data; 86 size_t data_len; 87 88 const struct git_hash_algo *hash_algo; 89 unsigned char num_chunks; 90 uint32_t num_commits; 91 struct object_id oid; 92 char *filename; 93 struct odb_source *odb_source; 94 95 uint32_t num_commits_in_base; 96 unsigned int read_generation_data; 97 struct commit_graph *base_graph; 98 99 const uint32_t *chunk_oid_fanout; 100 const unsigned char *chunk_oid_lookup; 101 const unsigned char *chunk_commit_data; 102 const unsigned char *chunk_generation_data; 103 const unsigned char *chunk_generation_data_overflow; 104 size_t chunk_generation_data_overflow_size; 105 const unsigned char *chunk_extra_edges; 106 size_t chunk_extra_edges_size; 107 const unsigned char *chunk_base_graphs; 108 size_t chunk_base_graphs_size; 109 const unsigned char *chunk_bloom_indexes; 110 const unsigned char *chunk_bloom_data; 111 size_t chunk_bloom_data_size; 112 113 struct topo_level_slab *topo_levels; 114 struct bloom_filter_settings *bloom_filter_settings; 115}; 116 117struct commit_graph *load_commit_graph_one_fd_st(struct odb_source *source, 118 int fd, struct stat *st); 119struct commit_graph *load_commit_graph_chain_fd_st(struct object_database *odb, 120 int fd, struct stat *st, 121 int *incomplete_chain); 122struct commit_graph *read_commit_graph_one(struct odb_source *source); 123 124struct repo_settings; 125 126/* 127 * Callers should initialize the repo_settings with prepare_repo_settings() 128 * prior to calling parse_commit_graph(). 129 */ 130struct commit_graph *parse_commit_graph(struct repository *r, 131 void *graph_map, size_t graph_size); 132 133/* 134 * Return 1 if and only if the repository has a commit-graph 135 * file and generation numbers are computed in that file. 136 */ 137int generation_numbers_enabled(struct repository *r); 138 139/* 140 * Return 1 if and only if the repository has a commit-graph 141 * file and generation data chunk has been written for the file. 142 */ 143int corrected_commit_dates_enabled(struct repository *r); 144 145struct bloom_filter_settings *get_bloom_filter_settings(struct repository *r); 146 147enum commit_graph_write_flags { 148 COMMIT_GRAPH_WRITE_APPEND = (1 << 0), 149 COMMIT_GRAPH_WRITE_PROGRESS = (1 << 1), 150 COMMIT_GRAPH_WRITE_SPLIT = (1 << 2), 151 COMMIT_GRAPH_WRITE_BLOOM_FILTERS = (1 << 3), 152 COMMIT_GRAPH_NO_WRITE_BLOOM_FILTERS = (1 << 4), 153}; 154 155enum commit_graph_split_flags { 156 COMMIT_GRAPH_SPLIT_UNSPECIFIED = 0, 157 COMMIT_GRAPH_SPLIT_MERGE_PROHIBITED = 1, 158 COMMIT_GRAPH_SPLIT_REPLACE = 2 159}; 160 161struct commit_graph_opts { 162 int size_multiple; 163 int max_commits; 164 timestamp_t expire_time; 165 enum commit_graph_split_flags split_flags; 166 int max_new_filters; 167}; 168 169/* 170 * The write_commit_graph* methods return zero on success 171 * and a negative value on failure. Note that if the repository 172 * is not compatible with the commit-graph feature, then the 173 * methods will return 0 without writing a commit-graph. 174 */ 175int write_commit_graph_reachable(struct odb_source *source, 176 enum commit_graph_write_flags flags, 177 const struct commit_graph_opts *opts); 178int write_commit_graph(struct odb_source *source, 179 const struct string_list *pack_indexes, 180 struct oidset *commits, 181 enum commit_graph_write_flags flags, 182 const struct commit_graph_opts *opts); 183 184#define COMMIT_GRAPH_VERIFY_SHALLOW (1 << 0) 185 186int verify_commit_graph(struct commit_graph *g, int flags); 187 188void close_commit_graph(struct object_database *); 189void free_commit_graph(struct commit_graph *); 190 191/* 192 * Disable further use of the commit graph in this process when parsing a 193 * "struct commit". 194 */ 195void disable_commit_graph(struct repository *r); 196 197struct commit_graph_data { 198 uint32_t graph_pos; 199 timestamp_t generation; 200}; 201 202/* 203 * Commits should be parsed before accessing generation, graph positions. 204 */ 205timestamp_t commit_graph_generation(const struct commit *); 206uint32_t commit_graph_position(const struct commit *); 207 208/* 209 * After this method, all commits reachable from those in the given 210 * list will have non-zero, non-infinite generation numbers. 211 */ 212void ensure_generations_valid(struct repository *r, 213 struct commit **commits, size_t nr); 214 215#endif