CHECKPOINT [ ( option [, ...] ) ]
<phrase>where <replaceable class="parameter">option</replaceable> can be one of:</phrase>
+
+ MODE { FAST | SPREAD }
</synopsis>
</refsynopsisdiv>
</para>
<para>
- The <command>CHECKPOINT</command> command forces a fast
+ By default, the <command>CHECKPOINT</command> command forces a fast
checkpoint when the command is issued, without waiting for a
regular checkpoint scheduled by the system (controlled by the settings in
<xref linkend="runtime-config-wal-checkpoints"/>).
+ To request the checkpoint be spread over a longer interval, set the
+ <literal>MODE</literal> option to <literal>SPREAD</literal>.
<command>CHECKPOINT</command> is not intended for use during normal
operation.
</para>
+ <para>
+ The server may consolidate concurrently requested checkpoints. Such
+ consolidated requests will contain a combined set of options. For example,
+ if one session requests a fast checkpoint and another requests a spread
+ checkpoint, the server may combine those requests and perform one fast
+ checkpoint.
+ </para>
+
<para>
If executed during recovery, the <command>CHECKPOINT</command> command
will force a restartpoint (see <xref linkend="wal-configuration"/>)
<refsect1>
<title>Parameters</title>
- <para>
- </para>
+ <variablelist>
+ <varlistentry>
+ <term><literal>MODE</literal></term>
+ <listitem>
+ <para>
+ When set to <literal>FAST</literal>, which is the default, the requested
+ checkpoint will be completed as fast as possible, which may result in a
+ significantly higher rate of I/O during the checkpoint.
+ </para>
+ <para>
+ <literal>MODE</literal> can also be set to <literal>SPREAD</literal> to
+ request the checkpoint be spread over a longer interval (controlled via
+ the settings in <xref linkend="runtime-config-wal-checkpoints"/>), like a
+ regular checkpoint scheduled by the system. This can reduce the rate of
+ I/O during the checkpoint.
+ </para>
+ </listitem>
+ </varlistentry>
+ </variablelist>
</refsect1>
<refsect1>
#include "access/xlog_internal.h"
#include "access/xlogrecovery.h"
#include "catalog/pg_authid.h"
+#include "commands/defrem.h"
#include "libpq/pqsignal.h"
#include "miscadmin.h"
#include "pgstat.h"
void
ExecCheckpoint(ParseState *pstate, CheckPointStmt *stmt)
{
+ bool fast = true;
+
foreach_ptr(DefElem, opt, stmt->options)
- ereport(ERROR,
- (errcode(ERRCODE_SYNTAX_ERROR),
- errmsg("unrecognized CHECKPOINT option \"%s\"", opt->defname),
- parser_errposition(pstate, opt->location)));
+ {
+ if (strcmp(opt->defname, "mode") == 0)
+ {
+ char *mode = defGetString(opt);
+
+ if (strcmp(mode, "spread") == 0)
+ fast = false;
+ else if (strcmp(mode, "fast") != 0)
+ ereport(ERROR,
+ (errcode(ERRCODE_SYNTAX_ERROR),
+ errmsg("unrecognized MODE option \"%s\"", mode),
+ parser_errposition(pstate, opt->location)));
+ }
+ else
+ ereport(ERROR,
+ (errcode(ERRCODE_SYNTAX_ERROR),
+ errmsg("unrecognized CHECKPOINT option \"%s\"", opt->defname),
+ parser_errposition(pstate, opt->location)));
+ }
if (!has_privs_of_role(GetUserId(), ROLE_PG_CHECKPOINT))
ereport(ERROR,
"pg_checkpoint")));
RequestCheckpoint(CHECKPOINT_WAIT |
- CHECKPOINT_FAST |
+ (fast ? CHECKPOINT_FAST : 0) |
(RecoveryInProgress() ? 0 : CHECKPOINT_FORCE));
}
/* CHECKPOINT */
else if (Matches("CHECKPOINT"))
COMPLETE_WITH("(");
+ else if (HeadMatches("CHECKPOINT", "(*") &&
+ !HeadMatches("CHECKPOINT", "(*)"))
+ {
+ /*
+ * This fires if we're in an unfinished parenthesized option list.
+ * get_previous_words treats a completed parenthesized option list as
+ * one word, so the above test is correct.
+ */
+ if (ends_with(prev_wd, '(') || ends_with(prev_wd, ','))
+ COMPLETE_WITH("MODE");
+ else if (TailMatches("MODE"))
+ COMPLETE_WITH("FAST", "SPREAD");
+ }
/* CLOSE */
else if (Matches("CLOSE"))
COMPLETE_WITH_QUERY_PLUS(Query_for_list_of_cursors,
-- of the checkpoint. But after a second checkpoint we'll see at least the
-- results of the first.
--
--- While at it, test checkpoint options.
+-- While at it, test checkpoint options. Note that we don't test MODE SPREAD
+-- because it would prolong the test.
CHECKPOINT (WRONG);
ERROR: unrecognized CHECKPOINT option "wrong"
LINE 1: CHECKPOINT (WRONG);
^
-CHECKPOINT;
+CHECKPOINT (MODE WRONG);
+ERROR: unrecognized MODE option "wrong"
+LINE 1: CHECKPOINT (MODE WRONG);
+ ^
+CHECKPOINT (MODE FAST);
CHECKPOINT;
SELECT num_requested > :rqst_ckpts_before FROM pg_stat_checkpointer;
?column?
-- of the checkpoint. But after a second checkpoint we'll see at least the
-- results of the first.
--
--- While at it, test checkpoint options.
+-- While at it, test checkpoint options. Note that we don't test MODE SPREAD
+-- because it would prolong the test.
CHECKPOINT (WRONG);
-CHECKPOINT;
+CHECKPOINT (MODE WRONG);
+CHECKPOINT (MODE FAST);
CHECKPOINT;
SELECT num_requested > :rqst_ckpts_before FROM pg_stat_checkpointer;