Skip to content
Snippets Groups Projects
Commit b58349e5 authored by Rémi Bernon's avatar Rémi Bernon :speech_balloon: Committed by Alexandre Julliard
Browse files

winex11: Route kernel callbacks through user32.

parent 7f09a97d
No related branches found
No related tags found
No related merge requests found
...@@ -25,23 +25,15 @@ ...@@ -25,23 +25,15 @@
HMODULE x11drv_module = 0; HMODULE x11drv_module = 0;
static const KERNEL_CALLBACK_PROC kernel_callbacks[] =
{
x11drv_dnd_enter_event,
x11drv_dnd_position_event,
x11drv_dnd_post_drop,
x11drv_dnd_drop_event,
x11drv_dnd_leave_event,
};
C_ASSERT( NtUserDriverCallbackFirst + ARRAYSIZE(kernel_callbacks) == client_func_last );
BOOL WINAPI DllMain( HINSTANCE instance, DWORD reason, void *reserved ) BOOL WINAPI DllMain( HINSTANCE instance, DWORD reason, void *reserved )
{ {
KERNEL_CALLBACK_PROC *callback_table;
struct init_params params = struct init_params params =
{ {
.dnd_enter_event_callback = (UINT_PTR)x11drv_dnd_enter_event,
.dnd_position_event_callback = (UINT_PTR)x11drv_dnd_position_event,
.dnd_post_drop_callback = (UINT_PTR)x11drv_dnd_post_drop,
.dnd_drop_event_callback = (UINT_PTR)x11drv_dnd_drop_event,
.dnd_leave_event_callback = (UINT_PTR)x11drv_dnd_leave_event,
.foreign_window_proc = (UINT_PTR)foreign_window_proc, .foreign_window_proc = (UINT_PTR)foreign_window_proc,
}; };
...@@ -52,8 +44,6 @@ BOOL WINAPI DllMain( HINSTANCE instance, DWORD reason, void *reserved ) ...@@ -52,8 +44,6 @@ BOOL WINAPI DllMain( HINSTANCE instance, DWORD reason, void *reserved )
if (__wine_init_unix_call()) return FALSE; if (__wine_init_unix_call()) return FALSE;
if (X11DRV_CALL( init, &params )) return FALSE; if (X11DRV_CALL( init, &params )) return FALSE;
callback_table = NtCurrentTeb()->Peb->KernelCallbackTable;
memcpy( callback_table + NtUserDriverCallbackFirst, kernel_callbacks, sizeof(kernel_callbacks) );
return TRUE; return TRUE;
} }
......
...@@ -1428,10 +1428,13 @@ static HWND find_drop_window( HWND hQueryWnd, LPPOINT lpPt ) ...@@ -1428,10 +1428,13 @@ static HWND find_drop_window( HWND hQueryWnd, LPPOINT lpPt )
static void post_drop( HWND hwnd, DROPFILES *drop, ULONG size ) static void post_drop( HWND hwnd, DROPFILES *drop, ULONG size )
{ {
struct dnd_post_drop_params *params; struct dnd_post_drop_params *params;
void *ret_ptr;
ULONG ret_len;
if (!(params = malloc( sizeof(*params) + size - sizeof(*drop) ))) return; if (!(params = malloc( sizeof(*params) + size - sizeof(*drop) ))) return;
memcpy( &params->drop, drop, size ); memcpy( &params->drop, drop, size );
params->drop.fWide = HandleToUlong( hwnd ); /* abuse fWide to pass window handle */ params->drop.fWide = HandleToUlong( hwnd ); /* abuse fWide to pass window handle */
x11drv_client_func( client_func_dnd_post_drop, params, size ); params->dispatch.callback = dnd_post_drop_callback;
KeUserDispatchCallback( &params->dispatch, size, &ret_ptr, &ret_len );
free( params ); free( params );
} }
...@@ -1698,8 +1701,11 @@ static void handle_xdnd_enter_event( HWND hWnd, XClientMessageEvent *event ) ...@@ -1698,8 +1701,11 @@ static void handle_xdnd_enter_event( HWND hWnd, XClientMessageEvent *event )
xdndtypes, count, &size ); xdndtypes, count, &size );
if (data && (params = malloc( sizeof(*params) + size ))) if (data && (params = malloc( sizeof(*params) + size )))
{ {
void *ret_ptr;
ULONG ret_len;
memcpy( params->entries, data, size ); memcpy( params->entries, data, size );
x11drv_client_func( client_func_dnd_enter_event, params, sizeof(*params) + size ); params->dispatch.callback = dnd_enter_event_callback;
KeUserDispatchCallback( &params->dispatch, sizeof(*params) + size, &ret_ptr, &ret_len );
free( params ); free( params );
} }
free( data ); free( data );
...@@ -1753,12 +1759,12 @@ static void handle_xdnd_position_event( HWND hwnd, XClientMessageEvent *event ) ...@@ -1753,12 +1759,12 @@ static void handle_xdnd_position_event( HWND hwnd, XClientMessageEvent *event )
ULONG ret_len; ULONG ret_len;
UINT effect; UINT effect;
params.dispatch.callback = dnd_position_event_callback;
params.hwnd = HandleToUlong( hwnd ); params.hwnd = HandleToUlong( hwnd );
params.point = root_to_virtual_screen( event->data.l[2] >> 16, event->data.l[2] & 0xFFFF ); params.point = root_to_virtual_screen( event->data.l[2] >> 16, event->data.l[2] & 0xFFFF );
params.effect = effect = xdnd_action_to_drop_effect( event->data.l[4] ); params.effect = effect = xdnd_action_to_drop_effect( event->data.l[4] );
if (KeUserModeCallback( client_func_dnd_position_event, &params, sizeof(params), if (KeUserDispatchCallback( &params.dispatch, sizeof(params), &ret_ptr, &ret_len ) || ret_len != sizeof(effect))
&ret_ptr, &ret_len ) || ret_len != sizeof(effect))
return; return;
effect = *(UINT *)ret_ptr; effect = *(UINT *)ret_ptr;
...@@ -1785,14 +1791,13 @@ static void handle_xdnd_position_event( HWND hwnd, XClientMessageEvent *event ) ...@@ -1785,14 +1791,13 @@ static void handle_xdnd_position_event( HWND hwnd, XClientMessageEvent *event )
static void handle_xdnd_drop_event( HWND hwnd, XClientMessageEvent *event ) static void handle_xdnd_drop_event( HWND hwnd, XClientMessageEvent *event )
{ {
struct dnd_drop_event_params params = {.hwnd = HandleToULong(hwnd)}; struct dnd_drop_event_params params = {.dispatch.callback = dnd_leave_event_callback, .hwnd = HandleToULong(hwnd)};
XClientMessageEvent e; XClientMessageEvent e;
void *ret_ptr; void *ret_ptr;
ULONG ret_len; ULONG ret_len;
UINT effect; UINT effect;
if (KeUserModeCallback( client_func_dnd_drop_event, &params, sizeof(params), if (KeUserDispatchCallback( &params.dispatch, sizeof(params), &ret_ptr, &ret_len ) || ret_len != sizeof(effect))
&ret_ptr, &ret_len ) || ret_len != sizeof(effect))
return; return;
effect = *(UINT *)ret_ptr; effect = *(UINT *)ret_ptr;
...@@ -1812,7 +1817,10 @@ static void handle_xdnd_drop_event( HWND hwnd, XClientMessageEvent *event ) ...@@ -1812,7 +1817,10 @@ static void handle_xdnd_drop_event( HWND hwnd, XClientMessageEvent *event )
static void handle_xdnd_leave_event( HWND hwnd, XClientMessageEvent *event ) static void handle_xdnd_leave_event( HWND hwnd, XClientMessageEvent *event )
{ {
x11drv_client_func( client_func_dnd_leave_event, NULL, 0 ); struct dispatch_callback_params params = {.callback = dnd_leave_event_callback};
void *ret_ptr;
ULONG ret_len;
KeUserDispatchCallback( &params, sizeof(params), &ret_ptr, &ret_len );
} }
......
...@@ -35,6 +35,11 @@ enum x11drv_funcs ...@@ -35,6 +35,11 @@ enum x11drv_funcs
/* x11drv_init params */ /* x11drv_init params */
struct init_params struct init_params
{ {
UINT64 dnd_enter_event_callback;
UINT64 dnd_position_event_callback;
UINT64 dnd_post_drop_callback;
UINT64 dnd_drop_event_callback;
UINT64 dnd_leave_event_callback;
UINT64 foreign_window_proc; UINT64 foreign_window_proc;
}; };
...@@ -53,20 +58,6 @@ struct xim_preedit_state_params ...@@ -53,20 +58,6 @@ struct xim_preedit_state_params
BOOL open; BOOL open;
}; };
/* driver client callbacks exposed with KernelCallbackTable interface */
enum x11drv_client_funcs
{
client_func_dnd_enter_event = NtUserDriverCallbackFirst,
client_func_dnd_position_event,
client_func_dnd_post_drop,
client_func_dnd_drop_event,
client_func_dnd_leave_event,
client_func_last
};
C_ASSERT( client_func_last <= NtUserDriverCallbackLast + 1 );
/* x11drv_dnd_enter_event params */
struct format_entry struct format_entry
{ {
UINT format; UINT format;
...@@ -77,7 +68,7 @@ struct format_entry ...@@ -77,7 +68,7 @@ struct format_entry
/* x11drv_dnd_enter_event params */ /* x11drv_dnd_enter_event params */
struct dnd_enter_event_params struct dnd_enter_event_params
{ {
int placeholder; struct dispatch_callback_params dispatch;
struct format_entry entries[]; struct format_entry entries[];
}; };
...@@ -86,6 +77,7 @@ C_ASSERT(sizeof(struct dnd_enter_event_params) == offsetof(struct dnd_enter_even ...@@ -86,6 +77,7 @@ C_ASSERT(sizeof(struct dnd_enter_event_params) == offsetof(struct dnd_enter_even
/* x11drv_dnd_position_event params */ /* x11drv_dnd_position_event params */
struct dnd_position_event_params struct dnd_position_event_params
{ {
struct dispatch_callback_params dispatch;
ULONG hwnd; ULONG hwnd;
POINT point; POINT point;
DWORD effect; DWORD effect;
...@@ -94,12 +86,15 @@ struct dnd_position_event_params ...@@ -94,12 +86,15 @@ struct dnd_position_event_params
/* x11drv_dnd_drop_event params */ /* x11drv_dnd_drop_event params */
struct dnd_drop_event_params struct dnd_drop_event_params
{ {
struct dispatch_callback_params dispatch;
ULONG hwnd; ULONG hwnd;
}; };
/* x11drv_dnd_post_drop params */ /* x11drv_dnd_post_drop params */
struct dnd_post_drop_params struct dnd_post_drop_params
{ {
struct dispatch_callback_params dispatch;
UINT32 __pad;
DROPFILES drop; DROPFILES drop;
char data[]; char data[];
}; };
......
...@@ -439,6 +439,11 @@ extern int xrender_error_base; ...@@ -439,6 +439,11 @@ extern int xrender_error_base;
extern char *process_name; extern char *process_name;
extern Display *clipboard_display; extern Display *clipboard_display;
extern UINT64 client_foreign_window_proc; extern UINT64 client_foreign_window_proc;
extern UINT64 dnd_enter_event_callback;
extern UINT64 dnd_position_event_callback;
extern UINT64 dnd_post_drop_callback;
extern UINT64 dnd_drop_event_callback;
extern UINT64 dnd_leave_event_callback;
/* atoms */ /* atoms */
...@@ -838,9 +843,6 @@ extern NTSTATUS x11drv_tablet_get_packet( void *arg ); ...@@ -838,9 +843,6 @@ extern NTSTATUS x11drv_tablet_get_packet( void *arg );
extern NTSTATUS x11drv_tablet_load_info( void *arg ); extern NTSTATUS x11drv_tablet_load_info( void *arg );
extern NTSTATUS x11drv_tablet_info( void *arg ); extern NTSTATUS x11drv_tablet_info( void *arg );
extern NTSTATUS x11drv_client_func( enum x11drv_client_funcs func, const void *params,
ULONG size );
/* GDI helpers */ /* GDI helpers */
static inline BOOL lp_to_dp( HDC hdc, POINT *points, INT count ) static inline BOOL lp_to_dp( HDC hdc, POINT *points, INT count )
......
...@@ -86,6 +86,11 @@ int alloc_system_colors = 256; ...@@ -86,6 +86,11 @@ int alloc_system_colors = 256;
int xrender_error_base = 0; int xrender_error_base = 0;
char *process_name = NULL; char *process_name = NULL;
UINT64 client_foreign_window_proc = 0; UINT64 client_foreign_window_proc = 0;
UINT64 dnd_enter_event_callback = 0;
UINT64 dnd_position_event_callback = 0;
UINT64 dnd_post_drop_callback = 0;
UINT64 dnd_drop_event_callback = 0;
UINT64 dnd_leave_event_callback = 0;
static x11drv_error_callback err_callback; /* current callback for error */ static x11drv_error_callback err_callback; /* current callback for error */
static Display *err_callback_display; /* display callback is set for */ static Display *err_callback_display; /* display callback is set for */
...@@ -643,6 +648,11 @@ static NTSTATUS x11drv_init( void *arg ) ...@@ -643,6 +648,11 @@ static NTSTATUS x11drv_init( void *arg )
if (!XInitThreads()) ERR( "XInitThreads failed, trouble ahead\n" ); if (!XInitThreads()) ERR( "XInitThreads failed, trouble ahead\n" );
if (!(display = XOpenDisplay( NULL ))) return STATUS_UNSUCCESSFUL; if (!(display = XOpenDisplay( NULL ))) return STATUS_UNSUCCESSFUL;
dnd_enter_event_callback = params->dnd_enter_event_callback;
dnd_position_event_callback = params->dnd_position_event_callback;
dnd_post_drop_callback = params->dnd_post_drop_callback;
dnd_drop_event_callback = params->dnd_drop_event_callback;
dnd_leave_event_callback = params->dnd_leave_event_callback;
client_foreign_window_proc = params->foreign_window_proc; client_foreign_window_proc = params->foreign_window_proc;
fcntl( ConnectionNumber(display), F_SETFD, 1 ); /* set close on exec flag */ fcntl( ConnectionNumber(display), F_SETFD, 1 ); /* set close on exec flag */
...@@ -801,14 +811,6 @@ BOOL X11DRV_SystemParametersInfo( UINT action, UINT int_param, void *ptr_param, ...@@ -801,14 +811,6 @@ BOOL X11DRV_SystemParametersInfo( UINT action, UINT int_param, void *ptr_param,
return FALSE; /* let user32 handle it */ return FALSE; /* let user32 handle it */
} }
NTSTATUS x11drv_client_func( enum x11drv_client_funcs id, const void *params, ULONG size )
{
void *ret_ptr;
ULONG ret_len;
return KeUserModeCallback( id, params, size, &ret_ptr, &ret_len );
}
const unixlib_entry_t __wine_unix_call_funcs[] = const unixlib_entry_t __wine_unix_call_funcs[] =
{ {
x11drv_init, x11drv_init,
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment