aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--src/backend/executor/execProcnode.c17
-rw-r--r--src/backend/executor/nodeGather.c3
-rw-r--r--src/backend/executor/nodeLimit.c2
3 files changed, 22 insertions, 0 deletions
diff --git a/src/backend/executor/execProcnode.c b/src/backend/executor/execProcnode.c
index 8b3663b3c9d..eaed9fb5a97 100644
--- a/src/backend/executor/execProcnode.c
+++ b/src/backend/executor/execProcnode.c
@@ -752,6 +752,19 @@ ExecShutdownNode(PlanState *node)
planstate_tree_walker(node, ExecShutdownNode, NULL);
+ /*
+ * Treat the node as running while we shut it down, but only if it's run
+ * at least once already. We don't expect much CPU consumption during
+ * node shutdown, but in the case of Gather or Gather Merge, we may shut
+ * down workers at this stage. If so, their buffer usage will get
+ * propagated into pgBufferUsage at this point, and we want to make sure
+ * that it gets associated with the Gather node. We skip this if the node
+ * has never been executed, so as to avoid incorrectly making it appear
+ * that it has.
+ */
+ if (node->instrument && node->instrument->running)
+ InstrStartNode(node->instrument);
+
switch (nodeTag(node))
{
case T_GatherState:
@@ -776,6 +789,10 @@ ExecShutdownNode(PlanState *node)
break;
}
+ /* Stop the node if we started it above, reporting 0 tuples. */
+ if (node->instrument && node->instrument->running)
+ InstrStopNode(node->instrument, 0);
+
return false;
}
diff --git a/src/backend/executor/nodeGather.c b/src/backend/executor/nodeGather.c
index cdc9c51bd15..4a700b7b30e 100644
--- a/src/backend/executor/nodeGather.c
+++ b/src/backend/executor/nodeGather.c
@@ -324,7 +324,10 @@ gather_readnext(GatherState *gatherstate)
Assert(!tup);
--gatherstate->nreaders;
if (gatherstate->nreaders == 0)
+ {
+ ExecShutdownGatherWorkers(gatherstate);
return NULL;
+ }
memmove(&gatherstate->reader[gatherstate->nextreader],
&gatherstate->reader[gatherstate->nextreader + 1],
sizeof(TupleQueueReader *)
diff --git a/src/backend/executor/nodeLimit.c b/src/backend/executor/nodeLimit.c
index 56d98b4490b..66ea6aa3c35 100644
--- a/src/backend/executor/nodeLimit.c
+++ b/src/backend/executor/nodeLimit.c
@@ -134,6 +134,8 @@ ExecLimit(PlanState *pstate)
node->position - node->offset >= node->count)
{
node->lstate = LIMIT_WINDOWEND;
+ /* Allow nodes to release or shut down resources. */
+ (void) ExecShutdownNode(outerPlan);
return NULL;
}