Movatterモバイル変換


[0]ホーム

URL:


Skip to content

Navigation Menu

Sign in
Appearance settings

Search code, repositories, users, issues, pull requests...

Provide feedback

We read every piece of feedback, and take your input very seriously.

Saved searches

Use saved searches to filter your results more quickly

Sign up
Appearance settings

Commit041b968

Browse files
committed
Use streaming I/O in ANALYZE.
The ANALYZE command prefetches and reads sample blocks chosen by aBlockSampler algorithm. Instead of calling [Prefetch|Read]Buffer() foreach block, ANALYZE now uses the streaming API introduced inb5a9b18.Author: Nazir Bilal Yavuz <byavuz81@gmail.com>Reviewed-by: Melanie Plageman <melanieplageman@gmail.com>Reviewed-by: Andres Freund <andres@anarazel.de>Reviewed-by: Jakub Wartak <jakub.wartak@enterprisedb.com>Reviewed-by: Heikki Linnakangas <hlinnaka@iki.fi>Reviewed-by: Thomas Munro <thomas.munro@gmail.com>Discussion:https://postgr.es/m/flat/CAN55FZ0UhXqk9v3y-zW_fp4-WCp43V8y0A72xPmLkOM%2B6M%2BmJg%40mail.gmail.com
1 parentf587338 commit041b968

File tree

3 files changed

+43
-76
lines changed

3 files changed

+43
-76
lines changed

‎src/backend/access/heap/heapam_handler.c

Lines changed: 16 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -1055,33 +1055,36 @@ heapam_relation_copy_for_cluster(Relation OldHeap, Relation NewHeap,
10551055
}
10561056

10571057
/*
1058-
* Prepare to analyze block `blockno` of `scan`. The scan has been started
1058+
* Prepare to analyze the next block in the read stream. Returns false if
1059+
* the stream is exhausted and true otherwise. The scan must have been started
10591060
* with SO_TYPE_ANALYZE option.
10601061
*
10611062
* This routine holds a buffer pin and lock on the heap page. They are held
10621063
* until heapam_scan_analyze_next_tuple() returns false. That is until all the
10631064
* items of the heap page are analyzed.
10641065
*/
1065-
void
1066-
heapam_scan_analyze_next_block(TableScanDescscan,BlockNumberblockno,
1067-
BufferAccessStrategybstrategy)
1066+
bool
1067+
heapam_scan_analyze_next_block(TableScanDescscan,ReadStream*stream)
10681068
{
10691069
HeapScanDeschscan= (HeapScanDesc)scan;
10701070

10711071
/*
10721072
* We must maintain a pin on the target page's buffer to ensure that
10731073
* concurrent activity - e.g. HOT pruning - doesn't delete tuples out from
1074-
* under us. Hence, pin the page until we are done looking at it. We
1075-
* also choose to hold sharelock on the buffer throughout --- we could
1076-
* release and re-acquire sharelock for each tuple, but since we aren't
1077-
* doing much work per tuple, the extra lock traffic is probably better
1078-
* avoided.
1074+
* under us. It comes from the stream already pinned. We also choose to
1075+
* hold sharelock on the buffer throughout --- we could release and
1076+
* re-acquire sharelock for each tuple, but since we aren't doing much
1077+
* work per tuple, the extra lock traffic is probably better avoided.
10791078
*/
1080-
hscan->rs_cblock=blockno;
1081-
hscan->rs_cindex=FirstOffsetNumber;
1082-
hscan->rs_cbuf=ReadBufferExtended(scan->rs_rd,MAIN_FORKNUM,
1083-
blockno,RBM_NORMAL,bstrategy);
1079+
hscan->rs_cbuf=read_stream_next_buffer(stream,NULL);
1080+
if (!BufferIsValid(hscan->rs_cbuf))
1081+
return false;
1082+
10841083
LockBuffer(hscan->rs_cbuf,BUFFER_LOCK_SHARE);
1084+
1085+
hscan->rs_cblock=BufferGetBlockNumber(hscan->rs_cbuf);
1086+
hscan->rs_cindex=FirstOffsetNumber;
1087+
return true;
10851088
}
10861089

10871090
/*

‎src/backend/commands/analyze.c

Lines changed: 25 additions & 60 deletions
Original file line numberDiff line numberDiff line change
@@ -1102,6 +1102,20 @@ examine_attribute(Relation onerel, int attnum, Node *index_expr)
11021102
returnstats;
11031103
}
11041104

1105+
/*
1106+
* Read stream callback returning the next BlockNumber as chosen by the
1107+
* BlockSampling algorithm.
1108+
*/
1109+
staticBlockNumber
1110+
block_sampling_read_stream_next(ReadStream*stream,
1111+
void*callback_private_data,
1112+
void*per_buffer_data)
1113+
{
1114+
BlockSamplerData*bs=callback_private_data;
1115+
1116+
returnBlockSampler_HasMore(bs) ?BlockSampler_Next(bs) :InvalidBlockNumber;
1117+
}
1118+
11051119
/*
11061120
* acquire_sample_rows -- acquire a random sample of rows from the heap
11071121
*
@@ -1154,10 +1168,7 @@ acquire_sample_rows(Relation onerel, int elevel,
11541168
TableScanDescscan;
11551169
BlockNumbernblocks;
11561170
BlockNumberblksdone=0;
1157-
#ifdefUSE_PREFETCH
1158-
intprefetch_maximum=0;/* blocks to prefetch if enabled */
1159-
BlockSamplerDataprefetch_bs;
1160-
#endif
1171+
ReadStream*stream;
11611172

