struct pack_list *next;
struct packed_git *pack;
struct llist *unique_objects;
- struct llist *all_objects;
+ struct llist *remaining_objects;
+ size_t all_objects_size;
} *local_packs = NULL, *altodb_packs = NULL;
static struct llist_item *free_nodes;
l = (hint == NULL) ? list->front : hint;
prev = NULL;
while (l) {
- int cmp = oidcmp(l->oid, oid);
+ const int cmp = oidcmp(l->oid, oid);
if (cmp > 0) /* not in list, since sorted */
return prev;
if (!cmp) { /* found */
const unsigned int hashsz = the_hash_algo->rawsz;
if (!p1->unique_objects)
- p1->unique_objects = llist_copy(p1->all_objects);
+ p1->unique_objects = llist_copy(p1->remaining_objects);
if (!p2->unique_objects)
- p2->unique_objects = llist_copy(p2->all_objects);
+ p2->unique_objects = llist_copy(p2->remaining_objects);
p1_base = p1->pack->index_data;
p2_base = p2->pack->index_data;
while (p1_off < p1->pack->num_objects * p1_step &&
p2_off < p2->pack->num_objects * p2_step)
{
- int cmp = hashcmp(p1_base + p1_off, p2_base + p2_off);
+ const int cmp = hashcmp(p1_base + p1_off, p2_base + p2_off);
/* cmp ~ p1 - p2 */
if (cmp == 0) {
p1_hint = llist_sorted_remove(p1->unique_objects,
return ret;
}
-static int cmp_pack_list_reverse(const void *a, const void *b)
+static int cmp_remaining_objects(const void *a, const void *b)
{
struct pack_list *pl_a = *((struct pack_list **)a);
struct pack_list *pl_b = *((struct pack_list **)b);
- size_t sz_a = pl_a->all_objects->size;
- size_t sz_b = pl_b->all_objects->size;
- if (sz_a == sz_b)
- return 0;
- else if (sz_a < sz_b)
+ if (pl_a->remaining_objects->size == pl_b->remaining_objects->size) {
+ /* have the same remaining_objects, big pack first */
+ if (pl_a->all_objects_size == pl_b->all_objects_size)
+ return 0;
+ else if (pl_a->all_objects_size < pl_b->all_objects_size)
+ return 1;
+ else
+ return -1;
+ } else if (pl_a->remaining_objects->size < pl_b->remaining_objects->size) {
+ /* sort by remaining objects, more objects first */
return 1;
- else
+ } else {
return -1;
+ }
}
-/* Sort pack_list, greater size of all_objects first */
+/* Sort pack_list, greater size of remaining_objects first */
static void sort_pack_list(struct pack_list **pl)
{
struct pack_list **ary, *p;
for (n = 0, p = *pl; p; p = p->next)
ary[n++] = p;
- QSORT(ary, n, cmp_pack_list_reverse);
+ QSORT(ary, n, cmp_remaining_objects);
/* link them back again */
for (i = 0; i < n - 1; i++)
missing = llist_copy(all_objects);
pl = unique;
while (pl) {
- llist_sorted_difference_inplace(missing, pl->all_objects);
+ llist_sorted_difference_inplace(missing, pl->remaining_objects);
pl = pl->next;
}
/* remove unique pack objects from the non_unique packs */
pl = non_unique;
while (pl) {
- llist_sorted_difference_inplace(pl->all_objects, unique_pack_objects);
+ llist_sorted_difference_inplace(pl->remaining_objects, unique_pack_objects);
pl = pl->next;
}
while (non_unique) {
- /* sort the non_unique packs, greater size of all_objects first */
+ /* sort the non_unique packs, greater size of remaining_objects first */
sort_pack_list(&non_unique);
- if (non_unique->all_objects->size == 0)
+ if (non_unique->remaining_objects->size == 0)
break;
pack_list_insert(min, non_unique);
- for (pl = non_unique->next; pl && pl->all_objects->size > 0; pl = pl->next)
- llist_sorted_difference_inplace(pl->all_objects, non_unique->all_objects);
+ for (pl = non_unique->next; pl && pl->remaining_objects->size > 0; pl = pl->next)
+ llist_sorted_difference_inplace(pl->remaining_objects, non_unique->remaining_objects);
non_unique = non_unique->next;
}
while (pl) {
hint = NULL;
- l = pl->all_objects->front;
+ l = pl->remaining_objects->front;
while (l) {
hint = llist_insert_sorted_unique(all_objects,
l->oid, hint);
/* remove objects present in remote packs */
pl = altodb_packs;
while (pl) {
- llist_sorted_difference_inplace(all_objects, pl->all_objects);
+ llist_sorted_difference_inplace(all_objects, pl->remaining_objects);
pl = pl->next;
}
}
while (alt) {
local = local_packs;
while (local) {
- llist_sorted_difference_inplace(local->all_objects,
- alt->all_objects);
+ llist_sorted_difference_inplace(local->remaining_objects,
+ alt->remaining_objects);
local = local->next;
}
alt = alt->next;
return NULL;
l.pack = p;
- llist_init(&l.all_objects);
+ llist_init(&l.remaining_objects);
if (open_pack_index(p))
return NULL;
base += 256 * 4 + ((p->index_version < 2) ? 4 : 8);
step = the_hash_algo->rawsz + ((p->index_version < 2) ? 4 : 0);
while (off < p->num_objects * step) {
- llist_insert_back(l.all_objects, (const struct object_id *)(base + off));
+ llist_insert_back(l.remaining_objects, (const struct object_id *)(base + off));
off += step;
}
+ l.all_objects_size = l.remaining_objects->size;
l.unique_objects = NULL;
if (p->pack_local)
return pack_list_insert(&local_packs, &l);
llist_sorted_difference_inplace(all_objects, ignore);
pl = local_packs;
while (pl) {
- llist_sorted_difference_inplace(pl->all_objects, ignore);
+ llist_sorted_difference_inplace(pl->remaining_objects, ignore);
pl = pl->next;
}