PostgreSQL Source Code  git master
 All Data Structures Namespaces Files Functions Variables Typedefs Enumerations Enumerator Macros
nodeValuesscan.c File Reference
Include dependency graph for nodeValuesscan.c:

Go to the source code of this file.

Functions

static TupleTableSlotValuesNext (ValuesScanState *node)
 
static bool ValuesRecheck (ValuesScanState *node, TupleTableSlot *slot)
 
static TupleTableSlotExecValuesScan (PlanState *pstate)
 
ValuesScanStateExecInitValuesScan (ValuesScan *node, EState *estate, int eflags)
 
void ExecEndValuesScan (ValuesScanState *node)
 
void ExecReScanValuesScan (ValuesScanState *node)
 

Function Documentation

void ExecEndValuesScan ( ValuesScanState node)

Definition at line 289 of file nodeValuesscan.c.

References ExecClearTuple(), ExecFreeExprContext(), ScanState::ps, PlanState::ps_ExprContext, PlanState::ps_ResultTupleSlot, ValuesScanState::rowcontext, ValuesScanState::ss, and ScanState::ss_ScanTupleSlot.

Referenced by ExecEndNode().

290 {
291  /*
292  * Free both exprcontexts
293  */
294  ExecFreeExprContext(&node->ss.ps);
295  node->ss.ps.ps_ExprContext = node->rowcontext;
296  ExecFreeExprContext(&node->ss.ps);
297 
298  /*
299  * clean out the tuple table
300  */
303 }
ExprContext * ps_ExprContext
Definition: execnodes.h:881
TupleTableSlot * ExecClearTuple(TupleTableSlot *slot)
Definition: execTuples.c:439
TupleTableSlot * ss_ScanTupleSlot
Definition: execnodes.h:1103
void ExecFreeExprContext(PlanState *planstate)
Definition: execUtils.c:521
ScanState ss
Definition: execnodes.h:1448
PlanState ps
Definition: execnodes.h:1100
TupleTableSlot * ps_ResultTupleSlot
Definition: execnodes.h:880
ExprContext * rowcontext
Definition: execnodes.h:1449
ValuesScanState* ExecInitValuesScan ( ValuesScan node,
EState estate,
int  eflags 
)

Definition at line 203 of file nodeValuesscan.c.

References ValuesScanState::array_len, Assert, ValuesScanState::curr_idx, ExecAssignExprContext(), ExecAssignResultTypeFromTL(), ExecAssignScanProjectionInfo(), ExecAssignScanType(), ExecInitQual(), ExecInitResultTupleSlot(), ExecInitScanTupleSlot(), PlanState::ExecProcNode, ExecTypeFromExprList(), ExecValuesScan(), ValuesScanState::exprlists, i, innerPlan, lfirst, linitial, list_length(), makeNode, outerPlan, palloc(), Scan::plan, PlanState::plan, ScanState::ps, PlanState::ps_ExprContext, Plan::qual, PlanState::qual, ValuesScanState::rowcontext, ValuesScan::scan, ValuesScanState::ss, PlanState::state, and ValuesScan::values_lists.

Referenced by ExecInitNode().