11621173
Assert(targrows>0);
11631174

@@ -1170,13 +1181,6 @@ acquire_sample_rows(Relation onerel, int elevel,
11701181
randseed=pg_prng_uint32(&pg_global_prng_state);
11711182
nblocks=BlockSampler_Init(&bs,totalblocks,targrows,randseed);
11721183

1173-
#ifdefUSE_PREFETCH
1174-
prefetch_maximum=get_tablespace_maintenance_io_concurrency(onerel->rd_rel->reltablespace);
1175-
/* Create another BlockSampler, using the same seed, for prefetching */
1176-
if (prefetch_maximum)
1177-
(void)BlockSampler_Init(&prefetch_bs,totalblocks,targrows,randseed);
1178-
#endif
1179-
11801184
/* Report sampling block numbers */
11811185
pgstat_progress_update_param(PROGRESS_ANALYZE_BLOCKS_TOTAL,
11821186
nblocks);
@@ -1187,60 +1191,19 @@ acquire_sample_rows(Relation onerel, int elevel,
11871191
scan=heap_beginscan(onerel,NULL,0,NULL,NULL,SO_TYPE_ANALYZE);
11881192
slot=table_slot_create(onerel,NULL);
11891193

1190-
#ifdefUSE_PREFETCH
1191-
1192-
/*
1193-
* If we are doing prefetching, then go ahead and tell the kernel about
1194-
* the first set of pages we are going to want. This also moves our
1195-
* iterator out ahead of the main one being used, where we will keep it so
1196-
* that we're always pre-fetching out prefetch_maximum number of blocks
1197-
* ahead.
1198-
*/
1199-
if (prefetch_maximum)
1200-
{
1201-
for (inti=0;i<prefetch_maximum;i++)
1202-
{
1203-
BlockNumberprefetch_block;
1204-
1205-
if (!BlockSampler_HasMore(&prefetch_bs))
1206-
break;
1207-
1208-
prefetch_block=BlockSampler_Next(&prefetch_bs);
1209-
PrefetchBuffer(scan->rs_rd,MAIN_FORKNUM,prefetch_block);
1210-
}
1211-
}
1212-
#endif
1194+
stream=read_stream_begin_relation(READ_STREAM_MAINTENANCE,
1195+
vac_strategy,
1196+
scan->rs_rd,
1197+
MAIN_FORKNUM,
1198+
block_sampling_read_stream_next,
1199+
&bs,
1200+
0);
12131201

12141202
/* Outer loop over blocks to sample */
1215-
while (BlockSampler_HasMore(&bs))
1203+
while (heapam_scan_analyze_next_block(scan,stream))
12161204
{
1217-
BlockNumbertargblock=BlockSampler_Next(&bs);
1218-
#ifdefUSE_PREFETCH
1219-
BlockNumberprefetch_targblock=InvalidBlockNumber;
1220-
1221-
/*
1222-
* Make sure that every time the main BlockSampler is moved forward
1223-
* that our prefetch BlockSampler also gets moved forward, so that we
1224-
* always stay out ahead.
1225-
*/
1226-
if (prefetch_maximum&&BlockSampler_HasMore(&prefetch_bs))
1227-
prefetch_targblock=BlockSampler_Next(&prefetch_bs);
1228-
#endif
1229-
12301205
vacuum_delay_point();
12311206

1232-
heapam_scan_analyze_next_block(scan,targblock,vac_strategy);
1233-
1234-
#ifdefUSE_PREFETCH
1235-
1236-
/*
1237-
* When pre-fetching, after we get a block, tell the kernel about the
1238-
* next one we will want, if there's any left.
1239-
*/
1240-
if (prefetch_maximum&&prefetch_targblock!=InvalidBlockNumber)
1241-
PrefetchBuffer(scan->rs_rd,MAIN_FORKNUM,prefetch_targblock);
1242-
#endif
1243-
12441207
while (heapam_scan_analyze_next_tuple(scan,OldestXmin,&liverows,&deadrows,slot))
12451208
{
12461209
/*
@@ -1290,6 +1253,8 @@ acquire_sample_rows(Relation onerel, int elevel,
12901253
++blksdone);
12911254
}
12921255

1256+
read_stream_end(stream);
1257+
12931258
ExecDropSingleTupleTableSlot(slot);
12941259
heap_endscan(scan);
12951260

‎src/include/access/heapam.h

Lines changed: 2 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -413,9 +413,8 @@ extern bool HeapTupleIsSurelyDead(HeapTuple htup,
413413
structGlobalVisState*vistest);
414414

415415
/* in heap/heapam_handler.c*/
416-
externvoidheapam_scan_analyze_next_block(TableScanDescscan,
417-
BlockNumberblockno,
418-
BufferAccessStrategybstrategy);
416+
externboolheapam_scan_analyze_next_block(TableScanDescscan,
417+
ReadStream*stream);
419418
externboolheapam_scan_analyze_next_tuple(TableScanDescscan,
420419
TransactionIdOldestXmin,
421420
double*liverows,double*deadrows,

0 commit comments

Comments
 (0)

[8]ページ先頭

©2009-2025 Movatter.jp