PostgreSQL Source Code git master
Data Structures | Macros | Typedefs | Enumerations | Functions | Variables
xlogutils.h File Reference
#include "access/xlogreader.h"
#include "storage/bufmgr.h"
Include dependency graph for xlogutils.h:
This graph shows which files directly or indirectly include this file:

Go to the source code of this file.

Data Structures

 

Macros

 

Typedefs

 

Enumerations

 
 

Functions

bool  XLogHaveInvalidPages (void)
 
void  XLogCheckInvalidPages (void)
 
void  XLogDropRelation (RelFileLocator rlocator, ForkNumber forknum)
 
void  XLogDropDatabase (Oid dbid)
 
void  XLogTruncateRelation (RelFileLocator rlocator, ForkNumber forkNum, BlockNumber nblocks)
 
 
 
 
 
 
 
int  read_local_xlog_page (XLogReaderState *state, XLogRecPtr targetPagePtr, int reqLen, XLogRecPtr targetRecPtr, char *cur_page)
 
int  read_local_xlog_page_no_wait (XLogReaderState *state, XLogRecPtr targetPagePtr, int reqLen, XLogRecPtr targetRecPtr, char *cur_page)
 
 
 
 
void  WALReadRaiseError (WALReadError *errinfo)
 

Variables

 
 
 

Macro Definition Documentation

InHotStandby

#define InHotStandby   (standbyState >= STANDBY_SNAPSHOT_PENDING)

Definition at line 60 of file xlogutils.h.

Typedef Documentation

ReadLocalXLogPageNoWaitPrivate

Enumeration Type Documentation

HotStandbyState

Enumerator
STANDBY_DISABLED 
STANDBY_INITIALIZED 
STANDBY_SNAPSHOT_PENDING 
STANDBY_SNAPSHOT_READY 

Definition at line 50 of file xlogutils.h.

