diff --git a/win32ss/user/ntuser/ime.c b/win32ss/user/ntuser/ime.c index 7b6c06b9f94..6b6e17391ef 100644 --- a/win32ss/user/ntuser/ime.c +++ b/win32ss/user/ntuser/ime.c @@ -1362,9 +1362,7 @@ PIMC FASTCALL UserCreateInputContext(ULONG_PTR dwClientImcData) else // First time. It's the default IMC. { // Add the first one (default) to the list. - if (pti->spDefaultImc) - UserDereferenceObject(pti->spDefaultImc); - pti->spDefaultImc = pIMC; + UserAssignmentLock((PVOID*)&pti->spDefaultImc, pIMC); pIMC->pImcNext = NULL; } diff --git a/win32ss/user/ntuser/main.c b/win32ss/user/ntuser/main.c index dfdf2d64c0b..1010d7970ef 100644 --- a/win32ss/user/ntuser/main.c +++ b/win32ss/user/ntuser/main.c @@ -696,6 +696,7 @@ error: VOID UserDisplayNotifyShutdown(PPROCESSINFO ppiCurrent); +// Win: xxxDestroyThreadInfo NTSTATUS NTAPI ExitThreadCallback(PETHREAD Thread) @@ -783,6 +784,7 @@ ExitThreadCallback(PETHREAD Thread) ASSERT(FALSE); return STATUS_UNSUCCESSFUL; } + UserAssignmentUnlock((PVOID*)&ptiCurrent->spDefaultImc); if (ppiCurrent && ppiCurrent->ptiList == ptiCurrent && !ptiCurrent->ptiSibling && ppiCurrent->W32PF_flags & W32PF_CLASSESREGISTERED) diff --git a/win32ss/user/ntuser/object.c b/win32ss/user/ntuser/object.c index cc2bebdb8bc..492d4ab2b6b 100644 --- a/win32ss/user/ntuser/object.c +++ b/win32ss/user/ntuser/object.c @@ -801,3 +801,39 @@ CLEANUP: UserLeave(); END_CLEANUP; } + +// Win: HMAssignmentLock +PVOID FASTCALL UserAssignmentLock(PVOID *ppvObj, PVOID pvNew) +{ + PVOID pvOld = *ppvObj; + *ppvObj = pvNew; + + if (pvOld && pvOld == pvNew) + return pvOld; + + if (pvNew) + UserReferenceObject(pvNew); + + if (pvOld) + { + if (UserDereferenceObject(pvOld)) + pvOld = NULL; + } + + return pvOld; +} + +// Win: HMAssignmentUnlock +PVOID FASTCALL UserAssignmentUnlock(PVOID *ppvObj) +{ + PVOID pvOld = *ppvObj; + *ppvObj = NULL; + + if (pvOld) + { + if (UserDereferenceObject(pvOld)) + pvOld = NULL; + } + + return pvOld; +} diff --git a/win32ss/user/ntuser/object.h b/win32ss/user/ntuser/object.h index 9fb1b7f6637..0d6bc6dda88 100644 --- a/win32ss/user/ntuser/object.h +++ b/win32ss/user/ntuser/object.h @@ -20,6 +20,8 @@ void DbgUserDumpHandleTable(); PVOID FASTCALL ValidateHandle(HANDLE handle, HANDLE_TYPE type); BOOLEAN UserDestroyObjectsForOwner(PUSER_HANDLE_TABLE Table, PVOID Owner); BOOL FASTCALL UserMarkObjectDestroy(PVOID); +PVOID FASTCALL UserAssignmentLock(PVOID *ppvObj, PVOID pvNew); +PVOID FASTCALL UserAssignmentUnlock(PVOID *ppvObj); static __inline VOID UserRefObjectCo(PVOID obj, PUSER_REFERENCE_ENTRY UserReferenceEntry)