204 {
205  ValuesScanState *scanstate;
206  TupleDesc tupdesc;
207  ListCell *vtl;
208  int i;
209  PlanState *planstate;
210 
211  /*
212  * ValuesScan should not have any children.
213  */
214  Assert(outerPlan(node) == NULL);
215  Assert(innerPlan(node) == NULL);
216 
217  /*
218  * create new ScanState for node
219  */
220  scanstate = makeNode(ValuesScanState);
221  scanstate->ss.ps.plan = (Plan *) node;
222  scanstate->ss.ps.state = estate;
223  scanstate->ss.ps.ExecProcNode = ExecValuesScan;
224 
225  /*
226  * Miscellaneous initialization
227  */
228  planstate = &scanstate->ss.ps;
229 
230  /*
231  * Create expression contexts. We need two, one for per-sublist
232  * processing and one for execScan.c to use for quals and projections. We
233  * cheat a little by using ExecAssignExprContext() to build both.
234  */
235  ExecAssignExprContext(estate, planstate);
236  scanstate->rowcontext = planstate->ps_ExprContext;
237  ExecAssignExprContext(estate, planstate);
238 
239  /*
240  * tuple table initialization
241  */
242  ExecInitResultTupleSlot(estate, &scanstate->ss.ps);
243  ExecInitScanTupleSlot(estate, &scanstate->ss);
244 
245  /*
246  * initialize child expressions
247  */
248  scanstate->ss.ps.qual =
249  ExecInitQual(node->scan.plan.qual, (PlanState *) scanstate);
250 
251  /*
252  * get info about values list
253  */
254  tupdesc = ExecTypeFromExprList((List *) linitial(node->values_lists));
255 
256  ExecAssignScanType(&scanstate->ss, tupdesc);
257 
258  /*
259  * Other node-specific setup
260  */
261  scanstate->curr_idx = -1;
262  scanstate->array_len = list_length(node->values_lists);
263 
264  /* convert list of sublists into array of sublists for easy addressing */
265  scanstate->exprlists = (List **)
266  palloc(scanstate->array_len * sizeof(List *));
267  i = 0;
268  foreach(vtl, node->values_lists)
269  {
270  scanstate->exprlists[i++] = (List *) lfirst(vtl);
271  }
272 
273  /*
274  * Initialize result tuple type and projection info.
275  */
276  ExecAssignResultTypeFromTL(&scanstate->ss.ps);
277  ExecAssignScanProjectionInfo(&scanstate->ss);
278 
279  return scanstate;
280 }
List * qual
Definition: plannodes.h:145
Plan plan
Definition: plannodes.h:328
static TupleTableSlot * ExecValuesScan(PlanState *pstate)
void ExecInitScanTupleSlot(EState *estate, ScanState *scanstate)
Definition: execTuples.c:842
ExprContext * ps_ExprContext
Definition: execnodes.h:881
List * values_lists
Definition: plannodes.h:519
EState * state
Definition: execnodes.h:849
Scan scan
Definition: plannodes.h:518
ExprState * ExecInitQual(List *qual, PlanState *parent)
Definition: execExpr.c:160
void ExecAssignResultTypeFromTL(PlanState *planstate)
Definition: execUtils.c:445
ScanState ss
Definition: execnodes.h:1448
PlanState ps
Definition: execnodes.h:1100
#define linitial(l)
Definition: pg_list.h:111
void ExecAssignScanProjectionInfo(ScanState *node)
Definition: execScan.c:237
void ExecInitResultTupleSlot(EState *estate, PlanState *planstate)
Definition: execTuples.c:832
#define innerPlan(node)
Definition: plannodes.h:173
#define outerPlan(node)
Definition: plannodes.h:174
ExecProcNodeMtd ExecProcNode
Definition: execnodes.h:853
ExprContext * rowcontext
Definition: execnodes.h:1449
Plan * plan
Definition: execnodes.h:847
#define makeNode(_type_)
Definition: nodes.h:557
#define Assert(condition)
Definition: c.h:664
#define lfirst(lc)
Definition: pg_list.h:106
void ExecAssignExprContext(EState *estate, PlanState *planstate)
Definition: execUtils.c:423
static int list_length(const List *l)
Definition: pg_list.h:89
ExprState * qual
Definition: execnodes.h:865
TupleDesc ExecTypeFromExprList(List *exprList)
Definition: execTuples.c:947
void * palloc(Size size)
Definition: mcxt.c:848
int i
void ExecAssignScanType(ScanState *scanstate, TupleDesc tupDesc)
Definition: execUtils.c:545
List ** exprlists
Definition: execnodes.h:1450
Definition: pg_list.h:45
void ExecReScanValuesScan ( ValuesScanState node)

Definition at line 312 of file nodeValuesscan.c.

References ValuesScanState::curr_idx, ExecClearTuple(), ExecScanReScan(), ScanState::ps, PlanState::ps_ResultTupleSlot, and ValuesScanState::ss.

Referenced by ExecReScan().