51{
HotStandbyState
Definition: xlogutils.h:51
@ STANDBY_DISABLED
Definition: xlogutils.h:52
@ STANDBY_SNAPSHOT_READY
Definition: xlogutils.h:55
@ STANDBY_SNAPSHOT_PENDING
Definition: xlogutils.h:54
@ STANDBY_INITIALIZED
Definition: xlogutils.h:53

XLogRedoAction

Enumerator
BLK_NEEDS_REDO 
BLK_DONE 
BLK_RESTORED 
BLK_NOTFOUND 

Definition at line 72 of file xlogutils.h.

73{
74 BLK_NEEDS_REDO, /* changes from WAL record need to be applied */
75 BLK_DONE, /* block is already up-to-date */
76 BLK_RESTORED, /* block was restored from a full-page image */
77 BLK_NOTFOUND, /* block was not found (and hence does not
78 * need to be replayed) */
XLogRedoAction
Definition: xlogutils.h:73
@ BLK_RESTORED
Definition: xlogutils.h:76
@ BLK_NEEDS_REDO
Definition: xlogutils.h:74
@ BLK_DONE
Definition: xlogutils.h:75
@ BLK_NOTFOUND
Definition: xlogutils.h:77

Function Documentation

CreateFakeRelcacheEntry()

Relation CreateFakeRelcacheEntry ( RelFileLocator  rlocator )

Definition at line 571 of file xlogutils.c.

572{
573 FakeRelCacheEntry fakeentry;
574 Relation rel;
575
576 /* Allocate the Relation struct and all related space in one block. */
577 fakeentry = palloc0(sizeof(FakeRelCacheEntryData));
578 rel = (Relation) fakeentry;
579
580 rel->rd_rel = &fakeentry->pgc;
581 rel->rd_locator = rlocator;
582
583 /*
584 * We will never be working with temp rels during recovery or while
585 * syncing WAL-skipped files.
586 */
588
589 /* It must be a permanent table here */
590 rel->rd_rel->relpersistence = RELPERSISTENCE_PERMANENT;
591
592 /* We don't know the name of the relation; use relfilenumber instead */
593 sprintf(RelationGetRelationName(rel), "%u", rlocator.relNumber);
594
595 /*
596 * We set up the lockRelId in case anything tries to lock the dummy
597 * relation. Note that this is fairly bogus since relNumber may be
598 * different from the relation's OID. It shouldn't really matter though.
599 * In recovery, we are running by ourselves and can't have any lock
600 * conflicts. While syncing, we already hold AccessExclusiveLock.
601 */
602 rel->rd_lockInfo.lockRelId.dbId = rlocator.dbOid;
603 rel->rd_lockInfo.lockRelId.relId = rlocator.relNumber;
604
605 /*
606 * Set up a non-pinned SMgrRelation reference, so that we don't need to
607 * worry about unpinning it on error.
608 */
609 rel->rd_smgr = smgropen(rlocator, INVALID_PROC_NUMBER);
610
611 return rel;
612}
struct RelationData * Relation
Definition: genam.h:30
void * palloc0(Size size)
Definition: mcxt.c:1395
#define sprintf
Definition: port.h:241
#define INVALID_PROC_NUMBER
Definition: procnumber.h:26
#define RelationGetRelationName(relation)
Definition: rel.h:548
SMgrRelation smgropen(RelFileLocator rlocator, ProcNumber backend)
Definition: smgr.c:240
FormData_pg_class pgc
Definition: xlogutils.c:551
LockRelId lockRelId
Definition: rel.h:46
Oid relId
Definition: rel.h:40
Oid dbId
Definition: rel.h:41
RelFileNumber relNumber
Definition: relfilelocator.h:62
Definition: rel.h:56
ProcNumber rd_backend
Definition: rel.h:60
LockInfoData rd_lockInfo
Definition: rel.h:114
SMgrRelation rd_smgr
Definition: rel.h:58
RelFileLocator rd_locator
Definition: rel.h:57
Form_pg_class rd_rel
Definition: rel.h:111

References LockRelId::dbId, RelFileLocator::dbOid, INVALID_PROC_NUMBER, LockInfoData::lockRelId, palloc0(), FakeRelCacheEntryData::pgc, RelationData::rd_backend, RelationData::rd_locator, RelationData::rd_lockInfo, RelationData::rd_rel, RelationData::rd_smgr, RelationGetRelationName, LockRelId::relId, RelFileLocator::relNumber, smgropen(), and sprintf.

Referenced by heap_xlog_delete(), heap_xlog_insert(), heap_xlog_lock(), heap_xlog_lock_updated(), heap_xlog_multi_insert(), heap_xlog_update(), heap_xlog_visible(), smgr_redo(), and smgrDoPendingSyncs().

FreeFakeRelcacheEntry()

void FreeFakeRelcacheEntry ( Relation  fakerel )

Definition at line 618 of file xlogutils.c.

619{
620 pfree(fakerel);
621}
void pfree(void *pointer)
Definition: mcxt.c:1594

References pfree().

Referenced by heap_xlog_delete(), heap_xlog_insert(), heap_xlog_lock(), heap_xlog_lock_updated(), heap_xlog_multi_insert(), heap_xlog_update(), heap_xlog_visible(), smgr_redo(), and smgrDoPendingSyncs().

read_local_xlog_page()

int read_local_xlog_page ( XLogReaderStatestate,
XLogRecPtr  targetPagePtr,
int  reqLen,
XLogRecPtr  targetRecPtr,
char *  cur_page 
)

Definition at line 845 of file xlogutils.c.

847{
848 return read_local_xlog_page_guts(state, targetPagePtr, reqLen,
849 targetRecPtr, cur_page, true);
850}
Definition: regguts.h:323
static int read_local_xlog_page_guts(XLogReaderState *state, XLogRecPtr targetPagePtr, int reqLen, XLogRecPtr targetRecPtr, char *cur_page, bool wait_for_wal)
Definition: xlogutils.c:869

References read_local_xlog_page_guts().

Referenced by create_logical_replication_slot(), LogicalReplicationSlotHasPendingWal(), LogicalSlotAdvanceAndCheckSnapState(), pg_logical_slot_get_changes_guts(), and XlogReadTwoPhaseData().

read_local_xlog_page_no_wait()

int read_local_xlog_page_no_wait ( XLogReaderStatestate,
XLogRecPtr  targetPagePtr,
int  reqLen,
XLogRecPtr  targetRecPtr,
char *  cur_page 
)

Definition at line 857 of file xlogutils.c.

860{
861 return read_local_xlog_page_guts(state, targetPagePtr, reqLen,
862 targetRecPtr, cur_page, false);
863}

References read_local_xlog_page_guts().

Referenced by InitXLogReaderState().

wal_segment_close()

void wal_segment_close ( XLogReaderStatestate )

Definition at line 831 of file xlogutils.c.

832{
833 close(state->seg.ws_file);
834 /* need to check errno? */
835 state->seg.ws_file = -1;
836}
#define close(a)
Definition: win32.h:12

References close.

Referenced by create_logical_replication_slot(), CreateReplicationSlot(), InitWalRecovery(), InitXLogReaderState(), LogicalReplicationSlotHasPendingWal(), LogicalSlotAdvanceAndCheckSnapState(), pg_logical_slot_get_changes_guts(), StartLogicalReplication(), StartReplication(), SummarizeWAL(), WalSndErrorCleanup(), XlogReadTwoPhaseData(), and XLogSendPhysical().

wal_segment_open()

void wal_segment_open ( XLogReaderStatestate,
XLogSegNo  nextSegNo,
TimeLineIDtli_p 
)

Definition at line 806 of file xlogutils.c.

808{
809 TimeLineID tli = *tli_p;
810 char path[MAXPGPATH];
811
812 XLogFilePath(path, tli, nextSegNo, state->segcxt.ws_segsize);
813 state->seg.ws_file = BasicOpenFile(path, O_RDONLY | PG_BINARY);
814 if (state->seg.ws_file >= 0)
815 return;
816
817 if (errno == ENOENT)
820 errmsg("requested WAL segment %s has already been removed",
821 path)));
822 else
825 errmsg("could not open file \"%s\": %m",
826 path)));
827}
#define PG_BINARY
Definition: c.h:1272
int errcode_for_file_access(void)
Definition: elog.c:877
int errmsg(const char *fmt,...)
Definition: elog.c:1071
#define ERROR
Definition: elog.h:39
#define ereport(elevel,...)
Definition: elog.h:150
int BasicOpenFile(const char *fileName, int fileFlags)
Definition: fd.c:1086
#define MAXPGPATH
static void XLogFilePath(char *path, TimeLineID tli, XLogSegNo logSegNo, int wal_segsz_bytes)
Definition: xlog_internal.h:210
uint32 TimeLineID
Definition: xlogdefs.h:62

