1996-07-09 02:22:35 -04:00
|
|
|
/*-------------------------------------------------------------------------
|
|
|
|
|
*
|
1999-02-13 18:22:53 -05:00
|
|
|
* nodeIndexscan.h
|
1996-07-09 02:22:35 -04:00
|
|
|
*
|
|
|
|
|
*
|
|
|
|
|
*
|
2025-01-01 11:21:55 -05:00
|
|
|
* Portions Copyright (c) 1996-2025, PostgreSQL Global Development Group
|
2000-01-26 00:58:53 -05:00
|
|
|
* Portions Copyright (c) 1994, Regents of the University of California
|
1996-07-09 02:22:35 -04:00
|
|
|
*
|
2010-09-20 16:08:53 -04:00
|
|
|
* src/include/executor/nodeIndexscan.h
|
1996-07-09 02:22:35 -04:00
|
|
|
*
|
|
|
|
|
*-------------------------------------------------------------------------
|
|
|
|
|
*/
|
|
|
|
|
#ifndef NODEINDEXSCAN_H
|
|
|
|
|
#define NODEINDEXSCAN_H
|
1997-09-07 01:04:48 -04:00
|
|
|
|
2019-12-26 18:09:00 -05:00
|
|
|
#include "access/genam.h"
|
2017-02-15 13:53:24 -05:00
|
|
|
#include "access/parallel.h"
|
2002-12-05 10:50:39 -05:00
|
|
|
#include "nodes/execnodes.h"
|
1996-07-09 02:22:35 -04:00
|
|
|
|
2006-02-27 23:10:28 -05:00
|
|
|
extern IndexScanState *ExecInitIndexScan(IndexScan *node, EState *estate, int eflags);
|
2002-12-05 10:50:39 -05:00
|
|
|
extern void ExecEndIndexScan(IndexScanState *node);
|
|
|
|
|
extern void ExecIndexMarkPos(IndexScanState *node);
|
|
|
|
|
extern void ExecIndexRestrPos(IndexScanState *node);
|
2010-07-12 13:01:06 -04:00
|
|
|
extern void ExecReScanIndexScan(IndexScanState *node);
|
2017-02-15 13:53:24 -05:00
|
|
|
extern void ExecIndexScanEstimate(IndexScanState *node, ParallelContext *pcxt);
|
|
|
|
|
extern void ExecIndexScanInitializeDSM(IndexScanState *node, ParallelContext *pcxt);
|
Separate reinitialization of shared parallel-scan state from ExecReScan.
Previously, the parallel executor logic did reinitialization of shared
state within the ExecReScan code for parallel-aware scan nodes. This is
problematic, because it means that the ExecReScan call has to occur
synchronously (ie, during the parent Gather node's ReScan call). That is
swimming very much against the tide so far as the ExecReScan machinery is
concerned; the fact that it works at all today depends on a lot of fragile
assumptions, such as that no plan node between Gather and a parallel-aware
scan node is parameterized. Another objection is that because ExecReScan
might be called in workers as well as the leader, hacky extra tests are
needed in some places to prevent unwanted shared-state resets.
Hence, let's separate this code into two functions, a ReInitializeDSM
call and the ReScan call proper. ReInitializeDSM is called only in
the leader and is guaranteed to run before we start new workers.
ReScan is returned to its traditional function of resetting only local
state, which means that ExecReScan's usual habits of delaying or
eliminating child rescan calls are safe again.
As with the preceding commit 7df2c1f8d, it doesn't seem to be necessary
to make these changes in 9.6, which is a good thing because the FDW and
CustomScan APIs are impacted.
Discussion: https://postgr.es/m/CAA4eK1JkByysFJNh9M349u_nNjqETuEnY_y1VUc_kJiU0bxtaQ@mail.gmail.com
2017-08-30 13:18:16 -04:00
|
|
|
extern void ExecIndexScanReInitializeDSM(IndexScanState *node, ParallelContext *pcxt);
|
2017-11-16 20:28:11 -05:00
|
|
|
extern void ExecIndexScanInitializeWorker(IndexScanState *node,
|
|
|
|
|
ParallelWorkerContext *pwcxt);
|
Show index search count in EXPLAIN ANALYZE, take 2.
Expose the count of index searches/index descents in EXPLAIN ANALYZE's
output for index scan/index-only scan/bitmap index scan nodes. This
information is particularly useful with scans that use ScalarArrayOp
quals, where the number of index searches can be unpredictable due to
implementation details that interact with physical index characteristics
(at least with nbtree SAOP scans, since Postgres 17 commit 5bf748b8).
The information shown also provides useful context when EXPLAIN ANALYZE
runs a plan with an index scan node that successfully applied the skip
scan optimization (set to be added to nbtree by an upcoming patch).
The instrumentation works by teaching all index AMs to increment a new
nsearches counter whenever a new index search begins. The counter is
incremented at exactly the same point that index AMs already increment
the pg_stat_*_indexes.idx_scan counter (we're counting the same event,
but at the scan level rather than the relation level). Parallel queries
have workers copy their local counter struct into shared memory when an
index scan node ends -- even when it isn't a parallel aware scan node.
An earlier version of this patch that only worked with parallel aware
scans became commit 5ead85fb (though that was quickly reverted by commit
d00107cd following "debug_parallel_query=regress" buildfarm failures).
Our approach doesn't match the approach used when tracking other index
scan related costs (e.g., "Rows Removed by Filter:"). It is comparable
to the approach used in similar cases involving costs that are only
readily accessible inside an access method, not from the executor proper
(e.g., "Heap Blocks:" output for a Bitmap Heap Scan, which was recently
enhanced to show per-worker costs by commit 5a1e6df3, using essentially
the same scheme as the one used here). It is necessary for index AMs to
have direct responsibility for maintaining the new counter, since the
counter might need to be incremented multiple times per amgettuple call
(or per amgetbitmap call). But it is also necessary for the executor
proper to manage the shared memory now used to transfer each worker's
counter struct to the leader.
Author: Peter Geoghegan <pg@bowt.ie>
Reviewed-By: Robert Haas <robertmhaas@gmail.com>
Reviewed-By: Tomas Vondra <tomas@vondra.me>
Reviewed-By: Masahiro Ikeda <ikedamsh@oss.nttdata.com>
Reviewed-By: Matthias van de Meent <boekewurm+postgres@gmail.com>
Discussion: https://postgr.es/m/CAH2-WzkRqvaqR2CTNqTZP0z6FuL4-3ED6eQB0yx38XBNj1v-4Q@mail.gmail.com
Discussion: https://postgr.es/m/CAH2-Wz=PKR6rB7qbx+Vnd7eqeB5VTcrW=iJvAsTsKbdG+kW_UA@mail.gmail.com
2025-03-11 09:20:50 -04:00
|
|
|
extern void ExecIndexScanRetrieveInstrumentation(IndexScanState *node);
|
2002-12-05 10:50:39 -05:00
|
|
|
|
2011-10-11 14:20:06 -04:00
|
|
|
/*
|
|
|
|
|
* These routines are exported to share code with nodeIndexonlyscan.c and
|
|
|
|
|
* nodeBitmapIndexscan.c
|
|
|
|
|
*/
|
2006-01-25 15:29:24 -05:00
|
|
|
extern void ExecIndexBuildScanKeys(PlanState *planstate, Relation index,
|
2011-10-11 14:20:06 -04:00
|
|
|
List *quals, bool isorderby,
|
2010-12-02 20:50:48 -05:00
|
|
|
ScanKey *scanKeys, int *numScanKeys,
|
2005-11-25 14:47:50 -05:00
|
|
|
IndexRuntimeKeyInfo **runtimeKeys, int *numRuntimeKeys,
|
|
|
|
|
IndexArrayKeyInfo **arrayKeys, int *numArrayKeys);
|
2005-04-24 21:30:14 -04:00
|
|
|
extern void ExecIndexEvalRuntimeKeys(ExprContext *econtext,
|
2005-11-25 14:47:50 -05:00
|
|
|
IndexRuntimeKeyInfo *runtimeKeys, int numRuntimeKeys);
|
|
|
|
|
extern bool ExecIndexEvalArrayKeys(ExprContext *econtext,
|
|
|
|
|
IndexArrayKeyInfo *arrayKeys, int numArrayKeys);
|
|
|
|
|
extern bool ExecIndexAdvanceArrayKeys(IndexArrayKeyInfo *arrayKeys, int numArrayKeys);
|
2005-04-24 21:30:14 -04:00
|
|
|
|
1996-07-09 02:22:35 -04:00
|
|
|
#endif /* NODEINDEXSCAN_H */
|