From e0090c86900877bf0911c53dcf4a30bc81d03047 Mon Sep 17 00:00:00 2001 From: Michael Paquier Date: Sat, 23 Mar 2019 08:37:36 +0900 Subject: [PATCH] Add option -N/--no-sync to pg_checksums This is an option consistent with what pg_dump, pg_rewind and pg_basebackup provide which is useful for leveraging the I/O effort when testing things, not to be used in a production environment. Author: Michael Paquier Reviewed-by: Michael Banck, Fabien Coelho, Sergei Kornilov Discussion: https://postgr.es/m/20181221201616.GD4974@nighthawk.caipicrew.dd-dns.de --- doc/src/sgml/ref/pg_checksums.sgml | 16 ++++++++++++++++ src/bin/pg_checksums/pg_checksums.c | 17 +++++++++++++---- src/bin/pg_checksums/t/002_actions.pl | 10 +++++----- 3 files changed, 34 insertions(+), 9 deletions(-) diff --git a/doc/src/sgml/ref/pg_checksums.sgml b/doc/src/sgml/ref/pg_checksums.sgml index 5343a8aa7e8..1f4d4ab8b44 100644 --- a/doc/src/sgml/ref/pg_checksums.sgml +++ b/doc/src/sgml/ref/pg_checksums.sgml @@ -100,6 +100,22 @@ PostgreSQL documentation + + + + + + By default, pg_checksums will wait for all files + to be written safely to disk. This option causes + pg_checksums to return without waiting, which is + faster, but means that a subsequent operating system crash can leave + the updated data folder corrupt. Generally, this option is useful + for testing but should not be used on a production installation. + This option has no effect when using --check. + + + + diff --git a/src/bin/pg_checksums/pg_checksums.c b/src/bin/pg_checksums/pg_checksums.c index 25238cd69b4..f9ab27c77c6 100644 --- a/src/bin/pg_checksums/pg_checksums.c +++ b/src/bin/pg_checksums/pg_checksums.c @@ -35,6 +35,7 @@ static int64 badblocks = 0; static ControlFileData *ControlFile; static char *only_relfilenode = NULL; +static bool do_sync = true; static bool verbose = false; typedef enum @@ -69,6 +70,7 @@ usage(void) printf(_(" -c, --check check data checksums (default)\n")); printf(_(" -d, --disable disable data checksums\n")); printf(_(" -e, --enable enable data checksums\n")); + printf(_(" -N, --no-sync do not wait for changes to be written safely to disk\n")); printf(_(" -v, --verbose output verbose messages\n")); printf(_(" -r RELFILENODE check only relation with specified relfilenode\n")); printf(_(" -V, --version output version information, then exit\n")); @@ -297,6 +299,7 @@ main(int argc, char *argv[]) {"pgdata", required_argument, NULL, 'D'}, {"disable", no_argument, NULL, 'd'}, {"enable", no_argument, NULL, 'e'}, + {"no-sync", no_argument, NULL, 'N'}, {"verbose", no_argument, NULL, 'v'}, {NULL, 0, NULL, 0} }; @@ -324,7 +327,7 @@ main(int argc, char *argv[]) } } - while ((c = getopt_long(argc, argv, "cD:der:v", long_options, &option_index)) != -1) + while ((c = getopt_long(argc, argv, "cD:deNr:v", long_options, &option_index)) != -1) { switch (c) { @@ -337,6 +340,9 @@ main(int argc, char *argv[]) case 'e': mode = PG_MODE_ENABLE; break; + case 'N': + do_sync = false; + break; case 'v': verbose = true; break; @@ -472,11 +478,14 @@ main(int argc, char *argv[]) ControlFile->data_checksum_version = (mode == PG_MODE_ENABLE) ? PG_DATA_CHECKSUM_VERSION : 0; - printf(_("Syncing data directory\n")); - fsync_pgdata(DataDir, progname, PG_VERSION_NUM); + if (do_sync) + { + printf(_("Syncing data directory\n")); + fsync_pgdata(DataDir, progname, PG_VERSION_NUM); + } printf(_("Updating control file\n")); - update_controlfile(DataDir, progname, ControlFile, true); + update_controlfile(DataDir, progname, ControlFile, do_sync); if (verbose) printf(_("Data checksum version: %d\n"), ControlFile->data_checksum_version); diff --git a/src/bin/pg_checksums/t/002_actions.pl b/src/bin/pg_checksums/t/002_actions.pl index 3ab18a6b891..41575c52459 100644 --- a/src/bin/pg_checksums/t/002_actions.pl +++ b/src/bin/pg_checksums/t/002_actions.pl @@ -101,11 +101,11 @@ mkdir "$pgdata/global/pgsql_tmp"; append_to_file "$pgdata/global/pgsql_tmp/1.1", "foo"; # Enable checksums. -command_ok(['pg_checksums', '--enable', '-D', $pgdata], +command_ok(['pg_checksums', '--enable', '--no-sync', '-D', $pgdata], "checksums successfully enabled in cluster"); # Successive attempt to enable checksums fails. -command_fails(['pg_checksums', '--enable', '-D', $pgdata], +command_fails(['pg_checksums', '--enable', '--no-sync', '-D', $pgdata], "enabling checksums fails if already enabled"); # Control file should know that checksums are enabled. @@ -113,12 +113,12 @@ command_like(['pg_controldata', $pgdata], qr/Data page checksum version:.*1/, 'checksums enabled in control file'); -# Disable checksums again. +# Disable checksums again. Flush result here as that should be cheap. command_ok(['pg_checksums', '--disable', '-D', $pgdata], "checksums successfully disabled in cluster"); # Successive attempt to disable checksums fails. -command_fails(['pg_checksums', '--disable', '-D', $pgdata], +command_fails(['pg_checksums', '--disable', '--no-sync', '-D', $pgdata], "disabling checksums fails if already disabled"); # Control file should know that checksums are disabled. @@ -127,7 +127,7 @@ command_like(['pg_controldata', $pgdata], 'checksums disabled in control file'); # Enable checksums again for follow-up tests. -command_ok(['pg_checksums', '--enable', '-D', $pgdata], +command_ok(['pg_checksums', '--enable', '--no-sync', '-D', $pgdata], "checksums successfully enabled in cluster"); # Control file should know that checksums are enabled.