Re: [HACKERS] Upgrading postmaster's log messages about bind/listen errors - Mailing list pgsql-hackers

From Tom Lane
Subject Re: [HACKERS] Upgrading postmaster's log messages about bind/listen errors
Date
Msg-id 17211.1489189214@sss.pgh.pa.us
Whole thread Raw
In response to Re: [HACKERS] Upgrading postmaster's log messages about bind/listen errors  (Tom Lane <tgl@sss.pgh.pa.us>)
Responses Re: [HACKERS] Upgrading postmaster's log messages about bind/listen errors  (Tom Lane <tgl@sss.pgh.pa.us>)
List pgsql-hackers
I wrote:
> I think that what would actually be of some use nowadays is a LOG-level
> message emitted if the wraparound *isn't* activated immediately at start.
> But otherwise, we should follow the rule that silence is golden.

Concretely, how about the attached?  It preserves the original
"protections are now enabled" message at LOG level, but emits it only
when oldestOffsetKnown becomes true *after* startup.  Meanwhile, if
oldestOffsetKnown is still not true at the conclusion of TrimMultiXact,
then it emits a new LOG message about "protections are not active".
In this way we have LOG messages but they're only emitted in "interesting"
cases.

I dropped the IsUnderPostmaster test because I see no good reason not
to warn in standalone backends as well.

I think this might actually be a reasonable candidate to back-patch,
because a deficiency of the existing code is that it fails to warn
you when something's wrong.  But in any case I'd like to put it in HEAD.

            regards, tom lane

