diff options
Diffstat (limited to 'src/backend')
-rw-r--r-- | src/backend/optimizer/path/joinrels.c | 15 | ||||
-rw-r--r-- | src/backend/optimizer/util/relnode.c | 18 |
2 files changed, 14 insertions, 19 deletions
diff --git a/src/backend/optimizer/path/joinrels.c b/src/backend/optimizer/path/joinrels.c index a3677f824fe..7db5e30eef8 100644 --- a/src/backend/optimizer/path/joinrels.c +++ b/src/backend/optimizer/path/joinrels.c @@ -1547,6 +1547,7 @@ try_partitionwise_join(PlannerInfo *root, RelOptInfo *rel1, RelOptInfo *rel2, RelOptInfo *child_joinrel; AppendRelInfo **appinfos; int nappinfos; + Relids child_relids; if (joinrel->partbounds_merged) { @@ -1642,9 +1643,8 @@ try_partitionwise_join(PlannerInfo *root, RelOptInfo *rel1, RelOptInfo *rel2, child_rel2->relids); /* Find the AppendRelInfo structures */ - appinfos = find_appinfos_by_relids(root, - bms_union(child_rel1->relids, - child_rel2->relids), + child_relids = bms_union(child_rel1->relids, child_rel2->relids); + appinfos = find_appinfos_by_relids(root, child_relids, &nappinfos); /* @@ -1662,7 +1662,7 @@ try_partitionwise_join(PlannerInfo *root, RelOptInfo *rel1, RelOptInfo *rel2, { child_joinrel = build_child_join_rel(root, child_rel1, child_rel2, joinrel, child_restrictlist, - child_sjinfo); + child_sjinfo, nappinfos, appinfos); joinrel->part_rels[cnt_parts] = child_joinrel; joinrel->live_parts = bms_add_member(joinrel->live_parts, cnt_parts); joinrel->all_partrels = bms_add_members(joinrel->all_partrels, @@ -1679,7 +1679,14 @@ try_partitionwise_join(PlannerInfo *root, RelOptInfo *rel1, RelOptInfo *rel2, child_joinrel, child_sjinfo, child_restrictlist); + /* + * When there are thousands of partitions involved, this loop will + * accumulate a significant amount of memory usage from objects that + * are only needed within the loop. Free these local objects eagerly + * at the end of each iteration. + */ pfree(appinfos); + bms_free(child_relids); free_child_join_sjinfo(child_sjinfo); } } diff --git a/src/backend/optimizer/util/relnode.c b/src/backend/optimizer/util/relnode.c index e05b21c884e..971d1c7aae5 100644 --- a/src/backend/optimizer/util/relnode.c +++ b/src/backend/optimizer/util/relnode.c @@ -876,15 +876,15 @@ build_join_rel(PlannerInfo *root, * 'restrictlist': list of RestrictInfo nodes that apply to this particular * pair of joinable relations * 'sjinfo': child join's join-type details + * 'nappinfos' and 'appinfos': AppendRelInfo array for child relids */ RelOptInfo * build_child_join_rel(PlannerInfo *root, RelOptInfo *outer_rel, RelOptInfo *inner_rel, RelOptInfo *parent_joinrel, - List *restrictlist, SpecialJoinInfo *sjinfo) + List *restrictlist, SpecialJoinInfo *sjinfo, + int nappinfos, AppendRelInfo **appinfos) { RelOptInfo *joinrel = makeNode(RelOptInfo); - AppendRelInfo **appinfos; - int nappinfos; /* Only joins between "other" relations land here. */ Assert(IS_OTHER_REL(outer_rel) && IS_OTHER_REL(inner_rel)); @@ -892,16 +892,6 @@ build_child_join_rel(PlannerInfo *root, RelOptInfo *outer_rel, /* The parent joinrel should have consider_partitionwise_join set. */ Assert(parent_joinrel->consider_partitionwise_join); - /* - * Find the AppendRelInfo structures for the child baserels. We'll need - * these for computing the child join's relid set, and later for mapping - * Vars to the child rel. - */ - appinfos = find_appinfos_by_relids(root, - bms_union(outer_rel->relids, - inner_rel->relids), - &nappinfos); - joinrel->reloptkind = RELOPT_OTHER_JOINREL; joinrel->relids = adjust_child_relids(parent_joinrel->relids, nappinfos, appinfos); @@ -1017,8 +1007,6 @@ build_child_join_rel(PlannerInfo *root, RelOptInfo *outer_rel, nappinfos, appinfos, parent_joinrel, joinrel); - pfree(appinfos); - return joinrel; } |