PostgreSQL Source Code  git master
nodeBitmapIndexscan.h File Reference
#include "nodes/execnodes.h"
Include dependency graph for nodeBitmapIndexscan.h:
This graph shows which files directly or indirectly include this file:

Go to the source code of this file.

Functions

BitmapIndexScanStateExecInitBitmapIndexScan (BitmapIndexScan *node, EState *estate, int eflags)
 
NodeMultiExecBitmapIndexScan (BitmapIndexScanState *node)
 
void ExecEndBitmapIndexScan (BitmapIndexScanState *node)
 
void ExecReScanBitmapIndexScan (BitmapIndexScanState *node)
 

Function Documentation

◆ ExecEndBitmapIndexScan()

void ExecEndBitmapIndexScan ( BitmapIndexScanState node)

Definition at line 176 of file nodeBitmapIndexscan.c.

References BitmapIndexScanState::biss_RelationDesc, BitmapIndexScanState::biss_RuntimeContext, BitmapIndexScanState::biss_ScanDesc, FreeExprContext(), index_close(), index_endscan(), and NoLock.

Referenced by ExecEndNode().

177 {
178  Relation indexRelationDesc;
179  IndexScanDesc indexScanDesc;
180 
181  /*
182  * extract information from the node
183  */
184  indexRelationDesc = node->biss_RelationDesc;
185  indexScanDesc = node->biss_ScanDesc;
186 
187  /*
188  * Free the exprcontext ... now dead code, see ExecFreeExprContext
189  */
190 #ifdef NOT_USED
191  if (node->biss_RuntimeContext)
193 #endif
194 
195  /*
196  * close the index relation (no-op if we didn't open it)
197  */
198  if (indexScanDesc)
199  index_endscan(indexScanDesc);
200  if (indexRelationDesc)
201  index_close(indexRelationDesc, NoLock);
202 }
struct IndexScanDescData * biss_ScanDesc
Definition: execnodes.h:1509
Relation biss_RelationDesc
Definition: execnodes.h:1508
#define NoLock
Definition: lockdefs.h:34
void index_endscan(IndexScanDesc scan)
Definition: indexam.c:315
void FreeExprContext(ExprContext *econtext, bool isCommit)
Definition: execUtils.c:375
void index_close(Relation relation, LOCKMODE lockmode)
Definition: indexam.c:152
ExprContext * biss_RuntimeContext
Definition: execnodes.h:1507

◆ ExecInitBitmapIndexScan()

BitmapIndexScanState* ExecInitBitmapIndexScan ( BitmapIndexScan node,
EState estate,
int  eflags 
)

Definition at line 211 of file nodeBitmapIndexscan.c.

References Assert, BitmapIndexScanState::biss_NumRuntimeKeys, BitmapIndexScanState::biss_RelationDesc, BitmapIndexScanState::biss_result, BitmapIndexScanState::biss_RuntimeKeys, BitmapIndexScanState::biss_RuntimeKeysReady, EState::es_snapshot, EXEC_FLAG_BACKWARD, EXEC_FLAG_EXPLAIN_ONLY, EXEC_FLAG_MARK, exec_rt_fetch(), ExecAssignExprContext(), ExecBitmapIndexScan(), ExecIndexBuildScanKeys(), PlanState::ExecProcNode, index_beginscan_bitmap(), index_open(), index_rescan(), BitmapIndexScan::indexid, BitmapIndexScan::indexqual, makeNode, PlanState::plan, ScanState::ps, PlanState::ps_ExprContext, RangeTblEntry::rellockmode, BitmapIndexScan::scan, Scan::scanrelid, BitmapIndexScanState::ss, ScanState::ss_currentRelation, ScanState::ss_currentScanDesc, and PlanState::state.

Referenced by ExecInitNode().

212 {
213  BitmapIndexScanState *indexstate;
214  LOCKMODE lockmode;
215 
216  /* check for unsupported flags */
217  Assert(!(eflags & (EXEC_FLAG_BACKWARD | EXEC_FLAG_MARK)));
218 
219  /*
220  * create state structure
221  */
222  indexstate = makeNode(BitmapIndexScanState);
223  indexstate->ss.ps.plan = (Plan *) node;
224  indexstate->ss.ps.state = estate;
225  indexstate->ss.ps.ExecProcNode = ExecBitmapIndexScan;
226 
227  /* normally we don't make the result bitmap till runtime */
228  indexstate->biss_result = NULL;
229 
230  /*
231  * We do not open or lock the base relation here. We assume that an
232  * ancestor BitmapHeapScan node is holding AccessShareLock (or better) on
233  * the heap relation throughout the execution of the plan tree.
234  */
235 
236  indexstate->ss.ss_currentRelation = NULL;
237  indexstate->ss.ss_currentScanDesc = NULL;
238 
239  /*
240  * Miscellaneous initialization
241  *
242  * We do not need a standard exprcontext for this node, though we may
243  * decide below to create a runtime-key exprcontext
244  */
245 
246  /*
247  * initialize child expressions
248  *
249  * We don't need to initialize targetlist or qual since neither are used.
250  *
251  * Note: we don't initialize all of the indexqual expression, only the
252  * sub-parts corresponding to runtime keys (see below).
253  */
254 
255  /*
256  * If we are just doing EXPLAIN (ie, aren't going to run the plan), stop
257  * here. This allows an index-advisor plugin to EXPLAIN a plan containing
258  * references to nonexistent indexes.
259  */
260  if (eflags & EXEC_FLAG_EXPLAIN_ONLY)
261  return indexstate;
262 
263  /* Open the index relation. */
264  lockmode = exec_rt_fetch(node->scan.scanrelid, estate)->rellockmode;
265  indexstate->biss_RelationDesc = index_open(node->indexid, lockmode);
266 
267  /*
268  * Initialize index-specific scan state
269  */
270  indexstate->biss_RuntimeKeysReady = false;
271  indexstate->biss_RuntimeKeys = NULL;
272  indexstate->biss_NumRuntimeKeys = 0;
273 
274  /*
275  * build the index scan keys from the index qualification
276  */
277  ExecIndexBuildScanKeys((PlanState *) indexstate,
278  indexstate->biss_RelationDesc,
279  node->indexqual,
280  false,
281  &indexstate->biss_ScanKeys,
282  &indexstate->biss_NumScanKeys,
283  &indexstate->biss_RuntimeKeys,
284  &indexstate->biss_NumRuntimeKeys,
285  &indexstate->biss_ArrayKeys,
286  &indexstate->biss_NumArrayKeys);
287 
288  /*
289  * If we have runtime keys or array keys, we need an ExprContext to
290  * evaluate them. We could just create a "standard" plan node exprcontext,
291  * but to keep the code looking similar to nodeIndexscan.c, it seems
292  * better to stick with the approach of using a separate ExprContext.
293  */
294  if (indexstate->biss_NumRuntimeKeys != 0 ||
295  indexstate->biss_NumArrayKeys != 0)
296  {
297  ExprContext *stdecontext = indexstate->ss.ps.ps_ExprContext;
298 
299  ExecAssignExprContext(estate, &indexstate->ss.ps);
300  indexstate->biss_RuntimeContext = indexstate->ss.ps.ps_ExprContext;
301  indexstate->ss.ps.ps_ExprContext = stdecontext;
302  }
303  else
304  {
305  indexstate->biss_RuntimeContext = NULL;
306  }
307 
308  /*
309  * Initialize scan descriptor.
310  */
311  indexstate->biss_ScanDesc =
313  estate->es_snapshot,
314  indexstate->biss_NumScanKeys);
315 
316  /*
317  * If no run-time keys to calculate, go ahead and pass the scankeys to the
318  * index AM.
319  */
320  if (indexstate->biss_NumRuntimeKeys == 0 &&
321  indexstate->biss_NumArrayKeys == 0)
322  index_rescan(indexstate->biss_ScanDesc,
323  indexstate->biss_ScanKeys, indexstate->biss_NumScanKeys,
324  NULL, 0);
325 
326  /*
327  * all done.
328  */
329  return indexstate;
330 }
IndexScanDesc index_beginscan_bitmap(Relation indexRelation, Snapshot snapshot, int nkeys)
Definition: indexam.c:226
IndexRuntimeKeyInfo * biss_RuntimeKeys
Definition: execnodes.h:1502
struct IndexScanDescData * biss_ScanDesc
Definition: execnodes.h:1509
Index scanrelid
Definition: plannodes.h:341
int LOCKMODE
Definition: lockdefs.h:26
ExprContext * ps_ExprContext
Definition: execnodes.h:978
List * indexqual
Definition: plannodes.h:459
Relation biss_RelationDesc
Definition: execnodes.h:1508
void index_rescan(IndexScanDesc scan, ScanKey keys, int nkeys, ScanKey orderbys, int norderbys)
Definition: indexam.c:289
struct TableScanDescData * ss_currentScanDesc
Definition: execnodes.h:1332
Snapshot es_snapshot
Definition: execnodes.h:502
Relation ss_currentRelation
Definition: execnodes.h:1331
EState * state
Definition: execnodes.h:941
struct ScanKeyData * biss_ScanKeys
Definition: execnodes.h:1500
PlanState ps
Definition: execnodes.h:1330
#define EXEC_FLAG_BACKWARD
Definition: executor.h:58
static RangeTblEntry * exec_rt_fetch(Index rti, EState *estate)
Definition: executor.h:537
ExecProcNodeMtd ExecProcNode
Definition: execnodes.h:945
TIDBitmap * biss_result
Definition: execnodes.h:1499
Plan * plan
Definition: execnodes.h:939
#define makeNode(_type_)
Definition: nodes.h:573
#define Assert(condition)
Definition: c.h:739
#define EXEC_FLAG_MARK
Definition: executor.h:59
static TupleTableSlot * ExecBitmapIndexScan(PlanState *pstate)
void ExecAssignExprContext(EState *estate, PlanState *planstate)
Definition: execUtils.c:444
void ExecIndexBuildScanKeys(PlanState *planstate, Relation index, List *quals, bool isorderby, ScanKey *scanKeys, int *numScanKeys, IndexRuntimeKeyInfo **runtimeKeys, int *numRuntimeKeys, IndexArrayKeyInfo **arrayKeys, int *numArrayKeys)
ExprContext * biss_RuntimeContext
Definition: execnodes.h:1507
#define EXEC_FLAG_EXPLAIN_ONLY
Definition: executor.h:56
Relation index_open(Oid relationId, LOCKMODE lockmode)
Definition: indexam.c:126

