Fix various memory leaks hit by the pseudo-merge machinery. These leaks are exposed by t5333, but plugging them does not yet make the whole test suite pass. Signed-off-by: Patrick Steinhardt <ps@xxxxxx> --- pack-bitmap-write.c | 8 ++++++++ pack-bitmap.c | 4 ++-- pseudo-merge.c | 19 +++++++++++++++++++ pseudo-merge.h | 2 ++ 4 files changed, 31 insertions(+), 2 deletions(-) diff --git a/pack-bitmap-write.c b/pack-bitmap-write.c index 4dc0fe8e40..6413dd1731 100644 --- a/pack-bitmap-write.c +++ b/pack-bitmap-write.c @@ -64,6 +64,12 @@ static void free_pseudo_merge_commit_idx(struct pseudo_merge_commit_idx *idx) free(idx); } +static void pseudo_merge_group_release_cb(void *payload, const char *name UNUSED) +{ + pseudo_merge_group_release(payload); + free(payload); +} + void bitmap_writer_free(struct bitmap_writer *writer) { uint32_t i; @@ -82,6 +88,8 @@ void bitmap_writer_free(struct bitmap_writer *writer) kh_foreach_value(writer->pseudo_merge_commits, idx, free_pseudo_merge_commit_idx(idx)); kh_destroy_oid_map(writer->pseudo_merge_commits); + string_list_clear_func(&writer->pseudo_merge_groups, + pseudo_merge_group_release_cb); for (i = 0; i < writer->selected_nr; i++) { struct bitmapped_commit *bc = &writer->selected[i]; diff --git a/pack-bitmap.c b/pack-bitmap.c index 9d9b8c4bfb..32b222a7af 100644 --- a/pack-bitmap.c +++ b/pack-bitmap.c @@ -1390,8 +1390,8 @@ static struct bitmap *find_objects(struct bitmap_index *bitmap_git, } base = bitmap_new(); - if (!cascade_pseudo_merges_1(bitmap_git, base, roots_bitmap)) - bitmap_free(roots_bitmap); + cascade_pseudo_merges_1(bitmap_git, base, roots_bitmap); + bitmap_free(roots_bitmap); } /* diff --git a/pseudo-merge.c b/pseudo-merge.c index 10ebd9a4e9..28782a31c6 100644 --- a/pseudo-merge.c +++ b/pseudo-merge.c @@ -97,6 +97,25 @@ static void pseudo_merge_group_init(struct pseudo_merge_group *group) group->stable_size = DEFAULT_PSEUDO_MERGE_STABLE_SIZE; } +void pseudo_merge_group_release(struct pseudo_merge_group *group) +{ + struct hashmap_iter iter; + struct strmap_entry *e; + + regfree(group->pattern); + free(group->pattern); + + strmap_for_each_entry(&group->matches, &iter, e) { + struct pseudo_merge_matches *matches = e->value; + free(matches->stable); + free(matches->unstable); + free(matches); + } + strmap_clear(&group->matches, 0); + + free(group->merges); +} + static int pseudo_merge_config(const char *var, const char *value, const struct config_context *ctx, void *cb_data) diff --git a/pseudo-merge.h b/pseudo-merge.h index 4b5febaa63..29df8a32ec 100644 --- a/pseudo-merge.h +++ b/pseudo-merge.h @@ -51,6 +51,8 @@ struct pseudo_merge_group { timestamp_t stable_threshold; }; +void pseudo_merge_group_release(struct pseudo_merge_group *group); + struct pseudo_merge_matches { struct commit **stable; struct commit **unstable; -- 2.46.2.852.g229c0bf0e5.dirty