References BasicOpenFile(), ereport, errcode_for_file_access(), errmsg(), ERROR, MAXPGPATH, PG_BINARY, and XLogFilePath().

Referenced by create_logical_replication_slot(), InitXLogReaderState(), LogicalReplicationSlotHasPendingWal(), LogicalSlotAdvanceAndCheckSnapState(), pg_logical_slot_get_changes_guts(), SummarizeWAL(), and XlogReadTwoPhaseData().

WALReadRaiseError()

void WALReadRaiseError ( WALReadErrorerrinfo )

Definition at line 1011 of file xlogutils.c.

1012{
1013 WALOpenSegment *seg = &errinfo->wre_seg;
1014 char fname[MAXFNAMELEN];
1015
1016 XLogFileName(fname, seg->ws_tli, seg->ws_segno, wal_segment_size);
1017
1018 if (errinfo->wre_read < 0)
1019 {
1020 errno = errinfo->wre_errno;
1021 ereport(ERROR,
1023 errmsg("could not read from WAL segment %s, offset %d: %m",
1024 fname, errinfo->wre_off)));
1025 }
1026 else if (errinfo->wre_read == 0)
1027 {
1028 ereport(ERROR,
1030 errmsg("could not read from WAL segment %s, offset %d: read %d of %d",
1031 fname, errinfo->wre_off, errinfo->wre_read,
1032 errinfo->wre_req)));
1033 }
1034}
int errcode(int sqlerrcode)
Definition: elog.c:854
#define ERRCODE_DATA_CORRUPTED
Definition: pg_basebackup.c:42
XLogSegNo ws_segno
Definition: xlogreader.h:48
TimeLineID ws_tli
Definition: xlogreader.h:49
int wre_off
Definition: xlogreader.h:385
int wre_read
Definition: xlogreader.h:387
int wre_errno
Definition: xlogreader.h:384
int wre_req
Definition: xlogreader.h:386
WALOpenSegment wre_seg
Definition: xlogreader.h:388
int wal_segment_size
Definition: xlog.c:144
#define MAXFNAMELEN
Definition: xlog_internal.h:156
static void XLogFileName(char *fname, TimeLineID tli, XLogSegNo logSegNo, int wal_segsz_bytes)
Definition: xlog_internal.h:166

References ereport, errcode(), ERRCODE_DATA_CORRUPTED, errcode_for_file_access(), errmsg(), ERROR, MAXFNAMELEN, wal_segment_size, WALReadError::wre_errno, WALReadError::wre_off, WALReadError::wre_read, WALReadError::wre_req, WALReadError::wre_seg, WALOpenSegment::ws_segno, WALOpenSegment::ws_tli, and XLogFileName().

Referenced by logical_read_xlog_page(), read_local_xlog_page_guts(), summarizer_read_local_xlog_page(), and XLogSendPhysical().

XLogCheckInvalidPages()

void XLogCheckInvalidPages ( void  )

Definition at line 234 of file xlogutils.c.

235{
236 HASH_SEQ_STATUS status;
237 xl_invalid_page *hentry;
238 bool foundone = false;
239
240 if (invalid_page_tab == NULL)
241 return; /* nothing to do */
242
244
245 /*
246 * Our strategy is to emit WARNING messages for all remaining entries and
247 * only PANIC after we've dumped all the available info.
248 */
249 while ((hentry = (xl_invalid_page *) hash_seq_search(&status)) != NULL)
250 {
252 hentry->key.blkno, hentry->present);
253 foundone = true;
254 }
255
256 if (foundone)
258 "WAL contains references to invalid pages");
259
261 invalid_page_tab = NULL;
262}
void hash_destroy(HTAB *hashp)
Definition: dynahash.c:865
void * hash_seq_search(HASH_SEQ_STATUS *status)
Definition: dynahash.c:1415
void hash_seq_init(HASH_SEQ_STATUS *status, HTAB *hashp)
Definition: dynahash.c:1380
#define WARNING
Definition: elog.h:36
#define PANIC
Definition: elog.h:42
#define elog(elevel,...)
Definition: elog.h:226
BlockNumber blkno
Definition: xlogutils.c:69
RelFileLocator locator
Definition: xlogutils.c:67
ForkNumber forkno
Definition: xlogutils.c:68
xl_invalid_page_key key
Definition: xlogutils.c:74
bool present
Definition: xlogutils.c:75
bool ignore_invalid_pages
Definition: xlogutils.c:34
static void report_invalid_page(int elevel, RelFileLocator locator, ForkNumber forkno, BlockNumber blkno, bool present)
Definition: xlogutils.c:86
static HTAB * invalid_page_tab
Definition: xlogutils.c:78

