aboutsummaryrefslogtreecommitdiff
path: root/src/backend/access/transam/xlog.c
diff options
context:
space:
mode:
Diffstat (limited to 'src/backend/access/transam/xlog.c')
-rw-r--r--src/backend/access/transam/xlog.c33
1 files changed, 33 insertions, 0 deletions
diff --git a/src/backend/access/transam/xlog.c b/src/backend/access/transam/xlog.c
index 473a9c5c2f8..f86f4b5c4b7 100644
--- a/src/backend/access/transam/xlog.c
+++ b/src/backend/access/transam/xlog.c
@@ -498,6 +498,11 @@ typedef struct XLogCtlData
* If we create a new timeline when the system was started up,
* PrevTimeLineID is the old timeline's ID that we forked off from.
* Otherwise it's equal to InsertTimeLineID.
+ *
+ * We set these fields while holding info_lck. Most that reads these
+ * values knows that recovery is no longer in progress and so can safely
+ * read the value without a lock, but code that could be run either during
+ * or after recovery can take info_lck while reading these values.
*/
TimeLineID InsertTimeLineID;
TimeLineID PrevTimeLineID;
@@ -5315,6 +5320,13 @@ CleanupAfterArchiveRecovery(TimeLineID EndOfLogTLI, XLogRecPtr EndOfLog,
char partialfname[MAXFNAMELEN];
char partialpath[MAXPGPATH];
+ /*
+ * If we're summarizing WAL, we can't rename the partial file
+ * until the summarizer finishes with it, else it will fail.
+ */
+ if (summarize_wal)
+ WaitForWalSummarization(EndOfLog);
+
XLogFilePath(origpath, EndOfLogTLI, endLogSegNo, wal_segment_size);
snprintf(partialfname, MAXFNAMELEN, "%s.partial", origfname);
snprintf(partialpath, MAXPGPATH, "%s.partial", origpath);
@@ -5945,8 +5957,10 @@ StartupXLOG(void)
}
/* Save the selected TimeLineID in shared memory, too */
+ SpinLockAcquire(&XLogCtl->info_lck);
XLogCtl->InsertTimeLineID = newTLI;
XLogCtl->PrevTimeLineID = endOfRecoveryInfo->lastRecTLI;
+ SpinLockRelease(&XLogCtl->info_lck);
/*
* Actually, if WAL ended in an incomplete record, skip the parts that
@@ -6482,6 +6496,25 @@ GetWALInsertionTimeLine(void)
}
/*
+ * GetWALInsertionTimeLineIfSet -- If the system is not in recovery, returns
+ * the WAL insertion timeline; else, returns 0. Wherever possible, use
+ * GetWALInsertionTimeLine() instead, since it's cheaper. Note that this
+ * function decides recovery has ended as soon as the insert TLI is set, which
+ * happens before we set XLogCtl->SharedRecoveryState to RECOVERY_STATE_DONE.
+ */
+TimeLineID
+GetWALInsertionTimeLineIfSet(void)
+{
+ TimeLineID insertTLI;
+
+ SpinLockAcquire(&XLogCtl->info_lck);
+ insertTLI = XLogCtl->InsertTimeLineID;
+ SpinLockRelease(&XLogCtl->info_lck);
+
+ return insertTLI;
+}
+
+/*
* GetLastImportantRecPtr -- Returns the LSN of the last important record
* inserted. All records not explicitly marked as unimportant are considered
* important.