◆ ExecReScanBitmapIndexScan()

void ExecReScanBitmapIndexScan ( BitmapIndexScanState node)

Definition at line 132 of file nodeBitmapIndexscan.c.

References BitmapIndexScanState::biss_ArrayKeys, BitmapIndexScanState::biss_NumArrayKeys, BitmapIndexScanState::biss_NumRuntimeKeys, BitmapIndexScanState::biss_NumScanKeys, BitmapIndexScanState::biss_RuntimeContext, BitmapIndexScanState::biss_RuntimeKeys, BitmapIndexScanState::biss_RuntimeKeysReady, BitmapIndexScanState::biss_ScanDesc, BitmapIndexScanState::biss_ScanKeys, ExecIndexEvalArrayKeys(), ExecIndexEvalRuntimeKeys(), index_rescan(), and ResetExprContext.

Referenced by ExecReScan().

133 {
134  ExprContext *econtext = node->biss_RuntimeContext;
135 
136  /*
137  * Reset the runtime-key context so we don't leak memory as each outer
138  * tuple is scanned. Note this assumes that we will recalculate *all*
139  * runtime keys on each call.
140  */
141  if (econtext)
142  ResetExprContext(econtext);
143 
144  /*
145  * If we are doing runtime key calculations (ie, any of the index key
146  * values weren't simple Consts), compute the new key values.
147  *
148  * Array keys are also treated as runtime keys; note that if we return
149  * with biss_RuntimeKeysReady still false, then there is an empty array
150  * key so no index scan is needed.
151  */
152  if (node->biss_NumRuntimeKeys != 0)
153  ExecIndexEvalRuntimeKeys(econtext,
154  node->biss_RuntimeKeys,
155  node->biss_NumRuntimeKeys);
156  if (node->biss_NumArrayKeys != 0)
157  node->biss_RuntimeKeysReady =
158  ExecIndexEvalArrayKeys(econtext,
159  node->biss_ArrayKeys,
160  node->biss_NumArrayKeys);
161  else
162  node->biss_RuntimeKeysReady = true;
163 
164  /* reset index scan */
165  if (node->biss_RuntimeKeysReady)
167  node->biss_ScanKeys, node->biss_NumScanKeys,
168  NULL, 0);
169 }
IndexRuntimeKeyInfo * biss_RuntimeKeys
Definition: execnodes.h:1502
struct IndexScanDescData * biss_ScanDesc
Definition: execnodes.h:1509
void index_rescan(IndexScanDesc scan, ScanKey keys, int nkeys, ScanKey orderbys, int norderbys)
Definition: indexam.c:289
struct ScanKeyData * biss_ScanKeys
Definition: execnodes.h:1500
bool ExecIndexEvalArrayKeys(ExprContext *econtext, IndexArrayKeyInfo *arrayKeys, int numArrayKeys)
void ExecIndexEvalRuntimeKeys(ExprContext *econtext, IndexRuntimeKeyInfo *runtimeKeys, int numRuntimeKeys)
IndexArrayKeyInfo * biss_ArrayKeys
Definition: execnodes.h:1504
ExprContext * biss_RuntimeContext
Definition: execnodes.h:1507
#define ResetExprContext(econtext)
Definition: executor.h:495

◆ MultiExecBitmapIndexScan()

Node* MultiExecBitmapIndexScan ( BitmapIndexScanState node)

Definition at line 50 of file nodeBitmapIndexscan.c.