References xl_invalid_page_key::blkno, elog, xl_invalid_page_key::forkno, hash_destroy(), hash_seq_init(), hash_seq_search(), ignore_invalid_pages, invalid_page_tab, xl_invalid_page::key, xl_invalid_page_key::locator, PANIC, xl_invalid_page::present, report_invalid_page(), and WARNING.

Referenced by CheckRecoveryConsistency().

XLogDropDatabase()

void XLogDropDatabase ( Oid  dbid )

Definition at line 641 of file xlogutils.c.

642{
643 /*
644 * This is unnecessarily heavy-handed, as it will close SMgrRelation
645 * objects for other databases as well. DROP DATABASE occurs seldom enough
646 * that it's not worth introducing a variant of smgrdestroy for just this
647 * purpose.
648 */
650
652}
void smgrdestroyall(void)
Definition: smgr.c:386
static void forget_invalid_pages_db(Oid dbid)
Definition: xlogutils.c:196

References forget_invalid_pages_db(), and smgrdestroyall().

Referenced by dbase_redo().

XLogDropRelation()

void XLogDropRelation ( RelFileLocator  rlocator,
ForkNumber  forknum 
)

Definition at line 630 of file xlogutils.c.

631{
632 forget_invalid_pages(rlocator, forknum, 0);
633}
static void forget_invalid_pages(RelFileLocator locator, ForkNumber forkno, BlockNumber minblkno)
Definition: xlogutils.c:165

References forget_invalid_pages().

Referenced by DropRelationFiles().

XLogHaveInvalidPages()

bool XLogHaveInvalidPages ( void  )

Definition at line 224 of file xlogutils.c.

