Revert "Improve handling of parameter differences in physical replication"
authorPeter Eisentraut <peter@eisentraut.org>
Sat, 4 Apr 2020 07:08:12 +0000 (09:08 +0200)
committerPeter Eisentraut <peter@eisentraut.org>
Sat, 4 Apr 2020 07:08:12 +0000 (09:08 +0200)
This reverts commit 246f136e76ecd26844840f2b2057e2c87ec9868d.

That patch wasn't quite complete enough.

Discussion: https://www.postgresql.org/message-id/flat/E1jIpJu-0007Ql-CL%40gemulon.postgresql.org

doc/src/sgml/high-availability.sgml
src/backend/access/transam/twophase.c
src/backend/access/transam/xlog.c
src/backend/storage/ipc/procarray.c
src/backend/storage/lmgr/lock.c
src/include/access/xlog.h

index b5d32bb720a32a3b7afc59ae26002a5a84b1a1e1..bb5d9962ed337d274b78a1a2d09ec37751654b2c 100644 (file)
@@ -2148,14 +2148,18 @@ LOG:  database system is ready to accept read only connections
    </para>
 
    <para>
-    The settings of some parameters determine the size of shared memory for
-    tracking transaction IDs, locks, and prepared transactions.  These shared
-    memory structures should be no smaller on a standby than on the primary.
-    Otherwise, it could happen that the standby runs out of shared memory
-    during recovery.  For example, if the primary uses a prepared transaction
-    but the standby did not allocate any shared memory for tracking prepared
-    transactions, then recovery will abort and cannot continue until the
-    standby's configuration is changed.  The parameters affected are:
+    The setting of some parameters on the standby will need reconfiguration
+    if they have been changed on the primary. For these parameters,
+    the value on the standby must
+    be equal to or greater than the value on the primary.
+    Therefore, if you want to increase these values, you should do so on all
+    standby servers first, before applying the changes to the primary server.
+    Conversely, if you want to decrease these values, you should do so on the
+    primary server first, before applying the changes to all standby servers.
+    If these parameters
+    are not set high enough then the standby will refuse to start.
+    Higher values can then be supplied and the server
+    restarted to begin recovery again.  These parameters are:
 
       <itemizedlist>
        <listitem>
@@ -2184,34 +2188,6 @@ LOG:  database system is ready to accept read only connections
         </para>
        </listitem>
       </itemizedlist>
-
-    The easiest way to ensure this does not become a problem is to have these
-    parameters set on the standbys to values equal to or greater than on the
-    primary.  Therefore, if you want to increase these values, you should do
-    so on all standby servers first, before applying the changes to the
-    primary server.  Conversely, if you want to decrease these values, you
-    should do so on the primary server first, before applying the changes to
-    all standby servers.  The WAL tracks changes to these parameters on the
-    primary, and if a standby processes WAL that indicates that the current
-    value on the primary is higher than its own value, it will log a warning, for example:
-<screen>
-WARNING:  insufficient setting for parameter max_connections
-DETAIL:  max_connections = 80 is a lower setting than on the master server (where its value was 100).
-HINT:  Change parameters and restart the server, or there may be resource exhaustion errors sooner or later.
-</screen>
-    Recovery will continue but could abort at any time thereafter.  (It could
-    also never end up failing if the activity on the primary does not actually
-    require the full extent of the allocated shared memory resources.)  If
-    recovery reaches a point where it cannot continue due to lack of shared
-    memory, recovery will pause and another warning will be logged, for example:
-<screen>
-WARNING:  recovery paused because of insufficient parameter settings
-DETAIL:  See earlier in the log about which settings are insufficient.
-HINT:  Recovery cannot continue unless the configuration is changed and the server restarted.
-</screen>
-    This warning will repeated once a minute.  At that point, the settings on
-    the standby need to be updated and the instance restarted before recovery
-    can continue.
    </para>
 
    <para>
index ce35f15f347776124eec8a8638984afd9c63d0ab..5adf956f4133e98d836ac295d5e51748f644df05 100644 (file)
@@ -2360,14 +2360,11 @@ PrepareRedoAdd(char *buf, XLogRecPtr start_lsn,
 
        /* Get a free gxact from the freelist */
        if (TwoPhaseState->freeGXacts == NULL)
-       {
-               StandbyParamErrorPauseRecovery();
                ereport(ERROR,
                                (errcode(ERRCODE_OUT_OF_MEMORY),
                                 errmsg("maximum number of prepared transactions reached"),
                                 errhint("Increase max_prepared_transactions (currently %d).",
                                                 max_prepared_xacts)));
-       }
        gxact = TwoPhaseState->freeGXacts;
        TwoPhaseState->freeGXacts = gxact->next;
 
index 7b70bfef1aec027a9e7164812fbb0a4aefee3101..abf954ba392597a27ec6d12e7638026b55e395e4 100644 (file)
@@ -266,8 +266,6 @@ bool                InArchiveRecovery = false;
 static bool standby_signal_file_found = false;
 static bool recovery_signal_file_found = false;
 
-static bool need_restart_for_parameter_values = false;
-
 /* Was the last xlog file restored from archive, or local? */
 static bool restoredFromArchive = false;
 
@@ -6020,54 +6018,6 @@ SetRecoveryPause(bool recoveryPause)
        SpinLockRelease(&XLogCtl->info_lck);
 }
 
-/*
- * If in hot standby, pause recovery because of a parameter conflict.
- *
- * Similar to recoveryPausesHere() but with a different messaging.  The user
- * is expected to make the parameter change and restart the server.  If they
- * just unpause recovery, they will then run into whatever error is after this
- * function call for the non-hot-standby case.
- *
- * We intentionally do not give advice about specific parameters or values
- * here because it might be misleading.  For example, if we run out of lock
- * space, then in the single-server case we would recommend raising
- * max_locks_per_transaction, but in recovery it could equally be the case
- * that max_connections is out of sync with the primary.  If we get here, we
- * have already logged any parameter discrepancies in
- * RecoveryRequiresIntParameter(), so users can go back to that and get
- * concrete and accurate information.
- */
-void
-StandbyParamErrorPauseRecovery(void)
-{
-       TimestampTz last_warning = 0;
-
-       if (!AmStartupProcess() || !need_restart_for_parameter_values)
-               return;
-
-       SetRecoveryPause(true);
-
-       do
-       {
-               TimestampTz now = GetCurrentTimestamp();
-
-               if (TimestampDifferenceExceeds(last_warning, now, 60000))
-               {
-                       ereport(WARNING,
-                                       (errmsg("recovery paused because of insufficient parameter settings"),
-                                        errdetail("See earlier in the log about which settings are insufficient."),
-                                        errhint("Recovery cannot continue unless the configuration is changed and the server restarted.")));
-                       last_warning = now;
-               }
-
-               pgstat_report_wait_start(WAIT_EVENT_RECOVERY_PAUSE);
-               pg_usleep(1000000L);    /* 1000 ms */
-               pgstat_report_wait_end();
-               HandleStartupProcInterrupts();
-       }
-       while (RecoveryIsPaused());
-}
-
 /*
  * When recovery_min_apply_delay is set, we wait long enough to make sure
  * certain record types are applied at least that interval behind the master.
@@ -6247,20 +6197,16 @@ GetXLogReceiptTime(TimestampTz *rtime, bool *fromStream)
  * Note that text field supplied is a parameter name and does not require
  * translation
  */
-static void
-RecoveryRequiresIntParameter(const char *param_name, int currValue, int minValue)
-{
-       if (currValue < minValue)
-       {
-               ereport(WARNING,
-                               (errcode(ERRCODE_INVALID_PARAMETER_VALUE),
-                                errmsg("insufficient setting for parameter %s", param_name),
-                                errdetail("%s = %d is a lower setting than on the master server (where its value was %d).",
-                                                  param_name, currValue, minValue),
-                                errhint("Change parameters and restart the server, or there may be resource exhaustion errors sooner or later.")));
-               need_restart_for_parameter_values = true;
-       }
-}
+#define RecoveryRequiresIntParameter(param_name, currValue, minValue) \
+do { \
+       if ((currValue) < (minValue)) \
+               ereport(ERROR, \
+                               (errcode(ERRCODE_INVALID_PARAMETER_VALUE), \
+                                errmsg("hot standby is not possible because %s = %d is a lower setting than on the master server (its value was %d)", \
+                                               param_name, \
+                                               currValue, \
+                                               minValue))); \
+} while(0)
 
 /*
  * Check to see if required parameters are set high enough on this server
index 738c0484d33c3c1c7d499dad58ef7a9bfa9cbc78..281fe671bdf612a8d45cde959a774317b949a37b 100644 (file)
@@ -3654,14 +3654,7 @@ KnownAssignedXidsAdd(TransactionId from_xid, TransactionId to_xid,
                 * If it still won't fit then we're out of memory
                 */
                if (head + nxids > pArray->maxKnownAssignedXids)
-               {
-                       StandbyParamErrorPauseRecovery();
-                       ereport(ERROR,
-                                       (errcode(ERRCODE_OUT_OF_MEMORY),
-                                        errmsg("out of shared memory"),
-                                        errdetail("There are no more KnownAssignedXids slots."),
-                                        errhint("You might need to increase max_connections.")));
-               }
+                       elog(ERROR, "too many KnownAssignedXids");
        }
 
        /* Now we can insert the xids into the space starting at head */
index c8def1674f411d656e46c8386ba20a4c0de9edbd..3013ef63d051b45ab1cc39564980fac911ce3e9c 100644 (file)
@@ -965,13 +965,10 @@ LockAcquireExtended(const LOCKTAG *locktag,
                        if (locallockp)
                                *locallockp = NULL;
                        if (reportMemoryError)
-                       {
-                               StandbyParamErrorPauseRecovery();
                                ereport(ERROR,
                                                (errcode(ERRCODE_OUT_OF_MEMORY),
                                                 errmsg("out of shared memory"),
                                                 errhint("You might need to increase max_locks_per_transaction.")));
-                       }
                        else
                                return LOCKACQUIRE_NOT_AVAIL;
                }
@@ -1006,13 +1003,10 @@ LockAcquireExtended(const LOCKTAG *locktag,
                if (locallockp)
                        *locallockp = NULL;
                if (reportMemoryError)
-               {
-                       StandbyParamErrorPauseRecovery();
                        ereport(ERROR,
                                        (errcode(ERRCODE_OUT_OF_MEMORY),
                                         errmsg("out of shared memory"),
                                         errhint("You might need to increase max_locks_per_transaction.")));
-               }
                else
                        return LOCKACQUIRE_NOT_AVAIL;
        }
@@ -2834,7 +2828,6 @@ FastPathGetRelationLockEntry(LOCALLOCK *locallock)
                {
                        LWLockRelease(partitionLock);
                        LWLockRelease(&MyProc->backendLock);
-                       StandbyParamErrorPauseRecovery();
                        ereport(ERROR,
                                        (errcode(ERRCODE_OUT_OF_MEMORY),
                                         errmsg("out of shared memory"),
@@ -4165,7 +4158,6 @@ lock_twophase_recover(TransactionId xid, uint16 info,
        if (!lock)
        {
                LWLockRelease(partitionLock);
-               StandbyParamErrorPauseRecovery();
                ereport(ERROR,
                                (errcode(ERRCODE_OUT_OF_MEMORY),
                                 errmsg("out of shared memory"),
@@ -4231,7 +4223,6 @@ lock_twophase_recover(TransactionId xid, uint16 info,
                                elog(PANIC, "lock table corrupted");
                }
                LWLockRelease(partitionLock);
-               StandbyParamErrorPauseRecovery();
                ereport(ERROR,
                                (errcode(ERRCODE_OUT_OF_MEMORY),
                                 errmsg("out of shared memory"),
@@ -4524,7 +4515,6 @@ VirtualXactLock(VirtualTransactionId vxid, bool wait)
                {
                        LWLockRelease(partitionLock);
                        LWLockRelease(&proc->backendLock);
-                       StandbyParamErrorPauseRecovery();
                        ereport(ERROR,
                                        (errcode(ERRCODE_OUT_OF_MEMORY),
                                         errmsg("out of shared memory"),
index b91e724b2d446243d5cb189b7503e7131f786205..7412caa5f228bb54eb642069d0775c532f52338a 100644 (file)
@@ -288,7 +288,6 @@ extern XLogRecPtr GetXLogInsertRecPtr(void);
 extern XLogRecPtr GetXLogWriteRecPtr(void);
 extern bool RecoveryIsPaused(void);
 extern void SetRecoveryPause(bool recoveryPause);
-extern void StandbyParamErrorPauseRecovery(void);
 extern TimestampTz GetLatestXTime(void);
 extern TimestampTz GetCurrentChunkReplayStartTime(void);