PostgreSQL Source Code  git master
nodeGroup.c File Reference
#include "postgres.h"
#include "executor/executor.h"
#include "executor/nodeGroup.h"
#include "miscadmin.h"
#include "utils/memutils.h"
Include dependency graph for nodeGroup.c:

Go to the source code of this file.

Functions

static TupleTableSlotExecGroup (PlanState *pstate)
 
GroupStateExecInitGroup (Group *node, EState *estate, int eflags)
 
void ExecEndGroup (GroupState *node)
 
void ExecReScanGroup (GroupState *node)
 

Function Documentation

◆ ExecEndGroup()

void ExecEndGroup ( GroupState node)

Definition at line 224 of file nodeGroup.c.

References ExecClearTuple(), ExecEndNode(), ExecFreeExprContext(), outerPlan, outerPlanState, ScanState::ps, GroupState::ss, and ScanState::ss_ScanTupleSlot.

Referenced by ExecEndNode().

225 {
227 
228  ExecFreeExprContext(&node->ss.ps);
229 
230  /* clean up tuple table */
232 
233  outerPlan = outerPlanState(node);
234  ExecEndNode(outerPlan);
235 }
void ExecEndNode(PlanState *node)
Definition: execProcnode.c:538
TupleTableSlot * ExecClearTuple(TupleTableSlot *slot)
Definition: execTuples.c:475
TupleTableSlot * ss_ScanTupleSlot
Definition: execnodes.h:1195
void ExecFreeExprContext(PlanState *planstate)
Definition: execUtils.c:566
ScanState ss
Definition: execnodes.h:1867
PlanState ps
Definition: execnodes.h:1192
#define outerPlanState(node)
Definition: execnodes.h:966
#define outerPlan(node)
Definition: plannodes.h:176

◆ ExecGroup()

static TupleTableSlot* ExecGroup ( PlanState pstate)
static

Definition at line 37 of file nodeGroup.c.

References castNode, CHECK_FOR_INTERRUPTS, ExprContext::ecxt_innertuple, ExprContext::ecxt_outertuple, GroupState::eqfunction, ExecCopySlot(), ExecProcNode(), ExecProject(), ExecQual(), ExecQualAndReset(), GroupState::grp_done, InstrCountFiltered1, outerPlanState, ScanState::ps, PlanState::ps_ExprContext, PlanState::ps_ProjInfo, PlanState::qual, GroupState::ss, ScanState::ss_ScanTupleSlot, and TupIsNull.

Referenced by ExecInitGroup().

38 {
39  GroupState *node = castNode(GroupState, pstate);
40  ExprContext *econtext;
41  TupleTableSlot *firsttupleslot;
42  TupleTableSlot *outerslot;
43 
45 
46  /*
47  * get state info from node
48  */
49  if (node->grp_done)
50  return NULL;
51  econtext = node->ss.ps.ps_ExprContext;
52 
53  /*
54  * The ScanTupleSlot holds the (copied) first tuple of each group.
55  */
56  firsttupleslot = node->ss.ss_ScanTupleSlot;
57 
58  /*
59  * We need not call ResetExprContext here because ExecQualAndReset() will
60  * reset the per-tuple memory context once per input tuple.
61  */
62 
63  /*
64  * If first time through, acquire first input tuple and determine whether
65  * to return it or not.
66  */
67  if (TupIsNull(firsttupleslot))
68  {
69  outerslot = ExecProcNode(outerPlanState(node));
70  if (TupIsNull(outerslot))
71  {
72  /* empty input, so return nothing */
73  node->grp_done = true;
74  return NULL;
75  }
76  /* Copy tuple into firsttupleslot */
77  ExecCopySlot(firsttupleslot, outerslot);
78 
79  /*
80  * Set it up as input for qual test and projection. The expressions
81  * will access the input tuple as varno OUTER.
82  */
83  econtext->ecxt_outertuple = firsttupleslot;
84 
85  /*
86  * Check the qual (HAVING clause); if the group does not match, ignore
87  * it and fall into scan loop.
88  */
89  if (ExecQual(node->ss.ps.qual, econtext))
90  {
91  /*
92  * Form and return a projection tuple using the first input tuple.
93  */
94  return ExecProject(node->ss.ps.ps_ProjInfo);
95  }
96  else
97  InstrCountFiltered1(node, 1);
98  }
99 
100  /*
101  * This loop iterates once per input tuple group. At the head of the
102  * loop, we have finished processing the first tuple of the group and now
103  * need to scan over all the other group members.
104  */
105  for (;;)
106  {
107  /*
108  * Scan over all remaining tuples that belong to this group
109  */
110  for (;;)
111  {
112  outerslot = ExecProcNode(outerPlanState(node));
113  if (TupIsNull(outerslot))
114  {
115  /* no more groups, so we're done */
116  node->grp_done = true;
117  return NULL;
118  }
119 
120  /*
121  * Compare with first tuple and see if this tuple is of the same
122  * group. If so, ignore it and keep scanning.
123  */
124  econtext->ecxt_innertuple = firsttupleslot;
125  econtext->ecxt_outertuple = outerslot;
126  if (!ExecQualAndReset(node->eqfunction, econtext))
127  break;
128  }
129 
130  /*
131  * We have the first tuple of the next input group. See if we want to
132  * return it.
133  */
134  /* Copy tuple, set up as input for qual test and projection */
135  ExecCopySlot(firsttupleslot, outerslot);
136  econtext->ecxt_outertuple = firsttupleslot;
137 
138  /*
139  * Check the qual (HAVING clause); if the group does not match, ignore
140  * it and loop back to scan the rest of the group.
141  */
142  if (ExecQual(node->ss.ps.qual, econtext))
143  {
144  /*
145  * Form and return a projection tuple using the first input tuple.
146  */
147  return ExecProject(node->ss.ps.ps_ProjInfo);
148  }
149  else
150  InstrCountFiltered1(node, 1);
151  }
152 }
ProjectionInfo * ps_ProjInfo
Definition: execnodes.h:948
#define castNode(_type_, nodeptr)
Definition: nodes.h:586
ExprContext * ps_ExprContext
Definition: execnodes.h:947
TupleTableSlot * ss_ScanTupleSlot
Definition: execnodes.h:1195
static bool ExecQual(ExprState *state, ExprContext *econtext)
Definition: executor.h:361
bool grp_done
Definition: execnodes.h:1869
ScanState ss
Definition: execnodes.h:1867
PlanState ps
Definition: execnodes.h:1192
ExprState * eqfunction
Definition: execnodes.h:1868
#define outerPlanState(node)
Definition: execnodes.h:966
TupleTableSlot * ecxt_innertuple
Definition: execnodes.h:220
#define TupIsNull(slot)
Definition: tuptable.h:146
#define InstrCountFiltered1(node, delta)
Definition: execnodes.h:974
static bool ExecQualAndReset(ExprState *state, ExprContext *econtext)
Definition: executor.h:388
static TupleTableSlot * ExecProcNode(PlanState *node)
Definition: executor.h:233
TupleTableSlot * ExecCopySlot(TupleTableSlot *dstslot, TupleTableSlot *srcslot)
Definition: execTuples.c:851
TupleTableSlot * ecxt_outertuple
Definition: execnodes.h:222
ExprState * qual
Definition: execnodes.h:930
#define CHECK_FOR_INTERRUPTS()
Definition: miscadmin.h:98
static TupleTableSlot * ExecProject(ProjectionInfo *projInfo)
Definition: executor.h:324

◆ ExecInitGroup()

GroupState* ExecInitGroup ( Group node,
EState estate,
int  eflags 
)

Definition at line 162 of file nodeGroup.c.

References Assert, EXEC_FLAG_BACKWARD, EXEC_FLAG_MARK, ExecAssignExprContext(), ExecAssignProjectionInfo(), ExecCreateScanSlotFromOuterPlan(), ExecGetResultType(), ExecGroup(), ExecInitNode(), ExecInitQual(), ExecInitResultTupleSlotTL(), PlanState::ExecProcNode, execTuplesMatchPrepare(), GroupState::grp_done, Group::grpColIdx, Group::grpOperators, makeNode, Group::numCols, outerPlan, outerPlanState, Group::plan, PlanState::plan, ScanState::ps, Plan::qual, PlanState::qual, GroupState::ss, and PlanState::state.

Referenced by ExecInitNode().

