svn commit: r531835 - in head/devel/libuv: . files

Thierry Thomas thierry at FreeBSD.org
Thu Apr 16 09:37:41 UTC 2020


Author: thierry
Date: Thu Apr 16 09:37:39 2020
New Revision: 531835
URL: https://svnweb.freebsd.org/changeset/ports/531835

Log:
  Adding patches from upstream (by bnoordhuis) to solve an issue with dns/bind916).
  
  See <https://github.com/libuv/libuv/issues/2791>
  and <https://github.com/libuv/libuv/pull/2792>
  
  PR:		245653
  Reported by:	lysfjord.daniel(at)smokepit.net and many

Added:
  head/devel/libuv/files/
  head/devel/libuv/files/patch-docs_src_udp.rst   (contents, props changed)
  head/devel/libuv/files/patch-include_uv.h   (contents, props changed)
  head/devel/libuv/files/patch-src_unix_freebsd.c   (contents, props changed)
  head/devel/libuv/files/patch-src_unix_internal.h   (contents, props changed)
  head/devel/libuv/files/patch-src_unix_linux-syscalls.c   (contents, props changed)
  head/devel/libuv/files/patch-src_unix_linux-syscalls.h   (contents, props changed)
  head/devel/libuv/files/patch-src_unix_udp.c   (contents, props changed)
Modified:
  head/devel/libuv/Makefile

Modified: head/devel/libuv/Makefile
==============================================================================
--- head/devel/libuv/Makefile	Thu Apr 16 09:32:26 2020	(r531834)
+++ head/devel/libuv/Makefile	Thu Apr 16 09:37:39 2020	(r531835)
@@ -4,6 +4,7 @@
 PORTNAME=	libuv
 PORTVERSION=	1.36.0
 DISTVERSIONPREFIX=	v
+PORTREVISION=	1
 CATEGORIES=	devel
 
 MAINTAINER=	thierry at FreeBSD.org

Added: head/devel/libuv/files/patch-docs_src_udp.rst
==============================================================================
--- /dev/null	00:00:00 1970	(empty, because file is newly added)
+++ head/devel/libuv/files/patch-docs_src_udp.rst	Thu Apr 16 09:37:39 2020	(r531835)
@@ -0,0 +1,51 @@
+--- docs/src/udp.rst.orig	2020-04-15 16:31:21 UTC
++++ docs/src/udp.rst
+@@ -42,11 +42,6 @@ Data types
+             * any traffic, in effect "stealing" the port from the previous listener.
+             */
+             UV_UDP_REUSEADDR = 4
+-            /*
+-             * Indicates that the message was received by recvmmsg, so the buffer provided
+-             * must not be freed by the recv_cb callback.
+-             */
+-            UV_UDP_MMSG_CHUNK = 8
+         };
+ 
+ .. c:type:: void (*uv_udp_send_cb)(uv_udp_send_t* req, int status)
+@@ -67,18 +62,13 @@ Data types
+     * `buf`: :c:type:`uv_buf_t` with the received data.
+     * `addr`: ``struct sockaddr*`` containing the address of the sender.
+       Can be NULL. Valid for the duration of the callback only.
+-    * `flags`: One or more or'ed UV_UDP_* constants.
++    * `flags`: One or more or'ed UV_UDP_* constants. Right now only
++      ``UV_UDP_PARTIAL`` is used.
+ 
+     The callee is responsible for freeing the buffer, libuv does not reuse it.
+     The buffer may be a null buffer (where `buf->base` == NULL and `buf->len` == 0)
+     on error.
+ 
+-    When using :man:`recvmmsg(2)`, chunks will have the `UV_UDP_MMSG_CHUNK` flag set,
+-    those must not be freed. There will be a final callback with `nread` set to 0,
+-    `addr` set to NULL and the buffer pointing at the initially allocated data with
+-    the `UV_UDP_MMSG_CHUNK` flag cleared. This is a good chance for the callee to
+-    free the provided buffer.
+-
+     .. note::
+         The receive callback will be called with `nread` == 0 and `addr` == NULL when there is
+         nothing to read, and with `nread` == 0 and `addr` != NULL when an empty UDP packet is
+@@ -376,10 +366,6 @@ API
+ 
+     :returns: 0 on success, or an error code < 0 on failure.
+ 
+-    .. versionchanged:: 1.35.0 added support for :man:`recvmmsg(2)` on supported platforms).
+-                        The use of this feature requires a buffer larger than
+-                        2 * 64KB to be passed to `alloc_cb`.
+-
+ .. c:function:: int uv_udp_recv_stop(uv_udp_t* handle)
+ 
+     Stop listening for incoming datagrams.
+@@ -402,3 +388,4 @@ API
+     .. versionadded:: 1.19.0
+ 
+ .. seealso:: The :c:type:`uv_handle_t` API functions also apply.
++

Added: head/devel/libuv/files/patch-include_uv.h
==============================================================================
--- /dev/null	00:00:00 1970	(empty, because file is newly added)
+++ head/devel/libuv/files/patch-include_uv.h	Thu Apr 16 09:37:39 2020	(r531835)
@@ -0,0 +1,23 @@
+--- include/uv.h.orig	2020-04-15 16:31:21 UTC
++++ include/uv.h
+@@ -1,4 +1,4 @@
+-/* Copyright Joyent, Inc. and other Node contributors. All rights reserved.
++/* COPYRIGHT JOYENT, INC. AND OTHER NODE CONTRIBUTORS. ALL RIGHTS RESERVED.
+  *
+  * Permission is hereby granted, free of charge, to any person obtaining a copy
+  * of this software and associated documentation files (the "Software"), to
+@@ -607,8 +607,7 @@ enum uv_udp_flags {
+    */
+   UV_UDP_REUSEADDR = 4,
+   /*
+-   * Indicates that the message was received by recvmmsg, so the buffer provided
+-   * must not be freed by the recv_cb callback.
++   * Unused. Here for API/ABI compatibility.
+    */
+   UV_UDP_MMSG_CHUNK = 8
+ };
+@@ -1802,3 +1801,4 @@ UV_EXTERN void uv_loop_set_data(uv_loop_t*, void* data
+ }
+ #endif
+ #endif /* UV_H */
++

Added: head/devel/libuv/files/patch-src_unix_freebsd.c
==============================================================================
--- /dev/null	00:00:00 1970	(empty, because file is newly added)
+++ head/devel/libuv/files/patch-src_unix_freebsd.c	Thu Apr 16 09:37:39 2020	(r531835)
@@ -0,0 +1,30 @@
+--- src/unix/freebsd.c.orig	2020-04-15 16:31:21 UTC
++++ src/unix/freebsd.c
+@@ -289,27 +289,3 @@ int uv_cpu_info(uv_cpu_info_t** cpu_infos, int* count)
+   return 0;
+ }
+ 
+-
+-int uv__sendmmsg(int fd,
+-                 struct uv__mmsghdr* mmsg,
+-                 unsigned int vlen,
+-                 unsigned int flags) {
+-#if __FreeBSD__ >= 11
+-  return sendmmsg(fd, mmsg, vlen, flags);
+-#else
+-  return errno = ENOSYS, -1;
+-#endif
+-}
+-
+-
+-int uv__recvmmsg(int fd,
+-                 struct uv__mmsghdr* mmsg,
+-                 unsigned int vlen,
+-                 unsigned int flags,
+-                 struct timespec* timeout) {
+-#if __FreeBSD__ >= 11
+-  return recvmmsg(fd, mmsg, vlen, flags, timeout);
+-#else
+-  return errno = ENOSYS, -1;
+-#endif
+-}

