Skip to content

Commit

Permalink
Fix zenith_test_evict mode and clear_buffer_cache() function
Browse files Browse the repository at this point in the history
Using InvalidateBuffer is wrong, because if the page is concurrently
dirtied, it will throw away the dirty page without calling
smgwrite(). In Neon, that means that the last-written LSN update for
the page is missed.

In v16, use the new InvalidateVictimBuffer() function that does what
we need. In v15 and v14, backport the InvalidateVictimBuffer()
function.

Fixes issue neondatabase/neon#7802
  • Loading branch information
hlinnaka committed May 21, 2024
1 parent c271017 commit 3c2b9d5
Showing 1 changed file with 10 additions and 8 deletions.
18 changes: 10 additions & 8 deletions src/backend/storage/buffer/bufmgr.c
Original file line number Diff line number Diff line change
Expand Up @@ -2473,24 +2473,26 @@ UnpinBuffer(BufferDesc *buf)
if (zenith_test_evict && !InRecovery)
{
buf_state = LockBufHdr(buf);
if (BUF_STATE_GET_REFCOUNT(buf_state) == 0)
if ((buf_state & BM_VALID) && BUF_STATE_GET_REFCOUNT(buf_state) == 0)
{
ReservePrivateRefCountEntry();
PinBuffer_Locked(buf);
if (buf_state & BM_DIRTY)
{
ReservePrivateRefCountEntry();
PinBuffer_Locked(buf);
if (LWLockConditionalAcquire(BufferDescriptorGetContentLock(buf),
LW_SHARED))
{
FlushOneBuffer(b);
LWLockRelease(BufferDescriptorGetContentLock(buf));
}
UnpinBuffer(buf);
}
else
{
InvalidateBuffer(buf);
}

/*
* Try to invalidate the page. This can fail if the page is
* concurrently modified; we'll let it be in that case
*/
(void) InvalidateVictimBuffer(buf);
UnpinBuffer(buf);
}
else
UnlockBufHdr(buf, buf_state);
Expand Down

0 comments on commit 3c2b9d5

Please sign in to comment.