From e239ea5aba23812a8be13bb993c2b90c5d469332 Mon Sep 17 00:00:00 2001 From: naisila Date: Fri, 2 May 2025 12:19:08 +0300 Subject: [PATCH] Check for hasPseudoconstantQuals differently --- .../distributed/planner/distributed_planner.c | 2 - .../distributed/planner/recursive_planning.c | 66 +++++++++++++------ src/include/distributed/distributed_planner.h | 1 - 3 files changed, 46 insertions(+), 23 deletions(-) diff --git a/src/backend/distributed/planner/distributed_planner.c b/src/backend/distributed/planner/distributed_planner.c index d381d8768..193e2f250 100644 --- a/src/backend/distributed/planner/distributed_planner.c +++ b/src/backend/distributed/planner/distributed_planner.c @@ -2002,8 +2002,6 @@ multi_relation_restriction_hook(PlannerInfo *root, RelOptInfo *relOptInfo, relationRestriction->outerPlanParamsList = OuterPlanParamsList(root); relationRestriction->translatedVars = TranslatedVars(root, relationRestriction->index); - plannerRestrictionContext->relationRestrictionContext->hasPseudoConstantQuals = - root->hasPseudoConstantQuals; RelationRestrictionContext *relationRestrictionContext = plannerRestrictionContext->relationRestrictionContext; diff --git a/src/backend/distributed/planner/recursive_planning.c b/src/backend/distributed/planner/recursive_planning.c index 59b6ffaa0..9db6481cb 100644 --- a/src/backend/distributed/planner/recursive_planning.c +++ b/src/backend/distributed/planner/recursive_planning.c @@ -193,6 +193,10 @@ static Query * CreateOuterSubquery(RangeTblEntry *rangeTableEntry, List *outerSubqueryTargetList); static List * GenerateRequiredColNamesFromTargetList(List *targetList); static char * GetRelationNameAndAliasName(RangeTblEntry *rangeTablentry); +#if PG_VERSION_NUM < PG_VERSION_17 +static bool hasPseudoconstantQuals( + RelationRestrictionContext *relationRestrictionContext); +#endif /* * GenerateSubplansForSubqueriesAndCTEs is a wrapper around RecursivelyPlanSubqueriesAndCTEs. @@ -481,25 +485,23 @@ ShouldRecursivelyPlanOuterJoins(Query *query, RecursivePlanningContext *context) bool hasOuterJoin = context->plannerRestrictionContext->joinRestrictionContext->hasOuterJoin; #if PG_VERSION_NUM < PG_VERSION_17 - bool hasPseudoConstantQuals = - context->plannerRestrictionContext->relationRestrictionContext-> - hasPseudoConstantQuals; - - /* - * PG15 commit d1ef5631e620f9a5b6480a32bb70124c857af4f1 - * PG16 commit 695f5deb7902865901eb2d50a70523af655c3a00 - * disallows replacing joins with scans in queries with pseudoconstant quals. - * This commit prevents the set_join_pathlist_hook from being called - * if any of the join restrictions is a pseudo-constant. - * So in these cases, citus has no info on the join, never sees that the query - * has an outer join, and ends up producing an incorrect plan. - * PG17 fixes this by commit 9e9931d2bf40e2fea447d779c2e133c2c1256ef3 - * Therefore, we take this extra measure here for PG versions less than 17. - */ - if (hasPseudoConstantQuals && !hasOuterJoin) + if (!hasOuterJoin) { - if (FindNodeMatchingCheckFunction((Node *) query->jointree, - IsOuterJoinExpr)) + /* + * PG15 commit d1ef5631e620f9a5b6480a32bb70124c857af4f1 + * PG16 commit 695f5deb7902865901eb2d50a70523af655c3a00 + * disallows replacing joins with scans in queries with pseudoconstant quals. + * This commit prevents the set_join_pathlist_hook from being called + * if any of the join restrictions is a pseudo-constant. + * So in these cases, citus has no info on the join, never sees that the query + * has an outer join, and ends up producing an incorrect plan. + * PG17 fixes this by commit 9e9931d2bf40e2fea447d779c2e133c2c1256ef3 + * Therefore, we take this extra measure here for PG versions less than 17. + * hasOuterJoin can never be true when set_join_pathlist_hook is absent. + */ + if (hasPseudoconstantQuals( + context->plannerRestrictionContext->relationRestrictionContext) && + FindNodeMatchingCheckFunction((Node *) query->jointree, IsOuterJoinExpr)) { ereport(ERROR, (errmsg("Distributed queries with outer joins and " "pseudoconstant quals are not supported in PG15 and PG16."), @@ -2142,7 +2144,6 @@ TransformFunctionRTE(RangeTblEntry *rangeTblEntry) subquery->targetList = lappend(subquery->targetList, targetEntry); } } - /* * If tupleDesc is NULL we have 2 different cases: * @@ -2192,7 +2193,6 @@ TransformFunctionRTE(RangeTblEntry *rangeTblEntry) columnType = list_nth_oid(rangeTblFunction->funccoltypes, targetColumnIndex); } - /* use the types in the function definition otherwise */ else { @@ -2616,3 +2616,29 @@ GeneratingSubplans(void) { return recursivePlanningDepth > 0; } + + +#if PG_VERSION_NUM < PG_VERSION_17 + +/* + * hasPseudoconstantQuals returns true if any of the planner infos in the + * relation restriction list of the input relation restriction context + * has a pseudoconstant qual + */ +static bool +hasPseudoconstantQuals(RelationRestrictionContext *relationRestrictionContext) +{ + ListCell *objectCell = NULL; + foreach(objectCell, relationRestrictionContext->relationRestrictionList) + { + if (((RelationRestriction *) lfirst( + objectCell))->plannerInfo->hasPseudoConstantQuals) + { + return true; + } + } + return false; +} + + +#endif diff --git a/src/include/distributed/distributed_planner.h b/src/include/distributed/distributed_planner.h index 04e98e258..33a9c2fa8 100644 --- a/src/include/distributed/distributed_planner.h +++ b/src/include/distributed/distributed_planner.h @@ -36,7 +36,6 @@ extern int PlannerLevel; typedef struct RelationRestrictionContext { bool allReferenceTables; - bool hasPseudoConstantQuals; List *relationRestrictionList; } RelationRestrictionContext;