Commit 15b8f91e authored by Zebediah Figura's avatar Zebediah Figura Committed by Alexandre Julliard

server: Check the status code to determine whether the async has failed.

Instead of manually specifying success or failure. Based on test_return_status() in ntoskrnl. The changes in this patch don't affect device IRPs, but the tests show the heuristic that Windows uses, and in practice it turns out to be correct for all known asyncs. Signed-off-by: 's avatarZebediah Figura <zfigura@codeweavers.com> Signed-off-by: 's avatarAlexandre Julliard <julliard@winehq.org>
parent 285700a5
......@@ -1934,8 +1934,8 @@ static void test_ip_pktinfo(void)
todo_wine ok(WSAGetLastError() == ERROR_IO_PENDING, "got error %u\n", WSAGetLastError());
rc = SleepEx(1000, TRUE);
todo_wine ok(rc == WAIT_IO_COMPLETION, "got %d\n", rc);
todo_wine ok(got_ip_pktinfo_apc == 1, "apc was called %u times\n", got_ip_pktinfo_apc);
ok(rc == WAIT_IO_COMPLETION, "got %d\n", rc);
ok(got_ip_pktinfo_apc == 1, "apc was called %u times\n", got_ip_pktinfo_apc);
ok(hdr.dwFlags == MSG_CTRUNC, "got flags %#x\n", hdr.dwFlags);
got_ip_pktinfo_apc = 0;
......
......@@ -296,7 +296,7 @@ void set_async_pending( struct async *async, int signal )
}
/* return async object status and wait handle to client */
obj_handle_t async_handoff( struct async *async, int success, data_size_t *result, int force_blocking )
obj_handle_t async_handoff( struct async *async, data_size_t *result, int force_blocking )
{
if (async->unknown_status)
{
......@@ -305,7 +305,7 @@ obj_handle_t async_handoff( struct async *async, int success, data_size_t *resul
return async->wait_handle;
}
if (!success)
if (!async->pending && NT_ERROR( get_error() ))
{
close_handle( async->thread->process, async->wait_handle );
async->wait_handle = 0;
......
......@@ -2692,7 +2692,8 @@ DECL_HANDLER(flush)
if ((async = create_request_async( fd, fd->comp_flags, &req->async )))
{
reply->event = async_handoff( async, fd->fd_ops->flush( fd, async ), NULL, 1 );
fd->fd_ops->flush( fd, async );
reply->event = async_handoff( async, NULL, 1 );
release_object( async );
}
release_object( fd );
......@@ -2720,7 +2721,8 @@ DECL_HANDLER(get_volume_info)
if ((async = create_request_async( fd, fd->comp_flags, &req->async )))
{
reply->wait = async_handoff( async, fd->fd_ops->get_volume_info( fd, async, req->info_class ), NULL, 1 );
fd->fd_ops->get_volume_info( fd, async, req->info_class );
reply->wait = async_handoff( async, NULL, 1 );
release_object( async );
}
release_object( fd );
......@@ -2795,7 +2797,8 @@ DECL_HANDLER(read)
if ((async = create_request_async( fd, fd->comp_flags, &req->async )))
{
reply->wait = async_handoff( async, fd->fd_ops->read( fd, async, req->pos ), NULL, 0 );
fd->fd_ops->read( fd, async, req->pos );
reply->wait = async_handoff( async, NULL, 0 );
reply->options = fd->options;
release_object( async );
}
......@@ -2812,7 +2815,8 @@ DECL_HANDLER(write)
if ((async = create_request_async( fd, fd->comp_flags, &req->async )))
{
reply->wait = async_handoff( async, fd->fd_ops->write( fd, async, req->pos ), &reply->size, 0 );
fd->fd_ops->write( fd, async, req->pos );
reply->wait = async_handoff( async, &reply->size, 0 );
reply->options = fd->options;
release_object( async );
}
......@@ -2830,7 +2834,8 @@ DECL_HANDLER(ioctl)
if ((async = create_request_async( fd, fd->comp_flags, &req->async )))
{
reply->wait = async_handoff( async, fd->fd_ops->ioctl( fd, req->code, async ), NULL, 0 );
fd->fd_ops->ioctl( fd, req->code, async );
reply->wait = async_handoff( async, NULL, 0 );
reply->options = fd->options;
release_object( async );
}
......
......@@ -219,7 +219,7 @@ typedef void (*async_completion_callback)( void *private );
extern void free_async_queue( struct async_queue *queue );
extern struct async *create_async( struct fd *fd, struct thread *thread, const async_data_t *data, struct iosb *iosb );
extern struct async *create_request_async( struct fd *fd, unsigned int comp_flags, const async_data_t *data );
extern obj_handle_t async_handoff( struct async *async, int success, data_size_t *result, int force_blocking );
extern obj_handle_t async_handoff( struct async *async, data_size_t *result, int force_blocking );
extern void queue_async( struct async_queue *queue, struct async *async );
extern void async_set_timeout( struct async *async, timeout_t timeout, unsigned int status );
extern void async_set_result( struct object *obj, unsigned int status, apc_param_t total );
......
......@@ -2839,8 +2839,8 @@ static int poll_single_socket( struct sock *sock, int mask )
return get_poll_flags( sock, pollfd.revents ) & mask;
}
static int poll_socket( struct sock *poll_sock, struct async *async, timeout_t timeout,
unsigned int count, const struct poll_socket_input *input )
static void poll_socket( struct sock *poll_sock, struct async *async, timeout_t timeout,
unsigned int count, const struct poll_socket_input *input )
{
struct poll_socket_output *output;
BOOL signaled = FALSE;
......@@ -2848,13 +2848,13 @@ static int poll_socket( struct sock *poll_sock, struct async *async, timeout_t t
unsigned int i, j;
if (!(output = mem_alloc( count * sizeof(*output) )))
return 0;
return;
memset( output, 0, count * sizeof(*output) );
if (!(req = mem_alloc( offsetof( struct poll_req, sockets[count] ) )))
{
free( output );
return 0;
return;
}
req->timeout = NULL;
......@@ -2863,7 +2863,7 @@ static int poll_socket( struct sock *poll_sock, struct async *async, timeout_t t
{
free( req );
free( output );
return 0;
return;
}
for (i = 0; i < count; ++i)
......@@ -2875,7 +2875,7 @@ static int poll_socket( struct sock *poll_sock, struct async *async, timeout_t t
if (req->timeout) remove_timeout_user( req->timeout );
free( req );
free( output );
return 0;
return;
}
req->sockets[i].flags = input[i].flags;
}
......@@ -2917,7 +2917,6 @@ static int poll_socket( struct sock *poll_sock, struct async *async, timeout_t t
for (i = 0; i < req->count; ++i)
sock_reselect( req->sockets[i].sock );
set_error( STATUS_PENDING );
return 1;
}
#ifdef HAVE_LINUX_RTNETLINK_H
......@@ -3249,18 +3248,11 @@ DECL_HANDLER(recv_socket)
if ((async = create_request_async( fd, get_fd_comp_flags( fd ), &req->async )))
{
int success = 0;
if (status == STATUS_SUCCESS)
{
struct iosb *iosb = async_get_iosb( async );
iosb->result = req->total;
release_object( iosb );
success = 1;
}
else if (status == STATUS_PENDING)
{
success = 1;
}
set_error( status );
......@@ -3273,7 +3265,7 @@ DECL_HANDLER(recv_socket)
/* always reselect; we changed reported_events above */
sock_reselect( sock );
reply->wait = async_handoff( async, success, NULL, 0 );
reply->wait = async_handoff( async, NULL, 0 );
reply->options = get_fd_options( fd );
release_object( async );
}
......@@ -3293,7 +3285,8 @@ DECL_HANDLER(poll_socket)
if ((async = create_request_async( sock->fd, get_fd_comp_flags( sock->fd ), &req->async )))
{
reply->wait = async_handoff( async, poll_socket( sock, async, req->timeout, count, input ), NULL, 0 );
poll_socket( sock, async, req->timeout, count, input );
reply->wait = async_handoff( async, NULL, 0 );
reply->options = get_fd_options( sock->fd );
release_object( async );
}
......@@ -3357,18 +3350,11 @@ DECL_HANDLER(send_socket)
if ((async = create_request_async( fd, get_fd_comp_flags( fd ), &req->async )))
{
int success = 0;
if (status == STATUS_SUCCESS)
{
struct iosb *iosb = async_get_iosb( async );
iosb->result = req->total;
release_object( iosb );
success = 1;
}
else if (status == STATUS_PENDING)
{
success = 1;
}
set_error( status );
......@@ -3381,7 +3367,7 @@ DECL_HANDLER(send_socket)
/* always reselect; we changed reported_events above */
sock_reselect( sock );
reply->wait = async_handoff( async, success, NULL, 0 );
reply->wait = async_handoff( async, NULL, 0 );
reply->options = get_fd_options( fd );
release_object( async );
}
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment