From 25d7cf90f5199693c1f749919fff0fcb1f00c19b Mon Sep 17 00:00:00 2001 From: "Christoph M. Becker" Date: Tue, 5 May 2020 09:31:17 +0200 Subject: [PATCH] =?UTF-8?q?Support=20shmget(IPC=5FPRIVATE,=20=E2=80=A6)=20?= =?UTF-8?q?on=20Windows?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit We map the POSIX semantics of `IPC_PRIVATE` by creating unnamed file mapping objects on Windows. While that is not particularly useful for ext/shmop, which is the only bundled extension which uses `shmget()`, it may be useful for external extensions. --- TSRM/tsrm_win32.c | 16 +++++++++------- ext/shmop/tests/shmop_open_private.phpt | 23 +++++++++++++++++++++++ 2 files changed, 32 insertions(+), 7 deletions(-) create mode 100644 ext/shmop/tests/shmop_open_private.phpt diff --git a/TSRM/tsrm_win32.c b/TSRM/tsrm_win32.c index 45cfbba7e56d7..cccb0d3732ef5 100644 --- a/TSRM/tsrm_win32.c +++ b/TSRM/tsrm_win32.c @@ -613,14 +613,16 @@ TSRM_API int shmget(key_t key, size_t size, int flags) {/*{{{*/ shm_pair *shm; char shm_segment[26], shm_info[29]; - HANDLE shm_handle, info_handle; + HANDLE shm_handle = NULL, info_handle = NULL; BOOL created = FALSE; - snprintf(shm_segment, sizeof(shm_segment), "TSRM_SHM_SEGMENT:%d", key); - snprintf(shm_info, sizeof(shm_info), "TSRM_SHM_DESCRIPTOR:%d", key); + if (key != IPC_PRIVATE) { + snprintf(shm_segment, sizeof(shm_segment), "TSRM_SHM_SEGMENT:%d", key); + snprintf(shm_info, sizeof(shm_info), "TSRM_SHM_DESCRIPTOR:%d", key); - shm_handle = OpenFileMapping(FILE_MAP_ALL_ACCESS, FALSE, shm_segment); - info_handle = OpenFileMapping(FILE_MAP_ALL_ACCESS, FALSE, shm_info); + shm_handle = OpenFileMapping(FILE_MAP_ALL_ACCESS, FALSE, shm_segment); + info_handle = OpenFileMapping(FILE_MAP_ALL_ACCESS, FALSE, shm_info); + } if (!shm_handle && !info_handle) { if (flags & IPC_CREAT) { @@ -631,8 +633,8 @@ TSRM_API int shmget(key_t key, size_t size, int flags) DWORD high = 0; DWORD low = size; #endif - shm_handle = CreateFileMapping(INVALID_HANDLE_VALUE, NULL, PAGE_READWRITE, high, low, shm_segment); - info_handle = CreateFileMapping(INVALID_HANDLE_VALUE, NULL, PAGE_READWRITE, 0, sizeof(shm->descriptor), shm_info); + shm_handle = CreateFileMapping(INVALID_HANDLE_VALUE, NULL, PAGE_READWRITE, high, low, key == IPC_PRIVATE ? NULL : shm_segment); + info_handle = CreateFileMapping(INVALID_HANDLE_VALUE, NULL, PAGE_READWRITE, 0, sizeof(shm->descriptor), key == IPC_PRIVATE ? NULL : shm_info); created = TRUE; } if (!shm_handle || !info_handle) { diff --git a/ext/shmop/tests/shmop_open_private.phpt b/ext/shmop/tests/shmop_open_private.phpt new file mode 100644 index 0000000000000..df969885c9e71 --- /dev/null +++ b/ext/shmop/tests/shmop_open_private.phpt @@ -0,0 +1,23 @@ +--TEST-- +shmop_open with IPC_PRIVATE creates private SHM +--SKIPIF-- + +--FILE-- + +--EXPECT-- +bool(true)