Added: head/devel/libuv/files/patch-src_unix_internal.h
==============================================================================
--- /dev/null	00:00:00 1970	(empty, because file is newly added)
+++ head/devel/libuv/files/patch-src_unix_internal.h	Thu Apr 16 09:37:39 2020	(r531835)
@@ -0,0 +1,39 @@
+--- src/unix/internal.h.orig	2020-04-15 16:31:21 UTC
++++ src/unix/internal.h
+@@ -31,7 +31,6 @@
+ #include <fcntl.h>  /* O_CLOEXEC and O_NONBLOCK, if supported. */
+ #include <stdio.h>
+ #include <errno.h>
+-#include <sys/socket.h>
+ 
+ #if defined(__STRICT_ANSI__)
+ # define inline __inline
+@@ -328,27 +327,5 @@ int uv__getsockpeername(const uv_handle_t* handle,
+                         struct sockaddr* name,
+                         int* namelen);
+ 
+-#if defined(__linux__)            ||                                      \
+-    defined(__FreeBSD__)          ||                                      \
+-    defined(__FreeBSD_kernel__)
+-#define HAVE_MMSG 1
+-struct uv__mmsghdr {
+-  struct msghdr msg_hdr;
+-  unsigned int msg_len;
+-};
+-
+-int uv__recvmmsg(int fd,
+-                 struct uv__mmsghdr* mmsg,
+-                 unsigned int vlen,
+-                 unsigned int flags,
+-                 struct timespec* timeout);
+-int uv__sendmmsg(int fd,
+-                 struct uv__mmsghdr* mmsg,
+-                 unsigned int vlen,
+-                 unsigned int flags);
+-#else
+-#define HAVE_MMSG 0
+-#endif
+-
+-
+ #endif /* UV_UNIX_INTERNAL_H_ */
++

