Commit 0f73aae1 authored by Tom Lane's avatar Tom Lane

Allow the wal_buffers setting to be auto-tuned to a reasonable value.

If wal_buffers is initially set to -1 (which is now the default), it's
replaced by 1/32nd of shared_buffers, with a minimum of 8 (the old default)
and a maximum of the XLOG segment size.  The allowed range for manual
settings is still from 4 up to whatever will fit in shared memory.

Greg Smith, with implementation correction by me.
parent 518b1e96
...@@ -1638,12 +1638,25 @@ SET ENABLE_SEQSCAN TO OFF; ...@@ -1638,12 +1638,25 @@ SET ENABLE_SEQSCAN TO OFF;
</indexterm> </indexterm>
<listitem> <listitem>
<para> <para>
The amount of memory used in shared memory for WAL data. The The amount of shared memory used for WAL data that has not yet been
default is 64 kilobytes (<literal>64kB</>). The setting need only written to disk. The default setting of -1 selects a size equal to
be large enough to hold the amount of WAL data generated by one 1/32nd (about 3%) of <xref linkend="guc-shared-buffers">, but not less
typical transaction, since the data is written out to disk at than <literal>64kB</literal> nor more than the size of one WAL
every transaction commit. This parameter can only be set at server segment, typically <literal>16MB</literal>. This value can be set
start. manually if the automatic choice is too large or too small,
but any positive value less than <literal>32kB</literal> will be
treated as <literal>32kB</literal>.
This parameter can only be set at server start.
</para>
<para>
The contents of the WAL buffers are written out to disk at every
transaction commit, so extremely large values are unlikely to
provide a significant benefit. However, setting this value to at
least a few megabytes can improve write performance on a busy
server where many clients are committing at once. The auto-tuning
selected by the default setting of -1 should give reasonable
results in most cases.
</para> </para>
<para> <para>
......
...@@ -69,7 +69,7 @@ ...@@ -69,7 +69,7 @@
/* User-settable parameters */ /* User-settable parameters */
int CheckPointSegments = 3; int CheckPointSegments = 3;
int wal_keep_segments = 0; int wal_keep_segments = 0;
int XLOGbuffers = 8; int XLOGbuffers = -1;
int XLogArchiveTimeout = 0; int XLogArchiveTimeout = 0;
bool XLogArchiveMode = false; bool XLogArchiveMode = false;
char *XLogArchiveCommand = NULL; char *XLogArchiveCommand = NULL;
...@@ -4777,6 +4777,41 @@ GetSystemIdentifier(void) ...@@ -4777,6 +4777,41 @@ GetSystemIdentifier(void)
return ControlFile->system_identifier; return ControlFile->system_identifier;
} }
/*
* Auto-tune the number of XLOG buffers.
*
* If the user-set value of wal_buffers is -1, we auto-tune to about 3% of
* shared_buffers, with a maximum of one XLOG segment and a minimum of 8
* blocks (8 was the default value prior to PostgreSQL 9.1, when auto-tuning
* was added). We also clamp manually-set values to at least 4 blocks; prior
* to PostgreSQL 9.1, a minimum of 4 was enforced by guc.c, but since that
* is no longer possible, we just silently treat such values as a request for
* the minimum.
*/
static void
XLOGTuneNumBuffers(void)
{
int xbuffers = XLOGbuffers;
char buf[32];
if (xbuffers == -1)
{
xbuffers = NBuffers / 32;
if (xbuffers > XLOG_SEG_SIZE / XLOG_BLCKSZ)
xbuffers = XLOG_SEG_SIZE / XLOG_BLCKSZ;
if (xbuffers < 8)
xbuffers = 8;
}
else if (xbuffers < 4)
xbuffers = 4;
if (xbuffers != XLOGbuffers)
{
snprintf(buf, sizeof(buf), "%d", xbuffers);
SetConfigOption("wal_buffers", buf, PGC_POSTMASTER, PGC_S_OVERRIDE);
}
}
/* /*
* Initialization of shared memory for XLOG * Initialization of shared memory for XLOG
*/ */
...@@ -4785,6 +4820,10 @@ XLOGShmemSize(void) ...@@ -4785,6 +4820,10 @@ XLOGShmemSize(void)
{ {
Size size; Size size;
/* Figure out how many XLOG buffers we need. */
XLOGTuneNumBuffers();
Assert(XLOGbuffers > 0);
/* XLogCtl */ /* XLogCtl */
size = sizeof(XLogCtlData); size = sizeof(XLogCtlData);
/* xlblocks array */ /* xlblocks array */
......
...@@ -1765,7 +1765,7 @@ static struct config_int ConfigureNamesInt[] = ...@@ -1765,7 +1765,7 @@ static struct config_int ConfigureNamesInt[] =
GUC_UNIT_XBLOCKS GUC_UNIT_XBLOCKS
}, },
&XLOGbuffers, &XLOGbuffers,
8, 4, INT_MAX, NULL, NULL -1, -1, INT_MAX, NULL, NULL
}, },
{ {
......
...@@ -162,7 +162,7 @@ ...@@ -162,7 +162,7 @@
# fsync_writethrough # fsync_writethrough
# open_sync # open_sync
#full_page_writes = on # recover from partial page writes #full_page_writes = on # recover from partial page writes
#wal_buffers = 64kB # min 32kB #wal_buffers = -1 # min 32kB, -1 sets based on shared_buffers
# (change requires restart) # (change requires restart)
#wal_writer_delay = 200ms # 1-10000 milliseconds #wal_writer_delay = 200ms # 1-10000 milliseconds
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment