https://git.reactos.org/?p=reactos.git;a=commitdiff;h=d5deacd90305a83d413af…
commit d5deacd90305a83d413af18dca8fa41fe03e61b3
Author: Katayama Hirofumi MZ <katayama.hirofumi.mz(a)gmail.com>
AuthorDate: Sat Jan 1 20:59:00 2022 +0900
Commit: GitHub <noreply(a)github.com>
CommitDate: Sat Jan 1 20:59:00 2022 +0900
[NTUSER] Implement NtUserCreateInputContext (#4230)
- Modify NtUserCreateInputContext prototype.
- Add UserCreateInputContext helper function.
- Implement NtUserCreateInputContext function by using UserCreateInputContext.
- Call UserCreateInputContext(0) in InitThreadCallback function to create the default
input context.
CORE-11700
---
dll/win32/imm32/imm.c | 2 +-
win32ss/include/ntuser.h | 2 +-
win32ss/user/ntuser/main.c | 6 +++++
win32ss/user/ntuser/ntstubs.c | 57 ++++++++++++++++++++++++++++++++++++++---
win32ss/user/ntuser/userfuncs.h | 1 +
5 files changed, 63 insertions(+), 5 deletions(-)
diff --git a/dll/win32/imm32/imm.c b/dll/win32/imm32/imm.c
index e24806c86d4..e916d44480f 100644
--- a/dll/win32/imm32/imm.c
+++ b/dll/win32/imm32/imm.c
@@ -597,7 +597,7 @@ HIMC WINAPI ImmCreateContext(void)
if (pClientImc == NULL)
return NULL;
- hIMC = NtUserCreateInputContext(pClientImc);
+ hIMC = NtUserCreateInputContext((ULONG_PTR)pClientImc);
if (hIMC == NULL)
{
Imm32HeapFree(pClientImc);
diff --git a/win32ss/include/ntuser.h b/win32ss/include/ntuser.h
index 1e6234f84c1..4618c99af76 100644
--- a/win32ss/include/ntuser.h
+++ b/win32ss/include/ntuser.h
@@ -1937,7 +1937,7 @@ NtUserCreateDesktop(
HIMC
NTAPI
-NtUserCreateInputContext(PCLIENTIMC pClientImc);
+NtUserCreateInputContext(ULONG_PTR dwClientImcData);
NTSTATUS
NTAPI
diff --git a/win32ss/user/ntuser/main.c b/win32ss/user/ntuser/main.c
index 00a683af61c..8daf15ba95d 100644
--- a/win32ss/user/ntuser/main.c
+++ b/win32ss/user/ntuser/main.c
@@ -651,6 +651,12 @@ InitThreadCallback(PETHREAD Thread)
}
ptiCurrent->pClientInfo->dwTIFlags = ptiCurrent->TIF_flags;
+ /* Create the default input context */
+ if (IS_IMM_MODE())
+ {
+ UserCreateInputContext(0);
+ }
+
/* Last things to do only if we are not a SYSTEM or CSRSS thread */
if (!(ptiCurrent->TIF_flags & (TIF_SYSTEMTHREAD | TIF_CSRSSTHREAD)))
{
diff --git a/win32ss/user/ntuser/ntstubs.c b/win32ss/user/ntuser/ntstubs.c
index 95a87900242..ddf9ba09381 100644
--- a/win32ss/user/ntuser/ntstubs.c
+++ b/win32ss/user/ntuser/ntstubs.c
@@ -461,12 +461,63 @@ NtUserYieldTask(VOID)
return 0;
}
+PIMC FASTCALL UserCreateInputContext(ULONG_PTR dwClientImcData)
+{
+ PIMC pIMC;
+ PTHREADINFO pti = PsGetCurrentThreadWin32Thread();
+ PDESKTOP pdesk = pti->rpdesk;
+
+ if (!IS_IMM_MODE() || (pti->TIF_flags & TIF_DISABLEIME)) // Disabled?
+ return NULL;
+
+ if (!pdesk) // No desktop?
+ return NULL;
+
+ // pti->spDefaultImc should be already set if non-first time.
+ if (dwClientImcData && !pti->spDefaultImc)
+ return NULL;
+
+ // Create an input context user object.
+ pIMC = UserCreateObject(gHandleTable, pdesk, pti, NULL, TYPE_INPUTCONTEXT,
sizeof(IMC));
+ if (!pIMC)
+ return NULL;
+
+ if (dwClientImcData) // Non-first time.
+ {
+ // Insert pIMC to the second position (non-default) of the list.
+ pIMC->pImcNext = pti->spDefaultImc->pImcNext;
+ pti->spDefaultImc->pImcNext = pIMC;
+ }
+ else // First time. It's the default IMC.
+ {
+ // Add the first one (default) to the list.
+ pti->spDefaultImc = pIMC;
+ pIMC->pImcNext = NULL;
+ }
+
+ pIMC->dwClientImcData = dwClientImcData; // Set it.
+ return pIMC;
+}
+
HIMC
APIENTRY
-NtUserCreateInputContext(PCLIENTIMC pClientImc)
+NtUserCreateInputContext(ULONG_PTR dwClientImcData)
{
- STUB;
- return NULL;
+ PIMC pIMC;
+ HIMC ret = NULL;
+
+ UserEnterExclusive();
+
+ if (!IS_IMM_MODE() || !dwClientImcData)
+ goto Quit;
+
+ pIMC = UserCreateInputContext(dwClientImcData);
+ if (pIMC)
+ ret = UserHMGetHandle(pIMC);
+
+Quit:
+ UserLeave();
+ return ret;
}
DWORD
diff --git a/win32ss/user/ntuser/userfuncs.h b/win32ss/user/ntuser/userfuncs.h
index 6fb86e64d71..3bae17d5567 100644
--- a/win32ss/user/ntuser/userfuncs.h
+++ b/win32ss/user/ntuser/userfuncs.h
@@ -165,6 +165,7 @@ BOOL FASTCALL GetLayeredStatus(PWND pWnd);
/************** INPUT CONTEXT **************/
+PIMC FASTCALL UserCreateInputContext(ULONG_PTR dwClientImcData);
VOID UserFreeInputContext(PVOID Object);
BOOLEAN UserDestroyInputContext(PVOID Object);
PVOID AllocInputContextObject(PDESKTOP pDesk, PTHREADINFO pti, SIZE_T Size, PVOID*
HandleOwner);