PostgreSQL Source Code  git master
execProcnode.c File Reference
#include "postgres.h"
#include "executor/executor.h"
#include "executor/nodeAgg.h"
#include "executor/nodeAppend.h"
#include "executor/nodeBitmapAnd.h"
#include "executor/nodeBitmapHeapscan.h"
#include "executor/nodeBitmapIndexscan.h"
#include "executor/nodeBitmapOr.h"
#include "executor/nodeCtescan.h"
#include "executor/nodeCustom.h"
#include "executor/nodeForeignscan.h"
#include "executor/nodeFunctionscan.h"
#include "executor/nodeGather.h"
#include "executor/nodeGatherMerge.h"
#include "executor/nodeGroup.h"
#include "executor/nodeHash.h"
#include "executor/nodeHashjoin.h"
#include "executor/nodeIncrementalSort.h"
#include "executor/nodeIndexonlyscan.h"
#include "executor/nodeIndexscan.h"
#include "executor/nodeLimit.h"
#include "executor/nodeLockRows.h"
#include "executor/nodeMaterial.h"
#include "executor/nodeMemoize.h"
#include "executor/nodeMergeAppend.h"
#include "executor/nodeMergejoin.h"
#include "executor/nodeModifyTable.h"
#include "executor/nodeNamedtuplestorescan.h"
#include "executor/nodeNestloop.h"
#include "executor/nodeProjectSet.h"
#include "executor/nodeRecursiveunion.h"
#include "executor/nodeResult.h"
#include "executor/nodeSamplescan.h"
#include "executor/nodeSeqscan.h"
#include "executor/nodeSetOp.h"
#include "executor/nodeSort.h"
#include "executor/nodeSubplan.h"
#include "executor/nodeSubqueryscan.h"
#include "executor/nodeTableFuncscan.h"
#include "executor/nodeTidrangescan.h"
#include "executor/nodeTidscan.h"
#include "executor/nodeUnique.h"
#include "executor/nodeValuesscan.h"
#include "executor/nodeWindowAgg.h"
#include "executor/nodeWorktablescan.h"
#include "miscadmin.h"
#include "nodes/nodeFuncs.h"
Include dependency graph for execProcnode.c:

Go to the source code of this file.

Functions

static TupleTableSlotExecProcNodeFirst (PlanState *node)
 
static TupleTableSlotExecProcNodeInstr (PlanState *node)
 
static bool ExecShutdownNode_walker (PlanState *node, void *context)
 
PlanStateExecInitNode (Plan *node, EState *estate, int eflags)
 
void ExecSetExecProcNode (PlanState *node, ExecProcNodeMtd function)
 
NodeMultiExecProcNode (PlanState *node)
 
void ExecEndNode (PlanState *node)
 
void ExecShutdownNode (PlanState *node)
 
void ExecSetTupleBound (int64 tuples_needed, PlanState *child_node)
 

Function Documentation

◆ ExecEndNode()

void ExecEndNode ( PlanState node)

Definition at line 557 of file execProcnode.c.

