Skip to content
Projects
Groups
Snippets
Help
This project
Loading...
Sign in / Register
Toggle navigation
W
wine-winehq
Project
Project
Details
Activity
Cycle Analytics
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
Issues
0
Issues
0
List
Board
Labels
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Charts
Registry
Registry
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Charts
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
wine
wine-winehq
Commits
b724024d
Commit
b724024d
authored
May 28, 2019
by
Jacek Caban
Committed by
Alexandre Julliard
May 28, 2019
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
server: Notify kernel when IRP is terminated by server.
Signed-off-by:
Jacek Caban
<
jacek@codeweavers.com
>
Signed-off-by:
Alexandre Julliard
<
julliard@winehq.org
>
parent
dc5421f9
Hide whitespace changes
Inline
Side-by-side
Showing
5 changed files
with
82 additions
and
6 deletions
+82
-6
ntoskrnl.c
dlls/ntoskrnl.exe/ntoskrnl.c
+11
-1
server_protocol.h
include/wine/server_protocol.h
+9
-2
device.c
server/device.c
+49
-2
protocol.def
server/protocol.def
+8
-1
trace.c
server/trace.c
+5
-0
No files found.
dlls/ntoskrnl.exe/ntoskrnl.c
View file @
b724024d
...
...
@@ -838,6 +838,15 @@ static NTSTATUS dispatch_free( struct dispatch_context *context )
return
STATUS_SUCCESS
;
}
static
NTSTATUS
dispatch_cancel
(
struct
dispatch_context
*
context
)
{
IRP
*
irp
=
wine_server_get_ptr
(
context
->
params
.
cancel
.
irp
);
FIXME
(
"%p
\n
"
,
irp
);
return
STATUS_SUCCESS
;
}
typedef
NTSTATUS
(
*
dispatch_func
)(
struct
dispatch_context
*
context
);
static
const
dispatch_func
dispatch_funcs
[]
=
...
...
@@ -849,7 +858,8 @@ static const dispatch_func dispatch_funcs[] =
dispatch_write
,
/* IRP_CALL_WRITE */
dispatch_flush
,
/* IRP_CALL_FLUSH */
dispatch_ioctl
,
/* IRP_CALL_IOCTL */
dispatch_free
/* IRP_CALL_FREE */
dispatch_free
,
/* IRP_CALL_FREE */
dispatch_cancel
/* IRP_CALL_CANCEL */
};
/* helper function to update service status */
...
...
include/wine/server_protocol.h
View file @
b724024d
...
...
@@ -649,7 +649,8 @@ enum irp_type
IRP_CALL_WRITE
,
IRP_CALL_FLUSH
,
IRP_CALL_IOCTL
,
IRP_CALL_FREE
IRP_CALL_FREE
,
IRP_CALL_CANCEL
};
typedef
union
...
...
@@ -706,6 +707,12 @@ typedef union
int
__pad
;
client_ptr_t
obj
;
}
free
;
struct
{
enum
irp_type
type
;
int
__pad
;
client_ptr_t
irp
;
}
cancel
;
}
irp_params_t
;
...
...
@@ -6695,6 +6702,6 @@ union generic_reply
struct
resume_process_reply
resume_process_reply
;
};
#define SERVER_PROTOCOL_VERSION 58
4
#define SERVER_PROTOCOL_VERSION 58
5
#endif
/* __WINE_WINE_SERVER_PROTOCOL_H */
server/device.c
View file @
b724024d
...
...
@@ -52,6 +52,7 @@ struct irp_call
struct
async
*
async
;
/* pending async op */
irp_params_t
params
;
/* irp parameters */
struct
iosb
*
iosb
;
/* I/O status block */
int
canceled
;
/* the call was canceled */
client_ptr_t
user_ptr
;
/* client side pointer */
};
...
...
@@ -188,6 +189,7 @@ static int device_file_read( struct fd *fd, struct async *async, file_pos_t pos
static
int
device_file_write
(
struct
fd
*
fd
,
struct
async
*
async
,
file_pos_t
pos
);
static
int
device_file_flush
(
struct
fd
*
fd
,
struct
async
*
async
);
static
int
device_file_ioctl
(
struct
fd
*
fd
,
ioctl_code_t
code
,
struct
async
*
async
);
static
void
device_file_reselect_async
(
struct
fd
*
fd
,
struct
async_queue
*
queue
);
static
const
struct
object_ops
device_file_ops
=
{
...
...
@@ -224,7 +226,7 @@ static const struct fd_ops device_file_fd_ops =
no_fd_get_volume_info
,
/* get_volume_info */
device_file_ioctl
,
/* ioctl */
default_fd_queue_async
,
/* queue_async */
de
fault_fd_reselect_async
/* reselect_async */
de
vice_file_reselect_async
/* reselect_async */
};
...
...
@@ -352,6 +354,7 @@ static struct irp_call *create_irp( struct device_file *file, const irp_params_t
irp
->
async
=
NULL
;
irp
->
params
=
*
params
;
irp
->
iosb
=
NULL
;
irp
->
canceled
=
0
;
irp
->
user_ptr
=
0
;
if
(
async
)
irp
->
iosb
=
async_get_iosb
(
async
);
...
...
@@ -548,6 +551,7 @@ static int fill_irp_params( struct device_manager *manager, struct irp_call *irp
{
case
IRP_CALL_NONE
:
case
IRP_CALL_FREE
:
case
IRP_CALL_CANCEL
:
break
;
case
IRP_CALL_CREATE
:
irp
->
params
.
create
.
file
=
alloc_handle
(
current
->
process
,
irp
->
file
,
...
...
@@ -653,6 +657,40 @@ static int device_file_ioctl( struct fd *fd, ioctl_code_t code, struct async *as
return
queue_irp
(
file
,
&
params
,
async
);
}
static
void
cancel_irp_call
(
struct
irp_call
*
irp
)
{
struct
irp_call
*
cancel_irp
;
irp_params_t
params
;
irp
->
canceled
=
1
;
if
(
!
irp
->
user_ptr
||
!
irp
->
file
||
!
irp
->
file
->
device
->
manager
)
return
;
memset
(
&
params
,
0
,
sizeof
(
params
)
);
params
.
cancel
.
type
=
IRP_CALL_CANCEL
;
params
.
cancel
.
irp
=
irp
->
user_ptr
;
if
((
cancel_irp
=
create_irp
(
NULL
,
&
params
,
NULL
)))
{
add_irp_to_queue
(
irp
->
file
->
device
->
manager
,
cancel_irp
,
NULL
);
release_object
(
cancel_irp
);
}
set_irp_result
(
irp
,
STATUS_CANCELLED
,
NULL
,
0
,
0
);
}
static
void
device_file_reselect_async
(
struct
fd
*
fd
,
struct
async_queue
*
queue
)
{
struct
device_file
*
file
=
get_fd_user
(
fd
);
struct
irp_call
*
irp
;
LIST_FOR_EACH_ENTRY
(
irp
,
&
file
->
requests
,
struct
irp_call
,
dev_entry
)
if
(
irp
->
iosb
->
status
!=
STATUS_PENDING
)
{
cancel_irp_call
(
irp
);
return
;
}
}
static
struct
device
*
create_device
(
struct
object
*
root
,
const
struct
unicode_str
*
name
,
struct
device_manager
*
manager
)
{
...
...
@@ -897,6 +935,10 @@ DECL_HANDLER(get_next_device_request)
if
(
req
->
status
)
set_irp_result
(
irp
,
req
->
status
,
NULL
,
0
,
0
);
if
(
irp
->
canceled
)
/* if it was canceled during dispatch, we couldn't queue cancel call without client pointer,
* so we need to do it now */
cancel_irp_call
(
irp
);
else
if
(
irp
->
async
)
set_async_pending
(
irp
->
async
,
irp
->
file
&&
is_fd_overlapped
(
irp
->
file
->
fd
)
);
...
...
@@ -947,7 +989,12 @@ DECL_HANDLER(set_irp_result)
if
((
irp
=
(
struct
irp_call
*
)
get_handle_obj
(
current
->
process
,
req
->
handle
,
0
,
&
irp_call_ops
)))
{
set_irp_result
(
irp
,
req
->
status
,
get_req_data
(),
get_req_data_size
(),
req
->
size
);
if
(
!
irp
->
canceled
)
set_irp_result
(
irp
,
req
->
status
,
get_req_data
(),
get_req_data_size
(),
req
->
size
);
else
if
(
irp
->
user_ptr
)
/* cancel already queued */
set_error
(
STATUS_MORE_PROCESSING_REQUIRED
);
else
/* we may be still dispatching the IRP. don't bother queuing cancel if it's already complete */
irp
->
canceled
=
0
;
close_handle
(
current
->
process
,
req
->
handle
);
/* avoid an extra round-trip for close */
release_object
(
irp
);
}
...
...
server/protocol.def
View file @
b724024d
...
...
@@ -665,7 +665,8 @@ enum irp_type
IRP_CALL_WRITE,
IRP_CALL_FLUSH,
IRP_CALL_IOCTL,
IRP_CALL_FREE
IRP_CALL_FREE,
IRP_CALL_CANCEL
};
typedef union
...
...
@@ -722,6 +723,12 @@ typedef union
int __pad;
client_ptr_t obj; /* opaque ptr for the freed object */
} free;
struct
{
enum irp_type type; /* IRP_CALL_CANCEL */
int __pad;
client_ptr_t irp; /* opaque ptr for canceled irp */
} cancel;
} irp_params_t;
/* information about a PE image mapping, roughly equivalent to SECTION_IMAGE_INFORMATION */
...
...
server/trace.c
View file @
b724024d
...
...
@@ -363,6 +363,11 @@ static void dump_irp_params( const char *prefix, const irp_params_t *data )
dump_uint64
(
",obj="
,
&
data
->
free
.
obj
);
fputc
(
'}'
,
stderr
);
break
;
case
IRP_CALL_CANCEL
:
fprintf
(
stderr
,
"%s{CANCEL"
,
prefix
);
dump_uint64
(
",irp="
,
&
data
->
cancel
.
irp
);
fputc
(
'}'
,
stderr
);
break
;
}
}
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment