Rémi Bernon (@rbernon) commented about dlls/win32u/message.c:
+#define BTN_MASK (MOUSEEVENTF_LEFTDOWN|MOUSEEVENTF_LEFTUP|MOUSEEVENTF_RIGHTDOWN|MOUSEEVENTF_RIGHTUP| \ + MOUSEEVENTF_MIDDLEDOWN|MOUSEEVENTF_MIDDLEUP|MOUSEEVENTF_XDOWN|MOUSEEVENTF_XUP) + if (input->type == INPUT_KEYBOARD || + (input->type == INPUT_MOUSE && 0 != (input->mi.dwFlags & BTN_MASK))) + { + /* always invalidate cross-thread key caches after sending key-related input; + cache data from reply is only fresh if no other threads also incremented */ + if ((ULONG)InterlockedIncrement(&global_key_state_counter) == counter+1) + ++counter; + } +#undef BTN_MASK if (key_state_info) { key_state_info->time = NtGetTickCount(); key_state_info->counter = counter; } IIUC the problem is coming from one thread having a more up to date key state cache than the other because it received the X input and called `send_hardware_message`? And I understand this is caused by this part here, so what about instead:
1) Remove this optimization (as well as the key state buffer returned from `send_hardware_message` request), 2) Always invalidate the keystate for all threads by incrementing `global_key_state_counter` unconditionally in `case INPUT_KEYBOARD:` and `if (input->mi.dwFlags & ~(MOUSEEVENTF_ABSOLUTE | MOUSEEVENTF_MOVE))` in `case INPUT_MOUSE:`? -- https://gitlab.winehq.org/wine/wine/-/merge_requests/2153#note_25787