References BitmapIndexScanState::biss_ArrayKeys, BitmapIndexScanState::biss_NumArrayKeys, BitmapIndexScanState::biss_NumRuntimeKeys, BitmapIndexScanState::biss_NumScanKeys, BitmapIndexScanState::biss_result, BitmapIndexScanState::biss_RuntimeKeysReady, BitmapIndexScanState::biss_ScanDesc, BitmapIndexScanState::biss_ScanKeys, CHECK_FOR_INTERRUPTS, EState::es_query_dsa, ExecIndexAdvanceArrayKeys(), ExecReScan(), index_getbitmap(), index_rescan(), InstrStartNode(), InstrStopNode(), PlanState::instrument, PlanState::plan, ScanState::ps, BitmapIndexScanState::ss, PlanState::state, tbm_create(), and work_mem.

Referenced by MultiExecProcNode().

51 {
52  TIDBitmap *tbm;
53  IndexScanDesc scandesc;
54  double nTuples = 0;
55  bool doscan;
56 
57  /* must provide our own instrumentation support */
58  if (node->ss.ps.instrument)
60 
61  /*
62  * extract necessary information from index scan node
63  */
64  scandesc = node->biss_ScanDesc;
65 
66  /*
67  * If we have runtime keys and they've not already been set up, do it now.
68  * Array keys are also treated as runtime keys; note that if ExecReScan
69  * returns with biss_RuntimeKeysReady still false, then there is an empty
70  * array key so we should do nothing.
71  */
72  if (!node->biss_RuntimeKeysReady &&
73  (node->biss_NumRuntimeKeys != 0 || node->biss_NumArrayKeys != 0))
74  {
75  ExecReScan((PlanState *) node);
76  doscan = node->biss_RuntimeKeysReady;
77  }
78  else
79  doscan = true;
80 
81  /*
82  * Prepare the result bitmap. Normally we just create a new one to pass
83  * back; however, our parent node is allowed to store a pre-made one into
84  * node->biss_result, in which case we just OR our tuple IDs into the
85  * existing bitmap. (This saves needing explicit UNION steps.)
86  */
87  if (node->biss_result)
88  {
89  tbm = node->biss_result;
90  node->biss_result = NULL; /* reset for next time */
91  }
92  else
93  {
94  /* XXX should we use less than work_mem for this? */
95  tbm = tbm_create(work_mem * 1024L,
96  ((BitmapIndexScan *) node->ss.ps.plan)->isshared ?
97  node->ss.ps.state->es_query_dsa : NULL);
98  }
99 
100  /*
101  * Get TIDs from index and insert into bitmap
102  */
103  while (doscan)
104  {
105  nTuples += (double) index_getbitmap(scandesc, tbm);
106 
108 
110  node->biss_NumArrayKeys);
111  if (doscan) /* reset index scan */
113  node->biss_ScanKeys, node->biss_NumScanKeys,
114  NULL, 0);
115  }
116 
117  /* must provide our own instrumentation support */
118  if (node->ss.ps.instrument)
119  InstrStopNode(node->ss.ps.instrument, nTuples);
120 
121  return (Node *) tbm;
122 }
void InstrStopNode(Instrumentation *instr, double nTuples)
Definition: instrument.c:76
struct IndexScanDescData * biss_ScanDesc
Definition: execnodes.h:1509
struct dsa_area * es_query_dsa
Definition: execnodes.h:583
Instrumentation * instrument
Definition: execnodes.h:949
TIDBitmap * tbm_create(long maxbytes, dsa_area *dsa)
Definition: tidbitmap.c:265
bool ExecIndexAdvanceArrayKeys(IndexArrayKeyInfo *arrayKeys, int numArrayKeys)
void ExecReScan(PlanState *node)
Definition: execAmi.c:75
void index_rescan(IndexScanDesc scan, ScanKey keys, int nkeys, ScanKey orderbys, int norderbys)
Definition: indexam.c:289
Definition: nodes.h:525
EState * state
Definition: execnodes.h:941
struct ScanKeyData * biss_ScanKeys
Definition: execnodes.h:1500
PlanState ps
Definition: execnodes.h:1330
void InstrStartNode(Instrumentation *instr)
Definition: instrument.c:63
int64 index_getbitmap(IndexScanDesc scan, TIDBitmap *bitmap)
Definition: indexam.c:652
int work_mem
Definition: globals.c:121
TIDBitmap * biss_result
Definition: execnodes.h:1499
Plan * plan
Definition: execnodes.h:939
IndexArrayKeyInfo * biss_ArrayKeys
Definition: execnodes.h:1504
#define CHECK_FOR_INTERRUPTS()
Definition: miscadmin.h:99