PostgreSQL Source Code git master
Loading...
Searching...
No Matches
nodeAppend.h File Reference
#include "access/parallel.h"
#include "nodes/execnodes.h"
Include dependency graph for nodeAppend.h:
This graph shows which files directly or indirectly include this file:

Go to the source code of this file.

Functions

AppendStateExecInitAppend (Append *node, EState *estate, int eflags)
 
void ExecEndAppend (AppendState *node)
 
void ExecReScanAppend (AppendState *node)
 
void ExecAppendEstimate (AppendState *node, ParallelContext *pcxt)
 
void ExecAppendInitializeDSM (AppendState *node, ParallelContext *pcxt)
 
void ExecAppendReInitializeDSM (AppendState *node, ParallelContext *pcxt)
 
void ExecAppendInitializeWorker (AppendState *node, ParallelWorkerContext *pwcxt)
 
void ExecAsyncAppendResponse (AsyncRequest *areq)
 

Function Documentation

◆ ExecAppendEstimate()

void ExecAppendEstimate ( AppendState node,
ParallelContext pcxt 
)
extern

Definition at line 502 of file nodeAppend.c.

504{
505 node->pstate_len =
507 sizeof(bool) * node->as_nplans);
508
511}
Size add_size(Size s1, Size s2)
Definition mcxt.c:1733
static int fb(int x)
#define shm_toc_estimate_chunk(e, sz)
Definition shm_toc.h:51
#define shm_toc_estimate_keys(e, cnt)
Definition shm_toc.h:53
Size pstate_len
Definition execnodes.h:1553
shm_toc_estimator estimator
Definition parallel.h:43

References add_size(), AppendState::as_nplans, ParallelContext::estimator, fb(), AppendState::pstate_len, shm_toc_estimate_chunk, and shm_toc_estimate_keys.

Referenced by ExecParallelEstimate().

◆ ExecAppendInitializeDSM()

void ExecAppendInitializeDSM ( AppendState node,
ParallelContext pcxt 
)
extern

Definition at line 521 of file nodeAppend.c.

523{
524 ParallelAppendState *pstate;
525
526 pstate = shm_toc_allocate(pcxt->toc, node->pstate_len);
527 memset(pstate, 0, node->pstate_len);
529 shm_toc_insert(pcxt->toc, node->ps.plan->plan_node_id, pstate);
530
531 node->as_pstate = pstate;
533}
void LWLockInitialize(LWLock *lock, int tranche_id)
Definition lwlock.c:670
static bool choose_next_subplan_for_leader(AppendState *node)
Definition nodeAppend.c:638
void * shm_toc_allocate(shm_toc *toc, Size nbytes)
Definition shm_toc.c:88
void shm_toc_insert(shm_toc *toc, uint64 key, void *address)
Definition shm_toc.c:171
bool(* choose_next_subplan)(AppendState *)
Definition execnodes.h:1558
PlanState ps
Definition execnodes.h:1534
ParallelAppendState * as_pstate
Definition execnodes.h:1552
shm_toc * toc
Definition parallel.h:46
Plan * plan
Definition execnodes.h:1201
int plan_node_id
Definition plannodes.h:233

References AppendState::as_pstate, AppendState::choose_next_subplan, choose_next_subplan_for_leader(), fb(), LWLockInitialize(), ParallelAppendState::pa_lock, PlanState::plan, Plan::plan_node_id, AppendState::ps, AppendState::pstate_len, shm_toc_allocate(), shm_toc_insert(), and ParallelContext::toc.

Referenced by ExecParallelInitializeDSM().

◆ ExecAppendInitializeWorker()

void ExecAppendInitializeWorker ( AppendState node,
ParallelWorkerContext pwcxt 
)
extern

Definition at line 558 of file nodeAppend.c.

559{
560 node->as_pstate = shm_toc_lookup(pwcxt->toc, node->ps.plan->plan_node_id, false);
562}
static bool choose_next_subplan_for_worker(AppendState *node)
Definition nodeAppend.c:720
void * shm_toc_lookup(shm_toc *toc, uint64 key, bool noError)
Definition shm_toc.c:239

References AppendState::as_pstate, AppendState::choose_next_subplan, choose_next_subplan_for_worker(), fb(), PlanState::plan, Plan::plan_node_id, AppendState::ps, and shm_toc_lookup().

Referenced by ExecParallelInitializeWorker().

◆ ExecAppendReInitializeDSM()

void ExecAppendReInitializeDSM ( AppendState node,
ParallelContext pcxt 
)
extern

Definition at line 542 of file nodeAppend.c.

543{
544 ParallelAppendState *pstate = node->as_pstate;
545
546 pstate->pa_next_plan = 0;
547 memset(pstate->pa_finished, 0, sizeof(bool) * node->as_nplans);
548}
bool pa_finished[FLEXIBLE_ARRAY_MEMBER]
Definition nodeAppend.c:83

References AppendState::as_nplans, AppendState::as_pstate, fb(), ParallelAppendState::pa_finished, and ParallelAppendState::pa_next_plan.

Referenced by ExecParallelReInitializeDSM().

◆ ExecAsyncAppendResponse()

void ExecAsyncAppendResponse ( AsyncRequest areq)
extern

Definition at line 1145 of file nodeAppend.c.

1146{
1147 AppendState *node = (AppendState *) areq->requestor;
1148 TupleTableSlot *slot = areq->result;
1149
1150 /* The result should be a TupleTableSlot or NULL. */
1151 Assert(slot == NULL || IsA(slot, TupleTableSlot));
1152
1153 /* Nothing to do if the request is pending. */
1154 if (!areq->request_complete)
1155 {
1156 /* The request would have been pending for a callback. */
1157 Assert(areq->callback_pending);
1158 return;
1159 }
1160
1161 /* If the result is NULL or an empty slot, there's nothing more to do. */
1162 if (TupIsNull(slot))
1163 {
1164 /* The ending subplan wouldn't have been pending for a callback. */
1165 Assert(!areq->callback_pending);
1166 --node->as_nasyncremain;
1167 return;
1168 }
1169
1170 /* Save result so we can return it. */
1171 Assert(node->as_nasyncresults < node->as_nasyncplans);
1172 node->as_asyncresults[node->as_nasyncresults++] = slot;
1173
1174 /*
1175 * Mark the subplan that returned a result as ready for a new request. We
1176 * don't launch another one here immediately because it might complete.
1177 */
1178 node->as_needrequest = bms_add_member(node->as_needrequest,
1179 areq->request_index);
1180}
Bitmapset * bms_add_member(Bitmapset *a, int x)
Definition bitmapset.c:799
#define Assert(condition)
Definition c.h:943
#define IsA(nodeptr, _type_)
Definition nodes.h:164
#define TupIsNull(slot)
Definition tuptable.h:325

References AppendState::as_asyncresults, AppendState::as_nasyncplans, AppendState::as_nasyncremain, AppendState::as_nasyncresults, AppendState::as_needrequest, Assert, bms_add_member(), fb(), IsA, and TupIsNull.

Referenced by ExecAsyncResponse().

◆ ExecEndAppend()

void ExecEndAppend ( AppendState node)
extern

Definition at line 404 of file nodeAppend.c.

405{
406 PlanState **appendplans;
407 int nplans;
408 int i;
409
410 /*
411 * get information from the node
412 */
413 appendplans = node->appendplans;
414 nplans = node->as_nplans;
415
416 /*
417 * shut down each of the subscans
418 */
419 for (i = 0; i < nplans; i++)
420 ExecEndNode(appendplans[i]);
421}
void ExecEndNode(PlanState *node)
int i
Definition isn.c:77
PlanState ** appendplans
Definition execnodes.h:1535

References AppendState::appendplans, AppendState::as_nplans, ExecEndNode(), and i.

Referenced by ExecEndNode().

◆ ExecInitAppend()

AppendState * ExecInitAppend ( Append node,
EState estate,
int  eflags 
)
extern

Definition at line 112 of file nodeAppend.c.

