diff --git a/src/backend/postmaster/checkpointer.c b/src/backend/postmaster/checkpointer.c index c9473f7..c0883b1 100644 --- a/src/backend/postmaster/checkpointer.c +++ b/src/backend/postmaster/checkpointer.c @@ -47,6 +47,7 @@ #include "pgstat.h" #include "postmaster/bgwriter.h" #include "replication/syncrep.h" +#include "replication/walreceiver.h" #include "storage/bufmgr.h" #include "storage/ipc.h" #include "storage/lwlock.h" @@ -491,8 +492,8 @@ CheckpointerMain(void) * Initialize checkpointer-private variables used during checkpoint. */ ckpt_active = true; - if (!do_restartpoint) - ckpt_start_recptr = GetInsertRecPtr(); + ckpt_start_recptr = + do_restartpoint ? GetXLogReplayRecPtr(NULL) : GetInsertRecPtr(); ckpt_start_time = now; ckpt_cached_elapsed = 0; @@ -715,6 +716,7 @@ IsCheckpointOnSchedule(double progress) struct timeval now; double elapsed_xlogs, elapsed_time; + bool recovery_in_progress; Assert(ckpt_active); @@ -731,18 +733,27 @@ IsCheckpointOnSchedule(double progress) return false; /* - * Check progress against WAL segments written and checkpoint_segments. + * Check progress against WAL segments written, or replayed for + * hot standby, and checkpoint_segments. * * We compare the current WAL insert location against the location - * computed before calling CreateCheckPoint. The code in XLogInsert that - * actually triggers a checkpoint when checkpoint_segments is exceeded - * compares against RedoRecptr, so this is not completely accurate. - * However, it's good enough for our purposes, we're only calculating an - * estimate anyway. + * computed before calling CreateCheckPoint. The code in + * XLogInsert that actually triggers a checkpoint when + * checkpoint_segments is exceeded compares against RedoRecPtr. + * Similarly, we consult WAL replay location instead on hot + * standbys and XLogPageRead compares it aganst RedoRecPtr, too. + * Altough these are not completely accurate, it's good enough for + * our purposes, we're only calculating an estimate anyway. + */ + + /* + * Inhibit governing progress by segments in archive recovery. */ - if (!RecoveryInProgress()) + recovery_in_progress = RecoveryInProgress(); + if (!recovery_in_progress || WalRcvInProgress()) { - recptr = GetInsertRecPtr(); + recptr = recovery_in_progress ? GetXLogReplayRecPtr(NULL) : + GetInsertRecPtr(); elapsed_xlogs = (((double) (int32) (recptr.xlogid - ckpt_start_recptr.xlogid)) * XLogSegsPerFile + ((double) recptr.xrecoff - (double) ckpt_start_recptr.xrecoff) / XLogSegSize) /