Added: head/devel/libuv/files/patch-src_unix_linux-syscalls.c
==============================================================================
--- /dev/null	00:00:00 1970	(empty, because file is newly added)
+++ head/devel/libuv/files/patch-src_unix_linux-syscalls.c	Thu Apr 16 09:37:39 2020	(r531835)
@@ -0,0 +1,242 @@
+--- src/unix/linux-syscalls.c.orig	2020-04-15 16:31:21 UTC
++++ src/unix/linux-syscalls.c
+@@ -19,187 +19,71 @@
+  * IN THE SOFTWARE.
+  */
+ 
+-#include "linux-syscalls.h"
+-#include <unistd.h>
++#ifndef UV_LINUX_SYSCALL_H_
++#define UV_LINUX_SYSCALL_H_
++
++#undef  _GNU_SOURCE
++#define _GNU_SOURCE
++
++#include <stdint.h>
+ #include <signal.h>
+-#include <sys/syscall.h>
+ #include <sys/types.h>
+-#include <errno.h>
++#include <sys/time.h>
++#include <sys/socket.h>
+ 
+-#if defined(__arm__)
+-# if defined(__thumb__) || defined(__ARM_EABI__)
+-#  define UV_SYSCALL_BASE 0
+-# else
+-#  define UV_SYSCALL_BASE 0x900000
+-# endif
+-#endif /* __arm__ */
++struct uv__statx_timestamp {
++  int64_t tv_sec;
++  uint32_t tv_nsec;
++  int32_t unused0;
++};
+ 
+-#ifndef __NR_recvmmsg
+-# if defined(__x86_64__)
+-#  define __NR_recvmmsg 299
+-# elif defined(__i386__)
+-#  define __NR_recvmmsg 337
+-# elif defined(__arm__)
+-#  define __NR_recvmmsg (UV_SYSCALL_BASE + 365)
+-# endif
+-#endif /* __NR_recvmsg */
++struct uv__statx {
++  uint32_t stx_mask;
++  uint32_t stx_blksize;
++  uint64_t stx_attributes;
++  uint32_t stx_nlink;
++  uint32_t stx_uid;
++  uint32_t stx_gid;
++  uint16_t stx_mode;
++  uint16_t unused0;
++  uint64_t stx_ino;
++  uint64_t stx_size;
++  uint64_t stx_blocks;
++  uint64_t stx_attributes_mask;
++  struct uv__statx_timestamp stx_atime;
++  struct uv__statx_timestamp stx_btime;
++  struct uv__statx_timestamp stx_ctime;
++  struct uv__statx_timestamp stx_mtime;
++  uint32_t stx_rdev_major;
++  uint32_t stx_rdev_minor;
++  uint32_t stx_dev_major;
++  uint32_t stx_dev_minor;
++  uint64_t unused1[14];
++};
+ 
+-#ifndef __NR_sendmmsg
+-# if defined(__x86_64__)
+-#  define __NR_sendmmsg 307
+-# elif defined(__i386__)
+-#  define __NR_sendmmsg 345
+-# elif defined(__arm__)
+-#  define __NR_sendmmsg (UV_SYSCALL_BASE + 374)
+-# endif
+-#endif /* __NR_sendmmsg */
++struct uv__mmsghdr {
++  struct msghdr msg_hdr;
++  unsigned int msg_len;
++};
+ 
+-#ifndef __NR_utimensat
+-# if defined(__x86_64__)
+-#  define __NR_utimensat 280
+-# elif defined(__i386__)
+-#  define __NR_utimensat 320
+-# elif defined(__arm__)
+-#  define __NR_utimensat (UV_SYSCALL_BASE + 348)
+-# endif
+-#endif /* __NR_utimensat */
+-
+-#ifndef __NR_preadv
+-# if defined(__x86_64__)
+-#  define __NR_preadv 295
+-# elif defined(__i386__)
+-#  define __NR_preadv 333
+-# elif defined(__arm__)
+-#  define __NR_preadv (UV_SYSCALL_BASE + 361)
+-# endif
+-#endif /* __NR_preadv */
+-
+-#ifndef __NR_pwritev
+-# if defined(__x86_64__)
+-#  define __NR_pwritev 296
+-# elif defined(__i386__)
+-#  define __NR_pwritev 334
+-# elif defined(__arm__)
+-#  define __NR_pwritev (UV_SYSCALL_BASE + 362)
+-# endif
+-#endif /* __NR_pwritev */
+-
+-#ifndef __NR_dup3
+-# if defined(__x86_64__)
+-#  define __NR_dup3 292
+-# elif defined(__i386__)
+-#  define __NR_dup3 330
+-# elif defined(__arm__)
+-#  define __NR_dup3 (UV_SYSCALL_BASE + 358)
+-# endif
+-#endif /* __NR_pwritev */
+-
+-#ifndef __NR_statx
+-# if defined(__x86_64__)
+-#  define __NR_statx 332
+-# elif defined(__i386__)
+-#  define __NR_statx 383
+-# elif defined(__aarch64__)
+-#  define __NR_statx 397
+-# elif defined(__arm__)
+-#  define __NR_statx (UV_SYSCALL_BASE + 397)
+-# elif defined(__ppc__)
+-#  define __NR_statx 383
+-# elif defined(__s390__)
+-#  define __NR_statx 379
+-# endif
+-#endif /* __NR_statx */
+-
+-#ifndef __NR_getrandom
+-# if defined(__x86_64__)
+-#  define __NR_getrandom 318
+-# elif defined(__i386__)
+-#  define __NR_getrandom 355
+-# elif defined(__aarch64__)
+-#  define __NR_getrandom 384
+-# elif defined(__arm__)
+-#  define __NR_getrandom (UV_SYSCALL_BASE + 384)
+-# elif defined(__ppc__)
+-#  define __NR_getrandom 359
+-# elif defined(__s390__)
+-#  define __NR_getrandom 349
+-# endif
+-#endif /* __NR_getrandom */
+-
+-struct uv__mmsghdr;
+-
+-int uv__sendmmsg(int fd,
+-                 struct uv__mmsghdr* mmsg,
+-                 unsigned int vlen,
+-                 unsigned int flags) {
+-#if defined(__NR_sendmmsg)
+-  return syscall(__NR_sendmmsg, fd, mmsg, vlen, flags);
+-#else
+-  return errno = ENOSYS, -1;
+-#endif
+-}
+-
+-
+ int uv__recvmmsg(int fd,
+                  struct uv__mmsghdr* mmsg,
+                  unsigned int vlen,
+                  unsigned int flags,
+-                 struct timespec* timeout) {
+-#if defined(__NR_recvmmsg)
+-  return syscall(__NR_recvmmsg, fd, mmsg, vlen, flags, timeout);
+-#else
+-  return errno = ENOSYS, -1;
+-#endif
+-}
+-
+-
+-ssize_t uv__preadv(int fd, const struct iovec *iov, int iovcnt, int64_t offset) {
+-#if defined(__NR_preadv)
+-  return syscall(__NR_preadv, fd, iov, iovcnt, (long)offset, (long)(offset >> 32));
+-#else
+-  return errno = ENOSYS, -1;
+-#endif
+-}
+-
+-
+-ssize_t uv__pwritev(int fd, const struct iovec *iov, int iovcnt, int64_t offset) {
+-#if defined(__NR_pwritev)
+-  return syscall(__NR_pwritev, fd, iov, iovcnt, (long)offset, (long)(offset >> 32));
+-#else
+-  return errno = ENOSYS, -1;
+-#endif
+-}
+-
+-
+-int uv__dup3(int oldfd, int newfd, int flags) {
+-#if defined(__NR_dup3)
+-  return syscall(__NR_dup3, oldfd, newfd, flags);
+-#else
+-  return errno = ENOSYS, -1;
+-#endif
+-}
+-
+-
++                 struct timespec* timeout);
++int uv__sendmmsg(int fd,
++                 struct uv__mmsghdr* mmsg,
++                 unsigned int vlen,
++                 unsigned int flags);
++ssize_t uv__preadv(int fd, const struct iovec *iov, int iovcnt, int64_t offset);
++ssize_t uv__pwritev(int fd, const struct iovec *iov, int iovcnt, int64_t offset);
++int uv__dup3(int oldfd, int newfd, int flags);
+ int uv__statx(int dirfd,
+               const char* path,
+               int flags,
+               unsigned int mask,
+-              struct uv__statx* statxbuf) {
+-  /* __NR_statx make Android box killed by SIGSYS.
+-   * That looks like a seccomp2 sandbox filter rejecting the system call.
+-   */
+-#if defined(__NR_statx) && !defined(__ANDROID__)
+-  return syscall(__NR_statx, dirfd, path, flags, mask, statxbuf);
+-#else
+-  return errno = ENOSYS, -1;
+-#endif
+-}
++              struct uv__statx* statxbuf);
++ssize_t uv__getrandom(void* buf, size_t buflen, unsigned flags);
+ 
++#endif /* UV_LINUX_SYSCALL_H_ */
+ 
+-ssize_t uv__getrandom(void* buf, size_t buflen, unsigned flags) {
+-#if defined(__NR_getrandom)
+-  return syscall(__NR_getrandom, buf, buflen, flags);
+-#else
+-  return errno = ENOSYS, -1;
+-#endif
+-}

