aboutsummaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorSimon Riggs <simon@2ndQuadrant.com>2012-03-29 14:57:08 +0100
committerSimon Riggs <simon@2ndQuadrant.com>2012-03-29 14:57:08 +0100
commit20d98ab6e4110087d1816cd105a40fcc8ce0a307 (patch)
treea4cda4221136ce505035a66dbb2177ac782452e0 /src
parent4d278b785e22ff8d56ac86d5ed1871e096b2ea80 (diff)
downloadpostgresql-20d98ab6e4110087d1816cd105a40fcc8ce0a307.tar.gz
postgresql-20d98ab6e4110087d1816cd105a40fcc8ce0a307.zip
Correct epoch of txid_current() when executed on a Hot Standby server.
Initialise ckptXidEpoch from starting checkpoint and maintain the correct value as we roll forwards. This allows GetNextXidAndEpoch() to return the correct epoch when executed during recovery. Backpatch to 9.0 when the problem is first observable by a user. Bug report from Daniel Farina
Diffstat (limited to 'src')
-rw-r--r--src/backend/access/transam/xlog.c30
1 files changed, 26 insertions, 4 deletions
diff --git a/src/backend/access/transam/xlog.c b/src/backend/access/transam/xlog.c
index 49cccaed9c7..f0db58fb6e8 100644
--- a/src/backend/access/transam/xlog.c
+++ b/src/backend/access/transam/xlog.c
@@ -6331,6 +6331,10 @@ StartupXLOG(void)
/* No need to hold ControlFileLock yet, we aren't up far enough */
UpdateControlFile();
+ /* initialize shared-memory copy of latest checkpoint XID/epoch */
+ XLogCtl->ckptXidEpoch = ControlFile->checkPointCopy.nextXidEpoch;
+ XLogCtl->ckptXid = ControlFile->checkPointCopy.nextXid;
+
/* initialize our local copy of minRecoveryPoint */
minRecoveryPoint = ControlFile->minRecoveryPoint;
@@ -6875,10 +6879,6 @@ StartupXLOG(void)
/* start the archive_timeout timer running */
XLogCtl->Write.lastSegSwitchTime = (pg_time_t) time(NULL);
- /* initialize shared-memory copy of latest checkpoint XID/epoch */
- XLogCtl->ckptXidEpoch = ControlFile->checkPointCopy.nextXidEpoch;
- XLogCtl->ckptXid = ControlFile->checkPointCopy.nextXid;
-
/* also initialize latestCompletedXid, to nextXid - 1 */
ShmemVariableCache->latestCompletedXid = ShmemVariableCache->nextXid;
TransactionIdRetreat(ShmemVariableCache->latestCompletedXid);
@@ -8461,6 +8461,17 @@ xlog_redo(XLogRecPtr lsn, XLogRecord *record)
ControlFile->checkPointCopy.nextXidEpoch = checkPoint.nextXidEpoch;
ControlFile->checkPointCopy.nextXid = checkPoint.nextXid;
+ /* Update shared-memory copy of checkpoint XID/epoch */
+ {
+ /* use volatile pointer to prevent code rearrangement */
+ volatile XLogCtlData *xlogctl = XLogCtl;
+
+ SpinLockAcquire(&xlogctl->info_lck);
+ xlogctl->ckptXidEpoch = checkPoint.nextXidEpoch;
+ xlogctl->ckptXid = checkPoint.nextXid;
+ SpinLockRelease(&xlogctl->info_lck);
+ }
+
/*
* TLI may change in a shutdown checkpoint, but it shouldn't decrease
*/
@@ -8501,6 +8512,17 @@ xlog_redo(XLogRecPtr lsn, XLogRecord *record)
ControlFile->checkPointCopy.nextXidEpoch = checkPoint.nextXidEpoch;
ControlFile->checkPointCopy.nextXid = checkPoint.nextXid;
+ /* Update shared-memory copy of checkpoint XID/epoch */
+ {
+ /* use volatile pointer to prevent code rearrangement */
+ volatile XLogCtlData *xlogctl = XLogCtl;
+
+ SpinLockAcquire(&xlogctl->info_lck);
+ xlogctl->ckptXidEpoch = checkPoint.nextXidEpoch;
+ xlogctl->ckptXid = checkPoint.nextXid;
+ SpinLockRelease(&xlogctl->info_lck);
+ }
+
/* TLI should not change in an on-line checkpoint */
if (checkPoint.ThisTimeLineID != ThisTimeLineID)
ereport(PANIC,