mirror of
https://git.postgresql.org/git/postgresql.git
synced 2026-02-14 02:17:02 +08:00
Commit 28724fd90d2f85a0573a8107b48abad062a86d83 fixed things so that if a background worker fails to start due to fork() failure or because it is terminated before startup succeeds, BGWH_STOPPED will be reported. However, that only helps if the code that uses the background worker machinery notices the change in status, and the code in parallel.c did not. To fix that, do two things. First, make sure that when a worker exits, it triggers the leader to read from error queues. That way, if a worker which has attached to an error queue exits uncleanly, the leader is sure to throw some error, either the contents of the ErrorResponse sent by the worker, or "lost connection to parallel worker" if it exited without sending one. To cover the case where the worker never starts up in the first place or exits before attaching to the error queue, the ParallelContext now keeps track of which workers have sent at least one message via the error queue. A worker which sends no messages by the time the parallel operation finishes will be checked to see whether it exited before attaching to the error queue; if so, a new error message, "parallel worker failed to initialize", will be reported. If not, we'll continue to wait until it either starts up and exits cleanly, starts up and exits uncleanly, or fails to start, and then take the appropriate action. Patch by me, reviewed by Amit Kapila. Discussion: http://postgr.es/m/CA+TgmoYnBgXgdTu6wk5YPdWhmgabYc9nY_pFLq=tB=FSLYkD8Q@mail.gmail.com
78 lines
2.3 KiB
C
78 lines
2.3 KiB
C
/*-------------------------------------------------------------------------
|
|
*
|
|
* parallel.h
|
|
* Infrastructure for launching parallel workers
|
|
*
|
|
* Portions Copyright (c) 1996-2018, PostgreSQL Global Development Group
|
|
* Portions Copyright (c) 1994, Regents of the University of California
|
|
*
|
|
* src/include/access/parallel.h
|
|
*
|
|
*-------------------------------------------------------------------------
|
|
*/
|
|
|
|
#ifndef PARALLEL_H
|
|
#define PARALLEL_H
|
|
|
|
#include "access/xlogdefs.h"
|
|
#include "lib/ilist.h"
|
|
#include "postmaster/bgworker.h"
|
|
#include "storage/shm_mq.h"
|
|
#include "storage/shm_toc.h"
|
|
|
|
typedef void (*parallel_worker_main_type) (dsm_segment *seg, shm_toc *toc);
|
|
|
|
typedef struct ParallelWorkerInfo
|
|
{
|
|
BackgroundWorkerHandle *bgwhandle;
|
|
shm_mq_handle *error_mqh;
|
|
int32 pid;
|
|
} ParallelWorkerInfo;
|
|
|
|
typedef struct ParallelContext
|
|
{
|
|
dlist_node node;
|
|
SubTransactionId subid;
|
|
int nworkers;
|
|
int nworkers_launched;
|
|
char *library_name;
|
|
char *function_name;
|
|
ErrorContextCallback *error_context_stack;
|
|
shm_toc_estimator estimator;
|
|
dsm_segment *seg;
|
|
void *private_memory;
|
|
shm_toc *toc;
|
|
ParallelWorkerInfo *worker;
|
|
bool *any_message_received;
|
|
} ParallelContext;
|
|
|
|
typedef struct ParallelWorkerContext
|
|
{
|
|
dsm_segment *seg;
|
|
shm_toc *toc;
|
|
} ParallelWorkerContext;
|
|
|
|
extern volatile bool ParallelMessagePending;
|
|
extern PGDLLIMPORT int ParallelWorkerNumber;
|
|
extern PGDLLIMPORT bool InitializingParallelWorker;
|
|
|
|
#define IsParallelWorker() (ParallelWorkerNumber >= 0)
|
|
|
|
extern ParallelContext *CreateParallelContext(const char *library_name, const char *function_name, int nworkers);
|
|
extern void InitializeParallelDSM(ParallelContext *pcxt);
|
|
extern void ReinitializeParallelDSM(ParallelContext *pcxt);
|
|
extern void LaunchParallelWorkers(ParallelContext *pcxt);
|
|
extern void WaitForParallelWorkersToFinish(ParallelContext *pcxt);
|
|
extern void DestroyParallelContext(ParallelContext *pcxt);
|
|
extern bool ParallelContextActive(void);
|
|
|
|
extern void HandleParallelMessageInterrupt(void);
|
|
extern void HandleParallelMessages(void);
|
|
extern void AtEOXact_Parallel(bool isCommit);
|
|
extern void AtEOSubXact_Parallel(bool isCommit, SubTransactionId mySubId);
|
|
extern void ParallelWorkerReportLastRecEnd(XLogRecPtr last_xlog_end);
|
|
|
|
extern void ParallelWorkerMain(Datum main_arg);
|
|
|
|
#endif /* PARALLEL_H */
|