558 {
559  /*
560  * do nothing when we get to the end of a leaf on tree.
561  */
562  if (node == NULL)
563  return;
564 
565  /*
566  * Make sure there's enough stack available. Need to check here, in
567  * addition to ExecProcNode() (via ExecProcNodeFirst()), because it's not
568  * guaranteed that ExecProcNode() is reached for all nodes.
569  */
571 
572  if (node->chgParam != NULL)
573  {
574  bms_free(node->chgParam);
575  node->chgParam = NULL;
576  }
577 
578  switch (nodeTag(node))
579  {
580  /*
581  * control nodes
582  */
583  case T_ResultState:
584  ExecEndResult((ResultState *) node);
585  break;
586 
587  case T_ProjectSetState:
589  break;
590 
591  case T_ModifyTableState:
593  break;
594 
595  case T_AppendState:
596  ExecEndAppend((AppendState *) node);
597  break;
598 
599  case T_MergeAppendState:
601  break;
602 
603  case T_RecursiveUnionState:
605  break;
606 
607  case T_BitmapAndState:
609  break;
610 
611  case T_BitmapOrState:
612  ExecEndBitmapOr((BitmapOrState *) node);
613  break;
614 
615  /*
616  * scan nodes
617  */
618  case T_SeqScanState:
619  ExecEndSeqScan((SeqScanState *) node);
620  break;
621 
622  case T_SampleScanState:
624  break;
625 
626  case T_GatherState:
627  ExecEndGather((GatherState *) node);
628  break;
629 
630  case T_GatherMergeState:
632  break;
633 
634  case T_IndexScanState:
636  break;
637 
638  case T_IndexOnlyScanState:
640  break;
641 
642  case T_BitmapIndexScanState:
644  break;
645 
646  case T_BitmapHeapScanState:
648  break;
649 
650  case T_TidScanState:
651  ExecEndTidScan((TidScanState *) node);
652  break;
653 
654  case T_TidRangeScanState:
656  break;
657 
658  case T_SubqueryScanState:
660  break;
661 
662  case T_FunctionScanState:
664  break;
665 
666  case T_TableFuncScanState:
668  break;
669 
670  case T_CteScanState:
671  ExecEndCteScan((CteScanState *) node);
672  break;
673 
674  case T_ForeignScanState:
676  break;
677 
678  case T_CustomScanState:
680  break;
681 
682  /*
683  * join nodes
684  */
685  case T_NestLoopState:
686  ExecEndNestLoop((NestLoopState *) node);
687  break;
688 
689  case T_MergeJoinState:
691  break;
692 
693  case T_HashJoinState:
694  ExecEndHashJoin((HashJoinState *) node);
695  break;
696 
697  /*
698  * materialization nodes
699  */
700  case T_MaterialState:
701  ExecEndMaterial((MaterialState *) node);
702  break;
703 
704  case T_SortState:
705  ExecEndSort((SortState *) node);
706  break;
707 
708  case T_IncrementalSortState:
710  break;
711 
712  case T_MemoizeState:
713  ExecEndMemoize((MemoizeState *) node);
714  break;
715 
716  case T_GroupState:
717  ExecEndGroup((GroupState *) node);
718  break;
719 
720  case T_AggState:
721  ExecEndAgg((AggState *) node);
722  break;
723 
724  case T_WindowAggState:
726  break;
727 
728  case T_UniqueState:
729  ExecEndUnique((UniqueState *) node);
730  break;
731 
732  case T_HashState:
733  ExecEndHash((HashState *) node);
734  break;
735 
736  case T_SetOpState:
737  ExecEndSetOp((SetOpState *) node);
738  break;
739 
740  case T_LockRowsState:
741  ExecEndLockRows((LockRowsState *) node);
742  break;
743 
744  case T_LimitState:
745  ExecEndLimit((LimitState *) node);
746  break;
747 
748  /* No clean up actions for these nodes. */
749  case T_ValuesScanState:
750  case T_NamedTuplestoreScanState:
751  case T_WorkTableScanState:
752  break;
753 
754  default:
755  elog(ERROR, "unrecognized node type: %d", (int) nodeTag(node));
756  break;
757  }
758 }
void bms_free(Bitmapset *a)
Definition: bitmapset.c:239
#define ERROR
Definition: elog.h:39
#define elog(elevel,...)
Definition: elog.h:224
void ExecEndAgg(AggState *node)
Definition: nodeAgg.c:4304
void ExecEndAppend(AppendState *node)
Definition: nodeAppend.c:386
void ExecEndBitmapAnd(BitmapAndState *node)
void ExecEndBitmapHeapScan(BitmapHeapScanState *node)
void ExecEndBitmapIndexScan(BitmapIndexScanState *node)
void ExecEndBitmapOr(BitmapOrState *node)
Definition: nodeBitmapOr.c:196
void ExecEndCteScan(CteScanState *node)
Definition: nodeCtescan.c:288
void ExecEndCustomScan(CustomScanState *node)
Definition: nodeCustom.c:125
void ExecEndForeignScan(ForeignScanState *node)
void ExecEndFunctionScan(FunctionScanState *node)
void ExecEndGatherMerge(GatherMergeState *node)
void ExecEndGather(GatherState *node)
Definition: nodeGather.c:244
void ExecEndGroup(GroupState *node)
Definition: nodeGroup.c:226
void ExecEndHash(HashState *node)
Definition: nodeHash.c:413
void ExecEndHashJoin(HashJoinState *node)
Definition: nodeHashjoin.c:858
void ExecEndIncrementalSort(IncrementalSortState *node)
void ExecEndIndexOnlyScan(IndexOnlyScanState *node)
void ExecEndIndexScan(IndexScanState *node)
void ExecEndLimit(LimitState *node)
Definition: nodeLimit.c:534
void ExecEndLockRows(LockRowsState *node)
Definition: nodeLockRows.c:385
void ExecEndMaterial(MaterialState *node)
Definition: nodeMaterial.c:240
void ExecEndMemoize(MemoizeState *node)
Definition: nodeMemoize.c:1079
void ExecEndMergeAppend(MergeAppendState *node)
void ExecEndMergeJoin(MergeJoinState *node)
void ExecEndModifyTable(ModifyTableState *node)
void ExecEndNestLoop(NestLoopState *node)
Definition: nodeNestloop.c:361
void ExecEndProjectSet(ProjectSetState *node)
void ExecEndRecursiveUnion(RecursiveUnionState *node)
void ExecEndResult(ResultState *node)
Definition: nodeResult.c:240
void ExecEndSampleScan(SampleScanState *node)
void ExecEndSeqScan(SeqScanState *node)
Definition: nodeSeqscan.c:184
void ExecEndSetOp(SetOpState *node)
Definition: nodeSetOp.c:583
void ExecEndSort(SortState *node)
Definition: nodeSort.c:301
void ExecEndSubqueryScan(SubqueryScanState *node)
void ExecEndTableFuncScan(TableFuncScanState *node)
void ExecEndTidRangeScan(TidRangeScanState *node)
void ExecEndTidScan(TidScanState *node)
Definition: nodeTidscan.c:470
void ExecEndUnique(UniqueState *node)
Definition: nodeUnique.c:168
void ExecEndWindowAgg(WindowAggState *node)
#define nodeTag(nodeptr)
Definition: nodes.h:133
void check_stack_depth(void)
Definition: postgres.c:3531
Bitmapset * chgParam
Definition: execnodes.h:1075

