This changes the todos in the tests as it fixes the thread input not being attached, but then exposes a different todo.
As an alternative version of https://gitlab.winehq.org/wine/wine/-/merge_requests/5066/diffs?commit_id=f5... (hopefully better but I have no clue?)
-- v2: server: Use the startup info to connect the process winstation.
From: Rémi Bernon rbernon@codeweavers.com
This changes the todos in the tests as it fixes the thread input not being attached, but then exposes a different todo. --- dlls/dinput/tests/joystick8.c | 23 +++++++++-------------- dlls/user32/tests/input.c | 8 ++++---- server/process.c | 6 ++++-- server/user.h | 5 +++-- server/winstation.c | 27 +++++++++++++++++++++++++-- 5 files changed, 45 insertions(+), 24 deletions(-)
diff --git a/dlls/dinput/tests/joystick8.c b/dlls/dinput/tests/joystick8.c index 0553cb96a63..428fc59c1af 100644 --- a/dlls/dinput/tests/joystick8.c +++ b/dlls/dinput/tests/joystick8.c @@ -5756,23 +5756,23 @@ static DWORD WINAPI test_rawinput_desktop_thread( void *args ) rawbuffer_size = sizeof(rawbuffer); memset( rawbuffer, 0, sizeof(rawbuffer) ); res = msg_wait_for_events( 1, &rawinput_event, 100 ); - todo_wine + todo_wine_if( params->input ) ok( res == 0, "WaitForSingleObject returned %#lx\n", res ); - todo_wine + todo_wine_if( params->input ) ok( rawinput_calls == 1, "got %u WM_INPUT messages\n", rawinput_calls );
rawinput = (RAWINPUT *)rawbuffer; - todo_wine + todo_wine_if( params->input ) ok( rawinput->header.dwType == RIM_TYPEHID, "got dwType %lu\n", rawinput->header.dwType ); - todo_wine + todo_wine_if( params->input ) ok( rawinput->header.dwSize == offsetof(RAWINPUT, data.hid.bRawData[desc.caps.InputReportByteLength * rawinput->data.hid.dwCount]), "got header.dwSize %lu\n", rawinput->header.dwSize ); - todo_wine + todo_wine_if( params->input ) ok( rawinput->header.hDevice != 0, "got hDevice %p\n", rawinput->header.hDevice ); ok( rawinput->header.wParam == 0, "got wParam %#Ix\n", rawinput->header.wParam ); - todo_wine + todo_wine_if( params->input ) ok( rawinput->data.hid.dwSizeHid == desc.caps.InputReportByteLength, "got dwSizeHid %lu\n", rawinput->data.hid.dwSizeHid ); - todo_wine + todo_wine_if( params->input ) ok( rawinput->data.hid.dwCount >= 1, "got dwCount %lu\n", rawinput->data.hid.dwCount );
@@ -5864,28 +5864,23 @@ static void test_rawinput_desktop( const char *path, BOOL input ) res = msg_wait_for_events( 1, &rawinput_event, 100 ); if (input) { - todo_wine ok( res == 0, "WaitForSingleObject returned %#lx\n", res ); - todo_wine ok( rawinput_calls == 1, "got %u WM_INPUT messages\n", rawinput_calls );
rawinput = (RAWINPUT *)rawbuffer; - todo_wine ok( rawinput->header.dwType == RIM_TYPEHID, "got dwType %lu\n", rawinput->header.dwType ); - todo_wine ok( rawinput->header.dwSize == offsetof(RAWINPUT, data.hid.bRawData[desc.caps.InputReportByteLength * rawinput->data.hid.dwCount]), "got header.dwSize %lu\n", rawinput->header.dwSize ); - todo_wine ok( rawinput->header.hDevice != 0, "got hDevice %p\n", rawinput->header.hDevice ); ok( rawinput->header.wParam == 0, "got wParam %#Ix\n", rawinput->header.wParam ); - todo_wine ok( rawinput->data.hid.dwSizeHid == desc.caps.InputReportByteLength, "got dwSizeHid %lu\n", rawinput->data.hid.dwSizeHid ); - todo_wine ok( rawinput->data.hid.dwCount >= 1, "got dwCount %lu\n", rawinput->data.hid.dwCount ); } else { + todo_wine ok( res == WAIT_TIMEOUT, "WaitForSingleObject returned %#lx\n", res ); + todo_wine ok( rawinput_calls == 0, "got %u WM_INPUT messages\n", rawinput_calls ); }
diff --git a/dlls/user32/tests/input.c b/dlls/user32/tests/input.c index be95bd150b4..a78ea3b7c43 100644 --- a/dlls/user32/tests/input.c +++ b/dlls/user32/tests/input.c @@ -3855,19 +3855,19 @@ static void test_SendInput_mouse_messages(void) ok_ne( NULL, thread, HANDLE, "%p" );
ok_ret( 0, WaitForSingleObject( params.start_event, 5000 ) ); - todo_wine ok_ret( 1, AttachThreadInput( thread_id, GetCurrentThreadId(), TRUE ) ); + ok_ret( 1, AttachThreadInput( thread_id, GetCurrentThreadId(), TRUE ) ); ok_ret( 0, SendMessageW( params.hwnd, WM_USER, 0, 0 ) );
mouse_event( MOUSEEVENTF_LEFTDOWN, 0, 0, 0, 0 ); wait_messages( 5, FALSE ); - button_down_hwnd[1].message.hwnd = hwnd; - ok_seq( button_down_hwnd ); + button_down_hwnd_todo[1].message.hwnd = hwnd; + ok_seq( button_down_hwnd_todo ); mouse_event( MOUSEEVENTF_LEFTUP, 0, 0, 0, 0 ); wait_messages( 5, FALSE ); button_up_hwnd[1].message.hwnd = hwnd; ok_seq( button_up_hwnd );
- todo_wine ok_ret( 1, AttachThreadInput( thread_id, GetCurrentThreadId(), FALSE ) ); + ok_ret( 1, AttachThreadInput( thread_id, GetCurrentThreadId(), FALSE ) ); ok_ret( 1, SetEvent( params.end_event ) ); ok_ret( 0, WaitForSingleObject( thread, 5000 ) ); ok_ret( 1, CloseHandle( thread ) ); diff --git a/server/process.c b/server/process.c index 3651696f505..b6c21d15752 100644 --- a/server/process.c +++ b/server/process.c @@ -1133,7 +1133,7 @@ DECL_HANDLER(new_process) { struct startup_info *info; const void *info_ptr; - struct unicode_str name; + struct unicode_str name, desktop_path = {0}; const struct security_descriptor *sd; const struct object_attributes *objattr = get_req_object_attributes( &sd, &name, NULL ); struct process *process = NULL; @@ -1276,7 +1276,9 @@ DECL_HANDLER(new_process) FIXUP_LEN( info->data->imagepath_len ); FIXUP_LEN( info->data->cmdline_len ); FIXUP_LEN( info->data->title_len ); + desktop_path.str = (WCHAR *)((char *)info->data + pos); FIXUP_LEN( info->data->desktop_len ); + desktop_path.len = info->data->desktop_len; FIXUP_LEN( info->data->shellinfo_len ); FIXUP_LEN( info->data->runtime_len ); #undef FIXUP_LEN @@ -1327,7 +1329,7 @@ DECL_HANDLER(new_process) }
/* connect to the window station */ - connect_process_winstation( process, parent_thread, parent ); + connect_process_winstation( process, &desktop_path, parent_thread, parent );
/* inherit the process console, but keep pseudo handles (< 0), and 0 (= not attached to a console) as is */ if ((int)info->data->console > 0) diff --git a/server/user.h b/server/user.h index 8fa55e09b0f..bc58c93200d 100644 --- a/server/user.h +++ b/server/user.h @@ -22,6 +22,7 @@ #define __WINE_SERVER_USER_H
#include "wine/server_protocol.h" +#include "unicode.h"
struct thread; struct region; @@ -186,8 +187,8 @@ extern client_ptr_t get_class_client_ptr( struct window_class *class ); extern struct desktop *get_desktop_obj( struct process *process, obj_handle_t handle, unsigned int access ); extern struct winstation *get_process_winstation( struct process *process, unsigned int access ); extern struct desktop *get_thread_desktop( struct thread *thread, unsigned int access ); -extern void connect_process_winstation( struct process *process, struct thread *parent_thread, - struct process *parent_process ); +extern void connect_process_winstation( struct process *process, struct unicode_str *desktop_path, + struct thread *parent_thread, struct process *parent_process ); extern void set_process_default_desktop( struct process *process, struct desktop *desktop, obj_handle_t handle ); extern void close_process_desktop( struct process *process ); diff --git a/server/winstation.c b/server/winstation.c index 930c5c90d97..5715cb16ccc 100644 --- a/server/winstation.c +++ b/server/winstation.c @@ -373,18 +373,37 @@ void set_process_default_desktop( struct process *process, struct desktop *deskt }
/* connect a process to its window station */ -void connect_process_winstation( struct process *process, struct thread *parent_thread, - struct process *parent_process ) +void connect_process_winstation( struct process *process, struct unicode_str *desktop_path, + struct thread *parent_thread, struct process *parent_process ) { + struct unicode_str desktop_name = *desktop_path, winstation_name = {0}; + const int attributes = OBJ_CASE_INSENSITIVE | OBJ_OPENIF; struct winstation *winstation = NULL; struct desktop *desktop = NULL; obj_handle_t handle; + data_size_t pos; + + for (pos = 0; pos < desktop_name.len; pos++) + { + if (desktop_name.str[pos] == '\') + { + winstation_name.str = desktop_name.str; + winstation_name.len = pos; + desktop_name.str += pos + 1; + desktop_name.len -= pos + 1; + break; + } + }
/* check for an inherited winstation handle (don't ask...) */ if ((handle = find_inherited_handle( process, &winstation_ops ))) { winstation = (struct winstation *)get_handle_obj( process, handle, 0, &winstation_ops ); } + else if (winstation_name.len && (winstation = open_named_object( NULL, &winstation_ops, &winstation_name, attributes ))) + { + handle = alloc_handle( process, winstation, STANDARD_RIGHTS_REQUIRED | WINSTA_ALL_ACCESS, 0 ); + } else if (parent_process->winstation) { handle = duplicate_handle( parent_process, parent_process->winstation, @@ -399,6 +418,10 @@ void connect_process_winstation( struct process *process, struct thread *parent_ desktop = get_desktop_obj( process, handle, 0 ); if (!desktop || desktop->winstation != winstation) goto done; } + else if (desktop_name.len && (desktop = open_named_object( &winstation->obj, &desktop_ops, &desktop_name, attributes ))) + { + handle = alloc_handle( process, desktop, STANDARD_RIGHTS_REQUIRED | DESKTOP_ALL_ACCESS, 0 ); + } else { if (parent_thread && parent_thread->desktop)
Hi,
It looks like your patch introduced the new failures shown below. Please investigate and fix them before resubmitting your patch. If they are not new, fixing them anyway would help a lot. Otherwise please ask for the known failures list to be updated.
The tests also ran into some preexisting test failures. If you know how to fix them that would be helpful. See the TestBot job for the details:
The full results can be found at: https://testbot.winehq.org/JobDetails.pl?Key=143307
Your paranoid android.
=== debian11 (32 bit ja:JP report) ===
user32: input.c:3864: Test succeeded inside todo block: button_down_hwnd_todo 1: got MSG_TEST_WIN hwnd 0007004A, msg WM_LBUTTONDOWN, wparam 0x1, lparam 0x320032
=== debian11b (32 bit WoW report) ===
user32: input.c:3864: Test succeeded inside todo block: button_down_hwnd_todo 1: got MSG_TEST_WIN hwnd 00040096, msg WM_LBUTTONDOWN, wparam 0x1, lparam 0x320032
v2: Adjust dinput tests todos as well.
Unrelated Linux test failures in oleaut32:varformat. Unrelated Windows test failure in user32:sysparams.
Alexandre Julliard (@julliard) commented about server/winstation.c:
struct winstation *winstation = NULL; struct desktop *desktop = NULL; obj_handle_t handle;
- data_size_t pos;
- for (pos = 0; pos < desktop_name.len; pos++)
- {
if (desktop_name.str[pos] == '\\')
{
winstation_name.str = desktop_name.str;
winstation_name.len = pos;
desktop_name.str += pos + 1;
desktop_name.len -= pos + 1;
break;
}
- }
unicode_str lengths are in bytes, not WCHARs (same as UNICODE_STRING).