Introduce num_os_semaphores GUC.
authorNathan Bossart
Fri, 26 Jul 2024 20:28:55 +0000 (15:28 -0500)
committerNathan Bossart
Fri, 26 Jul 2024 20:28:55 +0000 (15:28 -0500)
The documentation for System V IPC parameters provides complicated
formulas to determine the appropriate values for SEMMNI and SEMMNS.
Furthermore, these formulas have often been wrong because folks
forget to update them (e.g., when adding a new auxiliary process).

This commit introduces a new runtime-computed GUC named
num_os_semaphores that reports the number of semaphores needed for
the configured number of allowed connections, worker processes,
etc.  This new GUC allows us to simplify the formulas in the
documentation, and it should help prevent future inaccuracies.
Like the other runtime-computed GUCs, users can view it with
"postgres -C" before starting the server, which is useful for
preconfiguring the necessary operating system resources.

Reviewed-by: Tom Lane, Sami Imseih, Andres Freund, Robert Haas
Discussion: https://postgr.es/m/20240517164452.GA1914161%40nathanxps13

doc/src/sgml/config.sgml
doc/src/sgml/runtime.sgml
src/backend/storage/ipc/ipci.c
src/backend/utils/misc/guc_tables.c

index 3dec0b7cfeb62e8defaac3f38274e8b77a6b4138..57cd7bb9727111143f169808bf6e990aad7aa0ca 100644 (file)
@@ -11145,6 +11145,24 @@ dynamic_library_path = 'C:\tools\postgresql;H:\my_project\lib;$libdir'
       
      
 
+     
+      num_os_semaphores (integer)
+      
+       num_os_semaphores configuration parameter
+      
+      
+      
+       
+        Reports the number of semaphores that are needed for the server based
+        on the configured number of allowed connections
+        (), allowed autovacuum worker
+        processes (), allowed WAL
+        sender processes (), allowed
+        background processes (), etc.
+       
+      
+     
+
      
       segment_size (integer)
       
index 2f7c61888691cefb9f99587232fe421826c1c2a1..2c4d5ef640d5708cb7e06b3a4137a85193dd00c5 100644 (file)
@@ -781,13 +781,13 @@ psql: error: connection to server on socket "/tmp/.s.PGSQL.5432" failed: No such
        
         SEMMNI
         Maximum number of semaphore identifiers (i.e., sets)
-        at least ceil((max_connections + autovacuum_max_workers + max_wal_senders + max_worker_processes + 7) / 16) plus room for other applications
+        at least ceil(num_os_semaphores / 16) plus room for other applications
        
 
        
         SEMMNS
         Maximum number of semaphores system-wide
-        ceil((max_connections + autovacuum_max_workers + max_wal_senders + max_worker_processes + 7) / 16) * 17 plus room for other applications
+        ceil(num_os_semaphores / 16) * 17 plus room for other applications
        
 
        
@@ -839,21 +839,28 @@ psql: error: connection to server on socket "/tmp/.s.PGSQL.5432" failed: No such
     PostgreSQL uses one semaphore per allowed connection
     (), allowed autovacuum worker process
     (), allowed WAL sender process
-    (), and allowed background
-    process (), in sets of 16.
-    Each such set will
+    (), allowed background
+    process (), etc., in sets of 16.
+    The runtime-computed parameter 
+    reports the number of semaphores required.  This parameter can be viewed
+    before starting the server with a postgres command like:
+
+$ postgres -D $PGDATA -C num_os_semaphores
+
+   
+
+   
+    Each set of 16 semaphores will
     also contain a 17th semaphore which contains a magic
     number, to detect collision with semaphore sets used by
     other applications. The maximum number of semaphores in the system
     is set by SEMMNS, which consequently must be at least
-    as high as max_connections plus
-    autovacuum_max_workers plus max_wal_senders,
-    plus max_worker_processes, plus one extra for each 16
-    allowed connections plus workers (see the formula in 
+    as high as num_os_semaphores plus one extra for
+    each set of 16 required semaphores (see the formula in 
     linkend="sysvipc-parameters"/>).  The parameter SEMMNI
     determines the limit on the number of semaphore sets that can
     exist on the system at one time.  Hence this parameter must be at
-    least ceil((max_connections + autovacuum_max_workers + max_wal_senders + max_worker_processes + 7) / 16).
+    least ceil(num_os_semaphores / 16).
     Lowering the number
     of allowed connections is a temporary workaround for failures,
     which are usually confusingly worded No space
@@ -885,8 +892,8 @@ psql: error: connection to server on socket "/tmp/.s.PGSQL.5432" failed: No such
     same as for System V, that is one semaphore per allowed connection
     (), allowed autovacuum worker process
     (), allowed WAL sender process
-    (), and allowed background
-    process ().
+    (), allowed background
+    process (), etc.
     On the platforms where this option is preferred, there is no specific
     kernel limit on the number of POSIX semaphores.
    
index 2100150f01cd41e7a72cc65e0123fd3c9a6b0ef3..ca930af08f2dc430143aa32aee93c019b3ed3ce0 100644 (file)
@@ -372,11 +372,12 @@ InitializeShmemGUCs(void)
    Size        size_b;
    Size        size_mb;
    Size        hp_size;
+   int         num_semas;
 
    /*
     * Calculate the shared memory size and round up to the nearest megabyte.
     */
-   size_b = CalculateShmemSize(NULL);
+   size_b = CalculateShmemSize(&num_semas);
    size_mb = add_size(size_b, (1024 * 1024) - 1) / (1024 * 1024);
    sprintf(buf, "%zu", size_mb);
    SetConfigOption("shared_memory_size", buf,
@@ -395,4 +396,7 @@ InitializeShmemGUCs(void)
        SetConfigOption("shared_memory_size_in_huge_pages", buf,
                        PGC_INTERNAL, PGC_S_DYNAMIC_DEFAULT);
    }
+
+   sprintf(buf, "%d", num_semas);
+   SetConfigOption("num_os_semaphores", buf, PGC_INTERNAL, PGC_S_DYNAMIC_DEFAULT);
 }
index f6fcdebb0312c0df761c941d7f165ea976b0ac62..6a623f5f3420f960a9fe35e12a20dc4cf5b407c0 100644 (file)
@@ -591,6 +591,7 @@ static int  segment_size;
 static int shared_memory_size_mb;
 static int shared_memory_size_in_huge_pages;
 static int wal_block_size;
+static int num_os_semaphores;
 static bool data_checksums;
 static bool integer_datetimes;
 
@@ -2283,6 +2284,17 @@ struct config_int ConfigureNamesInt[] =
        NULL, NULL, NULL
    },
 
+   {
+       {"num_os_semaphores", PGC_INTERNAL, PRESET_OPTIONS,
+           gettext_noop("Shows the number of semaphores required for the server."),
+           NULL,
+           GUC_NOT_IN_SAMPLE | GUC_DISALLOW_IN_FILE | GUC_RUNTIME_COMPUTED
+       },
+       &num_os_semaphores,
+       0, 0, INT_MAX,
+       NULL, NULL, NULL
+   },
+
    {
        {"commit_timestamp_buffers", PGC_POSTMASTER, RESOURCES_MEM,
            gettext_noop("Sets the size of the dedicated buffer pool used for the commit timestamp cache."),