Commit bb76134b authored by Peter Eisentraut's avatar Peter Eisentraut

Fix incorrect code in new REINDEX CONCURRENTLY code

The previous code was adding pointers to transient variables to a
list, but by the time the list was read, the variable might be gone,
depending on the compiler.  Fix it by making copies in the proper
memory context.
parent 5dc92b84
...@@ -2813,7 +2813,7 @@ ReindexRelationConcurrently(Oid relationOid, int options) ...@@ -2813,7 +2813,7 @@ ReindexRelationConcurrently(Oid relationOid, int options)
Relation indexRel; Relation indexRel;
Relation heapRel; Relation heapRel;
Relation newIndexRel; Relation newIndexRel;
LockRelId lockrelid; LockRelId *lockrelid;
indexRel = index_open(indexId, ShareUpdateExclusiveLock); indexRel = index_open(indexId, ShareUpdateExclusiveLock);
heapRel = table_open(indexRel->rd_index->indrelid, heapRel = table_open(indexRel->rd_index->indrelid,
...@@ -2847,10 +2847,12 @@ ReindexRelationConcurrently(Oid relationOid, int options) ...@@ -2847,10 +2847,12 @@ ReindexRelationConcurrently(Oid relationOid, int options)
* avoid multiple locks taken on the same relation, instead we rely on * avoid multiple locks taken on the same relation, instead we rely on
* parentRelationIds built earlier. * parentRelationIds built earlier.
*/ */
lockrelid = indexRel->rd_lockInfo.lockRelId; lockrelid = palloc(sizeof(*lockrelid));
relationLocks = lappend(relationLocks, &lockrelid); *lockrelid = indexRel->rd_lockInfo.lockRelId;
lockrelid = newIndexRel->rd_lockInfo.lockRelId; relationLocks = lappend(relationLocks, lockrelid);
relationLocks = lappend(relationLocks, &lockrelid); lockrelid = palloc(sizeof(*lockrelid));
*lockrelid = newIndexRel->rd_lockInfo.lockRelId;
relationLocks = lappend(relationLocks, lockrelid);
MemoryContextSwitchTo(oldcontext); MemoryContextSwitchTo(oldcontext);
...@@ -2866,19 +2868,21 @@ ReindexRelationConcurrently(Oid relationOid, int options) ...@@ -2866,19 +2868,21 @@ ReindexRelationConcurrently(Oid relationOid, int options)
foreach(lc, heapRelationIds) foreach(lc, heapRelationIds)
{ {
Relation heapRelation = table_open(lfirst_oid(lc), ShareUpdateExclusiveLock); Relation heapRelation = table_open(lfirst_oid(lc), ShareUpdateExclusiveLock);
LockRelId lockrelid = heapRelation->rd_lockInfo.lockRelId; LockRelId *lockrelid;
LOCKTAG *heaplocktag; LOCKTAG *heaplocktag;
/* Save the list of locks in private context */ /* Save the list of locks in private context */
oldcontext = MemoryContextSwitchTo(private_context); oldcontext = MemoryContextSwitchTo(private_context);
/* Add lockrelid of heap relation to the list of locked relations */ /* Add lockrelid of heap relation to the list of locked relations */
relationLocks = lappend(relationLocks, &lockrelid); lockrelid = palloc(sizeof(*lockrelid));
*lockrelid = heapRelation->rd_lockInfo.lockRelId;
relationLocks = lappend(relationLocks, lockrelid);
heaplocktag = (LOCKTAG *) palloc(sizeof(LOCKTAG)); heaplocktag = (LOCKTAG *) palloc(sizeof(LOCKTAG));
/* Save the LOCKTAG for this parent relation for the wait phase */ /* Save the LOCKTAG for this parent relation for the wait phase */
SET_LOCKTAG_RELATION(*heaplocktag, lockrelid.dbId, lockrelid.relId); SET_LOCKTAG_RELATION(*heaplocktag, lockrelid->dbId, lockrelid->relId);
lockTags = lappend(lockTags, heaplocktag); lockTags = lappend(lockTags, heaplocktag);
MemoryContextSwitchTo(oldcontext); MemoryContextSwitchTo(oldcontext);
...@@ -2890,9 +2894,9 @@ ReindexRelationConcurrently(Oid relationOid, int options) ...@@ -2890,9 +2894,9 @@ ReindexRelationConcurrently(Oid relationOid, int options)
/* Get a session-level lock on each table. */ /* Get a session-level lock on each table. */
foreach(lc, relationLocks) foreach(lc, relationLocks)
{ {
LockRelId lockRel = *((LockRelId *) lfirst(lc)); LockRelId *lockrelid = (LockRelId *) lfirst(lc);
LockRelationIdForSession(&lockRel, ShareUpdateExclusiveLock); LockRelationIdForSession(lockrelid, ShareUpdateExclusiveLock);
} }
PopActiveSnapshot(); PopActiveSnapshot();
...@@ -3127,9 +3131,9 @@ ReindexRelationConcurrently(Oid relationOid, int options) ...@@ -3127,9 +3131,9 @@ ReindexRelationConcurrently(Oid relationOid, int options)
*/ */
foreach(lc, relationLocks) foreach(lc, relationLocks)
{ {
LockRelId lockRel = *((LockRelId *) lfirst(lc)); LockRelId *lockrelid = (LockRelId *) lfirst(lc);
UnlockRelationIdForSession(&lockRel, ShareUpdateExclusiveLock); UnlockRelationIdForSession(lockrelid, ShareUpdateExclusiveLock);
} }
/* Start a new transaction to finish process properly */ /* Start a new transaction to finish process properly */
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment