PostgreSQL Source Code  git master
xlog.h File Reference
#include "access/rmgr.h"
#include "access/xlogdefs.h"
#include "access/xloginsert.h"
#include "access/xlogreader.h"
#include "datatype/timestamp.h"
#include "lib/stringinfo.h"
#include "nodes/pg_list.h"
#include "storage/fd.h"
Include dependency graph for xlog.h:
This graph shows which files directly or indirectly include this file:

Go to the source code of this file.

Data Structures

struct  CheckpointStatsData
 

Macros

#define SYNC_METHOD_FSYNC   0
 
#define SYNC_METHOD_FDATASYNC   1
 
#define SYNC_METHOD_OPEN   2 /* for O_SYNC */
 
#define SYNC_METHOD_FSYNC_WRITETHROUGH   3
 
#define SYNC_METHOD_OPEN_DSYNC   4 /* for O_DSYNC */
 
#define InHotStandby   (standbyState >= STANDBY_SNAPSHOT_PENDING)
 
#define XLogArchivingActive()   (AssertMacro(XLogArchiveMode == ARCHIVE_MODE_OFF || wal_level >= WAL_LEVEL_REPLICA), XLogArchiveMode > ARCHIVE_MODE_OFF)
 
#define XLogArchivingAlways()   (AssertMacro(XLogArchiveMode == ARCHIVE_MODE_OFF || wal_level >= WAL_LEVEL_REPLICA), XLogArchiveMode == ARCHIVE_MODE_ALWAYS)
 
#define XLogArchiveCommandSet()   (XLogArchiveCommand[0] != '\0')
 
#define XLogIsNeeded()   (wal_level >= WAL_LEVEL_REPLICA)
 
#define XLogHintBitIsNeeded()   (DataChecksumsEnabled() || wal_log_hints)
 
#define XLogStandbyInfoActive()   (wal_level >= WAL_LEVEL_REPLICA)
 
#define XLogLogicalInfoActive()   (wal_level >= WAL_LEVEL_LOGICAL)
 
#define CHECKPOINT_IS_SHUTDOWN   0x0001 /* Checkpoint is for shutdown */
 
#define CHECKPOINT_END_OF_RECOVERY
 
#define CHECKPOINT_IMMEDIATE   0x0004 /* Do it without delays */
 
#define CHECKPOINT_FORCE   0x0008 /* Force even if no activity */
 
#define CHECKPOINT_FLUSH_ALL
 
#define CHECKPOINT_WAIT   0x0020 /* Wait for completion */
 
#define CHECKPOINT_REQUESTED   0x0040 /* Checkpoint request has been made */
 
#define CHECKPOINT_CAUSE_XLOG   0x0080 /* XLOG consumption */
 
#define CHECKPOINT_CAUSE_TIME   0x0100 /* Elapsed time */
 
#define XLOG_INCLUDE_ORIGIN   0x01 /* include the replication origin */
 
#define XLOG_MARK_UNIMPORTANT   0x02 /* record not important for durability */
 
#define XLOG_INCLUDE_XID   0x04 /* include XID of top-level xact */
 
#define RECOVERY_SIGNAL_FILE   "recovery.signal"
 
#define STANDBY_SIGNAL_FILE   "standby.signal"
 
#define BACKUP_LABEL_FILE   "backup_label"
 
#define BACKUP_LABEL_OLD   "backup_label.old"
 
#define TABLESPACE_MAP   "tablespace_map"
 
#define TABLESPACE_MAP_OLD   "tablespace_map.old"
 
#define PROMOTE_SIGNAL_FILE   "promote"
 

Typedefs

typedef enum ArchiveMode ArchiveMode
 
typedef enum WalLevel WalLevel
 
typedef enum RecoveryState RecoveryState
 
typedef enum RecoveryPauseState RecoveryPauseState
 
typedef struct CheckpointStatsData CheckpointStatsData
 
typedef enum WALAvailability WALAvailability
 
typedef enum SessionBackupState SessionBackupState
 

Enumerations

enum  HotStandbyState { STANDBY_DISABLED, STANDBY_INITIALIZED, STANDBY_SNAPSHOT_PENDING, STANDBY_SNAPSHOT_READY }
 
enum  RecoveryTargetType {
  RECOVERY_TARGET_UNSET, RECOVERY_TARGET_XID, RECOVERY_TARGET_TIME, RECOVERY_TARGET_NAME,
  RECOVERY_TARGET_LSN, RECOVERY_TARGET_IMMEDIATE
}
 
enum  RecoveryTargetTimeLineGoal { RECOVERY_TARGET_TIMELINE_CONTROLFILE, RECOVERY_TARGET_TIMELINE_LATEST, RECOVERY_TARGET_TIMELINE_NUMERIC }
 
enum  ArchiveMode { ARCHIVE_MODE_OFF = 0, ARCHIVE_MODE_ON, ARCHIVE_MODE_ALWAYS }
 
enum  WalLevel { WAL_LEVEL_MINIMAL = 0, WAL_LEVEL_REPLICA, WAL_LEVEL_LOGICAL }
 
enum  RecoveryState { RECOVERY_STATE_CRASH = 0, RECOVERY_STATE_ARCHIVE, RECOVERY_STATE_DONE }
 
enum  RecoveryPauseState { RECOVERY_NOT_PAUSED, RECOVERY_PAUSE_REQUESTED, RECOVERY_PAUSED }
 
enum  WALAvailability {
  WALAVAIL_INVALID_LSN, WALAVAIL_RESERVED, WALAVAIL_EXTENDED, WALAVAIL_UNRESERVED,
  WALAVAIL_REMOVED
}
 
enum  SessionBackupState { SESSION_BACKUP_NONE, SESSION_BACKUP_EXCLUSIVE, SESSION_BACKUP_NON_EXCLUSIVE }
 

Functions

XLogRecPtr XLogInsertRecord (struct XLogRecData *rdata, XLogRecPtr fpw_lsn, uint8 flags, int num_fpi)
 
void XLogFlush (XLogRecPtr RecPtr)
 
bool XLogBackgroundFlush (void)
 
bool XLogNeedsFlush (XLogRecPtr RecPtr)
 
int XLogFileInit (XLogSegNo segno, bool *use_existent, bool use_lock)
 
int XLogFileOpen (XLogSegNo segno)
 
void CheckXLogRemoved (XLogSegNo segno, TimeLineID tli)
 
XLogSegNo XLogGetLastRemovedSegno (void)
 
void XLogSetAsyncXactLSN (XLogRecPtr record)
 
void XLogSetReplicationSlotMinimumLSN (XLogRecPtr lsn)
 
void xlog_redo (XLogReaderState *record)
 
void xlog_desc (StringInfo buf, XLogReaderState *record)
 
const char * xlog_identify (uint8 info)
 
void issue_xlog_fsync (int fd, XLogSegNo segno)
 
bool RecoveryInProgress (void)
 
RecoveryState GetRecoveryState (void)
 
bool HotStandbyActive (void)
 
bool HotStandbyActiveInReplay (void)
 
bool XLogInsertAllowed (void)
 
void GetXLogReceiptTime (TimestampTz *rtime, bool *fromStream)
 
XLogRecPtr GetXLogReplayRecPtr (TimeLineID *replayTLI)
 
XLogRecPtr GetXLogInsertRecPtr (void)
 
XLogRecPtr GetXLogWriteRecPtr (void)
 
RecoveryPauseState GetRecoveryPauseState (void)
 
void SetRecoveryPause (bool recoveryPause)
 
TimestampTz GetLatestXTime (void)
 
TimestampTz GetCurrentChunkReplayStartTime (void)
 
void UpdateControlFile (void)
 
uint64 GetSystemIdentifier (void)
 
char * GetMockAuthenticationNonce (void)
 
bool DataChecksumsEnabled (void)
 
XLogRecPtr GetFakeLSNForUnloggedRel (void)
 
Size XLOGShmemSize (void)
 
void XLOGShmemInit (void)
 
void BootStrapXLOG (void)
 
void LocalProcessControlFile (bool reset)
 
void StartupXLOG (void)
 
void ShutdownXLOG (int code, Datum arg)
 
void InitXLOGAccess (void)
 
void CreateCheckPoint (int flags)
 
bool CreateRestartPoint (int flags)
 
WALAvailability GetWALAvailability (XLogRecPtr targetLSN)
 
XLogRecPtr CalculateMaxmumSafeLSN (void)
 
void XLogPutNextOid (Oid nextOid)
 
XLogRecPtr XLogRestorePoint (const char *rpName)
 
void UpdateFullPageWrites (void)
 
void GetFullPageWriteInfo (XLogRecPtr *RedoRecPtr_p, bool *doPageWrites_p)
 
XLogRecPtr GetRedoRecPtr (void)
 
XLogRecPtr GetInsertRecPtr (void)
 
XLogRecPtr GetFlushRecPtr (void)
 
XLogRecPtr GetLastImportantRecPtr (void)
 
void RemovePromoteSignalFiles (void)
 
bool PromoteIsTriggered (void)
 
bool CheckPromoteSignal (void)
 
void WakeupRecovery (void)
 
void SetWalWriterSleeping (bool sleeping)
 
void StartupRequestWalReceiverRestart (void)
 
void XLogRequestWalReceiverReply (void)
 
void assign_max_wal_size (int newval, void *extra)
 
void assign_checkpoint_completion_target (double newval, void *extra)
 
XLogRecPtr do_pg_start_backup (const char *backupidstr, bool fast, TimeLineID *starttli_p, StringInfo labelfile, List **tablespaces, StringInfo tblspcmapfile)
 
XLogRecPtr do_pg_stop_backup (char *labelfile, bool waitforarchive, TimeLineID *stoptli_p)
 
void do_pg_abort_backup (int code, Datum arg)
 
void register_persistent_abort_backup_handler (void)
 
SessionBackupState get_backup_status (void)
 

Variables

int sync_method
 
PGDLLIMPORT TimeLineID ThisTimeLineID
 
bool InRecovery
 
HotStandbyState standbyState
 
XLogRecPtr ProcLastRecPtr
 
XLogRecPtr XactLastRecEnd
 
PGDLLIMPORT XLogRecPtr XactLastCommitEnd
 
bool reachedConsistency
 
int wal_segment_size
 
int min_wal_size_mb
 
int max_wal_size_mb
 
int wal_keep_size_mb
 
int max_slot_wal_keep_size_mb
 
int XLOGbuffers
 
int XLogArchiveTimeout
 
int wal_retrieve_retry_interval
 
char * XLogArchiveCommand
 
bool EnableHotStandby
 
bool fullPageWrites
 
bool wal_log_hints
 
bool wal_compression
 
bool wal_init_zero
 
bool wal_recycle
 
boolwal_consistency_checking
 
char * wal_consistency_checking_string
 
bool log_checkpoints
 
char * recoveryRestoreCommand
 
char * recoveryEndCommand
 
char * archiveCleanupCommand
 
bool recoveryTargetInclusive
 
int recoveryTargetAction
 
int recovery_min_apply_delay
 
char * PrimaryConnInfo
 
char * PrimarySlotName
 
bool wal_receiver_create_temp_slot
 
bool track_wal_io_timing
 
int wal_decode_buffer_size
 
TransactionId recoveryTargetXid
 
char * recovery_target_time_string
 
const char * recoveryTargetName
 
XLogRecPtr recoveryTargetLSN
 
RecoveryTargetType recoveryTarget
 
char * PromoteTriggerFile
 
RecoveryTargetTimeLineGoal recoveryTargetTimeLineGoal
 
TimeLineID recoveryTargetTLIRequested
 
TimeLineID recoveryTargetTLI
 
int CheckPointSegments
 
bool StandbyModeRequested
 
bool StandbyMode
 
int XLogArchiveMode
 
PGDLLIMPORT int wal_level
 
CheckpointStatsData CheckpointStats
 

Macro Definition Documentation

◆ BACKUP_LABEL_FILE

#define BACKUP_LABEL_FILE   "backup_label"

◆ BACKUP_LABEL_OLD

#define BACKUP_LABEL_OLD   "backup_label.old"

Definition at line 399 of file xlog.h.

Referenced by CancelBackup(), and StartupXLOG().

◆ CHECKPOINT_CAUSE_TIME

#define CHECKPOINT_CAUSE_TIME   0x0100 /* Elapsed time */

Definition at line 243 of file xlog.h.

Referenced by CheckpointerMain(), and LogCheckpointStart().

◆ CHECKPOINT_CAUSE_XLOG

#define CHECKPOINT_CAUSE_XLOG   0x0080 /* XLOG consumption */

Definition at line 242 of file xlog.h.

Referenced by CheckpointerMain(), LogCheckpointStart(), XLogPageRead(), and XLogWrite().

◆ CHECKPOINT_END_OF_RECOVERY

#define CHECKPOINT_END_OF_RECOVERY
Value:
0x0002 /* Like shutdown checkpoint, but
* issued at end of WAL recovery */

Definition at line 232 of file xlog.h.

Referenced by BufferSync(), CheckpointerMain(), CreateCheckPoint(), LogCheckpointStart(), StartupXLOG(), and update_checkpoint_display().

◆ CHECKPOINT_FLUSH_ALL

#define CHECKPOINT_FLUSH_ALL
Value:
0x0010 /* Flush all pages, including those
* belonging to unlogged tables */

Definition at line 236 of file xlog.h.

Referenced by BufferSync(), createdb(), LogCheckpointStart(), and movedb().

◆ CHECKPOINT_FORCE

#define CHECKPOINT_FORCE   0x0008 /* Force even if no activity */

◆ CHECKPOINT_IMMEDIATE

◆ CHECKPOINT_IS_SHUTDOWN

#define CHECKPOINT_IS_SHUTDOWN   0x0001 /* Checkpoint is for shutdown */

◆ CHECKPOINT_REQUESTED

#define CHECKPOINT_REQUESTED   0x0040 /* Checkpoint request has been made */

Definition at line 240 of file xlog.h.

Referenced by RequestCheckpoint().

◆ CHECKPOINT_WAIT

#define CHECKPOINT_WAIT   0x0020 /* Wait for completion */

◆ InHotStandby

◆ PROMOTE_SIGNAL_FILE

#define PROMOTE_SIGNAL_FILE   "promote"

Definition at line 405 of file xlog.h.

Referenced by CheckPromoteSignal(), pg_promote(), and RemovePromoteSignalFiles().

◆ RECOVERY_SIGNAL_FILE

#define RECOVERY_SIGNAL_FILE   "recovery.signal"

Definition at line 396 of file xlog.h.

Referenced by exitArchiveRecovery(), and readRecoverySignalFile().

◆ STANDBY_SIGNAL_FILE

#define STANDBY_SIGNAL_FILE   "standby.signal"

Definition at line 397 of file xlog.h.

Referenced by exitArchiveRecovery(), and readRecoverySignalFile().

◆ SYNC_METHOD_FDATASYNC

#define SYNC_METHOD_FDATASYNC   1

Definition at line 26 of file xlog.h.

Referenced by get_sync_bit(), and issue_xlog_fsync().

◆ SYNC_METHOD_FSYNC

#define SYNC_METHOD_FSYNC   0

Definition at line 25 of file xlog.h.

Referenced by get_sync_bit(), and issue_xlog_fsync().

◆ SYNC_METHOD_FSYNC_WRITETHROUGH

#define SYNC_METHOD_FSYNC_WRITETHROUGH   3

Definition at line 28 of file xlog.h.

Referenced by get_sync_bit(), issue_xlog_fsync(), and pg_fsync().

◆ SYNC_METHOD_OPEN

#define SYNC_METHOD_OPEN   2 /* for O_SYNC */

Definition at line 27 of file xlog.h.

Referenced by get_sync_bit(), issue_xlog_fsync(), and XLogWrite().

◆ SYNC_METHOD_OPEN_DSYNC

#define SYNC_METHOD_OPEN_DSYNC   4 /* for O_DSYNC */

Definition at line 29 of file xlog.h.

Referenced by get_sync_bit(), issue_xlog_fsync(), and XLogWrite().

◆ TABLESPACE_MAP

#define TABLESPACE_MAP   "tablespace_map"

◆ TABLESPACE_MAP_OLD

#define TABLESPACE_MAP_OLD   "tablespace_map.old"

Definition at line 402 of file xlog.h.

Referenced by CancelBackup(), and StartupXLOG().

◆ XLOG_INCLUDE_ORIGIN

#define XLOG_INCLUDE_ORIGIN   0x01 /* include the replication origin */

◆ XLOG_INCLUDE_XID

#define XLOG_INCLUDE_XID   0x04 /* include XID of top-level xact */

Definition at line 250 of file xlog.h.

Referenced by XLogRecordAssemble(), and XLogResetInsertion().

◆ XLOG_MARK_UNIMPORTANT

#define XLOG_MARK_UNIMPORTANT   0x02 /* record not important for durability */

◆ XLogArchiveCommandSet

#define XLogArchiveCommandSet ( )    (XLogArchiveCommand[0] != '\0')

Definition at line 195 of file xlog.h.

Referenced by pgarch_ArchiverCopyLoop(), and ShutdownXLOG().

◆ XLogArchivingActive

◆ XLogArchivingAlways

Definition at line 193 of file xlog.h.

Referenced by do_pg_stop_backup(), sigusr1_handler(), and XLogArchiveCheckDone().

◆ XLogHintBitIsNeeded

◆ XLogIsNeeded

◆ XLogLogicalInfoActive

◆ XLogStandbyInfoActive

Typedef Documentation

◆ ArchiveMode

typedef enum ArchiveMode ArchiveMode

◆ CheckpointStatsData

◆ RecoveryPauseState

◆ RecoveryState

◆ SessionBackupState

◆ WALAvailability

◆ WalLevel

typedef enum WalLevel WalLevel

Enumeration Type Documentation

◆ ArchiveMode

Enumerator
ARCHIVE_MODE_OFF 
ARCHIVE_MODE_ON 
ARCHIVE_MODE_ALWAYS 

Definition at line 155 of file xlog.h.

156 {
157  ARCHIVE_MODE_OFF = 0, /* disabled */
158  ARCHIVE_MODE_ON, /* enabled while server is running normally */
159  ARCHIVE_MODE_ALWAYS /* enabled always (even during recovery) */
160 } ArchiveMode;
ArchiveMode
Definition: xlog.h:155

◆ HotStandbyState

Enumerator
STANDBY_DISABLED 
STANDBY_INITIALIZED 
STANDBY_SNAPSHOT_PENDING 
STANDBY_SNAPSHOT_READY 

Definition at line 64 of file xlog.h.

◆ RecoveryPauseState

Enumerator
RECOVERY_NOT_PAUSED 
RECOVERY_PAUSE_REQUESTED 
RECOVERY_PAUSED 

Definition at line 180 of file xlog.h.

