| 188 | } |
| 189 | |
| 190 | int load_idx(const char *path, const unsigned int hashsz, void *idx_map, |
| 191 | size_t idx_size, struct packed_git *p) |
| 192 | { |
| 193 | struct pack_idx_header *hdr = idx_map; |
| 194 | uint32_t version, nr, i, *index; |
| 195 | |
| 196 | if (idx_size < 4 * 256 + hashsz + hashsz) |
| 197 | return error("index file %s is too small", path); |
| 198 | if (!idx_map) |
| 199 | return error("empty data"); |
| 200 | |
| 201 | if (hdr->idx_signature == htonl(PACK_IDX_SIGNATURE)) { |
| 202 | version = ntohl(hdr->idx_version); |
| 203 | if (version < 2 || version > 2) |
| 204 | return error("index file %s is version %"PRIu32 |
| 205 | " and is not supported by this binary" |
| 206 | " (try upgrading GIT to a newer version)", |
| 207 | path, version); |
| 208 | } else |
| 209 | version = 1; |
| 210 | |
| 211 | nr = 0; |
| 212 | index = idx_map; |
| 213 | if (version > 1) |
| 214 | index += 2; /* skip index header */ |
| 215 | for (i = 0; i < 256; i++) { |
| 216 | uint32_t n = ntohl(index[i]); |
| 217 | if (n < nr) |
| 218 | return error("non-monotonic index %s", path); |
| 219 | nr = n; |
| 220 | } |
| 221 | |
| 222 | if (version == 1) { |
| 223 | /* |
| 224 | * Total size: |
| 225 | * - 256 index entries 4 bytes each |
| 226 | * - 24-byte entries * nr (object ID + 4-byte offset) |
| 227 | * - hash of the packfile |
| 228 | * - file checksum |
| 229 | */ |
| 230 | if (idx_size != st_add(4 * 256 + hashsz + hashsz, st_mult(nr, hashsz + 4))) |
| 231 | return error("wrong index v1 file size in %s", path); |
| 232 | } else if (version == 2) { |
| 233 | /* |
| 234 | * Minimum size: |
| 235 | * - 8 bytes of header |
| 236 | * - 256 index entries 4 bytes each |
| 237 | * - object ID entry * nr |
| 238 | * - 4-byte crc entry * nr |
| 239 | * - 4-byte offset entry * nr |
| 240 | * - hash of the packfile |
| 241 | * - file checksum |
| 242 | * And after the 4-byte offset table might be a |
| 243 | * variable sized table containing 8-byte entries |
| 244 | * for offsets larger than 2^31. |
| 245 | */ |
| 246 | size_t min_size = st_add(8 + 4*256 + hashsz + hashsz, st_mult(nr, hashsz + 4 + 4)); |
| 247 | size_t max_size = min_size; |
no test coverage detected