[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: [PATCH v12 15/17] net: stream: move to QIO to enable additional parameters



On Thu, Oct 20, 2022 at 03:09:10PM +0200, Philippe Mathieu-Daudé wrote:
> On 20/10/22 11:16, Laurent Vivier wrote:
> > Use QIOChannel, QIOChannelSocket and QIONetListener.
> > This allows net/stream to use all the available parameters provided by
> > SocketAddress.
> > 
> > Signed-off-by: Laurent Vivier <lvivier@xxxxxxxxxx>
> > Acked-by: Michael S. Tsirkin <mst@xxxxxxxxxx>
> > ---
> >   meson           |   2 +-
> >   net/stream.c    | 493 +++++++++++++++++-------------------------------
> >   qemu-options.hx |   4 +-
> >   3 files changed, 180 insertions(+), 319 deletions(-)
> 
> >   static int net_stream_server_init(NetClientState *peer,
> > @@ -283,105 +287,61 @@ static int net_stream_server_init(NetClientState 
> > *peer,
> >   {
> >       NetClientState *nc;
> >       NetStreamState *s;
> > -    int fd, ret;
> > -
> > -    switch (addr->type) {
> > -    case SOCKET_ADDRESS_TYPE_INET: {
> > -        struct sockaddr_in saddr_in;
> > -
> > -        if (convert_host_port(&saddr_in, addr->u.inet.host, 
> > addr->u.inet.port,
> > -                              errp) < 0) {
> > -            return -1;
> > -        }
> > +    QIOChannelSocket *listen_sioc = qio_channel_socket_new();
> > -        fd = qemu_socket(PF_INET, SOCK_STREAM, 0);
> > -        if (fd < 0) {
> > -            error_setg_errno(errp, errno, "can't create stream socket");
> > -            return -1;
> > -        }
> > -        qemu_socket_set_nonblock(fd);
> > +    nc = qemu_new_net_client(&net_stream_info, peer, model, name);
> > +    s = DO_UPCAST(NetStreamState, nc, nc);
> > -        socket_set_fast_reuse(fd);
> > +    s->listen_ioc = QIO_CHANNEL(listen_sioc);
> > +    qio_channel_socket_listen_async(listen_sioc, addr, 0,
> > +                                    net_stream_server_listening, s,
> > +                                    NULL, NULL);
> > -        ret = bind(fd, (struct sockaddr *)&saddr_in, sizeof(saddr_in));
> > -        if (ret < 0) {
> > -            error_setg_errno(errp, errno, "can't bind ip=%s to socket",
> > -                             inet_ntoa(saddr_in.sin_addr));
> > -            closesocket(fd);
> > -            return -1;
> > -        }
> > -        break;
> > -    }
> > -    case SOCKET_ADDRESS_TYPE_UNIX: {
> > -        struct sockaddr_un saddr_un;
> > -
> > -        ret = unlink(addr->u.q_unix.path);
> > -        if (ret < 0 && errno != ENOENT) {
> > -            error_setg_errno(errp, errno, "failed to unlink socket %s",
> > -                             addr->u.q_unix.path);
> > -            return -1;
> > -        }
> > +    return 0;
> > +}
> > -        saddr_un.sun_family = PF_UNIX;
> > -        ret = snprintf(saddr_un.sun_path, sizeof(saddr_un.sun_path), "%s",
> > -                       addr->u.q_unix.path);
> > -        if (ret < 0 || ret >= sizeof(saddr_un.sun_path)) {
> > -            error_setg(errp, "UNIX socket path '%s' is too long",
> > -                       addr->u.q_unix.path);
> > -            error_append_hint(errp, "Path must be less than %zu bytes\n",
> > -                              sizeof(saddr_un.sun_path));
> > -            return -1;
> > -        }
> > +static void net_stream_client_connected(QIOTask *task, gpointer opaque)
> > +{
> > +    NetStreamState *s = opaque;
> > +    QIOChannelSocket *sioc = QIO_CHANNEL_SOCKET(s->ioc);
> > +    SocketAddress *addr;
> > +    gchar *uri;
> > +    int ret;
> > -        fd = qemu_socket(PF_UNIX, SOCK_STREAM, 0);
> > -        if (fd < 0) {
> > -            error_setg_errno(errp, errno, "can't create stream socket");
> > -            return -1;
> > -        }
> > -        qemu_socket_set_nonblock(fd);
> > -
> > -        ret = bind(fd, (struct sockaddr *)&saddr_un, sizeof(saddr_un));
> > -        if (ret < 0) {
> > -            error_setg_errno(errp, errno, "can't create socket with path: 
> > %s",
> > -                             saddr_un.sun_path);
> > -            closesocket(fd);
> > -            return -1;
> > -        }
> > -        break;
> > -    }
> > -    case SOCKET_ADDRESS_TYPE_FD:
> > -        fd = monitor_fd_param(monitor_cur(), addr->u.fd.str, errp);
> > -        if (fd == -1) {
> > -            return -1;
> > -        }
> > -        ret = qemu_socket_try_set_nonblock(fd);
> > -        if (ret < 0) {
> > -            error_setg_errno(errp, -ret, "%s: Can't use file descriptor 
> > %d",
> > -                             name, fd);
> > -            return -1;
> > -        }
> > -        break;
> > -    default:
> > -        error_setg(errp, "only support inet or fd type");
> > -        return -1;
> > +    if (sioc->fd < 0) {
> > +        qemu_set_info_str(&s->nc, "connection error");
> > +        goto error;
> >       }
> > -    ret = listen(fd, 0);
> > -    if (ret < 0) {
> > -        error_setg_errno(errp, errno, "can't listen on socket");
> > -        closesocket(fd);
> > -        return -1;
> > +    addr = qio_channel_socket_get_remote_address(sioc, NULL);
> > +    g_assert(addr != NULL);
> 
> Please use:
> 
>        addr = qio_channel_socket_get_remote_address(sioc, &error_fatal);

Just 'err' instead of '&error_fatal', and return - to the caller.
This is code where we need to propagate back to the caller, not
abort the running QEMU when hotplugging a NIC backend.

With regards,
Daniel
-- 
|: https://berrange.com      -o-    https://www.flickr.com/photos/dberrange :|
|: https://libvirt.org         -o-            https://fstop138.berrange.com :|
|: https://entangle-photo.org    -o-    https://www.instagram.com/dberrange :|




 


Rackspace

Lists.xenproject.org is hosted with RackSpace, monitoring our
servers 24x7x365 and backed by RackSpace's Fanatical Support®.