rpcrt4: Add close_read implementation for named pipe connections.

Signed-off-by: Jacek Caban <jacek@codeweavers.com>
Signed-off-by: Alexandre Julliard <julliard@winehq.org>
This commit is contained in:
Jacek Caban 2017-05-24 13:52:14 +02:00 committed by Alexandre Julliard
parent 42ba4d731a
commit 29f0b28240
1 changed files with 18 additions and 5 deletions

View File

@ -69,6 +69,7 @@ typedef struct _RpcConnection_np
HANDLE listen_event; HANDLE listen_event;
IO_STATUS_BLOCK io_status; IO_STATUS_BLOCK io_status;
HANDLE event_cache; HANDLE event_cache;
BOOL read_closed;
} RpcConnection_np; } RpcConnection_np;
static RpcConnection *rpcrt4_conn_np_alloc(void) static RpcConnection *rpcrt4_conn_np_alloc(void)
@ -384,7 +385,6 @@ static RPC_STATUS rpcrt4_ncalrpc_handoff(RpcConnection *old_conn, RpcConnection
static int rpcrt4_conn_np_read(RpcConnection *conn, void *buffer, unsigned int count) static int rpcrt4_conn_np_read(RpcConnection *conn, void *buffer, unsigned int count)
{ {
RpcConnection_np *connection = (RpcConnection_np *) conn; RpcConnection_np *connection = (RpcConnection_np *) conn;
IO_STATUS_BLOCK io_status;
HANDLE event; HANDLE event;
NTSTATUS status; NTSTATUS status;
@ -392,14 +392,23 @@ static int rpcrt4_conn_np_read(RpcConnection *conn, void *buffer, unsigned int c
if (!event) if (!event)
return -1; return -1;
status = NtReadFile(connection->pipe, event, NULL, NULL, &io_status, buffer, count, NULL, NULL); if (connection->read_closed)
status = STATUS_CANCELLED;
else
status = NtReadFile(connection->pipe, event, NULL, NULL, &connection->io_status, buffer, count, NULL, NULL);
if (status == STATUS_PENDING) if (status == STATUS_PENDING)
{ {
/* check read_closed again before waiting to avoid a race */
if (connection->read_closed)
{
IO_STATUS_BLOCK io_status;
NtCancelIoFileEx(connection->pipe, &connection->io_status, &io_status);
}
WaitForSingleObject(event, INFINITE); WaitForSingleObject(event, INFINITE);
status = io_status.Status; status = connection->io_status.Status;
} }
release_np_event(connection, event); release_np_event(connection, event);
return status && status != STATUS_BUFFER_OVERFLOW ? -1 : io_status.Information; return status && status != STATUS_BUFFER_OVERFLOW ? -1 : connection->io_status.Information;
} }
static int rpcrt4_conn_np_write(RpcConnection *conn, const void *buffer, unsigned int count) static int rpcrt4_conn_np_write(RpcConnection *conn, const void *buffer, unsigned int count)
@ -451,7 +460,11 @@ static int rpcrt4_conn_np_close(RpcConnection *conn)
static void rpcrt4_conn_np_close_read(RpcConnection *conn) static void rpcrt4_conn_np_close_read(RpcConnection *conn)
{ {
/* FIXME */ RpcConnection_np *connection = (RpcConnection_np*)conn;
IO_STATUS_BLOCK io_status;
connection->read_closed = TRUE;
NtCancelIoFileEx(connection->pipe, &connection->io_status, &io_status);
} }
static void rpcrt4_conn_np_cancel_call(RpcConnection *conn) static void rpcrt4_conn_np_cancel_call(RpcConnection *conn)