summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--deps/uv/.mailmap1
-rw-r--r--deps/uv/AUTHORS1
-rw-r--r--deps/uv/ChangeLog75
-rw-r--r--deps/uv/build.mk1
-rw-r--r--deps/uv/config-unix.mk18
-rw-r--r--deps/uv/include/uv-private/uv-win.h2
-rw-r--r--deps/uv/include/uv.h11
-rw-r--r--deps/uv/src/unix/core.c6
-rw-r--r--deps/uv/src/unix/cygwin.c90
-rw-r--r--deps/uv/src/unix/darwin-proctitle.c (renamed from deps/uv/src/unix/darwin-proctitle.m)7
-rw-r--r--deps/uv/src/unix/internal.h15
-rw-r--r--deps/uv/src/unix/kqueue.c16
-rw-r--r--deps/uv/src/unix/linux-core.c137
-rw-r--r--deps/uv/src/unix/linux-inotify.c9
-rw-r--r--deps/uv/src/unix/stream.c101
-rw-r--r--deps/uv/src/unix/sunos.c3
-rw-r--r--deps/uv/src/uv-common.c5
-rw-r--r--deps/uv/src/uv-common.h3
-rw-r--r--deps/uv/src/version.c2
-rw-r--r--deps/uv/src/win/core.c16
-rw-r--r--deps/uv/src/win/internal.h1
-rw-r--r--deps/uv/src/win/timer.c54
-rw-r--r--deps/uv/test/runner-unix.c28
-rw-r--r--deps/uv/test/runner-win.c40
-rw-r--r--deps/uv/test/runner.c94
-rw-r--r--deps/uv/test/runner.h5
-rw-r--r--deps/uv/test/task.h24
-rw-r--r--deps/uv/test/test-list.h9
-rw-r--r--deps/uv/test/test-osx-select.c82
-rw-r--r--deps/uv/test/test-ref.c12
-rw-r--r--deps/uv/uv.gyp21
31 files changed, 566 insertions, 323 deletions
diff --git a/deps/uv/.mailmap b/deps/uv/.mailmap
index 560a650018..5dc4075e39 100644
--- a/deps/uv/.mailmap
+++ b/deps/uv/.mailmap
@@ -2,6 +2,7 @@ Alan Gutierrez <alan@prettyrobots.com> <alan@blogometer.com>
Bert Belder <bertbelder@gmail.com> <info@2bs.nl>
Bert Belder <bertbelder@gmail.com> <user@ChrUbuntu.(none)>
Brandon Philips <brandon.philips@rackspace.com> <brandon@ifup.org>
+Brian White <mscdex@mscdex.net>
Brian White <mscdex@mscdex.net> <mscdex@gmail.com>
Frank Denis <github@pureftpd.org>
Isaac Z. Schlueter <i@izs.me>
diff --git a/deps/uv/AUTHORS b/deps/uv/AUTHORS
index 32793e193e..1562f4a680 100644
--- a/deps/uv/AUTHORS
+++ b/deps/uv/AUTHORS
@@ -84,3 +84,4 @@ Ben Kelly <ben@wanderview.com>
Kristian Evensen <kristian.evensen@gmail.com>
Nils Maier <maierman@web.de>
Nicholas Vavilov <vvnicholas@gmail.com>
+Miroslav Bajtoš <miro.bajtos@gmail.com>
diff --git a/deps/uv/ChangeLog b/deps/uv/ChangeLog
index 99798d767e..c96f8086ef 100644
--- a/deps/uv/ChangeLog
+++ b/deps/uv/ChangeLog
@@ -1,4 +1,73 @@
-2013.04.11, Version 0.11.1 (Unstable)
+2013.05.11, Version 0.11.2 (Unstable)
+
+Changes since version 0.11.1:
+
+* darwin: look up file path with F_GETPATH (Ben Noordhuis)
+
+* unix, windows: add uv_has_ref() function (Saúl Ibarra Corretgé)
+
+* build: avoid double / in paths for dtrace (Timothy J. Fontaine)
+
+* unix: remove src/unix/cygwin.c (Ben Noordhuis)
+
+* windows: deal with the fact that GetTickCount might lag (Bert Belder)
+
+* unix: silence STATIC_ASSERT compiler warnings (Ben Noordhuis)
+
+* linux: don't use fopen() in uv_resident_set_memory() (Ben Noordhuis)
+
+
+2013.04.24, Version 0.10.5 (Stable), 6595a7732c52eb4f8e57c88655f72997a8567a67
+
+Changes since version 0.10.4:
+
+* unix: silence STATIC_ASSERT compiler warnings (Ben Noordhuis)
+
+* windows: make timers handle large timeouts (Miroslav Bajtoš)
+
+* windows: remove superfluous assert statement (Bert Belder)
+
+* unix: silence STATIC_ASSERT compiler warnings (Ben Noordhuis)
+
+* linux: don't use fopen() in uv_resident_set_memory() (Ben Noordhuis)
+
+
+2013.04.12, Version 0.10.4 (Stable), 85827e26403ac6dfa331af8ec9916ea7e27bd833
+
+Changes since version 0.10.3:
+
+* include: update uv_backend_fd() documentation (Ben Noordhuis)
+
+* unix: include uv.h in src/version.c (Ben Noordhuis)
+
+* unix: don't write more than IOV_MAX iovecs (Fedor Indutny)
+
+* mingw-w64: don't call _set_invalid_parameter_handler (Nils Maier)
+
+* build: gyp disable thin archives (Timothy J. Fontaine)
+
+* sunos: re-export entire library when static (Timothy J. Fontaine)
+
+* unix: dtrace probes for tick-start and tick-stop (Timothy J. Fontaine)
+
+* windows: fix memory leak in fs__sendfile (Shannen Saez)
+
+* windows: remove double initialization in uv_tty_init (Shannen Saez)
+
+* build: fix dtrace-enabled out of tree build (Ben Noordhuis)
+
+* build: squelch -Wdollar-in-identifier-extension warnings (Ben Noordhuis)
+
+* inet: snprintf returns int, not size_t (Brian White)
+
+* win: refactor uv_cpu_info (Bert Belder)
+
+* build: add support for Visual Studio 2012 (Nicholas Vavilov)
+
+* build: -Wno-dollar-in-identifier-extension is clang only (Ben Noordhuis)
+
+
+2013.04.11, Version 0.11.1 (Unstable), 5c10e82ae0bc99eff86d4b9baff1f1aa0bf84c0a
This is the first versioned release from the current unstable libuv branch.
@@ -36,7 +105,7 @@ Changes since Node.js v0.11.0:
* build: add support for Visual Studio 2012 (Nicholas Vavilov)
-2013.02.04, Version 0.10.3 (Stable)
+2013.03.28, Version 0.10.3 (Stable), 31ebe23973dd98fd8a24c042b606f37a794e99d0
Changes since version 0.10.2:
@@ -53,7 +122,7 @@ Changes since version 0.10.2:
* unix: don't clear flags after closing UDP handle (Saúl Ibarra Corretgé)
-2013.03.25, Version 0.10.2 (Stable)
+2013.03.25, Version 0.10.2 (Stable), 0f36a00568f3e7608f97f6c6cdb081f4800a50c9
This is the first officially versioned release of libuv. Starting now
libuv will make releases independently of Node.js.
diff --git a/deps/uv/build.mk b/deps/uv/build.mk
index 00c71a5378..d3a9046b9a 100644
--- a/deps/uv/build.mk
+++ b/deps/uv/build.mk
@@ -88,6 +88,7 @@ TESTS= \
test/test-loop-stop.o \
test/test-multiple-listen.o \
test/test-mutexes.o \
+ test/test-osx-select.o \
test/test-pass-always.o \
test/test-ping-pong.o \
test/test-pipe-bind-error.o \
diff --git a/deps/uv/config-unix.mk b/deps/uv/config-unix.mk
index e126a30d75..3cecb57bde 100644
--- a/deps/uv/config-unix.mk
+++ b/deps/uv/config-unix.mk
@@ -18,8 +18,6 @@
# FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
# IN THE SOFTWARE.
-OBJC ?= $(CC)
-
E=
CSTDFLAG=--std=c89 -pedantic -Wall -Wextra -Wno-unused-parameter
CFLAGS += -g
@@ -80,8 +78,12 @@ endif
ifeq (darwin,$(PLATFORM))
HAVE_DTRACE=1
-# dtrace(1) probes contain dollar signs.
+# dtrace(1) probes contain dollar signs on OS X. Mute the warnings they
+# generate but only when CC=clang, -Wno-dollar-in-identifier-extension
+# is a clang extension.
+ifeq (__clang__,$(shell sh -c "$(CC) -dM -E - </dev/null | grep -ow __clang__"))
CFLAGS += -Wno-dollar-in-identifier-extension
+endif
CPPFLAGS += -D_DARWIN_USE_64_BIT_INODE=1
LDFLAGS += -framework Foundation \
-framework CoreServices \
@@ -130,13 +132,6 @@ OBJS += src/unix/openbsd.o
OBJS += src/unix/kqueue.o
endif
-ifneq (,$(findstring cygwin,$(PLATFORM)))
-# We drop the --std=c89, it hides CLOCK_MONOTONIC on cygwin
-CSTDFLAG = -D_GNU_SOURCE
-LDFLAGS+=
-OBJS += src/unix/cygwin.o
-endif
-
ifeq (sunos,$(PLATFORM))
RUNNER_LDFLAGS += -pthreads
else
@@ -181,9 +176,6 @@ test/%.o: test/%.c include/uv.h test/.buildstamp
clean-platform:
$(RM) test/run-{tests,benchmarks}.dSYM $(OBJS) $(OBJS:%.o=%.pic.o) src/unix/uv-dtrace.h
-%.pic.o %.o: %.m
- $(OBJC) $(CPPFLAGS) $(CFLAGS) -c $^ -o $@
-
src/unix/uv-dtrace.h: src/unix/uv-dtrace.d
dtrace -h -xnolibs -s $< -o $@
diff --git a/deps/uv/include/uv-private/uv-win.h b/deps/uv/include/uv-private/uv-win.h
index 4f0b7b1aa2..0ca4bc28b6 100644
--- a/deps/uv/include/uv-private/uv-win.h
+++ b/deps/uv/include/uv-private/uv-win.h
@@ -275,6 +275,8 @@ RB_HEAD(uv_timer_tree_s, uv_timer_s);
HANDLE iocp; \
/* The current time according to the event loop. in msecs. */ \
uint64_t time; \
+ /* GetTickCount() result when the event loop time was last updated. */ \
+ DWORD last_tick_count; \
/* Tail of a single-linked circular queue of pending reqs. If the queue */ \
/* is empty, tail_ is NULL. If there is only one item, */ \
/* tail_->next_req == tail_ */ \
diff --git a/deps/uv/include/uv.h b/deps/uv/include/uv.h
index 3b61e28f60..a3ebaa40b5 100644
--- a/deps/uv/include/uv.h
+++ b/deps/uv/include/uv.h
@@ -281,6 +281,7 @@ UV_EXTERN void uv_stop(uv_loop_t*);
*/
UV_EXTERN void uv_ref(uv_handle_t*);
UV_EXTERN void uv_unref(uv_handle_t*);
+UV_EXTERN int uv_has_ref(const uv_handle_t*);
UV_EXTERN void uv_update_time(uv_loop_t*);
UV_EXTERN uint64_t uv_now(uv_loop_t*);
@@ -579,9 +580,9 @@ UV_EXTERN int uv_accept(uv_stream_t* server, uv_stream_t* client);
/*
* Read data from an incoming stream. The callback will be made several
- * several times until there is no more data to read or uv_read_stop is
- * called. When we've reached EOF nread will be set to -1 and the error is
- * set to UV_EOF. When nread == -1 the buf parameter might not point to a
+ * times until there is no more data to read or uv_read_stop is called.
+ * When we've reached EOF nread will be set to -1 and the error is set
+ * to UV_EOF. When nread == -1 the buf parameter might not point to a
* valid buffer; in that case buf.len and buf.base are both set to 0.
* Note that nread might also be 0, which does *not* indicate an error or
* eof; it happens when libuv requested a buffer through the alloc callback
@@ -1754,9 +1755,9 @@ UV_EXTERN int uv_signal_stop(uv_signal_t* handle);
/*
- * Gets load avg
+ * Gets load average.
* See: http://en.wikipedia.org/wiki/Load_(computing)
- * (Returns [0,0,0] for windows and cygwin)
+ * Returns [0,0,0] on Windows.
*/
UV_EXTERN void uv_loadavg(double avg[3]);
diff --git a/deps/uv/src/unix/core.c b/deps/uv/src/unix/core.c
index 9268f40c37..98b48989a7 100644
--- a/deps/uv/src/unix/core.c
+++ b/deps/uv/src/unix/core.c
@@ -71,10 +71,8 @@ STATIC_ASSERT(sizeof(&((uv_buf_t*) 0)->base) ==
sizeof(((struct iovec*) 0)->iov_base));
STATIC_ASSERT(sizeof(&((uv_buf_t*) 0)->len) ==
sizeof(((struct iovec*) 0)->iov_len));
-STATIC_ASSERT((uintptr_t) &((uv_buf_t*) 0)->base ==
- (uintptr_t) &((struct iovec*) 0)->iov_base);
-STATIC_ASSERT((uintptr_t) &((uv_buf_t*) 0)->len ==
- (uintptr_t) &((struct iovec*) 0)->iov_len);
+STATIC_ASSERT(offsetof(uv_buf_t, base) == offsetof(struct iovec, iov_base));
+STATIC_ASSERT(offsetof(uv_buf_t, len) == offsetof(struct iovec, iov_len));
uint64_t uv_hrtime(void) {
diff --git a/deps/uv/src/unix/cygwin.c b/deps/uv/src/unix/cygwin.c
deleted file mode 100644
index 9ee520d7ec..0000000000
--- a/deps/uv/src/unix/cygwin.c
+++ /dev/null
@@ -1,90 +0,0 @@
-/* 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.
- */
-
-#include "uv.h"
-#include "internal.h"
-
-#include <assert.h>
-#include <stdint.h>
-#include <stddef.h>
-#include <errno.h>
-#include <unistd.h>
-#include <time.h>
-
-#undef NANOSEC
-#define NANOSEC ((uint64_t) 1e9)
-
-
-int uv__platform_loop_init(uv_loop_t* loop, int default_loop) {
- return 0;
-}
-
-
-void uv__platform_loop_delete(uv_loop_t* loop) {
-}
-
-
-uint64_t uv__hrtime(void) {
- struct timespec ts;
- clock_gettime(CLOCK_MONOTONIC, &ts);
- return (((uint64_t) ts.tv_sec) * NANOSEC + ts.tv_nsec);
-}
-
-
-void uv_loadavg(double avg[3]) {
- /* Unsupported as of cygwin 1.7.7 */
- avg[0] = avg[1] = avg[2] = 0;
-}
-
-
-int uv_exepath(char* buffer, size_t* size) {
- uint32_t usize;
-
- if (!buffer || !size) {
- return -1;
- }
-
- *size = readlink("/proc/self/exe", buffer, *size - 1);
- if (*size <= 0) return -1;
- buffer[*size] = '\0';
- return 0;
-}
-
-uint64_t uv_get_free_memory(void) {
- return (uint64_t) sysconf(_SC_PAGESIZE) * sysconf(_SC_AVPHYS_PAGES);
-}
-
-uint64_t uv_get_total_memory(void) {
- return (uint64_t) sysconf(_SC_PAGESIZE) * sysconf(_SC_PHYS_PAGES);
-}
-
-int uv_fs_event_init(uv_loop_t* loop,
- uv_fs_event_t* handle,
- const char* filename,
- uv_fs_event_cb cb,
- int flags) {
- uv__set_sys_error(loop, ENOSYS);
- return -1;
-}
-
-
-void uv__fs_event_close(uv_fs_event_t* handle) {
- assert(0 && "implement me");
-}
diff --git a/deps/uv/src/unix/darwin-proctitle.m b/deps/uv/src/unix/darwin-proctitle.c
index d0ee95b498..e6c85905c0 100644
--- a/deps/uv/src/unix/darwin-proctitle.m
+++ b/deps/uv/src/unix/darwin-proctitle.c
@@ -18,7 +18,8 @@
* IN THE SOFTWARE.
*/
-#include <Cocoa/Cocoa.h>
+#include <CoreFoundation/CoreFoundation.h>
+#include <ApplicationServices/ApplicationServices.h>
int uv__set_process_title(const char* title) {
@@ -43,14 +44,14 @@ int uv__set_process_title(const char* title) {
if (launch_services_bundle == NULL)
return -1;
- ls_get_current_application_asn =
+ ls_get_current_application_asn = (LSGetCurrentApplicationASNType)
CFBundleGetFunctionPointerForName(launch_services_bundle,
CFSTR("_LSGetCurrentApplicationASN"));
if (ls_get_current_application_asn == NULL)
return -1;
- ls_set_application_information_item =
+ ls_set_application_information_item = (LSSetApplicationInformationItemType)
CFBundleGetFunctionPointerForName(launch_services_bundle,
CFSTR("_LSSetApplicationInformationItem"));
diff --git a/deps/uv/src/unix/internal.h b/deps/uv/src/unix/internal.h
index 899c972b08..2f4d526a61 100644
--- a/deps/uv/src/unix/internal.h
+++ b/deps/uv/src/unix/internal.h
@@ -26,6 +26,7 @@
#include <assert.h>
#include <stdlib.h> /* abort */
+#include <string.h> /* strrchr */
#if defined(__STRICT_ANSI__)
# define inline __inline
@@ -46,7 +47,7 @@
#endif
#define STATIC_ASSERT(expr) \
- void uv__static_assert(int static_assert_failed[0 - !(expr)])
+ void uv__static_assert(int static_assert_failed[1 - 2 * !(expr)])
#define ACCESS_ONCE(type, var) \
(*(volatile type*) &(var))
@@ -256,6 +257,18 @@ static void uv__update_time(uv_loop_t* loop) {
loop->time = uv__hrtime() / 1000000;
}
+__attribute__((unused))
+static char* uv__basename_r(const char* path) {
+ char* s;
+
+ s = strrchr(path, '/');
+ if (s == NULL)
+ return (char*) path;
+
+ return s + 1;
+}
+
+
#ifdef HAVE_DTRACE
#include "uv-dtrace.h"
#else
diff --git a/deps/uv/src/unix/kqueue.c b/deps/uv/src/unix/kqueue.c
index 9ad06da4c0..fa40f6147e 100644
--- a/deps/uv/src/unix/kqueue.c
+++ b/deps/uv/src/unix/kqueue.c
@@ -259,6 +259,11 @@ static void uv__fs_event(uv_loop_t* loop, uv__io_t* w, unsigned int fflags) {
uv_fs_event_t* handle;
struct kevent ev;
int events;
+ const char* path;
+#if defined(F_GETPATH)
+ /* MAXPATHLEN == PATH_MAX but the former is what XNU calls it internally. */
+ char pathbuf[MAXPATHLEN];
+#endif
handle = container_of(w, uv_fs_event_t, event_watcher);
@@ -267,7 +272,16 @@ static void uv__fs_event(uv_loop_t* loop, uv__io_t* w, unsigned int fflags) {
else
events = UV_RENAME;
- handle->cb(handle, NULL, events, 0);
+ path = NULL;
+#if defined(F_GETPATH)
+ /* Also works when the file has been unlinked from the file system. Passing
+ * in the path when the file has been deleted is arguably a little strange
+ * but it's consistent with what the inotify backend does.
+ */
+ if (fcntl(handle->event_watcher.fd, F_GETPATH, pathbuf) == 0)
+ path = uv__basename_r(pathbuf);
+#endif
+ handle->cb(handle, path, events, 0);
if (handle->event_watcher.fd == -1)
return;
diff --git a/deps/uv/src/unix/linux-core.c b/deps/uv/src/unix/linux-core.c
index 630f5a1ccc..7bb05b5d32 100644
--- a/deps/uv/src/unix/linux-core.c
+++ b/deps/uv/src/unix/linux-core.c
@@ -284,98 +284,59 @@ uint64_t uv_get_total_memory(void) {
uv_err_t uv_resident_set_memory(size_t* rss) {
- FILE* f;
- int itmp;
- char ctmp;
- unsigned int utmp;
- size_t page_size = getpagesize();
- char *cbuf;
- int foundExeEnd;
- char buf[PATH_MAX + 1];
-
- f = fopen("/proc/self/stat", "r");
- if (!f) return uv__new_sys_error(errno);
-
- /* PID */
- if (fscanf(f, "%d ", &itmp) == 0) goto error; /* coverity[secure_coding] */
- /* Exec file */
- cbuf = buf;
- foundExeEnd = 0;
- if (fscanf (f, "%c", cbuf++) == 0) goto error;
- while (1) {
- if (fscanf(f, "%c", cbuf) == 0) goto error;
- if (*cbuf == ')') {
- foundExeEnd = 1;
- } else if (foundExeEnd && *cbuf == ' ') {
- *cbuf = 0;
- break;
- }
+ char buf[1024];
+ const char* s;
+ ssize_t n;
+ long val;
+ int fd;
+ int i;
+
+ do
+ fd = open("/proc/self/stat", O_RDONLY);
+ while (fd == -1 && errno == EINTR);
+
+ if (fd == -1)
+ return uv__new_sys_error(errno);
+
+ do
+ n = read(fd, buf, sizeof(buf) - 1);
+ while (n == -1 && errno == EINTR);
+
+ SAVE_ERRNO(close(fd));
+ if (n == -1)
+ return uv__new_sys_error(errno);
+ buf[n] = '\0';
+
+ s = strchr(buf, ' ');
+ if (s == NULL)
+ goto err;
- cbuf++;
+ s += 1;
+ if (*s != '(')
+ goto err;
+
+ s = strchr(s, ')');
+ if (s == NULL)
+ goto err;
+
+ for (i = 1; i <= 22; i++) {
+ s = strchr(s + 1, ' ');
+ if (s == NULL)
+ goto err;
}
- /* State */
- if (fscanf (f, "%c ", &ctmp) == 0) goto error; /* coverity[secure_coding] */
- /* Parent process */
- if (fscanf (f, "%d ", &itmp) == 0) goto error; /* coverity[secure_coding] */
- /* Process group */
- if (fscanf (f, "%d ", &itmp) == 0) goto error; /* coverity[secure_coding] */
- /* Session id */
- if (fscanf (f, "%d ", &itmp) == 0) goto error; /* coverity[secure_coding] */
- /* TTY */
- if (fscanf (f, "%d ", &itmp) == 0) goto error; /* coverity[secure_coding] */
- /* TTY owner process group */
- if (fscanf (f, "%d ", &itmp) == 0) goto error; /* coverity[secure_coding] */
- /* Flags */
- if (fscanf (f, "%u ", &utmp) == 0) goto error; /* coverity[secure_coding] */
- /* Minor faults (no memory page) */
- if (fscanf (f, "%u ", &utmp) == 0) goto error; /* coverity[secure_coding] */
- /* Minor faults, children */
- if (fscanf (f, "%u ", &utmp) == 0) goto error; /* coverity[secure_coding] */
- /* Major faults (memory page faults) */
- if (fscanf (f, "%u ", &utmp) == 0) goto error; /* coverity[secure_coding] */
- /* Major faults, children */
- if (fscanf (f, "%u ", &utmp) == 0) goto error; /* coverity[secure_coding] */
- /* utime */
- if (fscanf (f, "%d ", &itmp) == 0) goto error; /* coverity[secure_coding] */
- /* stime */
- if (fscanf (f, "%d ", &itmp) == 0) goto error; /* coverity[secure_coding] */
- /* utime, children */
- if (fscanf (f, "%d ", &itmp) == 0) goto error; /* coverity[secure_coding] */
- /* stime, children */
- if (fscanf (f, "%d ", &itmp) == 0) goto error; /* coverity[secure_coding] */
- /* jiffies remaining in current time slice */
- if (fscanf (f, "%d ", &itmp) == 0) goto error; /* coverity[secure_coding] */
- /* 'nice' value */
- if (fscanf (f, "%d ", &itmp) == 0) goto error; /* coverity[secure_coding] */
- /* jiffies until next timeout */
- if (fscanf (f, "%u ", &utmp) == 0) goto error; /* coverity[secure_coding] */
- /* jiffies until next SIGALRM */
- if (fscanf (f, "%u ", &utmp) == 0) goto error; /* coverity[secure_coding] */
- /* start time (jiffies since system boot) */
- if (fscanf (f, "%d ", &itmp) == 0) goto error; /* coverity[secure_coding] */
-
- /* Virtual memory size */
- if (fscanf (f, "%u ", &utmp) == 0) goto error; /* coverity[secure_coding] */
-
- /* Resident set size */
- if (fscanf (f, "%u ", &utmp) == 0) goto error; /* coverity[secure_coding] */
- *rss = (size_t) utmp * page_size;
-
- /* rlim */
- if (fscanf (f, "%u ", &utmp) == 0) goto error; /* coverity[secure_coding] */
- /* Start of text */
- if (fscanf (f, "%u ", &utmp) == 0) goto error; /* coverity[secure_coding] */
- /* End of text */
- if (fscanf (f, "%u ", &utmp) == 0) goto error; /* coverity[secure_coding] */
- /* Start of stack */
- if (fscanf (f, "%u ", &utmp) == 0) goto error; /* coverity[secure_coding] */
-
- fclose (f);
+
+ errno = 0;
+ val = strtol(s, NULL, 10);
+ if (errno != 0)
+ goto err;
+ if (val < 0)
+ goto err;
+
+ *rss = val * getpagesize();
return uv_ok_;
-error:
- fclose (f);
- return uv__new_sys_error(errno);
+err:
+ return uv__new_artificial_error(UV_EINVAL);
}
diff --git a/deps/uv/src/unix/linux-inotify.c b/deps/uv/src/unix/linux-inotify.c
index 76b9dfa450..af0242477e 100644
--- a/deps/uv/src/unix/linux-inotify.c
+++ b/deps/uv/src/unix/linux-inotify.c
@@ -45,13 +45,6 @@ struct watcher_root {
#define CAST(p) ((struct watcher_root*)(p))
-/* Don't look aghast, this is exactly how glibc's basename() works. */
-static char* basename_r(const char* path) {
- char* s = strrchr(path, '/');
- return s ? (s + 1) : (char*)path;
-}
-
-
static int compare_watchers(const struct watcher_list* a,
const struct watcher_list* b) {
if (a->wd < b->wd) return -1;
@@ -156,7 +149,7 @@ static void uv__inotify_read(uv_loop_t* loop,
* for modifications. Repurpose the filename for API compatibility.
* I'm not convinced this is a good thing, maybe it should go.
*/
- path = e->len ? (const char*) (e + 1) : basename_r(w->path);
+ path = e->len ? (const char*) (e + 1) : uv__basename_r(w->path);
QUEUE_FOREACH(q, &w->watchers) {
h = QUEUE_DATA(q, uv_fs_event_t, watchers);
diff --git a/deps/uv/src/unix/stream.c b/deps/uv/src/unix/stream.c
index 7a185ab621..0c38231d68 100644
--- a/deps/uv/src/unix/stream.c
+++ b/deps/uv/src/unix/stream.c
@@ -46,8 +46,8 @@ typedef struct uv__stream_select_s uv__stream_select_t;
struct uv__stream_select_s {
uv_stream_t* stream;
uv_thread_t thread;
- uv_sem_t sem;
- uv_mutex_t mutex;
+ uv_sem_t close_sem;
+ uv_sem_t async_sem;
uv_async_t async;
int events;
int fake_fd;
@@ -139,7 +139,7 @@ static void uv__stream_osx_select(void* arg) {
stream = arg;
s = stream->select;
- fd = stream->io_watcher.fd;
+ fd = s->fd;
if (fd > s->int_fd)
max_fd = fd;
@@ -148,7 +148,7 @@ static void uv__stream_osx_select(void* arg) {
while (1) {
/* Terminate on semaphore */
- if (uv_sem_trywait(&s->sem) == 0)
+ if (uv_sem_trywait(&s->close_sem) == 0)
break;
/* Watch fd using select(2) */
@@ -202,12 +202,16 @@ static void uv__stream_osx_select(void* arg) {
if (FD_ISSET(fd, &swrite))
events |= UV__POLLOUT;
- uv_mutex_lock(&s->mutex);
- s->events |= events;
- uv_mutex_unlock(&s->mutex);
+ assert(events != 0 || FD_ISSET(s->int_fd, &sread));
+ if (events != 0) {
+ ACCESS_ONCE(int, s->events) = events;
- if (events != 0)
uv_async_send(&s->async);
+ uv_sem_wait(&s->async_sem);
+
+ /* Should be processed at this stage */
+ assert((s->events == 0) || (stream->flags & UV_CLOSING));
+ }
}
}
@@ -240,10 +244,9 @@ static void uv__stream_osx_select_cb(uv_async_t* handle, int status) {
stream = s->stream;
/* Get and reset stream's events */
- uv_mutex_lock(&s->mutex);
events = s->events;
- s->events = 0;
- uv_mutex_unlock(&s->mutex);
+ ACCESS_ONCE(int, s->events) = 0;
+ uv_sem_post(&s->async_sem);
assert(events != 0);
assert(events == (events & (UV__POLLIN | UV__POLLOUT)));
@@ -305,6 +308,7 @@ int uv__stream_try_select(uv_stream_t* stream, int* fd) {
if (s == NULL)
return uv__set_artificial_error(stream->loop, UV_ENOMEM);
+ s->events = 0;
s->fd = *fd;
if (uv_async_init(stream->loop, &s->async, uv__stream_osx_select_cb)) {
@@ -315,10 +319,10 @@ int uv__stream_try_select(uv_stream_t* stream, int* fd) {
s->async.flags |= UV__HANDLE_INTERNAL;
uv__handle_unref(&s->async);
- if (uv_sem_init(&s->sem, 0))
+ if (uv_sem_init(&s->close_sem, 0))
goto fatal1;
- if (uv_mutex_init(&s->mutex))
+ if (uv_sem_init(&s->async_sem, 0))
goto fatal2;
/* Create fds for io watcher and to interrupt the select() loop. */
@@ -343,9 +347,9 @@ fatal4:
s->fake_fd = -1;
s->int_fd = -1;
fatal3:
- uv_mutex_destroy(&s->mutex);
+ uv_sem_destroy(&s->async_sem);
fatal2:
- uv_sem_destroy(&s->sem);
+ uv_sem_destroy(&s->close_sem);
fatal1:
uv_close((uv_handle_t*) &s->async, uv__stream_osx_cb_close);
return uv__set_sys_error(stream->loop, errno);
@@ -437,7 +441,6 @@ void uv__stream_destroy(uv_stream_t* stream) {
*/
static int uv__emfile_trick(uv_loop_t* loop, int accept_fd) {
int fd;
- int r;
if (loop->emfile_fd == -1)
return -1;
@@ -455,14 +458,8 @@ static int uv__emfile_trick(uv_loop_t* loop, int accept_fd) {
if (errno == EINTR)
continue;
- if (errno == EAGAIN || errno == EWOULDBLOCK)
- r = 0;
- else
- r = -1;
-
- loop->emfile_fd = uv__open_cloexec("/", O_RDONLY);
-
- return r;
+ SAVE_ERRNO(loop->emfile_fd = uv__open_cloexec("/", O_RDONLY));
+ return errno;
}
}
@@ -475,10 +472,9 @@ static int uv__emfile_trick(uv_loop_t* loop, int accept_fd) {
void uv__server_io(uv_loop_t* loop, uv__io_t* w, unsigned int events) {
- static int use_emfile_trick = -1;
uv_stream_t* stream;
+ int err;
int fd;
- int r;
stream = container_of(w, uv_stream_t, io_watcher);
assert(events == UV__POLLIN);
@@ -492,50 +488,32 @@ void uv__server_io(uv_loop_t* loop, uv__io_t* w, unsigned int events) {
*/
while (uv__stream_fd(stream) != -1) {
assert(stream->accepted_fd == -1);
+
#if defined(UV_HAVE_KQUEUE)
if (w->rcount <= 0)
return;
#endif /* defined(UV_HAVE_KQUEUE) */
- fd = uv__accept(uv__stream_fd(stream));
+ fd = uv__accept(uv__stream_fd(stream));
if (fd == -1) {
- switch (errno) {
-#if EWOULDBLOCK != EAGAIN
- case EWOULDBLOCK:
-#endif
- case EAGAIN:
- return; /* Not an error. */
-
- case ECONNABORTED:
- UV_DEC_BACKLOG(w)
- continue; /* Ignore. */
-
- case EMFILE:
- case ENFILE:
- if (use_emfile_trick == -1) {
- const char* val = getenv("UV_ACCEPT_EMFILE_TRICK");
- use_emfile_trick = (val == NULL || atoi(val) != 0);
- }
-
- if (use_emfile_trick) {
- SAVE_ERRNO(r = uv__emfile_trick(loop, uv__stream_fd(stream)));
- if (r == 0) {
- UV_DEC_BACKLOG(w)
- continue;
- }
- }
+ if (errno == EAGAIN || errno == EWOULDBLOCK)
+ return; /* Not an error. */
- /* Fall through. */
+ if (errno == ECONNABORTED)
+ continue; /* Ignore. Nothing we can do about that. */
- default:
- uv__set_sys_error(loop, errno);
- stream->connection_cb(stream, -1);
- continue;
+ if (errno == EMFILE || errno == ENFILE) {
+ SAVE_ERRNO(err = uv__emfile_trick(loop, uv__stream_fd(stream)));
+ if (err == EAGAIN || err == EWOULDBLOCK)
+ break;
}
+
+ uv__set_sys_error(loop, errno);
+ stream->connection_cb(stream, -1);
+ continue;
}
UV_DEC_BACKLOG(w)
-
stream->accepted_fd = fd;
stream->connection_cb(stream, 0);
@@ -1356,11 +1334,12 @@ void uv__stream_close(uv_stream_t* handle) {
s = handle->select;
- uv_sem_post(&s->sem);
+ uv_sem_post(&s->close_sem);
+ uv_sem_post(&s->async_sem);
uv__stream_osx_interrupt_select(handle);
uv_thread_join(&s->thread);
- uv_sem_destroy(&s->sem);
- uv_mutex_destroy(&s->mutex);
+ uv_sem_destroy(&s->close_sem);
+ uv_sem_destroy(&s->async_sem);
close(s->fake_fd);
close(s->int_fd);
uv_close((uv_handle_t*) &s->async, uv__stream_osx_cb_close);
diff --git a/deps/uv/src/unix/sunos.c b/deps/uv/src/unix/sunos.c
index e134b0a181..2413105c0f 100644
--- a/deps/uv/src/unix/sunos.c
+++ b/deps/uv/src/unix/sunos.c
@@ -189,6 +189,9 @@ void uv__io_poll(uv_loop_t* loop, int timeout) {
w->cb(loop, w, pe->portev_events);
nevents++;
+ if (w != loop->watchers[fd])
+ continue; /* Disabled by callback. */
+
/* Events Ports operates in oneshot mode, rearm timer on next run. */
if (w->pevents != 0 && QUEUE_EMPTY(&w->watcher_queue))
QUEUE_INSERT_TAIL(&loop->watcher_queue, &w->watcher_queue);
diff --git a/deps/uv/src/uv-common.c b/deps/uv/src/uv-common.c
index c95dfdd3e3..fc8831fd97 100644
--- a/deps/uv/src/uv-common.c
+++ b/deps/uv/src/uv-common.c
@@ -426,6 +426,11 @@ void uv_unref(uv_handle_t* handle) {
}
+int uv_has_ref(const uv_handle_t* handle) {
+ return uv__has_ref(handle);
+}
+
+
void uv_stop(uv_loop_t* loop) {
loop->stop_flag = 1;
}
diff --git a/deps/uv/src/uv-common.h b/deps/uv/src/uv-common.h
index e2d2f4bc12..6a47513be3 100644
--- a/deps/uv/src/uv-common.h
+++ b/deps/uv/src/uv-common.h
@@ -186,6 +186,9 @@ void uv__fs_poll_close(uv_fs_poll_t* handle);
} \
while (0)
+#define uv__has_ref(h) \
+ (((h)->flags & UV__HANDLE_REF) != 0)
+
#if defined(_WIN32)
# define uv__handle_platform_init(h)
#else
diff --git a/deps/uv/src/version.c b/deps/uv/src/version.c
index b413332499..0d502d01b7 100644
--- a/deps/uv/src/version.c
+++ b/deps/uv/src/version.c
@@ -29,7 +29,7 @@
#define UV_VERSION_MAJOR 0
#define UV_VERSION_MINOR 11
-#define UV_VERSION_PATCH 1
+#define UV_VERSION_PATCH 2
#define UV_VERSION_IS_RELEASE 1
diff --git a/deps/uv/src/win/core.c b/deps/uv/src/win/core.c
index a8699e1985..3ba3203803 100644
--- a/deps/uv/src/win/core.c
+++ b/deps/uv/src/win/core.c
@@ -90,6 +90,7 @@ static void uv_loop_init(uv_loop_t* loop) {
/* To prevent uninitialized memory access, loop->time must be intialized */
/* to zero before calling uv_update_time for the first time. */
loop->time = 0;
+ loop->last_tick_count = 0;
uv_update_time(loop);
QUEUE_INIT(&loop->handle_queue);
@@ -205,12 +206,15 @@ static void uv_poll(uv_loop_t* loop, int block) {
if (overlapped) {
/* Package was dequeued */
req = uv_overlapped_to_req(overlapped);
-
uv_insert_pending_req(loop, req);
-
} else if (GetLastError() != WAIT_TIMEOUT) {
/* Serious error */
uv_fatal_error(GetLastError(), "GetQueuedCompletionStatus");
+ } else {
+ /* We're sure that at least `timeout` milliseconds have expired, but */
+ /* this may not be reflected yet in the GetTickCount() return value. */
+ /* Therefore we ensure it's taken into account here. */
+ uv__time_forward(loop, timeout);
}
}
@@ -229,14 +233,13 @@ static void uv_poll_ex(uv_loop_t* loop, int block) {
timeout = 0;
}
- assert(pGetQueuedCompletionStatusEx);
-
success = pGetQueuedCompletionStatusEx(loop->iocp,
overlappeds,
ARRAY_SIZE(overlappeds),
&count,
timeout,
FALSE);
+
if (success) {
for (i = 0; i < count; i++) {
/* Package was dequeued */
@@ -246,6 +249,11 @@ static void uv_poll_ex(uv_loop_t* loop, int block) {
} else if (GetLastError() != WAIT_TIMEOUT) {
/* Serious error */
uv_fatal_error(GetLastError(), "GetQueuedCompletionStatusEx");
+ } else if (timeout > 0) {
+ /* We're sure that at least `timeout` milliseconds have expired, but */
+ /* this may not be reflected yet in the GetTickCount() return value. */
+ /* Therefore we ensure it's taken into account here. */
+ uv__time_forward(loop, timeout);
}
}
diff --git a/deps/uv/src/win/internal.h b/deps/uv/src/win/internal.h
index 9920f704ab..f0909cdf0e 100644
--- a/deps/uv/src/win/internal.h
+++ b/deps/uv/src/win/internal.h
@@ -206,6 +206,7 @@ void uv_poll_endgame(uv_loop_t* loop, uv_poll_t* handle);
void uv_timer_endgame(uv_loop_t* loop, uv_timer_t* handle);
DWORD uv_get_poll_timeout(uv_loop_t* loop);
+void uv__time_forward(uv_loop_t* loop, uint64_t msecs);
void uv_process_timers(uv_loop_t* loop);
diff --git a/deps/uv/src/win/timer.c b/deps/uv/src/win/timer.c
index 0c055da941..52c124e892 100644
--- a/deps/uv/src/win/timer.c
+++ b/deps/uv/src/win/timer.c
@@ -29,19 +29,38 @@
void uv_update_time(uv_loop_t* loop) {
- DWORD ticks = GetTickCount();
+ DWORD ticks;
+ ULARGE_INTEGER time;
- /* The assumption is made that LARGE_INTEGER.QuadPart has the same type */
- /* loop->time, which happens to be. Is there any way to assert this? */
- LARGE_INTEGER* time = (LARGE_INTEGER*) &loop->time;
+ ticks = GetTickCount();
- /* If the timer has wrapped, add 1 to it's high-order dword. */
+ time.QuadPart = loop->time;
+
+ /* GetTickCount() can conceivably wrap around, so when the current tick */
+ /* count is lower than the last tick count, we'll assume it has wrapped. */
/* uv_poll must make sure that the timer can never overflow more than */
/* once between two subsequent uv_update_time calls. */
- if (ticks < time->LowPart) {
- time->HighPart += 1;
- }
- time->LowPart = ticks;
+ time.LowPart = ticks;
+ if (ticks < loop->last_tick_count)
+ time.HighPart++;
+
+ /* Remember the last tick count. */
+ loop->last_tick_count = ticks;
+
+ /* The GetTickCount() resolution isn't too good. Sometimes it'll happen */
+ /* that GetQueuedCompletionStatus() or GetQueuedCompletionStatusEx() has */
+ /* waited for a couple of ms but this is not reflected in the GetTickCount */
+ /* result yet. Therefore whenever GetQueuedCompletionStatus times out */
+ /* we'll add the number of ms that it has waited to the current loop time. */
+ /* When that happened the loop time might be a little ms farther than what */
+ /* we've just computed, and we shouldn't update the loop time. */
+ if (loop->time < time.QuadPart)
+ loop->time = time.QuadPart;
+}
+
+
+void uv__time_forward(uv_loop_t* loop, uint64_t msecs) {
+ loop->time += msecs;
}
@@ -87,6 +106,17 @@ void uv_timer_endgame(uv_loop_t* loop, uv_timer_t* handle) {
}
+static uint64_t get_clamped_due_time(uint64_t loop_time, uint64_t timeout) {
+ uint64_t clamped_timeout;
+
+ clamped_timeout = loop_time + timeout;
+ if (clamped_timeout < timeout)
+ clamped_timeout = (uint64_t) -1;
+
+ return clamped_timeout;
+}
+
+
int uv_timer_start(uv_timer_t* handle, uv_timer_cb timer_cb, uint64_t timeout,
uint64_t repeat) {
uv_loop_t* loop = handle->loop;
@@ -97,7 +127,7 @@ int uv_timer_start(uv_timer_t* handle, uv_timer_cb timer_cb, uint64_t timeout,
}
handle->timer_cb = timer_cb;
- handle->due = loop->time + timeout;
+ handle->due = get_clamped_due_time(loop->time, timeout);
handle->repeat = repeat;
handle->flags |= UV_HANDLE_ACTIVE;
uv__handle_start(handle);
@@ -143,7 +173,7 @@ int uv_timer_again(uv_timer_t* handle) {
}
if (handle->repeat) {
- handle->due = loop->time + handle->repeat;
+ handle->due = get_clamped_due_time(loop->time, handle->repeat);
if (RB_INSERT(uv_timer_tree_s, &loop->timers, handle) != NULL) {
uv_fatal_error(ERROR_INVALID_DATA, "RB_INSERT");
@@ -212,7 +242,7 @@ void uv_process_timers(uv_loop_t* loop) {
if (timer->repeat != 0) {
/* If it is a repeating timer, reschedule with repeat timeout. */
- timer->due += timer->repeat;
+ timer->due = get_clamped_due_time(timer->due, timer->repeat);
if (timer->due < loop->time) {
timer->due = loop->time;
}
diff --git a/deps/uv/test/runner-unix.c b/deps/uv/test/runner-unix.c
index eefb700835..b66df51b98 100644
--- a/deps/uv/test/runner-unix.c
+++ b/deps/uv/test/runner-unix.c
@@ -286,6 +286,34 @@ int process_copy_output(process_info_t *p, int fd) {
}
+/* Copy the last line of the stdio output buffer to `buffer` */
+int process_read_last_line(process_info_t *p,
+ char* buffer,
+ size_t buffer_len) {
+ char* ptr;
+
+ int r = fseek(p->stdout_file, 0, SEEK_SET);
+ if (r < 0) {
+ perror("fseek");
+ return -1;
+ }
+
+ buffer[0] = '\0';
+
+ while (fgets(buffer, buffer_len, p->stdout_file) != NULL) {
+ for (ptr = buffer; *ptr && *ptr != '\r' && *ptr != '\n'; ptr++);
+ *ptr = '\0';
+ }
+
+ if (ferror(p->stdout_file)) {
+ perror("read");
+ buffer[0] = '\0';
+ return -1;
+ }
+ return 0;
+}
+
+
/* Return the name that was specified when `p` was started by process_start */
char* process_get_name(process_info_t *p) {
return p->name;
diff --git a/deps/uv/test/runner-win.c b/deps/uv/test/runner-win.c
index 3aae1c3e9c..5d23259437 100644
--- a/deps/uv/test/runner-win.c
+++ b/deps/uv/test/runner-win.c
@@ -248,6 +248,46 @@ int process_copy_output(process_info_t *p, int fd) {
}
+int process_read_last_line(process_info_t *p,
+ char * buffer,
+ size_t buffer_len) {
+ DWORD size;
+ DWORD read;
+ DWORD start;
+ OVERLAPPED overlapped;
+
+ ASSERT(buffer_len > 0);
+
+ size = GetFileSize(p->stdio_out, NULL);
+ if (size == INVALID_FILE_SIZE)
+ return -1;
+
+ if (size == 0) {
+ buffer[0] = '\0';
+ return 1;
+ }
+
+ memset(&overlapped, 0, sizeof overlapped);
+ if (size >= buffer_len)
+ overlapped.Offset = size - buffer_len - 1;
+
+ if (!ReadFile(p->stdio_out, buffer, buffer_len - 1, &read, &overlapped))
+ return -1;
+
+ for (start = read - 1; start >= 0; start--) {
+ if (buffer[start] == '\n' || buffer[start] == '\r')
+ break;
+ }
+
+ if (start > 0)
+ memmove(buffer, buffer + start, read - start);
+
+ buffer[read - start] = '\0';
+
+ return 0;
+}
+
+
char* process_get_name(process_info_t *p) {
return p->name;
}
diff --git a/deps/uv/test/runner.c b/deps/uv/test/runner.c
index bda1080a18..d8e9ddeb01 100644
--- a/deps/uv/test/runner.c
+++ b/deps/uv/test/runner.c
@@ -31,12 +31,25 @@ char executable_path[PATHMAX] = { '\0' };
int tap_output = 0;
-static void log_progress(int total, int passed, int failed, const char* name) {
+static void log_progress(int total,
+ int passed,
+ int failed,
+ int todos,
+ int skipped,
+ const char* name) {
+ int progress;
+
if (total == 0)
total = 1;
- LOGF("[%% %3d|+ %3d|- %3d]: %s", (int) ((passed + failed) / ((double) total) * 100.0),
- passed, failed, name);
+ progress = 100 * (passed + failed + skipped + todos) / total;
+ LOGF("[%% %3d|+ %3d|- %3d|T %3d|S %3d]: %s",
+ progress,
+ passed,
+ failed,
+ todos,
+ skipped,
+ name);
}
@@ -78,7 +91,13 @@ const char* fmt(double d) {
int run_tests(int timeout, int benchmark_output) {
- int total, passed, failed, current;
+ int total;
+ int passed;
+ int failed;
+ int todos;
+ int skipped;
+ int current;
+ int test_result;
task_entry_t* task;
/* Count the number of tests. */
@@ -96,6 +115,8 @@ int run_tests(int timeout, int benchmark_output) {
/* Run all tests. */
passed = 0;
failed = 0;
+ todos = 0;
+ skipped = 0;
current = 1;
for (task = TASKS; task->main; task++) {
if (task->is_helper) {
@@ -106,13 +127,15 @@ int run_tests(int timeout, int benchmark_output) {
rewind_cursor();
if (!benchmark_output && !tap_output) {
- log_progress(total, passed, failed, task->task_name);
+ log_progress(total, passed, failed, todos, skipped, task->task_name);
}
- if (run_test(task->task_name, timeout, benchmark_output, current) == 0) {
- passed++;
- } else {
- failed++;
+ test_result = run_test(task->task_name, timeout, benchmark_output, current);
+ switch (test_result) {
+ case TEST_OK: passed++; break;
+ case TEST_TODO: todos++; break;
+ case TEST_SKIP: skipped++; break;
+ default: failed++;
}
current++;
}
@@ -121,13 +144,50 @@ int run_tests(int timeout, int benchmark_output) {
rewind_cursor();
if (!benchmark_output && !tap_output) {
- log_progress(total, passed, failed, "Done.\n");
+ log_progress(total, passed, failed, todos, skipped, "Done.\n");
}
return failed;
}
+void log_tap_result(int test_count,
+ const char* test,
+ int status,
+ process_info_t* process) {
+ const char* result;
+ const char* directive;
+ char reason[1024];
+
+ switch (status) {
+ case TEST_OK:
+ result = "ok";
+ directive = "";
+ break;
+ case TEST_TODO:
+ result = "not ok";
+ directive = " # TODO ";
+ break;
+ case TEST_SKIP:
+ result = "ok";
+ directive = " # SKIP ";
+ break;
+ default:
+ result = "not ok";
+ directive = "";
+ }
+
+ if ((status == TEST_SKIP || status == TEST_TODO) &&
+ process_output_size(process) > 0) {
+ process_read_last_line(process, reason, sizeof reason);
+ } else {
+ reason[0] = '\0';
+ }
+
+ LOGF("%s %d - %s%s%s\n", result, test_count, test, directive, reason);
+}
+
+
int run_test(const char* test,
int timeout,
int benchmark_output,
@@ -231,7 +291,7 @@ int run_test(const char* test,
}
status = process_reap(main_proc);
- if (status != 0) {
+ if (status != TEST_OK) {
snprintf(errmsg,
sizeof errmsg,
"exit code %d",
@@ -255,17 +315,17 @@ out:
FATAL("process_wait failed");
}
- if (tap_output) {
- if (status == 0)
- LOGF("ok %d - %s\n", test_count, test);
- else
- LOGF("not ok %d - %s\n", test_count, test);
- }
+ if (tap_output)
+ log_tap_result(test_count, test, status, &processes[i]);
/* Show error and output from processes if the test failed. */
if (status != 0 || task->show_output) {
if (tap_output) {
LOGF("#");
+ } else if (status == TEST_TODO) {
+ LOGF("\n`%s` todo\n", test);
+ } else if (status == TEST_SKIP) {
+ LOGF("\n`%s` skipped\n", test);
} else if (status != 0) {
LOGF("\n`%s` failed: %s\n", test, errmsg);
} else {
diff --git a/deps/uv/test/runner.h b/deps/uv/test/runner.h
index 8be9e39fcc..aa7f205407 100644
--- a/deps/uv/test/runner.h
+++ b/deps/uv/test/runner.h
@@ -143,6 +143,11 @@ long int process_output_size(process_info_t *p);
/* Copy the contents of the stdio output buffer to `fd`. */
int process_copy_output(process_info_t *p, int fd);
+/* Copy the last line of the stdio output buffer to `buffer` */
+int process_read_last_line(process_info_t *p,
+ char * buffer,
+ size_t buffer_len);
+
/* Return the name that was specified when `p` was started by process_start */
char* process_get_name(process_info_t *p);
diff --git a/deps/uv/test/task.h b/deps/uv/test/task.h
index de7c80ec3a..308201e579 100644
--- a/deps/uv/test/task.h
+++ b/deps/uv/test/task.h
@@ -119,4 +119,28 @@ void uv_sleep(int msec);
/* Format big numbers nicely. WARNING: leaks memory. */
const char* fmt(double d);
+/* Reserved test exit codes. */
+enum test_status {
+ TEST_OK = 0,
+ TEST_TODO,
+ TEST_SKIP
+};
+
+#define RETURN_OK() \
+ do { \
+ return TEST_OK; \
+ } while (0)
+
+#define RETURN_TODO(explanation) \
+ do { \
+ LOGF("%s\n", explanation); \
+ return TEST_TODO; \
+ } while (0)
+
+#define RETURN_SKIP(explanation) \
+ do { \
+ LOGF("%s\n", explanation); \
+ return TEST_SKIP; \
+ } while (0)
+
#endif /* TASK_H_ */
diff --git a/deps/uv/test/test-list.h b/deps/uv/test/test-list.h
index 30a2a0a28f..0822d7f151 100644
--- a/deps/uv/test/test-list.h
+++ b/deps/uv/test/test-list.h
@@ -128,6 +128,7 @@ TEST_DECLARE (pipe_ref2)
TEST_DECLARE (pipe_ref3)
TEST_DECLARE (pipe_ref4)
TEST_DECLARE (process_ref)
+TEST_DECLARE (has_ref)
TEST_DECLARE (active)
TEST_DECLARE (embed)
TEST_DECLARE (async)
@@ -221,6 +222,9 @@ TEST_DECLARE (we_get_signal)
TEST_DECLARE (we_get_signals)
TEST_DECLARE (signal_multiple_loops)
#endif
+#ifdef __APPLE__
+TEST_DECLARE (osx_select)
+#endif
HELPER_DECLARE (tcp4_echo_server)
HELPER_DECLARE (tcp6_echo_server)
HELPER_DECLARE (udp4_echo_server)
@@ -377,6 +381,7 @@ TASK_LIST_START
TEST_ENTRY (pipe_ref4)
TEST_HELPER (pipe_ref4, pipe_echo_server)
TEST_ENTRY (process_ref)
+ TEST_ENTRY (has_ref)
TEST_ENTRY (loop_handles)
TEST_ENTRY (walk_handles)
@@ -442,6 +447,10 @@ TASK_LIST_START
TEST_ENTRY (signal_multiple_loops)
#endif
+#ifdef __APPLE__
+ TEST_ENTRY (osx_select)
+#endif
+
TEST_ENTRY (fs_file_noent)
TEST_ENTRY (fs_file_nametoolong)
TEST_ENTRY (fs_file_loop)
diff --git a/deps/uv/test/test-osx-select.c b/deps/uv/test/test-osx-select.c
new file mode 100644
index 0000000000..5c2cbd4d93
--- /dev/null
+++ b/deps/uv/test/test-osx-select.c
@@ -0,0 +1,82 @@
+/* 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.
+ */
+
+#include "uv.h"
+#include "task.h"
+
+#ifdef __APPLE__
+
+#include <sys/ioctl.h>
+#include <string.h>
+
+static int read_count;
+
+
+static uv_buf_t alloc_cb(uv_handle_t* handle, size_t size) {
+ static char buf[1024];
+
+ return uv_buf_init(buf, ARRAY_SIZE(buf));
+}
+
+
+static void read_cb(uv_stream_t* stream, ssize_t nread, uv_buf_t buf) {
+ fprintf(stdout, "got data %d\n", ++read_count);
+
+ if (read_count == 3)
+ uv_close((uv_handle_t*) stream, NULL);
+}
+
+
+TEST_IMPL(osx_select) {
+ int r;
+ int fd;
+ size_t i;
+ size_t len;
+ const char* str;
+ uv_tty_t tty;
+
+ fd = open("/dev/tty", O_RDONLY);
+
+ ASSERT(fd >= 0);
+
+ r = uv_tty_init(uv_default_loop(), &tty, fd, 1);
+ ASSERT(r == 0);
+
+ uv_read_start((uv_stream_t*) &tty, alloc_cb, read_cb);
+
+ // Emulate user-input
+ str = "got some input\n"
+ "with a couple of lines\n"
+ "feel pretty happy\n";
+ for (i = 0, len = strlen(str); i < len; i++) {
+ r = ioctl(fd, TIOCSTI, str + i);
+ ASSERT(r == 0);
+ }
+
+ uv_run(uv_default_loop(), UV_RUN_DEFAULT);
+
+ ASSERT(read_count == 3);
+
+ MAKE_VALGRIND_HAPPY();
+ return 0;
+}
+
+#endif /* __APPLE__ */
diff --git a/deps/uv/test/test-ref.c b/deps/uv/test/test-ref.c
index 9fc214ab60..37279ac89a 100644
--- a/deps/uv/test/test-ref.c
+++ b/deps/uv/test/test-ref.c
@@ -413,3 +413,15 @@ TEST_IMPL(process_ref) {
MAKE_VALGRIND_HAPPY();
return 0;
}
+
+
+TEST_IMPL(has_ref) {
+ uv_idle_t h;
+ uv_idle_init(uv_default_loop(), &h);
+ uv_ref((uv_handle_t*)&h);
+ ASSERT(uv_has_ref((uv_handle_t*)&h) == 1);
+ uv_unref((uv_handle_t*)&h);
+ ASSERT(uv_has_ref((uv_handle_t*)&h) == 0);
+ MAKE_VALGRIND_HAPPY();
+ return 0;
+}
diff --git a/deps/uv/uv.gyp b/deps/uv/uv.gyp
index 6f1de77b0f..f2cdd538d3 100644
--- a/deps/uv/uv.gyp
+++ b/deps/uv/uv.gyp
@@ -5,7 +5,8 @@
# this is only relevant when dtrace is enabled and libuv is a child project
# as it's necessary to correctly locate the object files for post
# processing.
- 'uv_parent_path': '',
+ # XXX gyp is quite sensitive about paths with double / they don't normalize
+ 'uv_parent_path': '/',
},
'target_defaults': {
@@ -176,7 +177,7 @@
'sources': [
'src/unix/darwin.c',
'src/unix/fsevents.c',
- 'src/unix/darwin-proctitle.m',
+ 'src/unix/darwin-proctitle.c',
],
'link_settings': {
'libraries': [
@@ -235,21 +236,16 @@
}],
[ 'OS=="freebsd" or OS=="dragonflybsd"', {
'sources': [ 'src/unix/freebsd.c' ],
- 'link_settings': {
- 'libraries': [
- '-lkvm',
- ],
- },
}],
[ 'OS=="openbsd"', {
'sources': [ 'src/unix/openbsd.c' ],
}],
[ 'OS=="netbsd"', {
'sources': [ 'src/unix/netbsd.c' ],
+ }],
+ [ 'OS in "freebsd dragonflybsd openbsd netbsd".split()', {
'link_settings': {
- 'libraries': [
- '-lkvm',
- ],
+ 'libraries': [ '-lkvm' ],
},
}],
[ 'OS in "mac freebsd dragonflybsd openbsd netbsd".split()', {
@@ -309,6 +305,7 @@
'test/test-loop-stop.c',
'test/test-walk-handles.c',
'test/test-multiple-listen.c',
+ 'test/test-osx-select.c',
'test/test-pass-always.c',
'test/test-ping-pong.c',
'test/test-pipe-bind-error.c',
@@ -475,10 +472,10 @@
'action_name': 'uv_dtrace_o',
'inputs': [
'src/unix/uv-dtrace.d',
- '<(PRODUCT_DIR)/obj.target/libuv/<(uv_parent_path)/src/unix/core.o',
+ '<(PRODUCT_DIR)/obj.target/libuv<(uv_parent_path)src/unix/core.o',
],
'outputs': [
- '<(PRODUCT_DIR)/obj.target/libuv/<(uv_parent_path)/src/unix/dtrace.o',
+ '<(PRODUCT_DIR)/obj.target/libuv<(uv_parent_path)src/unix/dtrace.o',
],
'action': [ 'dtrace', '-G', '-xnolibs', '-s', '<@(_inputs)',
'-o', '<@(_outputs)' ]