313 {
315 
316  ExecScanReScan(&node->ss);
317 
318  node->curr_idx = -1;
319 }
TupleTableSlot * ExecClearTuple(TupleTableSlot *slot)
Definition: execTuples.c:439
ScanState ss
Definition: execnodes.h:1448
PlanState ps
Definition: execnodes.h:1100
TupleTableSlot * ps_ResultTupleSlot
Definition: execnodes.h:880
void ExecScanReScan(ScanState *node)
Definition: execScan.c:329
static TupleTableSlot* ExecValuesScan ( PlanState pstate)
static

Definition at line 189 of file nodeValuesscan.c.

References castNode, ExecScan(), ValuesScanState::ss, ValuesNext(), and ValuesRecheck().

Referenced by ExecInitValuesScan().

190 {
191  ValuesScanState *node = castNode(ValuesScanState, pstate);
192 
193  return ExecScan(&node->ss,
196 }
#define castNode(_type_, nodeptr)
Definition: nodes.h:578
TupleTableSlot * ExecScan(ScanState *node, ExecScanAccessMtd accessMtd, ExecScanRecheckMtd recheckMtd)
Definition: execScan.c:123
ScanState ss
Definition: execnodes.h:1448
TupleTableSlot *(* ExecScanAccessMtd)(ScanState *node)
Definition: executor.h:409
bool(* ExecScanRecheckMtd)(ScanState *node, TupleTableSlot *slot)
Definition: executor.h:410
static TupleTableSlot * ValuesNext(ValuesScanState *node)
static bool ValuesRecheck(ValuesScanState *node, TupleTableSlot *slot)
static TupleTableSlot * ValuesNext ( ValuesScanState node)
static

Definition at line 46 of file nodeValuesscan.c.

References ValuesScanState::array_len, Assert, ValuesScanState::curr_idx, ExprContext::ecxt_per_tuple_memory, EState::es_direction, ExecClearTuple(), ExecEvalExpr(), ExecInitExprList(), ExecStoreVirtualTuple(), ValuesScanState::exprlists, lfirst, list_length(), MakeExpandedObjectReadOnly, MemoryContextSwitchTo(), tupleDesc::natts, NIL, ScanState::ps, ReScanExprContext(), ValuesScanState::rowcontext, ScanDirectionIsForward, ValuesScanState::ss, ScanState::ss_ScanTupleSlot, PlanState::state, TupleTableSlot::tts_isnull, TupleTableSlot::tts_tupleDescriptor, TupleTableSlot::tts_values, TupleDescAttr, and values.

Referenced by ExecValuesScan().

47 {
48  TupleTableSlot *slot;
49  EState *estate;
50  ExprContext *econtext;
51  ScanDirection direction;
52  List *exprlist;
53 
54  /*
55  * get information from the estate and scan state
56  */
57  estate = node->ss.ps.state;
58  direction = estate->es_direction;
59  slot = node->ss.ss_ScanTupleSlot;
60  econtext = node->rowcontext;
61 
62  /*
63  * Get the next tuple. Return NULL if no more tuples.
64  */
65  if (ScanDirectionIsForward(direction))
66  {
67  if (node->curr_idx < node->array_len)
68  node->curr_idx++;
69  if (node->curr_idx < node->array_len)
70  exprlist = node->exprlists[node->curr_idx];
71  else
72  exprlist = NIL;
73  }
74  else
75  {
76  if (node->curr_idx >= 0)
77  node->curr_idx--;
78  if (node->curr_idx >= 0)
79  exprlist = node->exprlists[node->curr_idx];
80  else
81  exprlist = NIL;
82  }
83 
84  /*
85  * Always clear the result slot; this is appropriate if we are at the end
86  * of the data, and if we're not, we still need it as the first step of
87  * the store-virtual-tuple protocol. It seems wise to clear the slot
88  * before we reset the context it might have pointers into.
89  */
90  ExecClearTuple(slot);
91 
92  if (exprlist)
93  {
94  MemoryContext oldContext;
95  List *exprstatelist;
96  Datum *values;
97  bool *isnull;
98  ListCell *lc;
99  int resind;
100 
101  /*
102  * Get rid of any prior cycle's leftovers. We use ReScanExprContext
103  * not just ResetExprContext because we want any registered shutdown
104  * callbacks to be called.
105  */
106  ReScanExprContext(econtext);
107 
108  /*
109  * Build the expression eval state in the econtext's per-tuple memory.
110  * This is a tad unusual, but we want to delete the eval state again
111  * when we move to the next row, to avoid growth of memory
112  * requirements over a long values list.
113  */
114  oldContext = MemoryContextSwitchTo(econtext->ecxt_per_tuple_memory);
115 
116  /*
117  * Pass NULL, not my plan node, because we don't want anything in this
118  * transient state linking into permanent state. The only possibility
119  * is a SubPlan, and there shouldn't be any (any subselects in the
120  * VALUES list should be InitPlans).
121  */
122  exprstatelist = ExecInitExprList(exprlist, NULL);
123 
124  /* parser should have checked all sublists are the same length */
125  Assert(list_length(exprstatelist) == slot->tts_tupleDescriptor->natts);
126 
127  /*
128  * Compute the expressions and build a virtual result tuple. We
129  * already did ExecClearTuple(slot).
130  */
131  values = slot->tts_values;
132  isnull = slot->tts_isnull;
133 
134  resind = 0;
135  foreach(lc, exprstatelist)
136  {
137  ExprState *estate = (ExprState *) lfirst(lc);
139  resind);
140 
141  values[resind] = ExecEvalExpr(estate,
142  econtext,
143  &isnull[resind]);
144 
145  /*
146  * We must force any R/W expanded datums to read-only state, in
147  * case they are multiply referenced in the plan node's output
148  * expressions, or in case we skip the output projection and the
149  * output column is multiply referenced in higher plan nodes.
150  */
151  values[resind] = MakeExpandedObjectReadOnly(values[resind],
152  isnull[resind],
153  attr->attlen);
154 
155  resind++;
156  }
157 
158  MemoryContextSwitchTo(oldContext);
159 
160  /*
161  * And return the virtual tuple.
162  */
163  ExecStoreVirtualTuple(slot);
164  }
165 
166  return slot;
167 }
#define NIL
Definition: pg_list.h:69
#define ScanDirectionIsForward(direction)
Definition: sdir.h:55
#define TupleDescAttr(tupdesc, i)
Definition: tupdesc.h:84
MemoryContext ecxt_per_tuple_memory
Definition: execnodes.h:203
TupleTableSlot * ExecClearTuple(TupleTableSlot *slot)
Definition: execTuples.c:439
static MemoryContext MemoryContextSwitchTo(MemoryContext context)
Definition: palloc.h:109
Datum * tts_values
Definition: tuptable.h:125
TupleTableSlot * ss_ScanTupleSlot
Definition: execnodes.h:1103
EState * state
Definition: execnodes.h:849
int natts
Definition: tupdesc.h:73
ScanDirection es_direction
Definition: execnodes.h:428
ScanState ss
Definition: execnodes.h:1448
PlanState ps
Definition: execnodes.h:1100
bool * tts_isnull
Definition: tuptable.h:126
static Datum ExecEvalExpr(ExprState *state, ExprContext *econtext, bool *isNull)
Definition: executor.h:286
ScanDirection
Definition: sdir.h:22
List * ExecInitExprList(List *nodes, PlanState *parent)
Definition: execExpr.c:266
#define MakeExpandedObjectReadOnly(d, isnull, typlen)
FormData_pg_attribute * Form_pg_attribute
Definition: pg_attribute.h:187
TupleDesc tts_tupleDescriptor
Definition: tuptable.h:121
uintptr_t Datum
Definition: postgres.h:372
ExprContext * rowcontext
Definition: execnodes.h:1449
#define Assert(condition)
Definition: c.h:664
#define lfirst(lc)
Definition: pg_list.h:106
static int list_length(const List *l)
Definition: pg_list.h:89
void ReScanExprContext(ExprContext *econtext)
Definition: execUtils.c:381
static Datum values[MAXATTR]
Definition: bootstrap.c:164
List ** exprlists
Definition: execnodes.h:1450
Definition: pg_list.h:45
TupleTableSlot * ExecStoreVirtualTuple(TupleTableSlot *slot)
Definition: execTuples.c:488
static bool ValuesRecheck ( ValuesScanState node,
TupleTableSlot slot 
)
static

Definition at line 173 of file nodeValuesscan.c.

Referenced by ExecValuesScan().

174 {
175  /* nothing to check */
176  return true;
177 }