postgresql/src/backend
Tom Lane e842908233 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
2015-12-30 17:13:15 -05:00
..
access Rename (new|old)estCommitTs to (new|old)estCommitTsXid 2015-12-28 12:34:11 -08:00
bootstrap
catalog Adjust behavior of single-user -j mode for better initdb error reporting. 2015-12-17 19:34:15 -05:00
commands Avoid useless truncation attempts during VACUUM. 2015-12-30 17:13:15 -05:00
executor Read from the same worker repeatedly until it returns no tuple. 2015-12-23 14:06:52 -05:00
foreign
lib Avoid use of float arithmetic in bipartite_match.c. 2015-08-23 13:02:18 -04:00
libpq Message improvements 2015-11-16 21:39:23 -05:00
main
nodes Remove unnecessary escaping in C character literals 2015-12-22 22:43:46 -05:00
optimizer Add some comments about division of labor between rewriter and planner. 2015-12-29 18:50:35 -05:00
parser Allow omitting one or both boundaries in an array slice specifier. 2015-12-22 21:05:29 -05:00
po
port On Windows, ensure shared memory handle gets closed if not being used. 2015-10-13 11:21:33 -04:00
postmaster Message improvements 2015-11-16 21:39:23 -05:00
regex Fix enforcement of restrictions inside regexp lookaround constraints. 2015-11-07 12:43:24 -05:00
replication Remove duplicate word. 2015-12-18 12:43:52 -05:00
rewrite Put back one copyObject() in rewriteTargetView(). 2015-12-29 16:45:47 -05:00
snowball Adjust behavior of single-user -j mode for better initdb error reporting. 2015-12-17 19:34:15 -05:00
storage Teach mdnblocks() not to create zero-length files. 2015-12-15 13:57:45 -05:00
tcop Adjust behavior of single-user -j mode for better initdb error reporting. 2015-12-17 19:34:15 -05:00
tsearch
utils Remove unnecessary escaping in C character literals 2015-12-22 22:43:46 -05:00
.gitignore Add .gitignore entries for AIX-specific intermediate build artifacts. 2015-07-08 20:44:22 -04:00
common.mk
Makefile Revert "Have dtrace depend on object files directly, not objfiles.txt" 2015-10-15 13:16:03 -04:00
nls.mk Remove trailing slashes from directories in find command 2015-09-18 22:06:54 -04:00