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

Commitebcbc8c

Browse files
committed
Avoid changing an index's indcheckxmin horizon during REINDEX.
There can never be a need to push the indcheckxmin horizon forward, sinceany HOT chains that are actually broken with respect to the index mustpre-date its original creation. So we can just avoid changing pg_indexaltogether during a REINDEX operation.This offers a cleaner solution than my previous patch for the problemfound a few days ago that we mustn't try to update pg_index while we arereindexing it. System catalog indexes will always be created withindcheckxmin = false during initdb, and with this modified code we shouldnever try to change their pg_index entries. This avoids special-casingsystem catalogs as the former patch did, and should provide a performancebenefit for many cases where REINDEX formerly caused an index to beconsidered unusable for a short time.Back-patch to 8.3 to cover all versions containing HOT. Note that thispatch changes the API for index_build(), but I believe it is unlikely thatany add-on code is calling that directly.
1 parent1da9966 commitebcbc8c

File tree

6 files changed

+42
-11
lines changed

6 files changed

+42
-11
lines changed

‎src/backend/bootstrap/bootstrap.c

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1127,7 +1127,7 @@ build_indices(void)
11271127
heap=heap_open(ILHead->il_heap,NoLock);
11281128
ind=index_open(ILHead->il_ind,NoLock);
11291129

1130-
index_build(heap,ind,ILHead->il_info, false);
1130+
index_build(heap,ind,ILHead->il_info, false, false);
11311131

11321132
index_close(ind,NoLock);
11331133
heap_close(heap,NoLock);

‎src/backend/catalog/heap.c

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2451,7 +2451,7 @@ RelationTruncateIndexes(Relation heapRelation)
24512451

24522452
/* Initialize the index and rebuild */
24532453
/* Note: we do not need to re-establish pkey setting */
2454-
index_build(heapRelation,currentIndex,indexInfo, false);
2454+
index_build(heapRelation,currentIndex,indexInfo, false, true);
24552455

24562456
/* We're done with this index */
24572457
index_close(currentIndex,NoLock);

‎src/backend/catalog/index.c

Lines changed: 31 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -957,7 +957,7 @@ index_create(Oid heapRelationId,
957957
}
958958
else
959959
{
960-
index_build(heapRelation,indexRelation,indexInfo,isprimary);
960+
index_build(heapRelation,indexRelation,indexInfo,isprimary, false);
961961
}
962962