225{
226 if (invalid_page_tab != NULL &&
228 return true;
229 return false;
230}
int64 hash_get_num_entries(HTAB *hashp)
Definition: dynahash.c:1336

References hash_get_num_entries(), and invalid_page_tab.

Referenced by RecoveryRestartPoint().

XLogInitBufferForRedo()

Buffer XLogInitBufferForRedo ( XLogReaderStaterecord,
uint8  block_id 
)

Definition at line 315 of file xlogutils.c.

316{
317 Buffer buf;
318
319 XLogReadBufferForRedoExtended(record, block_id, RBM_ZERO_AND_LOCK, false,
320 &buf);
321 return buf;
322}
int Buffer
Definition: buf.h:23
@ RBM_ZERO_AND_LOCK
Definition: bufmgr.h:47
static char * buf
Definition: pg_test_fsync.c:72
XLogRedoAction XLogReadBufferForRedoExtended(XLogReaderState *record, uint8 block_id, ReadBufferMode mode, bool get_cleanup_lock, Buffer *buf)
Definition: xlogutils.c:340

References buf, RBM_ZERO_AND_LOCK, and XLogReadBufferForRedoExtended().

Referenced by _bt_restore_meta(), brin_xlog_createidx(), brin_xlog_insert_update(), brin_xlog_revmap_extend(), btree_xlog_mark_page_halfdead(), btree_xlog_newroot(), btree_xlog_split(), btree_xlog_unlink_page(), ginRedoCreatePTree(), ginRedoDeleteListPages(), ginRedoInsertListPage(), ginRedoUpdateMetapage(), gistRedoPageSplitRecord(), hash_xlog_add_ovfl_page(), hash_xlog_init_bitmap_page(), hash_xlog_init_meta_page(), heap_xlog_insert(), heap_xlog_multi_insert(), heap_xlog_update(), seq_redo(), spgRedoAddLeaf(), spgRedoAddNode(), spgRedoMoveLeafs(), spgRedoPickSplit(), and spgRedoSplitTuple().

XLogReadBufferExtended()

Buffer XLogReadBufferExtended ( RelFileLocator  rlocator,
ForkNumber  forknum,
BlockNumber  blkno,
ReadBufferMode  mode,
Buffer  recent_buffer 
)

Definition at line 460 of file xlogutils.c.

463{
464 BlockNumber lastblock;
465 Buffer buffer;
466 SMgrRelation smgr;
467
468 Assert(blkno != P_NEW);
469
470 /* Do we have a clue where the buffer might be already? */
471 if (BufferIsValid(recent_buffer) &&
472 mode == RBM_NORMAL &&
473 ReadRecentBuffer(rlocator, forknum, blkno, recent_buffer))
474 {
475 buffer = recent_buffer;
476 goto recent_buffer_fast_path;
477 }
478
479 /* Open the relation at smgr level */
480 smgr = smgropen(rlocator, INVALID_PROC_NUMBER);
481
482 /*
483 * Create the target file if it doesn't already exist. This lets us cope
484 * if the replay sequence contains writes to a relation that is later
485 * deleted. (The original coding of this routine would instead suppress
486 * the writes, but that seems like it risks losing valuable data if the
487 * filesystem loses an inode during a crash. Better to write the data
488 * until we are actually told to delete the file.)
489 */
490 smgrcreate(smgr, forknum, true);
491
492 lastblock = smgrnblocks(smgr, forknum);
493
494 if (blkno < lastblock)
495 {
496 /* page exists in file */
497 buffer = ReadBufferWithoutRelcache(rlocator, forknum, blkno,
498 mode, NULL, true);
499 }
500 else
501 {
502 /* hm, page doesn't exist in file */
503 if (mode == RBM_NORMAL)
504 {
505 log_invalid_page(rlocator, forknum, blkno, false);
506 return InvalidBuffer;
507 }
508 if (mode == RBM_NORMAL_NO_LOG)
509 return InvalidBuffer;
510 /* OK to extend the file */
511 /* we do this in recovery only - no rel-extension lock needed */
513 buffer = ExtendBufferedRelTo(BMR_SMGR(smgr, RELPERSISTENCE_PERMANENT),
514 forknum,
515 NULL,
518 blkno + 1,
519 mode);
520 }
521
522recent_buffer_fast_path:
523 if (mode == RBM_NORMAL)
524 {
525 /* check that page has been initialized */
526 Page page = BufferGetPage(buffer);
527
528 /*
529 * We assume that PageIsNew is safe without a lock. During recovery,
530 * there should be no other backends that could modify the buffer at
531 * the same time.
532 */
533 if (PageIsNew(page))
534 {
535 ReleaseBuffer(buffer);
536 log_invalid_page(rlocator, forknum, blkno, true);
537 return InvalidBuffer;
538 }
539 }
540
541 return buffer;
542}
uint32 BlockNumber
Definition: block.h:31
#define InvalidBuffer
Definition: buf.h:25
Buffer ExtendBufferedRelTo(BufferManagerRelation bmr, ForkNumber fork, BufferAccessStrategy strategy, uint32 flags, BlockNumber extend_to, ReadBufferMode mode)
Definition: bufmgr.c:922
void ReleaseBuffer(Buffer buffer)
Definition: bufmgr.c:5338
Buffer ReadBufferWithoutRelcache(RelFileLocator rlocator, ForkNumber forkNum, BlockNumber blockNum, ReadBufferMode mode, BufferAccessStrategy strategy, bool permanent)
Definition: bufmgr.c:842
bool ReadRecentBuffer(RelFileLocator rlocator, ForkNumber forkNum, BlockNumber blockNum, Buffer recent_buffer)
Definition: bufmgr.c:682
#define P_NEW
Definition: bufmgr.h:191
static Page BufferGetPage(Buffer buffer)
Definition: bufmgr.h:417
#define BMR_SMGR(p_smgr, p_relpersistence)
Definition: bufmgr.h:112
@ EB_PERFORMING_RECOVERY
Definition: bufmgr.h:78
@ EB_SKIP_EXTENSION_LOCK
Definition: bufmgr.h:75
@ RBM_NORMAL
Definition: bufmgr.h:46
@ RBM_NORMAL_NO_LOG
Definition: bufmgr.h:52
static bool BufferIsValid(Buffer bufnum)
Definition: bufmgr.h:368
static bool PageIsNew(const PageData *page)
Definition: bufpage.h:234
PageData * Page
Definition: bufpage.h:82
Assert(PointerIsAligned(start, uint64))
static PgChecksumMode mode
Definition: pg_checksums.c:55
BlockNumber smgrnblocks(SMgrRelation reln, ForkNumber forknum)
Definition: smgr.c:819
void smgrcreate(SMgrRelation reln, ForkNumber forknum, bool isRedo)
Definition: smgr.c:481
bool InRecovery
Definition: xlogutils.c:50
static void log_invalid_page(RelFileLocator locator, ForkNumber forkno, BlockNumber blkno, bool present)
Definition: xlogutils.c:101

References Assert(), BMR_SMGR, BufferGetPage(), BufferIsValid(), EB_PERFORMING_RECOVERY, EB_SKIP_EXTENSION_LOCK, ExtendBufferedRelTo(), InRecovery, INVALID_PROC_NUMBER, InvalidBuffer, log_invalid_page(), mode, P_NEW, PageIsNew(), RBM_NORMAL, RBM_NORMAL_NO_LOG, ReadBufferWithoutRelcache(), ReadRecentBuffer(), ReleaseBuffer(), smgrcreate(), smgrnblocks(), and smgropen().

Referenced by verifyBackupPageConsistency(), XLogReadBufferForRedoExtended(), and XLogRecordPageWithFreeSpace().

XLogReadBufferForRedo()

XLogRedoAction XLogReadBufferForRedo ( XLogReaderStaterecord,
uint8  block_id,
Bufferbuf 
)

Definition at line 303 of file xlogutils.c.

305{
306 return XLogReadBufferForRedoExtended(record, block_id, RBM_NORMAL,
307 false, buf);
308}

References buf, RBM_NORMAL, and XLogReadBufferForRedoExtended().

Referenced by _bt_clear_incomplete_split(), brin_xlog_desummarize_page(), brin_xlog_insert_update(), brin_xlog_revmap_extend(), brin_xlog_samepage_update(), brin_xlog_update(), btree_xlog_dedup(), btree_xlog_delete(), btree_xlog_insert(), btree_xlog_mark_page_halfdead(), btree_xlog_split(), btree_xlog_unlink_page(), generic_redo(), ginRedoClearIncompleteSplit(), ginRedoDeletePage(), ginRedoInsert(), ginRedoSplit(), ginRedoUpdateMetapage(), ginRedoVacuumDataLeafPage(), ginRedoVacuumPage(), gistRedoClearFollowRight(), gistRedoDeleteRecord(), gistRedoPageDelete(), gistRedoPageUpdateRecord(), hash_xlog_add_ovfl_page(), hash_xlog_delete(), hash_xlog_init_bitmap_page(), hash_xlog_insert(), hash_xlog_move_page_contents(), hash_xlog_split_allocate_page(), hash_xlog_split_cleanup(), hash_xlog_split_complete(), hash_xlog_split_page(), hash_xlog_squeeze_page(), hash_xlog_update_meta_page(), hash_xlog_vacuum_one_page(), heap_xlog_confirm(), heap_xlog_delete(), heap_xlog_inplace(), heap_xlog_insert(), heap_xlog_lock(), heap_xlog_lock_updated(), heap_xlog_multi_insert(), heap_xlog_update(), heap_xlog_visible(), spgRedoAddLeaf(), spgRedoAddNode(), spgRedoMoveLeafs(), spgRedoPickSplit(), spgRedoSplitTuple(), spgRedoVacuumLeaf(), spgRedoVacuumRedirect(), spgRedoVacuumRoot(), and xlog_redo().

XLogReadBufferForRedoExtended()

XLogRedoAction XLogReadBufferForRedoExtended ( XLogReaderStaterecord,
uint8  block_id,
ReadBufferMode  mode,
bool  get_cleanup_lock,
Bufferbuf 
)

Definition at line 340 of file xlogutils.c.

344{
345 XLogRecPtr lsn = record->EndRecPtr;
346 RelFileLocator rlocator;
347 ForkNumber forknum;
348 BlockNumber blkno;
349 Buffer prefetch_buffer;
350 Page page;
351 bool zeromode;
352 bool willinit;
353
354 if (!XLogRecGetBlockTagExtended(record, block_id, &rlocator, &forknum, &blkno,
355 &prefetch_buffer))
356 {
357 /* Caller specified a bogus block_id */
358 elog(PANIC, "failed to locate backup block with ID %d in WAL record",
359 block_id);
360 }
361
362 /*
363 * Make sure that if the block is marked with WILL_INIT, the caller is
364 * going to initialize it. And vice versa.
365 */
367 willinit = (XLogRecGetBlock(record, block_id)->flags & BKPBLOCK_WILL_INIT) != 0;
368 if (willinit && !zeromode)
369 elog(PANIC, "block with WILL_INIT flag in WAL record must be zeroed by redo routine");
370 if (!willinit && zeromode)
371 elog(PANIC, "block to be initialized in redo routine must be marked with WILL_INIT flag in the WAL record");
372
373 /* If it has a full-page image and it should be restored, do it. */
374 if (XLogRecBlockImageApply(record, block_id))
375 {
376 Assert(XLogRecHasBlockImage(record, block_id));
377 *buf = XLogReadBufferExtended(rlocator, forknum, blkno,
378 get_cleanup_lock ? RBM_ZERO_AND_CLEANUP_LOCK : RBM_ZERO_AND_LOCK,
379 prefetch_buffer);
380 page = BufferGetPage(*buf);
381 if (!RestoreBlockImage(record, block_id, page))
383 (errcode(ERRCODE_INTERNAL_ERROR),
384 errmsg_internal("%s", record->errormsg_buf)));
385
386 /*
387 * The page may be uninitialized. If so, we can't set the LSN because
388 * that would corrupt the page.
389 */
390 if (!PageIsNew(page))
391 {
392 PageSetLSN(page, lsn);
393 }
394
396
397 /*
398 * At the end of crash recovery the init forks of unlogged relations
399 * are copied, without going through shared buffers. So we need to
400 * force the on-disk state of init forks to always be in sync with the
401 * state in shared buffers.
402 */
403 if (forknum == INIT_FORKNUM)
405
406 return BLK_RESTORED;
407 }
408 else
409 {
410 *buf = XLogReadBufferExtended(rlocator, forknum, blkno, mode, prefetch_buffer);
411 if (BufferIsValid(*buf))
412 {
414 {
415 if (get_cleanup_lock)
417 else
419 }
420 if (lsn <= PageGetLSN(BufferGetPage(*buf)))
421 return BLK_DONE;
422 else
423 return BLK_NEEDS_REDO;
424 }
425 else
426 return BLK_NOTFOUND;
427 }
428}
void MarkBufferDirty(Buffer buffer)
Definition: bufmgr.c:2921
void LockBufferForCleanup(Buffer buffer)
Definition: bufmgr.c:5652
void LockBuffer(Buffer buffer, int mode)
Definition: bufmgr.c:5572
void FlushOneBuffer(Buffer buffer)
Definition: bufmgr.c:5318
#define BUFFER_LOCK_EXCLUSIVE
Definition: bufmgr.h:198
@ RBM_ZERO_AND_CLEANUP_LOCK
Definition: bufmgr.h:49
static void PageSetLSN(Page page, XLogRecPtr lsn)
Definition: bufpage.h:391
static XLogRecPtr PageGetLSN(const PageData *page)
Definition: bufpage.h:386
int errmsg_internal(const char *fmt,...)
Definition: elog.c:1161
ForkNumber
Definition: relpath.h:56
@ INIT_FORKNUM
Definition: relpath.h:61
char * errormsg_buf
Definition: xlogreader.h:311
XLogRecPtr EndRecPtr
Definition: xlogreader.h:207
uint64 XLogRecPtr
Definition: xlogdefs.h:21
bool XLogRecGetBlockTagExtended(XLogReaderState *record, uint8 block_id, RelFileLocator *rlocator, ForkNumber *forknum, BlockNumber *blknum, Buffer *prefetch_buffer)
Definition: xlogreader.c:2017
bool RestoreBlockImage(XLogReaderState *record, uint8 block_id, char *page)
Definition: xlogreader.c:2076
#define XLogRecBlockImageApply(decoder, block_id)
Definition: xlogreader.h:425
#define XLogRecGetBlock(decoder, i)
Definition: xlogreader.h:419
#define XLogRecHasBlockImage(decoder, block_id)
Definition: xlogreader.h:423
#define BKPBLOCK_WILL_INIT
Definition: xlogrecord.h:199
Buffer XLogReadBufferExtended(RelFileLocator rlocator, ForkNumber forknum, BlockNumber blkno, ReadBufferMode mode, Buffer recent_buffer)
Definition: xlogutils.c:460

