1
0
mirror of https://github.com/postgres/postgres.git synced 2025-07-02 09:02:37 +03:00

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.
This commit is contained in:
Tom Lane
2003-02-09 00:30:41 +00:00
parent c15a4c2aef
commit 145014f811
17 changed files with 267 additions and 193 deletions

View File

@ -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;
}
}

View File

@ -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))

View File

@ -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;
Bitmapset *parmset;
foreach(nl, newchg)
{
int paramId = lfirsti(nl);
/* 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);
}
/*

View File

@ -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);
}

View File

@ -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;

View File

@ -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;
int paramid = lfirsti(lst);
ParamExecData *prm = &(econtext->ecxt_param_exec_vals[paramid]);
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));
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));
}

View File

@ -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

View File

@ -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