References bms_free(), check_stack_depth(), PlanState::chgParam, elog, ERROR, ExecEndAgg(), ExecEndAppend(), ExecEndBitmapAnd(), ExecEndBitmapHeapScan(), ExecEndBitmapIndexScan(), ExecEndBitmapOr(), ExecEndCteScan(), ExecEndCustomScan(), ExecEndForeignScan(), ExecEndFunctionScan(), ExecEndGather(), ExecEndGatherMerge(), ExecEndGroup(), ExecEndHash(), ExecEndHashJoin(), ExecEndIncrementalSort(), ExecEndIndexOnlyScan(), ExecEndIndexScan(), ExecEndLimit(), ExecEndLockRows(), ExecEndMaterial(), ExecEndMemoize(), ExecEndMergeAppend(), ExecEndMergeJoin(), ExecEndModifyTable(), ExecEndNestLoop(), ExecEndProjectSet(), ExecEndRecursiveUnion(), ExecEndResult(), ExecEndSampleScan(), ExecEndSeqScan(), ExecEndSetOp(), ExecEndSort(), ExecEndSubqueryScan(), ExecEndTableFuncScan(), ExecEndTidRangeScan(), ExecEndTidScan(), ExecEndUnique(), ExecEndWindowAgg(), and nodeTag.

Referenced by EvalPlanQualEnd(), ExecEndAgg(), ExecEndAppend(), ExecEndBitmapAnd(), ExecEndBitmapHeapScan(), ExecEndBitmapOr(), ExecEndForeignScan(), ExecEndGather(), ExecEndGatherMerge(), ExecEndGroup(), ExecEndHash(), ExecEndHashJoin(), ExecEndIncrementalSort(), ExecEndLimit(), ExecEndLockRows(), ExecEndMaterial(), ExecEndMemoize(), ExecEndMergeAppend(), ExecEndMergeJoin(), ExecEndModifyTable(), ExecEndNestLoop(), ExecEndPlan(), ExecEndProjectSet(), ExecEndRecursiveUnion(), ExecEndResult(), ExecEndSetOp(), ExecEndSort(), ExecEndSubqueryScan(), ExecEndUnique(), and ExecEndWindowAgg().

◆ ExecInitNode()

PlanState* ExecInitNode ( Plan node,
EState estate,
int  eflags 
)

Definition at line 142 of file execProcnode.c.