diff --git a/src/backend/access/transam/multixact.c b/src/backend/access/transam/multixact.c
index 59d1252..3f66cdb 100644
*** a/src/backend/access/transam/multixact.c
--- b/src/backend/access/transam/multixact.c
*************** static void ExtendMultiXactOffset(MultiX
*** 363,369 ****
  static void ExtendMultiXactMember(MultiXactOffset offset, int nmembers);
  static bool MultiXactOffsetWouldWrap(MultiXactOffset boundary,
                           MultiXactOffset start, uint32 distance);
! static bool SetOffsetVacuumLimit(void);
  static bool find_multixact_start(MultiXactId multi, MultiXactOffset *result);
  static void WriteMZeroPageXlogRec(int pageno, uint8 info);
  static void WriteMTruncateXlogRec(Oid oldestMultiDB,
--- 363,369 ----
  static void ExtendMultiXactMember(MultiXactOffset offset, int nmembers);
  static bool MultiXactOffsetWouldWrap(MultiXactOffset boundary,
                           MultiXactOffset start, uint32 distance);
! static bool SetOffsetVacuumLimit(bool is_startup);
  static bool find_multixact_start(MultiXactId multi, MultiXactOffset *result);
  static void WriteMZeroPageXlogRec(int pageno, uint8 info);
  static void WriteMTruncateXlogRec(Oid oldestMultiDB,
*************** TrimMultiXact(void)
*** 2095,2101 ****
      LWLockRelease(MultiXactGenLock);

      /* Now compute how far away the next members wraparound is. */
!     SetMultiXactIdLimit(oldestMXact, oldestMXactDB);
  }

  /*
--- 2095,2101 ----
      LWLockRelease(MultiXactGenLock);

      /* Now compute how far away the next members wraparound is. */
!     SetMultiXactIdLimit(oldestMXact, oldestMXactDB, true);
  }

  /*
*************** MultiXactSetNextMXact(MultiXactId nextMu
*** 2186,2194 ****
   * Determine the last safe MultiXactId to allocate given the currently oldest
   * datminmxid (ie, the oldest MultiXactId that might exist in any database
   * of our cluster), and the OID of the (or a) database with that value.
   */
  void
! SetMultiXactIdLimit(MultiXactId oldest_datminmxid, Oid oldest_datoid)
  {
      MultiXactId multiVacLimit;
      MultiXactId multiWarnLimit;
--- 2186,2198 ----
   * Determine the last safe MultiXactId to allocate given the currently oldest
   * datminmxid (ie, the oldest MultiXactId that might exist in any database
   * of our cluster), and the OID of the (or a) database with that value.
+  *
+  * is_startup is true when we are just starting the cluster, false when we
+  * are updating state in a running cluster.  This only affects log messages.
   */
  void
! SetMultiXactIdLimit(MultiXactId oldest_datminmxid, Oid oldest_datoid,
!                     bool is_startup)
  {
      MultiXactId multiVacLimit;
      MultiXactId multiWarnLimit;
*************** SetMultiXactIdLimit(MultiXactId oldest_d
*** 2277,2283 ****
      Assert(!InRecovery);

      /* Set limits for offset vacuum. */
!     needs_offset_vacuum = SetOffsetVacuumLimit();

      /*
       * If past the autovacuum force point, immediately signal an autovac
--- 2281,2287 ----
      Assert(!InRecovery);

      /* Set limits for offset vacuum. */
!     needs_offset_vacuum = SetOffsetVacuumLimit(is_startup);

      /*
       * If past the autovacuum force point, immediately signal an autovac
*************** MultiXactAdvanceOldest(MultiXactId oldes
*** 2370,2376 ****
      Assert(InRecovery);

      if (MultiXactIdPrecedes(MultiXactState->oldestMultiXactId, oldestMulti))
!         SetMultiXactIdLimit(oldestMulti, oldestMultiDB);
  }

  /*
--- 2374,2380 ----
      Assert(InRecovery);

      if (MultiXactIdPrecedes(MultiXactState->oldestMultiXactId, oldestMulti))
!         SetMultiXactIdLimit(oldestMulti, oldestMultiDB, false);
  }

  /*
*************** GetOldestMultiXactId(void)
*** 2537,2543 ****
   * otherwise.
   */
  static bool
! SetOffsetVacuumLimit(void)
  {
      MultiXactId oldestMultiXactId;
      MultiXactId nextMXact;
--- 2541,2547 ----
   * otherwise.
   */
  static bool
! SetOffsetVacuumLimit(bool is_startup)
  {
      MultiXactId oldestMultiXactId;
      MultiXactId nextMXact;
*************** SetOffsetVacuumLimit(void)
*** 2619,2627 ****
          /* always leave one segment before the wraparound point */
          offsetStopLimit -= (MULTIXACT_MEMBERS_PER_PAGE * SLRU_PAGES_PER_SEGMENT);

!         if (!prevOldestOffsetKnown && IsUnderPostmaster)
              ereport(LOG,
                      (errmsg("MultiXact member wraparound protections are now enabled")));
          ereport(DEBUG1,
          (errmsg("MultiXact member stop limit is now %u based on MultiXact %u",
                  offsetStopLimit, oldestMultiXactId)));
--- 2623,2632 ----
          /* always leave one segment before the wraparound point */
          offsetStopLimit -= (MULTIXACT_MEMBERS_PER_PAGE * SLRU_PAGES_PER_SEGMENT);

!         if (!prevOldestOffsetKnown && !is_startup)
              ereport(LOG,
                      (errmsg("MultiXact member wraparound protections are now enabled")));
+
          ereport(DEBUG1,
          (errmsg("MultiXact member stop limit is now %u based on MultiXact %u",
                  offsetStopLimit, oldestMultiXactId)));
*************** SetOffsetVacuumLimit(void)
*** 2639,2644 ****
--- 2644,2654 ----
          offsetStopLimit = prevOffsetStopLimit;
      }

+     /* Warn at startup if wraparound protection isn't active */
+     if (is_startup && !oldestOffsetKnown)
+         ereport(LOG,
+          (errmsg("MultiXact member wraparound protections are not active")));
+
      /* Install the computed values */
      LWLockAcquire(MultiXactGenLock, LW_EXCLUSIVE);
      MultiXactState->oldestOffset = oldestOffset;
*************** multixact_redo(XLogReaderState *record)
*** 3312,3318 ****
           * Advance the horizon values, so they're current at the end of
           * recovery.
           */
!         SetMultiXactIdLimit(xlrec.endTruncOff, xlrec.oldestMultiDB);

          PerformMembersTruncation(xlrec.startTruncMemb, xlrec.endTruncMemb);

--- 3322,3328 ----
           * Advance the horizon values, so they're current at the end of
           * recovery.
           */
!         SetMultiXactIdLimit(xlrec.endTruncOff, xlrec.oldestMultiDB, false);

          PerformMembersTruncation(xlrec.startTruncMemb, xlrec.endTruncMemb);

diff --git a/src/backend/access/transam/xlog.c b/src/backend/access/transam/xlog.c
index 744360c..299ce30 100644
*** a/src/backend/access/transam/xlog.c
--- b/src/backend/access/transam/xlog.c
*************** BootStrapXLOG(void)
*** 4995,5001 ****
      ShmemVariableCache->oidCount = 0;
      MultiXactSetNextMXact(checkPoint.nextMulti, checkPoint.nextMultiOffset);
      SetTransactionIdLimit(checkPoint.oldestXid, checkPoint.oldestXidDB);
!     SetMultiXactIdLimit(checkPoint.oldestMulti, checkPoint.oldestMultiDB);
      SetCommitTsLimit(InvalidTransactionId, InvalidTransactionId);

      /* Set up the XLOG page header */
--- 4995,5001 ----
      ShmemVariableCache->oidCount = 0;
      MultiXactSetNextMXact(checkPoint.nextMulti, checkPoint.nextMultiOffset);
      SetTransactionIdLimit(checkPoint.oldestXid, checkPoint.oldestXidDB);
!     SetMultiXactIdLimit(checkPoint.oldestMulti, checkPoint.oldestMultiDB, true);
      SetCommitTsLimit(InvalidTransactionId, InvalidTransactionId);

      /* Set up the XLOG page header */
*************** StartupXLOG(void)
*** 6597,6603 ****
      ShmemVariableCache->oidCount = 0;
      MultiXactSetNextMXact(checkPoint.nextMulti, checkPoint.nextMultiOffset);
      SetTransactionIdLimit(checkPoint.oldestXid, checkPoint.oldestXidDB);
!     SetMultiXactIdLimit(checkPoint.oldestMulti, checkPoint.oldestMultiDB);
      SetCommitTsLimit(checkPoint.oldestCommitTsXid,
                       checkPoint.newestCommitTsXid);
      XLogCtl->ckptXidEpoch = checkPoint.nextXidEpoch;
--- 6597,6603 ----
      ShmemVariableCache->oidCount = 0;
      MultiXactSetNextMXact(checkPoint.nextMulti, checkPoint.nextMultiOffset);
      SetTransactionIdLimit(checkPoint.oldestXid, checkPoint.oldestXidDB);
!     SetMultiXactIdLimit(checkPoint.oldestMulti, checkPoint.oldestMultiDB, true);
      SetCommitTsLimit(checkPoint.oldestCommitTsXid,
                       checkPoint.newestCommitTsXid);
      XLogCtl->ckptXidEpoch = checkPoint.nextXidEpoch;
diff --git a/src/backend/commands/vacuum.c b/src/backend/commands/vacuum.c
index 3a9b965..3b3dfee 100644
*** a/src/backend/commands/vacuum.c
--- b/src/backend/commands/vacuum.c
*************** vac_truncate_clog(TransactionId frozenXI
*** 1205,1211 ****
       * signalling twice?
       */
      SetTransactionIdLimit(frozenXID, oldestxid_datoid);
!     SetMultiXactIdLimit(minMulti, minmulti_datoid);
  }


--- 1205,1211 ----
       * signalling twice?
       */
      SetTransactionIdLimit(frozenXID, oldestxid_datoid);
!     SetMultiXactIdLimit(minMulti, minmulti_datoid, false);
  }


diff --git a/src/include/access/multixact.h b/src/include/access/multixact.h
index 1d01988..85997a4 100644
*** a/src/include/access/multixact.h
--- b/src/include/access/multixact.h
*************** extern void StartupMultiXact(void);
*** 127,133 ****
  extern void TrimMultiXact(void);
  extern void ShutdownMultiXact(void);
  extern void SetMultiXactIdLimit(MultiXactId oldest_datminmxid,
!                     Oid oldest_datoid);
  extern void MultiXactGetCheckptMulti(bool is_shutdown,
                           MultiXactId *nextMulti,
                           MultiXactOffset *nextMultiOffset,
--- 127,134 ----
  extern void TrimMultiXact(void);
  extern void ShutdownMultiXact(void);
  extern void SetMultiXactIdLimit(MultiXactId oldest_datminmxid,
!                     Oid oldest_datoid,
!                     bool is_startup);
  extern void MultiXactGetCheckptMulti(bool is_shutdown,
                           MultiXactId *nextMulti,
                           MultiXactOffset *nextMultiOffset,

-- 
Sent via pgsql-hackers mailing list (pgsql-hackers@postgresql.org)
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers

pgsql-hackers by date:

Previous
From: Corey Huinker
Date:
Subject: Re: [HACKERS] asynchronous execution
Next
From: Peter Eisentraut
Date:
Subject: Re: [HACKERS] Need a builtin way to run all tests faster manner