113{
119 int nplans;
120 int nasyncplans;
121 int firstvalid;
122 int i,
123 j;
124
125 /* check for unsupported flags */
126 Assert(!(eflags & EXEC_FLAG_MARK));
127
128 /*
129 * create new AppendState for our append node
130 */
131 appendstate->ps.plan = (Plan *) node;
132 appendstate->ps.state = estate;
133 appendstate->ps.ExecProcNode = ExecAppend;
134
135 /* Let choose_next_subplan_* function handle setting the first subplan */
136 appendstate->as_whichplan = INVALID_SUBPLAN_INDEX;
137 appendstate->as_syncdone = false;
138 appendstate->as_begun = false;
139
140 /* If run-time partition pruning is enabled, then set that up now */
141 if (node->part_prune_index >= 0)
142 {
144
145 /*
146 * Set up pruning data structure. This also initializes the set of
147 * subplans to initialize (validsubplans) by taking into account the
148 * result of performing initial pruning if any.
149 */
152 node->part_prune_index,
153 node->apprelids,
155 appendstate->as_prune_state = prunestate;
157
158 /*
159 * When no run-time pruning is required and there's at least one
160 * subplan, we can fill as_valid_subplans immediately, preventing
161 * later calls to ExecFindMatchingSubPlans.
162 */
163 if (!prunestate->do_exec_prune && nplans > 0)
164 {
165 appendstate->as_valid_subplans = bms_add_range(NULL, 0, nplans - 1);
166 appendstate->as_valid_subplans_identified = true;
167 }
168 }
169 else
170 {
171 nplans = list_length(node->appendplans);
172
173 /*
174 * When run-time partition pruning is not enabled we can just mark all
175 * subplans as valid; they must also all be initialized.
176 */
177 Assert(nplans > 0);
178 appendstate->as_valid_subplans = validsubplans =
179 bms_add_range(NULL, 0, nplans - 1);
180 appendstate->as_valid_subplans_identified = true;
181 appendstate->as_prune_state = NULL;
182 }
183
184 appendplanstates = (PlanState **) palloc(nplans *
185 sizeof(PlanState *));
186
187 /*
188 * call ExecInitNode on each of the valid plans to be executed and save
189 * the results into the appendplanstates array.
190 *
191 * While at it, find out the first valid partial plan.
192 */
193 j = 0;
195 nasyncplans = 0;
196 firstvalid = nplans;
197 i = -1;
198 while ((i = bms_next_member(validsubplans, i)) >= 0)
199 {
200 Plan *initNode = (Plan *) list_nth(node->appendplans, i);
201
202 /*
203 * Record async subplans. When executing EvalPlanQual, we treat them
204 * as sync ones; don't do this when initializing an EvalPlanQual plan
205 * tree.
206 */
207 if (initNode->async_capable && estate->es_epq_active == NULL)
208 {
210 nasyncplans++;
211 }
212
213 /*
214 * Record the lowest appendplans index which is a valid partial plan.
215 */
216 if (i >= node->first_partial_plan && j < firstvalid)
217 firstvalid = j;
218
219 appendplanstates[j++] = ExecInitNode(initNode, estate, eflags);
220 }
221
222 appendstate->as_first_partial_plan = firstvalid;
223 appendstate->appendplans = appendplanstates;
224 appendstate->as_nplans = nplans;
225
226 /*
227 * Initialize Append's result tuple type and slot. If the child plans all
228 * produce the same fixed slot type, we can use that slot type; otherwise
229 * make a virtual slot. (Note that the result slot itself is used only to
230 * return a null tuple at end of execution; real tuples are returned to
231 * the caller in the children's own result slots. What we are doing here
232 * is allowing the parent plan node to optimize if the Append will return
233 * only one kind of slot.)
234 */
236 if (appendops != NULL)
237 {
239 }
240 else
241 {
243 /* show that the output slot type is not fixed */
244 appendstate->ps.resultopsset = true;
245 appendstate->ps.resultopsfixed = false;
246 }
247
248 /* Initialize async state */
249 appendstate->as_asyncplans = asyncplans;
250 appendstate->as_nasyncplans = nasyncplans;
251 appendstate->as_asyncrequests = NULL;
252 appendstate->as_asyncresults = NULL;
253 appendstate->as_nasyncresults = 0;
254 appendstate->as_nasyncremain = 0;
255 appendstate->as_needrequest = NULL;
256 appendstate->as_eventset = NULL;
257 appendstate->as_valid_asyncplans = NULL;
258
259 if (nasyncplans > 0)
260 {
261 appendstate->as_asyncrequests = (AsyncRequest **)
262 palloc0(nplans * sizeof(AsyncRequest *));
263
264 i = -1;
265 while ((i = bms_next_member(asyncplans, i)) >= 0)
266 {
268
270 areq->requestor = (PlanState *) appendstate;
271 areq->requestee = appendplanstates[i];
272 areq->request_index = i;
273 areq->callback_pending = false;
274 areq->request_complete = false;
275 areq->result = NULL;
276
277 appendstate->as_asyncrequests[i] = areq;
278 }
279
280 appendstate->as_asyncresults = (TupleTableSlot **)
281 palloc0(nasyncplans * sizeof(TupleTableSlot *));
282
283 if (appendstate->as_valid_subplans_identified)
285 }
286
287 /*
288 * Miscellaneous initialization
289 */
290
291 appendstate->ps.ps_ProjInfo = NULL;
292
293 /* For parallel query, this will be overridden later. */
294 appendstate->choose_next_subplan = choose_next_subplan_locally;
295
296 return appendstate;
297}
int bms_next_member(const Bitmapset *a, int prevbit)
Definition bitmapset.c:1290
Bitmapset * bms_add_range(Bitmapset *a, int lower, int upper)
Definition bitmapset.c:1003
int bms_num_members(const Bitmapset *a)
Definition bitmapset.c:744
PartitionPruneState * ExecInitPartitionExecPruning(PlanState *planstate, int n_total_subplans, int part_prune_index, Bitmapset *relids, Bitmapset **initially_valid_subplans)
PlanState * ExecInitNode(Plan *node, EState *estate, int eflags)
const TupleTableSlotOps TTSOpsVirtual
Definition execTuples.c:84
void ExecInitResultTupleSlotTL(PlanState *planstate, const TupleTableSlotOps *tts_ops)
const TupleTableSlotOps * ExecGetCommonSlotOps(PlanState **planstates, int nplans)
Definition execUtils.c:541
#define EXEC_FLAG_MARK
Definition executor.h:71
#define palloc_object(type)
Definition fe_memutils.h:89
int j
Definition isn.c:78
void * palloc0(Size size)
Definition mcxt.c:1420
void * palloc(Size size)
Definition mcxt.c:1390
static void classify_matching_subplans(AppendState *node)
static TupleTableSlot * ExecAppend(PlanState *pstate)
Definition nodeAppend.c:306
#define INVALID_SUBPLAN_INDEX
Definition nodeAppend.c:86
static bool choose_next_subplan_locally(AppendState *node)
Definition nodeAppend.c:572
#define makeNode(_type_)
Definition nodes.h:161
static int list_length(const List *l)
Definition pg_list.h:152
static void * list_nth(const List *list, int n)
Definition pg_list.h:331
int first_partial_plan
Definition plannodes.h:418
int part_prune_index
Definition plannodes.h:425
Bitmapset * apprelids
Definition plannodes.h:403
List * appendplans
Definition plannodes.h:409
struct EPQState * es_epq_active
Definition execnodes.h:778