References Assert(), BKPBLOCK_WILL_INIT, BLK_DONE, BLK_NEEDS_REDO, BLK_NOTFOUND, BLK_RESTORED, buf, BUFFER_LOCK_EXCLUSIVE, BufferGetPage(), BufferIsValid(), elog, XLogReaderState::EndRecPtr, ereport, errcode(), errmsg_internal(), ERROR, XLogReaderState::errormsg_buf, FlushOneBuffer(), INIT_FORKNUM, LockBuffer(), LockBufferForCleanup(), MarkBufferDirty(), mode, PageGetLSN(), PageIsNew(), PageSetLSN(), PANIC, RBM_ZERO_AND_CLEANUP_LOCK, RBM_ZERO_AND_LOCK, RestoreBlockImage(), XLogReadBufferExtended(), XLogRecBlockImageApply, XLogRecGetBlock, XLogRecGetBlockTagExtended(), and XLogRecHasBlockImage.

Referenced by btree_xlog_vacuum(), hash_xlog_delete(), hash_xlog_move_page_contents(), hash_xlog_split_allocate_page(), hash_xlog_squeeze_page(), hash_xlog_vacuum_one_page(), heap_xlog_prune_freeze(), heap_xlog_visible(), XLogInitBufferForRedo(), and XLogReadBufferForRedo().