Added: head/devel/libuv/files/patch-src_unix_linux-syscalls.h
==============================================================================
--- /dev/null	00:00:00 1970	(empty, because file is newly added)
+++ head/devel/libuv/files/patch-src_unix_linux-syscalls.h	Thu Apr 16 09:37:39 2020	(r531835)
@@ -0,0 +1,28 @@
+--- src/unix/linux-syscalls.h.orig	2020-04-15 16:31:21 UTC
++++ src/unix/linux-syscalls.h
+@@ -61,6 +61,20 @@ struct uv__statx {
+   uint64_t unused1[14];
+ };
+ 
++struct uv__mmsghdr {
++  struct msghdr msg_hdr;
++  unsigned int msg_len;
++};
++
++int uv__recvmmsg(int fd,
++                 struct uv__mmsghdr* mmsg,
++                 unsigned int vlen,
++                 unsigned int flags,
++                 struct timespec* timeout);
++int uv__sendmmsg(int fd,
++                 struct uv__mmsghdr* mmsg,
++                 unsigned int vlen,
++                 unsigned int flags);
+ ssize_t uv__preadv(int fd, const struct iovec *iov, int iovcnt, int64_t offset);
+ ssize_t uv__pwritev(int fd, const struct iovec *iov, int iovcnt, int64_t offset);
+ int uv__dup3(int oldfd, int newfd, int flags);
+@@ -72,3 +86,4 @@ int uv__statx(int dirfd,
+ ssize_t uv__getrandom(void* buf, size_t buflen, unsigned flags);
+ 
+ #endif /* UV_LINUX_SYSCALL_H_ */
++

Added: head/devel/libuv/files/patch-src_unix_udp.c
==============================================================================
--- /dev/null	00:00:00 1970	(empty, because file is newly added)
+++ head/devel/libuv/files/patch-src_unix_udp.c	Thu Apr 16 09:37:39 2020	(r531835)
@@ -0,0 +1,277 @@
+--- src/unix/udp.c.orig	2020-04-15 16:31:21 UTC
++++ src/unix/udp.c
+@@ -32,8 +32,6 @@
+ #endif
+ #include <sys/un.h>
+ 
+-#define UV__UDP_DGRAM_MAXSIZE (64 * 1024)
+-
+ #if defined(IPV6_JOIN_GROUP) && !defined(IPV6_ADD_MEMBERSHIP)
+ # define IPV6_ADD_MEMBERSHIP IPV6_JOIN_GROUP
+ #endif
+@@ -51,37 +49,7 @@ static int uv__udp_maybe_deferred_bind(uv_udp_t* handl
+                                        int domain,
+                                        unsigned int flags);
+ 
+-#if HAVE_MMSG
+ 
+-#define UV__MMSG_MAXWIDTH 20
+-
+-static int uv__udp_recvmmsg(uv_udp_t* handle, uv_buf_t* buf);
+-static void uv__udp_sendmmsg(uv_udp_t* handle);
+-
+-static int uv__recvmmsg_avail;
+-static int uv__sendmmsg_avail;
+-static uv_once_t once = UV_ONCE_INIT;
+-
+-static void uv__udp_mmsg_init(void) {
+-  int ret;
+-  int s;
+-  s = uv__socket(AF_INET, SOCK_DGRAM, 0);
+-  if (s < 0)
+-    return;
+-  ret = uv__sendmmsg(s, NULL, 0, 0);
+-  if (ret == 0 || errno != ENOSYS) {
+-    uv__sendmmsg_avail = 1;
+-    uv__recvmmsg_avail = 1;
+-  } else {
+-    ret = uv__recvmmsg(s, NULL, 0, 0, NULL);
+-    if (ret == 0 || errno != ENOSYS)
+-      uv__recvmmsg_avail = 1;
+-  }
+-  uv__close(s);
+-}
+-
+-#endif
+-
+ void uv__udp_close(uv_udp_t* handle) {
+   uv__io_close(handle->loop, &handle->io_watcher);
+   uv__handle_stop(handle);
+@@ -180,62 +148,7 @@ static void uv__udp_io(uv_loop_t* loop, uv__io_t* w, u
+   }
+ }
+ 
+-#if HAVE_MMSG
+-static int uv__udp_recvmmsg(uv_udp_t* handle, uv_buf_t* buf) {
+-  struct sockaddr_in6 peers[UV__MMSG_MAXWIDTH];
+-  struct iovec iov[UV__MMSG_MAXWIDTH];
+-  struct uv__mmsghdr msgs[UV__MMSG_MAXWIDTH];
+-  ssize_t nread;
+-  uv_buf_t chunk_buf;
+-  size_t chunks;
+-  int flags;
+-  size_t k;
+ 
+-  /* prepare structures for recvmmsg */
+-  chunks = buf->len / UV__UDP_DGRAM_MAXSIZE;
+-  if (chunks > ARRAY_SIZE(iov))
+-    chunks = ARRAY_SIZE(iov);
+-  for (k = 0; k < chunks; ++k) {
+-    iov[k].iov_base = buf->base + k * UV__UDP_DGRAM_MAXSIZE;
+-    iov[k].iov_len = UV__UDP_DGRAM_MAXSIZE;
+-    msgs[k].msg_hdr.msg_iov = iov + k;
+-    msgs[k].msg_hdr.msg_iovlen = 1;
+-    msgs[k].msg_hdr.msg_name = peers + k;
+-    msgs[k].msg_hdr.msg_namelen = sizeof(peers[0]);
+-  }
+-
+-  do
+-    nread = uv__recvmmsg(handle->io_watcher.fd, msgs, chunks, 0, NULL);
+-  while (nread == -1 && errno == EINTR);
+-
+-  if (nread < 1) {
+-    if (nread == 0 || errno == EAGAIN || errno == EWOULDBLOCK)
+-      handle->recv_cb(handle, 0, buf, NULL, 0);
+-    else
+-      handle->recv_cb(handle, UV__ERR(errno), buf, NULL, 0);
+-  } else {
+-    /* pass each chunk to the application */
+-    for (k = 0; k < (size_t) nread && handle->recv_cb != NULL; k++) {
+-      flags = UV_UDP_MMSG_CHUNK;
+-      if (msgs[k].msg_hdr.msg_flags & MSG_TRUNC)
+-        flags |= UV_UDP_PARTIAL;
+-
+-      chunk_buf = uv_buf_init(iov[k].iov_base, iov[k].iov_len);
+-      handle->recv_cb(handle,
+-                      msgs[k].msg_len,
+-                      &chunk_buf,
+-                      msgs[k].msg_hdr.msg_name,
+-                      flags);
+-    }
+-
+-    /* one last callback so the original buffer is freed */
+-    if (handle->recv_cb != NULL)
+-      handle->recv_cb(handle, 0, buf, NULL, 0);
+-  }
+-  return nread;
+-}
+-#endif
+-
+ static void uv__udp_recvmsg(uv_udp_t* handle) {
+   struct sockaddr_storage peer;
+   struct msghdr h;
+@@ -254,27 +167,13 @@ static void uv__udp_recvmsg(uv_udp_t* handle) {
+ 
+   do {
+     buf = uv_buf_init(NULL, 0);
+-    handle->alloc_cb((uv_handle_t*) handle, UV__UDP_DGRAM_MAXSIZE, &buf);
++    handle->alloc_cb((uv_handle_t*) handle, 64 * 1024, &buf);
+     if (buf.base == NULL || buf.len == 0) {
+       handle->recv_cb(handle, UV_ENOBUFS, &buf, NULL, 0);
+       return;
+     }
+     assert(buf.base != NULL);
+ 
+-#if HAVE_MMSG
+-    uv_once(&once, uv__udp_mmsg_init);
+-    if (uv__recvmmsg_avail) {
+-      /* Returned space for more than 1 datagram, use it to receive
+-       * multiple datagrams. */
+-      if (buf.len >= 2 * UV__UDP_DGRAM_MAXSIZE) {
+-        nread = uv__udp_recvmmsg(handle, &buf);
+-        if (nread > 0)
+-          count -= nread;
+-        continue;
+-      }
+-    }
+-#endif
+-
+     memset(&h, 0, sizeof(h));
+     memset(&peer, 0, sizeof(peer));
+     h.msg_name = &peer;
+@@ -300,120 +199,21 @@ static void uv__udp_recvmsg(uv_udp_t* handle) {
+ 
+       handle->recv_cb(handle, nread, &buf, (const struct sockaddr*) &peer, flags);
+     }
+-    count--;
+   }
+   /* recv_cb callback may decide to pause or close the handle */
+   while (nread != -1
+-      && count > 0
++      && count-- > 0
+       && handle->io_watcher.fd != -1
+       && handle->recv_cb != NULL);
+ }
+ 
+-#if HAVE_MMSG
+-static void uv__udp_sendmmsg(uv_udp_t* handle) {
+-  uv_udp_send_t* req;
+-  struct uv__mmsghdr h[UV__MMSG_MAXWIDTH];
+-  struct uv__mmsghdr *p;
+-  QUEUE* q;
+-  ssize_t npkts;
+-  size_t pkts;
+-  size_t i;
+ 
+-  if (QUEUE_EMPTY(&handle->write_queue))
+-    return;
+-
+-write_queue_drain:
+-  for (pkts = 0, q = QUEUE_HEAD(&handle->write_queue);
+-       pkts < UV__MMSG_MAXWIDTH && q != &handle->write_queue;
+-       ++pkts, q = QUEUE_HEAD(q)) {
+-    assert(q != NULL);
+-    req = QUEUE_DATA(q, uv_udp_send_t, queue);
+-    assert(req != NULL);
+-
+-    p = &h[pkts];
+-    memset(p, 0, sizeof(*p));
+-    if (req->addr.ss_family == AF_UNSPEC) {
+-      p->msg_hdr.msg_name = NULL;
+-      p->msg_hdr.msg_namelen = 0;
+-    } else {
+-      p->msg_hdr.msg_name = &req->addr;
+-      if (req->addr.ss_family == AF_INET6)
+-        p->msg_hdr.msg_namelen = sizeof(struct sockaddr_in6);
+-      else if (req->addr.ss_family == AF_INET)
+-        p->msg_hdr.msg_namelen = sizeof(struct sockaddr_in);
+-      else if (req->addr.ss_family == AF_UNIX)
+-        p->msg_hdr.msg_namelen = sizeof(struct sockaddr_un);
+-      else {
+-        assert(0 && "unsupported address family");
+-        abort();
+-      }
+-    }
+-    h[pkts].msg_hdr.msg_iov = (struct iovec*) req->bufs;
+-    h[pkts].msg_hdr.msg_iovlen = req->nbufs;
+-  }
+-
+-  do
+-    npkts = uv__sendmmsg(handle->io_watcher.fd, h, pkts, 0);
+-  while (npkts == -1 && errno == EINTR);
+-
+-  if (npkts < 1) {
+-    if (errno == EAGAIN || errno == EWOULDBLOCK || errno == ENOBUFS)
+-      return;
+-    for (i = 0, q = QUEUE_HEAD(&handle->write_queue);
+-         i < pkts && q != &handle->write_queue;
+-         ++i, q = QUEUE_HEAD(q)) {
+-      assert(q != NULL);
+-      req = QUEUE_DATA(q, uv_udp_send_t, queue);
+-      assert(req != NULL);
+-
+-      req->status = UV__ERR(errno);
+-      QUEUE_REMOVE(&req->queue);
+-      QUEUE_INSERT_TAIL(&handle->write_completed_queue, &req->queue);
+-    }
+-    uv__io_feed(handle->loop, &handle->io_watcher);
+-    return;
+-  }
+-
+-  for (i = 0, q = QUEUE_HEAD(&handle->write_queue);
+-       i < pkts && q != &handle->write_queue;
+-       ++i, q = QUEUE_HEAD(&handle->write_queue)) {
+-    assert(q != NULL);
+-    req = QUEUE_DATA(q, uv_udp_send_t, queue);
+-    assert(req != NULL);
+-
+-    req->status = req->bufs[0].len;
+-
+-    /* Sending a datagram is an atomic operation: either all data
+-     * is written or nothing is (and EMSGSIZE is raised). That is
+-     * why we don't handle partial writes. Just pop the request
+-     * off the write queue and onto the completed queue, done.
+-     */
+-    QUEUE_REMOVE(&req->queue);
+-    QUEUE_INSERT_TAIL(&handle->write_completed_queue, &req->queue);
+-  }
+-
+-  /* couldn't batch everything, continue sending (jump to avoid stack growth) */
+-  if (!QUEUE_EMPTY(&handle->write_queue))
+-    goto write_queue_drain;
+-  uv__io_feed(handle->loop, &handle->io_watcher);
+-  return;
+-}
+-#endif
+-
+ static void uv__udp_sendmsg(uv_udp_t* handle) {
+   uv_udp_send_t* req;
+-  struct msghdr h;
+   QUEUE* q;
++  struct msghdr h;
+   ssize_t size;
+ 
+-#if HAVE_MMSG
+-  uv_once(&once, uv__udp_mmsg_init);
+-  if (uv__sendmmsg_avail) {
+-    uv__udp_sendmmsg(handle);
+-    return;
+-  }
+-#endif
+-
+   while (!QUEUE_EMPTY(&handle->write_queue)) {
+     q = QUEUE_HEAD(&handle->write_queue);
+     assert(q != NULL);
+@@ -463,6 +263,7 @@ static void uv__udp_sendmsg(uv_udp_t* handle) {
+   }
+ }
+ 
++
+ /* On the BSDs, SO_REUSEPORT implies SO_REUSEADDR but with some additional
+  * refinements for programs that use multicast.
+  *
+@@ -1333,3 +1134,4 @@ int uv__udp_recv_stop(uv_udp_t* handle) {
+ 
+   return 0;
+ }
++


More information about the svn-ports-all mailing list