>From 126bb729d236dc943379bf37b8ce1f764d736542 Mon Sep 17 00:00:00 2001 From: Manu Date: Mon, 21 Sep 2026 20:53:25 -0300 Subject: [PATCH v2 2/6] Reset the index build progress counters for every index build Index AMs report their subphase, tuple counts and scan block counts whether or not index_build() was asked to report progress, but index_build() only reset those counters when it was. When one command builds several indexes without progress for each of them, as REPACK and VACUUM FULL do when rebuilding a table's indexes, or CREATE INDEX does for the partitions of a partitioned table, each build started from the counts left by the previous one: tuples_done could be above the new tuples_total until the AM got to its first update. Reset those counters in every build. They are the parameters whose numbers were chosen not to collide with those of the commands that build indexes, so writing them under another command is fine. The phase is still only set when progress is reported, since REPACK uses that number for index_rebuild_count. Found with the PROGRESS_DEBUG tracing proposed in the same thread. Oversight in caec9d9fadf, which made the whole reset conditional. --- src/backend/catalog/index.c | 23 ++++++++++++++++------- 1 file changed, 16 insertions(+), 7 deletions(-) diff --git a/src/backend/catalog/index.c b/src/backend/catalog/index.c index 2a46cc4de19..09e716fadd2 100644 --- a/src/backend/catalog/index.c +++ b/src/backend/catalog/index.c @@ -3175,24 +3175,33 @@ index_build(Relation heapRelation, save_nestlevel = NewGUCNestLevel(); RestrictSearchPath(); - /* Set up initial progress report status */ - if (progress) + /* + * Set up initial progress report status. + * + * Index AMs report their subphase, tuple and block counts whether or not + * the caller asked for progress, so reset those in any case: otherwise + * they would start from the values left by an earlier index build of the + * same command. Their parameter numbers are reserved so as not to + * collide with those of the commands that build indexes. The phase is + * only set when progress is reported. + */ { const int progress_index[] = { - PROGRESS_CREATEIDX_PHASE, PROGRESS_CREATEIDX_SUBPHASE, PROGRESS_CREATEIDX_TUPLES_DONE, PROGRESS_CREATEIDX_TUPLES_TOTAL, PROGRESS_SCAN_BLOCKS_DONE, - PROGRESS_SCAN_BLOCKS_TOTAL + PROGRESS_SCAN_BLOCKS_TOTAL, + PROGRESS_CREATEIDX_PHASE }; const int64 progress_vals[] = { - PROGRESS_CREATEIDX_PHASE_BUILD, PROGRESS_CREATEIDX_SUBPHASE_INITIALIZE, - 0, 0, 0, 0 + 0, 0, 0, 0, + PROGRESS_CREATEIDX_PHASE_BUILD }; - pgstat_progress_update_multi_param(6, progress_index, progress_vals); + pgstat_progress_update_multi_param(progress ? 6 : 5, + progress_index, progress_vals); } /* -- 2.55.0