XLogReadDetermineTimeline()

void XLogReadDetermineTimeline ( XLogReaderStatestate,
XLogRecPtr  wantPage,
uint32  wantLength,
TimeLineID  currTLI 
)

Definition at line 707 of file xlogutils.c.

709{
710 const XLogRecPtr lastReadPage = (state->seg.ws_segno *
711 state->segcxt.ws_segsize + state->segoff);
712
713 Assert(wantPage != InvalidXLogRecPtr && wantPage % XLOG_BLCKSZ == 0);
714 Assert(wantLength <= XLOG_BLCKSZ);
715 Assert(state->readLen == 0 || state->readLen <= XLOG_BLCKSZ);
716 Assert(currTLI != 0);
717
718 /*
719 * If the desired page is currently read in and valid, we have nothing to
720 * do.
721 *
722 * The caller should've ensured that it didn't previously advance readOff
723 * past the valid limit of this timeline, so it doesn't matter if the
724 * current TLI has since become historical.
725 */
726 if (lastReadPage == wantPage &&
727 state->readLen != 0 &&
728 lastReadPage + state->readLen >= wantPage + Min(wantLength, XLOG_BLCKSZ - 1))
729 return;
730
731 /*
732 * If we're reading from the current timeline, it hasn't become historical
733 * and the page we're reading is after the last page read, we can again
734 * just carry on. (Seeking backwards requires a check to make sure the
735 * older page isn't on a prior timeline).
736 *
737 * currTLI might've become historical since the caller obtained the value,
738 * but the caller is required not to read past the flush limit it saw at
739 * the time it looked up the timeline. There's nothing we can do about it
740 * if StartupXLOG() renames it to .partial concurrently.
741 */
742 if (state->currTLI == currTLI && wantPage >= lastReadPage)
743 {
744 Assert(state->currTLIValidUntil == InvalidXLogRecPtr);
745 return;
746 }
747
748 /*
749 * If we're just reading pages from a previously validated historical
750 * timeline and the timeline we're reading from is valid until the end of
751 * the current segment we can just keep reading.
752 */
753 if (state->currTLIValidUntil != InvalidXLogRecPtr &&
754 state->currTLI != currTLI &&
755 state->currTLI != 0 &&
756 ((wantPage + wantLength) / state->segcxt.ws_segsize) <
757 (state->currTLIValidUntil / state->segcxt.ws_segsize))
758 return;
759
760 /*
761 * If we reach this point we're either looking up a page for random
762 * access, the current timeline just became historical, or we're reading
763 * from a new segment containing a timeline switch. In all cases we need
764 * to determine the newest timeline on the segment.
765 *
766 * If it's the current timeline we can just keep reading from here unless
767 * we detect a timeline switch that makes the current timeline historical.
768 * If it's a historical timeline we can read all the segment on the newest
769 * timeline because it contains all the old timelines' data too. So only
770 * one switch check is required.
771 */
772 {
773 /*
774 * We need to re-read the timeline history in case it's been changed
775 * by a promotion or replay from a cascaded replica.
776 */
777 List *timelineHistory = readTimeLineHistory(currTLI);
778 XLogRecPtr endOfSegment;
779
780 endOfSegment = ((wantPage / state->segcxt.ws_segsize) + 1) *
781 state->segcxt.ws_segsize - 1;
782 Assert(wantPage / state->segcxt.ws_segsize ==
783 endOfSegment / state->segcxt.ws_segsize);
784
785 /*
786 * Find the timeline of the last LSN on the segment containing
787 * wantPage.
788 */
789 state->currTLI = tliOfPointInHistory(endOfSegment, timelineHistory);
790 state->currTLIValidUntil = tliSwitchPoint(state->currTLI, timelineHistory,
791 &state->nextTLI);
792
793 Assert(state->currTLIValidUntil == InvalidXLogRecPtr ||
794 wantPage + wantLength < state->currTLIValidUntil);
795
796 list_free_deep(timelineHistory);
797
798 elog(DEBUG3, "switched to timeline %u valid until %X/%08X",
799 state->currTLI,
800 LSN_FORMAT_ARGS(state->currTLIValidUntil));
801 }
802}
List * readTimeLineHistory(TimeLineID targetTLI)
Definition: timeline.c:76
TimeLineID tliOfPointInHistory(XLogRecPtr ptr, List *history)
Definition: timeline.c:544
XLogRecPtr tliSwitchPoint(TimeLineID tli, List *history, TimeLineID *nextTLI)
Definition: timeline.c:572
#define Min(x, y)
Definition: c.h:1003
#define DEBUG3
Definition: elog.h:28
void list_free_deep(List *list)
Definition: list.c:1560
Definition: pg_list.h:54
#define LSN_FORMAT_ARGS(lsn)
Definition: xlogdefs.h:46
#define InvalidXLogRecPtr
Definition: xlogdefs.h:28

References Assert(), DEBUG3, elog, InvalidXLogRecPtr, list_free_deep(), LSN_FORMAT_ARGS, Min, readTimeLineHistory(), tliOfPointInHistory(), and tliSwitchPoint().

Referenced by logical_read_xlog_page(), and read_local_xlog_page_guts().

XLogTruncateRelation()

void XLogTruncateRelation ( RelFileLocator  rlocator,
ForkNumber  forkNum,
BlockNumber  nblocks 
)

Definition at line 660 of file xlogutils.c.

662{
663 forget_invalid_pages(rlocator, forkNum, nblocks);
664}

References forget_invalid_pages().

Referenced by smgr_redo().

Variable Documentation

ignore_invalid_pages

PGDLLIMPORT bool ignore_invalid_pages
extern

Definition at line 34 of file xlogutils.c.

Referenced by log_invalid_page(), and XLogCheckInvalidPages().

InRecovery

standbyState

AltStyle によって変換されたページ (->オリジナル) /