]> git.ipfire.org Git - thirdparty/postgresql.git/commitdiff
Fix memory leak on DSM slot exhaustion.
authorThomas Munro <tmunro@postgresql.org>
Sat, 1 Feb 2020 01:29:13 +0000 (14:29 +1300)
committerThomas Munro <tmunro@postgresql.org>
Sat, 1 Feb 2020 02:10:20 +0000 (15:10 +1300)
If we attempt to create a DSM segment when no slots are available,
we should return the memory to the operating system.  Previously
we did that if the DSM_CREATE_NULL_IF_MAXSEGMENTS flag was
passed in, but we didn't do it if an error was raised.  Repair.

Back-patch to 9.4, where DSM segments arrived.

Author: Thomas Munro
Reviewed-by: Robert Haas
Reported-by: Julian Backes
Discussion: https://postgr.es/m/CA%2BhUKGKAAoEw-R4om0d2YM4eqT1eGEi6%3DQot-3ceDR-SLiWVDw%40mail.gmail.com

src/backend/storage/ipc/dsm.c

index 0e5a0c399f3118bdeb5d5488bb94f4deb3a99c7b..ed0b1f15f7ca5f1db42f6fb5efaab3cdfdea455a 100644 (file)
@@ -496,9 +496,18 @@ dsm_create(Size size)
 
        /* Verify that we can support an additional mapping. */
        if (nitems >= dsm_control->maxitems)
+       {
+               LWLockRelease(DynamicSharedMemoryControlLock);
+               dsm_impl_op(DSM_OP_DESTROY, seg->handle, 0, &seg->impl_private,
+                                       &seg->mapped_address, &seg->mapped_size, WARNING);
+               if (seg->resowner != NULL)
+                       ResourceOwnerForgetDSM(seg->resowner, seg);
+               dlist_delete(&seg->node);
+               pfree(seg);
                ereport(ERROR,
                                (errcode(ERRCODE_INSUFFICIENT_RESOURCES),
                                 errmsg("too many dynamic shared memory segments")));
+       }
 
        /* Enter the handle into a new array slot. */
        dsm_control->item[nitems].handle = seg->handle;