Thanks to visit codestin.com
Credit goes to github.com

Skip to content

Commit f179e9f

Browse files
author
Amit Kapila
committed
Allow parallel create index to accumulate buffer usage stats.
Currently, we don't account for buffer usage incurred by parallel workers for parallel create index.  This commit allows each worker to record the buffer usage stats and leader backend to accumulate that stats at the end of the operation.  This will allow pg_stat_statements to display correct buffer usage stats for (parallel) create index command. Reported-by: Julien Rouhaud Author: Sawada Masahiko Reviewed-by: Dilip Kumar, Julien Rouhaud and Amit Kapila Backpatch-through: 11, where this was introduced Discussion: https://postgr.es/m/20200328151721.GB12854@nol
1 parent d050c61 commit f179e9f

File tree

1 file changed

+39
-0
lines changed

1 file changed

+39
-0
lines changed

src/backend/access/nbtree/nbtsort.c

Lines changed: 39 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -64,6 +64,7 @@
6464
#include "access/xlog.h"
6565
#include "access/xloginsert.h"
6666
#include "catalog/index.h"
67+
#include "executor/instrument.h"
6768
#include "miscadmin.h"
6869
#include "pgstat.h"
6970
#include "storage/smgr.h"
@@ -78,6 +79,7 @@
7879
#define PARALLEL_KEY_TUPLESORT UINT64CONST(0xA000000000000002)
7980
#define PARALLEL_KEY_TUPLESORT_SPOOL2 UINT64CONST(0xA000000000000003)
8081
#define PARALLEL_KEY_QUERY_TEXT UINT64CONST(0xA000000000000004)
82+
#define PARALLEL_KEY_BUFFER_USAGE UINT64CONST(0xA000000000000005)
8183

8284
/*
8385
* DISABLE_LEADER_PARTICIPATION disables the leader's participation in
@@ -192,6 +194,7 @@ typedef struct BTLeader
192194
Sharedsort *sharedsort;
193195
Sharedsort *sharedsort2;
194196
Snapshot snapshot;
197+
BufferUsage *bufferusage;
195198
} BTLeader;
196199

197200
/*
@@ -1240,6 +1243,7 @@ _bt_begin_parallel(BTBuildState *buildstate, bool isconcurrent, int request)
12401243
Sharedsort *sharedsort2;
12411244
BTSpool *btspool = buildstate->spool;
12421245
BTLeader *btleader = (BTLeader *) palloc0(sizeof(BTLeader));
1246+
BufferUsage *bufferusage;
12431247
bool leaderparticipates = true;
12441248
char *sharedquery;
12451249
int querylen;
@@ -1292,6 +1296,17 @@ _bt_begin_parallel(BTBuildState *buildstate, bool isconcurrent, int request)
12921296
shm_toc_estimate_keys(&pcxt->estimator, 3);
12931297
}
12941298

1299+
/*
1300+
* Estimate space for BufferUsage -- PARALLEL_KEY_BUFFER_USAGE.
1301+
*
1302+
* If there are no extensions loaded that care, we could skip this. We
1303+
* have no way of knowing whether anyone's looking at pgBufferUsage, so do
1304+
* it unconditionally.
1305+
*/
1306+
shm_toc_estimate_chunk(&pcxt->estimator,
1307+
mul_size(sizeof(BufferUsage), pcxt->nworkers));
1308+
shm_toc_estimate_keys(&pcxt->estimator, 1);
1309+
12951310
/* Finally, estimate PARALLEL_KEY_QUERY_TEXT space */
12961311
querylen = strlen(debug_query_string);
12971312
shm_toc_estimate_chunk(&pcxt->estimator, querylen + 1);
@@ -1361,6 +1376,11 @@ _bt_begin_parallel(BTBuildState *buildstate, bool isconcurrent, int request)
13611376
memcpy(sharedquery, debug_query_string, querylen + 1);
13621377
shm_toc_insert(pcxt->toc, PARALLEL_KEY_QUERY_TEXT, sharedquery);
13631378

1379+
/* Allocate space for each worker's BufferUsage; no need to initialize */
1380+
bufferusage = shm_toc_allocate(pcxt->toc,
1381+
mul_size(sizeof(BufferUsage), pcxt->nworkers));
1382+
shm_toc_insert(pcxt->toc, PARALLEL_KEY_BUFFER_USAGE, bufferusage);
1383+
13641384
/* Launch workers, saving status for leader/caller */
13651385
LaunchParallelWorkers(pcxt);
13661386
btleader->pcxt = pcxt;
@@ -1371,6 +1391,7 @@ _bt_begin_parallel(BTBuildState *buildstate, bool isconcurrent, int request)
13711391
btleader->sharedsort = sharedsort;
13721392
btleader->sharedsort2 = sharedsort2;
13731393
btleader->snapshot = snapshot;
1394+
btleader->bufferusage = bufferusage;
13741395

13751396
/* If no workers were successfully launched, back out (do serial build) */
13761397
if (pcxt->nworkers_launched == 0)
@@ -1399,8 +1420,18 @@ _bt_begin_parallel(BTBuildState *buildstate, bool isconcurrent, int request)
13991420
static void
14001421
_bt_end_parallel(BTLeader *btleader)
14011422
{
1423+
int i;
1424+
14021425
/* Shutdown worker processes */
14031426
WaitForParallelWorkersToFinish(btleader->pcxt);
1427+
1428+
/*
1429+
* Next, accumulate buffer usage. (This must wait for the workers to
1430+
* finish, or we might get incomplete data.)
1431+
*/
1432+
for (i = 0; i < btleader->pcxt->nworkers_launched; i++)
1433+
InstrAccumParallelQuery(&btleader->bufferusage[i]);
1434+
14041435
/* Free last reference to MVCC snapshot, if one was used */
14051436
if (IsMVCCSnapshot(btleader->snapshot))
14061437
UnregisterSnapshot(btleader->snapshot);
@@ -1537,6 +1568,7 @@ _bt_parallel_build_main(dsm_segment *seg, shm_toc *toc)
15371568
Relation indexRel;
15381569
LOCKMODE heapLockmode;
15391570
LOCKMODE indexLockmode;
1571+
BufferUsage *bufferusage;
15401572
int sortmem;
15411573

15421574
#ifdef BTREE_BUILD_STATS
@@ -1598,11 +1630,18 @@ _bt_parallel_build_main(dsm_segment *seg, shm_toc *toc)
15981630
tuplesort_attach_shared(sharedsort2, seg);
15991631
}
16001632

1633+
/* Prepare to track buffer usage during parallel execution */
1634+
InstrStartParallelQuery();
1635+
16011636
/* Perform sorting of spool, and possibly a spool2 */
16021637
sortmem = maintenance_work_mem / btshared->scantuplesortstates;
16031638
_bt_parallel_scan_and_sort(btspool, btspool2, btshared, sharedsort,
16041639
sharedsort2, sortmem);
16051640

1641+
/* Report buffer usage during parallel execution */
1642+
bufferusage = shm_toc_lookup(toc, PARALLEL_KEY_BUFFER_USAGE, false);
1643+
InstrEndParallelQuery(&bufferusage[ParallelWorkerNumber]);
1644+
16061645
#ifdef BTREE_BUILD_STATS
16071646
if (log_btree_build_stats)
16081647
{

0 commit comments

Comments
 (0)