181 {
182  RECOVERY_NOT_PAUSED, /* pause not requested */
183  RECOVERY_PAUSE_REQUESTED, /* pause requested, but not yet paused */
184  RECOVERY_PAUSED /* recovery is paused */
RecoveryPauseState
Definition: xlog.h:180

◆ RecoveryState

Enumerator
RECOVERY_STATE_CRASH 
RECOVERY_STATE_ARCHIVE 
RECOVERY_STATE_DONE 

Definition at line 172 of file xlog.h.

173 {
174  RECOVERY_STATE_CRASH = 0, /* crash recovery */
175  RECOVERY_STATE_ARCHIVE, /* archive recovery */
176  RECOVERY_STATE_DONE /* currently in production */
177 } RecoveryState;
RecoveryState
Definition: xlog.h:172

◆ RecoveryTargetTimeLineGoal

Enumerator
RECOVERY_TARGET_TIMELINE_CONTROLFILE 
RECOVERY_TARGET_TIMELINE_LATEST 
RECOVERY_TARGET_TIMELINE_NUMERIC 

Definition at line 93 of file xlog.h.

◆ RecoveryTargetType

Enumerator
RECOVERY_TARGET_UNSET 
RECOVERY_TARGET_XID 
RECOVERY_TARGET_TIME 
RECOVERY_TARGET_NAME 
RECOVERY_TARGET_LSN 
RECOVERY_TARGET_IMMEDIATE 

Definition at line 80 of file xlog.h.

◆ SessionBackupState

Enumerator
SESSION_BACKUP_NONE 
SESSION_BACKUP_EXCLUSIVE 
SESSION_BACKUP_NON_EXCLUSIVE 

Definition at line 379 of file xlog.h.

◆ WALAvailability

Enumerator
WALAVAIL_INVALID_LSN 
WALAVAIL_RESERVED 
WALAVAIL_EXTENDED 
WALAVAIL_UNRESERVED 
WALAVAIL_REMOVED 

Definition at line 281 of file xlog.h.

282 {
283  WALAVAIL_INVALID_LSN, /* parameter error */
284  WALAVAIL_RESERVED, /* WAL segment is within max_wal_size */
285  WALAVAIL_EXTENDED, /* WAL segment is reserved by a slot or
286  * wal_keep_size */
287  WALAVAIL_UNRESERVED, /* no longer reserved, but not removed yet */
288  WALAVAIL_REMOVED /* WAL segment has been removed */
WALAvailability
Definition: xlog.h:281

◆ WalLevel

enum WalLevel
Enumerator
WAL_LEVEL_MINIMAL 
WAL_LEVEL_REPLICA 
WAL_LEVEL_LOGICAL 

Definition at line 164 of file xlog.h.

Function Documentation

◆ assign_checkpoint_completion_target()

void assign_checkpoint_completion_target ( double  newval,
void *  extra 
)

Definition at line 2346 of file xlog.c.

References CalculateCheckpointSegments(), CheckPointCompletionTarget, and newval.

2347 {
2350 }
static void CalculateCheckpointSegments(void)
Definition: xlog.c:2310
#define newval
double CheckPointCompletionTarget
Definition: checkpointer.c:148

◆ assign_max_wal_size()

void assign_max_wal_size ( int  newval,
void *  extra 
)

Definition at line 2339 of file xlog.c.

References CalculateCheckpointSegments(), max_wal_size_mb, and newval.

2340 {
2343 }
static void CalculateCheckpointSegments(void)
Definition: xlog.c:2310
int max_wal_size_mb
Definition: xlog.c:92
#define newval

◆ BootStrapXLOG()

void BootStrapXLOG ( void  )

Definition at line 5249 of file xlog.c.

References AdvanceOldestClogXid(), Assert, BootStrapCLOG(), BootStrapCommitTs(), BootStrapMultiXact(), BootStrapSUBTRANS(), ControlFileData::checkPoint, ControlFileData::checkPointCopy, close, COMP_CRC32C, ereport, errcode_for_file_access(), errmsg(), FIN_CRC32C, FirstBootstrapObjectId, FirstMultiXactId, FirstNormalTransactionId, CheckPoint::fullPageWrites, fullPageWrites, FullTransactionIdFromEpochAndXid(), gettimeofday(), INIT_CRC32C, InitControlFile(), InvalidTransactionId, MultiXactSetNextMXact(), CheckPoint::newestCommitTsXid, CheckPoint::nextMulti, CheckPoint::nextMultiOffset, CheckPoint::nextOid, VariableCacheData::nextOid, CheckPoint::nextXid, VariableCacheData::nextXid, offsetof, VariableCacheData::oidCount, CheckPoint::oldestActiveXid, CheckPoint::oldestCommitTsXid, CheckPoint::oldestMulti, CheckPoint::oldestMultiDB, CheckPoint::oldestXid, CheckPoint::oldestXidDB, openLogFile, palloc(), PANIC, pfree(), pg_fsync(), pgstat_report_wait_end(), pgstat_report_wait_start(), CheckPoint::PrevTimeLineID, ReadControlFile(), CheckPoint::redo, SetCommitTsLimit(), SetMultiXactIdLimit(), SetTransactionIdLimit(), ShmemVariableCache, SizeOfXLogLongPHD, SizeOfXLogRecord, SizeOfXLogRecordDataHeaderShort, CheckPoint::ThisTimeLineID, ThisTimeLineID, CheckPoint::time, ControlFileData::time, TYPEALIGN, WAIT_EVENT_WAL_BOOTSTRAP_SYNC, WAIT_EVENT_WAL_BOOTSTRAP_WRITE, wal_segment_size, write, WriteControlFile(), XLogRecord::xl_info, XLogRecord::xl_prev, XLogRecord::xl_rmid, XLogRecord::xl_tot_len, XLogRecord::xl_xid, XLOG_CHECKPOINT_SHUTDOWN, XLOG_PAGE_MAGIC, XLogFileInit(), XLogPageHeaderData::xlp_info, XLP_LONG_HEADER, XLogPageHeaderData::xlp_magic, XLogPageHeaderData::xlp_pageaddr, XLogLongPageHeaderData::xlp_seg_size, XLogLongPageHeaderData::xlp_sysid, XLogPageHeaderData::xlp_tli, XLogLongPageHeaderData::xlp_xlog_blcksz, and XLR_BLOCK_ID_DATA_SHORT.

Referenced by AuxiliaryProcessMain().

5250 {
5251  CheckPoint checkPoint;
5252  char *buffer;
5253  XLogPageHeader page;
5254  XLogLongPageHeader longpage;
5255  XLogRecord *record;
5256  char *recptr;
5257  bool use_existent;
5258  uint64 sysidentifier;
5259  struct timeval tv;
5260  pg_crc32c crc;
5261 
5262  /*
5263  * Select a hopefully-unique system identifier code for this installation.
5264  * We use the result of gettimeofday(), including the fractional seconds
5265  * field, as being about as unique as we can easily get. (Think not to
5266  * use random(), since it hasn't been seeded and there's no portable way
5267  * to seed it other than the system clock value...) The upper half of the
5268  * uint64 value is just the tv_sec part, while the lower half contains the
5269  * tv_usec part (which must fit in 20 bits), plus 12 bits from our current
5270  * PID for a little extra uniqueness. A person knowing this encoding can
5271  * determine the initialization time of the installation, which could
5272  * perhaps be useful sometimes.
5273  */
5274  gettimeofday(&tv, NULL);
5275  sysidentifier = ((uint64) tv.tv_sec) << 32;
5276  sysidentifier |= ((uint64) tv.tv_usec) << 12;
5277  sysidentifier |= getpid() & 0xFFF;
5278 
5279  /* First timeline ID is always 1 */
5280  ThisTimeLineID = 1;
5281 
5282  /* page buffer must be aligned suitably for O_DIRECT */
5283  buffer = (char *) palloc(XLOG_BLCKSZ + XLOG_BLCKSZ);
5284  page = (XLogPageHeader) TYPEALIGN(XLOG_BLCKSZ, buffer);
5285  memset(page, 0, XLOG_BLCKSZ);
5286 
5287  /*
5288  * Set up information for the initial checkpoint record
5289  *
5290  * The initial checkpoint record is written to the beginning of the WAL
5291  * segment with logid=0 logseg=1. The very first WAL segment, 0/0, is not
5292  * used, so that we can use 0/0 to mean "before any valid WAL segment".
5293  */
5294  checkPoint.redo = wal_segment_size + SizeOfXLogLongPHD;
5295  checkPoint.ThisTimeLineID = ThisTimeLineID;
5296  checkPoint.PrevTimeLineID = ThisTimeLineID;
5297  checkPoint.fullPageWrites = fullPageWrites;
5298  checkPoint.nextXid =
5300  checkPoint.nextOid = FirstBootstrapObjectId;
5301  checkPoint.nextMulti = FirstMultiXactId;
5302  checkPoint.nextMultiOffset = 0;
5303  checkPoint.oldestXid = FirstNormalTransactionId;
5304  checkPoint.oldestXidDB = TemplateDbOid;
5305  checkPoint.oldestMulti = FirstMultiXactId;
5306  checkPoint.oldestMultiDB = TemplateDbOid;
5309  checkPoint.time = (pg_time_t) time(NULL);
5311 
5312  ShmemVariableCache->nextXid = checkPoint.nextXid;
5313  ShmemVariableCache->nextOid = checkPoint.nextOid;
5315  MultiXactSetNextMXact(checkPoint.nextMulti, checkPoint.nextMultiOffset);
5316  AdvanceOldestClogXid(checkPoint.oldestXid);
5317  SetTransactionIdLimit(checkPoint.oldestXid, checkPoint.oldestXidDB);
5318  SetMultiXactIdLimit(checkPoint.oldestMulti, checkPoint.oldestMultiDB, true);
5320 
5321  /* Set up the XLOG page header */
5322  page->xlp_magic = XLOG_PAGE_MAGIC;
5323  page->xlp_info = XLP_LONG_HEADER;
5324  page->xlp_tli = ThisTimeLineID;
5326  longpage = (XLogLongPageHeader) page;
5327  longpage->xlp_sysid = sysidentifier;
5328  longpage->xlp_seg_size = wal_segment_size;
5329  longpage->xlp_xlog_blcksz = XLOG_BLCKSZ;
5330 
5331  /* Insert the initial checkpoint record */
5332  recptr = ((char *) page + SizeOfXLogLongPHD);
5333  record = (XLogRecord *) recptr;
5334  record->xl_prev = 0;
5335  record->xl_xid = InvalidTransactionId;
5336  record->xl_tot_len = SizeOfXLogRecord + SizeOfXLogRecordDataHeaderShort + sizeof(checkPoint);
5338  record->xl_rmid = RM_XLOG_ID;
5339  recptr += SizeOfXLogRecord;
5340  /* fill the XLogRecordDataHeaderShort struct */
5341  *(recptr++) = (char) XLR_BLOCK_ID_DATA_SHORT;
5342  *(recptr++) = sizeof(checkPoint);
5343  memcpy(recptr, &checkPoint, sizeof(checkPoint));
5344  recptr += sizeof(checkPoint);
5345  Assert(recptr - (char *) record == record->xl_tot_len);
5346 
5347  INIT_CRC32C(crc);
5348  COMP_CRC32C(crc, ((char *) record) + SizeOfXLogRecord, record->xl_tot_len - SizeOfXLogRecord);
5349  COMP_CRC32C(crc, (char *) record, offsetof(XLogRecord, xl_crc));
5350  FIN_CRC32C(crc);
5351  record->xl_crc = crc;
5352 
5353  /* Create first XLOG segment file */
5354  use_existent = false;
5355  openLogFile = XLogFileInit(1, &use_existent, false);
5356 
5357  /*
5358  * We needn't bother with Reserve/ReleaseExternalFD here, since we'll
5359  * close the file again in a moment.
5360  */
5361 
5362  /* Write the first page with the initial record */
5363  errno = 0;
5365  if (write(openLogFile, page, XLOG_BLCKSZ) != XLOG_BLCKSZ)
5366  {
5367  /* if write didn't set errno, assume problem is no disk space */
5368  if (errno == 0)
5369  errno = ENOSPC;
5370  ereport(PANIC,
5372  errmsg("could not write bootstrap write-ahead log file: %m")));
5373  }
5375 
5377  if (pg_fsync(openLogFile) != 0)
5378  ereport(PANIC,
5380  errmsg("could not fsync bootstrap write-ahead log file: %m")));
5382 
5383  if (close(openLogFile) != 0)
5384  ereport(PANIC,
5386  errmsg("could not close bootstrap write-ahead log file: %m")));
5387 
5388  openLogFile = -1;
5389 
5390  /* Now create pg_control */
5391  InitControlFile(sysidentifier);
5392  ControlFile->time = checkPoint.time;
5393  ControlFile->checkPoint = checkPoint.redo;
5394  ControlFile->checkPointCopy = checkPoint;
5395 
5396  /* some additional ControlFile fields are set in WriteControlFile() */
5397  WriteControlFile();
5398 
5399  /* Bootstrap the commit log, too */
5400  BootStrapCLOG();
5404 
5405  pfree(buffer);
5406 
5407  /*
5408  * Force control file to be read - in contrast to normal processing we'd
5409  * otherwise never run the checks and GUC related initializations therein.
5410  */
5411  ReadControlFile();
5412 }
static void WriteControlFile(void)
Definition: xlog.c:4665
#define INIT_CRC32C(crc)
Definition: pg_crc32c.h:41
XLogRecPtr xl_prev
Definition: xlogrecord.h:45
int gettimeofday(struct timeval *tp, struct timezone *tzp)
Definition: gettimeofday.c:104
int64 pg_time_t
Definition: pgtime.h:23
static void pgstat_report_wait_end(void)
Definition: wait_event.h:277
int wal_segment_size
Definition: xlog.c:121
pg_time_t time
Definition: pg_control.h:128
void SetCommitTsLimit(TransactionId oldestXact, TransactionId newestXact)
Definition: commit_ts.c:876
uint32 oidCount
Definition: transam.h:208
#define write(a, b, c)
Definition: win32.h:14
#define SizeOfXLogRecordDataHeaderShort
Definition: xlogrecord.h:200
uint32 pg_crc32c
Definition: pg_crc32c.h:38
TransactionId oldestActiveXid
Definition: pg_control.h:63
int XLogFileInit(XLogSegNo logsegno, bool *use_existent, bool use_lock)
Definition: xlog.c:3288
void BootStrapMultiXact(void)
Definition: multixact.c:1891
MultiXactId oldestMulti
Definition: pg_control.h:49
TimeLineID PrevTimeLineID
Definition: pg_control.h:40
static void InitControlFile(uint64 sysidentifier)
Definition: xlog.c:4630
RmgrId xl_rmid
Definition: xlogrecord.h:47
XLogPageHeaderData * XLogPageHeader
Definition: xlog_internal.h:54
CheckPoint checkPointCopy
Definition: pg_control.h:131
TransactionId oldestXid
Definition: pg_control.h:47
FullTransactionId nextXid
Definition: transam.h:213
pg_time_t time
Definition: pg_control.h:51
#define PANIC
Definition: elog.h:50
XLogLongPageHeaderData * XLogLongPageHeader
Definition: xlog_internal.h:71
bool fullPageWrites
Definition: xlog.c:100
void BootStrapSUBTRANS(void)
Definition: subtrans.c:211
MultiXactOffset nextMultiOffset
Definition: pg_control.h:46
void AdvanceOldestClogXid(TransactionId oldest_datfrozenxid)
Definition: varsup.c:328
TransactionId oldestCommitTsXid
Definition: pg_control.h:52
void pfree(void *pointer)
Definition: mcxt.c:1169
#define FirstNormalTransactionId
Definition: transam.h:34
uint32 xl_tot_len
Definition: xlogrecord.h:43
#define XLOG_PAGE_MAGIC
Definition: xlog_internal.h:34
static void ReadControlFile(void)
Definition: xlog.c:4756
#define XLOG_CHECKPOINT_SHUTDOWN
Definition: pg_control.h:67
int errcode_for_file_access(void)
Definition: elog.c:721
VariableCache ShmemVariableCache
Definition: varsup.c:34
#define InvalidTransactionId
Definition: transam.h:31
#define FirstBootstrapObjectId
Definition: transam.h:189
#define FirstMultiXactId
Definition: multixact.h:25
TimeLineID xlp_tli
Definition: xlog_internal.h:40
static void pgstat_report_wait_start(uint32 wait_event_info)
Definition: wait_event.h:261
XLogRecPtr xlp_pageaddr
Definition: xlog_internal.h:41
#define SizeOfXLogRecord
Definition: xlogrecord.h:55
TransactionId newestCommitTsXid
Definition: pg_control.h:54
Oid oldestMultiDB
Definition: pg_control.h:50
static int openLogFile
Definition: xlog.c:809
static ControlFileData * ControlFile
Definition: xlog.c:748
void SetMultiXactIdLimit(MultiXactId oldest_datminmxid, Oid oldest_datoid, bool is_startup)
Definition: multixact.c:2210
TimeLineID ThisTimeLineID
Definition: xlog.c:196
Oid nextOid
Definition: pg_control.h:44
#define ereport(elevel,...)
Definition: elog.h:157
#define TYPEALIGN(ALIGNVAL, LEN)
Definition: c.h:750
bool fullPageWrites
Definition: pg_control.h:42
void BootStrapCLOG(void)
Definition: clog.c:707
#define Assert(condition)
Definition: c.h:804
#define XLP_LONG_HEADER
Definition: xlog_internal.h:76
Oid oldestXidDB
Definition: pg_control.h:48
void SetTransactionIdLimit(TransactionId oldest_datfrozenxid, Oid oldest_datoid)
Definition: varsup.c:345
uint8 xl_info
Definition: xlogrecord.h:46
MultiXactId nextMulti
Definition: pg_control.h:45
static FullTransactionId FullTransactionIdFromEpochAndXid(uint32 epoch, TransactionId xid)
Definition: transam.h:71
#define XLR_BLOCK_ID_DATA_SHORT
Definition: xlogrecord.h:223
TransactionId xl_xid
Definition: xlogrecord.h:44
TimeLineID ThisTimeLineID
Definition: pg_control.h:39
void * palloc(Size size)
Definition: mcxt.c:1062
int errmsg(const char *fmt,...)
Definition: elog.c:909
int pg_fsync(int fd)
Definition: fd.c:352
#define close(a)
Definition: win32.h:12
void BootStrapCommitTs(void)
Definition: commit_ts.c:569
#define COMP_CRC32C(crc, data, len)
Definition: pg_crc32c.h:89
#define FIN_CRC32C(crc)
Definition: pg_crc32c.h:94
XLogRecPtr checkPoint
Definition: pg_control.h:129
XLogRecPtr redo
Definition: pg_control.h:37
#define offsetof(type, field)
Definition: c.h:727
FullTransactionId nextXid
Definition: pg_control.h:43
#define SizeOfXLogLongPHD
Definition: xlog_internal.h:69
void MultiXactSetNextMXact(MultiXactId nextMulti, MultiXactOffset nextMultiOffset)
Definition: multixact.c:2176

◆ CalculateMaxmumSafeLSN()

XLogRecPtr CalculateMaxmumSafeLSN ( void  )

◆ CheckPromoteSignal()

bool CheckPromoteSignal ( void  )

Definition at line 12920 of file xlog.c.

References PROMOTE_SIGNAL_FILE, and stat.

Referenced by CheckForStandbyTrigger(), and sigusr1_handler().

12921 {
12922  struct stat stat_buf;
12923 
12924  if (stat(PROMOTE_SIGNAL_FILE, &stat_buf) == 0)
12925  return true;
12926 
12927  return false;
12928 }
#define PROMOTE_SIGNAL_FILE
Definition: xlog.h:405
#define stat
Definition: win32_port.h:275

◆ CheckXLogRemoved()

void CheckXLogRemoved ( XLogSegNo  segno,
TimeLineID  tli 
)

Definition at line 3976 of file xlog.c.

References ereport, errcode_for_file_access(), errmsg(), ERROR, filename, XLogCtlData::info_lck, XLogCtlData::lastRemovedSegNo, MAXFNAMELEN, SpinLockAcquire, SpinLockRelease, wal_segment_size, and XLogFileName.

Referenced by logical_read_xlog_page(), perform_base_backup(), and XLogSendPhysical().

3977 {
3978  int save_errno = errno;
3979  XLogSegNo lastRemovedSegNo;
3980 
3982  lastRemovedSegNo = XLogCtl->lastRemovedSegNo;
3984 
3985  if (segno <= lastRemovedSegNo)
3986  {
3987  char filename[MAXFNAMELEN];
3988 
3989  XLogFileName(filename, tli, segno, wal_segment_size);
3990  errno = save_errno;
3991  ereport(ERROR,
3993  errmsg("requested WAL segment %s has already been removed",
3994  filename)));
3995  }
3996  errno = save_errno;
3997 }
int wal_segment_size
Definition: xlog.c:121
slock_t info_lck
Definition: xlog.c:737
XLogSegNo lastRemovedSegNo
Definition: xlog.c:609
#define SpinLockAcquire(lock)
Definition: spin.h:62
#define ERROR
Definition: elog.h:46
uint64 XLogSegNo
Definition: xlogdefs.h:48
int errcode_for_file_access(void)
Definition: elog.c:721
#define MAXFNAMELEN
#define SpinLockRelease(lock)
Definition: spin.h:64
#define ereport(elevel,...)
Definition: elog.h:157
#define XLogFileName(fname, tli, logSegNo, wal_segsz_bytes)
static XLogCtlData * XLogCtl
Definition: xlog.c:740
static char * filename
Definition: pg_dumpall.c:91
int errmsg(const char *fmt,...)
Definition: elog.c:909

◆ CreateCheckPoint()

void CreateCheckPoint ( int  flags)

Definition at line 8919 of file xlog.c.

References ControlFileData::checkPoint, CHECKPOINT_END_OF_RECOVERY, CHECKPOINT_FORCE, CHECKPOINT_IS_SHUTDOWN, ControlFileData::checkPointCopy, CheckPointGuts(), CheckpointStatsData::ckpt_bufs_written, CheckpointStatsData::ckpt_segs_added, CheckpointStatsData::ckpt_segs_recycled, CheckpointStatsData::ckpt_segs_removed, CheckpointStatsData::ckpt_start_t, XLogCtlData::ckptFullXid, XLogCtlInsert::CurrBytePos, DB_SHUTDOWNED, DB_SHUTDOWNING, DEBUG1, elog, END_CRIT_SECTION, ereport, errmsg(), errmsg_internal(), ERROR, CheckPoint::fullPageWrites, XLogCtlInsert::fullPageWrites, GetCurrentTimestamp(), GetLastImportantRecPtr(), GetOldestActiveTransactionId(), GetOldestTransactionIdConsideredRunning(), GetVirtualXIDsDelayingChkpt(), HaveVirtualXIDsDelayingChkpt(), XLogCtlData::info_lck, InitXLogInsert(), Insert(), XLogCtlData::Insert, INSERT_FREESPACE, InvalidateObsoleteReplicationSlots(), InvalidTransactionId, InvalidXLogRecPtr, KeepLogSeg(), LocalSetXLogInsertAllowed(), LocalXLogInsertAllowed, log_checkpoints, LogCheckpointEnd(), LogCheckpointStart(), LogStandbySnapshot(), LW_EXCLUSIVE, LW_SHARED, LWLockAcquire(), LWLockRelease(), MemSet, ControlFileData::minRecoveryPoint, ControlFileData::minRecoveryPointTLI, MultiXactGetCheckptMulti(), NBuffers, CheckPoint::newestCommitTsXid, VariableCacheData::newestCommitTsXid, CheckPoint::nextMulti, CheckPoint::nextMultiOffset, CheckPoint::nextOid, VariableCacheData::nextOid, CheckPoint::nextXid, VariableCacheData::nextXid, VariableCacheData::oidCount, CheckPoint::oldestActiveXid, CheckPoint::oldestCommitTsXid, VariableCacheData::oldestCommitTsXid, CheckPoint::oldestMulti, CheckPoint::oldestMultiDB, CheckPoint::oldestXid, VariableCacheData::oldestXid, CheckPoint::oldestXidDB, VariableCacheData::oldestXidDB, PANIC, pfree(), pg_usleep(), PreallocXlogFiles(), CheckPoint::PrevTimeLineID, XLogCtlData::PrevTimeLineID, ProcLastRecPtr, RecoveryInProgress(), CheckPoint::redo, RedoRecPtr, XLogCtlInsert::RedoRecPtr, XLogCtlData::RedoRecPtr, RemoveOldXlogFiles(), ShmemVariableCache, SizeOfXLogLongPHD, SizeOfXLogShortPHD, SpinLockAcquire, SpinLockRelease, START_CRIT_SECTION, ControlFileData::state, SyncPostCheckpoint(), SyncPreCheckpoint(), CheckPoint::ThisTimeLineID, ThisTimeLineID, CheckPoint::time, ControlFileData::time, TruncateSUBTRANS(), XLogCtlData::ulsn_lck, ControlFileData::unloggedLSN, XLogCtlData::unloggedLSN, update_checkpoint_display(), UpdateCheckPointDistanceEstimate(), UpdateControlFile(), wal_segment_size, WALInsertLockAcquireExclusive(), WALInsertLockRelease(), XLByteToSeg, XLOG_CHECKPOINT_ONLINE, XLOG_CHECKPOINT_SHUTDOWN, XLogBeginInsert(), XLogBytePosToRecPtr(), XLogFlush(), XLogInsert(), XLogRegisterData(), XLogSegmentOffset, and XLogStandbyInfoActive.

Referenced by CheckpointerMain(), RequestCheckpoint(), ShutdownXLOG(), and StartupXLOG().

8920 {
8921  bool shutdown;
8922  CheckPoint checkPoint;
8923  XLogRecPtr recptr;
8924  XLogSegNo _logSegNo;
8926  uint32 freespace;
8927  XLogRecPtr PriorRedoPtr;
8928  XLogRecPtr curInsert;
8929  XLogRecPtr last_important_lsn;
8930  VirtualTransactionId *vxids;
8931  int nvxids;
8932 
8933  /*
8934  * An end-of-recovery checkpoint is really a shutdown checkpoint, just
8935  * issued at a different time.
8936  */
8938  shutdown = true;
8939  else
8940  shutdown = false;
8941 
8942  /* sanity check */
8943  if (RecoveryInProgress() && (flags & CHECKPOINT_END_OF_RECOVERY) == 0)
8944  elog(ERROR, "can't create a checkpoint during recovery");
8945 
8946  /*
8947  * Initialize InitXLogInsert working areas before entering the critical
8948  * section. Normally, this is done by the first call to
8949  * RecoveryInProgress() or LocalSetXLogInsertAllowed(), but when creating
8950  * an end-of-recovery checkpoint, the LocalSetXLogInsertAllowed call is
8951  * done below in a critical section, and InitXLogInsert cannot be called
8952  * in a critical section.
8953  */
8954  InitXLogInsert();
8955 
8956  /*
8957  * Prepare to accumulate statistics.
8958  *
8959  * Note: because it is possible for log_checkpoints to change while a
8960  * checkpoint proceeds, we always accumulate stats, even if
8961  * log_checkpoints is currently off.
8962  */
8963  MemSet(&CheckpointStats, 0, sizeof(CheckpointStats));
8965 
8966  /*
8967  * Use a critical section to force system panic if we have trouble.
8968  */
8970 
8971  if (shutdown)
8972  {
8973  LWLockAcquire(ControlFileLock, LW_EXCLUSIVE);
8975  ControlFile->time = (pg_time_t) time(NULL);
8977  LWLockRelease(ControlFileLock);
8978  }
8979 
8980  /*
8981  * Let smgr prepare for checkpoint; this has to happen before we determine
8982  * the REDO pointer. Note that smgr must not do anything that'd have to
8983  * be undone if we decide no checkpoint is needed.
8984  */
8986 
8987  /* Begin filling in the checkpoint WAL record */
8988  MemSet(&checkPoint, 0, sizeof(checkPoint));
8989  checkPoint.time = (pg_time_t) time(NULL);
8990 
8991  /*
8992  * For Hot Standby, derive the oldestActiveXid before we fix the redo
8993  * pointer. This allows us to begin accumulating changes to assemble our
8994  * starting snapshot of locks and transactions.
8995  */
8996  if (!shutdown && XLogStandbyInfoActive())
8998  else
9000 
9001  /*
9002  * Get location of last important record before acquiring insert locks (as
9003  * GetLastImportantRecPtr() also locks WAL locks).
9004  */
9005  last_important_lsn = GetLastImportantRecPtr();
9006 
9007  /*
9008  * We must block concurrent insertions while examining insert state to
9009  * determine the checkpoint REDO pointer.
9010  */
9012  curInsert = XLogBytePosToRecPtr(Insert->CurrBytePos);
9013 
9014  /*
9015  * If this isn't a shutdown or forced checkpoint, and if there has been no
9016  * WAL activity requiring a checkpoint, skip it. The idea here is to
9017  * avoid inserting duplicate checkpoints when the system is idle.
9018  */
9019  if ((flags & (CHECKPOINT_IS_SHUTDOWN | CHECKPOINT_END_OF_RECOVERY |
9020  CHECKPOINT_FORCE)) == 0)
9021  {
9022  if (last_important_lsn == ControlFile->checkPoint)
9023  {
9025  END_CRIT_SECTION();
9026  ereport(DEBUG1,
9027  (errmsg_internal("checkpoint skipped because system is idle")));
9028  return;
9029  }
9030  }
9031 
9032  /*
9033  * An end-of-recovery checkpoint is created before anyone is allowed to
9034  * write WAL. To allow us to write the checkpoint record, temporarily
9035  * enable XLogInsertAllowed. (This also ensures ThisTimeLineID is
9036  * initialized, which we need here and in AdvanceXLInsertBuffer.)
9037  */
9038  if (flags & CHECKPOINT_END_OF_RECOVERY)
9040 
9041  checkPoint.ThisTimeLineID = ThisTimeLineID;
9042  if (flags & CHECKPOINT_END_OF_RECOVERY)
9043  checkPoint.PrevTimeLineID = XLogCtl->PrevTimeLineID;
9044  else
9045  checkPoint.PrevTimeLineID = ThisTimeLineID;
9046 
9047  checkPoint.fullPageWrites = Insert->fullPageWrites;
9048 
9049  /*
9050  * Compute new REDO record ptr = location of next XLOG record.
9051  *
9052  * NB: this is NOT necessarily where the checkpoint record itself will be,
9053  * since other backends may insert more XLOG records while we're off doing
9054  * the buffer flush work. Those XLOG records are logically after the
9055  * checkpoint, even though physically before it. Got that?
9056  */
9057  freespace = INSERT_FREESPACE(curInsert);
9058  if (freespace == 0)
9059  {
9060  if (XLogSegmentOffset(curInsert, wal_segment_size) == 0)
9061  curInsert += SizeOfXLogLongPHD;
9062  else
9063  curInsert += SizeOfXLogShortPHD;
9064  }
9065  checkPoint.redo = curInsert;
9066 
9067  /*
9068  * Here we update the shared RedoRecPtr for future XLogInsert calls; this
9069  * must be done while holding all the insertion locks.
9070  *
9071  * Note: if we fail to complete the checkpoint, RedoRecPtr will be left
9072  * pointing past where it really needs to point. This is okay; the only
9073  * consequence is that XLogInsert might back up whole buffers that it
9074  * didn't really need to. We can't postpone advancing RedoRecPtr because
9075  * XLogInserts that happen while we are dumping buffers must assume that
9076  * their buffer changes are not included in the checkpoint.
9077  */
9078  RedoRecPtr = XLogCtl->Insert.RedoRecPtr = checkPoint.redo;
9079 
9080  /*
9081  * Now we can release the WAL insertion locks, allowing other xacts to
9082  * proceed while we are flushing disk buffers.
9083  */
9085 
9086  /* Update the info_lck-protected copy of RedoRecPtr as well */
9088  XLogCtl->RedoRecPtr = checkPoint.redo;
9090 
9091  /*
9092  * If enabled, log checkpoint start. We postpone this until now so as not
9093  * to log anything if we decided to skip the checkpoint.
9094  */
9095  if (log_checkpoints)
9096  LogCheckpointStart(flags, false);
9097 
9098  /* Update the process title */
9099  update_checkpoint_display(flags, false, false);
9100 
9101  TRACE_POSTGRESQL_CHECKPOINT_START(flags);
9102 
9103  /*
9104  * Get the other info we need for the checkpoint record.
9105  *
9106  * We don't need to save oldestClogXid in the checkpoint, it only matters
9107  * for the short period in which clog is being truncated, and if we crash
9108  * during that we'll redo the clog truncation and fix up oldestClogXid
9109  * there.
9110  */
9111  LWLockAcquire(XidGenLock, LW_SHARED);
9112  checkPoint.nextXid = ShmemVariableCache->nextXid;
9113  checkPoint.oldestXid = ShmemVariableCache->oldestXid;
9115  LWLockRelease(XidGenLock);
9116 
9117  LWLockAcquire(CommitTsLock, LW_SHARED);
9120  LWLockRelease(CommitTsLock);
9121 
9122  LWLockAcquire(OidGenLock, LW_SHARED);
9123  checkPoint.nextOid = ShmemVariableCache->nextOid;
9124  if (!shutdown)
9125  checkPoint.nextOid += ShmemVariableCache->oidCount;
9126  LWLockRelease(OidGenLock);
9127 
9128  MultiXactGetCheckptMulti(shutdown,
9129  &checkPoint.nextMulti,
9130  &checkPoint.nextMultiOffset,
9131  &checkPoint.oldestMulti,
9132  &checkPoint.oldestMultiDB);
9133 
9134  /*
9135  * Having constructed the checkpoint record, ensure all shmem disk buffers
9136  * and commit-log buffers are flushed to disk.
9137  *
9138  * This I/O could fail for various reasons. If so, we will fail to
9139  * complete the checkpoint, but there is no reason to force a system
9140  * panic. Accordingly, exit critical section while doing it.
9141  */
9142  END_CRIT_SECTION();
9143 
9144  /*
9145  * In some cases there are groups of actions that must all occur on one
9146  * side or the other of a checkpoint record. Before flushing the
9147  * checkpoint record we must explicitly wait for any backend currently
9148  * performing those groups of actions.
9149  *
9150  * One example is end of transaction, so we must wait for any transactions
9151  * that are currently in commit critical sections. If an xact inserted
9152  * its commit record into XLOG just before the REDO point, then a crash
9153  * restart from the REDO point would not replay that record, which means
9154  * that our flushing had better include the xact's update of pg_xact. So
9155  * we wait till he's out of his commit critical section before proceeding.
9156  * See notes in RecordTransactionCommit().
9157  *
9158  * Because we've already released the insertion locks, this test is a bit
9159  * fuzzy: it is possible that we will wait for xacts we didn't really need
9160  * to wait for. But the delay should be short and it seems better to make
9161  * checkpoint take a bit longer than to hold off insertions longer than
9162  * necessary. (In fact, the whole reason we have this issue is that xact.c
9163  * does commit record XLOG insertion and clog update as two separate steps
9164  * protected by different locks, but again that seems best on grounds of
9165  * minimizing lock contention.)
9166  *
9167  * A transaction that has not yet set delayChkpt when we look cannot be at
9168  * risk, since he's not inserted his commit record yet; and one that's
9169  * already cleared it is not at risk either, since he's done fixing clog
9170  * and we will correctly flush the update below. So we cannot miss any
9171  * xacts we need to wait for.
9172  */
9173  vxids = GetVirtualXIDsDelayingChkpt(&nvxids);
9174  if (nvxids > 0)
9175  {
9176  do
9177  {
9178  pg_usleep(10000L); /* wait for 10 msec */
9179  } while (HaveVirtualXIDsDelayingChkpt(vxids, nvxids));
9180  }
9181  pfree(vxids);
9182 
9183  CheckPointGuts(checkPoint.redo, flags);
9184 
9185  /*
9186  * Take a snapshot of running transactions and write this to WAL. This
9187  * allows us to reconstruct the state of running transactions during
9188  * archive recovery, if required. Skip, if this info disabled.
9189  *
9190  * If we are shutting down, or Startup process is completing crash
9191  * recovery we don't need to write running xact data.
9192  */
9193  if (!shutdown && XLogStandbyInfoActive())
9195 
9197 
9198  /*
9199  * Now insert the checkpoint record into XLOG.
9200  */
9201  XLogBeginInsert();
9202  XLogRegisterData((char *) (&checkPoint), sizeof(checkPoint));
9203  recptr = XLogInsert(RM_XLOG_ID,
9204  shutdown ? XLOG_CHECKPOINT_SHUTDOWN :
9206 
9207  XLogFlush(recptr);
9208 
9209  /*
9210  * We mustn't write any new WAL after a shutdown checkpoint, or it will be
9211  * overwritten at next startup. No-one should even try, this just allows
9212  * sanity-checking. In the case of an end-of-recovery checkpoint, we want
9213  * to just temporarily disable writing until the system has exited
9214  * recovery.
9215  */
9216  if (shutdown)
9217  {
9218  if (flags & CHECKPOINT_END_OF_RECOVERY)
9219  LocalXLogInsertAllowed = -1; /* return to "check" state */
9220  else
9221  LocalXLogInsertAllowed = 0; /* never again write WAL */
9222  }
9223 
9224  /*
9225  * We now have ProcLastRecPtr = start of actual checkpoint record, recptr
9226  * = end of actual checkpoint record.
9227  */
9228  if (shutdown && checkPoint.redo != ProcLastRecPtr)
9229  ereport(PANIC,
9230  (errmsg("concurrent write-ahead log activity while database system is shutting down")));
9231 
9232  /*
9233  * Remember the prior checkpoint's redo ptr for
9234  * UpdateCheckPointDistanceEstimate()
9235  */
9236  PriorRedoPtr = ControlFile->checkPointCopy.redo;
9237 
9238  /*
9239  * Update the control file.
9240  */
9241  LWLockAcquire(ControlFileLock, LW_EXCLUSIVE);
9242  if (shutdown)
9245  ControlFile->checkPointCopy = checkPoint;
9246  ControlFile->time = (pg_time_t) time(NULL);
9247  /* crash recovery should always recover to the end of WAL */
9250 
9251  /*
9252  * Persist unloggedLSN value. It's reset on crash recovery, so this goes
9253  * unused on non-shutdown checkpoints, but seems useful to store it always
9254  * for debugging purposes.
9255  */
9259 
9261  LWLockRelease(ControlFileLock);
9262 
9263  /* Update shared-memory copy of checkpoint XID/epoch */
9265  XLogCtl->ckptFullXid = checkPoint.nextXid;
9267 
9268  /*
9269  * We are now done with critical updates; no need for system panic if we
9270  * have trouble while fooling with old log segments.
9271  */
9272  END_CRIT_SECTION();
9273 
9274  /*
9275  * Let smgr do post-checkpoint cleanup (eg, deleting old files).
9276  */
9278 
9279  /*
9280  * Update the average distance between checkpoints if the prior checkpoint
9281  * exists.
9282  */
9283  if (PriorRedoPtr != InvalidXLogRecPtr)
9285 
9286  /*
9287  * Delete old log files, those no longer needed for last checkpoint to
9288  * prevent the disk holding the xlog from growing full.
9289  */
9291  KeepLogSeg(recptr, &_logSegNo);
9293  _logSegNo--;
9294  RemoveOldXlogFiles(_logSegNo, RedoRecPtr, recptr);
9295 
9296  /*
9297  * Make more log segments if needed. (Do this after recycling old log
9298  * segments, since that may supply some of the needed files.)
9299  */
9300  if (!shutdown)
9301  PreallocXlogFiles(recptr);
9302 
9303  /*
9304  * Truncate pg_subtrans if possible. We can throw away all data before
9305  * the oldest XMIN of any running transaction. No future transaction will
9306  * attempt to reference any pg_subtrans entry older than that (see Asserts
9307  * in subtrans.c). During recovery, though, we mustn't do this because
9308  * StartupSUBTRANS hasn't been called yet.
9309  */
9310  if (!RecoveryInProgress())
9312 
9313  /* Real work is done, but log and update stats before releasing lock. */
9314  LogCheckpointEnd(false);
9315 
9316  /* Reset the process title */
9317  update_checkpoint_display(flags, false, true);
9318 
9319  TRACE_POSTGRESQL_CHECKPOINT_DONE(CheckpointStats.ckpt_bufs_written,
9320  NBuffers,
9324 }
XLogRecPtr GetLastImportantRecPtr(void)
Definition: xlog.c:8607
static void UpdateCheckPointDistanceEstimate(uint64 nbytes)
Definition: xlog.c:8824
static int LocalXLogInsertAllowed
Definition: xlog.c:257
bool log_checkpoints
Definition: xlog.c:107
#define InvalidXLogRecPtr
Definition: xlogdefs.h:28
#define DEBUG1
Definition: elog.h:25
int64 pg_time_t
Definition: pgtime.h:23
static void WALInsertLockRelease(void)
Definition: xlog.c:1744
int wal_segment_size
Definition: xlog.c:121
pg_time_t time
Definition: pg_control.h:128
#define XLOG_CHECKPOINT_ONLINE
Definition: pg_control.h:68
TimeLineID minRecoveryPointTLI
Definition: pg_control.h:167
uint32 oidCount
Definition: transam.h:208
TimestampTz GetCurrentTimestamp(void)
Definition: timestamp.c:1580
static XLogRecPtr XLogBytePosToRecPtr(uint64 bytepos)
Definition: xlog.c:2013
XLogRecPtr unloggedLSN
Definition: xlog.c:612
XLogRecPtr ProcLastRecPtr
Definition: xlog.c:364
TransactionId oldestActiveXid
Definition: pg_control.h:63
void InitXLogInsert(void)
Definition: xloginsert.c:1197
TimestampTz ckpt_start_t
Definition: xlog.h:256
slock_t info_lck
Definition: xlog.c:737
#define END_CRIT_SECTION()
Definition: miscadmin.h:137
VirtualTransactionId * GetVirtualXIDsDelayingChkpt(int *nvxids)
Definition: procarray.c:2977
MultiXactId oldestMulti
Definition: pg_control.h:49
TimeLineID PrevTimeLineID
Definition: xlog.c:653
TimeLineID PrevTimeLineID
Definition: pg_control.h:40
#define START_CRIT_SECTION()
Definition: miscadmin.h:135
int ckpt_segs_recycled
Definition: xlog.h:266
TransactionId oldestXid
Definition: transam.h:215
#define MemSet(start, val, len)
Definition: c.h:1008
void MultiXactGetCheckptMulti(bool is_shutdown, MultiXactId *nextMulti, MultiXactOffset *nextMultiOffset, MultiXactId *oldestMulti, Oid *oldestMultiDB)
Definition: multixact.c:2130
static void CheckPointGuts(XLogRecPtr checkPointRedo, int flags)
Definition: xlog.c:9384
CheckPoint checkPointCopy
Definition: pg_control.h:131
XLogCtlInsert Insert
Definition: xlog.c:600
TransactionId oldestXid
Definition: pg_control.h:47
bool RecoveryInProgress(void)
Definition: xlog.c:8237
void TruncateSUBTRANS(TransactionId oldestXact)
Definition: subtrans.c:338
FullTransactionId nextXid
Definition: transam.h:213
pg_time_t time
Definition: pg_control.h:51
#define PANIC
Definition: elog.h:50
bool fullPageWrites
Definition: xlog.c:575
void XLogFlush(XLogRecPtr record)
Definition: xlog.c:2881
static void update_checkpoint_display(int flags, bool restartpoint, bool reset)
Definition: xlog.c:8862
void LWLockRelease(LWLock *lock)
Definition: lwlock.c:1805
#define SpinLockAcquire(lock)
Definition: spin.h:62
void pg_usleep(long microsec)
Definition: signal.c:53
MultiXactOffset nextMultiOffset
Definition: pg_control.h:46
void UpdateControlFile(void)
Definition: xlog.c:4956
TransactionId oldestCommitTsXid
Definition: pg_control.h:52
void pfree(void *pointer)
Definition: mcxt.c:1169
XLogRecPtr LogStandbySnapshot(void)
Definition: standby.c:1220
#define ERROR
Definition: elog.h:46
static void LogCheckpointEnd(bool restartpoint)
Definition: xlog.c:8732
static XLogRecPtr RedoRecPtr
Definition: xlog.c:378
#define XLOG_CHECKPOINT_SHUTDOWN
Definition: pg_control.h:67
XLogRecPtr unloggedLSN
Definition: pg_control.h:133
static void PreallocXlogFiles(XLogRecPtr endptr)
Definition: xlog.c:3943
uint64 XLogSegNo
Definition: xlogdefs.h:48
#define CHECKPOINT_END_OF_RECOVERY
Definition: xlog.h:232
VariableCache ShmemVariableCache
Definition: varsup.c:34
#define InvalidTransactionId
Definition: transam.h:31
uint64 CurrBytePos
Definition: xlog.c:550
unsigned int uint32
Definition: c.h:441
XLogRecPtr RedoRecPtr
Definition: xlog.c:604
int ckpt_segs_removed
Definition: xlog.h:265
#define CHECKPOINT_FORCE
Definition: xlog.h:235
#define INSERT_FREESPACE(endptr)
Definition: xlog.c:754
TransactionId oldestCommitTsXid
Definition: transam.h:225
static void Insert(File file)
Definition: fd.c:1222
int ckpt_bufs_written
Definition: xlog.h:262
static void LocalSetXLogInsertAllowed(void)
Definition: xlog.c:8381
void XLogRegisterData(char *data, int len)
Definition: xloginsert.c:330
#define SpinLockRelease(lock)
Definition: spin.h:64
XLogRecPtr XLogInsert(RmgrId rmid, uint8 info)
Definition: xloginsert.c:422
TransactionId newestCommitTsXid
Definition: pg_control.h:54
static void KeepLogSeg(XLogRecPtr recptr, XLogSegNo *logSegNo)
Definition: xlog.c:9803
#define XLogSegmentOffset(xlogptr, wal_segsz_bytes)
Oid oldestMultiDB
Definition: pg_control.h:50
FullTransactionId ckptFullXid
Definition: xlog.c:605
#define XLogStandbyInfoActive()
Definition: xlog.h:215
static ControlFileData * ControlFile
Definition: xlog.c:748
TimeLineID ThisTimeLineID
Definition: xlog.c:196
Oid nextOid
Definition: pg_control.h:44
#define ereport(elevel,...)
Definition: elog.h:157
bool fullPageWrites
Definition: pg_control.h:42
int errmsg_internal(const char *fmt,...)
Definition: elog.c:996
uint64 XLogRecPtr
Definition: xlogdefs.h:21
Oid oldestXidDB
Definition: pg_control.h:48
TransactionId newestCommitTsXid
Definition: transam.h:226
CheckpointStatsData CheckpointStats
Definition: xlog.c:190
#define SizeOfXLogShortPHD
Definition: xlog_internal.h:52
MultiXactId nextMulti
Definition: pg_control.h:45
static void WALInsertLockAcquireExclusive(void)
Definition: xlog.c:1715
static XLogCtlData * XLogCtl
Definition: xlog.c:740
bool LWLockAcquire(LWLock *lock, LWLockMode mode)
Definition: lwlock.c:1203
TransactionId GetOldestTransactionIdConsideredRunning(void)
Definition: procarray.c:1968
int ckpt_segs_added
Definition: xlog.h:264
slock_t ulsn_lck
Definition: xlog.c:613
TimeLineID ThisTimeLineID
Definition: pg_control.h:39
int errmsg(const char *fmt,...)
Definition: elog.c:909
void InvalidateObsoleteReplicationSlots(XLogSegNo oldestSegno)
Definition: slot.c:1168
#define elog(elevel,...)
Definition: elog.h:232
static void RemoveOldXlogFiles(XLogSegNo segno, XLogRecPtr lastredoptr, XLogRecPtr endptr)
Definition: xlog.c:4074
void SyncPostCheckpoint(void)
Definition: sync.c:195
TransactionId GetOldestActiveTransactionId(void)
Definition: procarray.c:2816
int NBuffers
Definition: globals.c:135
bool HaveVirtualXIDsDelayingChkpt(VirtualTransactionId *vxids, int nvxids)
Definition: procarray.c:3021
void XLogBeginInsert(void)
Definition: xloginsert.c:123
XLogRecPtr RedoRecPtr
Definition: xlog.c:573
XLogRecPtr checkPoint
Definition: pg_control.h:129
XLogRecPtr redo
Definition: pg_control.h:37
static void LogCheckpointStart(int flags, bool restartpoint)
Definition: xlog.c:8700
#define CHECKPOINT_IS_SHUTDOWN
Definition: xlog.h:231
XLogRecPtr minRecoveryPoint
Definition: pg_control.h:166
void SyncPreCheckpoint(void)
Definition: sync.c:180
FullTransactionId nextXid
Definition: pg_control.h:43
#define SizeOfXLogLongPHD
Definition: xlog_internal.h:69
#define XLByteToSeg(xlrp, logSegNo, wal_segsz_bytes)

◆ CreateRestartPoint()

bool CreateRestartPoint ( int  flags)

Definition at line 9465 of file xlog.c.

References archiveCleanupCommand, ControlFileData::checkPoint, CHECKPOINT_IS_SHUTDOWN, ControlFileData::checkPointCopy, CheckPointGuts(), CheckpointStatsData::ckpt_start_t, DB_IN_ARCHIVE_RECOVERY, DB_SHUTDOWNED_IN_RECOVERY, DEBUG2, EnableHotStandby, ereport, errdetail(), errmsg(), errmsg_internal(), ExecuteRecoveryCommand(), GetCurrentTimestamp(), GetLatestXTime(), GetOldestTransactionIdConsideredRunning(), GetWalRcvFlushRecPtr(), GetXLogReplayRecPtr(), XLogCtlData::info_lck, XLogCtlData::Insert, InvalidateObsoleteReplicationSlots(), InvalidXLogRecPtr, KeepLogSeg(), XLogCtlData::lastCheckPoint, XLogCtlData::lastCheckPointEndPtr, XLogCtlData::lastCheckPointRecPtr, LOG, log_checkpoints, LogCheckpointEnd(), LogCheckpointStart(), LSN_FORMAT_ARGS, LW_EXCLUSIVE, LWLockAcquire(), LWLockRelease(), MemSet, ControlFileData::minRecoveryPoint, minRecoveryPoint, ControlFileData::minRecoveryPointTLI, minRecoveryPointTLI, PreallocXlogFiles(), RecoveryInProgress(), CheckPoint::redo, RedoRecPtr, XLogCtlInsert::RedoRecPtr, XLogCtlData::RedoRecPtr, RemoveOldXlogFiles(), SpinLockAcquire, SpinLockRelease, ControlFileData::state, CheckPoint::ThisTimeLineID, ThisTimeLineID, ControlFileData::time, timestamptz_to_str(), TruncateSUBTRANS(), update_checkpoint_display(), UpdateCheckPointDistanceEstimate(), UpdateControlFile(), UpdateMinRecoveryPoint(), wal_segment_size, WALInsertLockAcquireExclusive(), WALInsertLockRelease(), XLByteToSeg, and XLogRecPtrIsInvalid.

Referenced by CheckpointerMain(), and ShutdownXLOG().

9466 {
9467  XLogRecPtr lastCheckPointRecPtr;
9468  XLogRecPtr lastCheckPointEndPtr;
9469  CheckPoint lastCheckPoint;
9470  XLogRecPtr PriorRedoPtr;
9471  XLogRecPtr receivePtr;
9472  XLogRecPtr replayPtr;
9473  TimeLineID replayTLI;
9474  XLogRecPtr endptr;
9475  XLogSegNo _logSegNo;
9476  TimestampTz xtime;
9477 
9478  /* Get a local copy of the last safe checkpoint record. */
9480  lastCheckPointRecPtr = XLogCtl->lastCheckPointRecPtr;
9481  lastCheckPointEndPtr = XLogCtl->lastCheckPointEndPtr;
9482  lastCheckPoint = XLogCtl->lastCheckPoint;
9484 
9485  /*
9486  * Check that we're still in recovery mode. It's ok if we exit recovery
9487  * mode after this check, the restart point is valid anyway.
9488  */
9489  if (!RecoveryInProgress())
9490  {
9491  ereport(DEBUG2,
9492  (errmsg_internal("skipping restartpoint, recovery has already ended")));
9493  return false;
9494  }
9495 
9496  /*
9497  * If the last checkpoint record we've replayed is already our last
9498  * restartpoint, we can't perform a new restart point. We still update
9499  * minRecoveryPoint in that case, so that if this is a shutdown restart
9500  * point, we won't start up earlier than before. That's not strictly
9501  * necessary, but when hot standby is enabled, it would be rather weird if
9502  * the database opened up for read-only connections at a point-in-time
9503  * before the last shutdown. Such time travel is still possible in case of
9504  * immediate shutdown, though.
9505  *
9506  * We don't explicitly advance minRecoveryPoint when we do create a
9507  * restartpoint. It's assumed that flushing the buffers will do that as a
9508  * side-effect.
9509  */
9510  if (XLogRecPtrIsInvalid(lastCheckPointRecPtr) ||
9511  lastCheckPoint.redo <= ControlFile->checkPointCopy.redo)
9512  {
9513  ereport(DEBUG2,
9514  (errmsg_internal("skipping restartpoint, already performed at %X/%X",
9515  LSN_FORMAT_ARGS(lastCheckPoint.redo))));
9516 
9518  if (flags & CHECKPOINT_IS_SHUTDOWN)
9519  {
9520  LWLockAcquire(ControlFileLock, LW_EXCLUSIVE);
9522  ControlFile->time = (pg_time_t) time(NULL);
9524  LWLockRelease(ControlFileLock);
9525  }
9526  return false;
9527  }
9528 
9529  /*
9530  * Update the shared RedoRecPtr so that the startup process can calculate
9531  * the number of segments replayed since last restartpoint, and request a
9532  * restartpoint if it exceeds CheckPointSegments.
9533  *
9534  * Like in CreateCheckPoint(), hold off insertions to update it, although
9535  * during recovery this is just pro forma, because no WAL insertions are
9536  * happening.
9537  */
9539  RedoRecPtr = XLogCtl->Insert.RedoRecPtr = lastCheckPoint.redo;
9541 
9542  /* Also update the info_lck-protected copy */
9544  XLogCtl->RedoRecPtr = lastCheckPoint.redo;
9546 
9547  /*
9548  * Prepare to accumulate statistics.
9549  *
9550  * Note: because it is possible for log_checkpoints to change while a
9551  * checkpoint proceeds, we always accumulate stats, even if
9552  * log_checkpoints is currently off.
9553  */
9554  MemSet(&CheckpointStats, 0, sizeof(CheckpointStats));
9556 
9557  if (log_checkpoints)
9558  LogCheckpointStart(flags, true);
9559 
9560  /* Update the process title */
9561  update_checkpoint_display(flags, true, false);
9562 
9563  CheckPointGuts(lastCheckPoint.redo, flags);
9564 
9565  /*
9566  * Remember the prior checkpoint's redo ptr for
9567  * UpdateCheckPointDistanceEstimate()
9568  */
9569  PriorRedoPtr = ControlFile->checkPointCopy.redo;
9570 
9571  /*
9572  * Update pg_control, using current time. Check that it still shows
9573  * DB_IN_ARCHIVE_RECOVERY state and an older checkpoint, else do nothing;
9574  * this is a quick hack to make sure nothing really bad happens if somehow
9575  * we get here after the end-of-recovery checkpoint.
9576  */
9577  LWLockAcquire(ControlFileLock, LW_EXCLUSIVE);
9579  ControlFile->checkPointCopy.redo < lastCheckPoint.redo)
9580  {
9581  ControlFile->checkPoint = lastCheckPointRecPtr;
9582  ControlFile->checkPointCopy = lastCheckPoint;
9583  ControlFile->time = (pg_time_t) time(NULL);
9584 
9585  /*
9586  * Ensure minRecoveryPoint is past the checkpoint record. Normally,
9587  * this will have happened already while writing out dirty buffers,
9588  * but not necessarily - e.g. because no buffers were dirtied. We do
9589  * this because a non-exclusive base backup uses minRecoveryPoint to
9590  * determine which WAL files must be included in the backup, and the
9591  * file (or files) containing the checkpoint record must be included,
9592  * at a minimum. Note that for an ordinary restart of recovery there's
9593  * no value in having the minimum recovery point any earlier than this
9594  * anyway, because redo will begin just after the checkpoint record.
9595  */
9596  if (ControlFile->minRecoveryPoint < lastCheckPointEndPtr)
9597  {
9598  ControlFile->minRecoveryPoint = lastCheckPointEndPtr;
9600 
9601  /* update local copy */
9604  }
9605  if (flags & CHECKPOINT_IS_SHUTDOWN)
9608  }
9609  LWLockRelease(ControlFileLock);
9610 
9611  /*
9612  * Update the average distance between checkpoints/restartpoints if the
9613  * prior checkpoint exists.
9614  */
9615  if (PriorRedoPtr != InvalidXLogRecPtr)
9617 
9618  /*
9619  * Delete old log files, those no longer needed for last restartpoint to
9620  * prevent the disk holding the xlog from growing full.
9621  */
9623 
9624  /*
9625  * Retreat _logSegNo using the current end of xlog replayed or received,
9626  * whichever is later.
9627  */
9628  receivePtr = GetWalRcvFlushRecPtr(NULL, NULL);
9629  replayPtr = GetXLogReplayRecPtr(&replayTLI);
9630  endptr = (receivePtr < replayPtr) ? replayPtr : receivePtr;
9631  KeepLogSeg(endptr, &_logSegNo);
9633  _logSegNo--;
9634 
9635  /*
9636  * Try to recycle segments on a useful timeline. If we've been promoted
9637  * since the beginning of this restartpoint, use the new timeline chosen
9638  * at end of recovery (RecoveryInProgress() sets ThisTimeLineID in that
9639  * case). If we're still in recovery, use the timeline we're currently
9640  * replaying.
9641  *
9642  * There is no guarantee that the WAL segments will be useful on the
9643  * current timeline; if recovery proceeds to a new timeline right after
9644  * this, the pre-allocated WAL segments on this timeline will not be used,
9645  * and will go wasted until recycled on the next restartpoint. We'll live
9646  * with that.
9647  */
9648  if (RecoveryInProgress())
9649  ThisTimeLineID = replayTLI;
9650 
9651  RemoveOldXlogFiles(_logSegNo, RedoRecPtr, endptr);
9652 
9653  /*
9654  * Make more log segments if needed. (Do this after recycling old log
9655  * segments, since that may supply some of the needed files.)
9656  */
9657  PreallocXlogFiles(endptr);
9658 
9659  /*
9660  * ThisTimeLineID is normally not set when we're still in recovery.
9661  * However, recycling/preallocating segments above needed ThisTimeLineID
9662  * to determine which timeline to install the segments on. Reset it now,
9663  * to restore the normal state of affairs for debugging purposes.
9664  */
9665  if (RecoveryInProgress())
9666  ThisTimeLineID = 0;
9667 
9668  /*
9669  * Truncate pg_subtrans if possible. We can throw away all data before
9670  * the oldest XMIN of any running transaction. No future transaction will
9671  * attempt to reference any pg_subtrans entry older than that (see Asserts
9672  * in subtrans.c). When hot standby is disabled, though, we mustn't do
9673  * this because StartupSUBTRANS hasn't been called yet.
9674  */
9675  if (EnableHotStandby)
9677 
9678  /* Real work is done, but log and update before releasing lock. */
9679  LogCheckpointEnd(true);
9680 
9681  /* Reset the process title */
9682  update_checkpoint_display(flags, true, true);
9683 
9684  xtime = GetLatestXTime();
9686  (errmsg("recovery restart point at %X/%X",
9687  LSN_FORMAT_ARGS(lastCheckPoint.redo)),
9688  xtime ? errdetail("Last completed transaction was at log time %s.",
9689  timestamptz_to_str(xtime)) : 0));
9690 
9691  /*
9692  * Finally, execute archive_cleanup_command, if any.
9693  */
9694  if (archiveCleanupCommand && strcmp(archiveCleanupCommand, "") != 0)
9696  "archive_cleanup_command",
9697  false);
9698 
9699  return true;
9700 }
static void UpdateCheckPointDistanceEstimate(uint64 nbytes)
Definition: xlog.c:8824
bool log_checkpoints
Definition: xlog.c:107
void ExecuteRecoveryCommand(const char *command, const char *commandName, bool failOnSignal)
Definition: xlogarchive.c:287
#define InvalidXLogRecPtr
Definition: xlogdefs.h:28
uint32 TimeLineID
Definition: xlogdefs.h:59
int64 pg_time_t
Definition: pgtime.h:23
static void WALInsertLockRelease(void)
Definition: xlog.c:1744
int wal_segment_size
Definition: xlog.c:121
pg_time_t time
Definition: pg_control.h:128
TimeLineID minRecoveryPointTLI
Definition: pg_control.h:167
TimestampTz GetCurrentTimestamp(void)
Definition: timestamp.c:1580
int64 TimestampTz
Definition: timestamp.h:39
static void UpdateMinRecoveryPoint(XLogRecPtr lsn, bool force)
Definition: xlog.c:2797
TimestampTz ckpt_start_t
Definition: xlog.h:256
slock_t info_lck
Definition: xlog.c:737
#define MemSet(start, val, len)
Definition: c.h:1008
static void CheckPointGuts(XLogRecPtr checkPointRedo, int flags)
Definition: xlog.c:9384
TimestampTz GetLatestXTime(void)
Definition: xlog.c:6263
CheckPoint checkPointCopy
Definition: pg_control.h:131
XLogCtlInsert Insert
Definition: xlog.c:600
#define LOG
Definition: elog.h:26
bool RecoveryInProgress(void)
Definition: xlog.c:8237
void TruncateSUBTRANS(TransactionId oldestXact)
Definition: subtrans.c:338
XLogRecPtr lastCheckPointRecPtr
Definition: xlog.c:705
static void update_checkpoint_display(int flags, bool restartpoint, bool reset)
Definition: xlog.c:8862
void LWLockRelease(LWLock *lock)
Definition: lwlock.c:1805
#define SpinLockAcquire(lock)
Definition: spin.h:62
#define LSN_FORMAT_ARGS(lsn)
Definition: xlogdefs.h:43
void UpdateControlFile(void)
Definition: xlog.c:4956
static void LogCheckpointEnd(bool restartpoint)
Definition: xlog.c:8732
XLogRecPtr GetXLogReplayRecPtr(TimeLineID *replayTLI)
Definition: xlog.c:11728
#define DEBUG2
Definition: elog.h:24
static XLogRecPtr RedoRecPtr
Definition: xlog.c:378
static void PreallocXlogFiles(XLogRecPtr endptr)
Definition: xlog.c:3943
uint64 XLogSegNo
Definition: xlogdefs.h:48
int errdetail(const char *fmt,...)
Definition: elog.c:1042
XLogRecPtr RedoRecPtr
Definition: xlog.c:604
CheckPoint lastCheckPoint
Definition: xlog.c:707
#define XLogRecPtrIsInvalid(r)
Definition: xlogdefs.h:29
#define SpinLockRelease(lock)
Definition: spin.h:64
static TimeLineID minRecoveryPointTLI
Definition: xlog.c:862
static void KeepLogSeg(XLogRecPtr recptr, XLogSegNo *logSegNo)
Definition: xlog.c:9803
static ControlFileData * ControlFile
Definition: xlog.c:748
TimeLineID ThisTimeLineID
Definition: xlog.c:196
#define ereport(elevel,...)
Definition: elog.h:157
int errmsg_internal(const char *fmt,...)
Definition: elog.c:996
uint64 XLogRecPtr
Definition: xlogdefs.h:21
CheckpointStatsData CheckpointStats
Definition: xlog.c:190
static void WALInsertLockAcquireExclusive(void)
Definition: xlog.c:1715
static XLogCtlData * XLogCtl
Definition: xlog.c:740
bool LWLockAcquire(LWLock *lock, LWLockMode mode)
Definition: lwlock.c:1203
TransactionId GetOldestTransactionIdConsideredRunning(void)
Definition: procarray.c:1968
XLogRecPtr GetWalRcvFlushRecPtr(XLogRecPtr *latestChunkStart, TimeLineID *receiveTLI)
bool EnableHotStandby
Definition: xlog.c:99
TimeLineID ThisTimeLineID
Definition: pg_control.h:39
int errmsg(const char *fmt,...)
Definition: elog.c:909
void InvalidateObsoleteReplicationSlots(XLogSegNo oldestSegno)
Definition: slot.c:1168
static void RemoveOldXlogFiles(XLogSegNo segno, XLogRecPtr lastredoptr, XLogRecPtr endptr)
Definition: xlog.c:4074
XLogRecPtr RedoRecPtr
Definition: xlog.c:573
XLogRecPtr lastCheckPointEndPtr
Definition: xlog.c:706
XLogRecPtr checkPoint
Definition: pg_control.h:129
XLogRecPtr redo
Definition: pg_control.h:37
static void LogCheckpointStart(int flags, bool restartpoint)
Definition: xlog.c:8700
char * archiveCleanupCommand
Definition: xlog.c:286
#define CHECKPOINT_IS_SHUTDOWN
Definition: xlog.h:231
XLogRecPtr minRecoveryPoint
Definition: pg_control.h:166
static XLogRecPtr minRecoveryPoint
Definition: xlog.c:861
const char * timestamptz_to_str(TimestampTz t)
Definition: timestamp.c:1774
#define XLByteToSeg(xlrp, logSegNo, wal_segsz_bytes)

