* position known to be fsync'd to disk.
*/
XLogRecPtr
-GetFlushRecPtr(void)
+GetFlushRecPtr(TimeLineID *insertTLI)
{
SpinLockAcquire(&XLogCtl->info_lck);
LogwrtResult = XLogCtl->LogwrtResult;
SpinLockRelease(&XLogCtl->info_lck);
+ /*
+ * If we're writing and flushing WAL, the time line can't be changing,
+ * so no lock is required.
+ */
+ if (insertTLI)
+ *insertTLI = XLogCtl->ThisTimeLineID;
+
return LogwrtResult.Flush;
}
+/*
+ * GetWALInsertionTimeLine -- Returns the current timeline of a system that
+ * is not in recovery.
+ */
+TimeLineID
+GetWALInsertionTimeLine(void)
+{
+ Assert(XLogCtl->SharedRecoveryState == RECOVERY_STATE_DONE);
+
+ /* Since the value can't be changing, no lock is required. */
+ return XLogCtl->ThisTimeLineID;
+}
+
/*
* GetLastImportantRecPtr -- Returns the LSN of the last important record
* inserted. All records not explicitly marked as unimportant are considered
errmsg("recovery is in progress"),
errhint("WAL control functions cannot be executed during recovery.")));
- current_recptr = GetFlushRecPtr();
+ current_recptr = GetFlushRecPtr(NULL);
PG_RETURN_LSN(current_recptr);
}
/*
* Determine the limit of xlog we can currently read to, and what the
* most recent timeline is.
- *
- * RecoveryInProgress() will update ThisTimeLineID when it first
- * notices recovery finishes, so we only have to maintain it for the
- * local process until recovery ends.
*/
if (!RecoveryInProgress())
- read_upto = GetFlushRecPtr();
+ read_upto = GetFlushRecPtr(&ThisTimeLineID);
else
read_upto = GetXLogReplayRecPtr(&ThisTimeLineID);
tli = ThisTimeLineID;
* Compute the current end-of-wal.
*/
if (!RecoveryInProgress())
- end_of_wal = GetFlushRecPtr();
+ end_of_wal = GetFlushRecPtr(NULL);
else
end_of_wal = GetXLogReplayRecPtr(NULL);
bool *have_pending_txes)
{
dlist_mutable_iter iter;
- XLogRecPtr local_flush = GetFlushRecPtr();
+ XLogRecPtr local_flush = GetFlushRecPtr(NULL);
*write = InvalidXLogRecPtr;
*flush = InvalidXLogRecPtr;
* target position accordingly.
*/
if (!RecoveryInProgress())
- moveto = Min(moveto, GetFlushRecPtr());
+ moveto = Min(moveto, GetFlushRecPtr(NULL));
else
moveto = Min(moveto, GetXLogReplayRecPtr(NULL));
logptr = GetStandbyFlushRecPtr();
}
else
- logptr = GetFlushRecPtr();
+ logptr = GetFlushRecPtr(&ThisTimeLineID);
snprintf(xloc, sizeof(xloc), "%X/%X", LSN_FORMAT_ARGS(logptr));
FlushPtr = GetStandbyFlushRecPtr();
}
else
- FlushPtr = GetFlushRecPtr();
+ FlushPtr = GetFlushRecPtr(&ThisTimeLineID);
if (cmd->timeline != 0)
{
/* Get a more recent flush pointer. */
if (!RecoveryInProgress())
- RecentFlushPtr = GetFlushRecPtr();
+ RecentFlushPtr = GetFlushRecPtr(NULL);
else
RecentFlushPtr = GetXLogReplayRecPtr(NULL);
/* Update our idea of the currently flushed position. */
if (!RecoveryInProgress())
- RecentFlushPtr = GetFlushRecPtr();
+ RecentFlushPtr = GetFlushRecPtr(NULL);
else
RecentFlushPtr = GetXLogReplayRecPtr(NULL);
* primary: if the primary subsequently crashes and restarts, standbys
* must not have applied any WAL that got lost on the primary.
*/
- SendRqstPtr = GetFlushRecPtr();
+ SendRqstPtr = GetFlushRecPtr(NULL);
}
/*
* we only need to update flushPtr if EndRecPtr is past it.
*/
if (flushPtr == InvalidXLogRecPtr)
- flushPtr = GetFlushRecPtr();
+ flushPtr = GetFlushRecPtr(NULL);
else if (logical_decoding_ctx->reader->EndRecPtr >= flushPtr)
- flushPtr = GetFlushRecPtr();
+ flushPtr = GetFlushRecPtr(NULL);
/* If EndRecPtr is still past our flushPtr, it means we caught up. */
if (logical_decoding_ctx->reader->EndRecPtr >= flushPtr)
extern void GetFullPageWriteInfo(XLogRecPtr *RedoRecPtr_p, bool *doPageWrites_p);
extern XLogRecPtr GetRedoRecPtr(void);
extern XLogRecPtr GetInsertRecPtr(void);
-extern XLogRecPtr GetFlushRecPtr(void);
+extern XLogRecPtr GetFlushRecPtr(TimeLineID *insertTLI);
+extern TimeLineID GetWALInsertionTimeLine(void);
extern XLogRecPtr GetLastImportantRecPtr(void);
extern void RemovePromoteSignalFiles(void);