Jacek Caban : server: Introduce server-side I/O mode for named pipes.
Alexandre Julliard
julliard at winehq.org
Mon Mar 20 17:16:47 CDT 2017
Module: wine
Branch: master
Commit: a8023d300cd9bb99a99d29a44c02e586d10756b4
URL: http://source.winehq.org/git/wine.git/?a=commit;h=a8023d300cd9bb99a99d29a44c02e586d10756b4
Author: Jacek Caban <jacek at codeweavers.com>
Date: Wed Mar 15 23:25:38 2017 +0100
server: Introduce server-side I/O mode for named pipes.
Signed-off-by: Jacek Caban <jacek at codeweavers.com>
Signed-off-by: Alexandre Julliard <julliard at winehq.org>
---
server/named_pipe.c | 45 +++++++++++++++++++++++++++++++++++----------
1 file changed, 35 insertions(+), 10 deletions(-)
diff --git a/server/named_pipe.c b/server/named_pipe.c
index a75f70b..0f6cf3d 100644
--- a/server/named_pipe.c
+++ b/server/named_pipe.c
@@ -277,6 +277,12 @@ static const struct fd_ops named_pipe_device_fd_ops =
default_fd_reselect_async /* reselect_async */
};
+/* Returns if we handle I/O via server calls. Currently disabled. */
+static int use_server_io( struct pipe_end *pipe_end )
+{
+ return 0; /* FIXME */
+}
+
static void named_pipe_dump( struct object *obj, int verbose )
{
fputs( "Named pipe\n", stderr );
@@ -394,7 +400,8 @@ static void do_disconnect( struct pipe_server *server )
server->client->pipe_end.fd = NULL;
}
assert( server->pipe_end.fd );
- shutdown( get_unix_fd( server->pipe_end.fd ), SHUT_RDWR );
+ if (!use_server_io( &server->pipe_end ))
+ shutdown( get_unix_fd( server->pipe_end.fd ), SHUT_RDWR );
release_object( server->pipe_end.fd );
server->pipe_end.fd = NULL;
}
@@ -539,6 +546,9 @@ static int pipe_data_remaining( struct pipe_server *server )
assert( server->client );
+ if (use_server_io( &server->pipe_end ))
+ return 0;
+
fd = get_unix_fd( server->client->pipe_end.fd );
if (fd < 0)
return 0;
@@ -590,7 +600,7 @@ static obj_handle_t pipe_server_flush( struct fd *fd, struct async *async, int b
handle = pipe_end_flush( &server->pipe_end, async, blocking );
/* there's no unix way to be alerted when a pipe becomes empty, so resort to polling */
- if (handle && !server->flush_poll)
+ if (handle && !use_server_io( &server->pipe_end ) && !server->flush_poll)
server->flush_poll = add_timeout_user( -TICKS_PER_SEC / 10, check_flushed, server );
return handle;
}
@@ -806,7 +816,22 @@ static struct object *named_pipe_open_file( struct object *obj, unsigned int acc
if ((client = create_pipe_client( options, pipe->flags, pipe->outsize )))
{
- if (!socketpair( PF_UNIX, SOCK_STREAM, 0, fds ))
+ if (use_server_io( &server->pipe_end ))
+ {
+ client->pipe_end.fd = alloc_pseudo_fd( &pipe_client_fd_ops, &client->pipe_end.obj, options );
+ if (client->pipe_end.fd)
+ {
+ set_fd_signaled( client->pipe_end.fd, 1 );
+ server->pipe_end.fd = (struct fd *)grab_object( server->ioctl_fd );
+ set_no_fd_status( server->ioctl_fd, STATUS_BAD_DEVICE_TYPE );
+ }
+ else
+ {
+ release_object( client );
+ client = NULL;
+ }
+ }
+ else if (!socketpair( PF_UNIX, SOCK_STREAM, 0, fds ))
{
assert( !server->pipe_end.fd );
@@ -831,14 +856,7 @@ static struct object *named_pipe_open_file( struct object *obj, unsigned int acc
server->pipe_end.fd = create_anonymous_fd( &pipe_server_fd_ops, fds[0], &server->pipe_end.obj, server->options );
if (client->pipe_end.fd && server->pipe_end.fd)
{
- allow_fd_caching( client->pipe_end.fd );
- allow_fd_caching( server->pipe_end.fd );
fd_copy_completion( server->ioctl_fd, server->pipe_end.fd );
- if (server->state == ps_wait_open)
- fd_async_wake_up( server->ioctl_fd, ASYNC_TYPE_WAIT, STATUS_SUCCESS );
- set_server_state( server, ps_connected_server );
- server->client = client;
- client->server = server;
}
else
{
@@ -854,6 +872,13 @@ static struct object *named_pipe_open_file( struct object *obj, unsigned int acc
}
if (client)
{
+ allow_fd_caching( client->pipe_end.fd );
+ allow_fd_caching( server->pipe_end.fd );
+ if (server->state == ps_wait_open)
+ fd_async_wake_up( server->ioctl_fd, ASYNC_TYPE_WAIT, STATUS_SUCCESS );
+ set_server_state( server, ps_connected_server );
+ server->client = client;
+ client->server = server;
server->pipe_end.connection = &client->pipe_end;
client->pipe_end.connection = &server->pipe_end;
}
More information about the wine-cvs
mailing list