◆ DataChecksumsEnabled()

bool DataChecksumsEnabled ( void  )

Definition at line 4985 of file xlog.c.

References Assert, and ControlFileData::data_checksum_version.

Referenced by PageIsVerifiedExtended(), PageSetChecksumCopy(), PageSetChecksumInplace(), pg_stat_get_db_checksum_failures(), pg_stat_get_db_checksum_last_failure(), ReadControlFile(), and sendFile().

4986 {
4987  Assert(ControlFile != NULL);
4988  return (ControlFile->data_checksum_version > 0);
4989 }
uint32 data_checksum_version
Definition: pg_control.h:220
static ControlFileData * ControlFile
Definition: xlog.c:748
#define Assert(condition)
Definition: c.h:804

◆ do_pg_abort_backup()

void do_pg_abort_backup ( int  code,
Datum  arg 
)

Definition at line 11680 of file xlog.c.

References Assert, DatumGetBool, ereport, errmsg(), EXCLUSIVE_BACKUP_NONE, XLogCtlInsert::exclusiveBackupState, XLogCtlInsert::forcePageWrites, XLogCtlData::Insert, XLogCtlInsert::nonExclusiveBackups, SESSION_BACKUP_NON_EXCLUSIVE, sessionBackupState, WALInsertLockAcquireExclusive(), WALInsertLockRelease(), and WARNING.

Referenced by perform_base_backup(), and register_persistent_abort_backup_handler().

11681 {
11682  bool emit_warning = DatumGetBool(arg);
11683 
11684  /*
11685  * Quick exit if session is not keeping around a non-exclusive backup
11686  * already started.
11687  */
11689  return;
11690 
11694 
11697  {
11698  XLogCtl->Insert.forcePageWrites = false;
11699  }
11701 
11702  if (emit_warning)
11703  ereport(WARNING,
11704  (errmsg("aborting backup due to backend exiting before pg_stop_backup was called")));
11705 }
static void WALInsertLockRelease(void)
Definition: xlog.c:1744
static SessionBackupState sessionBackupState
Definition: xlog.c:534
XLogCtlInsert Insert
Definition: xlog.c:600
bool forcePageWrites
Definition: xlog.c:574
#define DatumGetBool(X)
Definition: postgres.h:437
#define WARNING
Definition: elog.h:40
int nonExclusiveBackups
Definition: xlog.c:586
ExclusiveBackupState exclusiveBackupState
Definition: xlog.c:585
#define ereport(elevel,...)
Definition: elog.h:157
#define Assert(condition)
Definition: c.h:804
static void WALInsertLockAcquireExclusive(void)
Definition: xlog.c:1715
static XLogCtlData * XLogCtl
Definition: xlog.c:740
int errmsg(const char *fmt,...)
Definition: elog.c:909
void * arg

◆ do_pg_start_backup()

XLogRecPtr do_pg_start_backup ( const char *  backupidstr,
bool  fast,
TimeLineID starttli_p,
StringInfo  labelfile,
List **  tablespaces,
StringInfo  tblspcmapfile 
)

Definition at line 10749 of file xlog.c.

References AllocateDir(), AllocateFile(), appendStringInfo(), appendStringInfoChar(), BACKUP_LABEL_FILE, backup_started_in_recovery, BoolGetDatum, ControlFileData::checkPoint, CHECKPOINT_FORCE, CHECKPOINT_IMMEDIATE, CHECKPOINT_WAIT, ControlFileData::checkPointCopy, dirent::d_name, StringInfoData::data, DataDir, ereport, errcode(), errcode_for_file_access(), errhint(), errmsg(), ERROR, EXCLUSIVE_BACKUP_IN_PROGRESS, EXCLUSIVE_BACKUP_NONE, EXCLUSIVE_BACKUP_STARTING, XLogCtlInsert::exclusiveBackupState, XLogCtlInsert::forcePageWrites, FreeDir(), FreeFile(), CheckPoint::fullPageWrites, XLogCtlData::info_lck, initStringInfo(), XLogCtlData::Insert, IS_DIR_SEP, lappend(), XLogCtlInsert::lastBackupStart, XLogCtlData::lastFpwDisableRecPtr, StringInfoData::len, log_timezone, LSN_FORMAT_ARGS, LW_SHARED, LWLockAcquire(), LWLockRelease(), makeStringInfo(), MAXFNAMELEN, MAXPGPATH, XLogCtlInsert::nonExclusiveBackups, tablespaceinfo::oid, palloc(), tablespaceinfo::path, pfree(), PG_END_ENSURE_ERROR_CLEANUP, PG_ENSURE_ERROR_CLEANUP, pg_fsync(), pg_localtime(), pg_start_backup_callback(), pg_strftime(), pstrdup(), ReadDir(), readlink, RecoveryInProgress(), CheckPoint::redo, relpath, RequestCheckpoint(), RequestXLogSwitch(), tablespaceinfo::rpath, SESSION_BACKUP_EXCLUSIVE, SESSION_BACKUP_NON_EXCLUSIVE, sessionBackupState, tablespaceinfo::size, snprintf, SpinLockAcquire, SpinLockRelease, stat, TABLESPACE_MAP, CheckPoint::ThisTimeLineID, wal_segment_size, WALInsertLockAcquireExclusive(), WALInsertLockRelease(), WARNING, XLByteToSeg, XLogFileName, and XLogIsNeeded.

Referenced by perform_base_backup(), and pg_start_backup().

