Add option -N/--no-sync to pg_upgrade
authorMichael Paquier <michael@paquier.xyz>
Sat, 18 Dec 2021 07:18:45 +0000 (16:18 +0900)
committerMichael Paquier <michael@paquier.xyz>
Sat, 18 Dec 2021 07:18:45 +0000 (16:18 +0900)
This is an option consistent with what the other tools of src/bin/
(pg_checksums, pg_dump, pg_rewind and pg_basebackup) provide which is
useful for leveraging the I/O effort when testing things.  This is not
to be used in a production environment.

All the regression tests of pg_upgrade are updated to use this new
option.  This happens to cut at most a couple of seconds in environments
constrained on I/O, by avoiding a flush of data folder for the new
cluster upgraded.

Author: Michael Paquier
Reviewed-by: Peter Eisentraut
Discussion: https://postgr.es/m/YbrhzuBmBxS/DkfX@paquier.xyz

doc/src/sgml/ref/pgupgrade.sgml
src/bin/pg_upgrade/option.c
src/bin/pg_upgrade/pg_upgrade.c
src/bin/pg_upgrade/pg_upgrade.h
src/bin/pg_upgrade/test.sh
src/tools/msvc/vcregress.pl

index 1289123129d6d89ed7cbfc5f86ded11640057d95..c5ce732ee983db5cfaa35310f040c4b5c8b8c7da 100644 (file)
@@ -130,6 +130,22 @@ PostgreSQL documentation
       cluster</para></listitem>
      </varlistentry>
 
+     <varlistentry>
+      <term><option>-N</option></term>
+      <term><option>--no-sync</option></term>
+      <listitem>
+       <para>
+        By default, <command>pg_upgrade</command> will wait for all files
+        of the upgraded cluster to be written safely to disk.  This option
+        causes <command>pg_upgrade</command> to return without waiting, which
+        is faster, but means that a subsequent operating system crash can leave
+        the synchronized data directory corrupt.  Generally, this option is
+        useful for testing but should not be used on a production
+        installation.
+       </para>
+      </listitem>
+     </varlistentry>
+
      <varlistentry>
       <term><option>-o</option> <replaceable class="parameter">options</replaceable></term>
       <term><option>--old-options</option> <replaceable class="parameter">options</replaceable></term>
index 2d92294d9d35e70f803e9f59dc702eaf7601422e..66fe16964e6f7580e261677f2a83c39804007631 100644 (file)
@@ -43,6 +43,7 @@ parseCommandLine(int argc, char *argv[])
                {"new-datadir", required_argument, NULL, 'D'},
                {"old-bindir", required_argument, NULL, 'b'},
                {"new-bindir", required_argument, NULL, 'B'},
+               {"no-sync", no_argument, NULL, 'N'},
                {"old-options", required_argument, NULL, 'o'},
                {"new-options", required_argument, NULL, 'O'},
                {"old-port", required_argument, NULL, 'p'},
@@ -66,6 +67,7 @@ parseCommandLine(int argc, char *argv[])
        char      **filename;
        time_t          run_time = time(NULL);
 
+       user_opts.do_sync = true;
        user_opts.transfer_mode = TRANSFER_MODE_COPY;
 
        os_info.progname = get_progname(argv[0]);
@@ -101,7 +103,7 @@ parseCommandLine(int argc, char *argv[])
        if (os_user_effective_id == 0)
                pg_fatal("%s: cannot be run as root\n", os_info.progname);
 
