1 /*-------------------------------------------------------------------------
4 * contains dispatch functions which call the appropriate "initialize",
5 * "get a tuple", and "cleanup" routines for the given node type.
6 * If the node has children, then it will presumably call ExecInitNode,
7 * ExecProcNode, or ExecEndNode on its subnodes and do the appropriate
10 * Portions Copyright (c) 1996-2009, PostgreSQL Global Development Group
11 * Portions Copyright (c) 1994, Regents of the University of California
17 *-------------------------------------------------------------------------
21 * ExecCountSlotsNode - count tuple slots needed by plan tree
22 * ExecInitNode - initialize a plan node and its subplans
23 * ExecProcNode - get a tuple by executing the plan node
24 * ExecEndNode - shut down a plan node and its subplans
27 * This used to be three files. It is now all combined into
28 * one file so that it is easier to keep ExecInitNode, ExecProcNode,
29 * and ExecEndNode in sync when new nodes are added.
32 * Suppose we want the age of the manager of the shoe department and
33 * the number of employees in that department. So we have the query:
35 * select DEPT.no_emps, EMP.age
36 * where EMP.name = DEPT.mgr and
39 * Suppose the planner gives us the following plan:
41 * Nest Loop (DEPT.mgr = EMP.name)
48 * ExecutorStart() is called first.
49 * It calls InitPlan() which calls ExecInitNode() on
50 * the root of the plan -- the nest loop node.
52 * * ExecInitNode() notices that it is looking at a nest loop and
53 * as the code below demonstrates, it calls ExecInitNestLoop().
54 * Eventually this calls ExecInitNode() on the right and left subplans
55 * and so forth until the entire plan is initialized. The result
56 * of ExecInitNode() is a plan state tree built with the same structure
57 * as the underlying plan tree.
59 * * Then when ExecRun() is called, it calls ExecutePlan() which calls
60 * ExecProcNode() repeatedly on the top node of the plan state tree.
61 * Each time this happens, ExecProcNode() will end up calling
62 * ExecNestLoop(), which calls ExecProcNode() on its subplans.
63 * Each of these subplans is a sequential scan so ExecSeqScan() is
64 * called. The slots returned by ExecSeqScan() may contain
65 * tuples which contain the attributes ExecNestLoop() uses to
66 * form the tuples it returns.
68 * * Eventually ExecSeqScan() stops returning tuples and the nest
69 * loop join ends. Lastly, ExecEnd() calls ExecEndNode() which
70 * calls ExecEndNestLoop() which in turn calls ExecEndNode() on
71 * its subplans which result in ExecEndSeqScan().
73 * This should show how the executor works by having
74 * ExecInitNode(), ExecProcNode() and ExecEndNode() dispatch
75 * their work to the appopriate node support routines which may
76 * in turn call these routines themselves on their subplans.
80 #include "executor/executor.h"
81 #include "executor/instrument.h"
82 #include "executor/nodeAgg.h"
83 #include "executor/nodeAppend.h"
84 #include "executor/nodeBitmapAnd.h"
85 #include "executor/nodeBitmapHeapscan.h"
86 #include "executor/nodeBitmapIndexscan.h"
87 #include "executor/nodeBitmapOr.h"
88 #include "executor/nodeCtescan.h"
89 #include "executor/nodeFunctionscan.h"
90 #include "executor/nodeGroup.h"
91 #include "executor/nodeHash.h"
92 #include "executor/nodeHashjoin.h"
93 #include "executor/nodeIndexscan.h"
94 #include "executor/nodeLimit.h"
95 #include "executor/nodeMaterial.h"
96 #include "executor/nodeMergejoin.h"
97 #include "executor/nodeNestloop.h"
98 #include "executor/nodeRecursiveunion.h"
99 #include "executor/nodeResult.h"
100 #include "executor/nodeSeqscan.h"
101 #include "executor/nodeSetOp.h"
102 #include "executor/nodeSort.h"
103 #include "executor/nodeSubplan.h"
104 #include "executor/nodeSubqueryscan.h"
105 #include "executor/nodeTidscan.h"
106 #include "executor/nodeUnique.h"
107 #include "executor/nodeValuesscan.h"
108 #include "executor/nodeWindowAgg.h"
109 #include "executor/nodeWorktablescan.h"
110 #include "miscadmin.h"
113 /* ------------------------------------------------------------------------
116 * Recursively initializes all the nodes in the plan tree rooted
120 * 'node' is the current node of the plan produced by the query planner
121 * 'estate' is the shared execution state for the plan tree
122 * 'eflags' is a bitwise OR of flag bits described in executor.h
124 * Returns a PlanState node corresponding to the given Plan node.
125 * ------------------------------------------------------------------------
128 ExecInitNode(Plan
*node
, EState
*estate
, int eflags
)
135 * do nothing when we get to the end of a leaf on tree.
140 switch (nodeTag(node
))
146 result
= (PlanState
*) ExecInitResult((Result
*) node
,
151 result
= (PlanState
*) ExecInitAppend((Append
*) node
,
155 case T_RecursiveUnion
:
156 result
= (PlanState
*) ExecInitRecursiveUnion((RecursiveUnion
*) node
,
161 result
= (PlanState
*) ExecInitBitmapAnd((BitmapAnd
*) node
,
166 result
= (PlanState
*) ExecInitBitmapOr((BitmapOr
*) node
,
174 result
= (PlanState
*) ExecInitSeqScan((SeqScan
*) node
,
179 result
= (PlanState
*) ExecInitIndexScan((IndexScan
*) node
,
183 case T_BitmapIndexScan
:
184 result
= (PlanState
*) ExecInitBitmapIndexScan((BitmapIndexScan
*) node
,
188 case T_BitmapHeapScan
:
189 result
= (PlanState
*) ExecInitBitmapHeapScan((BitmapHeapScan
*) node
,
194 result
= (PlanState
*) ExecInitTidScan((TidScan
*) node
,
199 result
= (PlanState
*) ExecInitSubqueryScan((SubqueryScan
*) node
,
204 result
= (PlanState
*) ExecInitFunctionScan((FunctionScan
*) node
,
209 result
= (PlanState
*) ExecInitValuesScan((ValuesScan
*) node
,
214 result
= (PlanState
*) ExecInitCteScan((CteScan
*) node
,
218 case T_WorkTableScan
:
219 result
= (PlanState
*) ExecInitWorkTableScan((WorkTableScan
*) node
,
227 result
= (PlanState
*) ExecInitNestLoop((NestLoop
*) node
,
232 result
= (PlanState
*) ExecInitMergeJoin((MergeJoin
*) node
,
237 result
= (PlanState
*) ExecInitHashJoin((HashJoin
*) node
,
242 * materialization nodes
245 result
= (PlanState
*) ExecInitMaterial((Material
*) node
,
250 result
= (PlanState
*) ExecInitSort((Sort
*) node
,
255 result
= (PlanState
*) ExecInitGroup((Group
*) node
,
260 result
= (PlanState
*) ExecInitAgg((Agg
*) node
,
265 result
= (PlanState
*) ExecInitWindowAgg((WindowAgg
*) node
,
270 result
= (PlanState
*) ExecInitUnique((Unique
*) node
,
275 result
= (PlanState
*) ExecInitHash((Hash
*) node
,
280 result
= (PlanState
*) ExecInitSetOp((SetOp
*) node
,
285 result
= (PlanState
*) ExecInitLimit((Limit
*) node
,
290 elog(ERROR
, "unrecognized node type: %d", (int) nodeTag(node
));
291 result
= NULL
; /* keep compiler quiet */
296 * Initialize any initPlans present in this node. The planner put them in
297 * a separate list for us.
300 foreach(l
, node
->initPlan
)
302 SubPlan
*subplan
= (SubPlan
*) lfirst(l
);
303 SubPlanState
*sstate
;
305 Assert(IsA(subplan
, SubPlan
));
306 sstate
= ExecInitSubPlan(subplan
, result
);
307 subps
= lappend(subps
, sstate
);
309 result
->initPlan
= subps
;
311 /* Set up instrumentation for this node if requested */
312 if (estate
->es_instrument
)
313 result
->instrument
= InstrAlloc(1);
319 /* ----------------------------------------------------------------
322 * Execute the given node to return a(nother) tuple.
323 * ----------------------------------------------------------------
326 ExecProcNode(PlanState
*node
)
328 TupleTableSlot
*result
;
330 CHECK_FOR_INTERRUPTS();
332 if (node
->chgParam
!= NULL
) /* something changed */
333 ExecReScan(node
, NULL
); /* let ReScan handle this */
335 if (node
->instrument
)
336 InstrStartNode(node
->instrument
);
338 switch (nodeTag(node
))
344 result
= ExecResult((ResultState
*) node
);
348 result
= ExecAppend((AppendState
*) node
);
351 case T_RecursiveUnionState
:
352 result
= ExecRecursiveUnion((RecursiveUnionState
*) node
);
355 /* BitmapAndState does not yield tuples */
357 /* BitmapOrState does not yield tuples */
363 result
= ExecSeqScan((SeqScanState
*) node
);
366 case T_IndexScanState
:
367 result
= ExecIndexScan((IndexScanState
*) node
);
370 /* BitmapIndexScanState does not yield tuples */
372 case T_BitmapHeapScanState
:
373 result
= ExecBitmapHeapScan((BitmapHeapScanState
*) node
);
377 result
= ExecTidScan((TidScanState
*) node
);
380 case T_SubqueryScanState
:
381 result
= ExecSubqueryScan((SubqueryScanState
*) node
);
384 case T_FunctionScanState
:
385 result
= ExecFunctionScan((FunctionScanState
*) node
);
388 case T_ValuesScanState
:
389 result
= ExecValuesScan((ValuesScanState
*) node
);
393 result
= ExecCteScan((CteScanState
*) node
);
396 case T_WorkTableScanState
:
397 result
= ExecWorkTableScan((WorkTableScanState
*) node
);
403 case T_NestLoopState
:
404 result
= ExecNestLoop((NestLoopState
*) node
);
407 case T_MergeJoinState
:
408 result
= ExecMergeJoin((MergeJoinState
*) node
);
411 case T_HashJoinState
:
412 result
= ExecHashJoin((HashJoinState
*) node
);
416 * materialization nodes
418 case T_MaterialState
:
419 result
= ExecMaterial((MaterialState
*) node
);
423 result
= ExecSort((SortState
*) node
);
427 result
= ExecGroup((GroupState
*) node
);
431 result
= ExecAgg((AggState
*) node
);
434 case T_WindowAggState
:
435 result
= ExecWindowAgg((WindowAggState
*) node
);
439 result
= ExecUnique((UniqueState
*) node
);
443 result
= ExecHash((HashState
*) node
);
447 result
= ExecSetOp((SetOpState
*) node
);
451 result
= ExecLimit((LimitState
*) node
);
455 elog(ERROR
, "unrecognized node type: %d", (int) nodeTag(node
));
460 if (node
->instrument
)
461 InstrStopNode(node
->instrument
, TupIsNull(result
) ? 0.0 : 1.0);
467 /* ----------------------------------------------------------------
470 * Execute a node that doesn't return individual tuples
471 * (it might return a hashtable, bitmap, etc). Caller should
472 * check it got back the expected kind of Node.
474 * This has essentially the same responsibilities as ExecProcNode,
475 * but it does not do InstrStartNode/InstrStopNode (mainly because
476 * it can't tell how many returned tuples to count). Each per-node
477 * function must provide its own instrumentation support.
478 * ----------------------------------------------------------------
481 MultiExecProcNode(PlanState
*node
)
485 CHECK_FOR_INTERRUPTS();
487 if (node
->chgParam
!= NULL
) /* something changed */
488 ExecReScan(node
, NULL
); /* let ReScan handle this */
490 switch (nodeTag(node
))
493 * Only node types that actually support multiexec will be listed
497 result
= MultiExecHash((HashState
*) node
);
500 case T_BitmapIndexScanState
:
501 result
= MultiExecBitmapIndexScan((BitmapIndexScanState
*) node
);
504 case T_BitmapAndState
:
505 result
= MultiExecBitmapAnd((BitmapAndState
*) node
);
508 case T_BitmapOrState
:
509 result
= MultiExecBitmapOr((BitmapOrState
*) node
);
513 elog(ERROR
, "unrecognized node type: %d", (int) nodeTag(node
));
523 * ExecCountSlotsNode - count up the number of tuple table slots needed
525 * Note that this scans a Plan tree, not a PlanState tree, because we
526 * haven't built the PlanState tree yet ...
529 ExecCountSlotsNode(Plan
*node
)
534 switch (nodeTag(node
))
540 return ExecCountSlotsResult((Result
*) node
);
543 return ExecCountSlotsAppend((Append
*) node
);
545 case T_RecursiveUnion
:
546 return ExecCountSlotsRecursiveUnion((RecursiveUnion
*) node
);
549 return ExecCountSlotsBitmapAnd((BitmapAnd
*) node
);
552 return ExecCountSlotsBitmapOr((BitmapOr
*) node
);
558 return ExecCountSlotsSeqScan((SeqScan
*) node
);
561 return ExecCountSlotsIndexScan((IndexScan
*) node
);
563 case T_BitmapIndexScan
:
564 return ExecCountSlotsBitmapIndexScan((BitmapIndexScan
*) node
);
566 case T_BitmapHeapScan
:
567 return ExecCountSlotsBitmapHeapScan((BitmapHeapScan
*) node
);
570 return ExecCountSlotsTidScan((TidScan
*) node
);
573 return ExecCountSlotsSubqueryScan((SubqueryScan
*) node
);
576 return ExecCountSlotsFunctionScan((FunctionScan
*) node
);
579 return ExecCountSlotsValuesScan((ValuesScan
*) node
);
582 return ExecCountSlotsCteScan((CteScan
*) node
);
584 case T_WorkTableScan
:
585 return ExecCountSlotsWorkTableScan((WorkTableScan
*) node
);
591 return ExecCountSlotsNestLoop((NestLoop
*) node
);
594 return ExecCountSlotsMergeJoin((MergeJoin
*) node
);
597 return ExecCountSlotsHashJoin((HashJoin
*) node
);
600 * materialization nodes
603 return ExecCountSlotsMaterial((Material
*) node
);
606 return ExecCountSlotsSort((Sort
*) node
);
609 return ExecCountSlotsGroup((Group
*) node
);
612 return ExecCountSlotsAgg((Agg
*) node
);
615 return ExecCountSlotsWindowAgg((WindowAgg
*) node
);
619 return ExecCountSlotsUnique((Unique
*) node
);
622 return ExecCountSlotsHash((Hash
*) node
);
625 return ExecCountSlotsSetOp((SetOp
*) node
);
628 return ExecCountSlotsLimit((Limit
*) node
);
631 elog(ERROR
, "unrecognized node type: %d", (int) nodeTag(node
));
638 /* ----------------------------------------------------------------
641 * Recursively cleans up all the nodes in the plan rooted
644 * After this operation, the query plan will not be able to
645 * processed any further. This should be called only after
646 * the query plan has been fully executed.
647 * ----------------------------------------------------------------
650 ExecEndNode(PlanState
*node
)
653 * do nothing when we get to the end of a leaf on tree.
658 if (node
->chgParam
!= NULL
)
660 bms_free(node
->chgParam
);
661 node
->chgParam
= NULL
;
664 switch (nodeTag(node
))
670 ExecEndResult((ResultState
*) node
);
674 ExecEndAppend((AppendState
*) node
);
677 case T_RecursiveUnionState
:
678 ExecEndRecursiveUnion((RecursiveUnionState
*) node
);
681 case T_BitmapAndState
:
682 ExecEndBitmapAnd((BitmapAndState
*) node
);
685 case T_BitmapOrState
:
686 ExecEndBitmapOr((BitmapOrState
*) node
);
693 ExecEndSeqScan((SeqScanState
*) node
);
696 case T_IndexScanState
:
697 ExecEndIndexScan((IndexScanState
*) node
);
700 case T_BitmapIndexScanState
:
701 ExecEndBitmapIndexScan((BitmapIndexScanState
*) node
);
704 case T_BitmapHeapScanState
:
705 ExecEndBitmapHeapScan((BitmapHeapScanState
*) node
);
709 ExecEndTidScan((TidScanState
*) node
);
712 case T_SubqueryScanState
:
713 ExecEndSubqueryScan((SubqueryScanState
*) node
);
716 case T_FunctionScanState
:
717 ExecEndFunctionScan((FunctionScanState
*) node
);
720 case T_ValuesScanState
:
721 ExecEndValuesScan((ValuesScanState
*) node
);
725 ExecEndCteScan((CteScanState
*) node
);
728 case T_WorkTableScanState
:
729 ExecEndWorkTableScan((WorkTableScanState
*) node
);
735 case T_NestLoopState
:
736 ExecEndNestLoop((NestLoopState
*) node
);
739 case T_MergeJoinState
:
740 ExecEndMergeJoin((MergeJoinState
*) node
);
743 case T_HashJoinState
:
744 ExecEndHashJoin((HashJoinState
*) node
);
748 * materialization nodes
750 case T_MaterialState
:
751 ExecEndMaterial((MaterialState
*) node
);
755 ExecEndSort((SortState
*) node
);
759 ExecEndGroup((GroupState
*) node
);
763 ExecEndAgg((AggState
*) node
);
766 case T_WindowAggState
:
767 ExecEndWindowAgg((WindowAggState
*) node
);
771 ExecEndUnique((UniqueState
*) node
);
775 ExecEndHash((HashState
*) node
);
779 ExecEndSetOp((SetOpState
*) node
);
783 ExecEndLimit((LimitState
*) node
);
787 elog(ERROR
, "unrecognized node type: %d", (int) nodeTag(node
));