v4-0002-Introduce-shared_memory_size-GUC.patch

application/octet-stream

Filename: v4-0002-Introduce-shared_memory_size-GUC.patch
Type: application/octet-stream
Part: 2
Message: Re: Estimating HugePages Requirements?

Patch

Format: format-patch
Series: patch v4-0002
Subject: Introduce shared_memory_size GUC.
File+
doc/src/sgml/config.sgml 14 0
doc/src/sgml/runtime.sgml 10 12
src/backend/postmaster/postmaster.c 33 22
src/backend/storage/ipc/ipci.c 24 0
src/backend/utils/misc/guc.c 13 0
src/include/storage/ipc.h 1 0
From bda20ec9080b739ee6698b2b5f34d04fbe1b86f6 Mon Sep 17 00:00:00 2001
From: Nathan Bossart <bossartn@amazon.com>
Date: Wed, 1 Sep 2021 18:22:11 +0000
Subject: [PATCH v4 2/3] Introduce shared_memory_size GUC.

This runtime-computed GUC shows the size of the server's main
shared memory area.  It can also be viewed with 'postgres -C',
which is useful for calculating the number of huge pages required
prior to startup.
---
 doc/src/sgml/config.sgml            | 14 ++++++++++
 doc/src/sgml/runtime.sgml           | 22 +++++++--------
 src/backend/postmaster/postmaster.c | 55 ++++++++++++++++++++++---------------
 src/backend/storage/ipc/ipci.c      | 24 ++++++++++++++++
 src/backend/utils/misc/guc.c        | 13 +++++++++
 src/include/storage/ipc.h           |  1 +
 6 files changed, 95 insertions(+), 34 deletions(-)

diff --git a/doc/src/sgml/config.sgml b/doc/src/sgml/config.sgml
index 2c31c35a6b..ef0e2a7746 100644
--- a/doc/src/sgml/config.sgml
+++ b/doc/src/sgml/config.sgml
@@ -10275,6 +10275,20 @@ dynamic_library_path = 'C:\tools\postgresql;H:\my_project\lib;$libdir'
       </listitem>
      </varlistentry>
 
+     <varlistentry id="guc-shared-memory-size" xreflabel="shared_memory_size">
+      <term><varname>shared_memory_size</varname> (<type>integer</type>)
+      <indexterm>
+       <primary><varname>shared_memory_size</varname> configuration parameter</primary>
+      </indexterm>
+      </term>
+      <listitem>
+       <para>
+        Reports the size of the main shared memory area, rounded up to the
+        nearest megabyte.
+       </para>
+      </listitem>
+     </varlistentry>
+
      <varlistentry id="guc-ssl-library" xreflabel="ssl_library">
       <term><varname>ssl_library</varname> (<type>string</type>)
       <indexterm>
diff --git a/doc/src/sgml/runtime.sgml b/doc/src/sgml/runtime.sgml
index f1cbc1d9e9..2144c0abad 100644
--- a/doc/src/sgml/runtime.sgml
+++ b/doc/src/sgml/runtime.sgml
@@ -1442,17 +1442,15 @@ export PG_OOM_ADJUST_VALUE=0
     with <varname>CONFIG_HUGETLBFS=y</varname> and
     <varname>CONFIG_HUGETLB_PAGE=y</varname>. You will also have to configure
     the operating system to provide enough huge pages of the desired size.
-    To estimate the number of huge pages needed, start
-    <productname>PostgreSQL</productname> without huge pages enabled and check
-    the postmaster's anonymous shared memory segment size, as well as the
-    system's default and supported huge page sizes, using the
-    <filename>/proc</filename> and <filename>/sys</filename> file systems.
-    This might look like:
+    To estimate the number of huge pages needed, use the
+    <command>postgres</command> command to see the value of
+    <xref linkend="guc-shared-memory-size"/>, and use the
+    <filename>/proc</filename> and <filename>/sys</filename> file systems
+    to find the system's default and supported huge page sizes.  This might
+    look like:
 <programlisting>
-$ <userinput>head -1 $PGDATA/postmaster.pid</userinput>
-4170
-$ <userinput>pmap 4170 | awk '/rw-s/ &amp;&amp; /zero/ {print $2}'</userinput>
-6490428K
+$ <userinput>postgres -D $PGDATA -C shared_memory_size</userinput>
+6339
 $ <userinput>grep ^Hugepagesize /proc/meminfo</userinput>
 Hugepagesize:       2048 kB
 $ <userinput>ls /sys/kernel/mm/hugepages</userinput>
@@ -1463,8 +1461,8 @@ hugepages-1048576kB  hugepages-2048kB
      either 2MB or 1GB with <xref linkend="guc-huge-page-size"/>.
 
      Assuming <literal>2MB</literal> huge pages,
-     <literal>6490428</literal> / <literal>2048</literal> gives approximately
-     <literal>3169.154</literal>, so in this example we need at
+     <literal>6339</literal> / <literal>2</literal> gives
+     <literal>3169.5</literal>, so in this example we need at
      least <literal>3170</literal> huge pages.  A larger setting would be
      appropriate if other programs on the machine also need huge pages.
      We can set this with:
diff --git a/src/backend/postmaster/postmaster.c b/src/backend/postmaster/postmaster.c
index 9c2c98614a..c32c21d632 100644
--- a/src/backend/postmaster/postmaster.c
+++ b/src/backend/postmaster/postmaster.c
@@ -893,6 +893,39 @@ PostmasterMain(int argc, char *argv[])
 	if (!SelectConfigFiles(userDoption, progname))
 		ExitPostmaster(2);
 
