pack: move find_pack_entry_one(), is_pack_valid()
Signed-off-by: Jonathan Tan <jonathantanmy@google.com> Signed-off-by: Junio C Hamano <gitster@pobox.com>
This commit is contained in:

committed by
Junio C Hamano

parent
9e0f45f5a6
commit
a2551953b9
8
cache.h
8
cache.h
@ -1620,14 +1620,6 @@ extern int odb_mkstemp(struct strbuf *template, const char *pattern);
|
|||||||
*/
|
*/
|
||||||
extern int odb_pack_keep(const char *name);
|
extern int odb_pack_keep(const char *name);
|
||||||
|
|
||||||
/*
|
|
||||||
* If the object named sha1 is present in the specified packfile,
|
|
||||||
* return its offset within the packfile; otherwise, return 0.
|
|
||||||
*/
|
|
||||||
extern off_t find_pack_entry_one(const unsigned char *sha1, struct packed_git *);
|
|
||||||
|
|
||||||
extern int is_pack_valid(struct packed_git *);
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Iterate over the files in the loose-object parts of the object
|
* Iterate over the files in the loose-object parts of the object
|
||||||
* directory "path", triggering the following callbacks:
|
* directory "path", triggering the following callbacks:
|
||||||
|
76
packfile.c
76
packfile.c
@ -7,6 +7,7 @@
|
|||||||
#include "delta.h"
|
#include "delta.h"
|
||||||
#include "list.h"
|
#include "list.h"
|
||||||
#include "streaming.h"
|
#include "streaming.h"
|
||||||
|
#include "sha1-lookup.h"
|
||||||
|
|
||||||
char *odb_pack_name(struct strbuf *buf,
|
char *odb_pack_name(struct strbuf *buf,
|
||||||
const unsigned char *sha1,
|
const unsigned char *sha1,
|
||||||
@ -509,7 +510,7 @@ static int open_packed_git_1(struct packed_git *p)
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
int open_packed_git(struct packed_git *p)
|
static int open_packed_git(struct packed_git *p)
|
||||||
{
|
{
|
||||||
if (!open_packed_git_1(p))
|
if (!open_packed_git_1(p))
|
||||||
return 0;
|
return 0;
|
||||||
@ -1700,3 +1701,76 @@ off_t nth_packed_object_offset(const struct packed_git *p, uint32_t n)
|
|||||||
ntohl(*((uint32_t *)(index + 4)));
|
ntohl(*((uint32_t *)(index + 4)));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
off_t find_pack_entry_one(const unsigned char *sha1,
|
||||||
|
struct packed_git *p)
|
||||||
|
{
|
||||||
|
const uint32_t *level1_ofs = p->index_data;
|
||||||
|
const unsigned char *index = p->index_data;
|
||||||
|
unsigned hi, lo, stride;
|
||||||
|
static int debug_lookup = -1;
|
||||||
|
|
||||||
|
if (debug_lookup < 0)
|
||||||
|
debug_lookup = !!getenv("GIT_DEBUG_LOOKUP");
|
||||||
|
|
||||||
|
if (!index) {
|
||||||
|
if (open_pack_index(p))
|
||||||
|
return 0;
|
||||||
|
level1_ofs = p->index_data;
|
||||||
|
index = p->index_data;
|
||||||
|
}
|
||||||
|
if (p->index_version > 1) {
|
||||||
|
level1_ofs += 2;
|
||||||
|
index += 8;
|
||||||
|
}
|
||||||
|
index += 4 * 256;
|
||||||
|
hi = ntohl(level1_ofs[*sha1]);
|
||||||
|
lo = ((*sha1 == 0x0) ? 0 : ntohl(level1_ofs[*sha1 - 1]));
|
||||||
|
if (p->index_version > 1) {
|
||||||
|
stride = 20;
|
||||||
|
} else {
|
||||||
|
stride = 24;
|
||||||
|
index += 4;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (debug_lookup)
|
||||||
|
printf("%02x%02x%02x... lo %u hi %u nr %"PRIu32"\n",
|
||||||
|
sha1[0], sha1[1], sha1[2], lo, hi, p->num_objects);
|
||||||
|
|
||||||
|
while (lo < hi) {
|
||||||
|
unsigned mi = (lo + hi) / 2;
|
||||||
|
int cmp = hashcmp(index + mi * stride, sha1);
|
||||||
|
|
||||||
|
if (debug_lookup)
|
||||||
|
printf("lo %u hi %u rg %u mi %u\n",
|
||||||
|
lo, hi, hi - lo, mi);
|
||||||
|
if (!cmp)
|
||||||
|
return nth_packed_object_offset(p, mi);
|
||||||
|
if (cmp > 0)
|
||||||
|
hi = mi;
|
||||||
|
else
|
||||||
|
lo = mi+1;
|
||||||
|
}
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
int is_pack_valid(struct packed_git *p)
|
||||||
|
{
|
||||||
|
/* An already open pack is known to be valid. */
|
||||||
|
if (p->pack_fd != -1)
|
||||||
|
return 1;
|
||||||
|
|
||||||
|
/* If the pack has one window completely covering the
|
||||||
|
* file size, the pack is known to be valid even if
|
||||||
|
* the descriptor is not currently open.
|
||||||
|
*/
|
||||||
|
if (p->windows) {
|
||||||
|
struct pack_window *w = p->windows;
|
||||||
|
|
||||||
|
if (!w->offset && w->len == p->pack_size)
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Force the pack to open to prove its valid. */
|
||||||
|
return !open_packed_git(p);
|
||||||
|
}
|
||||||
|
@ -93,6 +93,13 @@ extern const struct object_id *nth_packed_object_oid(struct object_id *, struct
|
|||||||
*/
|
*/
|
||||||
extern off_t nth_packed_object_offset(const struct packed_git *, uint32_t n);
|
extern off_t nth_packed_object_offset(const struct packed_git *, uint32_t n);
|
||||||
|
|
||||||
|
/*
|
||||||
|
* If the object named sha1 is present in the specified packfile,
|
||||||
|
* return its offset within the packfile; otherwise, return 0.
|
||||||
|
*/
|
||||||
|
extern off_t find_pack_entry_one(const unsigned char *sha1, struct packed_git *);
|
||||||
|
|
||||||
|
extern int is_pack_valid(struct packed_git *);
|
||||||
extern void *unpack_entry(struct packed_git *, off_t, enum object_type *, unsigned long *);
|
extern void *unpack_entry(struct packed_git *, off_t, enum object_type *, unsigned long *);
|
||||||
extern unsigned long unpack_object_header_buffer(const unsigned char *buf, unsigned long len, enum object_type *type, unsigned long *sizep);
|
extern unsigned long unpack_object_header_buffer(const unsigned char *buf, unsigned long len, enum object_type *type, unsigned long *sizep);
|
||||||
extern unsigned long get_size_from_delta(struct packed_git *, struct pack_window **, off_t);
|
extern unsigned long get_size_from_delta(struct packed_git *, struct pack_window **, off_t);
|
||||||
@ -100,8 +107,6 @@ extern int unpack_object_header(struct packed_git *, struct pack_window **, off_
|
|||||||
|
|
||||||
extern void release_pack_memory(size_t);
|
extern void release_pack_memory(size_t);
|
||||||
|
|
||||||
extern int open_packed_git(struct packed_git *p);
|
|
||||||
|
|
||||||
/* global flag to enable extra checks when accessing packed objects */
|
/* global flag to enable extra checks when accessing packed objects */
|
||||||
extern int do_check_packed_object_crc;
|
extern int do_check_packed_object_crc;
|
||||||
|
|
||||||
|
73
sha1_file.c
73
sha1_file.c
@ -1075,79 +1075,6 @@ int parse_sha1_header(const char *hdr, unsigned long *sizep)
|
|||||||
return parse_sha1_header_extended(hdr, &oi, 0);
|
return parse_sha1_header_extended(hdr, &oi, 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
off_t find_pack_entry_one(const unsigned char *sha1,
|
|
||||||
struct packed_git *p)
|
|
||||||
{
|
|
||||||
const uint32_t *level1_ofs = p->index_data;
|
|
||||||
const unsigned char *index = p->index_data;
|
|
||||||
unsigned hi, lo, stride;
|
|
||||||
static int debug_lookup = -1;
|
|
||||||
|
|
||||||
if (debug_lookup < 0)
|
|
||||||
debug_lookup = !!getenv("GIT_DEBUG_LOOKUP");
|
|
||||||
|
|
||||||
if (!index) {
|
|
||||||
if (open_pack_index(p))
|
|
||||||
return 0;
|
|
||||||
level1_ofs = p->index_data;
|
|
||||||
index = p->index_data;
|
|
||||||
}
|
|
||||||
if (p->index_version > 1) {
|
|
||||||
level1_ofs += 2;
|
|
||||||
index += 8;
|
|
||||||
}
|
|
||||||
index += 4 * 256;
|
|
||||||
hi = ntohl(level1_ofs[*sha1]);
|
|
||||||
lo = ((*sha1 == 0x0) ? 0 : ntohl(level1_ofs[*sha1 - 1]));
|
|
||||||
if (p->index_version > 1) {
|
|
||||||
stride = 20;
|
|
||||||
} else {
|
|
||||||
stride = 24;
|
|
||||||
index += 4;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (debug_lookup)
|
|
||||||
printf("%02x%02x%02x... lo %u hi %u nr %"PRIu32"\n",
|
|
||||||
sha1[0], sha1[1], sha1[2], lo, hi, p->num_objects);
|
|
||||||
|
|
||||||
while (lo < hi) {
|
|
||||||
unsigned mi = (lo + hi) / 2;
|
|
||||||
int cmp = hashcmp(index + mi * stride, sha1);
|
|
||||||
|
|
||||||
if (debug_lookup)
|
|
||||||
printf("lo %u hi %u rg %u mi %u\n",
|
|
||||||
lo, hi, hi - lo, mi);
|
|
||||||
if (!cmp)
|
|
||||||
return nth_packed_object_offset(p, mi);
|
|
||||||
if (cmp > 0)
|
|
||||||
hi = mi;
|
|
||||||
else
|
|
||||||
lo = mi+1;
|
|
||||||
}
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
int is_pack_valid(struct packed_git *p)
|
|
||||||
{
|
|
||||||
/* An already open pack is known to be valid. */
|
|
||||||
if (p->pack_fd != -1)
|
|
||||||
return 1;
|
|
||||||
|
|
||||||
/* If the pack has one window completely covering the
|
|
||||||
* file size, the pack is known to be valid even if
|
|
||||||
* the descriptor is not currently open.
|
|
||||||
*/
|
|
||||||
if (p->windows) {
|
|
||||||
struct pack_window *w = p->windows;
|
|
||||||
|
|
||||||
if (!w->offset && w->len == p->pack_size)
|
|
||||||
return 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Force the pack to open to prove its valid. */
|
|
||||||
return !open_packed_git(p);
|
|
||||||
}
|
|
||||||
|
|
||||||
static int fill_pack_entry(const unsigned char *sha1,
|
static int fill_pack_entry(const unsigned char *sha1,
|
||||||
struct pack_entry *e,
|
struct pack_entry *e,
|
||||||
struct packed_git *p)
|
struct packed_git *p)
|
||||||
|
Reference in New Issue
Block a user