diff options
Diffstat (limited to 'src/backend/storage/buffer/bufmgr.c')
-rw-r--r-- | src/backend/storage/buffer/bufmgr.c | 41 |
1 files changed, 31 insertions, 10 deletions
diff --git a/src/backend/storage/buffer/bufmgr.c b/src/backend/storage/buffer/bufmgr.c index 8f68bcc66d9..1adb6d360dd 100644 --- a/src/backend/storage/buffer/bufmgr.c +++ b/src/backend/storage/buffer/bufmgr.c @@ -953,6 +953,7 @@ void MarkBufferDirty(Buffer buffer) { volatile BufferDesc *bufHdr; + bool dirtied = false; if (!BufferIsValid(buffer)) elog(ERROR, "bad buffer ID: %d", buffer); @@ -973,19 +974,25 @@ MarkBufferDirty(Buffer buffer) Assert(bufHdr->refcount > 0); + if (!(bufHdr->flags & BM_DIRTY)) + dirtied = true; + + bufHdr->flags |= (BM_DIRTY | BM_JUST_DIRTIED); + + UnlockBufHdr(bufHdr); + /* - * If the buffer was not dirty already, do vacuum accounting. + * If the buffer was not dirty already, do vacuum accounting, and + * nudge bgwriter. */ - if (!(bufHdr->flags & BM_DIRTY)) + if (dirtied) { VacuumPageDirty++; if (VacuumCostActive) VacuumCostBalance += VacuumCostPageDirty; + if (ProcGlobal->bgwriterLatch) + SetLatch(ProcGlobal->bgwriterLatch); } - - bufHdr->flags |= (BM_DIRTY | BM_JUST_DIRTIED); - - UnlockBufHdr(bufHdr); } /* @@ -1307,8 +1314,12 @@ BufferSync(int flags) * BgBufferSync -- Write out some dirty buffers in the pool. * * This is called periodically by the background writer process. + * + * Returns true if the clocksweep has been "lapped", so that there's nothing + * to do. Also returns true if there's nothing to do because bgwriter was + * effectively disabled by setting bgwriter_lru_maxpages to 0. */ -void +bool BgBufferSync(void) { /* info obtained from freelist.c */ @@ -1365,7 +1376,7 @@ BgBufferSync(void) if (bgwriter_lru_maxpages <= 0) { saved_info_valid = false; - return; + return true; } /* @@ -1584,6 +1595,8 @@ BgBufferSync(void) recent_alloc, strategy_delta, scans_per_alloc, smoothed_density); #endif } + + return (bufs_to_lap == 0); } /* @@ -2341,16 +2354,24 @@ SetBufferCommitInfoNeedsSave(Buffer buffer) if ((bufHdr->flags & (BM_DIRTY | BM_JUST_DIRTIED)) != (BM_DIRTY | BM_JUST_DIRTIED)) { + bool dirtied = false; + LockBufHdr(bufHdr); Assert(bufHdr->refcount > 0); if (!(bufHdr->flags & BM_DIRTY)) + dirtied = true; + bufHdr->flags |= (BM_DIRTY | BM_JUST_DIRTIED); + UnlockBufHdr(bufHdr); + + if (dirtied) { VacuumPageDirty++; if (VacuumCostActive) VacuumCostBalance += VacuumCostPageDirty; + /* The bgwriter may need to be woken. */ + if (ProcGlobal->bgwriterLatch) + SetLatch(ProcGlobal->bgwriterLatch); } - bufHdr->flags |= (BM_DIRTY | BM_JUST_DIRTIED); - UnlockBufHdr(bufHdr); } } |