server: Make timeout status for async I/O specifiable. Fix mailslots timeout handling.
This commit is contained in:
parent
3040e09ae3
commit
4e5c7038da
|
@ -299,7 +299,7 @@ static int mailslot_test(void)
|
||||||
ok( !ReadFile( hSlot, buffer, sizeof buffer, &count, NULL), "slot read\n");
|
ok( !ReadFile( hSlot, buffer, sizeof buffer, &count, NULL), "slot read\n");
|
||||||
ok( GetLastError() == ERROR_SEM_TIMEOUT, "wrong error %u\n", GetLastError() );
|
ok( GetLastError() == ERROR_SEM_TIMEOUT, "wrong error %u\n", GetLastError() );
|
||||||
dwTimeout = GetTickCount() - dwTimeout;
|
dwTimeout = GetTickCount() - dwTimeout;
|
||||||
todo_wine ok( dwTimeout >= 1000, "timeout too short %u\n", dwTimeout );
|
ok( dwTimeout >= 1000, "timeout too short %u\n", dwTimeout );
|
||||||
ok( CloseHandle( hSlot ), "closing the mailslot\n");
|
ok( CloseHandle( hSlot ), "closing the mailslot\n");
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
|
|
|
@ -38,6 +38,7 @@ struct async
|
||||||
struct thread *thread; /* owning thread */
|
struct thread *thread; /* owning thread */
|
||||||
struct list queue_entry; /* entry in file descriptor queue */
|
struct list queue_entry; /* entry in file descriptor queue */
|
||||||
struct timeout_user *timeout;
|
struct timeout_user *timeout;
|
||||||
|
unsigned int timeout_status; /* status to report upon timeout */
|
||||||
struct event *event;
|
struct event *event;
|
||||||
async_data_t data; /* data for async I/O call */
|
async_data_t data; /* data for async I/O call */
|
||||||
};
|
};
|
||||||
|
@ -149,7 +150,7 @@ static void async_timeout( void *private )
|
||||||
struct async *async = private;
|
struct async *async = private;
|
||||||
|
|
||||||
async->timeout = NULL;
|
async->timeout = NULL;
|
||||||
async_terminate( async, STATUS_TIMEOUT );
|
async_terminate( async, async->timeout_status );
|
||||||
}
|
}
|
||||||
|
|
||||||
/* create a new async queue for a given fd */
|
/* create a new async queue for a given fd */
|
||||||
|
@ -193,11 +194,12 @@ struct async *create_async( struct thread *thread, struct async_queue *queue, co
|
||||||
}
|
}
|
||||||
|
|
||||||
/* set the timeout of an async operation */
|
/* set the timeout of an async operation */
|
||||||
void async_set_timeout( struct async *async, const struct timeval *timeout )
|
void async_set_timeout( struct async *async, const struct timeval *timeout, unsigned int status )
|
||||||
{
|
{
|
||||||
if (async->timeout) remove_timeout_user( async->timeout );
|
if (async->timeout) remove_timeout_user( async->timeout );
|
||||||
if (timeout) async->timeout = add_timeout_user( timeout, async_timeout, async );
|
if (timeout) async->timeout = add_timeout_user( timeout, async_timeout, async );
|
||||||
else async->timeout = NULL;
|
else async->timeout = NULL;
|
||||||
|
async->timeout_status = status;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* store the result of the client-side async callback */
|
/* store the result of the client-side async callback */
|
||||||
|
|
|
@ -126,7 +126,8 @@ extern struct object *create_serial( struct fd *fd, unsigned int options );
|
||||||
extern struct async_queue *create_async_queue( struct fd *fd );
|
extern struct async_queue *create_async_queue( struct fd *fd );
|
||||||
extern struct async *create_async( struct thread *thread, struct async_queue *queue,
|
extern struct async *create_async( struct thread *thread, struct async_queue *queue,
|
||||||
const async_data_t *data );
|
const async_data_t *data );
|
||||||
extern void async_set_timeout( struct async *async, const struct timeval *timeout );
|
extern void async_set_timeout( struct async *async, const struct timeval *timeout,
|
||||||
|
unsigned int status );
|
||||||
extern void async_set_result( struct object *obj, unsigned int status );
|
extern void async_set_result( struct object *obj, unsigned int status );
|
||||||
extern int async_waiting( struct async_queue *queue );
|
extern int async_waiting( struct async_queue *queue );
|
||||||
extern void async_wake_up( struct async_queue *queue, unsigned int status );
|
extern void async_wake_up( struct async_queue *queue, unsigned int status );
|
||||||
|
|
|
@ -208,17 +208,6 @@ static void mailslot_dump( struct object *obj, int verbose )
|
||||||
mailslot->max_msgsize, mailslot->read_timeout );
|
mailslot->max_msgsize, mailslot->read_timeout );
|
||||||
}
|
}
|
||||||
|
|
||||||
static int mailslot_message_count(struct mailslot *mailslot)
|
|
||||||
{
|
|
||||||
struct pollfd pfd;
|
|
||||||
|
|
||||||
/* poll the socket to see if there's any messages */
|
|
||||||
pfd.fd = get_unix_fd( mailslot->fd );
|
|
||||||
pfd.events = POLLIN;
|
|
||||||
pfd.revents = 0;
|
|
||||||
return (poll( &pfd, 1, 0 ) == 1) ? 1 : 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
static enum server_fd_type mailslot_get_info( struct fd *fd, int *flags )
|
static enum server_fd_type mailslot_get_info( struct fd *fd, int *flags )
|
||||||
{
|
{
|
||||||
struct mailslot *mailslot = get_fd_user( fd );
|
struct mailslot *mailslot = get_fd_user( fd );
|
||||||
|
@ -286,20 +275,13 @@ static void mailslot_queue_async( struct fd *fd, const async_data_t *data, int t
|
||||||
|
|
||||||
assert(mailslot->obj.ops == &mailslot_ops);
|
assert(mailslot->obj.ops == &mailslot_ops);
|
||||||
|
|
||||||
if (list_empty( &mailslot->writers ) ||
|
|
||||||
!mailslot_message_count( mailslot ))
|
|
||||||
{
|
|
||||||
set_error(STATUS_IO_TIMEOUT);
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
if ((async = fd_queue_async( fd, data, type, count )))
|
if ((async = fd_queue_async( fd, data, type, count )))
|
||||||
{
|
{
|
||||||
if (mailslot->read_timeout != -1)
|
if (mailslot->read_timeout != -1)
|
||||||
{
|
{
|
||||||
struct timeval when = current_time;
|
struct timeval when = current_time;
|
||||||
add_timeout( &when, max(1,mailslot->read_timeout) );
|
add_timeout( &when, max(1,mailslot->read_timeout) );
|
||||||
async_set_timeout( async, &when );
|
async_set_timeout( async, &when, STATUS_IO_TIMEOUT );
|
||||||
}
|
}
|
||||||
release_object( async );
|
release_object( async );
|
||||||
set_error( STATUS_PENDING );
|
set_error( STATUS_PENDING );
|
||||||
|
|
|
@ -867,7 +867,7 @@ DECL_HANDLER(wait_named_pipe)
|
||||||
struct timeval when = current_time;
|
struct timeval when = current_time;
|
||||||
if (req->timeout == NMPWAIT_USE_DEFAULT_WAIT) add_timeout( &when, pipe->timeout );
|
if (req->timeout == NMPWAIT_USE_DEFAULT_WAIT) add_timeout( &when, pipe->timeout );
|
||||||
else add_timeout( &when, req->timeout );
|
else add_timeout( &when, req->timeout );
|
||||||
async_set_timeout( async, &when );
|
async_set_timeout( async, &when, STATUS_TIMEOUT );
|
||||||
}
|
}
|
||||||
release_object( async );
|
release_object( async );
|
||||||
set_error( STATUS_PENDING );
|
set_error( STATUS_PENDING );
|
||||||
|
|
|
@ -219,7 +219,7 @@ static void serial_queue_async( struct fd *fd, const async_data_t *data, int typ
|
||||||
{
|
{
|
||||||
struct timeval when = current_time;
|
struct timeval when = current_time;
|
||||||
add_timeout( &when, timeout );
|
add_timeout( &when, timeout );
|
||||||
async_set_timeout( async, &when );
|
async_set_timeout( async, &when, STATUS_TIMEOUT );
|
||||||
}
|
}
|
||||||
release_object( async );
|
release_object( async );
|
||||||
set_error( STATUS_PENDING );
|
set_error( STATUS_PENDING );
|
||||||
|
|
Loading…
Reference in New Issue