]> granicus.if.org Git - postgresql/commit
Avoid useless truncation attempts during VACUUM.
authorTom Lane <tgl@sss.pgh.pa.us>
Wed, 30 Dec 2015 22:13:15 +0000 (17:13 -0500)
committerTom Lane <tgl@sss.pgh.pa.us>
Wed, 30 Dec 2015 22:13:15 +0000 (17:13 -0500)
commite842908233bb9c5cea0e765fc828b52badd8228e
tree83c0c0d6bb99aea02b728660a3f3b16041864ac9
parente5e5267a91f4880c121bf50865cbc38078441989
Avoid useless truncation attempts during VACUUM.

VACUUM can skip heap pages altogether when there's a run of consecutive
pages that are all-visible according to the visibility map.  This causes it
to not update its nonempty_pages count, just as if those pages were empty,
which means that at the end we will think they are candidates for deletion.
Thus, we may take the table's AccessExclusive lock only to find that no
pages are really truncatable.  This usually causes no real problems on a
master server, thanks to the lock being acquired only conditionally; but on
hot-standby servers, the same lock must be acquired unconditionally which
can result in unnecessary query cancellations.

To improve matters, force examination of the table's last page whenever
we reach there with a nonempty_pages count that would allow a truncation
attempt.  If it's not empty, we'll advance nonempty_pages and thereby
prevent the truncation attempt.

If we are unable to acquire cleanup lock on that page, there's no need to
force it, unless we're doing an anti-wraparound vacuum.  We can just check
for tuples with a shared buffer lock and then give up.  (When we are doing
an anti-wraparound vacuum, and decide it's okay to skip the page because it
contains no freezable tuples, this patch still improves matters because
nonempty_pages is properly updated, which it was not before.)

Since only the last page is special-cased in this way, we might attempt a
truncation that will release many fewer pages than the normal heuristic
would suggest; at worst, only one page would be truncated.  But that seems
all right, because the situation won't repeat during the next vacuum.
The real problem with the old logic is that the useless truncation attempt
happens every time we vacuum, so long as the state of the last few dozen
pages doesn't change.

This is a longstanding deficiency, but since the consequences aren't very
severe in most scenarios, I'm not going to risk a back-patch.

Jeff Janes and Tom Lane
src/backend/commands/vacuumlazy.c