163 {
164  GroupState *grpstate;
165 
166  /* check for unsupported flags */
167  Assert(!(eflags & (EXEC_FLAG_BACKWARD | EXEC_FLAG_MARK)));
168 
169  /*
170  * create state structure
171  */
172  grpstate = makeNode(GroupState);
173  grpstate->ss.ps.plan = (Plan *) node;
174  grpstate->ss.ps.state = estate;
175  grpstate->ss.ps.ExecProcNode = ExecGroup;
176  grpstate->grp_done = false;
177 
178  /*
179  * create expression context
180  */
181  ExecAssignExprContext(estate, &grpstate->ss.ps);
182 
183  /*
184  * initialize child nodes
185  */
186  outerPlanState(grpstate) = ExecInitNode(outerPlan(node), estate, eflags);
187 
188  /*
189  * Initialize scan slot and type.
190  */
191  ExecCreateScanSlotFromOuterPlan(estate, &grpstate->ss);
192 
193  /*
194  * Initialize result slot, type and projection.
195  */
196  ExecInitResultTupleSlotTL(estate, &grpstate->ss.ps);
197  ExecAssignProjectionInfo(&grpstate->ss.ps, NULL);
198 
199  /*
200  * initialize child expressions
201  */
202  grpstate->ss.ps.qual =
203  ExecInitQual(node->plan.qual, (PlanState *) grpstate);
204 
205  /*
206  * Precompute fmgr lookup data for inner loop
207  */
208  grpstate->eqfunction =
210  node->numCols,
211  node->grpColIdx,
212  node->grpOperators,
213  &grpstate->ss.ps);
214 
215  return grpstate;
216 }
List * qual
Definition: plannodes.h:147
EState * state
Definition: execnodes.h:914
bool grp_done
Definition: execnodes.h:1869
ExprState * ExecInitQual(List *qual, PlanState *parent)
Definition: execExpr.c:205
ScanState ss
Definition: execnodes.h:1867
PlanState ps
Definition: execnodes.h:1192
ExprState * eqfunction
Definition: execnodes.h:1868
void ExecCreateScanSlotFromOuterPlan(EState *estate, ScanState *scanstate)
Definition: execUtils.c:598
#define EXEC_FLAG_BACKWARD
Definition: executor.h:60
#define outerPlanState(node)
Definition: execnodes.h:966
void ExecAssignProjectionInfo(PlanState *planstate, TupleDesc inputDesc)
Definition: execUtils.c:456
int numCols
Definition: plannodes.h:775
#define outerPlan(node)
Definition: plannodes.h:176
ExecProcNodeMtd ExecProcNode
Definition: execnodes.h:918
void ExecInitResultTupleSlotTL(EState *estate, PlanState *planstate)
Definition: execTuples.c:890
Plan * plan
Definition: execnodes.h:912
ExprState * execTuplesMatchPrepare(TupleDesc desc, int numCols, AttrNumber *keyColIdx, Oid *eqOperators, PlanState *parent)
Definition: execGrouping.c:60
#define makeNode(_type_)
Definition: nodes.h:565
#define Assert(condition)
Definition: c.h:699
#define EXEC_FLAG_MARK
Definition: executor.h:61
Plan plan
Definition: plannodes.h:774
void ExecAssignExprContext(EState *estate, PlanState *planstate)
Definition: execUtils.c:428
TupleDesc ExecGetResultType(PlanState *planstate)
Definition: execUtils.c:438
ExprState * qual
Definition: execnodes.h:930
static TupleTableSlot * ExecGroup(PlanState *pstate)
Definition: nodeGroup.c:37
AttrNumber * grpColIdx
Definition: plannodes.h:776
PlanState * ExecInitNode(Plan *node, EState *estate, int eflags)
Definition: execProcnode.c:139
Oid * grpOperators
Definition: plannodes.h:777

◆ ExecReScanGroup()

void ExecReScanGroup ( GroupState node)

Definition at line 238 of file nodeGroup.c.

References PlanState::chgParam, ExecClearTuple(), ExecReScan(), GroupState::grp_done, outerPlan, outerPlanState, GroupState::ss, and ScanState::ss_ScanTupleSlot.

Referenced by ExecReScan().

239 {
241 
242  node->grp_done = false;
243  /* must clear first tuple */
245 
246  /*
247  * if chgParam of subnode is not null then plan will be re-scanned by
248  * first ExecProcNode.
249  */
250  if (outerPlan->chgParam == NULL)
251  ExecReScan(outerPlan);
252 }
void ExecReScan(PlanState *node)
Definition: execAmi.c:76
TupleTableSlot * ExecClearTuple(TupleTableSlot *slot)
Definition: execTuples.c:475
TupleTableSlot * ss_ScanTupleSlot
Definition: execnodes.h:1195
bool grp_done
Definition: execnodes.h:1869
ScanState ss
Definition: execnodes.h:1867
#define outerPlanState(node)
Definition: execnodes.h:966
Bitmapset * chgParam
Definition: execnodes.h:941
#define outerPlan(node)
Definition: plannodes.h:176