+	/* Verify that DataDir looks reasonable */
+	checkDataDir();
+
+	/* Check that pg_control exists */
+	checkControlFile();
+
+	/* And switch working directory into it */
+	ChangeToDataDir();
+
+	/*
+	 * Register the apply launcher.  Since it registers a background worker,
+	 * it needs to be called before InitializeMaxBackends(), and it's probably
+	 * a good idea to call it before any modules had chance to take the
+	 * background worker slots.
+	 */
+	ApplyLauncherRegister();
+
+	/*
+	 * Process any libraries that should be preloaded at postmaster start.
+	 * Thie happens before running -C, so as it is possible to get an
+	 * estimation of the total shared memory size allocated to this system,
+	 * accounting for the portion from loaded libraries.
+	 */
+	process_shared_preload_libraries();
+
+	/*
+	 * Determine the value of any runtime-computed GUCs that depend on the
+	 * amount of shared memory required.  It is important to do this after
+	 * preloaded libraries have had a chance to request additional shared
+	 * memory.
+	 */
+	InitializeShmemGUCs();
+
 	if (output_config_variable != NULL)
 	{
 		/*
@@ -907,15 +940,6 @@ PostmasterMain(int argc, char *argv[])
 		ExitPostmaster(0);
 	}
 
-	/* Verify that DataDir looks reasonable */
-	checkDataDir();
-
-	/* Check that pg_control exists */
-	checkControlFile();
-
-	/* And switch working directory into it */
-	ChangeToDataDir();
-
 	/*
 	 * Check for invalid combinations of GUC settings.
 	 */
@@ -996,19 +1020,6 @@ PostmasterMain(int argc, char *argv[])
 	 */
 	LocalProcessControlFile(false);
 
-	/*
-	 * Register the apply launcher.  Since it registers a background worker,
-	 * it needs to be called before InitializeMaxBackends(), and it's probably
-	 * a good idea to call it before any modules had chance to take the
-	 * background worker slots.
-	 */
-	ApplyLauncherRegister();
-
-	/*
-	 * process any libraries that should be preloaded at postmaster start
-	 */
-	process_shared_preload_libraries();
-
 	/*
 	 * Initialize SSL library, if specified.
 	 */
diff --git a/src/backend/storage/ipc/ipci.c b/src/backend/storage/ipc/ipci.c
index b225b1ee70..f5736703a8 100644
--- a/src/backend/storage/ipc/ipci.c
+++ b/src/backend/storage/ipc/ipci.c
@@ -313,3 +313,27 @@ CreateSharedMemoryAndSemaphores(void)
 	if (shmem_startup_hook)
 		shmem_startup_hook();
 }
+
+/*
+ * InitializeShmemGUCs
+ *
+ * This function initializes runtime-computed GUCs related to the amount of
+ * shared memory required for the current configuration.
+ */
+void
+InitializeShmemGUCs(void)
+{
+	char	buf[64];
+	Size	size_b;
+	Size	size_mb;
+
+	/*
+	 * Calculate the shared memory size and round up to the nearest
+	 * megabyte.
+	 */
+	size_b = CalculateShmemSize(NULL);
+	size_mb = add_size(size_b, (1024 * 1024) - 1) / (1024 * 1024);
+
+	sprintf(buf, "%lu MB", size_mb);
+	SetConfigOption("shared_memory_size", buf, PGC_INTERNAL, PGC_S_OVERRIDE);
+}
diff --git a/src/backend/utils/misc/guc.c b/src/backend/utils/misc/guc.c
index 467b0fd6fe..a11387c5ce 100644
--- a/src/backend/utils/misc/guc.c
+++ b/src/backend/utils/misc/guc.c
@@ -620,6 +620,8 @@ char	   *pgstat_temp_directory;
 
 char	   *application_name;
 
+int			shmem_size_mb;
+
 int			tcp_keepalives_idle;
 int			tcp_keepalives_interval;
 int			tcp_keepalives_count;
@@ -2337,6 +2339,17 @@ static struct config_int ConfigureNamesInt[] =
 		NULL, NULL, NULL
 	},
 
+	{
+		{"shared_memory_size", PGC_INTERNAL, RESOURCES_MEM,
+			gettext_noop("Shows the size of the server's main shared memory area (rounded up to the nearest MB)."),
+			NULL,
+			GUC_NOT_IN_SAMPLE | GUC_DISALLOW_IN_FILE | GUC_UNIT_MB
+		},
+		&shmem_size_mb,
+		0, 0, INT_MAX,
+		NULL, NULL, NULL
+	},
+
 	{
 		{"temp_buffers", PGC_USERSET, RESOURCES_MEM,
 			gettext_noop("Sets the maximum number of temporary buffers used by each session."),
diff --git a/src/include/storage/ipc.h b/src/include/storage/ipc.h
index 80e191d407..7a1ebc8559 100644
--- a/src/include/storage/ipc.h
+++ b/src/include/storage/ipc.h
@@ -79,5 +79,6 @@ extern PGDLLIMPORT shmem_startup_hook_type shmem_startup_hook;
 
 extern Size CalculateShmemSize(int *num_semaphores);
 extern void CreateSharedMemoryAndSemaphores(void);
+extern void InitializeShmemGUCs(void);
 
 #endif							/* IPC_H */
-- 
2.16.6