143 {
144  PlanState *result;
145  List *subps;
146  ListCell *l;
147 
148  /*
149  * do nothing when we get to the end of a leaf on tree.
150  */
151  if (node == NULL)
152  return NULL;
153 
154  /*
155  * Make sure there's enough stack available. Need to check here, in
156  * addition to ExecProcNode() (via ExecProcNodeFirst()), to ensure the
157  * stack isn't overrun while initializing the node tree.
158  */
160 
161  switch (nodeTag(node))
162  {
163  /*
164  * control nodes
165  */
166  case T_Result:
167  result = (PlanState *) ExecInitResult((Result *) node,
168  estate, eflags);
169  break;
170 
171  case T_ProjectSet:
172  result = (PlanState *) ExecInitProjectSet((ProjectSet *) node,
173  estate, eflags);
174  break;
175 
176  case T_ModifyTable:
177  result = (PlanState *) ExecInitModifyTable((ModifyTable *) node,
178  estate, eflags);
179  break;
180 
181  case T_Append:
182  result = (PlanState *) ExecInitAppend((Append *) node,
183  estate, eflags);
184  break;
185 
186  case T_MergeAppend:
187  result = (PlanState *) ExecInitMergeAppend((MergeAppend *) node,
188  estate, eflags);
189  break;
190 
191  case T_RecursiveUnion:
192  result = (PlanState *) ExecInitRecursiveUnion((RecursiveUnion *) node,
193  estate, eflags);
194  break;
195 
196  case T_BitmapAnd:
197  result = (PlanState *) ExecInitBitmapAnd((BitmapAnd *) node,
198  estate, eflags);
199  break;
200 
201  case T_BitmapOr:
202  result = (PlanState *) ExecInitBitmapOr((BitmapOr *) node,
203  estate, eflags);
204  break;
205 
206  /*
207  * scan nodes
208  */
209  case T_SeqScan:
210  result = (PlanState *) ExecInitSeqScan((SeqScan *) node,
211  estate, eflags);
212  break;
213 
214  case T_SampleScan:
215  result = (PlanState *) ExecInitSampleScan((SampleScan *) node,
216  estate, eflags);
217  break;
218 
219  case T_IndexScan:
220  result = (PlanState *) ExecInitIndexScan((IndexScan *) node,
221  estate, eflags);
222  break;
223 
224  case T_IndexOnlyScan:
225  result = (PlanState *) ExecInitIndexOnlyScan((IndexOnlyScan *) node,
226  estate, eflags);
227  break;
228 
229  case T_BitmapIndexScan:
230  result = (PlanState *) ExecInitBitmapIndexScan((BitmapIndexScan *) node,
231  estate, eflags);
232  break;
233 
234  case T_BitmapHeapScan:
235  result = (PlanState *) ExecInitBitmapHeapScan((BitmapHeapScan *) node,
236  estate, eflags);
237  break;
238 
239  case T_TidScan:
240  result = (PlanState *) ExecInitTidScan((TidScan *) node,
241  estate, eflags);
242  break;
243 
244  case T_TidRangeScan:
245  result = (PlanState *) ExecInitTidRangeScan((TidRangeScan *) node,
246  estate, eflags);
247  break;
248 
249  case T_SubqueryScan:
250  result = (PlanState *) ExecInitSubqueryScan((SubqueryScan *) node,
251  estate, eflags);
252  break;
253 
254  case T_FunctionScan:
255  result = (PlanState *) ExecInitFunctionScan((FunctionScan *) node,
256  estate, eflags);
257  break;
258 
259  case T_TableFuncScan:
260  result = (PlanState *) ExecInitTableFuncScan((TableFuncScan *) node,
261  estate, eflags);
262  break;
263 
264  case T_ValuesScan:
265  result = (PlanState *) ExecInitValuesScan((ValuesScan *) node,
266  estate, eflags);
267  break;
268 
269  case T_CteScan:
270  result = (PlanState *) ExecInitCteScan((CteScan *) node,
271  estate, eflags);
272  break;
273 
274  case T_NamedTuplestoreScan:
276  estate, eflags);
277  break;
278 
279  case T_WorkTableScan:
280  result = (PlanState *) ExecInitWorkTableScan((WorkTableScan *) node,
281  estate, eflags);
282  break;
283 
284  case T_ForeignScan:
285  result = (PlanState *) ExecInitForeignScan((ForeignScan *) node,
286  estate, eflags);
287  break;
288 
289  case T_CustomScan:
290  result = (PlanState *) ExecInitCustomScan((CustomScan *) node,
291  estate, eflags);
292  break;
293 
294  /*
295  * join nodes
296  */
297  case T_NestLoop:
298  result = (PlanState *) ExecInitNestLoop((NestLoop *) node,
299  estate, eflags);
300  break;
301 
302  case T_MergeJoin:
303  result = (PlanState *) ExecInitMergeJoin((MergeJoin *) node,
304  estate, eflags);
305  break;
306 
307  case T_HashJoin:
308  result = (PlanState *) ExecInitHashJoin((HashJoin *) node,
309  estate, eflags);
310  break;
311 
312  /*
313  * materialization nodes
314  */
315  case T_Material:
316  result = (PlanState *) ExecInitMaterial((Material *) node,
317  estate, eflags);
318  break;
319 
320  case T_Sort:
321  result = (PlanState *) ExecInitSort((Sort *) node,
322  estate, eflags);
323  break;
324 
325  case T_IncrementalSort:
326  result = (PlanState *) ExecInitIncrementalSort((IncrementalSort *) node,
327  estate, eflags);
328  break;
329 
330  case T_Memoize:
331  result = (PlanState *) ExecInitMemoize((Memoize *) node, estate,
332  eflags);
333  break;
334 
335  case T_Group:
336  result = (PlanState *) ExecInitGroup((Group *) node,
337  estate, eflags);
338  break;
339 
340  case T_Agg:
341  result = (PlanState *) ExecInitAgg((Agg *) node,
342  estate, eflags);
343  break;
344 
345  case T_WindowAgg:
346  result = (PlanState *) ExecInitWindowAgg((WindowAgg *) node,
347  estate, eflags);
348  break;
349 
350  case T_Unique:
351  result = (PlanState *) ExecInitUnique((Unique *) node,
352  estate, eflags);
353  break;
354 
355  case T_Gather:
356  result = (PlanState *) ExecInitGather((Gather *) node,
357  estate, eflags);
358  break;
359 
360  case T_GatherMerge:
361  result = (PlanState *) ExecInitGatherMerge((GatherMerge *) node,
362  estate, eflags);
363  break;
364 
365  case T_Hash:
366  result = (PlanState *) ExecInitHash((Hash *) node,
367  estate, eflags);
368  break;
369 
370  case T_SetOp:
371  result = (PlanState *) ExecInitSetOp((SetOp *) node,
372  estate, eflags);
373  break;
374 
375  case T_LockRows:
376  result = (PlanState *) ExecInitLockRows((LockRows *) node,
377  estate, eflags);
378  break;
379 
380  case T_Limit:
381  result = (PlanState *) ExecInitLimit((Limit *) node,
382  estate, eflags);
383  break;
384 
385  default:
386  elog(ERROR, "unrecognized node type: %d", (int) nodeTag(node));
387  result = NULL; /* keep compiler quiet */
388  break;
389  }
390 
391  ExecSetExecProcNode(result, result->ExecProcNode);
392 
393  /*
394  * Initialize any initPlans present in this node. The planner put them in
395  * a separate list for us.
396  */
397  subps = NIL;
398  foreach(l, node->initPlan)
399  {
400  SubPlan *subplan = (SubPlan *) lfirst(l);
401  SubPlanState *sstate;
402 
403  Assert(IsA(subplan, SubPlan));
404  sstate = ExecInitSubPlan(subplan, result);
405  subps = lappend(subps, sstate);
406  }
407  result->initPlan = subps;
408 
409  /* Set up instrumentation for this node if requested */
410  if (estate->es_instrument)
411  result->instrument = InstrAlloc(1, estate->es_instrument,
412  result->async_capable);
413 
414  return result;
415 }
void ExecSetExecProcNode(PlanState *node, ExecProcNodeMtd function)
Definition: execProcnode.c:425
Instrumentation * InstrAlloc(int n, int instrument_options, bool async_mode)
Definition: instrument.c:31
Assert(fmt[strlen(fmt) - 1] !='\n')
List * lappend(List *list, void *datum)
Definition: list.c:339
AggState * ExecInitAgg(Agg *node, EState *estate, int eflags)
Definition: nodeAgg.c:3173
AppendState * ExecInitAppend(Append *node, EState *estate, int eflags)
Definition: nodeAppend.c:109
BitmapAndState * ExecInitBitmapAnd(BitmapAnd *node, EState *estate, int eflags)
Definition: nodeBitmapAnd.c:55
BitmapHeapScanState * ExecInitBitmapHeapScan(BitmapHeapScan *node, EState *estate, int eflags)
BitmapIndexScanState * ExecInitBitmapIndexScan(BitmapIndexScan *node, EState *estate, int eflags)
BitmapOrState * ExecInitBitmapOr(BitmapOr *node, EState *estate, int eflags)
Definition: nodeBitmapOr.c:56
CteScanState * ExecInitCteScan(CteScan *node, EState *estate, int eflags)
Definition: nodeCtescan.c:175
CustomScanState * ExecInitCustomScan(CustomScan *cscan, EState *estate, int eflags)
Definition: nodeCustom.c:26
ForeignScanState * ExecInitForeignScan(ForeignScan *node, EState *estate, int eflags)
FunctionScanState * ExecInitFunctionScan(FunctionScan *node, EState *estate, int eflags)
GatherMergeState * ExecInitGatherMerge(GatherMerge *node, EState *estate, int eflags)
GatherState * ExecInitGather(Gather *node, EState *estate, int eflags)
Definition: nodeGather.c:53
GroupState * ExecInitGroup(Group *node, EState *estate, int eflags)
Definition: nodeGroup.c:161
HashState * ExecInitHash(Hash *node, EState *estate, int eflags)
Definition: nodeHash.c:360
HashJoinState * ExecInitHashJoin(HashJoin *node, EState *estate, int eflags)
Definition: nodeHashjoin.c:709
IncrementalSortState * ExecInitIncrementalSort(IncrementalSort *node, EState *estate, int eflags)
IndexOnlyScanState * ExecInitIndexOnlyScan(IndexOnlyScan *node, EState *estate, int eflags)
IndexScanState * ExecInitIndexScan(IndexScan *node, EState *estate, int eflags)
LimitState * ExecInitLimit(Limit *node, EState *estate, int eflags)
Definition: nodeLimit.c:447
LockRowsState * ExecInitLockRows(LockRows *node, EState *estate, int eflags)
Definition: nodeLockRows.c:291
MaterialState * ExecInitMaterial(Material *node, EState *estate, int eflags)
Definition: nodeMaterial.c:164
MemoizeState * ExecInitMemoize(Memoize *node, EState *estate, int eflags)
Definition: nodeMemoize.c:951
MergeAppendState * ExecInitMergeAppend(MergeAppend *node, EState *estate, int eflags)
MergeJoinState * ExecInitMergeJoin(MergeJoin *node, EState *estate, int eflags)
ModifyTableState * ExecInitModifyTable(ModifyTable *node, EState *estate, int eflags)
NamedTuplestoreScanState * ExecInitNamedTuplestoreScan(NamedTuplestoreScan *node, EState *estate, int eflags)
NestLoopState * ExecInitNestLoop(NestLoop *node, EState *estate, int eflags)
Definition: nodeNestloop.c:262
ProjectSetState * ExecInitProjectSet(ProjectSet *node, EState *estate, int eflags)
RecursiveUnionState * ExecInitRecursiveUnion(RecursiveUnion *node, EState *estate, int eflags)
ResultState * ExecInitResult(Result *node, EState *estate, int eflags)
Definition: nodeResult.c:180
SampleScanState * ExecInitSampleScan(SampleScan *node, EState *estate, int eflags)
SeqScanState * ExecInitSeqScan(SeqScan *node, EState *estate, int eflags)
Definition: nodeSeqscan.c:123
SetOpState * ExecInitSetOp(SetOp *node, EState *estate, int eflags)
Definition: nodeSetOp.c:481
SortState * ExecInitSort(Sort *node, EState *estate, int eflags)
Definition: nodeSort.c:221
SubPlanState * ExecInitSubPlan(SubPlan *subplan, PlanState *parent)
Definition: nodeSubplan.c:823
SubqueryScanState * ExecInitSubqueryScan(SubqueryScan *node, EState *estate, int eflags)
TableFuncScanState * ExecInitTableFuncScan(TableFuncScan *node, EState *estate, int eflags)
TidRangeScanState * ExecInitTidRangeScan(TidRangeScan *node, EState *estate, int eflags)
TidScanState * ExecInitTidScan(TidScan *node, EState *estate, int eflags)
Definition: nodeTidscan.c:488
UniqueState * ExecInitUnique(Unique *node, EState *estate, int eflags)
Definition: nodeUnique.c:114
ValuesScanState * ExecInitValuesScan(ValuesScan *node, EState *estate, int eflags)
WindowAggState * ExecInitWindowAgg(WindowAgg *node, EState *estate, int eflags)
WorkTableScanState * ExecInitWorkTableScan(WorkTableScan *node, EState *estate, int eflags)
#define IsA(nodeptr, _type_)
Definition: nodes.h:158
#define lfirst(lc)
Definition: pg_list.h:172
#define NIL
Definition: pg_list.h:68
Definition: plannodes.h:995
Definition: pg_list.h:54
Instrumentation * instrument
Definition: execnodes.h:1053
List * initPlan
Definition: execnodes.h:1068
bool async_capable
Definition: execnodes.h:1085
ExecProcNodeMtd ExecProcNode
Definition: execnodes.h:1049
List * initPlan
Definition: plannodes.h:156

References Assert(), PlanState::async_capable, check_stack_depth(), elog, ERROR, EState::es_instrument, ExecInitAgg(), ExecInitAppend(), ExecInitBitmapAnd(), ExecInitBitmapHeapScan(), ExecInitBitmapIndexScan(), ExecInitBitmapOr(), ExecInitCteScan(), ExecInitCustomScan(), ExecInitForeignScan(), ExecInitFunctionScan(), ExecInitGather(), ExecInitGatherMerge(), ExecInitGroup(), ExecInitHash(), ExecInitHashJoin(), ExecInitIncrementalSort(), ExecInitIndexOnlyScan(), ExecInitIndexScan(), ExecInitLimit(), ExecInitLockRows(), ExecInitMaterial(), ExecInitMemoize(), ExecInitMergeAppend(), ExecInitMergeJoin(), ExecInitModifyTable(), ExecInitNamedTuplestoreScan(), ExecInitNestLoop(), ExecInitProjectSet(), ExecInitRecursiveUnion(), ExecInitResult(), ExecInitSampleScan(), ExecInitSeqScan(), ExecInitSetOp(), ExecInitSort(), ExecInitSubPlan(), ExecInitSubqueryScan(), ExecInitTableFuncScan(), ExecInitTidRangeScan(), ExecInitTidScan(), ExecInitUnique(), ExecInitValuesScan(), ExecInitWindowAgg(), ExecInitWorkTableScan(), PlanState::ExecProcNode, ExecSetExecProcNode(), PlanState::initPlan, Plan::initPlan, InstrAlloc(), PlanState::instrument, IsA, lappend(), lfirst, NIL, and nodeTag.