10752 {
10753  bool exclusive = (labelfile == NULL);
10754  bool backup_started_in_recovery = false;
10755  XLogRecPtr checkpointloc;
10756  XLogRecPtr startpoint;
10757  TimeLineID starttli;
10758  pg_time_t stamp_time;
10759  char strfbuf[128];
10760  char xlogfilename[MAXFNAMELEN];
10761  XLogSegNo _logSegNo;
10762  struct stat stat_buf;
10763  FILE *fp;
10764 
10765  backup_started_in_recovery = RecoveryInProgress();
10766 
10767  /*
10768  * Currently only non-exclusive backup can be taken during recovery.
10769  */
10770  if (backup_started_in_recovery && exclusive)
10771  ereport(ERROR,
10772  (errcode(ERRCODE_OBJECT_NOT_IN_PREREQUISITE_STATE),
10773  errmsg("recovery is in progress"),
10774  errhint("WAL control functions cannot be executed during recovery.")));
10775 
10776  /*
10777  * During recovery, we don't need to check WAL level. Because, if WAL
10778  * level is not sufficient, it's impossible to get here during recovery.
10779  */
10780  if (!backup_started_in_recovery && !XLogIsNeeded())
10781  ereport(ERROR,
10782  (errcode(ERRCODE_OBJECT_NOT_IN_PREREQUISITE_STATE),
10783  errmsg("WAL level not sufficient for making an online backup"),
10784  errhint("wal_level must be set to \"replica\" or \"logical\" at server start.")));
10785 
10786  if (strlen(backupidstr) > MAXPGPATH)
10787  ereport(ERROR,
10788  (errcode(ERRCODE_INVALID_PARAMETER_VALUE),
10789  errmsg("backup label too long (max %d bytes)",
10790  MAXPGPATH)));
10791 
10792  /*
10793  * Mark backup active in shared memory. We must do full-page WAL writes
10794  * during an on-line backup even if not doing so at other times, because
10795  * it's quite possible for the backup dump to obtain a "torn" (partially
10796  * written) copy of a database page if it reads the page concurrently with
10797  * our write to the same page. This can be fixed as long as the first
10798  * write to the page in the WAL sequence is a full-page write. Hence, we
10799  * turn on forcePageWrites and then force a CHECKPOINT, to ensure there
10800  * are no dirty pages in shared memory that might get dumped while the
10801  * backup is in progress without having a corresponding WAL record. (Once
10802  * the backup is complete, we need not force full-page writes anymore,
10803  * since we expect that any pages not modified during the backup interval
10804  * must have been correctly captured by the backup.)
10805  *
10806  * Note that forcePageWrites has no effect during an online backup from
10807  * the standby.
10808  *
10809  * We must hold all the insertion locks to change the value of
10810  * forcePageWrites, to ensure adequate interlocking against
10811  * XLogInsertRecord().
10812  */
10814  if (exclusive)
10815  {
10816  /*
10817  * At first, mark that we're now starting an exclusive backup, to
10818  * ensure that there are no other sessions currently running
10819  * pg_start_backup() or pg_stop_backup().
10820  */
10822  {
10824  ereport(ERROR,
10825  (errcode(ERRCODE_OBJECT_NOT_IN_PREREQUISITE_STATE),
10826  errmsg("a backup is already in progress"),
10827  errhint("Run pg_stop_backup() and try again.")));
10828  }
10830  }
10831  else
10833  XLogCtl->Insert.forcePageWrites = true;
10835 
10836  /* Ensure we release forcePageWrites if fail below */
10838  {
10839  bool gotUniqueStartpoint = false;
10840  DIR *tblspcdir;
10841  struct dirent *de;
10842  tablespaceinfo *ti;
10843  int datadirpathlen;
10844 
10845  /*
10846  * Force an XLOG file switch before the checkpoint, to ensure that the
10847  * WAL segment the checkpoint is written to doesn't contain pages with
10848  * old timeline IDs. That would otherwise happen if you called
10849  * pg_start_backup() right after restoring from a PITR archive: the
10850  * first WAL segment containing the startup checkpoint has pages in
10851  * the beginning with the old timeline ID. That can cause trouble at
10852  * recovery: we won't have a history file covering the old timeline if
10853  * pg_wal directory was not included in the base backup and the WAL
10854  * archive was cleared too before starting the backup.
10855  *
10856  * This also ensures that we have emitted a WAL page header that has
10857  * XLP_BKP_REMOVABLE off before we emit the checkpoint record.
10858  * Therefore, if a WAL archiver (such as pglesslog) is trying to
10859  * compress out removable backup blocks, it won't remove any that
10860  * occur after this point.
10861  *
10862  * During recovery, we skip forcing XLOG file switch, which means that
10863  * the backup taken during recovery is not available for the special
10864  * recovery case described above.
10865  */
10866  if (!backup_started_in_recovery)
10867  RequestXLogSwitch(false);
10868 
10869  do
10870  {
10871  bool checkpointfpw;
10872 
10873  /*
10874  * Force a CHECKPOINT. Aside from being necessary to prevent torn
10875  * page problems, this guarantees that two successive backup runs
10876  * will have different checkpoint positions and hence different
10877  * history file names, even if nothing happened in between.
10878  *
10879  * During recovery, establish a restartpoint if possible. We use
10880  * the last restartpoint as the backup starting checkpoint. This
10881  * means that two successive backup runs can have same checkpoint
10882  * positions.
10883  *
10884  * Since the fact that we are executing do_pg_start_backup()
10885  * during recovery means that checkpointer is running, we can use
10886  * RequestCheckpoint() to establish a restartpoint.
10887  *
10888  * We use CHECKPOINT_IMMEDIATE only if requested by user (via
10889  * passing fast = true). Otherwise this can take awhile.
10890  */
10892  (fast ? CHECKPOINT_IMMEDIATE : 0));
10893 
10894  /*
10895  * Now we need to fetch the checkpoint record location, and also
10896  * its REDO pointer. The oldest point in WAL that would be needed
10897  * to restore starting from the checkpoint is precisely the REDO
10898  * pointer.
10899  */
10900  LWLockAcquire(ControlFileLock, LW_SHARED);
10901  checkpointloc = ControlFile->checkPoint;
10902  startpoint = ControlFile->checkPointCopy.redo;
10904  checkpointfpw = ControlFile->checkPointCopy.fullPageWrites;
10905  LWLockRelease(ControlFileLock);
10906 
10907  if (backup_started_in_recovery)
10908  {
10909  XLogRecPtr recptr;
10910 
10911  /*
10912  * Check to see if all WAL replayed during online backup
10913  * (i.e., since last restartpoint used as backup starting
10914  * checkpoint) contain full-page writes.
10915  */
10917  recptr = XLogCtl->lastFpwDisableRecPtr;
10919 
10920  if (!checkpointfpw || startpoint <= recptr)
10921  ereport(ERROR,
10922  (errcode(ERRCODE_OBJECT_NOT_IN_PREREQUISITE_STATE),
10923  errmsg("WAL generated with full_page_writes=off was replayed "
10924  "since last restartpoint"),
10925  errhint("This means that the backup being taken on the standby "
10926  "is corrupt and should not be used. "
10927  "Enable full_page_writes and run CHECKPOINT on the primary, "
10928  "and then try an online backup again.")));
10929 
10930  /*
10931  * During recovery, since we don't use the end-of-backup WAL
10932  * record and don't write the backup history file, the
10933  * starting WAL location doesn't need to be unique. This means
10934  * that two base backups started at the same time might use
10935  * the same checkpoint as starting locations.
10936  */
10937  gotUniqueStartpoint = true;
10938  }
10939 
10940  /*
10941  * If two base backups are started at the same time (in WAL sender
10942  * processes), we need to make sure that they use different
10943  * checkpoints as starting locations, because we use the starting
10944  * WAL location as a unique identifier for the base backup in the
10945  * end-of-backup WAL record and when we write the backup history
10946  * file. Perhaps it would be better generate a separate unique ID
10947  * for each backup instead of forcing another checkpoint, but
10948  * taking a checkpoint right after another is not that expensive
10949  * either because only few buffers have been dirtied yet.
10950  */
10952  if (XLogCtl->Insert.lastBackupStart < startpoint)
10953  {
10954  XLogCtl->Insert.lastBackupStart = startpoint;
10955  gotUniqueStartpoint = true;
10956  }
10958  } while (!gotUniqueStartpoint);
10959 
10960  XLByteToSeg(startpoint, _logSegNo, wal_segment_size);
10961  XLogFileName(xlogfilename, starttli, _logSegNo, wal_segment_size);
10962 
10963  /*
10964  * Construct tablespace_map file. If caller isn't interested in this,
10965  * we make a local StringInfo.
10966  */
10967  if (tblspcmapfile == NULL)
10968  tblspcmapfile = makeStringInfo();
10969 
10970  datadirpathlen = strlen(DataDir);
10971 
10972  /* Collect information about all tablespaces */
10973  tblspcdir = AllocateDir("pg_tblspc");
10974  while ((de = ReadDir(tblspcdir, "pg_tblspc")) != NULL)
10975  {
10976  char fullpath[MAXPGPATH + 10];
10977  char linkpath[MAXPGPATH];
10978  char *relpath = NULL;
10979  int rllen;
10980  StringInfoData escapedpath;
10981  char *s;
10982 
10983  /* Skip anything that doesn't look like a tablespace */
10984  if (strspn(de->d_name, "0123456789") != strlen(de->d_name))
10985  continue;
10986 
10987  snprintf(fullpath, sizeof(fullpath), "pg_tblspc/%s", de->d_name);
10988 
10989 #if defined(HAVE_READLINK) || defined(WIN32)
10990  rllen = readlink(fullpath, linkpath, sizeof(linkpath));
10991  if (rllen < 0)
10992  {
10993  ereport(WARNING,
10994  (errmsg("could not read symbolic link \"%s\": %m",
10995  fullpath)));
10996  continue;
10997  }
10998  else if (rllen >= sizeof(linkpath))
10999  {
11000  ereport(WARNING,
11001  (errmsg("symbolic link \"%s\" target is too long",
11002  fullpath)));
11003  continue;
11004  }
11005  linkpath[rllen] = '\0';
11006 
11007  /*
11008  * Build a backslash-escaped version of the link path to include
11009  * in the tablespace map file.
11010  */
11011  initStringInfo(&escapedpath);
11012  for (s = linkpath; *s; s++)
11013  {
11014  if (*s == '\n' || *s == '\r' || *s == '\\')
11015  appendStringInfoChar(&escapedpath, '\\');
11016  appendStringInfoChar(&escapedpath, *s);
11017  }
11018 
11019  /*
11020  * Relpath holds the relative path of the tablespace directory
11021  * when it's located within PGDATA, or NULL if it's located
11022  * elsewhere.
11023  */
11024  if (rllen > datadirpathlen &&
11025  strncmp(linkpath, DataDir, datadirpathlen) == 0 &&
11026  IS_DIR_SEP(linkpath[datadirpathlen]))
11027  relpath = linkpath + datadirpathlen + 1;
11028 
11029  ti = palloc(sizeof(tablespaceinfo));
11030  ti->oid = pstrdup(de->d_name);
11031  ti->path = pstrdup(linkpath);
11032  ti->rpath = relpath ? pstrdup(relpath) : NULL;
11033  ti->size = -1;
11034 
11035  if (tablespaces)
11036  *tablespaces = lappend(*tablespaces, ti);
11037 
11038  appendStringInfo(tblspcmapfile, "%s %s\n",
11039  ti->oid, escapedpath.data);
11040 
11041  pfree(escapedpath.data);
11042 #else
11043 
11044  /*
11045  * If the platform does not have symbolic links, it should not be
11046  * possible to have tablespaces - clearly somebody else created
11047  * them. Warn about it and ignore.
11048  */
11049  ereport(WARNING,
11050  (errcode(ERRCODE_FEATURE_NOT_SUPPORTED),
11051  errmsg("tablespaces are not supported on this platform")));
11052 #endif
11053  }
11054  FreeDir(tblspcdir);
11055 
11056  /*
11057  * Construct backup label file. If caller isn't interested in this,
11058  * we make a local StringInfo.
11059  */
11060  if (labelfile == NULL)
11061  labelfile = makeStringInfo();
11062 
11063  /* Use the log timezone here, not the session timezone */
11064  stamp_time = (pg_time_t) time(NULL);
11065  pg_strftime(strfbuf, sizeof(strfbuf),
11066  "%Y-%m-%d %H:%M:%S %Z",
11067  pg_localtime(&stamp_time, log_timezone));
11068  appendStringInfo(labelfile, "START WAL LOCATION: %X/%X (file %s)\n",
11069  LSN_FORMAT_ARGS(startpoint), xlogfilename);
11070  appendStringInfo(labelfile, "CHECKPOINT LOCATION: %X/%X\n",
11071  LSN_FORMAT_ARGS(checkpointloc));
11072  appendStringInfo(labelfile, "BACKUP METHOD: %s\n",
11073  exclusive ? "pg_start_backup" : "streamed");
11074  appendStringInfo(labelfile, "BACKUP FROM: %s\n",
11075  backup_started_in_recovery ? "standby" : "primary");
11076  appendStringInfo(labelfile, "START TIME: %s\n", strfbuf);
11077  appendStringInfo(labelfile, "LABEL: %s\n", backupidstr);
11078  appendStringInfo(labelfile, "START TIMELINE: %u\n", starttli);
11079 
11080  /*
11081  * Okay, write the file, or return its contents to caller.
11082  */
11083  if (exclusive)
11084  {
11085  /*
11086  * Check for existing backup label --- implies a backup is already
11087  * running. (XXX given that we checked exclusiveBackupState
11088  * above, maybe it would be OK to just unlink any such label
11089  * file?)
11090  */
11091  if (stat(BACKUP_LABEL_FILE, &stat_buf) != 0)
11092  {
11093  if (errno != ENOENT)
11094  ereport(ERROR,
11096  errmsg("could not stat file \"%s\": %m",
11097  BACKUP_LABEL_FILE)));
11098  }
11099  else
11100  ereport(ERROR,
11101  (errcode(ERRCODE_OBJECT_NOT_IN_PREREQUISITE_STATE),
11102  errmsg("a backup is already in progress"),
11103  errhint("If you're sure there is no backup in progress, remove file \"%s\" and try again.",
11104  BACKUP_LABEL_FILE)));
11105 
11106  fp = AllocateFile(BACKUP_LABEL_FILE, "w");
11107 
11108  if (!fp)
11109  ereport(ERROR,
11111  errmsg("could not create file \"%s\": %m",
11112  BACKUP_LABEL_FILE)));
11113  if (fwrite(labelfile->data, labelfile->len, 1, fp) != 1 ||
11114  fflush(fp) != 0 ||
11115  pg_fsync(fileno(fp)) != 0 ||
11116  ferror(fp) ||
11117  FreeFile(fp))
11118  ereport(ERROR,
11120  errmsg("could not write file \"%s\": %m",
11121  BACKUP_LABEL_FILE)));
11122  /* Allocated locally for exclusive backups, so free separately */
11123  pfree(labelfile->data);
11124  pfree(labelfile);
11125 
11126  /* Write backup tablespace_map file. */
11127  if (tblspcmapfile->len > 0)
11128  {
11129  if (stat(TABLESPACE_MAP, &stat_buf) != 0)
11130  {
11131  if (errno != ENOENT)
11132  ereport(ERROR,
11134  errmsg("could not stat file \"%s\": %m",
11135  TABLESPACE_MAP)));
11136  }
11137  else
11138  ereport(ERROR,
11139  (errcode(ERRCODE_OBJECT_NOT_IN_PREREQUISITE_STATE),
11140  errmsg("a backup is already in progress"),
11141  errhint("If you're sure there is no backup in progress, remove file \"%s\" and try again.",
11142  TABLESPACE_MAP)));
11143 
11144  fp = AllocateFile(TABLESPACE_MAP, "w");
11145 
11146  if (!fp)
11147  ereport(ERROR,
11149  errmsg("could not create file \"%s\": %m",
11150  TABLESPACE_MAP)));
11151  if (fwrite(tblspcmapfile->data, tblspcmapfile->len, 1, fp) != 1 ||
11152  fflush(fp) != 0 ||
11153  pg_fsync(fileno(fp)) != 0 ||
11154  ferror(fp) ||
11155  FreeFile(fp))
11156  ereport(ERROR,
11158  errmsg("could not write file \"%s\": %m",
11159  TABLESPACE_MAP)));
11160  }
11161 
11162  /* Allocated locally for exclusive backups, so free separately */
11163  pfree(tblspcmapfile->data);
11164  pfree(tblspcmapfile);
11165  }
11166  }
11168 
11169  /*
11170  * Mark that start phase has correctly finished for an exclusive backup.
11171  * Session-level locks are updated as well to reflect that state.
11172  *
11173  * Note that CHECK_FOR_INTERRUPTS() must not occur while updating backup
11174  * counters and session-level lock. Otherwise they can be updated
11175  * inconsistently, and which might cause do_pg_abort_backup() to fail.
11176  */
11177  if (exclusive)
11178  {
11181 
11182  /* Set session-level lock */
11185  }
11186  else
11188 
11189  /*
11190  * We're done. As a convenience, return the starting WAL location.
11191  */
11192  if (starttli_p)
11193  *starttli_p = starttli;
11194  return startpoint;
11195 }
size_t pg_strftime(char *s, size_t max, const char *format, const struct pg_tm *tm)
Definition: strftime.c:128
XLogRecPtr RequestXLogSwitch(bool mark_unimportant)
Definition: xlog.c:9896
int errhint(const char *fmt,...)
Definition: elog.c:1156
uint32 TimeLineID
Definition: xlogdefs.h:59
int64 pg_time_t
Definition: pgtime.h:23
static void WALInsertLockRelease(void)
Definition: xlog.c:1744
int wal_segment_size
Definition: xlog.c:121
XLogRecPtr lastFpwDisableRecPtr
Definition: xlog.c:735
static SessionBackupState sessionBackupState
Definition: xlog.c:534
XLogRecPtr lastBackupStart
Definition: xlog.c:587
char * pstrdup(const char *in)
Definition: mcxt.c:1299
#define XLogIsNeeded()
Definition: xlog.h:201
char * rpath
Definition: basebackup.h:32
StringInfo makeStringInfo(void)
Definition: stringinfo.c:41
slock_t info_lck
Definition: xlog.c:737
int errcode(int sqlerrcode)
Definition: elog.c:698
CheckPoint checkPointCopy
Definition: pg_control.h:131
XLogCtlInsert Insert
Definition: xlog.c:600
bool RecoveryInProgress(void)
Definition: xlog.c:8237
static bool backup_started_in_recovery
Definition: basebackup.c:88
Definition: dirent.h:9
#define IS_DIR_SEP(ch)
Definition: port.h:84
pg_tz * log_timezone
Definition: pgtz.c:31
void LWLockRelease(LWLock *lock)
Definition: lwlock.c:1805
#define TABLESPACE_MAP
Definition: xlog.h:401
#define SpinLockAcquire(lock)
Definition: spin.h:62
#define LSN_FORMAT_ARGS(lsn)
Definition: xlogdefs.h:43
#define PG_ENSURE_ERROR_CLEANUP(cleanup_function, arg)
Definition: ipc.h:47
void pfree(void *pointer)
Definition: mcxt.c:1169
void appendStringInfo(StringInfo str, const char *fmt,...)
Definition: stringinfo.c:91
bool forcePageWrites
Definition: xlog.c:574
Definition: dirent.c:25
#define ERROR
Definition: elog.h:46
#define MAXPGPATH
uint64 XLogSegNo
Definition: xlogdefs.h:48
#define readlink(path, buf, size)
Definition: win32_port.h:228
int errcode_for_file_access(void)
Definition: elog.c:721
FILE * AllocateFile(const char *name, const char *mode)
Definition: fd.c:2373
DIR * AllocateDir(const char *dirname)
Definition: fd.c:2634
#define CHECKPOINT_FORCE
Definition: xlog.h:235
List * lappend(List *list, void *datum)
Definition: list.c:336
void appendStringInfoChar(StringInfo str, char ch)
Definition: stringinfo.c:188
void initStringInfo(StringInfo str)
Definition: stringinfo.c:59
#define WARNING
Definition: elog.h:40
int nonExclusiveBackups
Definition: xlog.c:586
#define MAXFNAMELEN
#define SpinLockRelease(lock)
Definition: spin.h:64
static void pg_start_backup_callback(int code, Datum arg)
Definition: xlog.c:11199
ExclusiveBackupState exclusiveBackupState
Definition: xlog.c:585
uintptr_t Datum
Definition: postgres.h:411
static ControlFileData * ControlFile
Definition: xlog.c:748
#define BoolGetDatum(X)
Definition: postgres.h:446
#define ereport(elevel,...)
Definition: elog.h:157
bool fullPageWrites
Definition: pg_control.h:42
#define CHECKPOINT_WAIT
Definition: xlog.h:239
uint64 XLogRecPtr
Definition: xlogdefs.h:21
struct dirent * ReadDir(DIR *dir, const char *dirname)
Definition: fd.c:2700
#define XLogFileName(fname, tli, logSegNo, wal_segsz_bytes)
static void WALInsertLockAcquireExclusive(void)
Definition: xlog.c:1715
static XLogCtlData * XLogCtl
Definition: xlog.c:740
bool LWLockAcquire(LWLock *lock, LWLockMode mode)
Definition: lwlock.c:1203
#define PG_END_ENSURE_ERROR_CLEANUP(cleanup_function, arg)
Definition: ipc.h:52
struct pg_tm * pg_localtime(const pg_time_t *timep, const pg_tz *tz)
Definition: localtime.c:1342
int FreeFile(FILE *file)
Definition: fd.c:2572
void * palloc(Size size)
Definition: mcxt.c:1062
TimeLineID ThisTimeLineID
Definition: pg_control.h:39
int errmsg(const char *fmt,...)
Definition: elog.c:909
#define CHECKPOINT_IMMEDIATE
Definition: xlog.h:234
#define relpath(rnode, forknum)
Definition: relpath.h:87
char * DataDir
Definition: globals.c:65
#define BACKUP_LABEL_FILE
Definition: xlog.h:398
int pg_fsync(int fd)
Definition: fd.c:352
char d_name[MAX_PATH]
Definition: dirent.h:15
#define snprintf
Definition: port.h:216
XLogRecPtr checkPoint
Definition: pg_control.h:129
XLogRecPtr redo
Definition: pg_control.h:37
int FreeDir(DIR *dir)
Definition: fd.c:2752
#define stat
Definition: win32_port.h:275
void RequestCheckpoint(int flags)
Definition: checkpointer.c:927
#define XLByteToSeg(xlrp, logSegNo, wal_segsz_bytes)

◆ do_pg_stop_backup()

XLogRecPtr do_pg_stop_backup ( char *  labelfile,
bool  waitforarchive,
TimeLineID stoptli_p 
)

Definition at line 11267 of file xlog.c.

References AllocateFile(), Assert, BACKUP_LABEL_FILE, backup_started_in_recovery, BackupHistoryFileName, BackupHistoryFilePath, BoolGetDatum, CHECK_FOR_INTERRUPTS, CleanupBackupHistory(), DEBUG1, durable_unlink(), ereport, errcode(), errcode_for_file_access(), errhint(), errmsg(), ERROR, EXCLUSIVE_BACKUP_IN_PROGRESS, EXCLUSIVE_BACKUP_NONE, EXCLUSIVE_BACKUP_STOPPING, XLogCtlInsert::exclusiveBackupState, XLogCtlInsert::forcePageWrites, fprintf, FreeFile(), XLogCtlData::info_lck, XLogCtlData::Insert, XLogCtlData::lastFpwDisableRecPtr, log_timezone, LSN_FORMAT_ARGS, LW_SHARED, LWLockAcquire(), LWLockRelease(), MAXFNAMELEN, MAXPGPATH, ControlFileData::minRecoveryPoint, ControlFileData::minRecoveryPointTLI, XLogCtlInsert::nonExclusiveBackups, NOTICE, palloc(), PG_END_ENSURE_ERROR_CLEANUP, PG_ENSURE_ERROR_CLEANUP, pg_localtime(), pg_stop_backup_callback(), pg_strftime(), pg_usleep(), pgstat_report_wait_end(), pgstat_report_wait_start(), RecoveryInProgress(), remaining, RequestXLogSwitch(), SESSION_BACKUP_NONE, sessionBackupState, SpinLockAcquire, SpinLockRelease, stat::st_size, stat, TABLESPACE_MAP, ThisTimeLineID, WAIT_EVENT_BACKUP_WAIT_WAL_ARCHIVE, wal_segment_size, WALInsertLockAcquireExclusive(), WALInsertLockRelease(), WARNING, XLByteToPrevSeg, XLByteToSeg, XLOG_BACKUP_END, XLogArchiveIsBusy(), XLogArchivingActive, XLogArchivingAlways, XLogBeginInsert(), XLogFileName, XLogInsert(), XLogIsNeeded, and XLogRegisterData().

Referenced by perform_base_backup(), pg_stop_backup(), and pg_stop_backup_v2().

