From 30d1e78ce73e07c463b5c946b571ee964caeb3eb Mon Sep 17 00:00:00 2001 From: root Date: Tue, 15 Dec 2020 07:14:58 -0500 Subject: [PATCH 2/2] support pctas in append tuple cost adjustment --- src/backend/optimizer/path/allpaths.c | 29 +++++++++++++++++++++++++++++ src/backend/optimizer/plan/planner.c | 9 +++++++-- src/include/commands/createas.h | 3 ++- 3 files changed, 38 insertions(+), 3 deletions(-) diff --git a/src/backend/optimizer/path/allpaths.c b/src/backend/optimizer/path/allpaths.c index 84a69b0..82f85b8 100644 --- a/src/backend/optimizer/path/allpaths.c +++ b/src/backend/optimizer/path/allpaths.c @@ -23,6 +23,7 @@ #include "catalog/pg_class.h" #include "catalog/pg_operator.h" #include "catalog/pg_proc.h" +#include "commands/createas.h" #include "foreign/fdwapi.h" #include "miscadmin.h" #include "nodes/makefuncs.h" @@ -1104,10 +1105,38 @@ set_append_rel_size(PlannerInfo *root, RelOptInfo *rel, set_rel_consider_parallel(root, childrel, childRTE); /* + * When subplan is subquery, It's possible to do parallel insert + * if top-node of subquery is Gather, so we set the flag to + * ignore parallel tuple cost by the Gather path in cost_gather + * if the SELECT is for CTAS. + */ + if(childrel->rtekind == RTE_SUBQUERY) + { + if((root->query_level == 1 || + root->parent_root->parse->CTASParallelInsInfo & + CTAS_PARALLEL_INS_IGN_TUP_COST_APPEND) + && + !(root->parse->rowMarks || + limit_needed(root->parse) || + root->parse->sortClause || + root->parse->distinctClause || + root->parse->hasWindowFuncs || + root->parse->groupClause || + root->parse->groupingSets || + root->parse->hasAggs || + root->hasHavingQual)) + root->parse->CTASParallelInsInfo |= + CTAS_PARALLEL_INS_IGN_TUP_COST_APPEND; + } + + /* * Compute the child's size. */ set_rel_size(root, childrel, childRTindex, childRTE); + if(root->parse->CTASParallelInsInfo & CTAS_PARALLEL_INS_IGN_TUP_COST_APPEND) + root->parse->CTASParallelInsInfo &= ~CTAS_PARALLEL_INS_IGN_TUP_COST_APPEND; + /* * It is possible that constraint exclusion detected a contradiction * within a child subquery, even though we didn't prove one above. If diff --git a/src/backend/optimizer/plan/planner.c b/src/backend/optimizer/plan/planner.c index d287b6b..86d42e1 100644 --- a/src/backend/optimizer/plan/planner.c +++ b/src/backend/optimizer/plan/planner.c @@ -7350,8 +7350,13 @@ can_partial_agg(PlannerInfo *root) static bool ignore_parallel_tuple_cost(PlannerInfo *root) { - if (root->query_level == 1 && - (root->parse->CTASParallelInsInfo & CTAS_PARALLEL_INS_SELECT)) + if(root->query_level != 1 && + (root->parent_root->parse->CTASParallelInsInfo & CTAS_PARALLEL_INS_IGN_TUP_COST_APPEND)) + { + root->parse->CTASParallelInsInfo |= CTAS_PARALLEL_INS_SELECT; + } + + if (root->parse->CTASParallelInsInfo & CTAS_PARALLEL_INS_SELECT) { /* * In each of following cases, a parent path will be generated for the diff --git a/src/include/commands/createas.h b/src/include/commands/createas.h index e01a615..7a50b18 100644 --- a/src/include/commands/createas.h +++ b/src/include/commands/createas.h @@ -54,7 +54,8 @@ typedef enum CTASParallelInsertOpt */ CTAS_PARALLEL_INS_TUP_COST_CAN_IGN = 1 << 1, - CTAS_PARALLEL_INS_TUP_COST_IGNORED = 1 << 2 + CTAS_PARALLEL_INS_TUP_COST_IGNORED = 1 << 2, + CTAS_PARALLEL_INS_IGN_TUP_COST_APPEND = 1 << 3 } CTASParallelInsertOpt; #define IS_CTAS(intoclause) (intoclause && IsA(intoclause, IntoClause)) -- 1.8.3.1