Referenced by EvalPlanQualStart(), ExecInitAgg(), ExecInitAppend(), ExecInitBitmapAnd(), ExecInitBitmapHeapScan(), ExecInitBitmapOr(), ExecInitForeignScan(), ExecInitGather(), ExecInitGatherMerge(), ExecInitGroup(), ExecInitHash(), ExecInitHashJoin(), ExecInitIncrementalSort(), ExecInitLimit(), ExecInitLockRows(), ExecInitMaterial(), ExecInitMemoize(), ExecInitMergeAppend(), ExecInitMergeJoin(), ExecInitModifyTable(), ExecInitNestLoop(), ExecInitProjectSet(), ExecInitRecursiveUnion(), ExecInitResult(), ExecInitSetOp(), ExecInitSort(), ExecInitSubqueryScan(), ExecInitUnique(), ExecInitWindowAgg(), and InitPlan().

◆ ExecProcNodeFirst()

static TupleTableSlot * ExecProcNodeFirst ( PlanState node)
static

Definition at line 443 of file execProcnode.c.

444 {
445  /*
446  * Perform stack depth check during the first execution of the node. We
447  * only do so the first time round because it turns out to not be cheap on
448  * some common architectures (eg. x86). This relies on the assumption
449  * that ExecProcNode calls for a given plan node will always be made at
450  * roughly the same stack depth.
451  */
453 
454  /*
455  * If instrumentation is required, change the wrapper to one that just
456  * does instrumentation. Otherwise we can dispense with all wrappers and
457  * have ExecProcNode() directly call the relevant function from now on.
458  */
459  if (node->instrument)
461  else
462  node->ExecProcNode = node->ExecProcNodeReal;
463 
464  return node->ExecProcNode(node);
465 }
static TupleTableSlot * ExecProcNodeInstr(PlanState *node)
Definition: execProcnode.c:474
ExecProcNodeMtd ExecProcNodeReal
Definition: execnodes.h:1050

References check_stack_depth(), PlanState::ExecProcNode, ExecProcNodeInstr(), PlanState::ExecProcNodeReal, and PlanState::instrument.

Referenced by ExecSetExecProcNode().

◆ ExecProcNodeInstr()

static TupleTableSlot * ExecProcNodeInstr ( PlanState node)
static

Definition at line 474 of file execProcnode.c.

475 {
476  TupleTableSlot *result;
477 
478  InstrStartNode(node->instrument);
479 
480  result = node->ExecProcNodeReal(node);
481 
482  InstrStopNode(node->instrument, TupIsNull(result) ? 0.0 : 1.0);
483 
484  return result;
485 }
void InstrStartNode(Instrumentation *instr)
Definition: instrument.c:68
void InstrStopNode(Instrumentation *instr, double nTuples)
Definition: instrument.c:84
#define TupIsNull(slot)
Definition: tuptable.h:300

References PlanState::ExecProcNodeReal, InstrStartNode(), InstrStopNode(), PlanState::instrument, and TupIsNull.

Referenced by ExecProcNodeFirst().

◆ ExecSetExecProcNode()

void ExecSetExecProcNode ( PlanState node,
ExecProcNodeMtd  function 
)

Definition at line 425 of file execProcnode.c.

426 {
427  /*
428  * Add a wrapper around the ExecProcNode callback that checks stack depth
429  * during the first execution and maybe adds an instrumentation wrapper.
430  * When the callback is changed after execution has already begun that
431  * means we'll superfluously execute ExecProcNodeFirst, but that seems ok.
432  */
433  node->ExecProcNodeReal = function;
435 }
static TupleTableSlot * ExecProcNodeFirst(PlanState *node)
Definition: execProcnode.c:443

References PlanState::ExecProcNode, ExecProcNodeFirst(), and PlanState::ExecProcNodeReal.

Referenced by ExecHashJoinInitializeDSM(), ExecHashJoinInitializeWorker(), and ExecInitNode().

◆ ExecSetTupleBound()