11268 {
11269  bool exclusive = (labelfile == NULL);
11270  bool backup_started_in_recovery = false;
11271  XLogRecPtr startpoint;
11272  XLogRecPtr stoppoint;
11273  TimeLineID stoptli;
11274  pg_time_t stamp_time;
11275  char strfbuf[128];
11276  char histfilepath[MAXPGPATH];
11277  char startxlogfilename[MAXFNAMELEN];
11278  char stopxlogfilename[MAXFNAMELEN];
11279  char lastxlogfilename[MAXFNAMELEN];
11280  char histfilename[MAXFNAMELEN];
11281  char backupfrom[20];
11282  XLogSegNo _logSegNo;
11283  FILE *lfp;
11284  FILE *fp;
11285  char ch;
11286  int seconds_before_warning;
11287  int waits = 0;
11288  bool reported_waiting = false;
11289  char *remaining;
11290  char *ptr;
11291  uint32 hi,
11292  lo;
11293 
11294  backup_started_in_recovery = RecoveryInProgress();
11295 
11296  /*
11297  * Currently only non-exclusive backup can be taken during recovery.
11298  */
11299  if (backup_started_in_recovery && exclusive)
11300  ereport(ERROR,
11301  (errcode(ERRCODE_OBJECT_NOT_IN_PREREQUISITE_STATE),
11302  errmsg("recovery is in progress"),
11303  errhint("WAL control functions cannot be executed during recovery.")));
11304 
11305  /*
11306  * During recovery, we don't need to check WAL level. Because, if WAL
11307  * level is not sufficient, it's impossible to get here during recovery.
11308  */
11309  if (!backup_started_in_recovery && !XLogIsNeeded())
11310  ereport(ERROR,
11311  (errcode(ERRCODE_OBJECT_NOT_IN_PREREQUISITE_STATE),
11312  errmsg("WAL level not sufficient for making an online backup"),
11313  errhint("wal_level must be set to \"replica\" or \"logical\" at server start.")));
11314 
11315  if (exclusive)
11316  {
11317  /*
11318  * At first, mark that we're now stopping an exclusive backup, to
11319  * ensure that there are no other sessions currently running
11320  * pg_start_backup() or pg_stop_backup().
11321  */
11324  {
11326  ereport(ERROR,
11327  (errcode(ERRCODE_OBJECT_NOT_IN_PREREQUISITE_STATE),
11328  errmsg("exclusive backup not in progress")));
11329  }
11332 
11333  /*
11334  * Remove backup_label. In case of failure, the state for an exclusive
11335  * backup is switched back to in-progress.
11336  */
11338  {
11339  /*
11340  * Read the existing label file into memory.
11341  */
11342  struct stat statbuf;
11343  int r;
11344 
11345  if (stat(BACKUP_LABEL_FILE, &statbuf))
11346  {
11347  /* should not happen per the upper checks */
11348  if (errno != ENOENT)
11349  ereport(ERROR,
11351  errmsg("could not stat file \"%s\": %m",
11352  BACKUP_LABEL_FILE)));
11353  ereport(ERROR,
11354  (errcode(ERRCODE_OBJECT_NOT_IN_PREREQUISITE_STATE),
11355  errmsg("a backup is not in progress")));
11356  }
11357 
11358  lfp = AllocateFile(BACKUP_LABEL_FILE, "r");
11359  if (!lfp)
11360  {
11361  ereport(ERROR,
11363  errmsg("could not read file \"%s\": %m",
11364  BACKUP_LABEL_FILE)));
11365  }
11366  labelfile = palloc(statbuf.st_size + 1);
11367  r = fread(labelfile, statbuf.st_size, 1, lfp);
11368  labelfile[statbuf.st_size] = '\0';
11369 
11370  /*
11371  * Close and remove the backup label file
11372  */
11373  if (r != 1 || ferror(lfp) || FreeFile(lfp))
11374  ereport(ERROR,
11376  errmsg("could not read file \"%s\": %m",
11377  BACKUP_LABEL_FILE)));
11379 
11380  /*
11381  * Remove tablespace_map file if present, it is created only if
11382  * there are tablespaces.
11383  */
11385  }
11387  }
11388 
11389  /*
11390  * OK to update backup counters, forcePageWrites and session-level lock.
11391  *
11392  * Note that CHECK_FOR_INTERRUPTS() must not occur while updating them.
11393  * Otherwise they can be updated inconsistently, and which might cause
11394  * do_pg_abort_backup() to fail.
11395  */
11397  if (exclusive)
11398  {
11400  }
11401  else
11402  {
11403  /*
11404  * The user-visible pg_start/stop_backup() functions that operate on
11405  * exclusive backups can be called at any time, but for non-exclusive
11406  * backups, it is expected that each do_pg_start_backup() call is
11407  * matched by exactly one do_pg_stop_backup() call.
11408  */
11411  }
11412 
11415  {
11416  XLogCtl->Insert.forcePageWrites = false;
11417  }
11418 
11419  /*
11420  * Clean up session-level lock.
11421  *
11422  * You might think that WALInsertLockRelease() can be called before
11423  * cleaning up session-level lock because session-level lock doesn't need
11424  * to be protected with WAL insertion lock. But since
11425  * CHECK_FOR_INTERRUPTS() can occur in it, session-level lock must be
11426  * cleaned up before it.
11427  */
11429 
11431 
11432  /*
11433  * Read and parse the START WAL LOCATION line (this code is pretty crude,
11434  * but we are not expecting any variability in the file format).
11435  */
11436  if (sscanf(labelfile, "START WAL LOCATION: %X/%X (file %24s)%c",
11437  &hi, &lo, startxlogfilename,
11438  &ch) != 4 || ch != '\n')
11439  ereport(ERROR,
11440  (errcode(ERRCODE_OBJECT_NOT_IN_PREREQUISITE_STATE),
11441  errmsg("invalid data in file \"%s\"", BACKUP_LABEL_FILE)));
11442  startpoint = ((uint64) hi) << 32 | lo;
11443  remaining = strchr(labelfile, '\n') + 1; /* %n is not portable enough */
11444 
11445  /*
11446  * Parse the BACKUP FROM line. If we are taking an online backup from the
11447  * standby, we confirm that the standby has not been promoted during the
11448  * backup.
11449  */
11450  ptr = strstr(remaining, "BACKUP FROM:");
11451  if (!ptr || sscanf(ptr, "BACKUP FROM: %19s\n", backupfrom) != 1)
11452  ereport(ERROR,
11453  (errcode(ERRCODE_OBJECT_NOT_IN_PREREQUISITE_STATE),
11454  errmsg("invalid data in file \"%s\"", BACKUP_LABEL_FILE)));
11455  if (strcmp(backupfrom, "standby") == 0 && !backup_started_in_recovery)
11456  ereport(ERROR,
11457  (errcode(ERRCODE_OBJECT_NOT_IN_PREREQUISITE_STATE),
11458  errmsg("the standby was promoted during online backup"),
11459  errhint("This means that the backup being taken is corrupt "
11460  "and should not be used. "
11461  "Try taking another online backup.")));
11462 
11463  /*
11464  * During recovery, we don't write an end-of-backup record. We assume that
11465  * pg_control was backed up last and its minimum recovery point can be
11466  * available as the backup end location. Since we don't have an
11467  * end-of-backup record, we use the pg_control value to check whether
11468  * we've reached the end of backup when starting recovery from this
11469  * backup. We have no way of checking if pg_control wasn't backed up last
11470  * however.
11471  *
11472  * We don't force a switch to new WAL file but it is still possible to
11473  * wait for all the required files to be archived if waitforarchive is
11474  * true. This is okay if we use the backup to start a standby and fetch
11475  * the missing WAL using streaming replication. But in the case of an
11476  * archive recovery, a user should set waitforarchive to true and wait for
11477  * them to be archived to ensure that all the required files are
11478  * available.
11479  *
11480  * We return the current minimum recovery point as the backup end
11481  * location. Note that it can be greater than the exact backup end
11482  * location if the minimum recovery point is updated after the backup of
11483  * pg_control. This is harmless for current uses.
11484  *
11485  * XXX currently a backup history file is for informational and debug
11486  * purposes only. It's not essential for an online backup. Furthermore,
11487  * even if it's created, it will not be archived during recovery because
11488  * an archiver is not invoked. So it doesn't seem worthwhile to write a
11489  * backup history file during recovery.
11490  */
11491  if (backup_started_in_recovery)
11492  {
11493  XLogRecPtr recptr;
11494 
11495  /*
11496  * Check to see if all WAL replayed during online backup contain
11497  * full-page writes.
11498  */
11500  recptr = XLogCtl->lastFpwDisableRecPtr;
11502 
11503  if (startpoint <= recptr)
11504  ereport(ERROR,
11505  (errcode(ERRCODE_OBJECT_NOT_IN_PREREQUISITE_STATE),
11506  errmsg("WAL generated with full_page_writes=off was replayed "
11507  "during online backup"),
11508  errhint("This means that the backup being taken on the standby "
11509  "is corrupt and should not be used. "
11510  "Enable full_page_writes and run CHECKPOINT on the primary, "
11511  "and then try an online backup again.")));
11512 
11513 
11514  LWLockAcquire(ControlFileLock, LW_SHARED);
11515  stoppoint = ControlFile->minRecoveryPoint;
11516  stoptli = ControlFile->minRecoveryPointTLI;
11517  LWLockRelease(ControlFileLock);
11518  }
11519  else
11520  {
11521  /*
11522  * Write the backup-end xlog record
11523  */
11524  XLogBeginInsert();
11525  XLogRegisterData((char *) (&startpoint), sizeof(startpoint));
11526  stoppoint = XLogInsert(RM_XLOG_ID, XLOG_BACKUP_END);
11527  stoptli = ThisTimeLineID;
11528 
11529  /*
11530  * Force a switch to a new xlog segment file, so that the backup is
11531  * valid as soon as archiver moves out the current segment file.
11532  */
11533  RequestXLogSwitch(false);
11534 
11535  XLByteToPrevSeg(stoppoint, _logSegNo, wal_segment_size);
11536  XLogFileName(stopxlogfilename, stoptli, _logSegNo, wal_segment_size);
11537 
11538  /* Use the log timezone here, not the session timezone */
11539  stamp_time = (pg_time_t) time(NULL);
11540  pg_strftime(strfbuf, sizeof(strfbuf),
11541  "%Y-%m-%d %H:%M:%S %Z",
11542  pg_localtime(&stamp_time, log_timezone));
11543 
11544  /*
11545  * Write the backup history file
11546  */
11547  XLByteToSeg(startpoint, _logSegNo, wal_segment_size);
11548  BackupHistoryFilePath(histfilepath, stoptli, _logSegNo,
11549  startpoint, wal_segment_size);
11550  fp = AllocateFile(histfilepath, "w");
11551  if (!fp)
11552  ereport(ERROR,
11554  errmsg("could not create file \"%s\": %m",
11555  histfilepath)));
11556  fprintf(fp, "START WAL LOCATION: %X/%X (file %s)\n",
11557  LSN_FORMAT_ARGS(startpoint), startxlogfilename);
11558  fprintf(fp, "STOP WAL LOCATION: %X/%X (file %s)\n",
11559  LSN_FORMAT_ARGS(stoppoint), stopxlogfilename);
11560 
11561  /*
11562  * Transfer remaining lines including label and start timeline to
11563  * history file.
11564  */
11565  fprintf(fp, "%s", remaining);
11566  fprintf(fp, "STOP TIME: %s\n", strfbuf);
11567  fprintf(fp, "STOP TIMELINE: %u\n", stoptli);
11568  if (fflush(fp) || ferror(fp) || FreeFile(fp))
11569  ereport(ERROR,
11571  errmsg("could not write file \"%s\": %m",
11572  histfilepath)));
11573 
11574  /*
11575  * Clean out any no-longer-needed history files. As a side effect,
11576  * this will post a .ready file for the newly created history file,
11577  * notifying the archiver that history file may be archived
11578  * immediately.
11579  */
11581  }
11582 
11583  /*
11584  * If archiving is enabled, wait for all the required WAL files to be
11585  * archived before returning. If archiving isn't enabled, the required WAL
11586  * needs to be transported via streaming replication (hopefully with
11587  * wal_keep_size set high enough), or some more exotic mechanism like
11588  * polling and copying files from pg_wal with script. We have no knowledge
11589  * of those mechanisms, so it's up to the user to ensure that he gets all
11590  * the required WAL.
11591  *
11592  * We wait until both the last WAL file filled during backup and the
11593  * history file have been archived, and assume that the alphabetic sorting
11594  * property of the WAL files ensures any earlier WAL files are safely
11595  * archived as well.
11596  *
11597  * We wait forever, since archive_command is supposed to work and we
11598  * assume the admin wanted his backup to work completely. If you don't
11599  * wish to wait, then either waitforarchive should be passed in as false,
11600  * or you can set statement_timeout. Also, some notices are issued to
11601  * clue in anyone who might be doing this interactively.
11602  */
11603 
11604  if (waitforarchive &&
11605  ((!backup_started_in_recovery && XLogArchivingActive()) ||
11606  (backup_started_in_recovery && XLogArchivingAlways())))
11607  {
11608  XLByteToPrevSeg(stoppoint, _logSegNo, wal_segment_size);
11609  XLogFileName(lastxlogfilename, stoptli, _logSegNo, wal_segment_size);
11610 
11611  XLByteToSeg(startpoint, _logSegNo, wal_segment_size);
11612  BackupHistoryFileName(histfilename, stoptli, _logSegNo,
11613  startpoint, wal_segment_size);
11614 
11615  seconds_before_warning = 60;
11616  waits = 0;
11617 
11618  while (XLogArchiveIsBusy(lastxlogfilename) ||
11619  XLogArchiveIsBusy(histfilename))
11620  {
11622 
11623  if (!reported_waiting && waits > 5)
11624  {
11625  ereport(NOTICE,
11626  (errmsg("base backup done, waiting for required WAL segments to be archived")));
11627  reported_waiting = true;
11628  }
11629 
11631  pg_usleep(1000000L);
11633 
11634  if (++waits >= seconds_before_warning)
11635  {
11636  seconds_before_warning *= 2; /* This wraps in >10 years... */
11637  ereport(WARNING,
11638  (errmsg("still waiting for all required WAL segments to be archived (%d seconds elapsed)",
11639  waits),
11640  errhint("Check that your archive_command is executing properly. "
11641  "You can safely cancel this backup, "
11642  "but the database backup will not be usable without all the WAL segments.")));
11643  }
11644  }
11645 
11646  ereport(NOTICE,
11647  (errmsg("all required WAL segments have been archived")));
11648  }
11649  else if (waitforarchive)
11650  ereport(NOTICE,
11651  (errmsg("WAL archiving is not enabled; you must ensure that all required WAL segments are copied through other means to complete the backup")));
11652 
11653  /*
11654  * We're done. As a convenience, return the ending WAL location.
11655  */
11656  if (stoptli_p)
11657  *stoptli_p = stoptli;
11658  return stoppoint;
11659 }
int remaining
Definition: informix.c:667
size_t pg_strftime(char *s, size_t max, const char *format, const struct pg_tm *tm)
Definition: strftime.c:128
XLogRecPtr RequestXLogSwitch(bool mark_unimportant)
Definition: xlog.c:9896
#define DEBUG1
Definition: elog.h:25
int errhint(const char *fmt,...)
Definition: elog.c:1156
uint32 TimeLineID
Definition: xlogdefs.h:59
int64 pg_time_t
Definition: pgtime.h:23
static void pgstat_report_wait_end(void)
Definition: wait_event.h:277
static void WALInsertLockRelease(void)
Definition: xlog.c:1744
int wal_segment_size
Definition: xlog.c:121
TimeLineID minRecoveryPointTLI
Definition: pg_control.h:167
XLogRecPtr lastFpwDisableRecPtr
Definition: xlog.c:735
static SessionBackupState sessionBackupState
Definition: xlog.c:534
#define XLByteToPrevSeg(xlrp, logSegNo, wal_segsz_bytes)
#define XLogIsNeeded()
Definition: xlog.h:201
slock_t info_lck
Definition: xlog.c:737
int errcode(int sqlerrcode)
Definition: elog.c:698
XLogCtlInsert Insert
Definition: xlog.c:600
#define BackupHistoryFileName(fname, tli, logSegNo, startpoint, wal_segsz_bytes)
bool RecoveryInProgress(void)
Definition: xlog.c:8237
static bool backup_started_in_recovery
Definition: basebackup.c:88
#define fprintf
Definition: port.h:220
pg_tz * log_timezone
Definition: pgtz.c:31
void LWLockRelease(LWLock *lock)
Definition: lwlock.c:1805
#define TABLESPACE_MAP
Definition: xlog.h:401
#define SpinLockAcquire(lock)
Definition: spin.h:62
void pg_usleep(long microsec)
Definition: signal.c:53
#define LSN_FORMAT_ARGS(lsn)
Definition: xlogdefs.h:43
#define PG_ENSURE_ERROR_CLEANUP(cleanup_function, arg)
Definition: ipc.h:47
#define XLogArchivingAlways()
Definition: xlog.h:193
bool forcePageWrites
Definition: xlog.c:574
#define ERROR
Definition: elog.h:46
static void CleanupBackupHistory(void)
Definition: xlog.c:4340
#define MAXPGPATH
uint64 XLogSegNo
Definition: xlogdefs.h:48
int errcode_for_file_access(void)
Definition: elog.c:721
FILE * AllocateFile(const char *name, const char *mode)
Definition: fd.c:2373
unsigned int uint32
Definition: c.h:441
#define XLOG_BACKUP_END
Definition: pg_control.h:72
static void pgstat_report_wait_start(uint32 wait_event_info)
Definition: wait_event.h:261
#define WARNING
Definition: elog.h:40
int nonExclusiveBackups
Definition: xlog.c:586
#define MAXFNAMELEN
void XLogRegisterData(char *data, int len)
Definition: xloginsert.c:330
#define SpinLockRelease(lock)
Definition: spin.h:64
#define BackupHistoryFilePath(path, tli, logSegNo, startpoint, wal_segsz_bytes)
XLogRecPtr XLogInsert(RmgrId rmid, uint8 info)
Definition: xloginsert.c:422
ExclusiveBackupState exclusiveBackupState
Definition: xlog.c:585
uintptr_t Datum
Definition: postgres.h:411
static ControlFileData * ControlFile
Definition: xlog.c:748
#define BoolGetDatum(X)
Definition: postgres.h:446
TimeLineID ThisTimeLineID
Definition: xlog.c:196
#define ereport(elevel,...)
Definition: elog.h:157
#define NOTICE
Definition: elog.h:37
bool XLogArchiveIsBusy(const char *xlog)
Definition: xlogarchive.c:626
uint64 XLogRecPtr
Definition: xlogdefs.h:21
#define Assert(condition)
Definition: c.h:804
#define XLogArchivingActive()
Definition: xlog.h:190
#define XLogFileName(fname, tli, logSegNo, wal_segsz_bytes)
static void WALInsertLockAcquireExclusive(void)
Definition: xlog.c:1715
static XLogCtlData * XLogCtl
Definition: xlog.c:740
bool LWLockAcquire(LWLock *lock, LWLockMode mode)
Definition: lwlock.c:1203
static void pg_stop_backup_callback(int code, Datum arg)
Definition: xlog.c:11228
#define PG_END_ENSURE_ERROR_CLEANUP(cleanup_function, arg)
Definition: ipc.h:52
struct pg_tm * pg_localtime(const pg_time_t *timep, const pg_tz *tz)
Definition: localtime.c:1342
int durable_unlink(const char *fname, int elevel)
Definition: fd.c:782
int FreeFile(FILE *file)
Definition: fd.c:2572
void * palloc(Size size)
Definition: mcxt.c:1062
int errmsg(const char *fmt,...)
Definition: elog.c:909
#define BACKUP_LABEL_FILE
Definition: xlog.h:398
#define CHECK_FOR_INTERRUPTS()
Definition: miscadmin.h:102
void XLogBeginInsert(void)
Definition: xloginsert.c:123
#define stat
Definition: win32_port.h:275
XLogRecPtr minRecoveryPoint
Definition: pg_control.h:166
#define XLByteToSeg(xlrp, logSegNo, wal_segsz_bytes)

◆ get_backup_status()

SessionBackupState get_backup_status ( void  )

Definition at line 11246 of file xlog.c.

References sessionBackupState.

Referenced by pg_start_backup(), pg_stop_backup(), and pg_stop_backup_v2().

11247 {
11248  return sessionBackupState;
11249 }
static SessionBackupState sessionBackupState
Definition: xlog.c:534

◆ GetCurrentChunkReplayStartTime()

TimestampTz GetCurrentChunkReplayStartTime ( void  )

Definition at line 6293 of file xlog.c.

References XLogCtlData::currentChunkStartTime, XLogCtlData::info_lck, SpinLockAcquire, and SpinLockRelease.

Referenced by GetReplicationApplyDelay().

6294 {
6295  TimestampTz xtime;
6296 
6298  xtime = XLogCtl->currentChunkStartTime;
6300 
6301  return xtime;
6302 }
int64 TimestampTz
Definition: timestamp.h:39
slock_t info_lck
Definition: xlog.c:737
#define SpinLockAcquire(lock)
Definition: spin.h:62
#define SpinLockRelease(lock)
Definition: spin.h:64
static XLogCtlData * XLogCtl
Definition: xlog.c:740
TimestampTz currentChunkStartTime
Definition: xlog.c:726

◆ GetFakeLSNForUnloggedRel()

XLogRecPtr GetFakeLSNForUnloggedRel ( void  )

Definition at line 5001 of file xlog.c.

References SpinLockAcquire, SpinLockRelease, XLogCtlData::ulsn_lck, and XLogCtlData::unloggedLSN.

Referenced by gistGetFakeLSN().

5002 {
5003  XLogRecPtr nextUnloggedLSN;
5004 
5005  /* increment the unloggedLSN counter, need SpinLock */
5007  nextUnloggedLSN = XLogCtl->unloggedLSN++;
5009 
5010  return nextUnloggedLSN;
5011 }
XLogRecPtr unloggedLSN
Definition: xlog.c:612
#define SpinLockAcquire(lock)
Definition: spin.h:62
#define SpinLockRelease(lock)
Definition: spin.h:64
uint64 XLogRecPtr
Definition: xlogdefs.h:21
static XLogCtlData * XLogCtl
Definition: xlog.c:740
slock_t ulsn_lck
Definition: xlog.c:613

◆ GetFlushRecPtr()

XLogRecPtr GetFlushRecPtr ( void  )

Definition at line 8589 of file xlog.c.

References XLogwrtResult::Flush, XLogCtlData::info_lck, XLogCtlData::LogwrtResult, SpinLockAcquire, and SpinLockRelease.

Referenced by get_flush_position(), IdentifySystem(), pg_current_wal_flush_lsn(), pg_logical_slot_get_changes_guts(), pg_replication_slot_advance(), read_local_xlog_page(), StartReplication(), WalSndWaitForWal(), XLogSendLogical(), and XLogSendPhysical().

8590 {
8594 
8595  return LogwrtResult.Flush;
8596 }
static XLogwrtResult LogwrtResult
Definition: xlog.c:786
slock_t info_lck
Definition: xlog.c:737
#define SpinLockAcquire(lock)
Definition: spin.h:62
XLogwrtResult LogwrtResult
Definition: xlog.c:623
#define SpinLockRelease(lock)
Definition: spin.h:64
static XLogCtlData * XLogCtl
Definition: xlog.c:740
XLogRecPtr Flush
Definition: xlog.c:448

◆ GetFullPageWriteInfo()

void GetFullPageWriteInfo ( XLogRecPtr RedoRecPtr_p,
bool doPageWrites_p 
)

Definition at line 8558 of file xlog.c.

References doPageWrites, and RedoRecPtr.

Referenced by XLogCheckBufferNeedsBackup(), and XLogInsert().

8559 {
8560  *RedoRecPtr_p = RedoRecPtr;
8561  *doPageWrites_p = doPageWrites;
8562 }
static bool doPageWrites
Definition: xlog.c:385
static XLogRecPtr RedoRecPtr
Definition: xlog.c:378

◆ GetInsertRecPtr()

XLogRecPtr GetInsertRecPtr ( void  )

Definition at line 8573 of file xlog.c.

References XLogCtlData::info_lck, XLogCtlData::LogwrtRqst, SpinLockAcquire, SpinLockRelease, and XLogwrtRqst::Write.

Referenced by CheckpointerMain(), gistvacuumscan(), and IsCheckpointOnSchedule().

8574 {
8575  XLogRecPtr recptr;
8576 
8578  recptr = XLogCtl->LogwrtRqst.Write;
8580 
8581  return recptr;
8582 }
slock_t info_lck
Definition: xlog.c:737
#define SpinLockAcquire(lock)
Definition: spin.h:62
#define SpinLockRelease(lock)
Definition: spin.h:64
XLogRecPtr Write
Definition: xlog.c:441
XLogwrtRqst LogwrtRqst
Definition: xlog.c:603
uint64 XLogRecPtr
Definition: xlogdefs.h:21
static XLogCtlData * XLogCtl
Definition: xlog.c:740

◆ GetLastImportantRecPtr()

XLogRecPtr GetLastImportantRecPtr ( void  )

Definition at line 8607 of file xlog.c.

References i, InvalidXLogRecPtr, WALInsertLockPadded::l, WALInsertLock::lastImportantAt, LW_EXCLUSIVE, LWLockAcquire(), LWLockRelease(), and NUM_XLOGINSERT_LOCKS.

Referenced by BackgroundWriterMain(), CheckArchiveTimeout(), and CreateCheckPoint().

8608 {
8610  int i;
8611 
8612  for (i = 0; i < NUM_XLOGINSERT_LOCKS; i++)
8613  {
8614  XLogRecPtr last_important;
8615 
8616  /*
8617  * Need to take a lock to prevent torn reads of the LSN, which are
8618  * possible on some of the supported platforms. WAL insert locks only
8619  * support exclusive mode, so we have to use that.
8620  */
8622  last_important = WALInsertLocks[i].l.lastImportantAt;
8623  LWLockRelease(&WALInsertLocks[i].l.lock);
8624 
8625  if (res < last_important)
8626  res = last_important;
8627  }
8628 
8629  return res;
8630 }
#define InvalidXLogRecPtr
Definition: xlogdefs.h:28
XLogRecPtr lastImportantAt
Definition: xlog.c:491
#define NUM_XLOGINSERT_LOCKS
Definition: xlog.c:128
WALInsertLock l
Definition: xlog.c:503
void LWLockRelease(LWLock *lock)
Definition: lwlock.c:1805
uint64 XLogRecPtr
Definition: xlogdefs.h:21
bool LWLockAcquire(LWLock *lock, LWLockMode mode)
Definition: lwlock.c:1203
int i
static WALInsertLockPadded * WALInsertLocks
Definition: xlog.c:743

◆ GetLatestXTime()

TimestampTz GetLatestXTime ( void  )

Definition at line 6263 of file xlog.c.

References XLogCtlData::info_lck, XLogCtlData::recoveryLastXTime, SpinLockAcquire, and SpinLockRelease.

Referenced by CreateRestartPoint(), pg_last_xact_replay_timestamp(), and StartupXLOG().

6264 {
6265  TimestampTz xtime;
6266 
6268  xtime = XLogCtl->recoveryLastXTime;
6270 
6271  return xtime;
6272 }
int64 TimestampTz
Definition: timestamp.h:39
slock_t info_lck
Definition: xlog.c:737
#define SpinLockAcquire(lock)
Definition: spin.h:62
TimestampTz recoveryLastXTime
Definition: xlog.c:720
#define SpinLockRelease(lock)
Definition: spin.h:64
static XLogCtlData * XLogCtl
Definition: xlog.c:740

◆ GetMockAuthenticationNonce()

char* GetMockAuthenticationNonce ( void  )

Definition at line 4975 of file xlog.c.

References Assert, and ControlFileData::mock_authentication_nonce.

Referenced by scram_mock_salt().

4976 {
4977  Assert(ControlFile != NULL);
4979 }
char mock_authentication_nonce[MOCK_AUTH_NONCE_LEN]
Definition: pg_control.h:227
static ControlFileData * ControlFile
Definition: xlog.c:748
#define Assert(condition)
Definition: c.h:804

◆ GetRecoveryPauseState()

RecoveryPauseState GetRecoveryPauseState ( void  )

Definition at line 6103 of file xlog.c.

References XLogCtlData::info_lck, XLogCtlData::recoveryPauseState, SpinLockAcquire, and SpinLockRelease.

Referenced by pg_get_wal_replay_pause_state(), pg_is_wal_replay_paused(), recoveryPausesHere(), and RecoveryRequiresIntParameter().

6104 {
6106 
6108  state = XLogCtl->recoveryPauseState;
6110 
6111  return state;
6112 }
RecoveryPauseState recoveryPauseState
Definition: xlog.c:728
slock_t info_lck
Definition: xlog.c:737
#define SpinLockAcquire(lock)
Definition: spin.h:62
RecoveryPauseState
Definition: xlog.h:180
#define SpinLockRelease(lock)
Definition: spin.h:64
Definition: regguts.h:317
static XLogCtlData * XLogCtl
Definition: xlog.c:740

◆ GetRecoveryState()

RecoveryState GetRecoveryState ( void  )

Definition at line 8290 of file xlog.c.

References XLogCtlData::info_lck, XLogCtlData::SharedRecoveryState, SpinLockAcquire, and SpinLockRelease.

Referenced by XLogArchiveCheckDone().

8291 {
8292  RecoveryState retval;
8293 
8295  retval = XLogCtl->SharedRecoveryState;
8297 
8298  return retval;
8299 }
slock_t info_lck
Definition: xlog.c:737
#define SpinLockAcquire(lock)
Definition: spin.h:62
RecoveryState SharedRecoveryState
Definition: xlog.c:659
#define SpinLockRelease(lock)
Definition: spin.h:64
static XLogCtlData * XLogCtl
Definition: xlog.c:740
RecoveryState
Definition: xlog.h:172

◆ GetRedoRecPtr()

XLogRecPtr GetRedoRecPtr ( void  )

Definition at line 8529 of file xlog.c.

References XLogCtlData::info_lck, RedoRecPtr, XLogCtlData::RedoRecPtr, SpinLockAcquire, and SpinLockRelease.

Referenced by CheckPointLogicalRewriteHeap(), CheckPointSnapBuild(), InitXLOGAccess(), nextval_internal(), ReplicationSlotReserveWal(), XLogPageRead(), XLogSaveBufferForHint(), and XLogWrite().

8530 {
8531  XLogRecPtr ptr;
8532 
8533  /*
8534  * The possibly not up-to-date copy in XlogCtl is enough. Even if we
8535  * grabbed a WAL insertion lock to read the authoritative value in
8536  * Insert->RedoRecPtr, someone might update it just after we've released
8537  * the lock.
8538  */
8540  ptr = XLogCtl->RedoRecPtr;
8542 
8543  if (RedoRecPtr < ptr)
8544  RedoRecPtr = ptr;
8545 
8546  return RedoRecPtr;
8547 }
slock_t info_lck
Definition: xlog.c:737
#define SpinLockAcquire(lock)
Definition: spin.h:62
static XLogRecPtr RedoRecPtr
Definition: xlog.c:378
XLogRecPtr RedoRecPtr
Definition: xlog.c:604
#define SpinLockRelease(lock)
Definition: spin.h:64
uint64 XLogRecPtr
Definition: xlogdefs.h:21
static XLogCtlData * XLogCtl
Definition: xlog.c:740

◆ GetSystemIdentifier()

uint64 GetSystemIdentifier ( void  )

Definition at line 4965 of file xlog.c.

References Assert, and ControlFileData::system_identifier.

Referenced by IdentifySystem(), ReplicationSlotNameForTablesync(), and WalReceiverMain().

4966 {
4967  Assert(ControlFile != NULL);
4969 }
uint64 system_identifier
Definition: pg_control.h:106
static ControlFileData * ControlFile
Definition: xlog.c:748
#define Assert(condition)
Definition: c.h:804

◆ GetWALAvailability()

WALAvailability GetWALAvailability ( XLogRecPtr  targetLSN)

Definition at line 9725 of file xlog.c.

References ConvertToXSegs, GetXLogWriteRecPtr(), KeepLogSeg(), max_wal_size_mb, wal_segment_size, WALAVAIL_EXTENDED, WALAVAIL_INVALID_LSN, WALAVAIL_REMOVED, WALAVAIL_RESERVED, WALAVAIL_UNRESERVED, XLByteToSeg, XLogGetLastRemovedSegno(), and XLogRecPtrIsInvalid.

Referenced by pg_get_replication_slots().

9726 {
9727  XLogRecPtr currpos; /* current write LSN */
9728  XLogSegNo currSeg; /* segid of currpos */
9729  XLogSegNo targetSeg; /* segid of targetLSN */
9730  XLogSegNo oldestSeg; /* actual oldest segid */
9731  XLogSegNo oldestSegMaxWalSize; /* oldest segid kept by max_wal_size */
9732  XLogSegNo oldestSlotSeg; /* oldest segid kept by slot */
9733  uint64 keepSegs;
9734 
9735  /*
9736  * slot does not reserve WAL. Either deactivated, or has never been active
9737  */
9738  if (XLogRecPtrIsInvalid(targetLSN))
9739  return WALAVAIL_INVALID_LSN;
9740 
9741  /*
9742  * Calculate the oldest segment currently reserved by all slots,
9743  * considering wal_keep_size and max_slot_wal_keep_size. Initialize
9744  * oldestSlotSeg to the current segment.
9745  */
9746  currpos = GetXLogWriteRecPtr();
9747  XLByteToSeg(currpos, oldestSlotSeg, wal_segment_size);
9748  KeepLogSeg(currpos, &oldestSlotSeg);
9749 
9750  /*
9751  * Find the oldest extant segment file. We get 1 until checkpoint removes
9752  * the first WAL segment file since startup, which causes the status being
9753  * wrong under certain abnormal conditions but that doesn't actually harm.
9754  */
9755  oldestSeg = XLogGetLastRemovedSegno() + 1;
9756 
9757  /* calculate oldest segment by max_wal_size */
9758  XLByteToSeg(currpos, currSeg, wal_segment_size);
9760 
9761  if (currSeg > keepSegs)
9762  oldestSegMaxWalSize = currSeg - keepSegs;
9763  else
9764  oldestSegMaxWalSize = 1;
9765 
9766  /* the segment we care about */
9767  XLByteToSeg(targetLSN, targetSeg, wal_segment_size);
9768 
9769  /*
9770  * No point in returning reserved or extended status values if the
9771  * targetSeg is known to be lost.
9772  */
9773  if (targetSeg >= oldestSlotSeg)
9774  {
9775  /* show "reserved" when targetSeg is within max_wal_size */
9776  if (targetSeg >= oldestSegMaxWalSize)
9777  return WALAVAIL_RESERVED;
9778 
9779  /* being retained by slots exceeding max_wal_size */
9780  return WALAVAIL_EXTENDED;
9781  }
9782 
9783  /* WAL segments are no longer retained but haven't been removed yet */
9784  if (targetSeg >= oldestSeg)
9785  return WALAVAIL_UNRESERVED;
9786 
9787  /* Definitely lost */
9788  return WALAVAIL_REMOVED;
9789 }
#define ConvertToXSegs(x, segsize)
Definition: xlog.c:777
int wal_segment_size
Definition: xlog.c:121
XLogSegNo XLogGetLastRemovedSegno(void)
Definition: xlog.c:4007
int max_wal_size_mb
Definition: xlog.c:92
uint64 XLogSegNo
Definition: xlogdefs.h:48
#define XLogRecPtrIsInvalid(r)
Definition: xlogdefs.h:29
static void KeepLogSeg(XLogRecPtr recptr, XLogSegNo *logSegNo)
Definition: xlog.c:9803
XLogRecPtr GetXLogWriteRecPtr(void)
Definition: xlog.c:11763
uint64 XLogRecPtr
Definition: xlogdefs.h:21
#define XLByteToSeg(xlrp, logSegNo, wal_segsz_bytes)

◆ GetXLogInsertRecPtr()

XLogRecPtr GetXLogInsertRecPtr ( void  )

Definition at line 11747 of file xlog.c.

References XLogCtlInsert::CurrBytePos, Insert(), XLogCtlData::Insert, XLogCtlInsert::insertpos_lck, SpinLockAcquire, SpinLockRelease, and XLogBytePosToRecPtr().

Referenced by GetSnapshotDataInitOldSnapshot(), gistGetFakeLSN(), logical_begin_heap_rewrite(), pg_current_wal_insert_lsn(), and ReplicationSlotReserveWal().

11748 {
11750  uint64 current_bytepos;
11751 
11752  SpinLockAcquire(&Insert->insertpos_lck);
11753  current_bytepos = Insert->CurrBytePos;
11754  SpinLockRelease(&Insert->insertpos_lck);
11755 
11756  return XLogBytePosToRecPtr(current_bytepos);
11757 }
slock_t insertpos_lck
Definition: xlog.c:541
static XLogRecPtr XLogBytePosToRecPtr(uint64 bytepos)
Definition: xlog.c:2013
XLogCtlInsert Insert
Definition: xlog.c:600
#define SpinLockAcquire(lock)
Definition: spin.h:62
uint64 CurrBytePos
Definition: xlog.c:550
static void Insert(File file)
Definition: fd.c:1222
#define SpinLockRelease(lock)
Definition: spin.h:64
static XLogCtlData * XLogCtl
Definition: xlog.c:740

◆ GetXLogReceiptTime()

void GetXLogReceiptTime ( TimestampTz rtime,
bool fromStream 
)

Definition at line 6309 of file xlog.c.

References Assert, InRecovery, XLOG_FROM_STREAM, XLogReceiptSource, and XLogReceiptTime.

Referenced by GetStandbyLimitTime().

6310 {
6311  /*
6312  * This must be executed in the startup process, since we don't export the
6313  * relevant state to shared memory.
6314  */
6315  Assert(InRecovery);
6316 
6317  *rtime = XLogReceiptTime;
6318  *fromStream = (XLogReceiptSource == XLOG_FROM_STREAM);
6319 }
static XLogSource XLogReceiptSource
Definition: xlog.c:848
bool InRecovery
Definition: xlog.c:209
static TimestampTz XLogReceiptTime
Definition: xlog.c:847
#define Assert(condition)
Definition: c.h:804

◆ GetXLogReplayRecPtr()

XLogRecPtr GetXLogReplayRecPtr ( TimeLineID replayTLI)

Definition at line 11728 of file xlog.c.

References XLogCtlData::info_lck, XLogCtlData::lastReplayedEndRecPtr, XLogCtlData::lastReplayedTLI, SpinLockAcquire, and SpinLockRelease.

Referenced by CheckpointerMain(), CreateRestartPoint(), GetReplicationApplyDelay(), GetStandbyFlushRecPtr(), IsCheckpointOnSchedule(), pg_last_wal_replay_lsn(), pg_logical_slot_get_changes_guts(), pg_replication_slot_advance(), read_local_xlog_page(), WalReceiverMain(), WalSndWaitForWal(), and XLogWalRcvSendReply().

11729 {
11730  XLogRecPtr recptr;
11731  TimeLineID tli;
11732 
11734  recptr = XLogCtl->lastReplayedEndRecPtr;
11735  tli = XLogCtl->lastReplayedTLI;
11737 
11738  if (replayTLI)
11739  *replayTLI = tli;
11740  return recptr;
11741 }
uint32 TimeLineID
Definition: xlogdefs.h:59
slock_t info_lck
Definition: xlog.c:737
#define SpinLockAcquire(lock)
Definition: spin.h:62
#define SpinLockRelease(lock)
Definition: spin.h:64
uint64 XLogRecPtr
Definition: xlogdefs.h:21
static XLogCtlData * XLogCtl
Definition: xlog.c:740
TimeLineID lastReplayedTLI
Definition: xlog.c:716
XLogRecPtr lastReplayedEndRecPtr
Definition: xlog.c:715

◆ GetXLogWriteRecPtr()

XLogRecPtr GetXLogWriteRecPtr ( void  )

Definition at line 11763 of file xlog.c.

References XLogCtlData::info_lck, XLogCtlData::LogwrtResult, SpinLockAcquire, SpinLockRelease, and XLogwrtResult::Write.

Referenced by GetWALAvailability(), pg_attribute_noreturn(), pg_current_wal_lsn(), and pg_get_replication_slots().

11764 {
11768 
11769  return LogwrtResult.Write;
11770 }
static XLogwrtResult LogwrtResult
Definition: xlog.c:786
slock_t info_lck
Definition: xlog.c:737
#define SpinLockAcquire(lock)
Definition: spin.h:62
XLogwrtResult LogwrtResult
Definition: xlog.c:623
#define SpinLockRelease(lock)
Definition: spin.h:64
static XLogCtlData * XLogCtl
Definition: xlog.c:740
XLogRecPtr Write
Definition: xlog.c:447

◆ HotStandbyActive()

bool HotStandbyActive ( void  )

Definition at line 8311 of file xlog.c.

References XLogCtlData::info_lck, LocalHotStandbyActive, XLogCtlData::SharedHotStandbyActive, SpinLockAcquire, and SpinLockRelease.

Referenced by XLogWalRcvSendHSFeedback().

8312 {
8313  /*
8314  * We check shared state each time only until Hot Standby is active. We
8315  * can't de-activate Hot Standby, so there's no need to keep checking
8316  * after the shared variable has once been seen true.
8317  */
8319  return true;
8320  else
8321  {
8322  /* spinlock is essential on machines with weak memory ordering! */
8326 
8327  return LocalHotStandbyActive;
8328  }
8329 }
bool SharedHotStandbyActive
Definition: xlog.c:665
slock_t info_lck
Definition: xlog.c:737
#define SpinLockAcquire(lock)
Definition: spin.h:62
static bool LocalHotStandbyActive
Definition: xlog.c:239
#define SpinLockRelease(lock)
Definition: spin.h:64
static XLogCtlData * XLogCtl
Definition: xlog.c:740

◆ HotStandbyActiveInReplay()

bool HotStandbyActiveInReplay ( void  )

Definition at line 8336 of file xlog.c.

References AmStartupProcess, Assert, IsPostmasterEnvironment, and LocalHotStandbyActive.

8337 {
8339  return LocalHotStandbyActive;
8340 }
#define AmStartupProcess()
Definition: miscadmin.h:433
bool IsPostmasterEnvironment
Definition: globals.c:111
static bool LocalHotStandbyActive
Definition: xlog.c:239
#define Assert(condition)
Definition: c.h:804

◆ InitXLOGAccess()

void InitXLOGAccess ( void  )

Definition at line 8503 of file xlog.c.

References Assert, doPageWrites, XLogCtlInsert::forcePageWrites, XLogCtlInsert::fullPageWrites, GetRedoRecPtr(), InitXLogInsert(), Insert(), XLogCtlData::Insert, IsBootstrapProcessingMode, ThisTimeLineID, XLogCtlData::ThisTimeLineID, wal_segment_size, and ControlFileData::xlog_seg_size.

Referenced by AuxiliaryProcessMain(), LocalSetXLogInsertAllowed(), and RecoveryInProgress().

8504 {
8506 
8507  /* ThisTimeLineID doesn't change so we need no lock to copy it */
8510 
8511  /* set wal_segment_size */
8513 
8514  /* Use GetRedoRecPtr to copy the RedoRecPtr safely */
8515  (void) GetRedoRecPtr();
8516  /* Also update our copy of doPageWrites. */
8517  doPageWrites = (Insert->fullPageWrites || Insert->forcePageWrites);
8518 
8519  /* Also initialize the working areas for constructing WAL records */
8520  InitXLogInsert();
8521 }
int wal_segment_size
Definition: xlog.c:121
void InitXLogInsert(void)
Definition: xloginsert.c:1197
TimeLineID ThisTimeLineID
Definition: xlog.c:652
XLogCtlInsert Insert
Definition: xlog.c:600
bool fullPageWrites
Definition: xlog.c:575
uint32 xlog_seg_size
Definition: pg_control.h:209
static bool doPageWrites
Definition: xlog.c:385
bool forcePageWrites
Definition: xlog.c:574
static void Insert(File file)
Definition: fd.c:1222
static ControlFileData * ControlFile
Definition: xlog.c:748
TimeLineID ThisTimeLineID
Definition: xlog.c:196
#define Assert(condition)
Definition: c.h:804
static XLogCtlData * XLogCtl
Definition: xlog.c:740
XLogRecPtr GetRedoRecPtr(void)
Definition: xlog.c:8529
#define IsBootstrapProcessingMode()
Definition: miscadmin.h:394

◆ issue_xlog_fsync()

void issue_xlog_fsync ( int  fd,
XLogSegNo  segno 
)

Definition at line 10629 of file xlog.c.

References _, Assert, duration, elog, enableFsync, ereport, errcode_for_file_access(), errmsg(), INSTR_TIME_GET_MICROSEC, INSTR_TIME_SET_CURRENT, INSTR_TIME_SUBTRACT, PgStat_MsgWal::m_wal_sync, PgStat_MsgWal::m_wal_sync_time, MAXFNAMELEN, PANIC, pg_fdatasync(), pg_fsync_no_writethrough(), pg_fsync_writethrough(), pgstat_report_wait_end(), pgstat_report_wait_start(), sync_method, SYNC_METHOD_FDATASYNC, SYNC_METHOD_FSYNC, SYNC_METHOD_FSYNC_WRITETHROUGH, SYNC_METHOD_OPEN, SYNC_METHOD_OPEN_DSYNC, ThisTimeLineID, track_wal_io_timing, WAIT_EVENT_WAL_SYNC, wal_segment_size, WalStats, and XLogFileName.

Referenced by XLogWalRcvFlush(), and XLogWrite().

10630 {
10631  char *msg = NULL;
10632  instr_time start;
10633 
10634  /*
10635  * Quick exit if fsync is disabled or write() has already synced the WAL
10636  * file.
10637  */
10638  if (!enableFsync ||
10641  return;
10642 
10643  /* Measure I/O timing to sync the WAL file */
10644  if (track_wal_io_timing)
10645  INSTR_TIME_SET_CURRENT(start);
10646 
10648  switch (sync_method)
10649  {
10650  case SYNC_METHOD_FSYNC:
10651  if (pg_fsync_no_writethrough(fd) != 0)
10652  msg = _("could not fsync file \"%s\": %m");
10653  break;
10654 #ifdef HAVE_FSYNC_WRITETHROUGH
10656  if (pg_fsync_writethrough(fd) != 0)
10657  msg = _("could not fsync write-through file \"%s\": %m");
10658  break;
10659 #endif
10660 #ifdef HAVE_FDATASYNC
10661  case SYNC_METHOD_FDATASYNC:
10662  if (pg_fdatasync(fd) != 0)
10663  msg = _("could not fdatasync file \"%s\": %m");
10664  break;
10665 #endif
10666  case SYNC_METHOD_OPEN:
10668  /* not reachable */
10669  Assert(false);
10670  break;
10671  default:
10672  elog(PANIC, "unrecognized wal_sync_method: %d", sync_method);
10673  break;
10674  }
10675 
10676  /* PANIC if failed to fsync */
10677  if (msg)
10678  {
10679  char xlogfname[MAXFNAMELEN];
10680  int save_errno = errno;
10681 
10682  XLogFileName(xlogfname, ThisTimeLineID, segno,
10684  errno = save_errno;
10685  ereport(PANIC,
10687  errmsg(msg, xlogfname)));
10688  }
10689 
10691 
10692  /*
10693  * Increment the I/O timing and the number of times WAL files were synced.
10694  */
10695  if (track_wal_io_timing)
10696  {
10698 
10699  INSTR_TIME_SET_CURRENT(duration);
10700  INSTR_TIME_SUBTRACT(duration, start);
10702  }
10703 
10704  WalStats.m_wal_sync++;
10705 }
static void pgstat_report_wait_end(void)
Definition: wait_event.h:277
int pg_fdatasync(int fd)
Definition: fd.c:442
int wal_segment_size
Definition: xlog.c:121
#define SYNC_METHOD_FSYNC_WRITETHROUGH
Definition: xlog.h:28
int pg_fsync_writethrough(int fd)
Definition: fd.c:419
struct timeval instr_time
Definition: instr_time.h:150
PgStat_Counter m_wal_sync
Definition: pgstat.h:511
int pg_fsync_no_writethrough(int fd)
Definition: fd.c:407
#define PANIC
Definition: elog.h:50
static int fd(const char *x, int i)
Definition: preproc-init.c:105
PgStat_Counter m_wal_sync_time
Definition: pgstat.h:514
int duration
Definition: pgbench.c:182
#define SYNC_METHOD_OPEN_DSYNC
Definition: xlog.h:29
bool track_wal_io_timing
Definition: xlog.c:115
#define INSTR_TIME_SUBTRACT(x, y)
Definition: instr_time.h:170
int errcode_for_file_access(void)
Definition: elog.c:721
#define SYNC_METHOD_FSYNC
Definition: xlog.h:25
#define SYNC_METHOD_OPEN
Definition: xlog.h:27
static void pgstat_report_wait_start(uint32 wait_event_info)
Definition: wait_event.h:261
#define MAXFNAMELEN
PgStat_MsgWal WalStats
Definition: pgstat.c:132
TimeLineID ThisTimeLineID
Definition: xlog.c:196
#define ereport(elevel,...)
Definition: elog.h:157
#define Assert(condition)
Definition: c.h:804
#define INSTR_TIME_GET_MICROSEC(t)
Definition: instr_time.h:205
#define XLogFileName(fname, tli, logSegNo, wal_segsz_bytes)
int sync_method
Definition: xlog.c:108
#define INSTR_TIME_SET_CURRENT(t)
Definition: instr_time.h:156
bool enableFsync
Definition: globals.c:122
#define SYNC_METHOD_FDATASYNC
Definition: xlog.h:26
int errmsg(const char *fmt,...)
Definition: elog.c:909
#define elog(elevel,...)
Definition: elog.h:232
#define _(x)
Definition: elog.c:89

◆ LocalProcessControlFile()

void LocalProcessControlFile ( bool  reset)

Definition at line 5085 of file xlog.c.

References Assert, palloc(), and ReadControlFile().

Referenced by BackendRun(), PostgresMain(), PostmasterMain(), and PostmasterStateMachine().

5086 {
5087  Assert(reset || ControlFile == NULL);
5088  ControlFile = palloc(sizeof(ControlFileData));
5089  ReadControlFile();
5090 }
void reset(void)
Definition: sql-declare.c:562
static void ReadControlFile(void)
Definition: xlog.c:4756
static ControlFileData * ControlFile
Definition: xlog.c:748
#define Assert(condition)
Definition: c.h:804
void * palloc(Size size)
Definition: mcxt.c:1062

◆ PromoteIsTriggered()

bool PromoteIsTriggered ( void  )

Definition at line 12839 of file xlog.c.

References XLogCtlData::info_lck, LocalPromoteIsTriggered, XLogCtlData::SharedPromoteIsTriggered, SpinLockAcquire, and SpinLockRelease.

Referenced by pg_wal_replay_pause(), and pg_wal_replay_resume().

12840 {
12841  /*
12842  * We check shared state each time only until a standby promotion is
12843  * triggered. We can't trigger a promotion again, so there's no need to
12844  * keep checking after the shared variable has once been seen true.
12845  */
12847  return true;
12848 
12852 
12853  return LocalPromoteIsTriggered;
12854 }
slock_t info_lck
Definition: xlog.c:737
static bool LocalPromoteIsTriggered
Definition: xlog.c:245
#define SpinLockAcquire(lock)
Definition: spin.h:62
#define SpinLockRelease(lock)
Definition: spin.h:64
static XLogCtlData * XLogCtl
Definition: xlog.c:740
bool SharedPromoteIsTriggered
Definition: xlog.c:671

◆ RecoveryInProgress()

bool RecoveryInProgress ( void  )

Definition at line 8237 of file xlog.c.

References InitXLOGAccess(), LocalRecoveryInProgress, pg_memory_barrier, RECOVERY_STATE_DONE, XLogCtlData::SharedRecoveryState, and XLogCtl.

Referenced by BackgroundWriterMain(), BeginReportingGUCOptions(), brin_desummarize_range(), brin_summarize_range(), btree_index_mainfork_expected(), check_transaction_read_only(), check_XactIsoLevel(), CheckArchiveTimeout(), CheckLogicalDecodingRequirements(), CheckpointerMain(), ComputeXidHorizons(), CreateCheckPoint(), CreateEndOfRecoveryRecord(), CreateRestartPoint(), do_pg_start_backup(), do_pg_stop_backup(), error_commit_ts_disabled(), get_relation_info(), GetNewMultiXactId(), GetNewObjectId(), GetNewTransactionId(), GetOldestActiveTransactionId(), GetOldestSafeDecodingTransactionId(), GetRunningTransactionData(), GetSerializableTransactionSnapshot(), GetSerializableTransactionSnapshotInt(), GetSnapshotData(), gin_clean_pending_list(), GlobalVisTestFor(), heap_force_common(), heap_page_prune_opt(), IdentifySystem(), InitPostgres(), InitTempTableNamespace(), IsCheckpointOnSchedule(), LockAcquireExtended(), MaintainLatestCompletedXid(), MarkBufferDirtyHint(), perform_base_backup(), pg_create_restore_point(), pg_current_wal_flush_lsn(), pg_current_wal_insert_lsn(), pg_current_wal_lsn(), pg_get_wal_replay_pause_state(), pg_is_in_recovery(), pg_is_wal_replay_paused(), pg_logical_slot_get_changes_guts(), pg_promote(), pg_replication_slot_advance(), pg_switch_wal(), pg_wal_replay_pause(), pg_wal_replay_resume(), pg_walfile_name(), pg_walfile_name_offset(), PrepareRedoAdd(), PrepareRedoRemove(), PreventCommandDuringRecovery(), ProcSendSignal(), ProcSleep(), read_local_xlog_page(), ReplicationSlotReserveWal(), replorigin_check_prerequisites(), ReportChangedGUCOptions(), sendDir(), SerialSetActiveSerXmin(), show_in_hot_standby(), ShutdownXLOG(), SnapBuildWaitSnapshot(), standard_ProcessUtility(), StartLogicalReplication(), StartTransaction(), TransactionIdIsInProgress(), TruncateMultiXact(), UpdateFullPageWrites(), WalReceiverMain(), WalSndWaitForWal(), XLogBackgroundFlush(), XLogInsertAllowed(), XLogNeedsFlush(), and XLogSendPhysical().

8238 {
8239  /*
8240  * We check shared state each time only until we leave recovery mode. We
8241  * can't re-enter recovery, so there's no need to keep checking after the
8242  * shared variable has once been seen false.
8243  */
8245  return false;
8246  else
8247  {
8248  /*
8249  * use volatile pointer to make sure we make a fresh read of the
8250  * shared variable.
8251  */
8252  volatile XLogCtlData *xlogctl = XLogCtl;
8253 
8255 
8256  /*
8257  * Initialize TimeLineID and RedoRecPtr when we discover that recovery
8258  * is finished. InitPostgres() relies upon this behaviour to ensure
8259  * that InitXLOGAccess() is called at backend startup. (If you change
8260  * this, see also LocalSetXLogInsertAllowed.)
8261  */
8263  {
8264  /*
8265  * If we just exited recovery, make sure we read TimeLineID and
8266  * RedoRecPtr after SharedRecoveryState (for machines with weak
8267  * memory ordering).
8268  */
8270  InitXLOGAccess();
8271  }
8272 
8273  /*
8274  * Note: We don't need a memory barrier when we're still in recovery.
8275  * We might exit recovery immediately after return, so the caller
8276  * can't rely on 'true' meaning that we're still in recovery anyway.
8277  */
8278 
8279  return LocalRecoveryInProgress;
8280  }
8281 }
void InitXLOGAccess(void)
Definition: xlog.c:8503
RecoveryState SharedRecoveryState
Definition: xlog.c:659
#define pg_memory_barrier()
Definition: atomics.h:145
static XLogCtlData * XLogCtl
Definition: xlog.c:740
static bool LocalRecoveryInProgress
Definition: xlog.c:233

◆ register_persistent_abort_backup_handler()

void register_persistent_abort_backup_handler ( void  )

Definition at line 11712 of file xlog.c.

References before_shmem_exit(), DatumGetBool, and do_pg_abort_backup().

Referenced by pg_start_backup().

11713 {
11714  static bool already_done = false;
11715 
11716  if (already_done)
11717  return;
11719  already_done = true;
11720 }
void do_pg_abort_backup(int code, Datum arg)
Definition: xlog.c:11680
#define DatumGetBool(X)
Definition: postgres.h:437
void before_shmem_exit(pg_on_exit_callback function, Datum arg)
Definition: ipc.c:333

◆ RemovePromoteSignalFiles()

void RemovePromoteSignalFiles ( void  )

Definition at line 12911 of file xlog.c.

References PROMOTE_SIGNAL_FILE.

Referenced by CheckForStandbyTrigger(), and PostmasterMain().

12912 {
12913  unlink(PROMOTE_SIGNAL_FILE);
12914 }
#define PROMOTE_SIGNAL_FILE
Definition: xlog.h:405

◆ SetRecoveryPause()

void SetRecoveryPause ( bool  recoveryPause)

Definition at line 6123 of file xlog.c.

References ConditionVariableBroadcast(), XLogCtlData::info_lck, RECOVERY_NOT_PAUSED, RECOVERY_PAUSE_REQUESTED, XLogCtlData::recoveryNotPausedCV, XLogCtlData::recoveryPauseState, SpinLockAcquire, and SpinLockRelease.

Referenced by pg_wal_replay_pause(), pg_wal_replay_resume(), RecoveryRequiresIntParameter(), and StartupXLOG().

6124 {
6126 
6127  if (!recoveryPause)
6131 
6133 
6134  if (!recoveryPause)
6136 }
RecoveryPauseState recoveryPauseState
Definition: xlog.c:728
slock_t info_lck
Definition: xlog.c:737
void ConditionVariableBroadcast(ConditionVariable *cv)
#define SpinLockAcquire(lock)
Definition: spin.h:62
ConditionVariable recoveryNotPausedCV
Definition: xlog.c:729
#define SpinLockRelease(lock)
Definition: spin.h:64
static XLogCtlData * XLogCtl
Definition: xlog.c:740

◆ SetWalWriterSleeping()

void SetWalWriterSleeping ( bool  sleeping)

Definition at line 12944 of file xlog.c.

References XLogCtlData::info_lck, SpinLockAcquire, SpinLockRelease, and XLogCtlData::WalWriterSleeping.

Referenced by WalWriterMain().

12945 {
12947  XLogCtl->WalWriterSleeping = sleeping;
12949 }
slock_t info_lck
Definition: xlog.c:737
#define SpinLockAcquire(lock)
Definition: spin.h:62
#define SpinLockRelease(lock)
Definition: spin.h:64
bool WalWriterSleeping
Definition: xlog.c:678
static XLogCtlData * XLogCtl
Definition: xlog.c:740

◆ ShutdownXLOG()

void ShutdownXLOG ( int  code,
Datum  arg 
)

Definition at line 8653 of file xlog.c.

References Assert, AuxProcessResourceOwner, CHECKPOINT_IMMEDIATE, CHECKPOINT_IS_SHUTDOWN, CreateCheckPoint(), CreateRestartPoint(), CurrentResourceOwner, ereport, errmsg(), IsPostmasterEnvironment, LOG, NOTICE, RecoveryInProgress(), RequestXLogSwitch(), WalSndInitStopping(), WalSndWaitStopping(), XLogArchiveCommandSet, and XLogArchivingActive.

Referenced by HandleCheckpointerInterrupts(), and InitPostgres().

8654 {
8655  /*
8656  * We should have an aux process resource owner to use, and we should not
8657  * be in a transaction that's installed some other resowner.
8658  */
8660  Assert(CurrentResourceOwner == NULL ||
8663 
8664  /* Don't be chatty in standalone mode */
8666  (errmsg("shutting down")));
8667 
8668  /*
8669  * Signal walsenders to move to stopping state.
8670  */
8672 
8673  /*
8674  * Wait for WAL senders to be in stopping state. This prevents commands
8675  * from writing new WAL.
8676  */
8678 
8679  if (RecoveryInProgress())
8681  else
8682  {
8683  /*
8684  * If archiving is enabled, rotate the last XLOG file so that all the
8685  * remaining records are archived (postmaster wakes up the archiver
8686  * process one more time at the end of shutdown). The checkpoint
8687  * record will go to the next XLOG file and won't be archived (yet).
8688  */
8690  RequestXLogSwitch(false);
8691 
8693  }
8694 }
bool IsPostmasterEnvironment
Definition: globals.c:111
XLogRecPtr RequestXLogSwitch(bool mark_unimportant)
Definition: xlog.c:9896
void CreateCheckPoint(int flags)
Definition: xlog.c:8919
ResourceOwner CurrentResourceOwner
Definition: resowner.c:146
bool CreateRestartPoint(int flags)
Definition: xlog.c:9465
#define XLogArchiveCommandSet()
Definition: xlog.h:195
#define LOG
Definition: elog.h:26
bool RecoveryInProgress(void)
Definition: xlog.c:8237
ResourceOwner AuxProcessResourceOwner
Definition: resowner.c:149
void WalSndWaitStopping(void)
Definition: walsender.c:3172
#define ereport(elevel,...)
Definition: elog.h:157
#define NOTICE
Definition: elog.h:37
void WalSndInitStopping(void)
Definition: walsender.c:3146
#define Assert(condition)
Definition: c.h:804
#define XLogArchivingActive()
Definition: xlog.h:190
int errmsg(const char *fmt,...)
Definition: elog.c:909
#define CHECKPOINT_IMMEDIATE
Definition: xlog.h:234
#define CHECKPOINT_IS_SHUTDOWN
Definition: xlog.h:231

◆ StartupRequestWalReceiverRestart()

void StartupRequestWalReceiverRestart ( void  )

Definition at line 12788 of file xlog.c.

References currentSource, ereport, errmsg(), LOG, pendingWalRcvRestart, WalRcvRunning(), and XLOG_FROM_STREAM.

Referenced by StartupRereadConfig().

12789 {
12791  {
12792  ereport(LOG,
12793  (errmsg("WAL receiver process shutdown requested")));
12794 
12795  pendingWalRcvRestart = true;
12796  }
12797 }
#define LOG
Definition: elog.h:26
static bool pendingWalRcvRestart
Definition: xlog.c:837
#define ereport(elevel,...)
Definition: elog.h:157
static XLogSource currentSource
Definition: xlog.c:835
int errmsg(const char *fmt,...)
Definition: elog.c:909
bool WalRcvRunning(void)

◆ StartupXLOG()

void StartupXLOG ( void  )

Definition at line 6450 of file xlog.c.

References AdvanceNextFullTransactionIdPastXid(), AdvanceOldestClogXid(), AllowCascadeReplication, appendStringInfo(), appendStringInfoString(), ArchiveRecoveryRequested, ErrorContextCallback::arg, Assert, AuxProcessResourceOwner, BACKUP_LABEL_FILE, BACKUP_LABEL_OLD, ControlFileData::backupEndPoint, ControlFileData::backupEndRequired, ControlFileData::backupStartPoint, bgwriterLaunched, buf, ErrorContextCallback::callback, ControlFileData::checkPoint, CHECKPOINT_END_OF_RECOVERY, CHECKPOINT_FORCE, CHECKPOINT_IMMEDIATE, CHECKPOINT_WAIT, ControlFileData::checkPointCopy, CheckRecoveryConsistency(), CheckRequiredParameterValues(), checkTimeLineSwitch(), checkXLogConsistency(), XLogCtlData::ckptFullXid, close, CompleteCommitTsInitialization(), CreateCheckPoint(), CreateEndOfRecoveryRecord(), XLogCtlInsert::CurrBytePos, XLogCtlData::currentChunkStartTime, CurrentResourceOwner, StringInfoData::data, DataDir, DB_IN_ARCHIVE_RECOVERY, DB_IN_CRASH_RECOVERY, DB_IN_PRODUCTION, DB_SHUTDOWNED, DB_SHUTDOWNED_IN_RECOVERY, DB_SHUTDOWNING, DEBUG1, DEBUG2, DEBUG3, DeleteAllExportedSnapshotFiles(), DisownLatch(), doPageWrites, doRequestWalReceiverReply, durable_rename(), elog, EnableHotStandby, EnableSyncRequestForwarding(), EndRecPtr, ereport, errcode(), errcode_for_file_access(), errdetail(), errhint(), errmsg(), errmsg_internal(), ERROR, error_context_stack, ExecuteRecoveryCommand(), exitArchiveRecovery(), FATAL, findNewestTimeLine(), FirstNormalUnloggedLSN, XLogwrtRqst::Flush, XLogwrtResult::Flush, CheckPoint::fullPageWrites, XLogCtlInsert::fullPageWrites, FullTransactionIdRetreat(), GetCurrentTimestamp(), GetLatestXTime(), HandleStartupProcInterrupts(), InArchiveRecovery, XLogCtlData::info_lck, XLogCtlData::InitializedUpTo, InitRecoveryTransactionEnvironment(), initStringInfo(), InRecovery, InRedo, Insert(), XLogCtlData::Insert, InvalidXLogRecPtr, IsPostmasterEnvironment, IsUnderPostmaster, lastFullPageWrites, LastRec, XLogCtlData::lastReplayedEndRecPtr, XLogCtlData::lastReplayedTLI, XLogCtlData::lastSegSwitchLSN, XLogCtlData::lastSegSwitchTime, RunningTransactionsData::latestCompletedXid, VariableCacheData::latestCompletedXid, lfirst, LocalPromoteIsTriggered, LocalSetXLogInsertAllowed(), LocalXLogInsertAllowed, LOG, XLogCtlData::LogwrtResult, LogwrtResult, XLogCtlData::LogwrtRqst, LSN_FORMAT_ARGS, LW_EXCLUSIVE, LWLockAcquire(), LWLockRelease(), MAXFNAMELEN, MAXPGPATH, ControlFileData::minRecoveryPoint, minRecoveryPoint, ControlFileData::minRecoveryPointTLI, minRecoveryPointTLI, MultiXactSetNextMXact(), CheckPoint::newestCommitTsXid, CheckPoint::nextMulti, CheckPoint::nextMultiOffset, CheckPoint::nextOid, VariableCacheData::nextOid, CheckPoint::nextXid, RunningTransactionsData::nextXid, VariableCacheData::nextXid, NIL, NOTICE, tablespaceinfo::oid, VariableCacheData::oidCount, CheckPoint::oldestActiveXid, CheckPoint::oldestCommitTsXid, CheckPoint::oldestMulti, CheckPoint::oldestMultiDB, RunningTransactionsData::oldestRunningXid, CheckPoint::oldestXid, CheckPoint::oldestXidDB, OwnLatch(), XLogCtlData::pages, palloc(), PANIC, tablespaceinfo::path, pfree(), pg_rusage_init(), pg_rusage_show(), pg_usleep(), pgstat_reset_all(), PMSIGNAL_RECOVERY_STARTED, PreallocXlogFiles(), PrescanPreparedTransactions(), XLogCtlInsert::PrevBytePos, ErrorContextCallback::previous, CheckPoint::PrevTimeLineID, xl_end_of_recovery::PrevTimeLineID, XLogCtlData::PrevTimeLineID, primary_image_masked, proc_exit(), ProcArrayApplyRecoveryInfo(), ProcArrayInitRecovery(), psprintf(), PublishStartupProcessInformation(), reachedConsistency, read_backup_label(), read_tablespace_map(), XLogReaderState::readBuf, ReadCheckpointRecord(), readFile, XLogReaderState::readPagePtr, ReadRecord(), readRecoverySignalFile(), XLogReaderState::ReadRecPtr, ReadRecPtr, RecordKnownAssignedTransactionIds(), RecoverPreparedTransactions(), RECOVERY_NOT_PAUSED, RECOVERY_STATE_ARCHIVE, RECOVERY_STATE_CRASH, RECOVERY_STATE_DONE, RECOVERY_TARGET_ACTION_PAUSE, RECOVERY_TARGET_ACTION_PROMOTE, RECOVERY_TARGET_ACTION_SHUTDOWN, RECOVERY_TARGET_IMMEDIATE, RECOVERY_TARGET_LSN, RECOVERY_TARGET_NAME, RECOVERY_TARGET_TIME, RECOVERY_TARGET_UNSET, RECOVERY_TARGET_XID, recoveryApplyDelay(), recoveryEndCommand, XLogCtlData::recoveryLastXTime, recoveryPausesHere(), XLogCtlData::recoveryPauseState, recoveryStopAfter, recoveryStopLSN, recoveryStopName, recoveryStopsAfter(), recoveryStopsBefore(), recoveryStopTime, recoveryStopXid, recoveryTarget, recoveryTargetAction, recoveryTargetLSN, recoveryTargetName, recoveryTargetTime, recoveryTargetTLI, recoveryTargetXid, XLogCtlData::recoveryWakeupLatch, CheckPoint::redo, RedoRecPtr, XLogCtlInsert::RedoRecPtr, XLogCtlData::RedoRecPtr, RedoStartLSN, RelationCacheInitFileRemove(), remove_tablespace_symlink(), RemoveNonParentXlogFiles(), RemoveTempXlogFiles(), replay_image_masked, XLogCtlData::replayEndRecPtr, XLogCtlData::replayEndTLI, RequestCheckpoint(), ResetUnloggedRelations(), restoreTimeLineHistoryFiles(), restoreTwoPhaseData(), RmgrData::rm_cleanup, RM_MAX_ID, RmgrData::rm_redo, rm_redo_error_callback(), RmgrData::rm_startup, RmgrTable, XLogReaderState::seg, SendPostmasterSignal(), SetCommitTsLimit(), SetMultiXactIdLimit(), SetRecoveryPause(), SetTransactionIdLimit(), XLogCtlData::SharedRecoveryState, ShmemVariableCache, ShutdownRecoveryTransactionEnvironment(), ShutdownWalRcv(), snprintf, SpinLockAcquire, SpinLockRelease, STANDBY_DISABLED, STANDBY_INITIALIZED, StandbyMode, StandbyModeRequested, StandbyRecoverPreparedTransactions(), standbyState, StartupCLOG(), StartupCommitTs(), StartupMultiXact(), StartupReorderBuffer(), StartupReplicationOrigin(), StartupReplicationSlots(), StartupSUBTRANS(), stat, ControlFileData::state, str_time(), RunningTransactionsData::subxcnt, RunningTransactionsData::subxid_overflow, symlink, SyncDataDirectory(), ControlFileData::system_identifier, XLogReaderState::system_identifier, TABLESPACE_MAP, TABLESPACE_MAP_OLD, CheckPoint::ThisTimeLineID, ThisTimeLineID, xl_end_of_recovery::ThisTimeLineID, XLogCtlData::ThisTimeLineID, CheckPoint::time, ControlFileData::time, timestamptz_to_str(), tliOfPointInHistory(), tliSwitchPoint(), trace_recovery_messages, ControlFileData::track_commit_timestamp, TransactionIdIsNormal, TransactionIdIsValid, TransactionIdRetreat, TrimCLOG(), TrimMultiXact(), U64FromFullTransactionId, UINT64_FORMAT, UNLOGGED_RELATION_CLEANUP, UNLOGGED_RELATION_INIT, ControlFileData::unloggedLSN, XLogCtlData::unloggedLSN, UpdateControlFile(), UpdateFullPageWrites(), validateRecoveryParameters(), ValidateXLOGDirectoryStructure(), wal_decode_buffer_size, wal_segment_close(), wal_segment_size, WalRcvForceReply(), WalRcvStreaming(), WalSndWakeup(), XLogwrtRqst::Write, XLogwrtResult::Write, writeTimeLineHistory(), WALOpenSegment::ws_tli, RunningTransactionsData::xcnt, XidFromFullTransactionId, RunningTransactionsData::xids, XLogRecord::xl_info, XLogRecord::xl_rmid, XLogRecord::xl_xid, XLogCtlData::xlblocks, XLByteToPrevSeg, XLOG_CHECKPOINT_SHUTDOWN, XLOG_END_OF_RECOVERY, xlog_outdesc(), XLogArchiveCleanup(), XLogArchiveIsReadyOrDone(), XLogArchiveNotify(), XLogArchivingActive, XLogBeginRead(), XLOGDIR, XLogFileName, XLogFilePath, XLogPageRead(), XLogPrefetch(), XLogPrefetchBegin(), XLogPrefetchEnd(), XLogPrefetchReconfigure(), xlogreader, XLogReaderAllocate(), XLogReaderFree(), XLogReaderSetDecodeBuffer(), XLogReceiptTime, XLogRecGetData, XLogRecPtrIsInvalid, XLogRecPtrToBufIdx, XLogRecPtrToBytePos(), XLogReportParameters(), XLogSegmentOffset, XLR_CHECK_CONSISTENCY, XLR_INFO_MASK, XLREAD_NEED_DATA, and XRecOffIsValid.

Referenced by InitPostgres(), and StartupProcessMain().

6451 {
6453  CheckPoint checkPoint;
6454  bool wasShutdown;
6455  bool reachedRecoveryTarget = false;
6456  bool haveBackupLabel = false;
6457  bool haveTblspcMap = false;
6458  XLogRecPtr RecPtr,
6459  checkPointLoc,
6460  EndOfLog;
6461  TimeLineID EndOfLogTLI;
6462  TimeLineID PrevTimeLineID;
6463  XLogRecord *record;
6464  TransactionId oldestActiveXID;
6465  bool backupEndRequired = false;
6466  bool backupFromStandby = false;
6467  DBState dbstate_at_startup;
6469  bool promoted = false;
6470  struct stat st;
6471 
6472  /*
6473  * We should have an aux process resource owner to use, and we should not
6474  * be in a transaction that's installed some other resowner.
6475  */
6477  Assert(CurrentResourceOwner == NULL ||
6480 
6481  /*
6482  * Check that contents look valid.
6483  */
6485  ereport(FATAL,
6486  (errmsg("control file contains invalid checkpoint location")));
6487 
6488  switch (ControlFile->state)
6489  {
6490  case DB_SHUTDOWNED:
6491 
6492  /*
6493  * This is the expected case, so don't be chatty in standalone
6494  * mode
6495  */
6497  (errmsg("database system was shut down at %s",
6498  str_time(ControlFile->time))));
6499  break;
6500 
6502  ereport(LOG,
6503  (errmsg("database system was shut down in recovery at %s",
6504  str_time(ControlFile->time))));
6505  break;
6506 
6507  case DB_SHUTDOWNING:
6508  ereport(LOG,
6509  (errmsg("database system shutdown was interrupted; last known up at %s",
6510  str_time(ControlFile->time))));
6511  break;
6512 
6513  case DB_IN_CRASH_RECOVERY:
6514  ereport(LOG,
6515  (errmsg("database system was interrupted while in recovery at %s",
6517  errhint("This probably means that some data is corrupted and"
6518  " you will have to use the last backup for recovery.")));
6519  break;
6520 
6522  ereport(LOG,
6523  (errmsg("database system was interrupted while in recovery at log time %s",
6525  errhint("If this has occurred more than once some data might be corrupted"
6526  " and you might need to choose an earlier recovery target.")));
6527  break;
6528 
6529  case DB_IN_PRODUCTION:
6530  ereport(LOG,
6531  (errmsg("database system was interrupted; last known up at %s",
6532  str_time(ControlFile->time))));
6533  break;
6534 
6535  default:
6536  ereport(FATAL,
6537  (errmsg("control file contains invalid database cluster state")));
6538  }
6539 
6540  /* This is just to allow attaching to startup process with a debugger */
6541 #ifdef XLOG_REPLAY_DELAY
6543  pg_usleep(60000000L);
6544 #endif
6545 
6546  /*
6547  * Verify that pg_wal and pg_wal/archive_status exist. In cases where
6548  * someone has performed a copy for PITR, these directories may have been
6549  * excluded and need to be re-created.
6550  */
6552 
6553  /*----------
6554  * If we previously crashed, perform a couple of actions:
6555  *
6556  * - The pg_wal directory may still include some temporary WAL segments
6557  * used when creating a new segment, so perform some clean up to not
6558  * bloat this path. This is done first as there is no point to sync
6559  * this temporary data.
6560  *
6561  * - There might be data which we had written, intending to fsync it, but
6562  * which we had not actually fsync'd yet. Therefore, a power failure in
6563  * the near future might cause earlier unflushed writes to be lost, even
6564  * though more recent data written to disk from here on would be
6565  * persisted. To avoid that, fsync the entire data directory.
6566  */
6567  if (ControlFile->state != DB_SHUTDOWNED &&
6569  {
6572  }
6573 
6574  /*
6575  * Initialize on the assumption we want to recover to the latest timeline
6576  * that's active according to pg_control.
6577  */
6581  else
6583 
6584  /*
6585  * Check for signal files, and if so set up state for offline recovery
6586  */
6589 
6591  {
6593  ereport(LOG,
6594  (errmsg("entering standby mode")));
6595  else if (recoveryTarget == RECOVERY_TARGET_XID)
6596  ereport(LOG,
6597  (errmsg("starting point-in-time recovery to XID %u",
6598  recoveryTargetXid)));
6600  ereport(LOG,
6601  (errmsg("starting point-in-time recovery to %s",
6604