Re: [PATCH] bufmgr: tighten LWLock:BufferMapping on InvalidateBuffer

From: Alexandre Felipe <o(dot)alexandre(dot)felipe(at)gmail(dot)com>
To: Yuhang Qiu <iamqyh(at)gmail(dot)com>
Cc: Andres Freund <andres(at)anarazel(dot)de>, PostgreSQL Hackers <pgsql-hackers(at)lists(dot)postgresql(dot)org>
Subject: Re: [PATCH] bufmgr: tighten LWLock:BufferMapping on InvalidateBuffer
Date: 2026-09-09 09:41:04
Message-ID: CAE8JnxMOJaSJSB0kVw6DkeCcoOqQUQiFTUkYbxGJnwDbohKhvw@mail.gmail.com
Views: Whole Thread | Raw Message | Download mbox | Resend email
Thread:
Lists: pgsql-hackers

On Tue, Aug 25, 2026 at 11:37 AM Yuhang Qiu <iamqyh(at)gmail(dot)com> wrote:

> I think it would be more useful to reduce unnecessary LWLock acquisitions
> or
> contention in higher-level code paths, such as buffer mapping and WAL
> buffers.
> For LWLock itself, the important part are atomic operations and cache-line
> contention (though there might be no lock contention, but at CPU level,
> emmm),
> wait-list contention, sleep/wakeup mechanism, and fairness...
>

Experiments show that a LWLockAcquire(...) = 1 is 1000x - 10000x slower
than an
LWLockAcquire(...) = 0. So, what I want to propose here is a more granular
lock.

I see that the locks are already used in partitions, I know that in
BufTable we are
using 128 locks, but it could have millions, we don't do it because of the
overhead, possibly managing waiting lists, and so on.

This patch supports granular LW_EXCLUSIVE locks, the immediate application I
could see is in BufTable, where a lock partition could be further
subdivided in up
to 26 rooms. Shared locks contend to any exclusive lock as today, but
exclusive
locks to different runs can be held simultaneously. (decided to include a
patch
with this before sending).

When the last LW_SHARED is released, all non-overlapping waiters are
awakened
simultaneously, with no need to wait. A LW_EXCLUSIVE might not be put to
sleep
if they don't require the same rooms.

A fairness consideration here is that this implementation doesn't wake up
the
waiters in order. The contending shared locks always lose to uncontended
exclusive locks, this might lead to (1 exclusive) shared (2-exclusive 1
exclusive)*
blocking shared forever. But I hope it serves to illustrate the idea.

If this seems acceptable, the next steps could be (not necessarily in that
order)
(1) adding a PRIORITY bit to mode to control whether it goes before or
after;
(2) don't skip a LW_SHARED if it is first on queue;
(3) accepting rooms on LW_SHARED mode, and promoting uncontended
locks to LW_EXCLUSIVE on the required rooms when the number of waiters is
small.
(4) combining the approaches choosing to release the configuration that
results
in the highest number of waiters being awakened.

I suspect that there are some "Wait for X" cases that I am not handling.

Attachment Content-Type Size
0001-lwlock-LW_EXCLUSIVE-Rooms.patch application/octet-stream 16.7 KB
0002-rooms-applied-to-BufferMapping.patch application/octet-stream 5.5 KB

In response to

Browse pgsql-hackers by date

  From Date Subject
Next Message Zsolt Parragi 2026-09-09 09:47:06 Re: pg_stat_progress_cluster: do not default to CLUSTER
Previous Message Zsolt Parragi 2026-09-09 09:36:12 Re: Improve error handling in test modules: test_extensible, test_bitmapset