]> git.ipfire.org Git - thirdparty/postgresql.git/commitdiff
Initialize random() in bootstrap/stand-alone postgres and in initdb.
authorNoah Misch <noah@leadboat.com>
Mon, 24 Sep 2018 05:56:39 +0000 (22:56 -0700)
committerNoah Misch <noah@leadboat.com>
Mon, 24 Sep 2018 05:56:57 +0000 (22:56 -0700)
This removes a difference between the standard IsUnderPostmaster
execution environment and that of --boot and --single.  In a stand-alone
backend, "SELECT random()" always started at the same seed.

On a system capable of using posix shared memory, initdb could still
conclude "selecting dynamic shared memory implementation ... sysv".
Crashed --boot or --single postgres processes orphaned shared memory
objects having names that collided with the not-actually-random names
that initdb probed.  The sysv fallback appeared after ten crashes of
--boot or --single postgres.  Since --boot and --single are rare in
production use, systems used for PostgreSQL development are the
principal candidate to notice this symptom.

Back-patch to 9.3 (all supported versions).  PostgreSQL 9.4 introduced
dynamic shared memory, but 9.3 does share the "SELECT random()" problem.

Reviewed by Tom Lane and Kyotaro HORIGUCHI.

Discussion: https://postgr.es/m/20180915221546.GA3159382@rfd.leadboat.com

src/backend/bootstrap/bootstrap.c
src/backend/tcop/postgres.c
src/bin/initdb/initdb.c

index 0e14b9272b5bdd0b8e5509a8e020236e060c34f1..0943a59d660121e6006d62f0f0b0ec562f5edd7d 100644 (file)
@@ -197,6 +197,14 @@ AuxiliaryProcessMain(int argc, char *argv[])
 
        MyStartTime = time(NULL);
 
+       /*
+        * Initialize random() for the first time, like PostmasterMain() would.
+        * In a regular IsUnderPostmaster backend, BackendRun() computes a
+        * high-entropy seed before any user query.  Fewer distinct initial seeds
+        * can occur here.
+        */
+       srandom((unsigned int) (MyProcPid ^ MyStartTime));
+
        /* Compute paths, if we didn't inherit them from postmaster */
        if (my_exec_path[0] == '\0')
        {
index 5903b228905e185d5a95c55fb18416b5ecbb5941..98180ed52abee2a59daec688794dbff015594295 100644 (file)
@@ -3611,6 +3611,14 @@ PostgresMain(int argc, char *argv[],
                MyProcPid = getpid();
 
                MyStartTime = time(NULL);
+
+               /*
+                * Initialize random() for the first time, like PostmasterMain()
+                * would.  In a regular IsUnderPostmaster backend, BackendRun()
+                * computes a high-entropy seed before any user query.  Fewer distinct
+                * initial seeds can occur here.
+                */
+               srandom((unsigned int) (MyProcPid ^ MyStartTime));
        }
 
        SetProcessingMode(InitProcessing);
index 6de22ba65e148f44a7153974d4ccd1a420df036f..fb16897adf0965ad2af83a218a3ef0cc3e11581c 100644 (file)
@@ -1055,6 +1055,9 @@ choose_dsm_implementation(void)
 #ifdef HAVE_SHM_OPEN
        int                     ntries = 10;
 
+       /* Initialize random(); this function is its only user in this program. */
+       srandom((unsigned int) (getpid() ^ time(NULL)));
+
        while (ntries > 0)
        {
                uint32          handle;