Skip to content

Commit 3eb245d

Browse files
authored
Add the CurrentUserOnly and CurrentSessionOnly options for named Mutex, Semaphore, and EventWaitHandle (#112213)
- In `Mutex`, `Semaphore`, and `EventWaitHandle`, added overloads for methods with a `name` argument to also include a `NamedWaitHandleOptions options` argument. The `CurrentUserOnly` option indicates whether the object should be limited in access to the current user. The `CurrentSessionOnly` option indicates whether the object object is intended to be used only within the current session (an alternative to the name prefixes, such as `Global\`). The default value for `NamedWaitHandleOptions` has `CurrentUserOnly=true` and `CurrentSessionOnly=true`. - On Unixes, named semaphores and events are not supported. Named mutexes are have a functional implementation on Unixes in CoreCLR. NativeAOT and Mono on Unixes use an incomplete/temporary implementation where named mutexes are just process-local mutexes stored in a dictionary keyed by the name and can't be used to synchronize between processes. This change only briefly extends the NativeAOT/Mono implementation to add another prefix to the name when `CurrentUserOnly=true`. Sharing the CoreCLR Unix named mutex implementation with NativeAOT/Mono is left to a separate change. Most of what is described below when `CurrentUserOnly=true` on Unixes refers to the CoreCLR implementation. - The plan is to also deprecate the APIs with a `name` argument but without an `options` argument in a separate change - API review: #102682 (comment) ### Windows with `CurrentUserOnly=true` When creating a named mutex, a security descriptor is created and assigned to the object. - The owner and group are set to the current user - The DACL has two ACEs: - One ACE allows the current user the relevant access rights - Another ACE allows the `BUILTIN\Administrators` group the `READ_CONTROL` access right to enable reading the security info for diagnostic purposes - The SACL has a mandatory label ACE - The access policy prevents principals with an integrity level lower than the object from opening the object - The integrity level assigned to the object is the same as what would be assigned by the system by default - When opening a named mutex, the owner and DACL are verified to see if they are as expected, and if not, a `WaitHandleCannotBeOpenedException` is thrown - Access controls are set when creating an object and checked when opening an object. Once a handle to the object is obtained, typical synchronization operations may not do further access checks. It's up to the caller to be careful about how the handle to the object is passed around. ### Unixes with `CurrentUserOnly=true` - Files relevant to named mutexes (shared memory and lock files) go under `/tmp/.dotnet-uidN/` where `N` is the effective user ID - `/tmp/` (or equivalent) was chosen mainly for the automatic cleanup, as the number of files can add up in cases where mutexes are not disposed, particularly when randomly generated names are used upon each invocation of a process. Due to the use of a global location `/tmp/` or equivalent, it would be possible for a user to deny access to the `.dotnet-uidN` directory of a different user if the directory hadn't been created yet. An alternative considered was to use the home directory and introduce some kind of periodic cleanup strategy, but there are also other tradeoffs. - `/tmp/` or equivalent must either have the sticky bit, or it must be owned by the current user and without write access for any other user. Otherwise, an exception is thrown. - Permissions of the `/tmp/.dotnet-uidN/` directory and files/directories under it are limited in access to the current user - When opening a named mutex, the owner and permissions of relevant files/directories are verified to see if they are as expected, and if not, an exception is thrown - Access controls are set when creating an object and checked when opening an object. Once a handle to the object is obtained, typical synchronization operations may not do further access checks. It's up to the caller to be careful about how the handle to the object is passed around. ### Namespaces - On Windows, there is no namespace for kernel objects for each user. `CurrentSessionOnly=true` is close, but it is possible for multiple users to be running code simultaneously in the same session. There is a global namespace, and a namespace per session. When `CurrentUserOnly=true`, callers may need to ensure that the name used is distinguished for different users. - On Unixes, a different directory tree is used when `CurrentUserOnly=true`, so each user has a separate namespace for objects, including for session-scoped and session-unscoped objects.
1 parent 82c916f commit 3eb245d

39 files changed

+3154
-638
lines changed

src/coreclr/System.Private.CoreLib/src/System/Threading/Mutex.CoreCLR.Unix.cs

Lines changed: 52 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -14,9 +14,40 @@ namespace System.Threading
1414
/// </summary>
1515
public sealed partial class Mutex : WaitHandle
1616
{
17-
private void CreateMutexCore(bool initiallyOwned, string? name, out bool createdNew)
17+
private unsafe void CreateMutexCore(bool initiallyOwned)
1818
{
19-
SafeWaitHandle mutexHandle = CreateMutexCore(initiallyOwned, name, out int errorCode, out string? errorDetails);
19+
SafeWaitHandle handle =
20+
CreateMutex(
21+
initiallyOwned,
22+
name: null,
23+
currentUserOnly: false,
24+
systemCallErrors: null,
25+
systemCallErrorsBufferSize: 0);
26+
if (handle.IsInvalid)
27+
{
28+
int errorCode = Marshal.GetLastPInvokeError();
29+
handle.SetHandleAsInvalid();
30+
throw Win32Marshal.GetExceptionForWin32Error(errorCode);
31+
}
32+
33+
SafeWaitHandle = handle;
34+
}
35+
36+
private void CreateMutexCore(
37+
bool initiallyOwned,
38+
string? name,
39+
NamedWaitHandleOptionsInternal options,
40+
out bool createdNew)
41+
{
42+
bool currentUserOnly = false;
43+
if (!string.IsNullOrEmpty(name) && options.WasSpecified)
44+
{
45+
name = options.GetNameWithSessionPrefix(name);
46+
currentUserOnly = options.CurrentUserOnly;
47+
}
48+
49+
SafeWaitHandle mutexHandle =
50+
CreateMutexCore(initiallyOwned, name, currentUserOnly, out int errorCode, out string? errorDetails);
2051
if (mutexHandle.IsInvalid)
2152
{
2253
mutexHandle.SetHandleAsInvalid();
@@ -33,16 +64,26 @@ private void CreateMutexCore(bool initiallyOwned, string? name, out bool created
3364
SafeWaitHandle = mutexHandle;
3465
}
3566

36-
private static OpenExistingResult OpenExistingWorker(string name, out Mutex? result)
67+
private static OpenExistingResult OpenExistingWorker(
68+
string name,
69+
NamedWaitHandleOptionsInternal options,
70+
out Mutex? result)
3771
{
3872
ArgumentException.ThrowIfNullOrEmpty(name);
3973

74+
bool currentUserOnly = false;
75+
if (options.WasSpecified)
76+
{
77+
name = options.GetNameWithSessionPrefix(name);
78+
currentUserOnly = options.CurrentUserOnly;
79+
}
80+
4081
result = null;
4182
// To allow users to view & edit the ACL's, call OpenMutex
4283
// with parameters to allow us to view & edit the ACL. This will
4384
// fail if we don't have permission to view or edit the ACL's.
4485
// If that happens, ask for less permissions.
45-
SafeWaitHandle myHandle = OpenMutexCore(name, out int errorCode, out string? errorDetails);
86+
SafeWaitHandle myHandle = OpenMutexCore(name, currentUserOnly, out int errorCode, out string? errorDetails);
4687

4788
if (myHandle.IsInvalid)
4889
{
@@ -86,11 +127,13 @@ public void ReleaseMutex()
86127
private static unsafe SafeWaitHandle CreateMutexCore(
87128
bool initialOwner,
88129
string? name,
130+
bool currentUserOnly,
89131
out int errorCode,
90132
out string? errorDetails)
91133
{
92134
byte* systemCallErrors = stackalloc byte[SystemCallErrorsBufferSize];
93-
SafeWaitHandle mutexHandle = CreateMutex(initialOwner, name, systemCallErrors, SystemCallErrorsBufferSize);
135+
SafeWaitHandle mutexHandle =
136+
CreateMutex(initialOwner, name, currentUserOnly, systemCallErrors, SystemCallErrorsBufferSize);
94137

95138
// Get the error code even if the handle is valid, as it could be ERROR_ALREADY_EXISTS, indicating that the mutex
96139
// already exists and was opened
@@ -100,10 +143,10 @@ private static unsafe SafeWaitHandle CreateMutexCore(
100143
return mutexHandle;
101144
}
102145

103-
private static unsafe SafeWaitHandle OpenMutexCore(string name, out int errorCode, out string? errorDetails)
146+
private static unsafe SafeWaitHandle OpenMutexCore(string name, bool currentUserOnly, out int errorCode, out string? errorDetails)
104147
{
105148
byte* systemCallErrors = stackalloc byte[SystemCallErrorsBufferSize];
106-
SafeWaitHandle mutexHandle = OpenMutex(name, systemCallErrors, SystemCallErrorsBufferSize);
149+
SafeWaitHandle mutexHandle = OpenMutex(name, currentUserOnly, systemCallErrors, SystemCallErrorsBufferSize);
107150
errorCode = mutexHandle.IsInvalid ? Marshal.GetLastPInvokeError() : Interop.Errors.ERROR_SUCCESS;
108151
errorDetails = mutexHandle.IsInvalid ? GetErrorDetails(systemCallErrors) : null;
109152
return mutexHandle;
@@ -127,9 +170,9 @@ private static unsafe SafeWaitHandle OpenMutexCore(string name, out int errorCod
127170
}
128171

129172
[LibraryImport(RuntimeHelpers.QCall, EntryPoint = "PAL_CreateMutexW", SetLastError = true, StringMarshalling = StringMarshalling.Utf16)]
130-
private static unsafe partial SafeWaitHandle CreateMutex([MarshalAs(UnmanagedType.Bool)] bool initialOwner, string? name, byte* systemCallErrors, uint systemCallErrorsBufferSize);
173+
private static unsafe partial SafeWaitHandle CreateMutex([MarshalAs(UnmanagedType.Bool)] bool initialOwner, string? name, [MarshalAs(UnmanagedType.Bool)] bool currentUserOnly, byte* systemCallErrors, uint systemCallErrorsBufferSize);
131174

132175
[LibraryImport(RuntimeHelpers.QCall, EntryPoint = "PAL_OpenMutexW", SetLastError = true, StringMarshalling = StringMarshalling.Utf16)]
133-
private static unsafe partial SafeWaitHandle OpenMutex(string name, byte* systemCallErrors, uint systemCallErrorsBufferSize);
176+
private static unsafe partial SafeWaitHandle OpenMutex(string name, [MarshalAs(UnmanagedType.Bool)] bool currentUserOnly, byte* systemCallErrors, uint systemCallErrorsBufferSize);
134177
}
135178
}

src/coreclr/pal/inc/pal.h

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -854,6 +854,7 @@ PALAPI
854854
PAL_CreateMutexW(
855855
IN BOOL bInitialOwner,
856856
IN LPCWSTR lpName,
857+
IN BOOL bCurrentUserOnly,
857858
IN LPSTR lpSystemCallErrors,
858859
IN DWORD dwSystemCallErrorsBufferSize);
859860

@@ -875,6 +876,7 @@ HANDLE
875876
PALAPI
876877
PAL_OpenMutexW(
877878
IN LPCWSTR lpName,
879+
IN BOOL bCurrentUserOnly,
878880
IN LPSTR lpSystemCallErrors,
879881
IN DWORD dwSystemCallErrorsBufferSize);
880882

src/coreclr/pal/inc/pal_error.h

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -147,7 +147,6 @@
147147
#define ERROR_PALINIT_TLS 65295L
148148
#define ERROR_PALINIT_ENV 65296L
149149
#define ERROR_PALINIT_DBG_CHANNELS 65297L
150-
#define ERROR_PALINIT_SHARED_MEMORY_MANAGER 65298L
151150
#define ERROR_PALINIT_SHM 65299L
152151
#define ERROR_PALINIT_MODULE_MANAGER 65300L
153152

src/coreclr/pal/src/include/pal/mutex.hpp

Lines changed: 5 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -37,6 +37,7 @@ namespace CorUnix
3737
LPSECURITY_ATTRIBUTES lpMutexAttributes,
3838
BOOL bInitialOwner,
3939
LPCSTR lpName,
40+
BOOL bCurrentUserOnly,
4041
HANDLE *phMutex
4142
);
4243

@@ -51,6 +52,7 @@ namespace CorUnix
5152
SharedMemorySystemCallErrors *errors,
5253
CPalThread *pThread,
5354
LPCSTR lpName,
55+
BOOL bCurrentUserOnly,
5456
HANDLE *phMutex
5557
);
5658

@@ -216,10 +218,10 @@ class NamedMutexProcessData : public SharedMemoryProcessDataBase
216218
bool m_hasRefFromLockOwnerThread;
217219

218220
public:
219-
static SharedMemoryProcessDataHeader *CreateOrOpen(SharedMemorySystemCallErrors *errors, LPCSTR name, bool acquireLockIfCreated, bool *createdRef);
220-
static SharedMemoryProcessDataHeader *Open(SharedMemorySystemCallErrors *errors, LPCSTR name);
221+
static SharedMemoryProcessDataHeader *CreateOrOpen(SharedMemorySystemCallErrors *errors, LPCSTR name, bool isUserScope, bool acquireLockIfCreated, bool *createdRef);
222+
static SharedMemoryProcessDataHeader *Open(SharedMemorySystemCallErrors *errors, LPCSTR name, bool isUserScope);
221223
private:
222-
static SharedMemoryProcessDataHeader *CreateOrOpen(SharedMemorySystemCallErrors *errors, LPCSTR name, bool createIfNotExist, bool acquireLockIfCreated, bool *createdRef);
224+
static SharedMemoryProcessDataHeader *CreateOrOpen(SharedMemorySystemCallErrors *errors, LPCSTR name, bool isUserScope, bool createIfNotExist, bool acquireLockIfCreated, bool *createdRef);
223225

224226
public:
225227
NamedMutexProcessData(

src/coreclr/pal/src/include/pal/sharedmemory.h

Lines changed: 53 additions & 32 deletions
Original file line numberDiff line numberDiff line change
@@ -27,27 +27,26 @@
2727
#define SHARED_MEMORY_MAX_FILE_NAME_CHAR_COUNT (_MAX_FNAME - 1)
2828
#define SHARED_MEMORY_MAX_NAME_CHAR_COUNT (STRING_LENGTH("Global\\") + SHARED_MEMORY_MAX_FILE_NAME_CHAR_COUNT)
2929

30-
#define SHARED_MEMORY_RUNTIME_TEMP_DIRECTORY_NAME ".dotnet"
31-
#define SHARED_MEMORY_SHARED_MEMORY_DIRECTORY_NAME ".dotnet/shm"
32-
#define SHARED_MEMORY_LOCK_FILES_DIRECTORY_NAME ".dotnet/lockfiles"
33-
static_assert_no_msg(ARRAY_SIZE(SHARED_MEMORY_LOCK_FILES_DIRECTORY_NAME) >= ARRAY_SIZE(SHARED_MEMORY_SHARED_MEMORY_DIRECTORY_NAME));
30+
#define SHARED_MEMORY_USER_UNSCOPED_RUNTIME_TEMP_DIRECTORY_NAME ".dotnet"
31+
#define SHARED_MEMORY_USER_SCOPED_RUNTIME_TEMP_DIRECTORY_NAME_PREFIX ".dotnet-uid"
32+
#define SHARED_MEMORY_SHARED_MEMORY_DIRECTORY_NAME "shm"
33+
#define SHARED_MEMORY_LOCK_FILES_DIRECTORY_NAME "lockfiles"
34+
static_assert_no_msg(STRING_LENGTH(SHARED_MEMORY_LOCK_FILES_DIRECTORY_NAME) >= STRING_LENGTH(SHARED_MEMORY_SHARED_MEMORY_DIRECTORY_NAME));
3435

3536
#define SHARED_MEMORY_GLOBAL_DIRECTORY_NAME "global"
3637
#define SHARED_MEMORY_SESSION_DIRECTORY_NAME_PREFIX "session"
37-
static_assert_no_msg(ARRAY_SIZE(SHARED_MEMORY_SESSION_DIRECTORY_NAME_PREFIX) >= ARRAY_SIZE(SHARED_MEMORY_GLOBAL_DIRECTORY_NAME));
3838

39-
#define SHARED_MEMORY_UNIQUE_TEMP_NAME_TEMPLATE ".coreclr.XXXXXX"
40-
41-
#define SHARED_MEMORY_MAX_SESSION_ID_CHAR_COUNT (10)
39+
#define SHARED_MEMORY_UNIQUE_TEMP_NAME_TEMPLATE ".dotnet.XXXXXX"
4240

4341
// Note that this Max size does not include the prefix folder path size which is unknown (in the case of sandbox) until runtime
4442
#define SHARED_MEMORY_MAX_FILE_PATH_CHAR_COUNT \
4543
( \
44+
STRING_LENGTH(SHARED_MEMORY_USER_SCOPED_RUNTIME_TEMP_DIRECTORY_NAME_PREFIX) + \
45+
11 /* user ID, path separator */ + \
4646
STRING_LENGTH(SHARED_MEMORY_LOCK_FILES_DIRECTORY_NAME) + \
4747
1 /* path separator */ + \
4848
STRING_LENGTH(SHARED_MEMORY_SESSION_DIRECTORY_NAME_PREFIX) + \
49-
SHARED_MEMORY_MAX_SESSION_ID_CHAR_COUNT + \
50-
1 /* path separator */ + \
49+
11 /* session ID, path separator */ + \
5150
SHARED_MEMORY_MAX_FILE_NAME_CHAR_COUNT \
5251
)
5352

@@ -98,12 +97,17 @@ class SharedMemorySystemCallErrors
9897
void Append(LPCSTR format, ...);
9998
};
10099

100+
class SharedMemoryId;
101+
101102
class SharedMemoryHelpers
102103
{
103104
private:
104-
static const mode_t PermissionsMask_CurrentUser_ReadWriteExecute;
105+
static const mode_t PermissionsMask_OwnerUser_ReadWrite;
106+
static const mode_t PermissionsMask_OwnerUser_ReadWriteExecute;
107+
static const mode_t PermissionsMask_NonOwnerUsers_Write;
105108
static const mode_t PermissionsMask_AllUsers_ReadWrite;
106109
static const mode_t PermissionsMask_AllUsers_ReadWriteExecute;
110+
static const mode_t PermissionsMask_Sticky;
107111
public:
108112
static const UINT32 InvalidProcessId;
109113
static const SIZE_T InvalidThreadId;
@@ -114,17 +118,14 @@ class SharedMemoryHelpers
114118
static SIZE_T AlignUp(SIZE_T value, SIZE_T alignment);
115119

116120
static void *Alloc(SIZE_T byteCount);
117-
118-
template<SIZE_T SuffixByteCount> static void BuildSharedFilesPath(PathCharString& destination, const char (&suffix)[SuffixByteCount]);
119-
static void BuildSharedFilesPath(PathCharString& destination, const char *suffix, int suffixByteCount);
120121
static bool AppendUInt32String(PathCharString& destination, UINT32 value);
121122

122-
static bool EnsureDirectoryExists(SharedMemorySystemCallErrors *errors, const char *path, bool isGlobalLockAcquired, bool createIfNotExist = true, bool isSystemDirectory = false);
123+
static bool EnsureDirectoryExists(SharedMemorySystemCallErrors *errors, const char *path, const SharedMemoryId *id, bool isGlobalLockAcquired, bool createIfNotExist = true, bool isSystemDirectory = false);
123124
private:
124125
static int Open(SharedMemorySystemCallErrors *errors, LPCSTR path, int flags, mode_t mode = static_cast<mode_t>(0));
125126
public:
126127
static int OpenDirectory(SharedMemorySystemCallErrors *errors, LPCSTR path);
127-
static int CreateOrOpenFile(SharedMemorySystemCallErrors *errors, LPCSTR path, bool createIfNotExist = true, bool *createdRef = nullptr);
128+
static int CreateOrOpenFile(SharedMemorySystemCallErrors *errors, LPCSTR path, const SharedMemoryId *id, bool createIfNotExist = true, bool *createdRef = nullptr);
128129
static void CloseFile(int fileDescriptor);
129130

130131
static int ChangeMode(LPCSTR path, mode_t mode);
@@ -150,19 +151,24 @@ class SharedMemoryId
150151
LPCSTR m_name;
151152
SIZE_T m_nameCharCount;
152153
bool m_isSessionScope; // false indicates global scope
154+
bool m_isUserScope;
155+
uid_t m_userScopeUid;
153156

154157
public:
155158
SharedMemoryId();
156-
SharedMemoryId(LPCSTR name, SIZE_T nameCharCount, bool isSessionScope);
157-
SharedMemoryId(LPCSTR name);
159+
SharedMemoryId(LPCSTR name, bool isUserScope);
158160

159161
public:
160162
LPCSTR GetName() const;
161163
SIZE_T GetNameCharCount() const;
164+
void ReplaceNamePtr(LPCSTR name);
162165
bool IsSessionScope() const;
163-
bool Equals(SharedMemoryId *other) const;
166+
bool IsUserScope() const;
167+
uid_t GetUserScopeUid() const;
168+
bool Equals(const SharedMemoryId *other) const;
164169

165170
public:
171+
bool AppendRuntimeTempDirectoryName(PathCharString& path) const;
166172
bool AppendSessionDirectoryName(PathCharString& path) const;
167173
};
168174

@@ -222,22 +228,22 @@ class SharedMemoryProcessDataHeader
222228
SharedMemoryProcessDataHeader *m_nextInProcessDataHeaderList;
223229

224230
public:
225-
static SharedMemoryProcessDataHeader *CreateOrOpen(SharedMemorySystemCallErrors *errors, LPCSTR name, SharedMemorySharedDataHeader requiredSharedDataHeader, SIZE_T sharedDataByteCount, bool createIfNotExist, bool *createdRef);
231+
static SharedMemoryProcessDataHeader *CreateOrOpen(SharedMemorySystemCallErrors *errors, LPCSTR name, bool isUserScope, SharedMemorySharedDataHeader requiredSharedDataHeader, SIZE_T sharedDataByteCount, bool createIfNotExist, bool *createdRef);
226232

227233
public:
228234
static SharedMemoryProcessDataHeader *PalObject_GetProcessDataHeader(CorUnix::IPalObject *object);
229235
static void PalObject_SetProcessDataHeader(CorUnix::IPalObject *object, SharedMemoryProcessDataHeader *processDataHeader);
230236
static void PalObject_Close(CorUnix::CPalThread *thread, CorUnix::IPalObject *object, bool isShuttingDown);
231237

232238
private:
233-
SharedMemoryProcessDataHeader(SharedMemoryId *id, int fileDescriptor, SharedMemorySharedDataHeader *sharedDataHeader, SIZE_T sharedDataTotalByteCount);
239+
SharedMemoryProcessDataHeader(const SharedMemoryId *id, int fileDescriptor, SharedMemorySharedDataHeader *sharedDataHeader, SIZE_T sharedDataTotalByteCount);
234240
public:
235-
static SharedMemoryProcessDataHeader *New(SharedMemoryId *id, int fileDescriptor, SharedMemorySharedDataHeader *sharedDataHeader, SIZE_T sharedDataTotalByteCount);
241+
static SharedMemoryProcessDataHeader *New(const SharedMemoryId *id, int fileDescriptor, SharedMemorySharedDataHeader *sharedDataHeader, SIZE_T sharedDataTotalByteCount);
236242
~SharedMemoryProcessDataHeader();
237243
void Close();
238244

239245
public:
240-
SharedMemoryId *GetId();
246+
const SharedMemoryId *GetId() const;
241247
SharedMemoryProcessDataBase *GetData() const;
242248
void SetData(SharedMemoryProcessDataBase *data);
243249
SharedMemorySharedDataHeader *GetSharedDataHeader() const;
@@ -256,8 +262,24 @@ class SharedMemoryManager
256262
static CRITICAL_SECTION s_creationDeletionProcessLock;
257263
static int s_creationDeletionLockFileDescriptor;
258264

259-
static PathCharString* s_runtimeTempDirectoryPath;
260-
static PathCharString* s_sharedMemoryDirectoryPath;
265+
struct UserScopeUidAndFileDescriptor
266+
{
267+
uid_t userScopeUid;
268+
int fileDescriptor;
269+
270+
UserScopeUidAndFileDescriptor() : userScopeUid((uid_t)0), fileDescriptor(-1)
271+
{
272+
}
273+
274+
UserScopeUidAndFileDescriptor(uid_t userScopeUid, int fileDescriptor)
275+
: userScopeUid(userScopeUid), fileDescriptor(fileDescriptor)
276+
{
277+
}
278+
};
279+
280+
static UserScopeUidAndFileDescriptor *s_userScopeUidToCreationDeletionLockFDs;
281+
static int s_userScopeUidToCreationDeletionLockFDsCount;
282+
static int s_userScopeUidToCreationDeletionLockFDsCapacity;
261283

262284
private:
263285
static SharedMemoryProcessDataHeader *s_processDataHeaderListHead;
@@ -269,17 +291,16 @@ class SharedMemoryManager
269291
#endif // _DEBUG
270292

271293
public:
272-
static bool StaticInitialize();
294+
static void StaticInitialize();
273295
static void StaticClose();
274296

275297
public:
276298
static void AcquireCreationDeletionProcessLock();
277299
static void ReleaseCreationDeletionProcessLock();
278-
static void AcquireCreationDeletionFileLock(SharedMemorySystemCallErrors *errors);
279-
static void ReleaseCreationDeletionFileLock();
280-
281-
public:
282-
static bool CopySharedMemoryBasePath(PathCharString& destination);
300+
static void AcquireCreationDeletionFileLock(SharedMemorySystemCallErrors *errors, const SharedMemoryId *id);
301+
static void ReleaseCreationDeletionFileLock(const SharedMemoryId *id);
302+
static void AddUserScopeUidCreationDeletionLockFD(uid_t userScopeUid, int creationDeletionLockFD);
303+
static int FindUserScopeCreationDeletionLockFD(uid_t userScopeUid);
283304

284305
#ifdef _DEBUG
285306
public:
@@ -290,7 +311,7 @@ class SharedMemoryManager
290311
public:
291312
static void AddProcessDataHeader(SharedMemoryProcessDataHeader *processDataHeader);
292313
static void RemoveProcessDataHeader(SharedMemoryProcessDataHeader *processDataHeader);
293-
static SharedMemoryProcessDataHeader *FindProcessDataHeader(SharedMemoryId *id);
314+
static SharedMemoryProcessDataHeader *FindProcessDataHeader(const SharedMemoryId *id);
294315
};
295316

296317
#endif // !_PAL_SHARED_MEMORY_H_

src/coreclr/pal/src/include/pal/sharedmemory.inl

Lines changed: 0 additions & 21 deletions
This file was deleted.

src/coreclr/pal/src/init/pal.cpp

Lines changed: 1 addition & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -410,12 +410,7 @@ Initialize(
410410
// we use large numbers of threads or have many open files.
411411
}
412412

413-
if (!SharedMemoryManager::StaticInitialize())
414-
{
415-
ERROR("Shared memory static initialization failed!\n");
416-
palError = ERROR_PALINIT_SHARED_MEMORY_MANAGER;
417-
goto CLEANUP1;
418-
}
413+
SharedMemoryManager::StaticInitialize();
419414

420415
//
421416
// Initialize global process data

0 commit comments

Comments
 (0)