[Top][All Lists]
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
Re: [Qemu-devel] [PATCH v2 1/3] net: asynchronous send/receive infrastru
From: |
ronnie sahlberg |
Subject: |
Re: [Qemu-devel] [PATCH v2 1/3] net: asynchronous send/receive infrastructure for net/socket.c |
Date: |
Wed, 22 Aug 2012 02:39:05 +1000 |
In
net_socket_update_fd_handler()
shouldnt you call qemu_notify_event() if any of the handlers have
changed from NULL to non-NULL ?
or else it might take a while before the change takes effect.
regards
ronnie sahlberg
On Wed, Aug 22, 2012 at 1:52 AM, Stefan Hajnoczi
<address@hidden> wrote:
> The net/socket.c net client is not truly asynchronous. This patch
> borrows the qemu_set_fd_handler2() code from net/tap.c as the basis for
> proper asynchronous send/receive.
>
> Only read packets from the socket when the peer is able to receive.
> This avoids needless queuing.
>
> Later patches implement asynchronous send.
>
> Signed-off-by: Stefan Hajnoczi <address@hidden>
> ---
> net/socket.c | 58
> ++++++++++++++++++++++++++++++++++++++++++++++++++++------
> 1 file changed, 52 insertions(+), 6 deletions(-)
>
> diff --git a/net/socket.c b/net/socket.c
> index c172c24..54e32f0 100644
> --- a/net/socket.c
> +++ b/net/socket.c
> @@ -42,9 +42,51 @@ typedef struct NetSocketState {
> unsigned int packet_len;
> uint8_t buf[4096];
> struct sockaddr_in dgram_dst; /* contains inet host and port destination
> iff connectionless (SOCK_DGRAM) */
> + IOHandler *send_fn; /* differs between SOCK_STREAM/SOCK_DGRAM
> */
> + bool read_poll; /* waiting to receive data? */
> + bool write_poll; /* waiting to transmit data? */
> } NetSocketState;
>
> static void net_socket_accept(void *opaque);
> +static void net_socket_writable(void *opaque);
> +
> +/* Only read packets from socket when peer can receive them */
> +static int net_socket_can_send(void *opaque)
> +{
> + NetSocketState *s = opaque;
> +
> + return qemu_can_send_packet(&s->nc);
> +}
> +
> +static void net_socket_update_fd_handler(NetSocketState *s)
> +{
> + qemu_set_fd_handler2(s->fd,
> + s->read_poll ? net_socket_can_send : NULL,
> + s->read_poll ? s->send_fn : NULL,
> + s->write_poll ? net_socket_writable : NULL,
> + s);
> +}
> +
> +static void net_socket_read_poll(NetSocketState *s, bool enable)
> +{
> + s->read_poll = enable;
> + net_socket_update_fd_handler(s);
> +}
> +
> +static void net_socket_write_poll(NetSocketState *s, bool enable)
> +{
> + s->write_poll = enable;
> + net_socket_update_fd_handler(s);
> +}
> +
> +static void net_socket_writable(void *opaque)
> +{
> + NetSocketState *s = opaque;
> +
> + net_socket_write_poll(s, false);
> +
> + qemu_flush_queued_packets(&s->nc);
> +}
>
> /* XXX: we consider we can send the whole packet without blocking */
> static ssize_t net_socket_receive(NetClientState *nc, const uint8_t *buf,
> size_t size)
> @@ -81,7 +123,8 @@ static void net_socket_send(void *opaque)
> } else if (size == 0) {
> /* end of connection */
> eoc:
> - qemu_set_fd_handler(s->fd, NULL, NULL, NULL);
> + net_socket_read_poll(s, false);
> + net_socket_write_poll(s, false);
> if (s->listen_fd != -1) {
> qemu_set_fd_handler(s->listen_fd, net_socket_accept, NULL, s);
> }
> @@ -152,7 +195,8 @@ static void net_socket_send_dgram(void *opaque)
> return;
> if (size == 0) {
> /* end of connection */
> - qemu_set_fd_handler(s->fd, NULL, NULL, NULL);
> + net_socket_read_poll(s, false);
> + net_socket_write_poll(s, false);
> return;
> }
> qemu_send_packet(&s->nc, s->buf, size);
> @@ -243,7 +287,8 @@ static void net_socket_cleanup(NetClientState *nc)
> {
> NetSocketState *s = DO_UPCAST(NetSocketState, nc, nc);
> if (s->fd != -1) {
> - qemu_set_fd_handler(s->fd, NULL, NULL, NULL);
> + net_socket_read_poll(s, false);
> + net_socket_write_poll(s, false);
> close(s->fd);
> s->fd = -1;
> }
> @@ -314,8 +359,8 @@ static NetSocketState
> *net_socket_fd_init_dgram(NetClientState *peer,
>
> s->fd = fd;
> s->listen_fd = -1;
> -
> - qemu_set_fd_handler(s->fd, net_socket_send_dgram, NULL, s);
> + s->send_fn = net_socket_send_dgram;
> + net_socket_read_poll(s, true);
>
> /* mcast: save bound address as dst */
> if (is_connected) {
> @@ -332,7 +377,8 @@ err:
> static void net_socket_connect(void *opaque)
> {
> NetSocketState *s = opaque;
> - qemu_set_fd_handler(s->fd, net_socket_send, NULL, s);
> + s->send_fn = net_socket_send;
> + net_socket_read_poll(s, true);
> }
>
> static NetClientInfo net_socket_info = {
> --
> 1.7.10.4
>
>
[Qemu-devel] [PATCH v2 2/3] net: EAGAIN handling for net/socket.c UDP, Stefan Hajnoczi, 2012/08/21
[Qemu-devel] [PATCH v2 3/3] net: EAGAIN handling for net/socket.c TCP, Stefan Hajnoczi, 2012/08/21
Re: [Qemu-devel] [PATCH v2 0/3] net: asynchronous send/receive for net/socket.c, Stefan Hajnoczi, 2012/08/29