963963
/*
@@ -1389,8 +1389,11 @@ index_update_stats(Relation rel,
13891389
* entries of the index and heap relation as needed, using statistics
13901390
* returned by ambuild as well as data passed by the caller.
13911391
*
1392-
* Note: when reindexing an existing index, isprimary can be false;
1393-
* the index is already properly marked and need not be re-marked.
1392+
* isprimary tells whether to mark the index as a primary-key index.
1393+
* isreindex indicates we are recreating a previously-existing index.
1394+
*
1395+
* Note: when reindexing an existing index, isprimary can be false even if
1396+
* the index is a PK; it's already properly marked and need not be re-marked.
13941397
*
13951398
* Note: before Postgres 8.2, the passed-in heap and index Relations
13961399
* were automatically closed by this routine. This is no longer the case.
@@ -1400,7 +1403,8 @@ void
14001403
index_build(RelationheapRelation,
14011404
RelationindexRelation,
14021405
IndexInfo*indexInfo,
1403-
boolisprimary)
1406+
boolisprimary,
1407+
boolisreindex)
14041408
{
14051409
RegProcedureprocedure;
14061410
IndexBuildResult*stats;
@@ -1454,8 +1458,15 @@ index_build(Relation heapRelation,
14541458
* If we found any potentially broken HOT chains, mark the index as not
14551459
* being usable until the current transaction is below the event horizon.
14561460
* See src/backend/access/heap/README.HOT for discussion.
1457-
*/
1458-
if (indexInfo->ii_BrokenHotChain)
1461+
*
1462+
* However, when reindexing an existing index, we should do nothing here.
1463+
* Any HOT chains that are broken with respect to the index must predate
1464+
* the index's original creation, so there is no need to change the
1465+
* index's usability horizon. Moreover, we *must not* try to change
1466+
* the index's pg_index entry while reindexing pg_index itself, and this
1467+
* optimization nicely prevents that.
1468+
*/
1469+
if (indexInfo->ii_BrokenHotChain&& !isreindex)
14591470
{
14601471
OidindexId=RelationGetRelid(indexRelation);
14611472
Relationpg_index;
@@ -1470,6 +1481,9 @@ index_build(Relation heapRelation,
14701481
elog(ERROR,"cache lookup failed for index %u",indexId);
14711482
indexForm= (Form_pg_index)GETSTRUCT(indexTuple);
14721483

1484+
/* If it's a new index, indcheckxmin shouldn't be set ... */
1485+
Assert(!indexForm->indcheckxmin);
1486+
14731487
indexForm->indcheckxmin= true;
14741488
simple_heap_update(pg_index,&indexTuple->t_self,indexTuple);
14751489
CatalogUpdateIndexes(pg_index,indexTuple);
@@ -2461,7 +2475,7 @@ reindex_index(Oid indexId, bool skip_constraint_checks)
24612475

24622476
/* Initialize the index and rebuild */
24632477
/* Note: we do not need to re-establish pkey setting */
2464-
index_build(heapRelation,iRel,indexInfo, false);
2478+
index_build(heapRelation,iRel,indexInfo, false, true);
24652479
}
24662480
PG_CATCH();
24672481
{
@@ -2481,6 +2495,16 @@ reindex_index(Oid indexId, bool skip_constraint_checks)
24812495
* We can also reset indcheckxmin, because we have now done a
24822496
* non-concurrent index build, *except* in the case where index_build
24832497
* found some still-broken HOT chains.
2498+
*
2499+
* Note that it is important to not update the pg_index entry if we don't
2500+
* have to, because updating it will move the index's usability horizon
2501+
* (recorded as the tuple's xmin value) if indcheckxmin is true. We don't
2502+
* really want REINDEX to move the usability horizon forward ever, but we
2503+
* have no choice if we are to fix indisvalid or indisready. Of course,
2504+
* clearing indcheckxmin eliminates the issue, so we're happy to do that
2505+
* if we can. Another reason for caution here is that while reindexing
2506+
* pg_index itself, we must not try to update it. We assume that
2507+
* pg_index's indexes will always have these flags in their clean state.
24842508
*/
24852509
if (!skipped_constraint)
24862510
{

‎src/backend/commands/cluster.c

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1360,6 +1360,12 @@ finish_heap_swap(Oid OIDOldHeap, Oid OIDNewHeap,
13601360
* advantage to the other order anyway because this is all transactional,
13611361
* so no chance to reclaim disk space before commit. We do not need a
13621362
* final CommandCounterIncrement() because reindex_relation does it.
1363+
*
1364+
* Note: because index_build is called via reindex_relation, it will never
1365+
* set indcheckxmin true for the indexes. This is OK even though in some
1366+
* sense we are building new indexes rather than rebuilding existing ones,
1367+
* because the new heap won't contain any HOT chains at all, let alone
1368+
* broken ones, so it can't be necessary to set indcheckxmin.
13631369
*/
13641370
reindex_flags=REINDEX_SUPPRESS_INDEX_USE;
13651371
if (check_constraints)

‎src/backend/commands/indexcmds.c

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -584,7 +584,7 @@ DefineIndex(RangeVar *heapRelation,
584584
indexInfo->ii_BrokenHotChain= false;
585585

586586
/* Now build the index */
587-
index_build(rel,indexRelation,indexInfo,primary);
587+
index_build(rel,indexRelation,indexInfo,primary, false);
588588

589589
/* Close both the relations, but keep the locks */
590590
heap_close(rel,NoLock);

‎src/include/catalog/index.h

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -59,7 +59,8 @@ extern void FormIndexDatum(IndexInfo *indexInfo,
5959
externvoidindex_build(RelationheapRelation,
6060
RelationindexRelation,
6161
IndexInfo*indexInfo,
62-
boolisprimary);
62+
boolisprimary,
63+
boolisreindex);
6364

6465
externdoubleIndexBuildHeapScan(RelationheapRelation,
6566
RelationindexRelation,

0 commit comments

Comments
 (0)

[8]ページ先頭

©2009-2025 Movatter.jp