summaryrefslogtreecommitdiff
path: root/src/include/nodes
diff options
context:
space:
mode:
authorRobert Haas <rhaas@postgresql.org>2017-03-09 07:40:36 -0500
committerRobert Haas <rhaas@postgresql.org>2017-03-09 07:49:29 -0500
commit355d3993c53ed62c5b53d020648e4fbcfbf5f155 (patch)
tree9a439084995c6553dd035fe218d9864011192b36 /src/include/nodes
parenta72f0365db4168e7d720608fe3ac0ca3fe9355df (diff)
downloadpostgresql-355d3993c53ed62c5b53d020648e4fbcfbf5f155.tar.gz
Add a Gather Merge executor node.
Like Gather, we spawn multiple workers and run the same plan in each one; however, Gather Merge is used when each worker produces the same output ordering and we want to preserve that output ordering while merging together the streams of tuples from various workers. (In a way, Gather Merge is like a hybrid of Gather and MergeAppend.) This works out to a win if it saves us from having to perform an expensive Sort. In cases where only a small amount of data would need to be sorted, it may actually be faster to use a regular Gather node and then sort the results afterward, because Gather Merge sometimes needs to wait synchronously for tuples whereas a pure Gather generally doesn't. But if this avoids an expensive sort then it's a win. Rushabh Lathia, reviewed and tested by Amit Kapila, Thomas Munro, and Neha Sharma, and reviewed and revised by me. Discussion: http://postgr.es/m/CAGPqQf09oPX-cQRpBKS0Gq49Z+m6KBxgxd_p9gX8CKk_d75HoQ@mail.gmail.com
Diffstat (limited to 'src/include/nodes')
-rw-r--r--src/include/nodes/execnodes.h29
-rw-r--r--src/include/nodes/nodes.h3
-rw-r--r--src/include/nodes/plannodes.h16
-rw-r--r--src/include/nodes/relation.h13
4 files changed, 61 insertions, 0 deletions
diff --git a/src/include/nodes/execnodes.h b/src/include/nodes/execnodes.h
index 6a0d590ef2..f856f6036f 100644
--- a/src/include/nodes/execnodes.h
+++ b/src/include/nodes/execnodes.h
@@ -2095,6 +2095,35 @@ typedef struct GatherState
} GatherState;
/* ----------------
+ * GatherMergeState information
+ *
+ * Gather merge nodes launch 1 or more parallel workers, run a
+ * subplan which produces sorted output in each worker, and then
+ * merge the results into a single sorted stream.
+ * ----------------
+ */
+struct GMReaderTuple;
+
+typedef struct GatherMergeState
+{
+ PlanState ps; /* its first field is NodeTag */
+ bool initialized;
+ struct ParallelExecutorInfo *pei;
+ int nreaders;
+ int nworkers_launched;
+ struct TupleQueueReader **reader;
+ TupleDesc tupDesc;
+ TupleTableSlot **gm_slots;
+ struct binaryheap *gm_heap; /* binary heap of slot indices */
+ bool gm_initialized; /* gather merge initilized ? */
+ bool need_to_scan_locally;
+ int gm_nkeys;
+ SortSupport gm_sortkeys; /* array of length ms_nkeys */
+ struct GMReaderTupleBuffer *gm_tuple_buffers; /* tuple buffer per
+ * reader */
+} GatherMergeState;
+
+/* ----------------
* HashState information
* ----------------
*/
diff --git a/src/include/nodes/nodes.h b/src/include/nodes/nodes.h
index 49fa944755..2bc7a5df11 100644
--- a/src/include/nodes/nodes.h
+++ b/src/include/nodes/nodes.h
@@ -77,6 +77,7 @@ typedef enum NodeTag
T_WindowAgg,
T_Unique,
T_Gather,
+ T_GatherMerge,
T_Hash,
T_SetOp,
T_LockRows,
@@ -127,6 +128,7 @@ typedef enum NodeTag
T_WindowAggState,
T_UniqueState,
T_GatherState,
+ T_GatherMergeState,
T_HashState,
T_SetOpState,
T_LockRowsState,
@@ -249,6 +251,7 @@ typedef enum NodeTag
T_MaterialPath,
T_UniquePath,
T_GatherPath,
+ T_GatherMergePath,
T_ProjectionPath,
T_ProjectSetPath,
T_SortPath,
diff --git a/src/include/nodes/plannodes.h b/src/include/nodes/plannodes.h
index 7fbb0c2c77..b880dc16cf 100644
--- a/src/include/nodes/plannodes.h
+++ b/src/include/nodes/plannodes.h
@@ -797,6 +797,22 @@ typedef struct Gather
bool invisible; /* suppress EXPLAIN display (for testing)? */
} Gather;
+/* ------------
+ * gather merge node
+ * ------------
+ */
+typedef struct GatherMerge
+{
+ Plan plan;
+ int num_workers;
+ /* remaining fields are just like the sort-key info in struct Sort */
+ int numCols; /* number of sort-key columns */
+ AttrNumber *sortColIdx; /* their indexes in the target list */
+ Oid *sortOperators; /* OIDs of operators to sort them by */
+ Oid *collations; /* OIDs of collations */
+ bool *nullsFirst; /* NULLS FIRST/LAST directions */
+} GatherMerge;
+
/* ----------------
* hash build node
*
diff --git a/src/include/nodes/relation.h b/src/include/nodes/relation.h
index f7ac6f600f..05d6f07aea 100644
--- a/src/include/nodes/relation.h
+++ b/src/include/nodes/relation.h
@@ -1204,6 +1204,19 @@ typedef struct GatherPath
} GatherPath;
/*
+ * GatherMergePath runs several copies of a plan in parallel and
+ * collects the results. For gather merge parallel leader always execute the
+ * plan.
+ */
+typedef struct GatherMergePath
+{
+ Path path;
+ Path *subpath; /* path for each worker */
+ int num_workers; /* number of workers sought to help */
+} GatherMergePath;
+
+
+/*
* All join-type paths share these fields.
*/