Skip to content

Commit 3a37876

Browse files
peffgitster
authored andcommitted
pack-objects: drop packlist index_pos optimization
Once upon a time, the code to add an object to our packing list in pack-objects all lived in a single function. It computed the position within the hash table once, then used it to check if the object was already present, and if not, to add it. Later, in 2834bc2 (pack-objects: refactor the packing list, 2013-10-24), this was split into two functions: packlist_find() and packlist_alloc(). We ended up with an "index_pos" variable that gets passed through several functions to make it from one to the other. The resulting code is rather confusing to follow. The "index_pos" variable is sometimes undefined, if we don't yet have a hash table. This works out in practice because in that case packlist_alloc() won't use it at all, since it will have to create/grow the hash table. But it's hard to verify that, and it does cause gcc 9.2.1's -Wmaybe-uninitialized to complain when compiled with "-flto -O3" (rightfully, since we do pass the uninitialized value as a function parameter, even if nobody ends up using it). All of this is to save computing the hash index again when we're inserting into the hash table, which I found doesn't make a measurable difference in the program runtime (which is not surprising, since we're doing all kinds of other heavyweight things for each object). Let's just drop this index_pos variable entirely, simplifying the code (and pleasing the compiler). We might be better still refactoring this custom hash table to use one of our existing implementations (an oidmap, or a kh_oid_map). I stopped short of that here, but this would be the likely first step towards that anyway. Reported-by: Stephan Beyer <[email protected]> Signed-off-by: Jeff King <[email protected]> Signed-off-by: Junio C Hamano <[email protected]>
1 parent 7e6b96c commit 3a37876

File tree

5 files changed

+29
-34
lines changed

5 files changed

+29
-34
lines changed

builtin/pack-objects.c

Lines changed: 14 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -610,12 +610,12 @@ static int mark_tagged(const char *path, const struct object_id *oid, int flag,
610610
void *cb_data)
611611
{
612612
struct object_id peeled;
613-
struct object_entry *entry = packlist_find(&to_pack, oid, NULL);
613+
struct object_entry *entry = packlist_find(&to_pack, oid);
614614

615615
if (entry)
616616
entry->tagged = 1;
617617
if (!peel_ref(path, &peeled)) {
618-
entry = packlist_find(&to_pack, &peeled, NULL);
618+
entry = packlist_find(&to_pack, &peeled);
619619
if (entry)
620620
entry->tagged = 1;
621621
}
@@ -996,12 +996,11 @@ static int no_try_delta(const char *path)
996996
* few lines later when we want to add the new entry.
997997
*/
998998
static int have_duplicate_entry(const struct object_id *oid,
999-
int exclude,
1000-
uint32_t *index_pos)
999+
int exclude)
10011000
{
10021001
struct object_entry *entry;
10031002

1004-
entry = packlist_find(&to_pack, oid, index_pos);
1003+
entry = packlist_find(&to_pack, oid);
10051004
if (!entry)
10061005
return 0;
10071006

@@ -1141,13 +1140,12 @@ static void create_object_entry(const struct object_id *oid,
11411140
uint32_t hash,
11421141
int exclude,
11431142
int no_try_delta,
1144-
uint32_t index_pos,
11451143
struct packed_git *found_pack,
11461144
off_t found_offset)
11471145
{
11481146
struct object_entry *entry;
11491147

1150-
entry = packlist_alloc(&to_pack, oid, index_pos);
1148+
entry = packlist_alloc(&to_pack, oid);
11511149
entry->hash = hash;
11521150
oe_set_type(entry, type);
11531151
if (exclude)
@@ -1171,11 +1169,10 @@ static int add_object_entry(const struct object_id *oid, enum object_type type,
11711169
{
11721170
struct packed_git *found_pack = NULL;
11731171
off_t found_offset = 0;
1174-
uint32_t index_pos;
11751172

11761173
display_progress(progress_state, ++nr_seen);
11771174

1178-
if (have_duplicate_entry(oid, exclude, &index_pos))
1175+
if (have_duplicate_entry(oid, exclude))
11791176
return 0;
11801177

11811178
if (!want_object_in_pack(oid, exclude, &found_pack, &found_offset)) {
@@ -1190,7 +1187,7 @@ static int add_object_entry(const struct object_id *oid, enum object_type type,
11901187

11911188
create_object_entry(oid, type, pack_name_hash(name),
11921189
exclude, name && no_try_delta(name),
1193-
index_pos, found_pack, found_offset);
1190+
found_pack, found_offset);
11941191
return 1;
11951192
}
11961193

@@ -1199,17 +1196,15 @@ static int add_object_entry_from_bitmap(const struct object_id *oid,
11991196
int flags, uint32_t name_hash,
12001197
struct packed_git *pack, off_t offset)
12011198
{
1202-
uint32_t index_pos;
1203-
12041199
display_progress(progress_state, ++nr_seen);
12051200

1206-
if (have_duplicate_entry(oid, 0, &index_pos))
1201+
if (have_duplicate_entry(oid, 0))
12071202
return 0;
12081203

12091204
if (!want_object_in_pack(oid, 0, &pack, &offset))
12101205
return 0;
12111206

1212-
create_object_entry(oid, type, name_hash, 0, 0, index_pos, pack, offset);
1207+
create_object_entry(oid, type, name_hash, 0, 0, pack, offset);
12131208
return 1;
12141209
}
12151210

@@ -1507,7 +1502,7 @@ static int can_reuse_delta(const unsigned char *base_sha1,
15071502
* First see if we're already sending the base (or it's explicitly in
15081503
* our "excluded" list).
15091504
*/
1510-
base = packlist_find(&to_pack, &base_oid, NULL);
1505+
base = packlist_find(&to_pack, &base_oid);
15111506
if (base) {
15121507
if (!in_same_island(&delta->idx.oid, &base->idx.oid))
15131508
return 0;
@@ -2579,7 +2574,7 @@ static void add_tag_chain(const struct object_id *oid)
25792574
* it was included via bitmaps, we would not have parsed it
25802575
* previously).
25812576
*/
2582-
if (packlist_find(&to_pack, oid, NULL))
2577+
if (packlist_find(&to_pack, oid))
25832578
return;
25842579

25852580
tag = lookup_tag(the_repository, oid);
@@ -2603,7 +2598,7 @@ static int add_ref_tag(const char *path, const struct object_id *oid, int flag,
26032598

26042599
if (starts_with(path, "refs/tags/") && /* is a tag? */
26052600
!peel_ref(path, &peeled) && /* peelable? */
2606-
packlist_find(&to_pack, &peeled, NULL)) /* object packed? */
2601+
packlist_find(&to_pack, &peeled)) /* object packed? */
26072602
add_tag_chain(oid);
26082603
return 0;
26092604
}
@@ -2803,7 +2798,7 @@ static void show_object(struct object *obj, const char *name, void *data)
28032798
for (p = strchr(name, '/'); p; p = strchr(p + 1, '/'))
28042799
depth++;
28052800

2806-
ent = packlist_find(&to_pack, &obj->oid, NULL);
2801+
ent = packlist_find(&to_pack, &obj->oid);
28072802
if (ent && depth > oe_tree_depth(&to_pack, ent))
28082803
oe_set_tree_depth(&to_pack, ent, depth);
28092804
}
@@ -3034,7 +3029,7 @@ static void loosen_unused_packed_objects(void)
30343029

30353030
for (i = 0; i < p->num_objects; i++) {
30363031
nth_packed_object_oid(&oid, p, i);
3037-
if (!packlist_find(&to_pack, &oid, NULL) &&
3032+
if (!packlist_find(&to_pack, &oid) &&
30383033
!has_sha1_pack_kept_or_nonlocal(&oid) &&
30393034
!loosened_object_can_be_discarded(&oid, p->mtime))
30403035
if (force_object_loose(&oid, p->mtime))

pack-bitmap-write.c

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -144,7 +144,7 @@ static inline void reset_all_seen(void)
144144

145145
static uint32_t find_object_pos(const struct object_id *oid)
146146
{
147-
struct object_entry *entry = packlist_find(writer.to_pack, oid, NULL);
147+
struct object_entry *entry = packlist_find(writer.to_pack, oid);
148148

149149
if (!entry) {
150150
die("Failed to write bitmap index. Packfile doesn't have full closure "

pack-bitmap.c

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1063,7 +1063,7 @@ int rebuild_existing_bitmaps(struct bitmap_index *bitmap_git,
10631063

10641064
entry = &bitmap_git->pack->revindex[i];
10651065
nth_packed_object_oid(&oid, bitmap_git->pack, entry->nr);
1066-
oe = packlist_find(mapping, &oid, NULL);
1066+
oe = packlist_find(mapping, &oid);
10671067

10681068
if (oe)
10691069
reposition[i] = oe_in_pack_pos(mapping, oe) + 1;

pack-objects.c

Lines changed: 11 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -68,8 +68,7 @@ static void rehash_objects(struct packing_data *pdata)
6868
}
6969

7070
struct object_entry *packlist_find(struct packing_data *pdata,
71-
const struct object_id *oid,
72-
uint32_t *index_pos)
71+
const struct object_id *oid)
7372
{
7473
uint32_t i;
7574
int found;
@@ -79,9 +78,6 @@ struct object_entry *packlist_find(struct packing_data *pdata,
7978

8079
i = locate_object_entry_hash(pdata, oid, &found);
8180

82-
if (index_pos)
83-
*index_pos = i;
84-
8581
if (!found)
8682
return NULL;
8783

@@ -153,8 +149,7 @@ void prepare_packing_data(struct repository *r, struct packing_data *pdata)
153149
}
154150

155151
struct object_entry *packlist_alloc(struct packing_data *pdata,
156-
const struct object_id *oid,
157-
uint32_t index_pos)
152+
const struct object_id *oid)
158153
{
159154
struct object_entry *new_entry;
160155

@@ -181,8 +176,15 @@ struct object_entry *packlist_alloc(struct packing_data *pdata,
181176

182177
if (pdata->index_size * 3 <= pdata->nr_objects * 4)
183178
rehash_objects(pdata);
184-
else
185-
pdata->index[index_pos] = pdata->nr_objects;
179+
else {
180+
int found;
181+
uint32_t pos = locate_object_entry_hash(pdata,
182+
&new_entry->idx.oid,
183+
&found);
184+
if (found)
185+
BUG("duplicate object inserted into hash");
186+
pdata->index[pos] = pdata->nr_objects;
187+
}
186188

187189
if (pdata->in_pack)
188190
pdata->in_pack[pdata->nr_objects - 1] = NULL;

pack-objects.h

Lines changed: 2 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -183,12 +183,10 @@ static inline void packing_data_unlock(struct packing_data *pdata)
183183
}
184184

185185
struct object_entry *packlist_alloc(struct packing_data *pdata,
186-
const struct object_id *oid,
187-
uint32_t index_pos);
186+
const struct object_id *oid);
188187

189188
struct object_entry *packlist_find(struct packing_data *pdata,
190-
const struct object_id *oid,
191-
uint32_t *index_pos);
189+
const struct object_id *oid);
192190

193191
static inline uint32_t pack_name_hash(const char *name)
194192
{

0 commit comments

Comments
 (0)