xref: /openbmc/qemu/net/socket.c (revision 9edc6313da34699ebd2bae4573ea22339b26450a)
1  /*
2   * QEMU System Emulator
3   *
4   * Copyright (c) 2003-2008 Fabrice Bellard
5   *
6   * Permission is hereby granted, free of charge, to any person obtaining a copy
7   * of this software and associated documentation files (the "Software"), to deal
8   * in the Software without restriction, including without limitation the rights
9   * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
10   * copies of the Software, and to permit persons to whom the Software is
11   * furnished to do so, subject to the following conditions:
12   *
13   * The above copyright notice and this permission notice shall be included in
14   * all copies or substantial portions of the Software.
15   *
16   * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
17   * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
18   * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
19   * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
20   * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
21   * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
22   * THE SOFTWARE.
23   */
24  #include "qemu/osdep.h"
25  
26  #include "net/net.h"
27  #include "clients.h"
28  #include "monitor/monitor.h"
29  #include "qapi/error.h"
30  #include "qemu-common.h"
31  #include "qemu/error-report.h"
32  #include "qemu/option.h"
33  #include "qemu/sockets.h"
34  #include "qemu/iov.h"
35  #include "qemu/main-loop.h"
36  
37  typedef struct NetSocketState {
38      NetClientState nc;
39      int listen_fd;
40      int fd;
41      SocketReadState rs;
42      unsigned int send_index;      /* number of bytes sent (only SOCK_STREAM) */
43      struct sockaddr_in dgram_dst; /* contains inet host and port destination iff connectionless (SOCK_DGRAM) */
44      IOHandler *send_fn;           /* differs between SOCK_STREAM/SOCK_DGRAM */
45      bool read_poll;               /* waiting to receive data? */
46      bool write_poll;              /* waiting to transmit data? */
47  } NetSocketState;
48  
49  static void net_socket_accept(void *opaque);
50  static void net_socket_writable(void *opaque);
51  
52  static void net_socket_update_fd_handler(NetSocketState *s)
53  {
54      qemu_set_fd_handler(s->fd,
55                          s->read_poll ? s->send_fn : NULL,
56                          s->write_poll ? net_socket_writable : NULL,
57                          s);
58  }
59  
60  static void net_socket_read_poll(NetSocketState *s, bool enable)
61  {
62      s->read_poll = enable;
63      net_socket_update_fd_handler(s);
64  }
65  
66  static void net_socket_write_poll(NetSocketState *s, bool enable)
67  {
68      s->write_poll = enable;
69      net_socket_update_fd_handler(s);
70  }
71  
72  static void net_socket_writable(void *opaque)
73  {
74      NetSocketState *s = opaque;
75  
76      net_socket_write_poll(s, false);
77  
78      qemu_flush_queued_packets(&s->nc);
79  }
80  
81  static ssize_t net_socket_receive(NetClientState *nc, const uint8_t *buf, size_t size)
82  {
83      NetSocketState *s = DO_UPCAST(NetSocketState, nc, nc);
84      uint32_t len = htonl(size);
85      struct iovec iov[] = {
86          {
87              .iov_base = &len,
88              .iov_len  = sizeof(len),
89          }, {
90              .iov_base = (void *)buf,
91              .iov_len  = size,
92          },
93      };
94      size_t remaining;
95      ssize_t ret;
96  
97      remaining = iov_size(iov, 2) - s->send_index;
98      ret = iov_send(s->fd, iov, 2, s->send_index, remaining);
99  
100      if (ret == -1 && errno == EAGAIN) {
101          ret = 0; /* handled further down */
102      }
103      if (ret == -1) {
104          s->send_index = 0;
105          return -errno;
106      }
107      if (ret < (ssize_t)remaining) {
108          s->send_index += ret;
109          net_socket_write_poll(s, true);
110          return 0;
111      }
112      s->send_index = 0;
113      return size;
114  }
115  
116  static ssize_t net_socket_receive_dgram(NetClientState *nc, const uint8_t *buf, size_t size)
117  {
118      NetSocketState *s = DO_UPCAST(NetSocketState, nc, nc);
119      ssize_t ret;
120  
121      do {
122          if (s->dgram_dst.sin_family != AF_UNIX) {
123              ret = sendto(s->fd, buf, size, 0,
124                           (struct sockaddr *)&s->dgram_dst,
125                           sizeof(s->dgram_dst));
126          } else {
127              ret = send(s->fd, buf, size, 0);
128          }
129      } while (ret == -1 && errno == EINTR);
130  
131      if (ret == -1 && errno == EAGAIN) {
132          net_socket_write_poll(s, true);
133          return 0;
134      }
135      return ret;
136  }
137  
138  static void net_socket_send_completed(NetClientState *nc, ssize_t len)
139  {
140      NetSocketState *s = DO_UPCAST(NetSocketState, nc, nc);
141  
142      if (!s->read_poll) {
143          net_socket_read_poll(s, true);
144      }
145  }
146  
147  static void net_socket_rs_finalize(SocketReadState *rs)
148  {
149      NetSocketState *s = container_of(rs, NetSocketState, rs);
150  
151      if (qemu_send_packet_async(&s->nc, rs->buf,
152                                 rs->packet_len,
153                                 net_socket_send_completed) == 0) {
154          net_socket_read_poll(s, false);
155      }
156  }
157  
158  static void net_socket_send(void *opaque)
159  {
160      NetSocketState *s = opaque;
161      int size;
162      int ret;
163      uint8_t buf1[NET_BUFSIZE];
164      const uint8_t *buf;
165  
166      size = recv(s->fd, buf1, sizeof(buf1), 0);
167      if (size < 0) {
168          if (errno != EWOULDBLOCK)
169              goto eoc;
170      } else if (size == 0) {
171          /* end of connection */
172      eoc:
173          net_socket_read_poll(s, false);
174          net_socket_write_poll(s, false);
175          if (s->listen_fd != -1) {
176              qemu_set_fd_handler(s->listen_fd, net_socket_accept, NULL, s);
177          }
178          closesocket(s->fd);
179  
180          s->fd = -1;
181          net_socket_rs_init(&s->rs, net_socket_rs_finalize, false);
182          s->nc.link_down = true;
183          memset(s->nc.info_str, 0, sizeof(s->nc.info_str));
184  
185          return;
186      }
187      buf = buf1;
188  
189      ret = net_fill_rstate(&s->rs, buf, size);
190  
191      if (ret == -1) {
192          goto eoc;
193      }
194  }
195  
196  static void net_socket_send_dgram(void *opaque)
197  {
198      NetSocketState *s = opaque;
199      int size;
200  
201      size = recv(s->fd, s->rs.buf, sizeof(s->rs.buf), 0);
202      if (size < 0)
203          return;
204      if (size == 0) {
205          /* end of connection */
206          net_socket_read_poll(s, false);
207          net_socket_write_poll(s, false);
208          return;
209      }
210      if (qemu_send_packet_async(&s->nc, s->rs.buf, size,
211                                 net_socket_send_completed) == 0) {
212          net_socket_read_poll(s, false);
213      }
214  }
215  
216  static int net_socket_mcast_create(struct sockaddr_in *mcastaddr,
217                                     struct in_addr *localaddr,
218                                     Error **errp)
219  {
220      struct ip_mreq imr;
221      int fd;
222      int val, ret;
223  #ifdef __OpenBSD__
224      unsigned char loop;
225  #else
226      int loop;
227  #endif
228  
229      if (!IN_MULTICAST(ntohl(mcastaddr->sin_addr.s_addr))) {
230          error_setg(errp, "specified mcastaddr %s (0x%08x) "
231                     "does not contain a multicast address",
232                     inet_ntoa(mcastaddr->sin_addr),
233                     (int)ntohl(mcastaddr->sin_addr.s_addr));
234          return -1;
235      }
236  
237      fd = qemu_socket(PF_INET, SOCK_DGRAM, 0);
238      if (fd < 0) {
239          error_setg_errno(errp, errno, "can't create datagram socket");
240          return -1;
241      }
242  
243      /* Allow multiple sockets to bind the same multicast ip and port by setting
244       * SO_REUSEADDR. This is the only situation where SO_REUSEADDR should be set
245       * on windows. Use socket_set_fast_reuse otherwise as it sets SO_REUSEADDR
246       * only on posix systems.
247       */
248      val = 1;
249      ret = setsockopt(fd, SOL_SOCKET, SO_REUSEADDR, &val, sizeof(val));
250      if (ret < 0) {
251          error_setg_errno(errp, errno,
252                           "can't set socket option SO_REUSEADDR");
253          goto fail;
254      }
255  
256      ret = bind(fd, (struct sockaddr *)mcastaddr, sizeof(*mcastaddr));
257      if (ret < 0) {
258          error_setg_errno(errp, errno, "can't bind ip=%s to socket",
259                           inet_ntoa(mcastaddr->sin_addr));
260          goto fail;
261      }
262  
263      /* Add host to multicast group */
264      imr.imr_multiaddr = mcastaddr->sin_addr;
265      if (localaddr) {
266          imr.imr_interface = *localaddr;
267      } else {
268          imr.imr_interface.s_addr = htonl(INADDR_ANY);
269      }
270  
271      ret = setsockopt(fd, IPPROTO_IP, IP_ADD_MEMBERSHIP,
272                       &imr, sizeof(struct ip_mreq));
273      if (ret < 0) {
274          error_setg_errno(errp, errno,
275                           "can't add socket to multicast group %s",
276                           inet_ntoa(imr.imr_multiaddr));
277          goto fail;
278      }
279  
280      /* Force mcast msgs to loopback (eg. several QEMUs in same host */
281      loop = 1;
282      ret = setsockopt(fd, IPPROTO_IP, IP_MULTICAST_LOOP,
283                       &loop, sizeof(loop));
284      if (ret < 0) {
285          error_setg_errno(errp, errno,
286                           "can't force multicast message to loopback");
287          goto fail;
288      }
289  
290      /* If a bind address is given, only send packets from that address */
291      if (localaddr != NULL) {
292          ret = setsockopt(fd, IPPROTO_IP, IP_MULTICAST_IF,
293                           localaddr, sizeof(*localaddr));
294          if (ret < 0) {
295              error_setg_errno(errp, errno,
296                               "can't set the default network send interface");
297              goto fail;
298          }
299      }
300  
301      qemu_set_nonblock(fd);
302      return fd;
303  fail:
304      if (fd >= 0)
305          closesocket(fd);
306      return -1;
307  }
308  
309  static void net_socket_cleanup(NetClientState *nc)
310  {
311      NetSocketState *s = DO_UPCAST(NetSocketState, nc, nc);
312      if (s->fd != -1) {
313          net_socket_read_poll(s, false);
314          net_socket_write_poll(s, false);
315          close(s->fd);
316          s->fd = -1;
317      }
318      if (s->listen_fd != -1) {
319          qemu_set_fd_handler(s->listen_fd, NULL, NULL, NULL);
320          closesocket(s->listen_fd);
321          s->listen_fd = -1;
322      }
323  }
324  
325  static NetClientInfo net_dgram_socket_info = {
326      .type = NET_CLIENT_DRIVER_SOCKET,
327      .size = sizeof(NetSocketState),
328      .receive = net_socket_receive_dgram,
329      .cleanup = net_socket_cleanup,
330  };
331  
332  static NetSocketState *net_socket_fd_init_dgram(NetClientState *peer,
333                                                  const char *model,
334                                                  const char *name,
335                                                  int fd, int is_connected,
336                                                  const char *mcast,
337                                                  Error **errp)
338  {
339      struct sockaddr_in saddr;
340      int newfd;
341      NetClientState *nc;
342      NetSocketState *s;
343      SocketAddress *sa;
344      SocketAddressType sa_type;
345  
346      sa = socket_local_address(fd, errp);
347      if (!sa) {
348          return NULL;
349      }
350      sa_type = sa->type;
351      qapi_free_SocketAddress(sa);
352  
353      /* fd passed: multicast: "learn" dgram_dst address from bound address and save it
354       * Because this may be "shared" socket from a "master" process, datagrams would be recv()
355       * by ONLY ONE process: we must "clone" this dgram socket --jjo
356       */
357  
358      if (is_connected && mcast != NULL) {
359              if (parse_host_port(&saddr, mcast, errp) < 0) {
360                  goto err;
361              }
362              /* must be bound */
363              if (saddr.sin_addr.s_addr == 0) {
364                  error_setg(errp, "can't setup multicast destination address");
365                  goto err;
366              }
367              /* clone dgram socket */
368              newfd = net_socket_mcast_create(&saddr, NULL, errp);
369              if (newfd < 0) {
370                  goto err;
371              }
372              /* clone newfd to fd, close newfd */
373              dup2(newfd, fd);
374              close(newfd);
375  
376      }
377  
378      nc = qemu_new_net_client(&net_dgram_socket_info, peer, model, name);
379  
380      s = DO_UPCAST(NetSocketState, nc, nc);
381  
382      s->fd = fd;
383      s->listen_fd = -1;
384      s->send_fn = net_socket_send_dgram;
385      net_socket_rs_init(&s->rs, net_socket_rs_finalize, false);
386      net_socket_read_poll(s, true);
387  
388      /* mcast: save bound address as dst */
389      if (is_connected && mcast != NULL) {
390          s->dgram_dst = saddr;
391          snprintf(nc->info_str, sizeof(nc->info_str),
392                   "socket: fd=%d (cloned mcast=%s:%d)",
393                   fd, inet_ntoa(saddr.sin_addr), ntohs(saddr.sin_port));
394      } else {
395          if (sa_type == SOCKET_ADDRESS_TYPE_UNIX) {
396              s->dgram_dst.sin_family = AF_UNIX;
397          }
398  
399          snprintf(nc->info_str, sizeof(nc->info_str),
400                   "socket: fd=%d %s", fd, SocketAddressType_str(sa_type));
401      }
402  
403      return s;
404  
405  err:
406      closesocket(fd);
407      return NULL;
408  }
409  
410  static void net_socket_connect(void *opaque)
411  {
412      NetSocketState *s = opaque;
413      s->send_fn = net_socket_send;
414      net_socket_read_poll(s, true);
415  }
416  
417  static NetClientInfo net_socket_info = {
418      .type = NET_CLIENT_DRIVER_SOCKET,
419      .size = sizeof(NetSocketState),
420      .receive = net_socket_receive,
421      .cleanup = net_socket_cleanup,
422  };
423  
424  static NetSocketState *net_socket_fd_init_stream(NetClientState *peer,
425                                                   const char *model,
426                                                   const char *name,
427                                                   int fd, int is_connected)
428  {
429      NetClientState *nc;
430      NetSocketState *s;
431  
432      nc = qemu_new_net_client(&net_socket_info, peer, model, name);
433  
434      snprintf(nc->info_str, sizeof(nc->info_str), "socket: fd=%d", fd);
435  
436      s = DO_UPCAST(NetSocketState, nc, nc);
437  
438      s->fd = fd;
439      s->listen_fd = -1;
440      net_socket_rs_init(&s->rs, net_socket_rs_finalize, false);
441  
442      /* Disable Nagle algorithm on TCP sockets to reduce latency */
443      socket_set_nodelay(fd);
444  
445      if (is_connected) {
446          net_socket_connect(s);
447      } else {
448          qemu_set_fd_handler(s->fd, NULL, net_socket_connect, s);
449      }
450      return s;
451  }
452  
453  static NetSocketState *net_socket_fd_init(NetClientState *peer,
454                                            const char *model, const char *name,
455                                            int fd, int is_connected,
456                                            const char *mc, Error **errp)
457  {
458      int so_type = -1, optlen=sizeof(so_type);
459  
460      if(getsockopt(fd, SOL_SOCKET, SO_TYPE, (char *)&so_type,
461          (socklen_t *)&optlen)< 0) {
462          error_setg(errp, "can't get socket option SO_TYPE");
463          closesocket(fd);
464          return NULL;
465      }
466      switch(so_type) {
467      case SOCK_DGRAM:
468          return net_socket_fd_init_dgram(peer, model, name, fd, is_connected,
469                                          mc, errp);
470      case SOCK_STREAM:
471          return net_socket_fd_init_stream(peer, model, name, fd, is_connected);
472      default:
473          error_setg(errp, "socket type=%d for fd=%d must be either"
474                     " SOCK_DGRAM or SOCK_STREAM", so_type, fd);
475          closesocket(fd);
476      }
477      return NULL;
478  }
479  
480  static void net_socket_accept(void *opaque)
481  {
482      NetSocketState *s = opaque;
483      struct sockaddr_in saddr;
484      socklen_t len;
485      int fd;
486  
487      for(;;) {
488          len = sizeof(saddr);
489          fd = qemu_accept(s->listen_fd, (struct sockaddr *)&saddr, &len);
490          if (fd < 0 && errno != EINTR) {
491              return;
492          } else if (fd >= 0) {
493              qemu_set_fd_handler(s->listen_fd, NULL, NULL, NULL);
494              break;
495          }
496      }
497  
498      s->fd = fd;
499      s->nc.link_down = false;
500      net_socket_connect(s);
501      snprintf(s->nc.info_str, sizeof(s->nc.info_str),
502               "socket: connection from %s:%d",
503               inet_ntoa(saddr.sin_addr), ntohs(saddr.sin_port));
504  }
505  
506  static int net_socket_listen_init(NetClientState *peer,
507                                    const char *model,
508                                    const char *name,
509                                    const char *host_str,
510                                    Error **errp)
511  {
512      NetClientState *nc;
513      NetSocketState *s;
514      struct sockaddr_in saddr;
515      int fd, ret;
516  
517      if (parse_host_port(&saddr, host_str, errp) < 0) {
518          return -1;
519      }
520  
521      fd = qemu_socket(PF_INET, SOCK_STREAM, 0);
522      if (fd < 0) {
523          error_setg_errno(errp, errno, "can't create stream socket");
524          return -1;
525      }
526      qemu_set_nonblock(fd);
527  
528      socket_set_fast_reuse(fd);
529  
530      ret = bind(fd, (struct sockaddr *)&saddr, sizeof(saddr));
531      if (ret < 0) {
532          error_setg_errno(errp, errno, "can't bind ip=%s to socket",
533                           inet_ntoa(saddr.sin_addr));
534          closesocket(fd);
535          return -1;
536      }
537      ret = listen(fd, 0);
538      if (ret < 0) {
539          error_setg_errno(errp, errno, "can't listen on socket");
540          closesocket(fd);
541          return -1;
542      }
543  
544      nc = qemu_new_net_client(&net_socket_info, peer, model, name);
545      s = DO_UPCAST(NetSocketState, nc, nc);
546      s->fd = -1;
547      s->listen_fd = fd;
548      s->nc.link_down = true;
549      net_socket_rs_init(&s->rs, net_socket_rs_finalize, false);
550  
551      qemu_set_fd_handler(s->listen_fd, net_socket_accept, NULL, s);
552      return 0;
553  }
554  
555  static int net_socket_connect_init(NetClientState *peer,
556                                     const char *model,
557                                     const char *name,
558                                     const char *host_str,
559                                     Error **errp)
560  {
561      NetSocketState *s;
562      int fd, connected, ret;
563      struct sockaddr_in saddr;
564  
565      if (parse_host_port(&saddr, host_str, errp) < 0) {
566          return -1;
567      }
568  
569      fd = qemu_socket(PF_INET, SOCK_STREAM, 0);
570      if (fd < 0) {
571          error_setg_errno(errp, errno, "can't create stream socket");
572          return -1;
573      }
574      qemu_set_nonblock(fd);
575  
576      connected = 0;
577      for(;;) {
578          ret = connect(fd, (struct sockaddr *)&saddr, sizeof(saddr));
579          if (ret < 0) {
580              if (errno == EINTR || errno == EWOULDBLOCK) {
581                  /* continue */
582              } else if (errno == EINPROGRESS ||
583                         errno == EALREADY ||
584                         errno == EINVAL) {
585                  break;
586              } else {
587                  error_setg_errno(errp, errno, "can't connect socket");
588                  closesocket(fd);
589                  return -1;
590              }
591          } else {
592              connected = 1;
593              break;
594          }
595      }
596      s = net_socket_fd_init(peer, model, name, fd, connected, NULL, errp);
597      if (!s) {
598          return -1;
599      }
600  
601      snprintf(s->nc.info_str, sizeof(s->nc.info_str),
602               "socket: connect to %s:%d",
603               inet_ntoa(saddr.sin_addr), ntohs(saddr.sin_port));
604      return 0;
605  }
606  
607  static int net_socket_mcast_init(NetClientState *peer,
608                                   const char *model,
609                                   const char *name,
610                                   const char *host_str,
611                                   const char *localaddr_str,
612                                   Error **errp)
613  {
614      NetSocketState *s;
615      int fd;
616      struct sockaddr_in saddr;
617      struct in_addr localaddr, *param_localaddr;
618  
619      if (parse_host_port(&saddr, host_str, errp) < 0) {
620          return -1;
621      }
622  
623      if (localaddr_str != NULL) {
624          if (inet_aton(localaddr_str, &localaddr) == 0) {
625              error_setg(errp, "localaddr '%s' is not a valid IPv4 address",
626                         localaddr_str);
627              return -1;
628          }
629          param_localaddr = &localaddr;
630      } else {
631          param_localaddr = NULL;
632      }
633  
634      fd = net_socket_mcast_create(&saddr, param_localaddr, errp);
635      if (fd < 0) {
636          return -1;
637      }
638  
639      s = net_socket_fd_init(peer, model, name, fd, 0, NULL, errp);
640      if (!s) {
641          return -1;
642      }
643  
644      s->dgram_dst = saddr;
645  
646      snprintf(s->nc.info_str, sizeof(s->nc.info_str),
647               "socket: mcast=%s:%d",
648               inet_ntoa(saddr.sin_addr), ntohs(saddr.sin_port));
649      return 0;
650  
651  }
652  
653  static int net_socket_udp_init(NetClientState *peer,
654                                   const char *model,
655                                   const char *name,
656                                   const char *rhost,
657                                   const char *lhost,
658                                   Error **errp)
659  {
660      NetSocketState *s;
661      int fd, ret;
662      struct sockaddr_in laddr, raddr;
663  
664      if (parse_host_port(&laddr, lhost, errp) < 0) {
665          return -1;
666      }
667  
668      if (parse_host_port(&raddr, rhost, errp) < 0) {
669          return -1;
670      }
671  
672      fd = qemu_socket(PF_INET, SOCK_DGRAM, 0);
673      if (fd < 0) {
674          error_setg_errno(errp, errno, "can't create datagram socket");
675          return -1;
676      }
677  
678      ret = socket_set_fast_reuse(fd);
679      if (ret < 0) {
680          error_setg_errno(errp, errno,
681                           "can't set socket option SO_REUSEADDR");
682          closesocket(fd);
683          return -1;
684      }
685      ret = bind(fd, (struct sockaddr *)&laddr, sizeof(laddr));
686      if (ret < 0) {
687          error_setg_errno(errp, errno, "can't bind ip=%s to socket",
688                           inet_ntoa(laddr.sin_addr));
689          closesocket(fd);
690          return -1;
691      }
692      qemu_set_nonblock(fd);
693  
694      s = net_socket_fd_init(peer, model, name, fd, 0, NULL, errp);
695      if (!s) {
696          return -1;
697      }
698  
699      s->dgram_dst = raddr;
700  
701      snprintf(s->nc.info_str, sizeof(s->nc.info_str),
702               "socket: udp=%s:%d",
703               inet_ntoa(raddr.sin_addr), ntohs(raddr.sin_port));
704      return 0;
705  }
706  
707  int net_init_socket(const Netdev *netdev, const char *name,
708                      NetClientState *peer, Error **errp)
709  {
710      const NetdevSocketOptions *sock;
711  
712      assert(netdev->type == NET_CLIENT_DRIVER_SOCKET);
713      sock = &netdev->u.socket;
714  
715      if (sock->has_fd + sock->has_listen + sock->has_connect + sock->has_mcast +
716          sock->has_udp != 1) {
717          error_setg(errp, "exactly one of listen=, connect=, mcast= or udp="
718                     " is required");
719          return -1;
720      }
721  
722      if (sock->has_localaddr && !sock->has_mcast && !sock->has_udp) {
723          error_setg(errp, "localaddr= is only valid with mcast= or udp=");
724          return -1;
725      }
726  
727      if (sock->has_fd) {
728          int fd, ret;
729  
730          fd = monitor_fd_param(monitor_cur(), sock->fd, errp);
731          if (fd == -1) {
732              return -1;
733          }
734          ret = qemu_try_set_nonblock(fd);
735          if (ret < 0) {
736              error_setg_errno(errp, -ret, "%s: Can't use file descriptor %d",
737                               name, fd);
738              return -1;
739          }
740          if (!net_socket_fd_init(peer, "socket", name, fd, 1, sock->mcast,
741                                  errp)) {
742              return -1;
743          }
744          return 0;
745      }
746  
747      if (sock->has_listen) {
748          if (net_socket_listen_init(peer, "socket", name, sock->listen, errp)
749              < 0) {
750              return -1;
751          }
752          return 0;
753      }
754  
755      if (sock->has_connect) {
756          if (net_socket_connect_init(peer, "socket", name, sock->connect, errp)
757              < 0) {
758              return -1;
759          }
760          return 0;
761      }
762  
763      if (sock->has_mcast) {
764          /* if sock->localaddr is missing, it has been initialized to "all bits
765           * zero" */
766          if (net_socket_mcast_init(peer, "socket", name, sock->mcast,
767                                    sock->localaddr, errp) < 0) {
768              return -1;
769          }
770          return 0;
771      }
772  
773      assert(sock->has_udp);
774      if (!sock->has_localaddr) {
775          error_setg(errp, "localaddr= is mandatory with udp=");
776          return -1;
777      }
778      if (net_socket_udp_init(peer, "socket", name, sock->udp, sock->localaddr,
779                              errp) < 0) {
780          return -1;
781      }
782      return 0;
783  }
784