Commit 145014f8 authored by Tom Lane's avatar Tom Lane

Make further use of new bitmapset code: executor's chgParam, extParam,

locParam lists can be converted to bitmapsets to speed updating.  Also,
replace 'locParam' with 'allParam', which contains all the paramIDs
relevant to the node (i.e., the union of extParam and locParam); this
saves a step during SetChangedParamList() without costing anything
elsewhere.
parent c15a4c2a
......@@ -6,7 +6,7 @@
* Portions Copyright (c) 1996-2002, PostgreSQL Global Development Group
* Portions Copyright (c) 1994, Regents of the University of California
*
* $Header: /cvsroot/pgsql/src/backend/executor/execAmi.c,v 1.68 2002/12/14 00:17:50 tgl Exp $
* $Header: /cvsroot/pgsql/src/backend/executor/execAmi.c,v 1.69 2003/02/09 00:30:39 tgl Exp $
*
*-------------------------------------------------------------------------
*/
......@@ -55,7 +55,7 @@ ExecReScan(PlanState *node, ExprContext *exprCtxt)
InstrEndLoop(node->instrument);
/* If we have changed parameters, propagate that info */
if (node->chgParam != NIL)
if (node->chgParam != NULL)
{
List *lst;
......@@ -64,10 +64,10 @@ ExecReScan(PlanState *node, ExprContext *exprCtxt)
SubPlanState *sstate = (SubPlanState *) lfirst(lst);
PlanState *splan = sstate->planstate;
if (splan->plan->extParam != NIL) /* don't care about child
* locParam */
SetChangedParamList(splan, node->chgParam);
if (splan->chgParam != NIL)
if (splan->plan->extParam != NULL) /* don't care about child
* local Params */
UpdateChangedParamSet(splan, node->chgParam);
if (splan->chgParam != NULL)
ExecReScanSetParamPlan(sstate, node);
}
foreach(lst, node->subPlan)
......@@ -75,14 +75,14 @@ ExecReScan(PlanState *node, ExprContext *exprCtxt)
SubPlanState *sstate = (SubPlanState *) lfirst(lst);
PlanState *splan = sstate->planstate;
if (splan->plan->extParam != NIL)
SetChangedParamList(splan, node->chgParam);
if (splan->plan->extParam != NULL)
UpdateChangedParamSet(splan, node->chgParam);
}
/* Well. Now set chgParam for left/right trees. */
if (node->lefttree != NULL)
SetChangedParamList(node->lefttree, node->chgParam);
UpdateChangedParamSet(node->lefttree, node->chgParam);
if (node->righttree != NULL)
SetChangedParamList(node->righttree, node->chgParam);
UpdateChangedParamSet(node->righttree, node->chgParam);
}
switch (nodeTag(node))
......@@ -165,10 +165,10 @@ ExecReScan(PlanState *node, ExprContext *exprCtxt)
return;
}
if (node->chgParam != NIL)
if (node->chgParam != NULL)
{
freeList(node->chgParam);
node->chgParam = NIL;
bms_free(node->chgParam);
node->chgParam = NULL;
}
}
......
......@@ -12,7 +12,7 @@
*
*
* IDENTIFICATION
* $Header: /cvsroot/pgsql/src/backend/executor/execProcnode.c,v 1.34 2002/12/14 00:17:50 tgl Exp $
* $Header: /cvsroot/pgsql/src/backend/executor/execProcnode.c,v 1.35 2003/02/09 00:30:39 tgl Exp $
*
*-------------------------------------------------------------------------
*/
......@@ -282,7 +282,7 @@ ExecProcNode(PlanState *node)
if (node == NULL)
return NULL;
if (node->chgParam != NIL) /* something changed */
if (node->chgParam != NULL) /* something changed */
ExecReScan(node, NULL); /* let ReScan handle this */
if (node->instrument)
......@@ -504,10 +504,10 @@ ExecEndNode(PlanState *node)
foreach(subp, node->subPlan)
ExecEndSubPlan((SubPlanState *) lfirst(subp));
if (node->chgParam != NIL)
if (node->chgParam != NULL)
{
freeList(node->chgParam);
node->chgParam = NIL;
bms_free(node->chgParam);
node->chgParam = NULL;
}
switch (nodeTag(node))
......
......@@ -8,7 +8,7 @@
*
*
* IDENTIFICATION
* $Header: /cvsroot/pgsql/src/backend/executor/execUtils.c,v 1.96 2003/01/23 05:10:39 tgl Exp $
* $Header: /cvsroot/pgsql/src/backend/executor/execUtils.c,v 1.97 2003/02/09 00:30:39 tgl Exp $
*
*-------------------------------------------------------------------------
*/
......@@ -874,25 +874,28 @@ ExecInsertIndexTuples(TupleTableSlot *slot,
}
}
/*
* UpdateChangedParamSet
* Add changed parameters to a plan node's chgParam set
*/
void
SetChangedParamList(PlanState *node, List *newchg)
UpdateChangedParamSet(PlanState *node, Bitmapset *newchg)
{
List *nl;
foreach(nl, newchg)
{
int paramId = lfirsti(nl);
Bitmapset *parmset;
/* if this node doesn't depend on a param ... */
if (!intMember(paramId, node->plan->extParam) &&
!intMember(paramId, node->plan->locParam))
continue;
/* if this param is already in list of changed ones ... */
if (intMember(paramId, node->chgParam))
continue;
/* else - add this param to the list */
node->chgParam = lappendi(node->chgParam, paramId);
}
/*
* The plan node only depends on params listed in its allParam set.
* Don't include anything else into its chgParam set.
*/
parmset = bms_intersect(node->plan->allParam, newchg);
/*
* Keep node->chgParam == NULL if there's not actually any members;
* this allows the simplest possible tests in executor node files.
*/
if (!bms_is_empty(parmset))
node->chgParam = bms_join(node->chgParam, parmset);
else
bms_free(parmset);
}
/*
......
......@@ -45,7 +45,7 @@
* Portions Copyright (c) 1994, Regents of the University of California
*
* IDENTIFICATION
* $Header: /cvsroot/pgsql/src/backend/executor/nodeAgg.c,v 1.103 2003/02/04 00:48:23 tgl Exp $
* $Header: /cvsroot/pgsql/src/backend/executor/nodeAgg.c,v 1.104 2003/02/09 00:30:39 tgl Exp $
*
*-------------------------------------------------------------------------
*/
......@@ -1405,7 +1405,7 @@ ExecReScanAgg(AggState *node, ExprContext *exprCtxt)
* if chgParam of subnode is not null then plan will be re-scanned by
* first ExecProcNode.
*/
if (((PlanState *) node)->lefttree->chgParam == NIL)
if (((PlanState *) node)->lefttree->chgParam == NULL)
ExecReScan(((PlanState *) node)->lefttree, exprCtxt);
}
......
......@@ -8,7 +8,7 @@
*
*
* IDENTIFICATION
* $Header: /cvsroot/pgsql/src/backend/executor/nodeAppend.c,v 1.51 2002/12/05 15:50:33 tgl Exp $
* $Header: /cvsroot/pgsql/src/backend/executor/nodeAppend.c,v 1.52 2003/02/09 00:30:39 tgl Exp $
*
*-------------------------------------------------------------------------
*/
......@@ -361,14 +361,14 @@ ExecReScanAppend(AppendState *node, ExprContext *exprCtxt)
* ExecReScan doesn't know about my subplans, so I have to do
* changed-parameter signaling myself.
*/
if (node->ps.chgParam != NIL)
SetChangedParamList(subnode, node->ps.chgParam);
if (node->ps.chgParam != NULL)
UpdateChangedParamSet(subnode, node->ps.chgParam);
/*
* if chgParam of subnode is not null then plan will be re-scanned
* by first ExecProcNode.
*/
if (subnode->chgParam == NIL)
if (subnode->chgParam == NULL)
{
/* make sure estate is correct for this subnode (needed??) */
node->as_whichplan = i;
......
......@@ -7,7 +7,7 @@
* Portions Copyright (c) 1994, Regents of the University of California
*
* IDENTIFICATION
* $Header: /cvsroot/pgsql/src/backend/executor/nodeSubplan.c,v 1.43 2003/01/12 04:03:34 tgl Exp $
* $Header: /cvsroot/pgsql/src/backend/executor/nodeSubplan.c,v 1.44 2003/02/09 00:30:39 tgl Exp $
*
*-------------------------------------------------------------------------
*/
......@@ -80,7 +80,7 @@ ExecHashSubPlan(SubPlanState *node,
* If first time through or we need to rescan the subplan, build
* the hash table.
*/
if (node->hashtable == NULL || planstate->chgParam != NIL)
if (node->hashtable == NULL || planstate->chgParam != NULL)
buildSubPlanHash(node);
/*
......@@ -218,22 +218,18 @@ ExecScanSubPlan(SubPlanState *node,
* Set Params of this plan from parent plan correlation Vars
*/
pvar = node->args;
if (subplan->parParam != NIL)
foreach(lst, subplan->parParam)
{
foreach(lst, subplan->parParam)
{
ParamExecData *prm;
prm = &(econtext->ecxt_param_exec_vals[lfirsti(lst)]);
Assert(pvar != NIL);
prm->value = ExecEvalExprSwitchContext((ExprState *) lfirst(pvar),
econtext,
&(prm->isnull),
NULL);
pvar = lnext(pvar);
}
planstate->chgParam = nconc(planstate->chgParam,
listCopy(subplan->parParam));
int paramid = lfirsti(lst);
ParamExecData *prm = &(econtext->ecxt_param_exec_vals[paramid]);
Assert(pvar != NIL);
prm->value = ExecEvalExprSwitchContext((ExprState *) lfirst(pvar),
econtext,
&(prm->isnull),
NULL);
pvar = lnext(pvar);
planstate->chgParam = bms_add_member(planstate->chgParam, paramid);
}
Assert(pvar == NIL);
......@@ -686,7 +682,12 @@ ExecInitSubPlan(SubPlanState *node, EState *estate)
/*
* If this plan is un-correlated or undirect correlated one and want
* to set params for parent plan then prepare parameters.
* to set params for parent plan then mark parameters as needing
* evaluation.
*
* Note that in the case of un-correlated subqueries we don't care
* about setting parent->chgParam here: indices take care about
* it, for others - it doesn't matter...
*/
if (subplan->setParam != NIL)
{
......@@ -694,16 +695,11 @@ ExecInitSubPlan(SubPlanState *node, EState *estate)
foreach(lst, subplan->setParam)
{
ParamExecData *prm = &(estate->es_param_exec_vals[lfirsti(lst)]);
int paramid = lfirsti(lst);
ParamExecData *prm = &(estate->es_param_exec_vals[paramid]);
prm->execPlan = node;
}
/*
* Note that in the case of un-correlated subqueries we don't care
* about setting parent->chgParam here: indices take care about
* it, for others - it doesn't matter...
*/
}
/*
......@@ -884,7 +880,9 @@ ExecSetParamPlan(SubPlanState *node, ExprContext *econtext)
if (subLinkType == EXISTS_SUBLINK)
{
ParamExecData *prm = &(econtext->ecxt_param_exec_vals[lfirsti(subplan->setParam)]);
/* There can be only one param... */
int paramid = lfirsti(subplan->setParam);
ParamExecData *prm = &(econtext->ecxt_param_exec_vals[paramid]);
prm->execPlan = NULL;
prm->value = BoolGetDatum(true);
......@@ -914,9 +912,13 @@ ExecSetParamPlan(SubPlanState *node, ExprContext *econtext)
node->curTuple = tup;
MemoryContextSwitchTo(node->sub_estate->es_query_cxt);
/*
* Now set all the setParam params from the columns of the tuple
*/
foreach(lst, subplan->setParam)
{
ParamExecData *prm = &(econtext->ecxt_param_exec_vals[lfirsti(lst)]);
int paramid = lfirsti(lst);
ParamExecData *prm = &(econtext->ecxt_param_exec_vals[paramid]);
prm->execPlan = NULL;
prm->value = heap_getattr(tup, i, tdesc, &(prm->isnull));
......@@ -928,7 +930,9 @@ ExecSetParamPlan(SubPlanState *node, ExprContext *econtext)
{
if (subLinkType == EXISTS_SUBLINK)
{
ParamExecData *prm = &(econtext->ecxt_param_exec_vals[lfirsti(subplan->setParam)]);
/* There can be only one param... */
int paramid = lfirsti(subplan->setParam);
ParamExecData *prm = &(econtext->ecxt_param_exec_vals[paramid]);
prm->execPlan = NULL;
prm->value = BoolGetDatum(false);
......@@ -938,7 +942,8 @@ ExecSetParamPlan(SubPlanState *node, ExprContext *econtext)
{
foreach(lst, subplan->setParam)
{
ParamExecData *prm = &(econtext->ecxt_param_exec_vals[lfirsti(lst)]);
int paramid = lfirsti(lst);
ParamExecData *prm = &(econtext->ecxt_param_exec_vals[paramid]);
prm->execPlan = NULL;
prm->value = (Datum) 0;
......@@ -979,12 +984,12 @@ ExecReScanSetParamPlan(SubPlanState *node, PlanState *parent)
EState *estate = parent->state;
List *lst;
if (subplan->parParam != NULL)
if (subplan->parParam != NIL)
elog(ERROR, "ExecReScanSetParamPlan: direct correlated subquery unsupported, yet");
if (subplan->setParam == NULL)
elog(ERROR, "ExecReScanSetParamPlan: setParam list is NULL");
if (planstate->plan->extParam == NULL)
elog(ERROR, "ExecReScanSetParamPlan: extParam list of plan is NULL");
if (subplan->setParam == NIL)
elog(ERROR, "ExecReScanSetParamPlan: setParam list is empty");
if (bms_is_empty(planstate->plan->extParam))
elog(ERROR, "ExecReScanSetParamPlan: extParam set of plan is empty");
/*
* Don't actually re-scan: ExecSetParamPlan does it if needed.
......@@ -995,10 +1000,10 @@ ExecReScanSetParamPlan(SubPlanState *node, PlanState *parent)
*/
foreach(lst, subplan->setParam)
{
ParamExecData *prm = &(estate->es_param_exec_vals[lfirsti(lst)]);
int paramid = lfirsti(lst);
ParamExecData *prm = &(estate->es_param_exec_vals[paramid]);
prm->execPlan = node;
parent->chgParam = bms_add_member(parent->chgParam, paramid);
}
parent->chgParam = nconc(parent->chgParam, listCopy(subplan->setParam));
}
......@@ -12,7 +12,7 @@
*
*
* IDENTIFICATION
* $Header: /cvsroot/pgsql/src/backend/executor/nodeSubqueryscan.c,v 1.17 2003/01/12 22:01:38 tgl Exp $
* $Header: /cvsroot/pgsql/src/backend/executor/nodeSubqueryscan.c,v 1.18 2003/02/09 00:30:39 tgl Exp $
*
*-------------------------------------------------------------------------
*/
......@@ -261,10 +261,10 @@ ExecSubqueryReScan(SubqueryScanState *node, ExprContext *exprCtxt)
* ExecReScan doesn't know about my subplan, so I have to do
* changed-parameter signaling myself. This is just as well,
* because the subplan has its own memory context in which its
* chgParam lists live.
* chgParam state lives.
*/
if (node->ss.ps.chgParam != NULL)
SetChangedParamList(node->subplan, node->ss.ps.chgParam);
UpdateChangedParamSet(node->subplan, node->ss.ps.chgParam);
/*
* if chgParam of subnode is not null then plan will be re-scanned by
......
......@@ -8,7 +8,7 @@
*
*
* IDENTIFICATION
* $Header: /cvsroot/pgsql/src/backend/executor/nodeTidscan.c,v 1.32 2003/02/03 15:07:07 tgl Exp $
* $Header: /cvsroot/pgsql/src/backend/executor/nodeTidscan.c,v 1.33 2003/02/09 00:30:39 tgl Exp $
*
*-------------------------------------------------------------------------
*/
......@@ -349,7 +349,7 @@ ExecInitTidScan(TidScan *node, EState *estate)
Oid relid;
Oid reloid;
Relation currentRelation;
List *execParam = NIL;
Bitmapset *execParam = NULL;
/*
* create state structure
......
......@@ -15,7 +15,7 @@
* Portions Copyright (c) 1994, Regents of the University of California
*
* IDENTIFICATION
* $Header: /cvsroot/pgsql/src/backend/nodes/copyfuncs.c,v 1.240 2003/02/08 20:20:53 tgl Exp $
* $Header: /cvsroot/pgsql/src/backend/nodes/copyfuncs.c,v 1.241 2003/02/09 00:30:39 tgl Exp $
*
*-------------------------------------------------------------------------
*/
......@@ -120,8 +120,8 @@ CopyPlanFields(Plan *from, Plan *newnode)
COPY_NODE_FIELD(lefttree);
COPY_NODE_FIELD(righttree);
COPY_NODE_FIELD(initPlan);
COPY_INTLIST_FIELD(extParam);
COPY_INTLIST_FIELD(locParam);
COPY_BITMAPSET_FIELD(extParam);
COPY_BITMAPSET_FIELD(allParam);
COPY_SCALAR_FIELD(nParamExec);
}
......
......@@ -8,7 +8,7 @@
*
*
* IDENTIFICATION
* $Header: /cvsroot/pgsql/src/backend/nodes/outfuncs.c,v 1.196 2003/02/08 20:20:54 tgl Exp $
* $Header: /cvsroot/pgsql/src/backend/nodes/outfuncs.c,v 1.197 2003/02/09 00:30:39 tgl Exp $
*
* NOTES
* Every node type that can appear in stored rules' parsetrees *must*
......@@ -255,8 +255,8 @@ _outPlanInfo(StringInfo str, Plan *node)
WRITE_NODE_FIELD(lefttree);
WRITE_NODE_FIELD(righttree);
WRITE_NODE_FIELD(initPlan);
WRITE_INTLIST_FIELD(extParam);
WRITE_INTLIST_FIELD(locParam);
WRITE_BITMAPSET_FIELD(extParam);
WRITE_BITMAPSET_FIELD(allParam);
WRITE_INT_FIELD(nParamExec);
}
......
......@@ -8,7 +8,7 @@
*
*
* IDENTIFICATION
* $Header: /cvsroot/pgsql/src/backend/optimizer/plan/planner.c,v 1.144 2003/02/04 00:50:00 tgl Exp $
* $Header: /cvsroot/pgsql/src/backend/optimizer/plan/planner.c,v 1.145 2003/02/09 00:30:39 tgl Exp $
*
*-------------------------------------------------------------------------
*/
......@@ -268,14 +268,14 @@ subquery_planner(Query *parse, double tuple_fraction)
/*
* If any subplans were generated, or if we're inside a subplan, build
* initPlan, extParam and locParam lists for plan nodes.
* initPlan list and extParam/allParam sets for plan nodes.
*/
if (PlannerPlanId != saved_planid || PlannerQueryLevel > 1)
{
Cost initplan_cost = 0;
/* Prepare extParam/locParam data for all nodes in tree */
(void) SS_finalize_plan(plan, parse->rtable);
/* Prepare extParam/allParam sets for all nodes in tree */
SS_finalize_plan(plan, parse->rtable);
/*
* SS_finalize_plan doesn't handle initPlans, so we have to manually
......@@ -293,8 +293,8 @@ subquery_planner(Query *parse, double tuple_fraction)
{
SubPlan *initplan = (SubPlan *) lfirst(lst);
plan->extParam = set_unioni(plan->extParam,
initplan->plan->extParam);
plan->extParam = bms_add_members(plan->extParam,
initplan->plan->extParam);
initplan_cost += initplan->plan->total_cost;
}
......
This diff is collapsed.
......@@ -7,7 +7,7 @@
* Portions Copyright (c) 1996-2002, PostgreSQL Global Development Group
* Portions Copyright (c) 1994, Regents of the University of California
*
* $Id: executor.h,v 1.88 2003/02/03 15:07:07 tgl Exp $
* $Id: executor.h,v 1.89 2003/02/09 00:30:39 tgl Exp $
*
*-------------------------------------------------------------------------
*/
......@@ -160,7 +160,7 @@ extern TupleTableSlot *ExecInitExtraTupleSlot(EState *estate);
extern TupleTableSlot *ExecInitNullTupleSlot(EState *estate,
TupleDesc tupType);
extern TupleDesc ExecTypeFromTL(List *targetList, bool hasoid);
extern void SetChangedParamList(PlanState *node, List *newchg);
extern void UpdateChangedParamSet(PlanState *node, Bitmapset *newchg);
typedef struct TupOutputState
{
......
......@@ -7,7 +7,7 @@
* Portions Copyright (c) 1996-2002, PostgreSQL Global Development Group
* Portions Copyright (c) 1994, Regents of the University of California
*
* $Id: execnodes.h,v 1.93 2003/02/03 21:15:44 tgl Exp $
* $Id: execnodes.h,v 1.94 2003/02/09 00:30:39 tgl Exp $
*
*-------------------------------------------------------------------------
*/
......@@ -18,6 +18,7 @@
#include "executor/hashjoin.h"
#include "executor/tuptable.h"
#include "fmgr.h"
#include "nodes/bitmapset.h"
#include "nodes/params.h"
#include "nodes/plannodes.h"
#include "utils/tuplestore.h"
......@@ -616,7 +617,7 @@ typedef struct PlanState
/*
* State for management of parameter-change-driven rescanning
*/
List *chgParam; /* integer list of IDs of changed Params */
Bitmapset *chgParam; /* set of IDs of changed Params */
/*
* Other run-time state needed by most if not all node types.
......
......@@ -7,7 +7,7 @@
* Portions Copyright (c) 1996-2002, PostgreSQL Global Development Group
* Portions Copyright (c) 1994, Regents of the University of California
*
* $Id: plannodes.h,v 1.63 2002/12/12 15:49:40 tgl Exp $
* $Id: plannodes.h,v 1.64 2003/02/09 00:30:40 tgl Exp $
*
*-------------------------------------------------------------------------
*/
......@@ -15,6 +15,7 @@
#define PLANNODES_H
#include "access/sdir.h"
#include "nodes/bitmapset.h"
#include "nodes/primnodes.h"
......@@ -65,14 +66,17 @@ typedef struct Plan
/*
* Information for management of parameter-change-driven rescanning
*
* extParam includes the paramIDs of all external PARAM_EXEC params
* affecting this plan node or its children. setParam params from
* the node's initPlans are not included, but their extParams are.
*
* allParam includes all the extParam paramIDs, plus the IDs of local
* params that affect the node (i.e., the setParams of its initplans).
* These are _all_ the PARAM_EXEC params that affect this node.
*/
List *extParam; /* indices of _all_ _external_ PARAM_EXEC
* for this plan in global
* es_param_exec_vals. Params from
* setParam from initPlan-s are not
* included, but their execParam-s are
* here!!! */
List *locParam; /* someones from setParam-s */
Bitmapset *extParam;
Bitmapset *allParam;
/*
* We really need in some TopPlan node to store range table and
......
......@@ -10,7 +10,7 @@
* Portions Copyright (c) 1996-2002, PostgreSQL Global Development Group
* Portions Copyright (c) 1994, Regents of the University of California
*
* $Id: primnodes.h,v 1.78 2003/02/03 21:15:44 tgl Exp $
* $Id: primnodes.h,v 1.79 2003/02/09 00:30:40 tgl Exp $
*
*-------------------------------------------------------------------------
*/
......@@ -435,9 +435,11 @@ typedef struct SubLink
* expressions to be evaluated in the outer-query context (currently these
* args are always just Vars, but in principle they could be any expression).
* The values are assigned to the global PARAM_EXEC params indexed by parParam
* (the parParam and args lists must have the same length). setParam is a
* (the parParam and args lists must have the same ordering). setParam is a
* list of the PARAM_EXEC params that are computed by the sub-select, if it
* is an initplan.
* is an initplan; they are listed in order by sub-select output column
* position. (parParam and setParam are integer Lists, not Bitmapsets,
* because their ordering is significant.)
*/
typedef struct SubPlan
{
......@@ -449,6 +451,7 @@ typedef struct SubPlan
/* The combining operators, transformed to executable expressions: */
List *exprs; /* list of OpExpr expression trees */
List *paramIds; /* IDs of Params embedded in the above */
/* Note: paramIds has a one-to-one correspondence to the exprs list */
/* The subselect, transformed to a Plan: */
struct Plan *plan; /* subselect plan itself */
int plan_id; /* dummy thing because of we haven't equal
......
......@@ -5,7 +5,7 @@
* Portions Copyright (c) 1996-2002, PostgreSQL Global Development Group
* Portions Copyright (c) 1994, Regents of the University of California
*
* $Id: subselect.h,v 1.17 2003/01/20 18:55:05 tgl Exp $
* $Id: subselect.h,v 1.18 2003/02/09 00:30:41 tgl Exp $
*
*-------------------------------------------------------------------------
*/
......@@ -22,6 +22,6 @@ extern int PlannerPlanId; /* to assign unique ID to subquery plans */
extern Node *convert_IN_to_join(Query *parse, SubLink *sublink);
extern Node *SS_replace_correlation_vars(Node *expr);
extern Node *SS_process_sublinks(Node *expr, bool isQual);
extern List *SS_finalize_plan(Plan *plan, List *rtable);
extern void SS_finalize_plan(Plan *plan, List *rtable);
#endif /* SUBSELECT_H */
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment