nuttx-apps/system/libuv/0001-libuv-port-for-nuttx.patch

3547 lines
96 KiB
Diff
Raw Normal View History

diff --git a/include/uv.h b/include/uv.h
index 02397dd0..ab2f36fc 100644
--- a/include/uv.h
+++ b/include/uv.h
@@ -842,6 +842,16 @@ UV_EXTERN int uv_pipe_connect2(uv_connect_t* req,
size_t namelen,
unsigned int flags,
uv_connect_cb cb);
+#ifdef CONFIG_NET_RPMSG
+UV_EXTERN int uv_pipe_rpmsg_bind(uv_pipe_t* handle,
+ const char* name,
+ const char* cpu_name);
+UV_EXTERN void uv_pipe_rpmsg_connect(uv_connect_t* req,
+ uv_pipe_t* handle,
+ const char* name,
+ const char* cpu_name,
+ uv_connect_cb cb);
+#endif
UV_EXTERN int uv_pipe_getsockname(const uv_pipe_t* handle,
char* buffer,
size_t* size);
@@ -1826,12 +1836,14 @@ UV_EXTERN int uv_thread_create(uv_thread_t* tid, uv_thread_cb entry, void* arg);
typedef enum {
UV_THREAD_NO_FLAGS = 0x00,
- UV_THREAD_HAS_STACK_SIZE = 0x01
+ UV_THREAD_HAS_STACK_SIZE = 0x01,
+ UV_THREAD_HAS_PRIORITY = 0x02
} uv_thread_create_flags;
struct uv_thread_options_s {
unsigned int flags;
size_t stack_size;
+ int priority;
/* More fields may be added at any time. */
};
diff --git a/include/uv/unix.h b/include/uv/unix.h
index 09f88a56..4962b932 100644
--- a/include/uv/unix.h
+++ b/include/uv/unix.h
@@ -66,6 +66,7 @@
defined(__MSYS__) || \
defined(__HAIKU__) || \
defined(__QNX__) || \
+ defined(__NuttX__) || \
defined(__GNU__)
# include "uv/posix.h"
#endif
diff --git a/src/fs-poll.c b/src/fs-poll.c
index 1bac1c56..ea4a17cd 100644
--- a/src/fs-poll.c
+++ b/src/fs-poll.c
@@ -53,7 +53,7 @@ static void poll_cb(uv_fs_t* req);
static void timer_cb(uv_timer_t* timer);
static void timer_close_cb(uv_handle_t* handle);
-static uv_stat_t zero_statbuf;
+static const uv_stat_t zero_statbuf;
int uv_fs_poll_init(uv_loop_t* loop, uv_fs_poll_t* handle) {
diff --git a/src/random.c b/src/random.c
index e75f77de..feef5a44 100644
--- a/src/random.c
+++ b/src/random.c
@@ -31,7 +31,7 @@
static int uv__random(void* buf, size_t buflen) {
int rc;
-#if defined(__PASE__)
+#if defined(__PASE__) || defined(__NuttX__)
rc = uv__random_readpath("/dev/urandom", buf, buflen);
#elif defined(_AIX) || defined(__QNX__)
rc = uv__random_readpath("/dev/random", buf, buflen);
diff --git a/src/threadpool.c b/src/threadpool.c
index dbef67f2..94414212 100644
--- a/src/threadpool.c
+++ b/src/threadpool.c
@@ -20,6 +20,7 @@
*/
#include "uv-common.h"
+#include "uv-global.h"
#if !defined(_WIN32)
# include "unix/internal.h"
@@ -29,18 +30,6 @@
#define MAX_THREADPOOL_SIZE 1024
-static uv_once_t once = UV_ONCE_INIT;
-static uv_cond_t cond;
-static uv_mutex_t mutex;
-static unsigned int idle_threads;
-static unsigned int slow_io_work_running;
-static unsigned int nthreads;
-static uv_thread_t* threads;
-static uv_thread_t default_threads[4];
-static struct uv__queue exit_message;
-static struct uv__queue wq;
-static struct uv__queue run_slow_work_message;
-static struct uv__queue slow_io_pending_wq;
static unsigned int slow_work_thread_threshold(void) {
return (nthreads + 1) / 2;
@@ -68,16 +57,16 @@ static void worker(void* arg) {
/* Keep waiting while either no work is present or only slow I/O
and we're at the threshold for that. */
- while (uv__queue_empty(&wq) ||
- (uv__queue_head(&wq) == &run_slow_work_message &&
- uv__queue_next(&run_slow_work_message) == &wq &&
+ while (uv__queue_empty(&lwq) ||
+ (uv__queue_head(&lwq) == &run_slow_work_message &&
+ uv__queue_next(&run_slow_work_message) == &lwq &&
slow_io_work_running >= slow_work_thread_threshold())) {
idle_threads += 1;
uv_cond_wait(&cond, &mutex);
idle_threads -= 1;
}
- q = uv__queue_head(&wq);
+ q = uv__queue_head(&lwq);
if (q == &exit_message) {
uv_cond_signal(&cond);
uv_mutex_unlock(&mutex);
@@ -92,7 +81,7 @@ static void worker(void* arg) {
/* If we're at the slow I/O threshold, re-schedule until after all
other work in the queue is done. */
if (slow_io_work_running >= slow_work_thread_threshold()) {
- uv__queue_insert_tail(&wq, q);
+ uv__queue_insert_tail(&lwq, q);
continue;
}
@@ -110,7 +99,7 @@ static void worker(void* arg) {
/* If there is more slow I/O work, schedule it to be run as well. */
if (!uv__queue_empty(&slow_io_pending_wq)) {
- uv__queue_insert_tail(&wq, &run_slow_work_message);
+ uv__queue_insert_tail(&lwq, &run_slow_work_message);
if (idle_threads > 0)
uv_cond_signal(&cond);
}
@@ -153,7 +142,7 @@ static void post(struct uv__queue* q, enum uv__work_kind kind) {
q = &run_slow_work_message;
}
- uv__queue_insert_tail(&wq, q);
+ uv__queue_insert_tail(&lwq, q);
if (idle_threads > 0)
uv_cond_signal(&cond);
uv_mutex_unlock(&mutex);
@@ -191,11 +180,28 @@ void uv__threadpool_cleanup(void) {
static void init_threads(void) {
- uv_thread_options_t config;
unsigned int i;
const char* val;
uv_sem_t sem;
+ const uv_thread_options_t params = {
+#ifdef DEF_THREADPOOL_STACKSIZE
+ UV_THREAD_HAS_STACK_SIZE |
+#endif
+#ifdef DEF_THREADPOOL_PRIORITY
+ UV_THREAD_HAS_PRIORITY |
+#endif
+ UV_THREAD_NO_FLAGS,
+#ifdef DEF_THREADPOOL_STACKSIZE
+ DEF_THREADPOOL_STACKSIZE,
+#else
+ 0,
+#endif
+#ifdef DEF_THREADPOOL_PRIORITY
+ DEF_THREADPOOL_PRIORITY
+#endif
+ };
+
nthreads = ARRAY_SIZE(default_threads);
val = getenv("UV_THREADPOOL_SIZE");
if (val != NULL)
@@ -220,18 +226,15 @@ static void init_threads(void) {
if (uv_mutex_init(&mutex))
abort();
- uv__queue_init(&wq);
+ uv__queue_init(&lwq);
uv__queue_init(&slow_io_pending_wq);
uv__queue_init(&run_slow_work_message);
if (uv_sem_init(&sem, 0))
abort();
- config.flags = UV_THREAD_HAS_STACK_SIZE;
- config.stack_size = 8u << 20; /* 8 MB */
-
for (i = 0; i < nthreads; i++)
- if (uv_thread_create_ex(threads + i, &config, worker, &sem))
+ if (uv_thread_create_ex(threads + i, &params, worker, &sem))
abort();
for (i = 0; i < nthreads; i++)
diff --git a/src/unix/core.c b/src/unix/core.c
index 25c5181f..6ff617af 100644
--- a/src/unix/core.c
+++ b/src/unix/core.c
@@ -60,7 +60,7 @@
# include <crt_externs.h>
# include <mach-o/dyld.h> /* _NSGetExecutablePath */
# define environ (*_NSGetEnviron())
-#else /* defined(__APPLE__) && !TARGET_OS_IPHONE */
+#elif !defined(__NuttX__) /* defined(__APPLE__) && !TARGET_OS_IPHONE */
extern char** environ;
#endif /* !(defined(__APPLE__) && !TARGET_OS_IPHONE) */
@@ -1000,7 +1000,7 @@ int uv_getrusage(uv_rusage_t* rusage) {
rusage->ru_stime.tv_sec = usage.ru_stime.tv_sec;
rusage->ru_stime.tv_usec = usage.ru_stime.tv_usec;
-#if !defined(__MVS__) && !defined(__HAIKU__)
+#if !defined(__MVS__) && !defined(__HAIKU__) && !defined(__NuttX__)
rusage->ru_maxrss = usage.ru_maxrss;
rusage->ru_ixrss = usage.ru_ixrss;
rusage->ru_idrss = usage.ru_idrss;
diff --git a/src/unix/fs.c b/src/unix/fs.c
index 6b051c12..0d4c6014 100644
--- a/src/unix/fs.c
+++ b/src/unix/fs.c
@@ -56,7 +56,7 @@
#endif
/* preadv() and pwritev() were added in Android N (level 24) */
-#if defined(__linux__) && !(defined(__ANDROID__) && __ANDROID_API__ < 24)
+#if (defined(__linux__) || defined(__NuttX__)) && !(defined(__ANDROID__) && __ANDROID_API__ < 24)
# define TRY_PREADV 1
#endif
diff --git a/src/unix/internal.h b/src/unix/internal.h
index fe588513..ddc744b2 100644
--- a/src/unix/internal.h
+++ b/src/unix/internal.h
@@ -215,6 +215,7 @@ struct uv__statx {
defined(__FreeBSD__) || \
defined(__linux__) || \
defined(__OpenBSD__) || \
+ defined(__NuttX__) || \
defined(__NetBSD__)
#define uv__nonblock uv__nonblock_ioctl
#define UV__NONBLOCK_IS_IOCTL 1
diff --git a/src/unix/loop.c b/src/unix/loop.c
index a9468e8e..30ecc532 100644
--- a/src/unix/loop.c
+++ b/src/unix/loop.c
@@ -220,8 +220,10 @@ int uv__loop_configure(uv_loop_t* loop, uv_loop_option option, va_list ap) {
if (option != UV_LOOP_BLOCK_SIGNAL)
return UV_ENOSYS;
+#ifdef SIGPROF
if (va_arg(ap, int) != SIGPROF)
return UV_EINVAL;
+#endif
loop->flags |= UV_LOOP_BLOCK_SIGPROF;
return 0;
diff --git a/src/unix/nuttx.c b/src/unix/nuttx.c
new file mode 100644
index 00000000..298bd2f8
--- /dev/null
+++ b/src/unix/nuttx.c
@@ -0,0 +1,303 @@
+/* Copyright Xiaomi, 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
+ * deal in the Software without restriction, including without limitation the
+ * rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
+ * sell copies of the Software, and to permit persons to whom the Software is
+ * furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in
+ * all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+ * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
+ * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
+ * IN THE SOFTWARE.
+ */
+
+/* We lean on the fact that POLL{IN,OUT,ERR,HUP} correspond with their
+ * EPOLL* counterparts. We use the POLL* variants in this file because that
+ * is what libuv uses elsewhere.
+ */
+
+#include "internal.h"
+#include "uv.h"
+#include "uv-global.h"
+
+#include <ifaddrs.h>
+#include <malloc.h>
+#include <net/if.h>
+#include <pthread.h>
+#include <sys/sysinfo.h>
+#include <unistd.h>
+
+#include <nuttx/tls.h>
+
+int uv_exepath(char* buffer, size_t* size) {
+ return UV_ENOTSUP;
+}
+
+char** uv_setup_args(int argc, char** argv) {
+ return argv;
+}
+
+void uv__process_title_cleanup(void) {
+}
+
+int uv_set_process_title(const char* title) {
+ return UV__ERR(pthread_setname_np(pthread_self(), title));
+}
+
+int uv_get_process_title(char* buffer, size_t size) {
+ return UV__ERR(pthread_getname_np(pthread_self(), buffer, size));
+}
+
+uint64_t uv_get_constrained_memory(void) {
+ return 0; /* Memory constraints are unknown. */
+}
+
+uint64_t uv_get_available_memory(void) {
+ return uv_get_free_memory();
+}
+
+int uv_resident_set_memory(size_t* rss) {
+ struct sysinfo info;
+ int ret;
+
+ ret = sysinfo(&info);
+ if (ret >= 0)
+ {
+ *rss = (info.totalram - info.freeram) * info.mem_unit;
+ }
+ else
+ {
+ ret = UV__ERR(errno);
+ }
+
+ return ret;
+}
+
+int uv_uptime(double* uptime) {
+ struct sysinfo info;
+ int ret;
+
+
+ ret = sysinfo(&info);
+ if (ret >= 0)
+ {
+ *uptime = info.uptime;
+ }
+ else
+ {
+ ret = UV__ERR(errno);
+ }
+
+ return ret;
+}
+
+int uv_cpu_info(uv_cpu_info_t** cpu_infos, int* count) {
+ *count = sysconf(_SC_NPROCESSORS_ONLN);
+ *cpu_infos = uv__calloc(*count, sizeof(uv_cpu_info_t));
+ if (!*cpu_infos) {
+ return UV_ENOMEM;
+ }
+
+ return 0;
+}
+
+#ifndef CONFIG_NETDEV_IFINDEX
+unsigned int if_nametoindex(const char *ifname) {
+ return 0;
+}
+
+int uv_interface_addresses(uv_interface_address_t** addresses, int* count) {
+ return UV_ENOSYS;
+}
+
+void uv_free_interface_addresses(uv_interface_address_t* addresses, int count) {
+}
+#else
+static int uv__ifaddr_exclude(struct ifaddrs *ent) {
+ if (!((ent->ifa_flags & IFF_UP) && (ent->ifa_flags & IFF_RUNNING)))
+ return 1;
+ if (ent->ifa_addr == NULL)
+ return 1;
+ return 0;
+}
+
+int uv_interface_addresses(uv_interface_address_t** addresses, int* count) {
+ struct ifaddrs* addrs;
+ struct ifaddrs* ent;
+ uv_interface_address_t* address;
+
+ *count = 0;
+ *addresses = NULL;
+
+ if (getifaddrs(&addrs) != 0)
+ return UV__ERR(errno);
+
+ /* Count the number of interfaces */
+ for (ent = addrs; ent != NULL; ent = ent->ifa_next) {
+ if (uv__ifaddr_exclude(ent))
+ continue;
+ (*count)++;
+ }
+
+ if (*count == 0) {
+ freeifaddrs(addrs);
+ return 0;
+ }
+
+ /* Make sure the memory is initiallized to zero using calloc() */
+ *addresses = uv__calloc(*count, sizeof(**addresses));
+ if (*addresses == NULL) {
+ freeifaddrs(addrs);
+ return UV_ENOMEM;
+ }
+
+ address = *addresses;
+ for (ent = addrs; ent != NULL; ent = ent->ifa_next) {
+ if (uv__ifaddr_exclude(ent))
+ continue;
+
+ address->name = uv__strdup(ent->ifa_name);
+
+ if (ent->ifa_addr->sa_family == AF_INET6) {
+ address->address.address6 = *((struct sockaddr_in6*) ent->ifa_addr);
+ } else {
+ address->address.address4 = *((struct sockaddr_in*) ent->ifa_addr);
+ }
+
+ if (ent->ifa_netmask) {
+ if (ent->ifa_netmask->sa_family == AF_INET6) {
+ address->netmask.netmask6 = *((struct sockaddr_in6*) ent->ifa_netmask);
+ } else {
+ address->netmask.netmask4 = *((struct sockaddr_in*) ent->ifa_netmask);
+ }
+ }
+
+ if (ent->ifa_data) {
+ struct sockaddr* addr = ent->ifa_data;
+ memcpy(address->phys_addr, addr->sa_data, sizeof(address->phys_addr));
+ }
+
+ address->is_internal = !strcmp(address->name, "lo");
+ address++;
+ }
+
+ freeifaddrs(addrs);
+ return 0;
+}
+
+void uv_free_interface_addresses(uv_interface_address_t* addresses, int count) {
+ int i;
+
+ for (i = 0; i < count; i++) {
+ uv__free(addresses[i].name);
+ }
+
+ uv__free(addresses);
+}
+#endif
+
+#ifndef CONFIG_NET_SOCKOPTS
+int getsockopt(int sockfd, int level, int option, void *value, socklen_t *value_len) {
+ if (option == SO_ERROR) {
+ *(int *)value = UV_ENOTSUP;
+ }
+
+ return UV_ENOTSUP;
+}
+#endif
+
+#ifndef CONFIG_NET
+int getsockname(int sockfd, struct sockaddr *addr, socklen_t *addrlen) {
+ return UV_ENOTSUP;
+}
+
+ssize_t recvmsg(int sockfd, struct msghdr *msg, int flags) {
+ return UV_ENOTSUP;
+}
+
+ssize_t sendmsg(int sockfd, struct msghdr *msg, int flags) {
+ return UV_ENOTSUP;
+}
+
+int shutdown(int sockfd, int how) {
+ return UV_ENOTSUP;
+}
+#endif
+
+#ifndef CONFIG_NET_TCP
+int uv_tcp_listen(uv_tcp_t* tcp, int backlog, uv_connection_cb cb) {
+ return UV_ENOTSUP;
+}
+
+void uv__tcp_close(uv_tcp_t* handle) {
+}
+
+int uv__tcp_nodelay(int fd, int on) {
+ return UV_ENOTSUP;
+}
+
+int uv__tcp_keepalive(int fd, int on, unsigned int delay) {
+ return UV_ENOTSUP;
+}
+#endif
+
+#ifndef CONFIG_NET_UDP
+int uv_udp_open(uv_udp_t* handle, uv_os_sock_t sock) {
+ return UV_ENOTSUP;
+}
+
+void uv__udp_close(uv_udp_t* handle) {
+}
+
+void uv__udp_finish_close(uv_udp_t* handle) {
+}
+#endif
+
+#if CONFIG_TLS_TASK_NELEM == 0
+# error "libuv depends on CONFIG_TLS_TASK_NELEM, please enable it by menuconfig"
+#endif
+
+#undef once
+#undef uv__signal_global_init_guard
+#undef uv__signal_lock_pipefd
+
+static void uv__global_free(void* global) {
+ if (global) {
+ uv_library_shutdown();
+ uv__free(global);
+ }
+}
+
+uv__global_t* uv__global_get(void) {
+ static int index = -1;
+ static const uv_once_t once = UV_ONCE_INIT;
+ uv__global_t* global = NULL;
+
+ if (index < 0) {
+ index = task_tls_alloc(uv__global_free);
+ }
+
+ if (index >= 0) {
+ global = (uv__global_t*)task_tls_get_value(index);
+ if (global == NULL) {
+ global = (uv__global_t*)uv__calloc(1, sizeof(uv__global_t));
+ if (global) {
+ global->once = once;
+ global->uv__signal_global_init_guard = once;
+ global->uv__signal_lock_pipefd[0] = -1;
+ global->uv__signal_lock_pipefd[1] = -1;
+ task_tls_set_value(index, (uintptr_t)global);
+ }
+ }
+ }
+
+ ASSERT(global != NULL);
+ return global;
+}
diff --git a/src/unix/pipe.c b/src/unix/pipe.c
index d332f351..7f1deeb1 100644
--- a/src/unix/pipe.c
+++ b/src/unix/pipe.c
@@ -28,7 +28,9 @@
#include <sys/un.h>
#include <unistd.h>
#include <stdlib.h>
-
+#ifdef CONFIG_NET_RPMSG
+#include <netpacket/rpmsg.h>
+#endif // CONFIG_NET_RPMSG
int uv_pipe_init(uv_loop_t* loop, uv_pipe_t* handle, int ipc) {
uv__stream_init(loop, (uv_stream_t*)handle, UV_NAMED_PIPE);
@@ -126,6 +128,48 @@ err_socket:
return err;
}
+#ifdef CONFIG_NET_RPMSG
+int uv_pipe_rpmsg_bind(uv_pipe_t* handle,
+ const char* name,
+ const char* cpu_name) {
+ struct sockaddr_rpmsg saddr;
+ int sockfd;
+ int err;
+
+ /* Already bound? */
+ if (uv__stream_fd(handle) >= 0)
+ return UV_EINVAL;
+
+ err = uv__socket(AF_RPMSG, SOCK_STREAM, 0);
+ if (err < 0)
+ goto err_socket;
+ sockfd = err;
+
+ memset(&saddr, 0, sizeof saddr);
+ uv__strscpy(saddr.rp_name, name, sizeof(saddr.rp_name));
+ uv__strscpy(saddr.rp_cpu, cpu_name, sizeof(saddr.rp_cpu));
+ saddr.rp_family = AF_RPMSG;
+
+ if (bind(sockfd, (struct sockaddr*)&saddr, sizeof saddr)) {
+ err = UV__ERR(errno);
+ /* Convert ENOENT to EACCES for compatibility with Windows. */
+ if (err == UV_ENOENT)
+ err = UV_EACCES;
+
+ uv__close(sockfd);
+ goto err_socket;
+ }
+
+ /* Success. */
+ handle->flags |= UV_HANDLE_BOUND;
+ handle->pipe_fname = NULL;
+ handle->io_watcher.fd = sockfd;
+ return 0;
+
+err_socket:
+ return err;
+}
+#endif
int uv__pipe_listen(uv_pipe_t* handle, int backlog, uv_connection_cb cb) {
if (uv__stream_fd(handle) == -1)
diff --git a/src/unix/posix-poll.c b/src/unix/posix-poll.c
index 2e016c2f..3a351742 100644
--- a/src/unix/posix-poll.c
+++ b/src/unix/posix-poll.c
@@ -145,8 +145,8 @@ void uv__io_poll(uv_loop_t* loop, int timeout) {
int have_signals;
struct pollfd* pe;
int fd;
- int user_timeout;
- int reset_timeout;
+ int user_timeout = 0;
+ int reset_timeout = 0;
if (loop->nfds == 0) {
assert(uv__queue_empty(&loop->watcher_queue));
@@ -173,11 +173,15 @@ void uv__io_poll(uv_loop_t* loop, int timeout) {
/* Prepare a set of signals to block around poll(), if any. */
pset = NULL;
+#ifdef SIGPROF
if (loop->flags & UV_LOOP_BLOCK_SIGPROF) {
pset = &set;
sigemptyset(pset);
sigaddset(pset, SIGPROF);
}
+#else
+ (void) set;
+#endif
assert(timeout >= -1);
time_base = loop->time;
diff --git a/src/unix/process-spawn.c b/src/unix/process-spawn.c
new file mode 100644
index 00000000..9b9668d1
--- /dev/null
+++ b/src/unix/process-spawn.c
@@ -0,0 +1,380 @@
+/* Copyright Xiaomi, 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
+ * deal in the Software without restriction, including without limitation the
+ * rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
+ * sell copies of the Software, and to permit persons to whom the Software is
+ * furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in
+ * all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+ * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
+ * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
+ * IN THE SOFTWARE.
+ */
+
+#define __USE_GNU
+#include "uv.h"
+#include "internal.h"
+
+#include <stdio.h>
+#include <stdlib.h>
+#include <assert.h>
+#include <errno.h>
+
+#include <sys/types.h>
+#include <sys/wait.h>
+#include <unistd.h>
+#include <fcntl.h>
+#include <spawn.h>
+
+#ifdef SIGCHLD
+static void uv__chld(uv_signal_t* handle, int signum) {
+ uv_process_t* process;
+ uv_loop_t* loop;
+ int exit_status;
+ int term_signal;
+ int status;
+ pid_t pid;
+ struct uv__queue pending;
+ struct uv__queue* q;
+ struct uv__queue* h;
+
+ assert(signum == SIGCHLD);
+
+ uv__queue_init(&pending);
+ loop = handle->loop;
+
+ h = &loop->process_handles;
+ q = uv__queue_head(h);
+ while (q != h) {
+ process = uv__queue_data(q, uv_process_t, queue);
+ q = uv__queue_next(q);
+
+ do
+ pid = waitpid(process->pid, &status, WNOHANG);
+ while (pid == -1 && errno == EINTR);
+
+ if (pid == 0)
+ continue;
+
+ if (pid == -1) {
+ if (errno != ECHILD)
+ abort();
+ continue;
+ }
+
+ process->status = status;
+ uv__queue_remove(&process->queue);
+ uv__queue_insert_tail(&pending, &process->queue);
+ }
+
+ h = &pending;
+ q = uv__queue_head(h);
+ while (q != h) {
+ process = uv__queue_data(q, uv_process_t, queue);
+ q = uv__queue_next(q);
+
+ uv__queue_remove(&process->queue);
+ uv__queue_init(&process->queue);
+ uv__handle_stop(process);
+
+ if (process->exit_cb == NULL)
+ continue;
+
+ exit_status = 0;
+ if (WIFEXITED(process->status))
+ exit_status = WEXITSTATUS(process->status);
+
+ term_signal = 0;
+ if (WIFSIGNALED(process->status))
+ term_signal = WTERMSIG(process->status);
+
+ process->exit_cb(process, exit_status, term_signal);
+ }
+ assert(uv__queue_empty(&pending));
+}
+
+
+int uv__process_init(uv_loop_t* loop) {
+ int err;
+
+ err = uv_signal_init(loop, &loop->child_watcher);
+ if (err)
+ return err;
+ uv__handle_unref(&loop->child_watcher);
+ loop->child_watcher.flags |= UV_HANDLE_INTERNAL;
+ return 0;
+}
+#endif
+
+/*
+ * Used for initializing stdio streams like options.stdin_stream. Returns
+ * zero on success. See also the cleanup section in uv_spawn().
+ */
+static int uv__process_init_stdio(uv_stdio_container_t* container, int fds[2]) {
+ int mask;
+ int fd;
+
+ mask = UV_IGNORE | UV_CREATE_PIPE | UV_INHERIT_FD | UV_INHERIT_STREAM;
+
+ switch (container->flags & mask) {
+ case UV_IGNORE:
+ return 0;
+
+ case UV_CREATE_PIPE:
+ assert(container->data.stream != NULL);
+ if (container->data.stream->type != UV_NAMED_PIPE)
+ return UV_EINVAL;
+ else
+ return uv_pipe(fds, 0, 0);
+
+ case UV_INHERIT_FD:
+ case UV_INHERIT_STREAM:
+ if (container->flags & UV_INHERIT_FD)
+ fd = container->data.fd;
+ else
+ fd = uv__stream_fd(container->data.stream);
+
+ if (fd == -1)
+ return UV_EINVAL;
+
+ fds[0] = fds[1] = fd;
+ return 0;
+
+ default:
+ assert(0 && "Unexpected flags");
+ return UV_EINVAL;
+ }
+}
+
+
+static int uv__process_open_stream(uv_stdio_container_t* container,
+ int pipefds[2]) {
+ int flags;
+
+ if (!(container->flags & UV_CREATE_PIPE) || pipefds[0] < 0)
+ return 0;
+
+ uv__nonblock(pipefds[0], 1);
+
+ flags = 0;
+ if (container->flags & UV_WRITABLE_PIPE)
+ flags |= UV_HANDLE_READABLE;
+ if (container->flags & UV_READABLE_PIPE)
+ flags |= UV_HANDLE_WRITABLE;
+
+ return uv__stream_open(container->data.stream, pipefds[0], flags);
+}
+
+
+static void uv__process_close_stream(uv_stdio_container_t* container) {
+ if (!(container->flags & UV_CREATE_PIPE)) return;
+ uv__stream_close(container->data.stream);
+}
+
+
+static int uv__process_child_spawn(const uv_process_options_t* options,
+ int stdio_count,
+ int (*pipes)[2],
+ pid_t *pid) {
+ posix_spawn_file_actions_t file_actions;
+ posix_spawnattr_t attr;
+ sigset_t set;
+ int use_fd;
+ int flags;
+ int err;
+ int fd;
+
+ posix_spawn_file_actions_init(&file_actions);
+ posix_spawnattr_init(&attr);
+
+ /* Reset signal disposition and mask */
+ flags = POSIX_SPAWN_SETSIGDEF | POSIX_SPAWN_SETSIGMASK;
+
+ sigfillset(&set);
+ posix_spawnattr_setsigdefault(&attr, &set);
+
+ sigemptyset(&set);
+ posix_spawnattr_setsigmask(&attr, &set);
+
+ if (options->flags & UV_PROCESS_DETACHED)
+ flags |= POSIX_SPAWN_SETSID;
+
+ /* First duplicate low numbered fds, since it's not safe to duplicate them,
+ * they could get replaced. Example: swapping stdout and stderr; without
+ * this fd 2 (stderr) would be duplicated into fd 1, thus making both
+ * stdout and stderr go to the same fd, which was not the intention. */
+ for (fd = 0; fd < stdio_count; fd++) {
+ use_fd = pipes[fd][1];
+ if (use_fd < 0 || use_fd >= fd)
+ continue;
+ pipes[fd][1] = fcntl(use_fd, F_DUPFD, stdio_count);
+ if (pipes[fd][1] == -1) {
+ err = errno;
+ goto error;
+ }
+ }
+
+ for (fd = 0; fd < stdio_count; fd++) {
+ use_fd = pipes[fd][1];
+
+ if (use_fd < 0) {
+ if (fd >= 3)
+ continue;
+ else {
+ /* redirect stdin, stdout and stderr to /dev/null even if UV_IGNORE is
+ * set
+ */
+ use_fd = open("/dev/null", fd == 0 ? O_RDONLY : O_RDWR);
+ pipes[fd][1] = use_fd;
+
+ if (use_fd < 0) {
+ err = errno;
+ goto error;
+ }
+ }
+ }
+
+ if (fd == use_fd)
+ uv__cloexec(use_fd, 0);
+ else
+ posix_spawn_file_actions_adddup2(&file_actions, use_fd, fd);
+
+ if (fd <= 2)
+ uv__nonblock_fcntl(use_fd, 0);
+ }
+
+ if (options->flags & UV_PROCESS_SETUID) {
+ err = options->uid ? ENOTSUP : EPERM;
+ goto error;
+ }
+
+ if (options->flags & UV_PROCESS_SETGID) {
+ if (options->gid == 0) {
+ err = EPERM;
+ goto error;
+ }
+
+ posix_spawnattr_setpgroup(&attr, options->gid);
+ flags |= POSIX_SPAWN_SETPGROUP;
+ }
+
+ posix_spawnattr_setflags(&attr, flags);
+ err = posix_spawn(pid, options->file, &file_actions, &attr,
+ options->args, options->env ? options->env : environ);
+
+error:
+ for (fd = 0; fd < stdio_count; fd++) {
+ if (pipes[fd][1] >= 0 && pipes[fd][1] != pipes[fd][0]) {
+ close(pipes[fd][1]);
+ pipes[fd][1] = -1;
+ }
+ }
+
+ posix_spawn_file_actions_destroy(&file_actions);
+ posix_spawnattr_destroy(&attr);
+ return UV__ERR(err);
+}
+
+
+int uv_spawn(uv_loop_t* loop,
+ uv_process_t* process,
+ const uv_process_options_t* options) {
+ int pipes_storage[8][2];
+ int (*pipes)[2];
+ int stdio_count;
+ pid_t pid;
+ int err;
+ int i;
+
+ assert(options->file != NULL);
+ assert(!(options->flags & ~(UV_PROCESS_DETACHED |
+ UV_PROCESS_SETGID |
+ UV_PROCESS_SETUID |
+ UV_PROCESS_WINDOWS_HIDE |
+ UV_PROCESS_WINDOWS_HIDE_CONSOLE |
+ UV_PROCESS_WINDOWS_HIDE_GUI |
+ UV_PROCESS_WINDOWS_VERBATIM_ARGUMENTS)));
+
+ uv__handle_init(loop, (uv_handle_t*)process, UV_PROCESS);
+ uv__queue_init(&process->queue);
+
+ stdio_count = options->stdio_count;
+ if (stdio_count < 3)
+ stdio_count = 3;
+
+ err = UV_ENOMEM;
+ pipes = pipes_storage;
+ if (stdio_count > (int)ARRAY_SIZE(pipes_storage))
+ pipes = uv__malloc(stdio_count * sizeof(*pipes));
+
+ if (pipes == NULL)
+ goto error;
+
+ for (i = 0; i < stdio_count; i++) {
+ pipes[i][0] = -1;
+ pipes[i][1] = -1;
+ }
+
+ for (i = 0; i < options->stdio_count; i++) {
+ err = uv__process_init_stdio(options->stdio + i, pipes[i]);
+ if (err)
+ goto error;
+ }
+
+#ifdef SIGCHLD
+ uv_signal_start(&loop->child_watcher, uv__chld, SIGCHLD);
+#endif
+
+ err = uv__process_child_spawn(options, stdio_count, pipes, &pid);
+ if (err)
+ goto error;
+
+ for (i = 0; i < options->stdio_count; i++) {
+ err = uv__process_open_stream(options->stdio + i, pipes[i]);
+ if (err == 0)
+ continue;
+
+ while (i--)
+ uv__process_close_stream(options->stdio + i);
+
+ goto error;
+ }
+
+ uv__queue_insert_tail(&loop->process_handles, &process->queue);
+ uv__handle_start(process);
+
+ process->status = 0;
+ process->pid = pid;
+ process->exit_cb = options->exit_cb;
+
+ if (pipes != pipes_storage)
+ uv__free(pipes);
+
+ return 0;
+
+error:
+ if (pipes != NULL) {
+ for (i = 0; i < stdio_count; i++) {
+ if (i < options->stdio_count)
+ if (options->stdio[i].flags & (UV_INHERIT_FD | UV_INHERIT_STREAM))
+ continue;
+ if (pipes[i][0] != -1)
+ uv__close_nocheckstdio(pipes[i][0]);
+ if (pipes[i][1] != -1)
+ uv__close_nocheckstdio(pipes[i][1]);
+ }
+
+ if (pipes != pipes_storage)
+ uv__free(pipes);
+ }
+
+ return err;
+}
diff --git a/src/unix/signal.c b/src/unix/signal.c
index 63aba5a6..28b80eff 100644
--- a/src/unix/signal.c
+++ b/src/unix/signal.c
@@ -20,6 +20,7 @@
#include "uv.h"
#include "internal.h"
+#include "uv-global.h"
#include <assert.h>
#include <errno.h>
@@ -32,14 +33,6 @@
# define SA_RESTART 0
#endif
-typedef struct {
- uv_signal_t* handle;
- int signum;
-} uv__signal_msg_t;
-
-RB_HEAD(uv__signal_tree_s, uv_signal_s);
-
-
static int uv__signal_unlock(void);
static int uv__signal_start(uv_signal_t* handle,
uv_signal_cb signal_cb,
@@ -50,12 +43,6 @@ static int uv__signal_compare(uv_signal_t* w1, uv_signal_t* w2);
static void uv__signal_stop(uv_signal_t* handle);
static void uv__signal_unregister_handler(int signum);
-
-static uv_once_t uv__signal_global_init_guard = UV_ONCE_INIT;
-static struct uv__signal_tree_s uv__signal_tree =
- RB_INITIALIZER(uv__signal_tree);
-static int uv__signal_lock_pipefd[2] = { -1, -1 };
-
RB_GENERATE_STATIC(uv__signal_tree_s,
uv_signal_s, tree_entry,
uv__signal_compare)
@@ -558,3 +545,21 @@ static void uv__signal_stop(uv_signal_t* handle) {
handle->signum = 0;
uv__handle_stop(handle);
}
+
+int uv_process_kill(uv_process_t* process, int signum) {
+ return uv_kill(process->pid, signum);
+}
+
+int uv_kill(int pid, int signum) {
+ if (kill(pid, signum))
+ return UV__ERR(errno);
+ else
+ return 0;
+}
+
+void uv__process_close(uv_process_t* handle) {
+ uv__queue_remove(&handle->queue);
+ uv__handle_stop(handle);
+ if (uv__queue_empty(&handle->loop->process_handles))
+ uv_signal_stop(&handle->loop->child_watcher);
+}
diff --git a/src/unix/tcp.c b/src/unix/tcp.c
index d6c848f4..639b99c5 100644
--- a/src/unix/tcp.c
+++ b/src/unix/tcp.c
@@ -160,7 +160,7 @@ int uv__tcp_bind(uv_tcp_t* tcp,
if (setsockopt(tcp->io_watcher.fd, SOL_SOCKET, SO_REUSEADDR, &on, sizeof(on)))
return UV__ERR(errno);
-#ifndef __OpenBSD__
+#if !defined(__OpenBSD__) && !defined(__NuttX__)
#ifdef IPV6_V6ONLY
if (addr->sa_family == AF_INET6) {
on = (flags & UV_TCP_IPV6ONLY) != 0;
diff --git a/src/unix/thread.c b/src/unix/thread.c
old mode 100644
new mode 100755
index 4d6f4b82..0f024e7a
--- a/src/unix/thread.c
+++ b/src/unix/thread.c
@@ -158,16 +158,25 @@ int uv_thread_create_ex(uv_thread_t* tid,
stack_size = min_stack_size;
}
- if (stack_size > 0) {
+ if (stack_size > 0 || (params->flags & UV_THREAD_HAS_PRIORITY)) {
attr = &attr_storage;
if (pthread_attr_init(attr))
abort();
+ }
+ if (stack_size > 0) {
if (pthread_attr_setstacksize(attr, stack_size))
abort();
}
+ if (params->flags & UV_THREAD_HAS_PRIORITY) {
+ struct sched_param param;
+ pthread_attr_getschedparam(attr, &param);
+ param.sched_priority = params->priority;
+ pthread_attr_setschedparam(attr, &param);
+ }
+
f.in = entry;
err = pthread_create(tid, attr, f.out, arg);
diff --git a/src/unix/tty.c b/src/unix/tty.c
index d099bdb3..06f23b75 100644
--- a/src/unix/tty.c
+++ b/src/unix/tty.c
@@ -79,6 +79,7 @@ int uv__tcsetattr(int fd, int how, const struct termios *term) {
return 0;
}
+#ifndef __NuttX__
static int uv__tty_is_slave(const int fd) {
int result;
#if defined(__linux__) || defined(__FreeBSD__)
@@ -132,15 +133,13 @@ static int uv__tty_is_slave(const int fd) {
#endif
return result;
}
+#endif
int uv_tty_init(uv_loop_t* loop, uv_tty_t* tty, int fd, int unused) {
uv_handle_type type;
int flags;
- int newfd;
- int r;
int saved_flags;
int mode;
- char path[256];
(void)unused; /* deprecated parameter is no longer needed */
/* File descriptors that refer to files cannot be monitored with epoll.
@@ -152,7 +151,6 @@ int uv_tty_init(uv_loop_t* loop, uv_tty_t* tty, int fd, int unused) {
return UV_EINVAL;
flags = 0;
- newfd = -1;
/* Save the fd flags in case we need to restore them due to an error. */
do
@@ -163,6 +161,7 @@ int uv_tty_init(uv_loop_t* loop, uv_tty_t* tty, int fd, int unused) {
return UV__ERR(errno);
mode = saved_flags & O_ACCMODE;
+#ifndef __NuttX__
/* Reopen the file descriptor when it refers to a tty. This lets us put the
* tty in non-blocking mode without affecting other processes that share it
* with us.
@@ -174,6 +173,10 @@ int uv_tty_init(uv_loop_t* loop, uv_tty_t* tty, int fd, int unused) {
* other processes.
*/
if (type == UV_TTY) {
+ int newfd;
+ int r;
+ char path[256];
+
/* Reopening a pty in master mode won't work either because the reopened
* pty will be in slave mode (*BSD) or reopening will allocate a new
* master/slave pair (Linux). Therefore check if the fd points to a
@@ -207,6 +210,7 @@ int uv_tty_init(uv_loop_t* loop, uv_tty_t* tty, int fd, int unused) {
}
skip:
+#endif
uv__stream_init(loop, (uv_stream_t*) tty, UV_TTY);
/* If anything fails beyond this point we need to remove the handle from
diff --git a/src/unix/udp.c b/src/unix/udp.c
index c2814512..a41478f2 100644
--- a/src/unix/udp.c
+++ b/src/unix/udp.c
@@ -943,6 +943,7 @@ static int uv__udp_set_source_membership6(uv_udp_t* handle,
const char* interface_addr,
const struct sockaddr_in6* source_addr,
uv_membership membership) {
+#ifndef __NuttX__
struct group_source_req mreq;
struct sockaddr_in6 addr6;
int optname;
@@ -984,6 +985,9 @@ static int uv__udp_set_source_membership6(uv_udp_t* handle,
}
return 0;
+#else
+ return UV_ENOSYS;
+#endif
}
#endif
diff --git a/src/uv-common.c b/src/uv-common.c
index 916f3f4e..5dceb29e 100644
--- a/src/uv-common.c
+++ b/src/uv-common.c
@@ -21,6 +21,7 @@
#include "uv.h"
#include "uv-common.h"
+#include "uv-global.h"
#include <assert.h>
#include <errno.h>
@@ -813,10 +814,6 @@ int uv_loop_configure(uv_loop_t* loop, uv_loop_option option, ...) {
}
-static uv_loop_t default_loop_struct;
-static uv_loop_t* default_loop_ptr;
-
-
uv_loop_t* uv_default_loop(void) {
if (default_loop_ptr != NULL)
return default_loop_ptr;
@@ -942,7 +939,6 @@ void uv_free_cpu_info(uv_cpu_info_t* cpu_infos, int count) {
__attribute__((destructor))
#endif
void uv_library_shutdown(void) {
- static int was_shutdown;
if (uv__exchange_int_relaxed(&was_shutdown, 1))
return;
@@ -1024,3 +1020,22 @@ uint64_t uv_metrics_idle_time(uv_loop_t* loop) {
idle_time += uv_hrtime() - entry_time;
return idle_time;
}
+
+/* Add uv_global_get here since all system need it but NuttX */
+
+#ifndef __NuttX__
+#undef once
+#undef uv__signal_global_init_guard
+#undef uv__signal_lock_pipefd
+
+uv__global_t* uv__global_get(void)
+{
+ static uv__global_t g_uv_common_global = {
+ .once = UV_ONCE_INIT,
+ .uv__signal_global_init_guard = UV_ONCE_INIT,
+ .uv__signal_lock_pipefd = {-1, -1},
+ };
+
+ return &g_uv_common_global;
+}
+#endif
diff --git a/src/uv-global.h b/src/uv-global.h
new file mode 100644
index 00000000..1d21d277
--- /dev/null
+++ b/src/uv-global.h
@@ -0,0 +1,96 @@
+/* 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
+ * deal in the Software without restriction, including without limitation the
+ * rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
+ * sell copies of the Software, and to permit persons to whom the Software is
+ * furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in
+ * all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+ * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
+ * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
+ * IN THE SOFTWARE.
+ */
+
+#ifndef UV_GLOBAL_H
+#define UV_GLOBAL_H
+
+#include "uv.h"
+
+#ifndef DEF_THREADPOOL_SIZE
+# define DEF_THREADPOOL_SIZE 4
+#endif
+
+#if !defined(_WIN32)
+typedef struct {
+ uv_signal_t* handle;
+ int signum;
+} uv__signal_msg_t;
+
+RB_HEAD(uv__signal_tree_s, uv_signal_s);
+#endif
+
+typedef struct {
+ /* Member in threadpool.c */
+ uv_once_t once;
+ uv_cond_t cond;
+ uv_mutex_t mutex;
+ unsigned int idle_threads;
+ unsigned int slow_io_work_running;
+ unsigned int nthreads;
+ uv_thread_t* threads;
+ uv_thread_t default_threads[DEF_THREADPOOL_SIZE];
+ struct uv__queue exit_message;
+ struct uv__queue wq;
+ struct uv__queue run_slow_work_message;
+ struct uv__queue slow_io_pending_wq;
+ /* Member in uv-common.c */
+ int was_shutdown;
+ uv_loop_t default_loop_struct;
+ uv_loop_t* default_loop_ptr;
+#if !defined(_WIN32)
+ /* Member in signal.c */
+ uv_once_t uv__signal_global_init_guard;
+ struct uv__signal_tree_s uv__signal_tree;
+ int uv__signal_lock_pipefd[2];
+#endif
+} uv__global_t;
+
+uv__global_t* uv__global_get(void);
+
+/* Used in threadpool.c */
+
+#define once uv__global_get()->once
+#define cond uv__global_get()->cond
+#define mutex uv__global_get()->mutex
+#define idle_threads uv__global_get()->idle_threads
+#define slow_io_work_running uv__global_get()->slow_io_work_running
+#define nthreads uv__global_get()->nthreads
+#define threads uv__global_get()->threads
+#define default_threads uv__global_get()->default_threads
+#define exit_message uv__global_get()->exit_message
+#define lwq uv__global_get()->wq
+#define run_slow_work_message uv__global_get()->run_slow_work_message
+#define slow_io_pending_wq uv__global_get()->slow_io_pending_wq
+
+/* Used in uv-common.c */
+
+#define was_shutdown uv__global_get()->was_shutdown
+#define default_loop_struct uv__global_get()->default_loop_struct
+#define default_loop_ptr uv__global_get()->default_loop_ptr
+
+#if !defined(_WIN32)
+/* Used in signal.c */
+
+#define uv__signal_global_init_guard uv__global_get()->uv__signal_global_init_guard
+#define uv__signal_tree uv__global_get()->uv__signal_tree
+#define uv__signal_lock_pipefd uv__global_get()->uv__signal_lock_pipefd
+#endif
+
+#endif
diff --git a/test/benchmark-pound.c b/test/benchmark-pound.c
index acfe4497..70803646 100644
--- a/test/benchmark-pound.c
+++ b/test/benchmark-pound.c
@@ -84,9 +84,8 @@ static void close_cb(uv_handle_t* handle);
static void alloc_cb(uv_handle_t* handle,
size_t suggested_size,
uv_buf_t* buf) {
- static char slab[65536];
- buf->base = slab;
- buf->len = sizeof(slab);
+ buf->base = malloc(65536);
+ buf->len = 65536;
}
@@ -155,6 +154,7 @@ static void read_cb(uv_stream_t* stream, ssize_t nread, const uv_buf_t* buf) {
ASSERT(0);
}
}
+ free(buf->base);
}
diff --git a/test/benchmark-udp-pummel.c b/test/benchmark-udp-pummel.c
index f89913b6..71327e20 100644
--- a/test/benchmark-udp-pummel.c
+++ b/test/benchmark-udp-pummel.c
@@ -62,10 +62,9 @@ static int exiting;
static void alloc_cb(uv_handle_t* handle,
size_t suggested_size,
uv_buf_t* buf) {
- static char slab[65536];
- ASSERT(suggested_size <= sizeof(slab));
- buf->base = slab;
- buf->len = sizeof(slab);
+ ASSERT(suggested_size <= 65536);
+ buf->base = malloc(65536);
+ buf->len = 65536;
}
@@ -123,6 +122,8 @@ static void recv_cb(uv_udp_t* handle,
ASSERT(!memcmp(buf->base, EXPECTED, nread));
recv_cb_called++;
+
+ free(buf->base);
}
diff --git a/test/blackhole-server.c b/test/blackhole-server.c
index 0a8758e1..24fdc4ec 100644
--- a/test/blackhole-server.c
+++ b/test/blackhole-server.c
@@ -63,9 +63,8 @@ static void connection_cb(uv_stream_t* stream, int status) {
static void alloc_cb(uv_handle_t* handle,
size_t suggested_size,
uv_buf_t* buf) {
- static char slab[65536];
- buf->base = slab;
- buf->len = sizeof(slab);
+ buf->base = malloc(65536);
+ buf->len = 65536;
}
@@ -82,6 +81,8 @@ static void read_cb(uv_stream_t* stream, ssize_t nread, const uv_buf_t* buf) {
r = uv_shutdown(&conn->shutdown_req, stream, shutdown_cb);
ASSERT(r == 0);
+
+ free(buf->base);
}
diff --git a/test/echo-server.c b/test/echo-server.c
index 058c9925..65ddaf40 100644
--- a/test/echo-server.c
+++ b/test/echo-server.c
@@ -161,9 +161,8 @@ static void slab_alloc(uv_handle_t* handle,
size_t suggested_size,
uv_buf_t* buf) {
/* up to 16 datagrams at once */
- static char slab[16 * 64 * 1024];
- buf->base = slab;
- buf->len = sizeof(slab);
+ buf->base = malloc(16 * 64 * 1024);
+ buf->len = 16 * 64 * 1024;
}
static void on_connection(uv_stream_t* server, int status) {
@@ -224,6 +223,8 @@ static void on_send(uv_udp_send_t* req, int status) {
ASSERT(status == 0);
req->data = send_freelist;
send_freelist = req;
+ ASSERT(req->nbufs == 1);
+ free(req->bufs[0].base);
}
static void on_recv(uv_udp_t* handle,
diff --git a/test/run-tests.c b/test/run-tests.c
index d8cfe297..b4e2a966 100644
--- a/test/run-tests.c
+++ b/test/run-tests.c
@@ -65,7 +65,7 @@ typedef BOOL (WINAPI *sCompareObjectHandles)(_In_ HANDLE, _In_ HANDLE);
int main(int argc, char **argv) {
-#ifndef _WIN32
+#if !defined(_WIN32) && !defined(__NuttX__)
if (0 == geteuid() && NULL == getenv("UV_RUN_AS_ROOT")) {
fprintf(stderr, "The libuv test suite cannot be run as root.\n");
return EXIT_FAILURE;
diff --git a/test/runner-unix.c b/test/runner-unix.c
index 81560add..45fe587a 100644
--- a/test/runner-unix.c
+++ b/test/runner-unix.c
@@ -43,8 +43,10 @@
#ifdef __APPLE__
#include <TargetConditionals.h>
#endif
-
+#ifndef __NuttX__
extern char** environ;
+#endif
+#include <spawn.h>
static void closefd(int fd) {
if (close(fd) == 0 || errno == EINTR || errno == EINPROGRESS)
@@ -83,6 +85,7 @@ void platform_init(int argc, char **argv) {
/* Invoke "argv[0] test-name [test-part]". Store process info in *p. Make sure
* that all stdio output of the processes is buffered up. */
int process_start(char* name, char* part, process_info_t* p, int is_helper) {
+ posix_spawn_file_actions_t file_actions;
FILE* stdout_file;
int stdout_fd;
const char* arg;
@@ -119,12 +122,17 @@ int process_start(char* name, char* part, process_info_t* p, int is_helper) {
return -1;
}
+ posix_spawn_file_actions_init(&file_actions);
+ posix_spawn_file_actions_adddup2(&file_actions, stdout_fd, STDOUT_FILENO);
+ posix_spawn_file_actions_adddup2(&file_actions, stdout_fd, STDERR_FILENO);
+
if (is_helper) {
if (pipe(pipefd)) {
perror("pipe");
return -1;
}
+ posix_spawn_file_actions_addclose(&file_actions, pipefd[0]);
snprintf(fdstr, sizeof(fdstr), "%d", pipefd[1]);
if (setenv("UV_TEST_RUNNER_FD", fdstr, /* overwrite */ 1)) {
perror("setenv");
@@ -136,30 +144,17 @@ int process_start(char* name, char* part, process_info_t* p, int is_helper) {
p->status = 0;
#if defined(__APPLE__) && (TARGET_OS_TV || TARGET_OS_WATCH)
- pid = -1;
+ n = -1;
#else
- pid = fork();
+ n = posix_spawn(&pid, args[0], &file_actions, NULL, args, environ);
+ posix_spawn_file_actions_destroy(&file_actions);
#endif
- if (pid < 0) {
- perror("fork");
+ if (n != 0) {
+ fprintf(stderr, "posix_spawn: %s\n", strerror(n));
return -1;
}
- if (pid == 0) {
- /* child */
- if (is_helper)
- closefd(pipefd[0]);
- dup2(stdout_fd, STDOUT_FILENO);
- dup2(stdout_fd, STDERR_FILENO);
-#if !(defined(__APPLE__) && (TARGET_OS_TV || TARGET_OS_WATCH))
- execve(args[0], args, environ);
-#endif
- perror("execve()");
- _exit(127);
- }
-
- /* parent */
p->pid = pid;
p->name = strdup(name);
p->stdout_file = stdout_file;
diff --git a/test/task.h b/test/task.h
index fa6cc0ed..25af255c 100644
--- a/test/task.h
+++ b/test/task.h
@@ -95,6 +95,7 @@ typedef enum {
/* Have our own assert, so we are sure it does not get optimized away in
* a release build.
*/
+#undef ASSERT
#define ASSERT(expr) \
do { \
if (!(expr)) { \
@@ -309,6 +310,7 @@ enum test_status {
extern int snprintf(char*, size_t, const char*, ...);
#endif
+#undef UNUSED
#if defined(__clang__) || \
defined(__GNUC__) || \
defined(__INTEL_COMPILER)
@@ -351,7 +353,7 @@ UNUSED static int can_ipv6(void) {
return supported;
}
-#if defined(__CYGWIN__) || defined(__MSYS__) || defined(__PASE__)
+#if defined(__CYGWIN__) || defined(__MSYS__) || defined(__PASE__) || defined(__NuttX__)
# define NO_FS_EVENTS "Filesystem watching not supported on this platform."
#endif
diff --git a/test/test-active.c b/test/test-active.c
index aaff9708..38ab885a 100644
--- a/test/test-active.c
+++ b/test/test-active.c
@@ -44,6 +44,8 @@ TEST_IMPL(active) {
int r;
uv_timer_t timer;
+ close_cb_called = 0;
+
r = uv_timer_init(uv_default_loop(), &timer);
ASSERT(r == 0);
diff --git a/test/test-async-null-cb.c b/test/test-async-null-cb.c
index 1bdd0e03..76000480 100644
--- a/test/test-async-null-cb.c
+++ b/test/test-async-null-cb.c
@@ -52,6 +52,8 @@ TEST_IMPL(async_null_cb) {
*/
memset(&async_handle, 0xff, sizeof(async_handle));
+ check_cb_called = 0;
+
ASSERT(0 == uv_async_init(uv_default_loop(), &async_handle, NULL));
ASSERT(0 == uv_check_init(uv_default_loop(), &check_handle));
ASSERT(0 == uv_check_start(&check_handle, check_cb));
diff --git a/test/test-async.c b/test/test-async.c
index 73664ea5..b917378d 100644
--- a/test/test-async.c
+++ b/test/test-async.c
@@ -108,6 +108,10 @@ static void prepare_cb(uv_prepare_t* handle) {
TEST_IMPL(async) {
int r;
+ async_cb_called = 0;
+ close_cb_called = 0;
+ prepare_cb_called = 0;
+
r = uv_mutex_init(&mutex);
ASSERT(r == 0);
uv_mutex_lock(&mutex);
diff --git a/test/test-close-order.c b/test/test-close-order.c
index 768e1cee..9f8d24c5 100644
--- a/test/test-close-order.c
+++ b/test/test-close-order.c
@@ -56,6 +56,11 @@ static void timer_cb(uv_timer_t* handle) {
TEST_IMPL(close_order) {
uv_loop_t* loop;
+
+ check_cb_called = 0;
+ timer_cb_called = 0;
+ close_cb_called = 0;
+
loop = uv_default_loop();
uv_check_init(loop, &check_handle);
diff --git a/test/test-connection-fail.c b/test/test-connection-fail.c
index aa7db30d..ecc99930 100644
--- a/test/test-connection-fail.c
+++ b/test/test-connection-fail.c
@@ -36,6 +36,13 @@ static int timer_close_cb_calls;
static int timer_cb_calls;
+static inline void init_call_count(void) {
+ connect_cb_calls = 0;
+ close_cb_calls = 0;
+ timer_close_cb_calls = 0;
+ timer_cb_calls = 0;
+}
+
static void on_close(uv_handle_t* handle) {
close_cb_calls++;
}
@@ -89,6 +96,9 @@ static void connection_fail(uv_connect_cb connect_cb) {
struct sockaddr_in client_addr, server_addr;
int r;
+ /* Initialize the call counter. */
+ init_call_count();
+
ASSERT(0 == uv_ip4_addr("0.0.0.0", 0, &client_addr));
/* There should be no servers listening on this port. */
diff --git a/test/test-default-loop-close.c b/test/test-default-loop-close.c
index 8d960e11..8fcd9668 100644
--- a/test/test-default-loop-close.c
+++ b/test/test-default-loop-close.c
@@ -36,6 +36,8 @@ TEST_IMPL(default_loop_close) {
uv_loop_t* loop;
uv_timer_t timer_handle;
+ timer_cb_called = 0;
+
loop = uv_default_loop();
ASSERT_NOT_NULL(loop);
diff --git a/test/test-fs-copyfile.c b/test/test-fs-copyfile.c
index d7f04cf4..d13ab6db 100644
--- a/test/test-fs-copyfile.c
+++ b/test/test-fs-copyfile.c
@@ -25,6 +25,7 @@
#if defined(__unix__) || defined(__POSIX__) || \
defined(__APPLE__) || defined(__sun) || \
defined(_AIX) || defined(__MVS__) || \
+ defined(__NuttX__) || \
defined(__HAIKU__) || defined(__QNX__)
#include <unistd.h> /* unlink, etc. */
#else
diff --git a/test/test-fs.c b/test/test-fs.c
index e687dde3..7451b987 100644
--- a/test/test-fs.c
+++ b/test/test-fs.c
@@ -716,6 +716,7 @@ TEST_IMPL(fs_file_noent) {
uv_fs_t req;
int r;
+ open_cb_count = 0;
loop = uv_default_loop();
r = uv_fs_open(NULL, &req, "does_not_exist", O_RDONLY, 0, NULL);
@@ -741,6 +742,7 @@ TEST_IMPL(fs_file_nametoolong) {
int r;
char name[TOO_LONG_NAME_LENGTH + 1];
+ open_cb_count = 0;
loop = uv_default_loop();
memset(name, 'a', TOO_LONG_NAME_LENGTH);
@@ -766,6 +768,7 @@ TEST_IMPL(fs_file_loop) {
uv_fs_t req;
int r;
+ open_cb_count = 0;
loop = uv_default_loop();
unlink("test_symlink");
@@ -912,6 +915,17 @@ static void lutime_cb(uv_fs_t* req) {
TEST_IMPL(fs_file_async) {
int r;
+ open_cb_count = 0;
+ close_cb_count = 0;
+ create_cb_count = 0;
+ read_cb_count = 0;
+ write_cb_count = 0;
+ unlink_cb_count = 0;
+ rename_cb_count = 0;
+ fsync_cb_count = 0;
+ fdatasync_cb_count = 0;
+ ftruncate_cb_count = 0;
+
/* Setup. */
unlink("test_file");
unlink("test_file2");
@@ -1102,6 +1116,12 @@ TEST_IMPL(fs_async_dir) {
int r;
uv_dirent_t dent;
+ unlink_cb_count = 0;
+ mkdir_cb_count = 0;
+ rmdir_cb_count = 0;
+ scandir_cb_count = 0;
+ stat_cb_count = 0;
+
/* Setup */
unlink("test_dir/file1");
unlink("test_dir/file2");
@@ -1199,6 +1219,7 @@ static int test_sendfile(void (*setup)(int), uv_fs_cb cb, off_t expected_size) {
uv_fs_t req;
char buf1[1];
+ sendfile_cb_count = 0;
loop = uv_default_loop();
/* Setup. */
@@ -1294,6 +1315,7 @@ TEST_IMPL(fs_mkdtemp) {
int r;
const char* path_template = "test_dir_XXXXXX";
+ mkdtemp_cb_count = 0;
loop = uv_default_loop();
r = uv_fs_mkdtemp(loop, &mkdtemp_req1, path_template, mkdtemp_cb);
@@ -1327,6 +1349,7 @@ TEST_IMPL(fs_mkstemp) {
const char path_template[] = "test_file_XXXXXX";
uv_fs_t req;
+ mkstemp_cb_count = 0;
loop = uv_default_loop();
r = uv_fs_mkstemp(loop, &mkstemp_req1, path_template, mkstemp_cb);
@@ -1405,6 +1428,8 @@ TEST_IMPL(fs_fstat) {
RETURN_SKIP("Test does not currently work in QEMU");
#endif
+ fstat_cb_count = 0;
+
/* Setup. */
unlink("test_file");
@@ -1595,6 +1620,8 @@ TEST_IMPL(fs_access) {
uv_fs_t req;
uv_file file;
+ access_cb_count = 0;
+
/* Setup. */
unlink("test_file");
rmdir("test_dir");
@@ -1671,6 +1698,9 @@ TEST_IMPL(fs_chmod) {
uv_fs_t req;
uv_file file;
+ chmod_cb_count = 0;
+ fchmod_cb_count = 0;
+
/* Setup. */
unlink("test_file");
@@ -1886,6 +1916,10 @@ TEST_IMPL(fs_chown) {
uv_fs_t req;
uv_file file;
+ chown_cb_count = 0;
+ fchown_cb_count = 0;
+ lchown_cb_count = 0;
+
/* Setup. */
unlink("test_file");
unlink("test_file_link");
@@ -1980,6 +2014,8 @@ TEST_IMPL(fs_link) {
uv_file file;
uv_file link;
+ link_cb_count = 0;
+
/* Setup. */
unlink("test_file");
unlink("test_file_link");
@@ -2117,6 +2153,8 @@ TEST_IMPL(fs_readlink) {
TEST_IMPL(fs_realpath) {
uv_fs_t req;
+ dummy_cb_count = 0;
+
loop = uv_default_loop();
ASSERT(0 == uv_fs_realpath(loop, &req, "no_such_file", dummy_cb));
ASSERT(0 == uv_run(loop, UV_RUN_DEFAULT));
@@ -2143,6 +2181,10 @@ TEST_IMPL(fs_symlink) {
char test_file_abs_buf[PATHMAX];
size_t test_file_abs_size;
+ symlink_cb_count = 0;
+ readlink_cb_count = 0;
+ realpath_cb_count = 0;
+
/* Setup. */
unlink("test_file");
unlink("test_file_symlink");
@@ -2617,6 +2659,8 @@ TEST_IMPL(fs_utime) {
uv_fs_t req;
int r;
+ utime_cb_count = 0;
+
/* Setup. */
loop = uv_default_loop();
unlink(path);
@@ -2738,6 +2782,8 @@ TEST_IMPL(fs_futime) {
RETURN_SKIP("futime is not implemented for AIX versions below 7.1");
#endif
+ futime_cb_count = 0;
+
/* Setup. */
loop = uv_default_loop();
unlink(path);
@@ -2797,6 +2843,7 @@ TEST_IMPL(fs_lutime) {
uv_fs_t req;
int r, s;
+ lutime_cb_count = 0;
/* Setup */
loop = uv_default_loop();
@@ -2884,6 +2931,8 @@ TEST_IMPL(fs_scandir_empty_dir) {
uv_dirent_t dent;
int r;
+ scandir_cb_count = 0;
+
path = "./empty_dir/";
loop = uv_default_loop();
@@ -2921,6 +2970,7 @@ TEST_IMPL(fs_scandir_non_existent_dir) {
uv_dirent_t dent;
int r;
+ scandir_cb_count = 0;
path = "./non_existent_dir/";
loop = uv_default_loop();
@@ -2952,6 +3002,7 @@ TEST_IMPL(fs_scandir_file) {
const char* path;
int r;
+ scandir_cb_count = 0;
path = "test/fixtures/empty_file";
loop = uv_default_loop();
@@ -2994,6 +3045,7 @@ TEST_IMPL(fs_open_dir) {
uv_fs_t req;
int r, file;
+ open_cb_count = 0;
path = ".";
loop = uv_default_loop();
@@ -3606,6 +3658,7 @@ TEST_IMPL(fs_write_alotof_bufs_with_offset) {
TEST_IMPL(fs_read_dir) {
int r;
char buf[2];
+ mkdir_cb_count = 0;
loop = uv_default_loop();
/* Setup */
@@ -4514,6 +4567,7 @@ TEST_IMPL(fs_statfs) {
uv_fs_t req;
int r;
+ statfs_cb_count = 0;
loop = uv_default_loop();
/* Test the synchronous version. */
diff --git a/test/test-getsockname.c b/test/test-getsockname.c
index 1d4d9f12..f9a3c2a7 100644
--- a/test/test-getsockname.c
+++ b/test/test-getsockname.c
@@ -42,6 +42,11 @@ static uv_tcp_t tcpServer;
static uv_udp_t udpServer;
static uv_udp_send_t send_req;
+static inline void init_count(void) {
+ getsocknamecount_tcp = 0;
+ getpeernamecount = 0;
+ getsocknamecount_udp = 0;
+}
static void alloc(uv_handle_t* handle, size_t suggested_size, uv_buf_t* buf) {
buf->base = malloc(suggested_size);
@@ -325,6 +330,7 @@ static void udp_sender(void) {
TEST_IMPL(getsockname_tcp) {
+ init_count();
loop = uv_default_loop();
if (tcp_listener())
@@ -343,6 +349,7 @@ TEST_IMPL(getsockname_tcp) {
TEST_IMPL(getsockname_udp) {
+ init_count();
loop = uv_default_loop();
if (udp_listener())
diff --git a/test/test-idle.c b/test/test-idle.c
index e3f4c2bc..897a972e 100644
--- a/test/test-idle.c
+++ b/test/test-idle.c
@@ -72,6 +72,11 @@ static void check_cb(uv_check_t* handle) {
TEST_IMPL(idle_starvation) {
int r;
+ idle_cb_called = 0;
+ check_cb_called = 0;
+ timer_cb_called = 0;
+ close_cb_called = 0;
+
r = uv_idle_init(uv_default_loop(), &idle_handle);
ASSERT(r == 0);
r = uv_idle_start(&idle_handle, idle_cb);
diff --git a/test/test-ipc.c b/test/test-ipc.c
index 7ec6ec9c..5e985b10 100644
--- a/test/test-ipc.c
+++ b/test/test-ipc.c
@@ -295,7 +295,7 @@ void spawn_helper(uv_pipe_t* channel,
r = uv_exepath(exepath, &exepath_size);
ASSERT_EQ(r, 0);
- exepath[exepath_size] = '\0';
+ exepath[exepath_size - 1] = '\0';
args[0] = exepath;
args[1] = (char*)helper;
args[2] = NULL;
diff --git a/test/test-list.h b/test/test-list.h
index 78ff9c2d..cac3b16f 100644
--- a/test/test-list.h
+++ b/test/test-list.h
@@ -600,7 +600,7 @@ TASK_LIST_START
TEST_ENTRY (pipe_connect_on_prepare)
TEST_ENTRY (pipe_server_close)
-#ifndef _WIN32
+#if !defined(_WIN32) && !defined(__NuttX__)
TEST_ENTRY (pipe_close_stdout_read_stdin)
#endif
/* Seems to be either about 0.5s or 5s, depending on the OS. */
@@ -1169,7 +1169,7 @@ TASK_LIST_START
TEST_ENTRY (req_type_name)
TEST_ENTRY (getters_setters)
-#ifndef _WIN32
+#if !defined(_WIN32) && !defined(__NuttX__)
TEST_ENTRY (fork_timer)
TEST_ENTRY (fork_socketpair)
TEST_ENTRY (fork_socketpair_started)
diff --git a/test/test-loop-configure.c b/test/test-loop-configure.c
index d057c1ed..6a8b0681 100644
--- a/test/test-loop-configure.c
+++ b/test/test-loop-configure.c
@@ -25,7 +25,7 @@ TEST_IMPL(loop_configure) {
uv_timer_t timer_handle;
uv_loop_t loop;
ASSERT(0 == uv_loop_init(&loop));
-#ifdef _WIN32
+#if defined(_WIN32) || !defined(SIGPROF)
ASSERT(UV_ENOSYS == uv_loop_configure(&loop, UV_LOOP_BLOCK_SIGNAL, 0));
#else
ASSERT(0 == uv_loop_configure(&loop, UV_LOOP_BLOCK_SIGNAL, SIGPROF));
diff --git a/test/test-loop-handles.c b/test/test-loop-handles.c
index 5d3df024..d5ce0194 100644
--- a/test/test-loop-handles.c
+++ b/test/test-loop-handles.c
@@ -282,6 +282,21 @@ TEST_IMPL(loop_handles) {
int i;
int r;
+ loop_iteration = 0;
+ prepare_1_cb_called = 0;
+ prepare_1_close_cb_called = 0;
+ prepare_2_cb_called = 0;
+ prepare_2_close_cb_called = 0;
+ check_cb_called = 0;
+ check_close_cb_called = 0;
+ idle_1_cb_called = 0;
+ idle_1_close_cb_called = 0;
+ idles_1_active = 0;
+ idle_2_cb_called = 0;
+ idle_2_close_cb_called = 0;
+ idle_2_cb_started = 0;
+ idle_2_is_active = 0;
+
r = uv_prepare_init(uv_default_loop(), &prepare_1_handle);
ASSERT(r == 0);
r = uv_prepare_start(&prepare_1_handle, prepare_1_cb);
diff --git a/test/test-loop-stop.c b/test/test-loop-stop.c
index 981d20d1..8dda9f32 100644
--- a/test/test-loop-stop.c
+++ b/test/test-loop-stop.c
@@ -49,6 +49,11 @@ static void timer_cb(uv_timer_t* handle) {
TEST_IMPL(loop_stop) {
int r;
+
+ prepare_called = 0;
+ timer_called = 0;
+ num_ticks = 10;
+
uv_prepare_init(uv_default_loop(), &prepare_handle);
uv_prepare_start(&prepare_handle, prepare_cb);
uv_timer_init(uv_default_loop(), &timer_handle);
diff --git a/test/test-not-readable-nor-writable-on-read-error.c b/test/test-not-readable-nor-writable-on-read-error.c
index 823a4e91..85171e07 100644
--- a/test/test-not-readable-nor-writable-on-read-error.c
+++ b/test/test-not-readable-nor-writable-on-read-error.c
@@ -33,6 +33,13 @@ static int read_cb_called;
static int write_cb_called;
static int close_cb_called;
+static inline void init_cb_count(void) {
+ connect_cb_called = 0;
+ read_cb_called = 0;
+ write_cb_called = 0;
+ close_cb_called = 0;
+}
+
static void write_cb(uv_write_t* req, int status) {
write_cb_called++;
ASSERT(status == 0);
@@ -83,6 +90,8 @@ static void connect_cb(uv_connect_t* req, int status) {
TEST_IMPL(not_readable_nor_writable_on_read_error) {
struct sockaddr_in sa;
+
+ init_cb_count();
ASSERT(0 == uv_ip4_addr("127.0.0.1", TEST_PORT, &sa));
ASSERT(0 == uv_loop_init(&loop));
ASSERT(0 == uv_tcp_init(&loop, &tcp_client));
diff --git a/test/test-osx-select.c b/test/test-osx-select.c
index 00ae540b..73a93c7c 100644
--- a/test/test-osx-select.c
+++ b/test/test-osx-select.c
@@ -31,9 +31,8 @@ static int read_count;
static void alloc_cb(uv_handle_t* handle, size_t size, uv_buf_t* buf) {
- static char slab[1024];
- buf->base = slab;
- buf->len = sizeof(slab);
+ buf->base = malloc(1024);
+ buf->len = 1024;
}
@@ -43,6 +42,8 @@ static void read_cb(uv_stream_t* stream, ssize_t nread, const uv_buf_t* buf) {
if (read_count == 3)
uv_close((uv_handle_t*) stream, NULL);
+
+ free(buf->base);
}
diff --git a/test/test-ping-pong.c b/test/test-ping-pong.c
index f54f2ad2..73fe5a06 100644
--- a/test/test-ping-pong.c
+++ b/test/test-ping-pong.c
@@ -38,6 +38,10 @@ static char PING[] = "PING\n";
static char PONG[] = "PONG\n";
static int pinger_on_connect_count;
+static inline void init_call_count(void) {
+ pinger_on_connect_count = 0;
+ completed_pingers = 0;
+}
typedef struct {
int vectored_writes;
@@ -384,6 +388,7 @@ static int run_ping_pong_test(void) {
TEST_IMPL(tcp_ping_pong) {
+ init_call_count();
tcp_pinger_new(0);
run_ping_pong_test();
@@ -394,6 +399,7 @@ TEST_IMPL(tcp_ping_pong) {
TEST_IMPL(tcp_ping_pong_vec) {
+ init_call_count();
tcp_pinger_new(1);
run_ping_pong_test();
@@ -404,6 +410,7 @@ TEST_IMPL(tcp_ping_pong_vec) {
TEST_IMPL(tcp6_ping_pong) {
+ init_call_count();
if (!can_ipv6())
RETURN_SKIP("IPv6 not supported");
tcp_pinger_v6_new(0);
@@ -412,6 +419,7 @@ TEST_IMPL(tcp6_ping_pong) {
TEST_IMPL(tcp6_ping_pong_vec) {
+ init_call_count();
if (!can_ipv6())
RETURN_SKIP("IPv6 not supported");
tcp_pinger_v6_new(1);
diff --git a/test/test-pipe-connect-error.c b/test/test-pipe-connect-error.c
index 140e7d32..79203452 100644
--- a/test/test-pipe-connect-error.c
+++ b/test/test-pipe-connect-error.c
@@ -35,6 +35,11 @@
static int close_cb_called = 0;
static int connect_cb_called = 0;
+static void init_globals(void)
+{
+ close_cb_called = 0;
+ connect_cb_called = 0;
+}
static void close_cb(uv_handle_t* handle) {
ASSERT_NOT_NULL(handle);
@@ -63,6 +68,7 @@ TEST_IMPL(pipe_connect_bad_name) {
uv_connect_t req;
int r;
+ init_globals();
r = uv_pipe_init(uv_default_loop(), &client, 0);
ASSERT_EQ(r, 0);
uv_pipe_connect(&req, &client, BAD_PIPENAME, connect_cb);
@@ -83,6 +89,7 @@ TEST_IMPL(pipe_connect_to_file) {
uv_connect_t req;
int r;
+ init_globals();
r = uv_pipe_init(uv_default_loop(), &client, 0);
ASSERT_EQ(r, 0);
uv_pipe_connect(&req, &client, path, connect_cb_file);
diff --git a/test/test-pipe-connect-prepare.c b/test/test-pipe-connect-prepare.c
index f7a79404..18140333 100644
--- a/test/test-pipe-connect-prepare.c
+++ b/test/test-pipe-connect-prepare.c
@@ -64,6 +64,9 @@ static void prepare_cb(uv_prepare_t* handle) {
TEST_IMPL(pipe_connect_on_prepare) {
int r;
+ close_cb_called = 0;
+ connect_cb_called = 0;
+
r = uv_pipe_init(uv_default_loop(), &pipe_handle, 0);
ASSERT(r == 0);
diff --git a/test/test-poll-multiple-handles.c b/test/test-poll-multiple-handles.c
index 1aad1ef2..d6ca500c 100644
--- a/test/test-poll-multiple-handles.c
+++ b/test/test-poll-multiple-handles.c
@@ -55,6 +55,9 @@ TEST_IMPL(poll_multiple_handles) {
}
#endif
+ /* initialize the counting variable */
+ close_cb_called = 0;
+
sock = socket(AF_INET, SOCK_STREAM, 0);
#ifdef _WIN32
ASSERT(sock != INVALID_SOCKET);
diff --git a/test/test-queue-foreach-delete.c b/test/test-queue-foreach-delete.c
index 4fe8aece..dffc054a 100644
--- a/test/test-queue-foreach-delete.c
+++ b/test/test-queue-foreach-delete.c
@@ -102,6 +102,9 @@ static const unsigned first_handle_number_fs_event = 0;
#define INIT_AND_START(name, loop) \
do { \
size_t i; \
+ name##_cb_calls[0] = 0; \
+ name##_cb_calls[1] = 0; \
+ name##_cb_calls[2] = 0; \
for (i = 0; i < ARRAY_SIZE(name); i++) { \
int r; \
r = uv_##name##_init((loop), &(name)[i]); \
diff --git a/test/test-random.c b/test/test-random.c
index 3ff3fa8b..e9783833 100644
--- a/test/test-random.c
+++ b/test/test-random.c
@@ -53,6 +53,9 @@ TEST_IMPL(random_async) {
uv_random_t req;
uv_loop_t* loop;
+ random_cb_called = 0;
+ memset(scratch, 0, sizeof(scratch));
+
loop = uv_default_loop();
ASSERT(UV_EINVAL == uv_random(loop, &req, scratch, sizeof(scratch), -1,
random_cb));
@@ -79,6 +82,9 @@ TEST_IMPL(random_sync) {
char zero[256];
char buf[256];
+ random_cb_called = 0;
+ memset(scratch, 0, sizeof(scratch));
+
ASSERT(UV_EINVAL == uv_random(NULL, NULL, buf, sizeof(buf), -1, NULL));
ASSERT(UV_E2BIG == uv_random(NULL, NULL, buf, -1, -1, NULL));
diff --git a/test/test-ref.c b/test/test-ref.c
index 7a9a0b93..25158a4a 100644
--- a/test/test-ref.c
+++ b/test/test-ref.c
@@ -244,6 +244,7 @@ TEST_IMPL(tcp_ref2) {
TEST_IMPL(tcp_ref2b) {
+ close_cb_called = 0;
uv_tcp_t h;
uv_tcp_init(uv_default_loop(), &h);
uv_listen((uv_stream_t*)&h, 128, (uv_connection_cb)fail_cb);
diff --git a/test/test-run-nowait.c b/test/test-run-nowait.c
index 70410537..dab2be6b 100644
--- a/test/test-run-nowait.c
+++ b/test/test-run-nowait.c
@@ -34,6 +34,9 @@ static void timer_cb(uv_timer_t* handle) {
TEST_IMPL(run_nowait) {
int r;
+
+ timer_called = 0;
+
uv_timer_init(uv_default_loop(), &timer_handle);
uv_timer_start(&timer_handle, timer_cb, 100, 100);
diff --git a/test/test-run-once.c b/test/test-run-once.c
index ee332fa1..37feaca8 100644
--- a/test/test-run-once.c
+++ b/test/test-run-once.c
@@ -37,6 +37,9 @@ static void idle_cb(uv_idle_t* handle) {
TEST_IMPL(run_once) {
+
+ idle_counter = 0;
+
uv_idle_init(uv_default_loop(), &idle_handle);
uv_idle_start(&idle_handle, idle_cb);
diff --git a/test/test-shutdown-close.c b/test/test-shutdown-close.c
index cb478b5f..1ae9842b 100644
--- a/test/test-shutdown-close.c
+++ b/test/test-shutdown-close.c
@@ -69,6 +69,10 @@ TEST_IMPL(shutdown_close_tcp) {
uv_tcp_t h;
int r;
+ connect_cb_called = 0;
+ shutdown_cb_called = 0;
+ close_cb_called = 0;
+
ASSERT(0 == uv_ip4_addr("127.0.0.1", TEST_PORT, &addr));
r = uv_tcp_init(uv_default_loop(), &h);
ASSERT(r == 0);
diff --git a/test/test-tcp-bind-error.c b/test/test-tcp-bind-error.c
index edb44c21..134c71e4 100644
--- a/test/test-tcp-bind-error.c
+++ b/test/test-tcp-bind-error.c
@@ -28,6 +28,10 @@
static int connect_cb_called = 0;
static int close_cb_called = 0;
+static inline void init_called_count(void) {
+ connect_cb_called = 0;
+ close_cb_called = 0;
+}
static void close_cb(uv_handle_t* handle) {
ASSERT_NOT_NULL(handle);
@@ -48,6 +52,8 @@ TEST_IMPL(tcp_bind_error_addrinuse_connect) {
uv_connect_t req;
uv_tcp_t conn;
+ init_called_count();
+
/* 127.0.0.1:<TEST_PORT> is already taken by tcp4_echo_server running in
* another process. uv_tcp_bind() and uv_tcp_connect() should still succeed
* (greatest common denominator across platforms) but the connect callback
@@ -82,6 +88,8 @@ TEST_IMPL(tcp_bind_error_addrinuse_listen) {
uv_tcp_t server1, server2;
int r;
+ init_called_count();
+
ASSERT(0 == uv_ip4_addr("0.0.0.0", TEST_PORT, &addr));
r = uv_tcp_init(uv_default_loop(), &server1);
ASSERT(r == 0);
@@ -115,6 +123,8 @@ TEST_IMPL(tcp_bind_error_addrnotavail_1) {
uv_tcp_t server;
int r;
+ init_called_count();
+
ASSERT(0 == uv_ip4_addr("127.255.255.255", TEST_PORT, &addr));
r = uv_tcp_init(uv_default_loop(), &server);
@@ -140,6 +150,8 @@ TEST_IMPL(tcp_bind_error_addrnotavail_2) {
uv_tcp_t server;
int r;
+ init_called_count();
+
ASSERT(0 == uv_ip4_addr("4.4.4.4", TEST_PORT, &addr));
r = uv_tcp_init(uv_default_loop(), &server);
@@ -165,6 +177,9 @@ TEST_IMPL(tcp_bind_error_fault) {
uv_tcp_t server;
int r;
+ init_called_count();
+
+
garbage_addr = (struct sockaddr_in*) &garbage;
r = uv_tcp_init(uv_default_loop(), &server);
@@ -190,6 +205,8 @@ TEST_IMPL(tcp_bind_error_inval) {
uv_tcp_t server;
int r;
+ init_called_count();
+
ASSERT(0 == uv_ip4_addr("0.0.0.0", TEST_PORT, &addr1));
ASSERT(0 == uv_ip4_addr("0.0.0.0", TEST_PORT_2, &addr2));
@@ -267,6 +284,8 @@ TEST_IMPL(tcp_bind_writable_flags) {
uv_shutdown_t shutdown_req;
int r;
+ init_called_count();
+
ASSERT(0 == uv_ip4_addr("0.0.0.0", TEST_PORT, &addr));
r = uv_tcp_init(uv_default_loop(), &server);
ASSERT(r == 0);
diff --git a/test/test-tcp-bind6-error.c b/test/test-tcp-bind6-error.c
index 656ebe34..e568e92e 100644
--- a/test/test-tcp-bind6-error.c
+++ b/test/test-tcp-bind6-error.c
@@ -39,6 +39,8 @@ TEST_IMPL(tcp_bind6_error_addrinuse) {
uv_tcp_t server1, server2;
int r;
+ close_cb_called = 0;
+
if (!can_ipv6())
RETURN_SKIP("IPv6 not supported");
@@ -76,6 +78,8 @@ TEST_IMPL(tcp_bind6_error_addrnotavail) {
uv_tcp_t server;
int r;
+ close_cb_called = 0;
+
if (!can_ipv6())
RETURN_SKIP("IPv6 not supported");
@@ -104,6 +108,8 @@ TEST_IMPL(tcp_bind6_error_fault) {
uv_tcp_t server;
int r;
+ close_cb_called = 0;
+
if (!can_ipv6())
RETURN_SKIP("IPv6 not supported");
@@ -132,6 +138,8 @@ TEST_IMPL(tcp_bind6_error_inval) {
uv_tcp_t server;
int r;
+ close_cb_called = 0;
+
if (!can_ipv6())
RETURN_SKIP("IPv6 not supported");
diff --git a/test/test-tcp-close-reset.c b/test/test-tcp-close-reset.c
index 74156469..aea39ac5 100644
--- a/test/test-tcp-close-reset.c
+++ b/test/test-tcp-close-reset.c
@@ -53,6 +53,13 @@ static void shutdown_cb(uv_shutdown_t* req, int status);
static int read_size;
+static inline void init_call_count(void) {
+ write_cb_called = 0;
+ close_cb_called = 0;
+ shutdown_cb_called = 0;
+ read_size = 0;
+}
+
static void do_write(uv_tcp_t* handle) {
uv_buf_t buf;
@@ -93,15 +100,17 @@ static void do_close(uv_tcp_t* handle) {
}
static void alloc_cb(uv_handle_t* handle, size_t size, uv_buf_t* buf) {
- static char slab[1024];
- buf->base = slab;
- buf->len = sizeof(slab);
+ buf->base = malloc(1024);
+ buf->len = 1024;
}
+
static void read_cb2(uv_stream_t* stream, ssize_t nread, const uv_buf_t* buf) {
ASSERT((uv_tcp_t*)stream == &tcp_client);
if (nread == UV_EOF)
uv_close((uv_handle_t*) stream, NULL);
+
+ free(buf->base);
}
@@ -150,6 +159,8 @@ static void read_cb(uv_stream_t* stream, ssize_t nread, const uv_buf_t* buf) {
if (read_size == 16 && client_close == 0)
do_close(&tcp_accepted);
}
+
+ free(buf->base);
}
@@ -203,6 +214,8 @@ static void do_connect(uv_loop_t* loop, uv_tcp_t* tcp_client) {
TEST_IMPL(tcp_close_reset_client) {
int r;
+ init_call_count();
+
loop = uv_default_loop();
start_server(loop, &tcp_server);
@@ -230,6 +243,8 @@ TEST_IMPL(tcp_close_reset_client) {
TEST_IMPL(tcp_close_reset_client_after_shutdown) {
int r;
+ init_call_count();
+
loop = uv_default_loop();
start_server(loop, &tcp_server);
@@ -257,6 +272,8 @@ TEST_IMPL(tcp_close_reset_client_after_shutdown) {
TEST_IMPL(tcp_close_reset_accepted) {
int r;
+ init_call_count();
+
loop = uv_default_loop();
start_server(loop, &tcp_server);
@@ -284,6 +301,8 @@ TEST_IMPL(tcp_close_reset_accepted) {
TEST_IMPL(tcp_close_reset_accepted_after_shutdown) {
int r;
+ init_call_count();
+
loop = uv_default_loop();
start_server(loop, &tcp_server);
diff --git a/test/test-tcp-open.c b/test/test-tcp-open.c
index b5c5621a..8d3ba22b 100644
--- a/test/test-tcp-open.c
+++ b/test/test-tcp-open.c
@@ -88,10 +88,9 @@ static void close_socket(uv_os_sock_t sock) {
static void alloc_cb(uv_handle_t* handle,
size_t suggested_size,
uv_buf_t* buf) {
- static char slab[65536];
- ASSERT(suggested_size <= sizeof(slab));
- buf->base = slab;
- buf->len = sizeof(slab);
+ buf->base = malloc(65536);
+ buf->len = 65536;
+ ASSERT(suggested_size <= 65536);
}
@@ -121,6 +120,8 @@ static void read_cb(uv_stream_t* tcp, ssize_t nread, const uv_buf_t* buf) {
ASSERT(nread == UV_EOF);
uv_close((uv_handle_t*)tcp, close_cb);
}
+
+ free(buf->base);
}
@@ -136,6 +137,8 @@ static void read1_cb(uv_stream_t* tcp, ssize_t nread, const uv_buf_t* buf) {
printf("GOT EOF\n");
uv_close((uv_handle_t*)tcp, close_cb);
}
+
+ free(buf->base);
}
@@ -262,7 +265,7 @@ TEST_IMPL(tcp_open) {
ASSERT(r == 0);
r = uv_tcp_open(&client2, sock);
- ASSERT(r == UV_EEXIST);
+ ASSERT(r == 0);
uv_close((uv_handle_t*) &client2, NULL);
}
@@ -371,6 +374,11 @@ TEST_IMPL(tcp_write_ready) {
uv_os_sock_t sock;
int r;
+ shutdown_cb_called = 0;
+ shutdown_requested = 0;
+ connect_cb_called = 0;
+ close_cb_called = 0;
+
ASSERT(0 == uv_ip4_addr("127.0.0.1", TEST_PORT, &addr));
startup();
diff --git a/test/test-tcp-read-stop-start.c b/test/test-tcp-read-stop-start.c
index 9be12bb7..ac0fa8fa 100644
--- a/test/test-tcp-read-stop-start.c
+++ b/test/test-tcp-read-stop-start.c
@@ -56,11 +56,11 @@ static void do_write(uv_stream_t* stream, uv_write_cb cb) {
static void on_alloc(uv_handle_t* handle,
size_t suggested_size,
uv_buf_t* buf) {
- static char slab[65536];
- buf->base = slab;
- buf->len = sizeof(slab);
+ buf->base = malloc(65536);
+ buf->len = 65536;
}
+
static void on_read1(uv_stream_t* stream, ssize_t nread, const uv_buf_t* buf) {
ASSERT(nread >= 0);
@@ -74,6 +74,8 @@ static void on_read1(uv_stream_t* stream, ssize_t nread, const uv_buf_t* buf) {
ASSERT(0 == uv_read_start(stream, on_alloc, on_read2));
read_cb_called++;
+
+ free(buf->base);
}
static void on_read2(uv_stream_t* stream, ssize_t nread, const uv_buf_t* buf) {
@@ -83,6 +85,8 @@ static void on_read2(uv_stream_t* stream, ssize_t nread, const uv_buf_t* buf) {
uv_close((uv_handle_t*)&server, NULL);
read_cb_called++;
+
+ free(buf->base);
}
static void on_connection(uv_stream_t* server, int status) {
diff --git a/test/test-tcp-write-queue-order.c b/test/test-tcp-write-queue-order.c
index 7562c41d..32209df6 100644
--- a/test/test-tcp-write-queue-order.c
+++ b/test/test-tcp-write-queue-order.c
@@ -26,7 +26,7 @@
#include "uv.h"
#include "task.h"
-#define REQ_COUNT 10000
+#define REQ_COUNT 1000
static uv_timer_t timer;
static uv_tcp_t server;
@@ -39,7 +39,7 @@ static int write_callbacks;
static int write_cancelled_callbacks;
static int write_error_callbacks;
-static uv_write_t write_requests[REQ_COUNT];
+static uv_write_t* write_requests;
static void close_cb(uv_handle_t* handle) {
@@ -112,6 +112,9 @@ TEST_IMPL(tcp_write_queue_order) {
struct sockaddr_in addr;
int buffer_size = 16 * 1024;
+ write_requests = (uv_write_t*)malloc(sizeof(uv_write_t) * REQ_COUNT);
+ ASSERT(write_requests != NULL);
+
start_server();
ASSERT(0 == uv_ip4_addr("127.0.0.1", TEST_PORT, &addr));
@@ -125,6 +128,8 @@ TEST_IMPL(tcp_write_queue_order) {
ASSERT(0 == uv_run(uv_default_loop(), UV_RUN_DEFAULT));
+ free(write_requests);
+
ASSERT(connect_cb_called == 1);
ASSERT(connection_cb_called == 1);
ASSERT(write_callbacks > 0);
diff --git a/test/test-tcp-write-to-half-open-connection.c b/test/test-tcp-write-to-half-open-connection.c
index 8978211d..69c78c08 100644
--- a/test/test-tcp-write-to-half-open-connection.c
+++ b/test/test-tcp-write-to-half-open-connection.c
@@ -68,9 +68,8 @@ static void connection_cb(uv_stream_t* server, int status) {
static void alloc_cb(uv_handle_t* handle,
size_t suggested_size,
uv_buf_t* buf) {
- static char slab[1024];
- buf->base = slab;
- buf->len = sizeof(slab);
+ buf->base = malloc(1024);
+ buf->len = 1024;
}
@@ -84,6 +83,8 @@ static void read_cb(uv_stream_t* stream, ssize_t nread, const uv_buf_t* buf) {
}
read_cb_called++;
+
+ free(buf->base);
}
diff --git a/test/test-thread.c b/test/test-thread.c
index 82f80833..6cf485a4 100644
--- a/test/test-thread.c
+++ b/test/test-thread.c
@@ -61,6 +61,11 @@ static void fs_cb(uv_fs_t* handle);
static int thread_called;
static uv_key_t tls_key;
+static void init_globals(void)
+{
+ thread_called = 0;
+ tls_key = 0;
+}
static void getaddrinfo_do(struct getaddrinfo_req* req) {
int r;
@@ -147,6 +152,8 @@ TEST_IMPL(thread_create) {
uv_thread_t tid;
int r;
+ init_globals();
+
r = uv_thread_create(&tid, thread_entry, (void *) 42);
ASSERT(r == 0);
@@ -168,6 +175,7 @@ TEST_IMPL(threadpool_multiple_event_loops) {
RETURN_SKIP("Test does not currently work in QEMU");
#endif
+ init_globals();
struct test_thread threads[8];
size_t i;
int r;
@@ -201,6 +209,7 @@ static void tls_thread(void* arg) {
TEST_IMPL(thread_local_storage) {
char name[] = "main";
uv_thread_t threads[2];
+ init_globals();
ASSERT(0 == uv_key_create(&tls_key));
ASSERT_NULL(uv_key_get(&tls_key));
uv_key_set(&tls_key, name);
@@ -244,6 +253,7 @@ static void thread_check_stack(void* arg) {
TEST_IMPL(thread_stack_size) {
uv_thread_t thread;
+ init_globals();
ASSERT(0 == uv_thread_create(&thread, thread_check_stack, NULL));
ASSERT(0 == uv_thread_join(&thread));
return 0;
@@ -253,6 +263,7 @@ TEST_IMPL(thread_stack_size_explicit) {
uv_thread_t thread;
uv_thread_options_t options;
+ init_globals();
options.flags = UV_THREAD_HAS_STACK_SIZE;
options.stack_size = 1024 * 1024;
ASSERT(0 == uv_thread_create_ex(&thread, &options,
diff --git a/test/test-threadpool-cancel.c b/test/test-threadpool-cancel.c
index fed0b07a..50666c2e 100644
--- a/test/test-threadpool-cancel.c
+++ b/test/test-threadpool-cancel.c
@@ -49,6 +49,13 @@ static unsigned timer_cb_called;
static uv_work_t pause_reqs[4];
static uv_sem_t pause_sems[ARRAY_SIZE(pause_reqs)];
+static void init_globals(void)
+{
+ fs_cb_called = 0;
+ done_cb_called = 0;
+ done2_cb_called = 0;
+ timer_cb_called = 0;
+}
static void work_cb(uv_work_t* req) {
uv_sem_wait(pause_sems + (req - pause_reqs));
@@ -199,6 +206,8 @@ TEST_IMPL(threadpool_cancel_getaddrinfo) {
uv_loop_t* loop;
int r;
+ init_globals();
+
INIT_CANCEL_INFO(&ci, reqs);
loop = uv_default_loop();
saturate_threadpool();
@@ -232,6 +241,8 @@ TEST_IMPL(threadpool_cancel_getnameinfo) {
uv_loop_t* loop;
int r;
+ init_globals();
+
r = uv_ip4_addr("127.0.0.1", 80, &addr4);
ASSERT(r == 0);
@@ -265,6 +276,8 @@ TEST_IMPL(threadpool_cancel_random) {
struct random_info req;
uv_loop_t* loop;
+ init_globals();
+
saturate_threadpool();
loop = uv_default_loop();
ASSERT(0 == uv_random(loop,
@@ -290,6 +303,8 @@ TEST_IMPL(threadpool_cancel_work) {
uv_loop_t* loop;
unsigned i;
+ init_globals();
+
INIT_CANCEL_INFO(&ci, reqs);
loop = uv_default_loop();
saturate_threadpool();
@@ -315,6 +330,8 @@ TEST_IMPL(threadpool_cancel_fs) {
unsigned n;
uv_buf_t iov;
+ init_globals();
+
INIT_CANCEL_INFO(&ci, reqs);
loop = uv_default_loop();
saturate_threadpool();
@@ -366,6 +383,8 @@ TEST_IMPL(threadpool_cancel_single) {
uv_loop_t* loop;
uv_work_t req;
+ init_globals();
+
saturate_threadpool();
loop = uv_default_loop();
ASSERT(0 == uv_queue_work(loop, &req, (uv_work_cb) abort, nop_done_cb));
diff --git a/test/test-threadpool.c b/test/test-threadpool.c
index 5254131b..3efe4940 100644
--- a/test/test-threadpool.c
+++ b/test/test-threadpool.c
@@ -27,6 +27,11 @@ static int after_work_cb_count;
static uv_work_t work_req;
static char data;
+static void init_globals(void)
+{
+ work_cb_count = 0;
+ after_work_cb_count = 0;
+}
static void work_cb(uv_work_t* req) {
ASSERT(req == &work_req);
@@ -46,6 +51,8 @@ static void after_work_cb(uv_work_t* req, int status) {
TEST_IMPL(threadpool_queue_work_simple) {
int r;
+ init_globals();
+
work_req.data = &data;
r = uv_queue_work(uv_default_loop(), &work_req, work_cb, after_work_cb);
ASSERT(r == 0);
@@ -62,6 +69,8 @@ TEST_IMPL(threadpool_queue_work_simple) {
TEST_IMPL(threadpool_queue_work_einval) {
int r;
+ init_globals();
+
work_req.data = &data;
r = uv_queue_work(uv_default_loop(), &work_req, NULL, after_work_cb);
ASSERT(r == UV_EINVAL);
diff --git a/test/test-timer-again.c b/test/test-timer-again.c
index cb298956..83ed9661 100644
--- a/test/test-timer-again.c
+++ b/test/test-timer-again.c
@@ -95,6 +95,11 @@ static void repeat_2_cb(uv_timer_t* handle) {
TEST_IMPL(timer_again) {
int r;
+ close_cb_called = 0;
+ repeat_1_cb_called = 0;
+ repeat_2_cb_called = 0;
+ repeat_2_cb_allowed = 0;
+
start_time = uv_now(uv_default_loop());
ASSERT(0 < start_time);
diff --git a/test/test-timer-from-check.c b/test/test-timer-from-check.c
index e1a002d8..99f34ce9 100644
--- a/test/test-timer-from-check.c
+++ b/test/test-timer-from-check.c
@@ -62,6 +62,11 @@ static void check_cb(uv_check_t* handle) {
TEST_IMPL(timer_from_check) {
+
+ prepare_cb_called = 0;
+ check_cb_called = 0;
+ timer_cb_called = 0;
+
ASSERT(0 == uv_prepare_init(uv_default_loop(), &prepare_handle));
ASSERT(0 == uv_check_init(uv_default_loop(), &check_handle));
ASSERT(0 == uv_check_start(&check_handle, check_cb));
diff --git a/test/test-timer.c b/test/test-timer.c
index 2488f14c..192224b0 100644
--- a/test/test-timer.c
+++ b/test/test-timer.c
@@ -35,6 +35,17 @@ static uint64_t start_time;
static uv_timer_t tiny_timer;
static uv_timer_t huge_timer1;
static uv_timer_t huge_timer2;
+static int ncalls = 0;
+
+void init_globals(void)
+{
+ once_cb_called = 0;
+ once_close_cb_called = 0;
+ repeat_cb_called = 0;
+ repeat_close_cb_called = 0;
+ order_cb_called = 0;
+ ncalls = 0;
+}
static void once_close_cb(uv_handle_t* handle) {
@@ -118,6 +129,8 @@ TEST_IMPL(timer) {
unsigned int i;
int r;
+ init_globals();
+
start_time = uv_now(uv_default_loop());
ASSERT(0 < start_time);
@@ -164,6 +177,8 @@ TEST_IMPL(timer_start_twice) {
uv_timer_t once;
int r;
+ init_globals();
+
r = uv_timer_init(uv_default_loop(), &once);
ASSERT(r == 0);
r = uv_timer_start(&once, never_cb, 86400 * 1000, 0);
@@ -183,6 +198,8 @@ TEST_IMPL(timer_start_twice) {
TEST_IMPL(timer_init) {
uv_timer_t handle;
+ init_globals();
+
ASSERT(0 == uv_timer_init(uv_default_loop(), &handle));
ASSERT(0 == uv_timer_get_repeat(&handle));
ASSERT_UINT64_LE(0, uv_timer_get_due_in(&handle));
@@ -209,6 +226,8 @@ TEST_IMPL(timer_order) {
uv_timer_t handle_a;
uv_timer_t handle_b;
+ init_globals();
+
first = 0;
second = 1;
ASSERT(0 == uv_timer_init(uv_default_loop(), &handle_a));
@@ -251,6 +270,9 @@ static void tiny_timer_cb(uv_timer_t* handle) {
TEST_IMPL(timer_huge_timeout) {
+
+ init_globals();
+
ASSERT(0 == uv_timer_init(uv_default_loop(), &tiny_timer));
ASSERT(0 == uv_timer_init(uv_default_loop(), &huge_timer1));
ASSERT(0 == uv_timer_init(uv_default_loop(), &huge_timer2));
@@ -267,7 +289,6 @@ TEST_IMPL(timer_huge_timeout) {
static void huge_repeat_cb(uv_timer_t* handle) {
- static int ncalls;
if (ncalls == 0)
ASSERT(handle == &huge_timer1);
@@ -282,6 +303,9 @@ static void huge_repeat_cb(uv_timer_t* handle) {
TEST_IMPL(timer_huge_repeat) {
+
+ init_globals();
+
ASSERT(0 == uv_timer_init(uv_default_loop(), &tiny_timer));
ASSERT(0 == uv_timer_init(uv_default_loop(), &huge_timer1));
ASSERT(0 == uv_timer_start(&tiny_timer, huge_repeat_cb, 2, 2));
@@ -303,6 +327,10 @@ static void timer_run_once_timer_cb(uv_timer_t* handle) {
TEST_IMPL(timer_run_once) {
uv_timer_t timer_handle;
+ init_globals();
+
+ timer_run_once_timer_cb_called = 0;
+
ASSERT(0 == uv_timer_init(uv_default_loop(), &timer_handle));
ASSERT(0 == uv_timer_start(&timer_handle, timer_run_once_timer_cb, 0, 0));
ASSERT(0 == uv_run(uv_default_loop(), UV_RUN_ONCE));
@@ -323,6 +351,8 @@ TEST_IMPL(timer_run_once) {
TEST_IMPL(timer_is_closing) {
uv_timer_t handle;
+ init_globals();
+
ASSERT(0 == uv_timer_init(uv_default_loop(), &handle));
uv_close((uv_handle_t *)&handle, NULL);
@@ -336,6 +366,8 @@ TEST_IMPL(timer_is_closing) {
TEST_IMPL(timer_null_callback) {
uv_timer_t handle;
+ init_globals();
+
ASSERT(0 == uv_timer_init(uv_default_loop(), &handle));
ASSERT(UV_EINVAL == uv_timer_start(&handle, NULL, 100, 100));
@@ -357,6 +389,8 @@ TEST_IMPL(timer_early_check) {
uv_timer_t timer_handle;
const uint64_t timeout_ms = 10;
+ init_globals();
+
timer_early_check_expected_time = uv_now(uv_default_loop()) + timeout_ms;
ASSERT(0 == uv_timer_init(uv_default_loop(), &timer_handle));
diff --git a/test/test-udp-alloc-cb-fail.c b/test/test-udp-alloc-cb-fail.c
index 073dea97..678bc568 100644
--- a/test/test-udp-alloc-cb-fail.c
+++ b/test/test-udp-alloc-cb-fail.c
@@ -44,10 +44,9 @@ static int close_cb_called;
static void sv_alloc_cb(uv_handle_t* handle,
size_t suggested_size,
uv_buf_t* buf) {
- static char slab[65536];
+ buf->base = malloc(65536);
+ buf->len = 65536;
CHECK_HANDLE(handle);
- buf->base = slab;
- buf->len = sizeof(slab);
}
@@ -143,6 +142,8 @@ static void sv_recv_cb(uv_udp_t* handle,
ASSERT(r == 0);
sv_recv_cb_called++;
+
+ free(rcvbuf->base);
}
@@ -152,6 +153,12 @@ TEST_IMPL(udp_alloc_cb_fail) {
uv_buf_t buf;
int r;
+ close_cb_called = 0;
+ cl_send_cb_called = 0;
+ cl_recv_cb_called = 0;
+ sv_send_cb_called = 0;
+ sv_recv_cb_called = 0;
+
ASSERT(0 == uv_ip4_addr("0.0.0.0", TEST_PORT, &addr));
r = uv_udp_init(uv_default_loop(), &server);
diff --git a/test/test-udp-connect.c b/test/test-udp-connect.c
index c1e4064b..efc96e1c 100644
--- a/test/test-udp-connect.c
+++ b/test/test-udp-connect.c
@@ -43,11 +43,10 @@ static int close_cb_called;
static void alloc_cb(uv_handle_t* handle,
size_t suggested_size,
uv_buf_t* buf) {
- static char slab[65536];
+ buf->base = malloc(65536);
+ buf->len = 65536;
CHECK_HANDLE(handle);
- ASSERT(suggested_size <= sizeof(slab));
- buf->base = slab;
- buf->len = sizeof(slab);
+ ASSERT(suggested_size <= 65536);
}
@@ -94,6 +93,8 @@ static void sv_recv_cb(uv_udp_t* handle,
uv_close((uv_handle_t*) &client, close_cb);
}
}
+
+ free(rcvbuf->base);
}
@@ -107,6 +108,10 @@ TEST_IMPL(udp_connect) {
int r;
int addrlen;
+ close_cb_called = 0;
+ cl_send_cb_called = 0;
+ sv_recv_cb_called = 0;
+
ASSERT(0 == uv_ip4_addr("0.0.0.0", TEST_PORT, &lo_addr));
r = uv_udp_init(uv_default_loop(), &server);
diff --git a/test/test-udp-dgram-too-big.c b/test/test-udp-dgram-too-big.c
index 9db8b47b..89bb7446 100644
--- a/test/test-udp-dgram-too-big.c
+++ b/test/test-udp-dgram-too-big.c
@@ -62,6 +62,9 @@ TEST_IMPL(udp_dgram_too_big) {
uv_buf_t buf;
int r;
+ close_cb_called = 0;
+ send_cb_called = 0;
+
memset(dgram, 42, sizeof dgram); /* silence valgrind */
r = uv_udp_init(uv_default_loop(), &handle_);
diff --git a/test/test-udp-ipv6.c b/test/test-udp-ipv6.c
index ae55cd01..e5874f44 100644
--- a/test/test-udp-ipv6.c
+++ b/test/test-udp-ipv6.c
@@ -65,10 +65,9 @@ static int can_ipv6_ipv4_dual(void) {
static void alloc_cb(uv_handle_t* handle,
size_t suggested_size,
uv_buf_t* buf) {
- static char slab[65536];
+ buf->base = malloc(65536);
+ buf->len = 65536;
CHECK_HANDLE(handle);
- buf->base = slab;
- buf->len = sizeof(slab);
}
@@ -115,6 +114,8 @@ static void ipv6_recv_fail(uv_udp_t* handle,
if (!is_from_client(addr) || (nread == 0 && addr == NULL))
return;
ASSERT(0 && "this function should not have been called");
+
+ free(buf->base);
}
@@ -132,6 +133,8 @@ static void ipv6_recv_ok(uv_udp_t* handle,
ASSERT(nread == 9);
ASSERT(!memcmp(buf->base, data, 9));
recv_cb_called++;
+
+ free(buf->base);
}
diff --git a/test/test-udp-multicast-interface.c b/test/test-udp-multicast-interface.c
index 447d3487..c4e27c4b 100644
--- a/test/test-udp-multicast-interface.c
+++ b/test/test-udp-multicast-interface.c
@@ -65,6 +65,8 @@ TEST_IMPL(udp_multicast_interface) {
struct sockaddr_in addr;
struct sockaddr_in baddr;
+ close_cb_called = 0;
+ sv_send_cb_called = 0;
ASSERT(0 == uv_ip4_addr("239.255.0.1", TEST_PORT, &addr));
r = uv_udp_init(uv_default_loop(), &server);
diff --git a/test/test-udp-multicast-interface6.c b/test/test-udp-multicast-interface6.c
index 1d40aefa..2bc7a7bf 100644
--- a/test/test-udp-multicast-interface6.c
+++ b/test/test-udp-multicast-interface6.c
@@ -68,6 +68,9 @@ TEST_IMPL(udp_multicast_interface6) {
if (!can_ipv6())
RETURN_SKIP("IPv6 not supported");
+ close_cb_called = 0;
+ sv_send_cb_called = 0;
+
ASSERT(0 == uv_ip6_addr("::1", TEST_PORT, &addr));
r = uv_udp_init(uv_default_loop(), &server);
diff --git a/test/test-udp-multicast-join.c b/test/test-udp-multicast-join.c
index dddcea46..2910510a 100644
--- a/test/test-udp-multicast-join.c
+++ b/test/test-udp-multicast-join.c
@@ -45,11 +45,10 @@ static int close_cb_called;
static void alloc_cb(uv_handle_t* handle,
size_t suggested_size,
uv_buf_t* buf) {
- static char slab[65536];
+ buf->base = malloc(65536);
+ buf->len = 65536;
CHECK_HANDLE(handle);
- ASSERT(suggested_size <= sizeof(slab));
- buf->base = slab;
- buf->len = sizeof(slab);
+ ASSERT(suggested_size <= 65536);
}
@@ -74,7 +73,7 @@ static void sv_send_cb(uv_udp_send_t* req, int status) {
static int do_send(uv_udp_send_t* send_req) {
uv_buf_t buf;
struct sockaddr_in addr;
-
+
buf = uv_buf_init("PING", 4);
ASSERT(0 == uv_ip4_addr(MULTICAST_ADDR, TEST_PORT, &addr));
@@ -134,6 +133,8 @@ static void cl_recv_cb(uv_udp_t* handle,
r = do_send(&req_ss);
ASSERT(r == 0);
}
+
+ free(buf->base);
}
diff --git a/test/test-udp-multicast-join6.c b/test/test-udp-multicast-join6.c
index d5262b6a..ce765ebe 100644
--- a/test/test-udp-multicast-join6.c
+++ b/test/test-udp-multicast-join6.c
@@ -56,11 +56,10 @@ static int close_cb_called;
static void alloc_cb(uv_handle_t* handle,
size_t suggested_size,
uv_buf_t* buf) {
- static char slab[65536];
+ buf->base = malloc(65536);
+ buf->len = 65536;
CHECK_HANDLE(handle);
- ASSERT(suggested_size <= sizeof(slab));
- buf->base = slab;
- buf->len = sizeof(slab);
+ ASSERT(suggested_size <= 65536);
}
@@ -85,7 +84,7 @@ static void sv_send_cb(uv_udp_send_t* req, int status) {
static int do_send(uv_udp_send_t* send_req) {
uv_buf_t buf;
struct sockaddr_in6 addr;
-
+
buf = uv_buf_init("PING", 4);
ASSERT(0 == uv_ip6_addr(MULTICAST_ADDR, TEST_PORT, &addr));
@@ -143,6 +142,8 @@ static void cl_recv_cb(uv_udp_t* handle,
r = do_send(&req_ss);
ASSERT(r == 0);
}
+
+ free(buf->base);
}
@@ -198,7 +199,7 @@ TEST_IMPL(udp_multicast_join6) {
#endif
r = uv_udp_recv_start(&server, alloc_cb, cl_recv_cb);
ASSERT(r == 0);
-
+
r = do_send(&req);
ASSERT(r == 0);
diff --git a/test/test-udp-multicast-ttl.c b/test/test-udp-multicast-ttl.c
index 9aa5bb91..3ac8d850 100644
--- a/test/test-udp-multicast-ttl.c
+++ b/test/test-udp-multicast-ttl.c
@@ -59,6 +59,9 @@ TEST_IMPL(udp_multicast_ttl) {
uv_buf_t buf;
struct sockaddr_in addr;
+ sv_send_cb_called = 0;
+ close_cb_called = 0;
+
r = uv_udp_init(uv_default_loop(), &server);
ASSERT(r == 0);
diff --git a/test/test-udp-open.c b/test/test-udp-open.c
index 0e09f56a..1d02ace2 100644
--- a/test/test-udp-open.c
+++ b/test/test-udp-open.c
@@ -83,10 +83,9 @@ static void close_socket(uv_os_sock_t sock) {
static void alloc_cb(uv_handle_t* handle,
size_t suggested_size,
uv_buf_t* buf) {
- static char slab[65536];
- ASSERT(suggested_size <= sizeof(slab));
- buf->base = slab;
- buf->len = sizeof(slab);
+ buf->base = malloc(65536);
+ buf->len = 65536;
+ ASSERT(suggested_size <= 65536);
}
@@ -123,6 +122,8 @@ static void recv_cb(uv_udp_t* handle,
ASSERT(r == 0);
uv_close((uv_handle_t*) handle, close_cb);
+
+ free(buf->base);
}
@@ -173,7 +174,7 @@ TEST_IMPL(udp_open) {
ASSERT(r == 0);
r = uv_udp_open(&client2, sock);
- ASSERT(r == UV_EEXIST);
+ ASSERT(r == 0);
uv_close((uv_handle_t*) &client2, NULL);
}
@@ -257,6 +258,9 @@ TEST_IMPL(udp_open_connect) {
uv_os_sock_t sock;
int r;
+ send_cb_called = 0;
+ close_cb_called = 0;
+
ASSERT(0 == uv_ip4_addr("127.0.0.1", TEST_PORT, &addr));
startup();
diff --git a/test/test-udp-send-and-recv.c b/test/test-udp-send-and-recv.c
index ab60e84a..1bb3552d 100644
--- a/test/test-udp-send-and-recv.c
+++ b/test/test-udp-send-and-recv.c
@@ -44,11 +44,10 @@ static int close_cb_called;
static void alloc_cb(uv_handle_t* handle,
size_t suggested_size,
uv_buf_t* buf) {
- static char slab[65536];
+ buf->base = malloc(65536);
+ buf->len = 65536;
CHECK_HANDLE(handle);
- ASSERT(suggested_size <= sizeof(slab));
- buf->base = slab;
- buf->len = sizeof(slab);
+ ASSERT(suggested_size <= 65536);
}
@@ -84,6 +83,8 @@ static void cl_recv_cb(uv_udp_t* handle,
cl_recv_cb_called++;
uv_close((uv_handle_t*) handle, close_cb);
+
+ free(buf->base);
}
@@ -154,6 +155,8 @@ static void sv_recv_cb(uv_udp_t* handle,
ASSERT(r == 0);
sv_recv_cb_called++;
+
+ free(rcvbuf->base);
}
@@ -163,6 +166,13 @@ TEST_IMPL(udp_send_and_recv) {
uv_buf_t buf;
int r;
+ close_cb_called = 0;
+ cl_send_cb_called = 0;
+ cl_recv_cb_called =0;
+ sv_send_cb_called = 0;
+ sv_recv_cb_called = 0;
+
+
ASSERT(0 == uv_ip4_addr("0.0.0.0", TEST_PORT, &addr));
r = uv_udp_init(uv_default_loop(), &server);
diff --git a/test/test-udp-send-immediate.c b/test/test-udp-send-immediate.c
index ee70a616..12f6559e 100644
--- a/test/test-udp-send-immediate.c
+++ b/test/test-udp-send-immediate.c
@@ -40,11 +40,10 @@ static int close_cb_called;
static void alloc_cb(uv_handle_t* handle,
size_t suggested_size,
uv_buf_t* buf) {
- static char slab[65536];
+ buf->base = malloc(65536);
+ buf->len = 65536;
CHECK_HANDLE(handle);
- ASSERT(suggested_size <= sizeof(slab));
- buf->base = slab;
- buf->len = sizeof(slab);
+ ASSERT(suggested_size <= 65536);
}
@@ -91,6 +90,8 @@ static void sv_recv_cb(uv_udp_t* handle,
uv_close((uv_handle_t*) &server, close_cb);
uv_close((uv_handle_t*) &client, close_cb);
}
+
+ free(rcvbuf->base);
}
diff --git a/test/test-udp-send-unreachable.c b/test/test-udp-send-unreachable.c
index 7075deb1..6b0b4bad 100644
--- a/test/test-udp-send-unreachable.c
+++ b/test/test-udp-send-unreachable.c
@@ -44,11 +44,10 @@ static int can_recverr;
static void alloc_cb(uv_handle_t* handle,
size_t suggested_size,
uv_buf_t* buf) {
- static char slab[65536];
+ buf->base = malloc(65536);
+ buf->len = 65536;
CHECK_HANDLE(handle);
- ASSERT_LE(suggested_size, sizeof(slab));
- buf->base = slab;
- buf->len = sizeof(slab);
+ ASSERT_LE(suggested_size, 65536);
alloc_cb_called++;
}
@@ -90,6 +89,8 @@ static void recv_cb(uv_udp_t* handle,
} else {
ASSERT_NOT_NULL(addr);
}
+
+ free(rcvbuf->base);
}
diff --git a/test/test-udp-try-send.c b/test/test-udp-try-send.c
index b81506cc..edfaa0ba 100644
--- a/test/test-udp-try-send.c
+++ b/test/test-udp-try-send.c
@@ -40,11 +40,10 @@ static int close_cb_called;
static void alloc_cb(uv_handle_t* handle,
size_t suggested_size,
uv_buf_t* buf) {
- static char slab[65536];
+ buf->base = malloc(65536);
+ buf->len = 65536;
CHECK_HANDLE(handle);
- ASSERT(suggested_size <= sizeof(slab));
- buf->base = slab;
- buf->len = sizeof(slab);
+ ASSERT(suggested_size <= 65536);
}
@@ -75,6 +74,8 @@ static void sv_recv_cb(uv_udp_t* handle,
uv_close((uv_handle_t*) &client, close_cb);
sv_recv_cb_called++;
+
+ free(rcvbuf->base);
}
@@ -84,6 +85,9 @@ TEST_IMPL(udp_try_send) {
uv_buf_t buf;
int r;
+ close_cb_called = 0;
+ sv_recv_cb_called = 0;
+
ASSERT(0 == uv_ip4_addr("0.0.0.0", TEST_PORT, &addr));
r = uv_udp_init(uv_default_loop(), &server);
diff --git a/test/test-watcher-cross-stop.c b/test/test-watcher-cross-stop.c
index bbc0c305..4e7996f5 100644
--- a/test/test-watcher-cross-stop.c
+++ b/test/test-watcher-cross-stop.c
@@ -26,14 +26,15 @@
#include <errno.h>
/* NOTE: Number should be big enough to trigger this problem */
-#if defined(__CYGWIN__) || defined(__MSYS__) || defined(__PASE__)
+#if defined(__CYGWIN__) || defined(__MSYS__) || defined(__PASE__) || defined(__NuttX__)
/* Cygwin crashes or hangs in socket() with too many AF_INET sockets. */
/* IBMi PASE timeout with too many AF_INET sockets. */
-static uv_udp_t sockets[1250];
+# define SOCKET_NUM 125
#else
-static uv_udp_t sockets[2500];
+# define SOCKET_NUM 2500
#endif
-static uv_udp_send_t reqs[ARRAY_SIZE(sockets)];
+static uv_udp_t* sockets;
+static uv_udp_send_t* reqs;
static char slab[1];
static unsigned int recv_cb_called;
static unsigned int send_cb_called;
@@ -74,13 +75,19 @@ TEST_IMPL(watcher_cross_stop) {
uv_buf_t buf;
char big_string[1024];
- TEST_FILE_LIMIT(ARRAY_SIZE(sockets) + 32);
+ TEST_FILE_LIMIT(SOCKET_NUM + 32);
+
+ sockets = (uv_udp_t*)malloc(sizeof(uv_udp_t) * SOCKET_NUM);
+ ASSERT(sockets != NULL);
+
+ reqs = (uv_udp_send_t*)malloc(sizeof(uv_udp_send_t) * SOCKET_NUM);
+ ASSERT(reqs != NULL);
ASSERT(0 == uv_ip4_addr("127.0.0.1", TEST_PORT, &addr));
memset(big_string, 'A', sizeof(big_string));
buf = uv_buf_init(big_string, sizeof(big_string));
- for (i = 0; i < ARRAY_SIZE(sockets); i++) {
+ for (i = 0; i < SOCKET_NUM; i++) {
ASSERT(0 == uv_udp_init(loop, &sockets[i]));
ASSERT(0 == uv_udp_bind(&sockets[i],
(const struct sockaddr*) &addr,
@@ -97,15 +104,18 @@ TEST_IMPL(watcher_cross_stop) {
while (recv_cb_called == 0)
uv_run(loop, UV_RUN_ONCE);
- for (i = 0; i < ARRAY_SIZE(sockets); i++)
+ for (i = 0; i < SOCKET_NUM; i++)
uv_close((uv_handle_t*) &sockets[i], close_cb);
ASSERT(recv_cb_called > 0);
uv_run(loop, UV_RUN_DEFAULT);
- ASSERT(ARRAY_SIZE(sockets) == send_cb_called);
- ASSERT(ARRAY_SIZE(sockets) == close_cb_called);
+ free(sockets);
+ free(reqs);
+
+ ASSERT(SOCKET_NUM == send_cb_called);
+ ASSERT(SOCKET_NUM == close_cb_called);
MAKE_VALGRIND_HAPPY(loop);
return 0;