SHMEM_ATTACH_UNKNOWN_SIZE reaches InitShmemIndexEntry() - #425
pg-hub-mirror[bot] wants to merge 1 commit into
Conversation
SHMEM_ATTACH_UNKNOWN_SIZE can be passed as argument to ShmemRequestStruct() when the caller wants to attach to an existing shared memory structure, whose size it does not know, after the startup. If the shared memory structure it wants to attach to does not exist, the request should fail. But instead ProcessShmemRequestsAfterStartup() ended up creating the structure with size = -1. InitShmemIndexEntry() did not catch it and created a ShmemIndexEntry with size = SIZE_MAX since size is an unsigned integer. ShmemAllocRaw() did not catch the overflow in size arithmetic and ended up allocating the new structure overlapping the earlier structure which can potentially cause memory corruption. Fix this by making ProcessShmemRequestsAfterStartup() reject the requests with size = SHMEM_ATTACH_UNKNOWN_SIZE when the structure with the requested name does not exist. Add an Assert() in InitShmemIndexEntry() to make sure that a request with unknown size never reaches it. Also make ShmemAllocRaw() check for overflow in its size arithmetic, as defense-in-depth against a similar mistake silently corrupting memory in the future. Also document use of SHMEM_ATTACH_UNKNOWN_SIZE. Author: Ashutosh Bapat <ashutosh.bapat.oss@gmail.com> Discussion: TBD
|
Heikki Linnakangas <hlinnaka(at)iki(dot)fi> via pgsql-hackers · original email On 18/09/2026 10:00, Ashutosh Bapat wrote:
|
pgsql-hackersCAExHW5u_fTsOAS85kG981Vu6eR1GV-344rup6zYew7xMjEDREw@mail.gmail.comPatch files:
Hi All, Heikki,
SHMEM_ATTACH_UNKNOWN_SIZE can be passed as argument to
ShmemRequestStruct() when the caller wants to attach to an existing
shared memory structure, whose size it does not know, after the
startup. If the shared memory structure it wants to attach to does not
exist, the request should fail. But instead
ProcessShmemRequestsAfterStartup() ended up creating the structure
with size = -1. InitShmemIndexEntry() did not catch it and created a
ShmemIndexEntry with size = SIZE_MAX since size is an unsigned
integer. ShmemAllocRaw() did not catch the overflow in address
arithmetic and ended up allocating the new structure overlapping the
earlier structure which can potentially cause memory corruption.
Attached patch fixes ProcessShmemRequestsAfterStartup() throw an error
in this case, adds an Assert() in InitShmemIndexEntry() to make sure
that a request with unknown size never reaches it, makes
ShmemAllocRaw() check for overflow, and documents use of
SHMEM_ATTACH_UNKNOWN_SIZE.
I found this problem when working on resizable shared structures where
the size of the structure may have changed from its initial size and
hence may not be known. It's good to defend our shared memory
structures from a bug in extension code.
Best Wishes,
Ashutosh Bapat