References Append::appendplans, Append::apprelids, Assert, bms_add_member(), bms_add_range(), bms_next_member(), bms_num_members(), choose_next_subplan_locally(), classify_matching_subplans(), EState::es_epq_active, EXEC_FLAG_MARK, ExecAppend(), ExecGetCommonSlotOps(), ExecInitNode(), ExecInitPartitionExecPruning(), ExecInitResultTupleSlotTL(), fb(), Append::first_partial_plan, i, INVALID_SUBPLAN_INDEX, j, list_length(), list_nth(), makeNode, palloc(), palloc0(), palloc_object, Append::part_prune_index, and TTSOpsVirtual.

Referenced by ExecInitNode().

◆ ExecReScanAppend()

void ExecReScanAppend ( AppendState node)
extern

Definition at line 424 of file nodeAppend.c.

425{
426 int nasyncplans = node->as_nasyncplans;
427 int i;
428
429 /*
430 * If any PARAM_EXEC Params used in pruning expressions have changed, then
431 * we'd better unset the valid subplans so that they are reselected for
432 * the new parameter values.
433 */
434 if (node->as_prune_state &&
435 bms_overlap(node->ps.chgParam,
437 {
438 node->as_valid_subplans_identified = false;
440 node->as_valid_subplans = NULL;
443 }
444
445 for (i = 0; i < node->as_nplans; i++)
446 {
447 PlanState *subnode = node->appendplans[i];
448
449 /*
450 * ExecReScan doesn't know about my subplans, so I have to do
451 * changed-parameter signaling myself.
452 */
453 if (node->ps.chgParam != NULL)
455
456 /*
457 * If chgParam of subnode is not null then plan will be re-scanned by
458 * first ExecProcNode or by first ExecAsyncRequest.
459 */
460 if (subnode->chgParam == NULL)
462 }
463
464 /* Reset async state */
465 if (nasyncplans > 0)
466 {
467 i = -1;
468 while ((i = bms_next_member(node->as_asyncplans, i)) >= 0)
469 {
471
472 areq->callback_pending = false;
473 areq->request_complete = false;
474 areq->result = NULL;
475 }
476
477 node->as_nasyncresults = 0;
478 node->as_nasyncremain = 0;
480 node->as_needrequest = NULL;
481 }
482
483 /* Let choose_next_subplan_* function handle setting the first subplan */
485 node->as_syncdone = false;
486 node->as_begun = false;
487}
void bms_free(Bitmapset *a)
Definition bitmapset.c:239
bool bms_overlap(const Bitmapset *a, const Bitmapset *b)
Definition bitmapset.c:575
void ExecReScan(PlanState *node)
Definition execAmi.c:78
void UpdateChangedParamSet(PlanState *node, Bitmapset *newchg)
Definition execUtils.c:936
struct PartitionPruneState * as_prune_state
Definition execnodes.h:1554
Bitmapset * as_valid_asyncplans
Definition execnodes.h:1557
Bitmapset * as_needrequest
Definition execnodes.h:1547
bool as_syncdone
Definition execnodes.h:1544
AsyncRequest ** as_asyncrequests
Definition execnodes.h:1541
Bitmapset * as_asyncplans
Definition execnodes.h:1539
int as_nasyncresults
Definition execnodes.h:1543
int as_nasyncremain
Definition execnodes.h:1546
Bitmapset * as_valid_subplans
Definition execnodes.h:1556
int as_nasyncplans
Definition execnodes.h:1540
bool as_valid_subplans_identified
Definition execnodes.h:1555
bool callback_pending
Definition execnodes.h:678
Bitmapset * execparamids
Bitmapset * chgParam
Definition execnodes.h:1235

References AppendState::appendplans, AppendState::as_asyncplans, AppendState::as_asyncrequests, AppendState::as_begun, AppendState::as_nasyncplans, AppendState::as_nasyncremain, AppendState::as_nasyncresults, AppendState::as_needrequest, AppendState::as_nplans, AppendState::as_prune_state, AppendState::as_syncdone, AppendState::as_valid_asyncplans, AppendState::as_valid_subplans, AppendState::as_valid_subplans_identified, AppendState::as_whichplan, bms_free(), bms_next_member(), bms_overlap(), AsyncRequest::callback_pending, PlanState::chgParam, PartitionPruneState::execparamids, ExecReScan(), fb(), i, INVALID_SUBPLAN_INDEX, AppendState::ps, and UpdateChangedParamSet().

Referenced by ExecReScan().