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

Commit40d3e92

Browse files
committed
index_destroy() must grab exclusive access to the parent table
of the index it wants to destroy. This ensures that no other backend isactively scanning or updating that index. Getting exclusive access onthe index alone is NOT sufficient, because the executor is rathercavalier about getting locks on indexes --- see ExecOpenIndices().It might be better to grab index locks in the executor, but I'm notsure the extra lockmanager traffic is really worth it just to makeindex_destroy cleaner.
1 parent3047b44 commit40d3e92

File tree

1 file changed

+51
-13
lines changed

1 file changed

+51
-13
lines changed

‎src/backend/catalog/index.c

Lines changed: 51 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,7 @@
77
*
88
*
99
* IDENTIFICATION
10-
* $Header: /cvsroot/pgsql/src/backend/catalog/index.c,v 1.95 1999/11/16 04:13:55 momjian Exp $
10+
* $Header: /cvsroot/pgsql/src/backend/catalog/index.c,v 1.96 1999/11/21 20:01:10 tgl Exp $
1111
*
1212
*
1313
* INTERFACE ROUTINES
@@ -72,6 +72,7 @@ static void DefaultBuild(Relation heapRelation, Relation indexRelation,
7272
intnumberOfAttributes,AttrNumber*attributeNumber,
7373
IndexStrategyindexStrategy,uint16parameterCount,
7474
Datum*parameter,FuncIndexInfoPtrfuncInfo,PredInfo*predInfo);
75+
staticOidIndexGetRelation(OidindexId);
7576

7677
/* ----------------------------------------------------------------
7778
* sysatts is a structure containing attribute tuple forms
@@ -1109,7 +1110,8 @@ index_create(char *heapRelationName,
11091110
void
11101111
index_destroy(OidindexId)
11111112
{
1112-
RelationuserindexRelation;
1113+
RelationuserHeapRelation;
1114+
RelationuserIndexRelation;
11131115
RelationindexRelation;
11141116
RelationrelationRelation;
11151117
RelationattributeRelation;
@@ -1118,12 +1120,21 @@ index_destroy(Oid indexId)
11181120

11191121
Assert(OidIsValid(indexId));
11201122

1121-
userindexRelation=index_open(indexId);
1122-
1123-
/*
1124-
* Get exclusive lock to ensure no one else is scanning this index.
1123+
/* ----------------
1124+
*To drop an index safely, we must grab exclusive lock on its parent
1125+
*table; otherwise there could be other backends using the index!
1126+
*Exclusive lock on the index alone is insufficient because the index
1127+
*access routines are a little slipshod about obtaining adequate locking
1128+
*(see ExecOpenIndices()). We do grab exclusive lock on the index too,
1129+
*just to be safe. Both locks must be held till end of transaction,
1130+
*else other backends will still see this index in pg_index.
1131+
* ----------------
11251132
*/
1126-
LockRelation(userindexRelation,AccessExclusiveLock);
1133+
userHeapRelation=heap_open(IndexGetRelation(indexId),
1134+
AccessExclusiveLock);
1135+
1136+
userIndexRelation=index_open(indexId);
1137+
LockRelation(userIndexRelation,AccessExclusiveLock);
11271138

11281139
/* ----------------
11291140
*DROP INDEX within a transaction block is dangerous, because
@@ -1137,14 +1148,13 @@ index_destroy(Oid indexId)
11371148
*they don't exist anyway. So, no warning in that case.
11381149
* ----------------
11391150
*/
1140-
if (IsTransactionBlock()&& !userindexRelation->rd_myxactonly)
1151+
if (IsTransactionBlock()&& !userIndexRelation->rd_myxactonly)
11411152
elog(NOTICE,"Caution: DROP INDEX cannot be rolled back, so don't abort now");
11421153

11431154
/* ----------------
11441155
* fix DESCRIPTION relation
11451156
* ----------------
11461157
*/
1147-
11481158
DeleteComments(indexId);
11491159

11501160
/* ----------------
@@ -1198,14 +1208,18 @@ index_destroy(Oid indexId)
11981208
heap_close(indexRelation,RowExclusiveLock);
11991209

12001210
/*
1201-
* flush cache and physically remove the file
1211+
* flushbuffercache and physically remove the file
12021212
*/
1203-
ReleaseRelationBuffers(userindexRelation);
1213+
ReleaseRelationBuffers(userIndexRelation);
12041214

1205-
if (smgrunlink(DEFAULT_SMGR,userindexRelation)!=SM_SUCCESS)
1215+
if (smgrunlink(DEFAULT_SMGR,userIndexRelation)!=SM_SUCCESS)
12061216
elog(ERROR,"index_destroy: unlink: %m");
12071217

1208-
index_close(userindexRelation);
1218+
/*
1219+
* Close rels, but keep locks
1220+
*/
1221+
index_close(userIndexRelation);
1222+
heap_close(userHeapRelation,NoLock);
12091223

12101224
RelationForgetRelation(indexId);
12111225

@@ -1720,6 +1734,30 @@ index_build(Relation heapRelation,
17201734
predInfo);
17211735
}
17221736

1737+
/*
1738+
* IndexGetRelation: given an index's relation OID, get the OID of the
1739+
* relation it is an index on. Uses the system cache.
1740+
*/
1741+
staticOid
1742+
IndexGetRelation(OidindexId)
1743+
{
1744+
HeapTupletuple;
1745+
Form_pg_indexindex;
1746+
1747+
tuple=SearchSysCacheTuple(INDEXRELID,
1748+
ObjectIdGetDatum(indexId),
1749+
0,0,0);
1750+
if (!HeapTupleIsValid(tuple))
1751+
{
1752+
elog(ERROR,"IndexGetRelation: can't find index id %u",
1753+
indexId);
1754+
}
1755+
index= (Form_pg_index)GETSTRUCT(tuple);
1756+
Assert(index->indexrelid==indexId);
1757+
1758+
returnindex->indrelid;
1759+
}
1760+
17231761
/*
17241762
* IndexIsUnique: given an index's relation OID, see if it
17251763
* is unique using the system cache.

0 commit comments

Comments
 (0)

[8]ページ先頭

©2009-2025 Movatter.jp