-       while ((option = getopt_long(argc, argv, "d:D:b:B:cj:ko:O:p:P:rs:U:v",
+       while ((option = getopt_long(argc, argv, "d:D:b:B:cj:kNo:O:p:P:rs:U:v",
                                                                 long_options, &optindex)) != -1)
        {
                switch (option)
@@ -134,6 +136,10 @@ parseCommandLine(int argc, char *argv[])
                                user_opts.transfer_mode = TRANSFER_MODE_LINK;
                                break;
 
+                       case 'N':
+                               user_opts.do_sync = false;
+                               break;
+
                        case 'o':
                                /* append option? */
                                if (!old_cluster.pgopts)
@@ -286,6 +292,7 @@ usage(void)
        printf(_("  -D, --new-datadir=DATADIR     new cluster data directory\n"));
        printf(_("  -j, --jobs=NUM                number of simultaneous processes or threads to use\n"));
        printf(_("  -k, --link                    link instead of copying files to new cluster\n"));
+       printf(_("  -N, --no-sync                 do not wait for changes to be written safely to disk\n"));
        printf(_("  -o, --old-options=OPTIONS     old cluster options to pass to the server\n"));
        printf(_("  -O, --new-options=OPTIONS     new cluster options to pass to the server\n"));
        printf(_("  -p, --old-port=PORT           old cluster port number (default %d)\n"), old_cluster.port);
index 3628bd74a7b276d82619ff06f34b763ef12a953f..f85cb2e2620051695e2beb3e36d76b26a3405ab4 100644 (file)
@@ -169,11 +169,14 @@ main(int argc, char **argv)
                          new_cluster.pgdata);
        check_ok();
 
-       prep_status("Sync data directory to disk");
-       exec_prog(UTILITY_LOG_FILE, NULL, true, true,
-                         "\"%s/initdb\" --sync-only \"%s\"", new_cluster.bindir,
-                         new_cluster.pgdata);
-       check_ok();
+       if (user_opts.do_sync)
+       {
+               prep_status("Sync data directory to disk");
+               exec_prog(UTILITY_LOG_FILE, NULL, true, true,
+                                 "\"%s/initdb\" --sync-only \"%s\"", new_cluster.bindir,
+                                 new_cluster.pgdata);
+               check_ok();
+       }
 
        create_script_for_old_cluster_deletion(&deletion_script_file_name);
 
index 235a7700262d3a50476199d1ba6c1cf82c21b758..22169f100212d331179a450cb0e34eb847d41466 100644 (file)
@@ -279,6 +279,7 @@ typedef struct
 {
        bool            check;                  /* true -> ask user for permission to make
                                                                 * changes */
+       bool            do_sync;                /* flush changes to disk */
        transferMode transfer_mode; /* copy files or link them? */
        int                     jobs;                   /* number of processes/threads to use */
        char       *socketdir;          /* directory to use for Unix sockets */
index 32d186d8974ce4ac4f9d0d72da23a40af184cb84..d6a318367ab699cb974a0dc0992902122c704fc1 100644 (file)
@@ -233,7 +233,7 @@ PGDATA="$BASE_PGDATA"
 
 standard_initdb 'initdb'
 
-pg_upgrade $PG_UPGRADE_OPTS -d "${PGDATA}.old" -D "$PGDATA" -b "$oldbindir" -p "$PGPORT" -P "$PGPORT"
+pg_upgrade $PG_UPGRADE_OPTS --no-sync -d "${PGDATA}.old" -D "$PGDATA" -b "$oldbindir" -p "$PGPORT" -P "$PGPORT"
 
 # make sure all directories and files have group permissions, on Unix hosts
 # Windows hosts don't support Unix-y permissions.
index dc5b2df7d722aa48901e8911bc79de2b6768cf55..29086cab5163c33b0a88ff3e02fa69ff1d0c00ed 100644 (file)
@@ -648,7 +648,9 @@ sub upgradecheck
        print "\nSetting up new cluster\n\n";
        standard_initdb() or exit 1;
        print "\nRunning pg_upgrade\n\n";
-       @args = ('pg_upgrade', '-d', "$data.old", '-D', $data, '-b', $bindir);
+       @args = (
+               'pg_upgrade', '-d', "$data.old", '-D', $data, '-b', $bindir,
+               '--no-sync');
        system(@args) == 0 or exit 1;
        print "\nStarting new cluster\n\n";
        @args = ('pg_ctl', '-l', "$logdir/postmaster2.log", 'start');