void ExecSetTupleBound ( int64  tuples_needed,
PlanState child_node 
)

Definition at line 843 of file execProcnode.c.

844 {
845  /*
846  * Since this function recurses, in principle we should check stack depth
847  * here. In practice, it's probably pointless since the earlier node
848  * initialization tree traversal would surely have consumed more stack.
849  */
850 
851  if (IsA(child_node, SortState))
852  {
853  /*
854  * If it is a Sort node, notify it that it can use bounded sort.
855  *
856  * Note: it is the responsibility of nodeSort.c to react properly to
857  * changes of these parameters. If we ever redesign this, it'd be a
858  * good idea to integrate this signaling with the parameter-change
859  * mechanism.
860  */
861  SortState *sortState = (SortState *) child_node;
862 
863  if (tuples_needed < 0)
864  {
865  /* make sure flag gets reset if needed upon rescan */
866  sortState->bounded = false;
867  }
868  else
869  {
870  sortState->bounded = true;
871  sortState->bound = tuples_needed;
872  }
873  }
874  else if (IsA(child_node, IncrementalSortState))
875  {
876  /*
877  * If it is an IncrementalSort node, notify it that it can use bounded
878  * sort.
879  *
880  * Note: it is the responsibility of nodeIncrementalSort.c to react
881  * properly to changes of these parameters. If we ever redesign this,
882  * it'd be a good idea to integrate this signaling with the
883  * parameter-change mechanism.
884  */
885  IncrementalSortState *sortState = (IncrementalSortState *) child_node;
886 
887  if (tuples_needed < 0)
888  {
889  /* make sure flag gets reset if needed upon rescan */
890  sortState->bounded = false;
891  }
892  else
893  {
894  sortState->bounded = true;
895  sortState->bound = tuples_needed;
896  }
897  }
898  else if (IsA(child_node, AppendState))
899  {
900  /*
901  * If it is an Append, we can apply the bound to any nodes that are
902  * children of the Append, since the Append surely need read no more
903  * than that many tuples from any one input.
904  */
905  AppendState *aState = (AppendState *) child_node;
906  int i;
907 
908  for (i = 0; i < aState->as_nplans; i++)
909  ExecSetTupleBound(tuples_needed, aState->appendplans[i]);
910  }
911  else if (IsA(child_node, MergeAppendState))
912  {
913  /*
914  * If it is a MergeAppend, we can apply the bound to any nodes that
915  * are children of the MergeAppend, since the MergeAppend surely need
916  * read no more than that many tuples from any one input.
917  */
918  MergeAppendState *maState = (MergeAppendState *) child_node;
919  int i;
920 
921  for (i = 0; i < maState->ms_nplans; i++)
922  ExecSetTupleBound(tuples_needed, maState->mergeplans[i]);
923  }
924  else if (IsA(child_node, ResultState))
925  {
926  /*
927  * Similarly, for a projecting Result, we can apply the bound to its
928  * child node.
929  *
930  * If Result supported qual checking, we'd have to punt on seeing a
931  * qual. Note that having a resconstantqual is not a showstopper: if
932  * that condition succeeds it affects nothing, while if it fails, no
933  * rows will be demanded from the Result child anyway.
934  */
935  if (outerPlanState(child_node))
936  ExecSetTupleBound(tuples_needed, outerPlanState(child_node));
937  }
938  else if (IsA(child_node, SubqueryScanState))
939  {
940  /*
941  * We can also descend through SubqueryScan, but only if it has no
942  * qual (otherwise it might discard rows).
943  */
944  SubqueryScanState *subqueryState = (SubqueryScanState *) child_node;
945 
946  if (subqueryState->ss.ps.qual == NULL)
947  ExecSetTupleBound(tuples_needed, subqueryState->subplan);
948  }
949  else if (IsA(child_node, GatherState))
950  {
951  /*
952  * A Gather node can propagate the bound to its workers. As with
953  * MergeAppend, no one worker could possibly need to return more
954  * tuples than the Gather itself needs to.
955  *
956  * Note: As with Sort, the Gather node is responsible for reacting
957  * properly to changes to this parameter.
958  */
959  GatherState *gstate = (GatherState *) child_node;
960 
961  gstate->tuples_needed = tuples_needed;
962 
963  /* Also pass down the bound to our own copy of the child plan */
964  ExecSetTupleBound(tuples_needed, outerPlanState(child_node));
965  }
966  else if (IsA(child_node, GatherMergeState))
967  {
968  /* Same comments as for Gather */
969  GatherMergeState *gstate = (GatherMergeState *) child_node;
970 
971  gstate->tuples_needed = tuples_needed;
972 
973  ExecSetTupleBound(tuples_needed, outerPlanState(child_node));
974  }
975 
976  /*
977  * In principle we could descend through any plan node type that is
978  * certain not to discard or combine input rows; but on seeing a node that
979  * can do that, we can't propagate the bound any further. For the moment
980  * it's unclear that any other cases are worth checking here.
981  */
982 }
void ExecSetTupleBound(int64 tuples_needed, PlanState *child_node)
Definition: execProcnode.c:843
#define outerPlanState(node)
Definition: execnodes.h:1139
int i
Definition: isn.c:73
PlanState ** appendplans
Definition: execnodes.h:1359
int64 tuples_needed
Definition: execnodes.h:2594
PlanState ** mergeplans
Definition: execnodes.h:1403
ExprState * qual
Definition: execnodes.h:1064
PlanState ps
Definition: execnodes.h:1483
bool bounded
Definition: execnodes.h:2255
int64 bound
Definition: execnodes.h:2256
PlanState * subplan
Definition: execnodes.h:1804

References AppendState::appendplans, AppendState::as_nplans, SortState::bound, IncrementalSortState::bound, SortState::bounded, IncrementalSortState::bounded, i, IsA, MergeAppendState::mergeplans, MergeAppendState::ms_nplans, outerPlanState, ScanState::ps, PlanState::qual, SubqueryScanState::ss, SubqueryScanState::subplan, GatherState::tuples_needed, and GatherMergeState::tuples_needed.

Referenced by ParallelQueryMain(), and recompute_limits().

◆ ExecShutdownNode()

void ExecShutdownNode ( PlanState node)

Definition at line 767 of file execProcnode.c.

768 {
769  (void) ExecShutdownNode_walker(node, NULL);
770 }
static bool ExecShutdownNode_walker(PlanState *node, void *context)
Definition: execProcnode.c:773

References ExecShutdownNode_walker().

Referenced by ExecutePlan().

◆ ExecShutdownNode_walker()

static bool ExecShutdownNode_walker ( PlanState node,
void *  context 
)
static

Definition at line 773 of file execProcnode.c.

774 {
775  if (node == NULL)
776  return false;
777 
779 
780  /*
781  * Treat the node as running while we shut it down, but only if it's run
782  * at least once already. We don't expect much CPU consumption during
783  * node shutdown, but in the case of Gather or Gather Merge, we may shut
784  * down workers at this stage. If so, their buffer usage will get
785  * propagated into pgBufferUsage at this point, and we want to make sure
786  * that it gets associated with the Gather node. We skip this if the node
787  * has never been executed, so as to avoid incorrectly making it appear
788  * that it has.
789  */
790  if (node->instrument && node->instrument->running)
791  InstrStartNode(node->instrument);
792 
794 
795  switch (nodeTag(node))
796  {
797  case T_GatherState:
799  break;
800  case T_ForeignScanState:
802  break;
803  case T_CustomScanState:
805  break;
806  case T_GatherMergeState:
808  break;
809  case T_HashState:
810  ExecShutdownHash((HashState *) node);
811  break;
812  case T_HashJoinState:
814  break;
815  default:
816  break;
817  }
818 
819  /* Stop the node if we started it above, reporting 0 tuples. */
820  if (node->instrument && node->instrument->running)
821  InstrStopNode(node->instrument, 0);
822 
823  return false;
824 }
void ExecShutdownCustomScan(CustomScanState *node)
Definition: nodeCustom.c:221
void ExecShutdownForeignScan(ForeignScanState *node)
#define planstate_tree_walker(ps, w, c)
Definition: nodeFuncs.h:177
void ExecShutdownGatherMerge(GatherMergeState *node)
void ExecShutdownGather(GatherState *node)
Definition: nodeGather.c:411
void ExecShutdownHash(HashState *node)
Definition: nodeHash.c:2804
void ExecShutdownHashJoin(HashJoinState *node)

References check_stack_depth(), ExecShutdownCustomScan(), ExecShutdownForeignScan(), ExecShutdownGather(), ExecShutdownGatherMerge(), ExecShutdownHash(), ExecShutdownHashJoin(), InstrStartNode(), InstrStopNode(), PlanState::instrument, nodeTag, planstate_tree_walker, and Instrumentation::running.

Referenced by ExecShutdownNode().

◆ MultiExecProcNode()

Node* MultiExecProcNode ( PlanState node)

Definition at line 502 of file execProcnode.c.

503 {
504  Node *result;
505 
507 
509 
510  if (node->chgParam != NULL) /* something changed */
511  ExecReScan(node); /* let ReScan handle this */
512 
513  switch (nodeTag(node))
514  {
515  /*
516  * Only node types that actually support multiexec will be listed
517  */
518 
519  case T_HashState:
520  result = MultiExecHash((HashState *) node);
521  break;
522 
523  case T_BitmapIndexScanState:
525  break;
526 
527  case T_BitmapAndState:
528  result = MultiExecBitmapAnd((BitmapAndState *) node);
529  break;
530 
531  case T_BitmapOrState:
532  result = MultiExecBitmapOr((BitmapOrState *) node);
533  break;
534 
535  default:
536  elog(ERROR, "unrecognized node type: %d", (int) nodeTag(node));
537  result = NULL;
538  break;
539  }
540 
541  return result;
542 }
void ExecReScan(PlanState *node)
Definition: execAmi.c:76
#define CHECK_FOR_INTERRUPTS()
Definition: miscadmin.h:122
Node * MultiExecBitmapAnd(BitmapAndState *node)
Node * MultiExecBitmapIndexScan(BitmapIndexScanState *node)
Node * MultiExecBitmapOr(BitmapOrState *node)
Definition: nodeBitmapOr.c:111
Node * MultiExecHash(HashState *node)
Definition: nodeHash.c:105
Definition: nodes.h:129

References CHECK_FOR_INTERRUPTS, check_stack_depth(), PlanState::chgParam, elog, ERROR, ExecReScan(), MultiExecBitmapAnd(), MultiExecBitmapIndexScan(), MultiExecBitmapOr(), MultiExecHash(), and nodeTag.

Referenced by BitmapHeapNext(), ExecHashJoinImpl(), MultiExecBitmapAnd(), and MultiExecBitmapOr().