summaryrefslogtreecommitdiff
path: root/deps/uv
diff options
context:
space:
mode:
authorcjihrig <cjihrig@gmail.com>2017-01-31 20:06:00 -0500
committercjihrig <cjihrig@gmail.com>2017-02-09 13:03:09 -0500
commit8514269876c4250e885a1b2407cfa7eb92498c0e (patch)
treef92827180e842283c68457a714480926032965f2 /deps/uv
parenta4bb9fdb893c8f2c36a6b77862e29b2608e080c2 (diff)
downloadandroid-node-v8-8514269876c4250e885a1b2407cfa7eb92498c0e.tar.gz
android-node-v8-8514269876c4250e885a1b2407cfa7eb92498c0e.tar.bz2
android-node-v8-8514269876c4250e885a1b2407cfa7eb92498c0e.zip
deps: upgrade libuv to 1.11.0
Fixes: https://github.com/nodejs/node/issues/10165 Fixes: https://github.com/nodejs/node/issues/9856 Fixes: https://github.com/nodejs/node/issues/10607 Fixes: https://github.com/nodejs/node/issues/11104 PR-URL: https://github.com/nodejs/node/pull/11094 Reviewed-By: James M Snell <jasnell@gmail.com> Reviewed-By: Sakthipriyan Vairamani <thechargingvolcano@gmail.com> Reviewed-By: Santiago Gimeno <santiago.gimeno@gmail.com> Reviewed-By: Michael Dawson <michael_dawson@ca.ibm.com>
Diffstat (limited to 'deps/uv')
-rw-r--r--deps/uv/.mailmap1
-rw-r--r--deps/uv/AUTHORS5
-rw-r--r--deps/uv/ChangeLog39
-rw-r--r--deps/uv/Makefile.am12
-rw-r--r--deps/uv/appveyor.yml2
-rw-r--r--deps/uv/common.gypi4
-rw-r--r--deps/uv/configure.ac2
-rw-r--r--deps/uv/docs/src/conf.py6
-rw-r--r--deps/uv/docs/src/misc.rst6
-rw-r--r--deps/uv/include/pthread-barrier.h2
-rw-r--r--deps/uv/include/uv-os390.h3
-rw-r--r--deps/uv/include/uv-unix.h4
-rw-r--r--deps/uv/include/uv-version.h4
-rw-r--r--deps/uv/include/uv-win.h1
-rw-r--r--deps/uv/src/unix/aix.c86
-rw-r--r--deps/uv/src/unix/atomic-ops.h27
-rw-r--r--deps/uv/src/unix/core.c3
-rw-r--r--deps/uv/src/unix/darwin.c10
-rw-r--r--deps/uv/src/unix/fs.c28
-rw-r--r--deps/uv/src/unix/internal.h4
-rw-r--r--deps/uv/src/unix/os390-syscalls.c334
-rw-r--r--deps/uv/src/unix/os390-syscalls.h69
-rw-r--r--deps/uv/src/unix/os390.c823
-rw-r--r--deps/uv/src/unix/process.c4
-rw-r--r--deps/uv/src/unix/proctitle.c6
-rw-r--r--deps/uv/src/unix/pthread-barrier.c3
-rw-r--r--deps/uv/src/unix/stream.c28
-rw-r--r--deps/uv/src/unix/sunos.c11
-rw-r--r--deps/uv/src/uv-common.c12
-rw-r--r--deps/uv/src/win/signal.c118
-rw-r--r--deps/uv/src/win/winapi.h4
-rw-r--r--deps/uv/test/test-error.c3
-rw-r--r--deps/uv/test/test-fs.c45
-rw-r--r--deps/uv/test/test-list.h4
-rw-r--r--deps/uv/test/test-process-title.c2
-rw-r--r--deps/uv/test/test-signal.c35
-rw-r--r--deps/uv/test/test-tty.c3
-rw-r--r--deps/uv/uv.gyp34
38 files changed, 1589 insertions, 198 deletions
diff --git a/deps/uv/.mailmap b/deps/uv/.mailmap
index 4966caf5fa..8acf8fecd1 100644
--- a/deps/uv/.mailmap
+++ b/deps/uv/.mailmap
@@ -1,6 +1,7 @@
Aaron Bieber <qbit@deftly.net> <deftly@gmail.com>
Alan Gutierrez <alan@prettyrobots.com> <alan@blogometer.com>
Andrius Bentkus <andrius.bentkus@gmail.com> <toxedvirus@gmail.com>
+Bert Belder <bertbelder@gmail.com> <i@bertbelder.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>
diff --git a/deps/uv/AUTHORS b/deps/uv/AUTHORS
index 49c8e17f23..4719d2368a 100644
--- a/deps/uv/AUTHORS
+++ b/deps/uv/AUTHORS
@@ -279,3 +279,8 @@ Philippe Laferriere <laferriere.phil@gmail.com>
Will Speak <lithiumflame@gmail.com>
Hitesh Kanwathirtha <digitalinfinity@gmail.com>
Eric Sciple <ersciple@microsoft.com>
+jBarz <jBarz@users.noreply.github.com>
+muflub <admin@lodle.net>
+Daniel Bevenius <daniel.bevenius@gmail.com>
+Howard Hellyer <hhellyer@uk.ibm.com>
+Chris Araman <chris.araman@fuze.com>
diff --git a/deps/uv/ChangeLog b/deps/uv/ChangeLog
index d865f22667..da4c3b13f1 100644
--- a/deps/uv/ChangeLog
+++ b/deps/uv/ChangeLog
@@ -1,3 +1,42 @@
+2017.02.02, Version 1.11.0 (Stable), 7452ef4e06a4f99ee26b694c65476401534f2725
+
+Changes since version 1.10.2:
+
+* Now working on version 1.10.3 (cjihrig)
+
+* win: added fcntl.h to uv-win.h (Michele Caini)
+
+* unix: move function call out of assert (jBarz)
+
+* fs: cleanup uv__fs_scandir (Santiago Gimeno)
+
+* fs: fix crash in uv_fs_scandir_next (muflub)
+
+* win,signal: fix potential deadlock (Bartosz Sosnowski)
+
+* unix: use async-signal safe functions between fork and exec (jBarz)
+
+* sunos: fix SUNOS_NO_IFADDRS build (Ben Noordhuis)
+
+* zos: make platform functional (John Barboza)
+
+* doc: add repitition qualifier to version regexs (Daniel Bevenius)
+
+* zos: use gyp OS label "os390" on z/OS (John Barboza)
+
+* aix: enable uv_get/set_process_title (Howard Hellyer)
+
+* zos: use built-in proctitle implementation (John Barboza)
+
+* Revert "darwin: use clock_gettime in macOS 10.12" (Chris Araman)
+
+* win,test: don't write uninitialized buffer to tty (Bert Belder)
+
+* win: define ERROR_ELEVATION_REQUIRED for MinGW (Richard Lau)
+
+* aix: re-enable fs watch facility (Gireesh Punathil)
+
+
2017.01.10, Version 1.10.2 (Stable), cb9f579a454b8db592030ffa274ae58df78dbe20
Changes since version 1.10.1:
diff --git a/deps/uv/Makefile.am b/deps/uv/Makefile.am
index c232b6dbdc..036464e71e 100644
--- a/deps/uv/Makefile.am
+++ b/deps/uv/Makefile.am
@@ -316,7 +316,11 @@ test_run_tests_CFLAGS += -D_UNIX03_THREADS \
endif
if AIX
-libuv_la_CFLAGS += -D_ALL_SOURCE -D_XOPEN_SOURCE=500 -D_LINUX_SOURCE_COMPAT -D_THREAD_SAFE
+libuv_la_CFLAGS += -D_ALL_SOURCE \
+ -D_XOPEN_SOURCE=500 \
+ -D_LINUX_SOURCE_COMPAT \
+ -D_THREAD_SAFE \
+ -DHAVE_SYS_AHAFS_EVPRODS_H
include_HEADERS += include/uv-aix.h
libuv_la_SOURCES += src/unix/aix.c
endif
@@ -402,8 +406,10 @@ libuv_la_CFLAGS += -D_UNIX03_THREADS \
-qFLOAT=IEEE
libuv_la_LDFLAGS += -qXPLINK
libuv_la_SOURCES += src/unix/pthread-fixes.c \
- src/unix/pthread-barrier.c
-libuv_la_SOURCES += src/unix/os390.c
+ src/unix/pthread-barrier.c \
+ src/unix/os390.c \
+ src/unix/os390-syscalls.c \
+ src/unix/proctitle.c
endif
if HAVE_PKG_CONFIG
diff --git a/deps/uv/appveyor.yml b/deps/uv/appveyor.yml
index 6329413783..e8e79f051e 100644
--- a/deps/uv/appveyor.yml
+++ b/deps/uv/appveyor.yml
@@ -1,4 +1,4 @@
-version: v1.10.2.build{build}
+version: v1.11.0.build{build}
install:
- cinst -y nsis
diff --git a/deps/uv/common.gypi b/deps/uv/common.gypi
index 44db701d68..470b73385d 100644
--- a/deps/uv/common.gypi
+++ b/deps/uv/common.gypi
@@ -35,7 +35,7 @@
'OTHER_CFLAGS': [ '-Wno-strict-aliasing' ],
},
'conditions': [
- ['OS != "zos"', {
+ ['OS != "os390"', {
'cflags': [ '-O0', '-fwrapv' ]
}],
['OS == "android"', {
@@ -154,7 +154,7 @@
'cflags': [ '-pthreads' ],
'ldflags': [ '-pthreads' ],
}],
- [ 'OS not in "solaris android zos"', {
+ [ 'OS not in "solaris android os390"', {
'cflags': [ '-pthread' ],
'ldflags': [ '-pthread' ],
}],
diff --git a/deps/uv/configure.ac b/deps/uv/configure.ac
index abaf971772..360652198e 100644
--- a/deps/uv/configure.ac
+++ b/deps/uv/configure.ac
@@ -13,7 +13,7 @@
# OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
AC_PREREQ(2.57)
-AC_INIT([libuv], [1.10.2], [https://github.com/libuv/libuv/issues])
+AC_INIT([libuv], [1.11.0], [https://github.com/libuv/libuv/issues])
AC_CONFIG_MACRO_DIR([m4])
m4_include([m4/libuv-extra-automake-flags.m4])
m4_include([m4/as_case.m4])
diff --git a/deps/uv/docs/src/conf.py b/deps/uv/docs/src/conf.py
index b9eaa13743..3f8689d2e5 100644
--- a/deps/uv/docs/src/conf.py
+++ b/deps/uv/docs/src/conf.py
@@ -21,11 +21,11 @@ def get_libuv_version():
with open('../../include/uv-version.h') as f:
data = f.read()
try:
- m = re.search(r"""^#define UV_VERSION_MAJOR (\d)$""", data, re.MULTILINE)
+ m = re.search(r"""^#define UV_VERSION_MAJOR (\d+)$""", data, re.MULTILINE)
major = int(m.group(1))
- m = re.search(r"""^#define UV_VERSION_MINOR (\d)$""", data, re.MULTILINE)
+ m = re.search(r"""^#define UV_VERSION_MINOR (\d+)$""", data, re.MULTILINE)
minor = int(m.group(1))
- m = re.search(r"""^#define UV_VERSION_PATCH (\d)$""", data, re.MULTILINE)
+ m = re.search(r"""^#define UV_VERSION_PATCH (\d+)$""", data, re.MULTILINE)
patch = int(m.group(1))
m = re.search(r"""^#define UV_VERSION_IS_RELEASE (\d)$""", data, re.MULTILINE)
is_release = int(m.group(1))
diff --git a/deps/uv/docs/src/misc.rst b/deps/uv/docs/src/misc.rst
index 95237f49c7..7193469462 100644
--- a/deps/uv/docs/src/misc.rst
+++ b/deps/uv/docs/src/misc.rst
@@ -192,7 +192,11 @@ API
.. c:function:: int uv_set_process_title(const char* title)
- Sets the current process title.
+ Sets the current process title. On platforms with a fixed size buffer for the
+ process title the contents of `title` will be copied to the buffer and
+ truncated if larger than the available space. Other platforms will return
+ `UV_ENOMEM` if they cannot allocate enough space to duplicate the contents of
+ `title`.
.. c:function:: int uv_resident_set_memory(size_t* rss)
diff --git a/deps/uv/include/pthread-barrier.h b/deps/uv/include/pthread-barrier.h
index 3e01705d9c..900ebedd30 100644
--- a/deps/uv/include/pthread-barrier.h
+++ b/deps/uv/include/pthread-barrier.h
@@ -18,7 +18,9 @@ OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
#define _UV_PTHREAD_BARRIER_
#include <errno.h>
#include <pthread.h>
+#if !defined(__MVS__)
#include <semaphore.h> /* sem_t */
+#endif
#define PTHREAD_BARRIER_SERIAL_THREAD 0x12345
diff --git a/deps/uv/include/uv-os390.h b/deps/uv/include/uv-os390.h
index b0b068f44e..58f926111a 100644
--- a/deps/uv/include/uv-os390.h
+++ b/deps/uv/include/uv-os390.h
@@ -24,4 +24,7 @@
#define UV_PLATFORM_SEM_T int
+#define UV_PLATFORM_LOOP_FIELDS \
+ void* ep; \
+
#endif /* UV_MVS_H */
diff --git a/deps/uv/include/uv-unix.h b/deps/uv/include/uv-unix.h
index bca2714476..3030f719a2 100644
--- a/deps/uv/include/uv-unix.h
+++ b/deps/uv/include/uv-unix.h
@@ -36,7 +36,9 @@
#include <termios.h>
#include <pwd.h>
+#if !defined(__MVS__)
#include <semaphore.h>
+#endif
#include <pthread.h>
#include <signal.h>
@@ -44,6 +46,8 @@
#if defined(__linux__)
# include "uv-linux.h"
+#elif defined (__MVS__)
+# include "uv-os390.h"
#elif defined(_AIX)
# include "uv-aix.h"
#elif defined(__sun)
diff --git a/deps/uv/include/uv-version.h b/deps/uv/include/uv-version.h
index 99f7eb8c1f..cf00048790 100644
--- a/deps/uv/include/uv-version.h
+++ b/deps/uv/include/uv-version.h
@@ -31,8 +31,8 @@
*/
#define UV_VERSION_MAJOR 1
-#define UV_VERSION_MINOR 10
-#define UV_VERSION_PATCH 2
+#define UV_VERSION_MINOR 11
+#define UV_VERSION_PATCH 0
#define UV_VERSION_IS_RELEASE 1
#define UV_VERSION_SUFFIX ""
diff --git a/deps/uv/include/uv-win.h b/deps/uv/include/uv-win.h
index e8b9b15e2f..9677ff164b 100644
--- a/deps/uv/include/uv-win.h
+++ b/deps/uv/include/uv-win.h
@@ -49,6 +49,7 @@ typedef struct pollfd {
#include <process.h>
#include <signal.h>
+#include <fcntl.h>
#include <sys/stat.h>
#if defined(_MSC_VER) && _MSC_VER < 1600
diff --git a/deps/uv/src/unix/aix.c b/deps/uv/src/unix/aix.c
index 652cd980f5..1d2cd4a80e 100644
--- a/deps/uv/src/unix/aix.c
+++ b/deps/uv/src/unix/aix.c
@@ -64,6 +64,11 @@
#define RDWR_BUF_SIZE 4096
#define EQ(a,b) (strcmp(a,b) == 0)
+static void* args_mem = NULL;
+static char** process_argv = NULL;
+static int process_argc = 0;
+static char* process_title_ptr = NULL;
+
int uv__platform_loop_init(uv_loop_t* loop) {
loop->fs_fd = -1;
@@ -753,6 +758,13 @@ static void uv__ahafs_event(uv_loop_t* loop, uv__io_t* event_watch, unsigned int
assert((bytes >= 0) && "uv__ahafs_event - Error reading monitor file");
+ /* In file / directory move cases, AIX Event infrastructure
+ * produces a second event with no data.
+ * Ignore it and return gracefully.
+ */
+ if(bytes == 0)
+ return;
+
/* Parse the data */
if(bytes > 0)
rc = uv__parse_data(result_data, &events, handle);
@@ -881,24 +893,94 @@ void uv__fs_event_close(uv_fs_event_t* handle) {
char** uv_setup_args(int argc, char** argv) {
- return argv;
+ char** new_argv;
+ size_t size;
+ char* s;
+ int i;
+
+ if (argc <= 0)
+ return argv;
+
+ /* Save the original pointer to argv.
+ * AIX uses argv to read the process name.
+ * (Not the memory pointed to by argv[0..n] as on Linux.)
+ */
+ process_argv = argv;
+ process_argc = argc;
+
+ /* Calculate how much memory we need for the argv strings. */
+ size = 0;
+ for (i = 0; i < argc; i++)
+ size += strlen(argv[i]) + 1;
+
+ /* Add space for the argv pointers. */
+ size += (argc + 1) * sizeof(char*);
+
+ new_argv = uv__malloc(size);
+ if (new_argv == NULL)
+ return argv;
+ args_mem = new_argv;
+
+ /* Copy over the strings and set up the pointer table. */
+ s = (char*) &new_argv[argc + 1];
+ for (i = 0; i < argc; i++) {
+ size = strlen(argv[i]) + 1;
+ memcpy(s, argv[i], size);
+ new_argv[i] = s;
+ s += size;
+ }
+ new_argv[i] = NULL;
+
+ return new_argv;
}
int uv_set_process_title(const char* title) {
+ char* new_title;
+
+ /* We cannot free this pointer when libuv shuts down,
+ * the process may still be using it.
+ */
+ new_title = uv__strdup(title);
+ if (new_title == NULL)
+ return -ENOMEM;
+
+ /* If this is the first time this is set,
+ * don't free and set argv[1] to NULL.
+ */
+ if (process_title_ptr != NULL)
+ uv__free(process_title_ptr);
+
+ process_title_ptr = new_title;
+
+ process_argv[0] = process_title_ptr;
+ if (process_argc > 1)
+ process_argv[1] = NULL;
+
return 0;
}
int uv_get_process_title(char* buffer, size_t size) {
+ size_t len;
+ len = strlen(process_argv[0]);
if (buffer == NULL || size == 0)
return -EINVAL;
+ else if (size <= len)
+ return -ENOBUFS;
+
+ memcpy(buffer, process_argv[0], len + 1);
- buffer[0] = '\0';
return 0;
}
+UV_DESTRUCTOR(static void free_args_mem(void)) {
+ uv__free(args_mem); /* Keep valgrind happy. */
+ args_mem = NULL;
+}
+
+
int uv_resident_set_memory(size_t* rss) {
char pp[64];
psinfo_t psinfo;
diff --git a/deps/uv/src/unix/atomic-ops.h b/deps/uv/src/unix/atomic-ops.h
index 815e355238..9dac2557f8 100644
--- a/deps/uv/src/unix/atomic-ops.h
+++ b/deps/uv/src/unix/atomic-ops.h
@@ -43,8 +43,12 @@ UV_UNUSED(static int cmpxchgi(int* ptr, int oldval, int newval)) {
__compare_and_swap(ptr, &oldval, newval);
return out;
#elif defined(__MVS__)
- return __plo_CS(ptr, (unsigned int*) ptr,
- oldval, (unsigned int*) &newval);
+ unsigned int op4;
+ if (__plo_CSST(ptr, (unsigned int*) &oldval, newval,
+ (unsigned int*) ptr, *ptr, &op4))
+ return oldval;
+ else
+ return op4;
#else
return __sync_val_compare_and_swap(ptr, oldval, newval);
#endif
@@ -67,13 +71,18 @@ UV_UNUSED(static long cmpxchgl(long* ptr, long oldval, long newval)) {
# endif /* if defined(__64BIT__) */
return out;
#elif defined (__MVS__)
-# ifdef _LP64
- return __plo_CSGR(ptr, (unsigned long long*) ptr,
- oldval, (unsigned long long*) &newval);
-# else
- return __plo_CS(ptr, (unsigned int*) ptr,
- oldval, (unsigned int*) &newval);
-# endif
+#ifdef _LP64
+ unsigned long long op4;
+ if (__plo_CSSTGR(ptr, (unsigned long long*) &oldval, newval,
+ (unsigned long long*) ptr, *ptr, &op4))
+#else
+ unsigned long op4;
+ if (__plo_CSST(ptr, (unsigned int*) &oldval, newval,
+ (unsigned int*) ptr, *ptr, &op4))
+#endif
+ return oldval;
+ else
+ return op4;
#else
return __sync_val_compare_and_swap(ptr, oldval, newval);
#endif
diff --git a/deps/uv/src/unix/core.c b/deps/uv/src/unix/core.c
index 6283ed3ec2..1ec549cccb 100644
--- a/deps/uv/src/unix/core.c
+++ b/deps/uv/src/unix/core.c
@@ -517,6 +517,9 @@ int uv__close_nocheckstdio(int fd) {
int uv__close(int fd) {
assert(fd > STDERR_FILENO); /* Catch stdio close bugs. */
+#if defined(__MVS__)
+ epoll_file_close(fd);
+#endif
return uv__close_nocheckstdio(fd);
}
diff --git a/deps/uv/src/unix/darwin.c b/deps/uv/src/unix/darwin.c
index b1ffbc37b4..cf95da2169 100644
--- a/deps/uv/src/unix/darwin.c
+++ b/deps/uv/src/unix/darwin.c
@@ -34,12 +34,8 @@
#include <mach-o/dyld.h> /* _NSGetExecutablePath */
#include <sys/resource.h>
#include <sys/sysctl.h>
-#include <time.h>
#include <unistd.h> /* sysconf */
-#undef NANOSEC
-#define NANOSEC ((uint64_t) 1e9)
-
int uv__platform_loop_init(uv_loop_t* loop) {
loop->cf_state = NULL;
@@ -57,11 +53,6 @@ void uv__platform_loop_delete(uv_loop_t* loop) {
uint64_t uv__hrtime(uv_clocktype_t type) {
-#ifdef MAC_OS_X_VERSION_10_12
- struct timespec ts;
- clock_gettime(CLOCK_MONOTONIC, &ts);
- return (((uint64_t) ts.tv_sec) * NANOSEC + ts.tv_nsec);
-#else
static mach_timebase_info_data_t info;
if ((ACCESS_ONCE(uint32_t, info.numer) == 0 ||
@@ -70,7 +61,6 @@ uint64_t uv__hrtime(uv_clocktype_t type) {
abort();
return mach_absolute_time() * info.numer / info.denom;
-#endif
}
diff --git a/deps/uv/src/unix/fs.c b/deps/uv/src/unix/fs.c
index e047b67165..f9513ea55a 100644
--- a/deps/uv/src/unix/fs.c
+++ b/deps/uv/src/unix/fs.c
@@ -380,7 +380,6 @@ static int uv__fs_scandir_sort(UV_CONST_DIRENT** a, UV_CONST_DIRENT** b) {
static ssize_t uv__fs_scandir(uv_fs_t* req) {
uv__dirent_t **dents;
- int saved_errno;
int n;
dents = NULL;
@@ -389,28 +388,17 @@ static ssize_t uv__fs_scandir(uv_fs_t* req) {
/* NOTE: We will use nbufs as an index field */
req->nbufs = 0;
- if (n == 0)
- goto out; /* osx still needs to deallocate some memory */
- else if (n == -1)
- return n;
-
- req->ptr = dents;
-
- return n;
-
-out:
- saved_errno = errno;
- if (dents != NULL) {
- int i;
-
- /* Memory was allocated using the system allocator, so use free() here. */
- for (i = 0; i < n; i++)
- free(dents[i]);
+ if (n == 0) {
+ /* OS X still needs to deallocate some memory.
+ * Memory was allocated using the system allocator, so use free() here.
+ */
free(dents);
+ dents = NULL;
+ } else if (n == -1) {
+ return n;
}
- errno = saved_errno;
- req->ptr = NULL;
+ req->ptr = dents;
return n;
}
diff --git a/deps/uv/src/unix/internal.h b/deps/uv/src/unix/internal.h
index ee76c837c4..1188e8fe70 100644
--- a/deps/uv/src/unix/internal.h
+++ b/deps/uv/src/unix/internal.h
@@ -38,6 +38,10 @@
# include "linux-syscalls.h"
#endif /* __linux__ */
+#if defined(__MVS__)
+# include "os390-syscalls.h"
+#endif /* __MVS__ */
+
#if defined(__sun)
# include <sys/port.h>
# include <port.h>
diff --git a/deps/uv/src/unix/os390-syscalls.c b/deps/uv/src/unix/os390-syscalls.c
new file mode 100644
index 0000000000..2bf3b73815
--- /dev/null
+++ b/deps/uv/src/unix/os390-syscalls.c
@@ -0,0 +1,334 @@
+/* Copyright libuv project 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 "os390-syscalls.h"
+#include <errno.h>
+#include <stdlib.h>
+#include <assert.h>
+#include <search.h>
+
+#define CW_CONDVAR 32
+
+#pragma linkage(BPX4CTW, OS)
+#pragma linkage(BPX1CTW, OS)
+
+static int number_of_epolls;
+static QUEUE global_epoll_queue;
+static uv_mutex_t global_epoll_lock;
+static uv_once_t once = UV_ONCE_INIT;
+
+int scandir(const char* maindir, struct dirent*** namelist,
+ int (*filter)(const struct dirent*),
+ int (*compar)(const struct dirent**,
+ const struct dirent **)) {
+ struct dirent** nl;
+ struct dirent* dirent;
+ unsigned count;
+ size_t allocated;
+ DIR* mdir;
+
+ nl = NULL;
+ count = 0;
+ allocated = 0;
+ mdir = opendir(maindir);
+ if (!mdir)
+ return -1;
+
+ while (1) {
+ dirent = readdir(mdir);
+ if (!dirent)
+ break;
+ if (!filter || filter(dirent)) {
+ struct dirent* copy;
+ copy = uv__malloc(sizeof(*copy));
+ if (!copy) {
+ while (count) {
+ dirent = nl[--count];
+ uv__free(dirent);
+ }
+ uv__free(nl);
+ closedir(mdir);
+ errno = ENOMEM;
+ return -1;
+ }
+ memcpy(copy, dirent, sizeof(*copy));
+
+ nl = uv__realloc(nl, sizeof(*copy) * (count + 1));
+ nl[count++] = copy;
+ }
+ }
+
+ qsort(nl, count, sizeof(struct dirent *),
+ (int (*)(const void *, const void *)) compar);
+
+ closedir(mdir);
+
+ *namelist = nl;
+ return count;
+}
+
+
+static unsigned int next_power_of_two(unsigned int val) {
+ val -= 1;
+ val |= val >> 1;
+ val |= val >> 2;
+ val |= val >> 4;
+ val |= val >> 8;
+ val |= val >> 16;
+ val += 1;
+ return val;
+}
+
+
+static void maybe_resize(uv__os390_epoll* lst, unsigned int len) {
+ unsigned int newsize;
+ unsigned int i;
+ struct pollfd* newlst;
+
+ if (len <= lst->size)
+ return;
+
+ newsize = next_power_of_two(len);
+ newlst = uv__realloc(lst->items, newsize * sizeof(lst->items[0]));
+
+ if (newlst == NULL)
+ abort();
+ for (i = lst->size; i < newsize; ++i)
+ newlst[i].fd = -1;
+
+ lst->items = newlst;
+ lst->size = newsize;
+}
+
+
+static void epoll_init() {
+ QUEUE_INIT(&global_epoll_queue);
+ if (uv_mutex_init(&global_epoll_lock))
+ abort();
+}
+
+
+uv__os390_epoll* epoll_create1(int flags) {
+ uv__os390_epoll* lst;
+
+ uv_once(&once, epoll_init);
+ uv_mutex_lock(&global_epoll_lock);
+ lst = uv__malloc(sizeof(*lst));
+ if (lst == -1)
+ return NULL;
+ QUEUE_INSERT_TAIL(&global_epoll_queue, &lst->member);
+ uv_mutex_unlock(&global_epoll_lock);
+
+ /* initialize list */
+ lst->size = 0;
+ lst->items = NULL;
+ return lst;
+}
+
+
+int epoll_ctl(uv__os390_epoll* lst,
+ int op,
+ int fd,
+ struct epoll_event *event) {
+ if(op == EPOLL_CTL_DEL) {
+ if (fd >= lst->size || lst->items[fd].fd == -1) {
+ errno = ENOENT;
+ return -1;
+ }
+ lst->items[fd].fd = -1;
+ } else if(op == EPOLL_CTL_ADD) {
+ maybe_resize(lst, fd + 1);
+ if (lst->items[fd].fd != -1) {
+ errno = EEXIST;
+ return -1;
+ }
+ lst->items[fd].fd = fd;
+ lst->items[fd].events = event->events;
+ } else if(op == EPOLL_CTL_MOD) {
+ if (fd >= lst->size || lst->items[fd].fd == -1) {
+ errno = ENOENT;
+ return -1;
+ }
+ lst->items[fd].events = event->events;
+ } else
+ abort();
+
+ return 0;
+}
+
+
+int epoll_wait(uv__os390_epoll* lst, struct epoll_event* events,
+ int maxevents, int timeout) {
+ size_t size;
+ struct pollfd* pfds;
+ int pollret;
+ int reventcount;
+
+ uv_mutex_lock(&global_epoll_lock);
+ uv_mutex_unlock(&global_epoll_lock);
+ size = lst->size;
+ pfds = lst->items;
+ pollret = poll(pfds, size, timeout);
+ if(pollret == -1)
+ return pollret;
+
+ reventcount = 0;
+ for (int i = 0; i < lst->size && i < maxevents; ++i) {
+ struct epoll_event ev;
+
+ ev.events = 0;
+ ev.fd = pfds[i].fd;
+ if(!pfds[i].revents)
+ continue;
+
+ if(pfds[i].revents & POLLRDNORM)
+ ev.events = ev.events | POLLIN;
+
+ if(pfds[i].revents & POLLWRNORM)
+ ev.events = ev.events | POLLOUT;
+
+ if(pfds[i].revents & POLLHUP)
+ ev.events = ev.events | POLLHUP;
+
+ pfds[i].revents = 0;
+ events[reventcount++] = ev;
+ }
+
+ return reventcount;
+}
+
+
+int epoll_file_close(int fd) {
+ QUEUE* q;
+
+ uv_once(&once, epoll_init);
+ uv_mutex_lock(&global_epoll_lock);
+ QUEUE_FOREACH(q, &global_epoll_queue) {
+ uv__os390_epoll* lst;
+
+ lst = QUEUE_DATA(q, uv__os390_epoll, member);
+ if (fd < lst->size && lst->items != NULL && lst->items[fd].fd != -1)
+ lst->items[fd].fd = -1;
+ }
+
+ uv_mutex_unlock(&global_epoll_lock);
+ return 0;
+}
+
+void epoll_queue_close(uv__os390_epoll* lst) {
+ uv_mutex_lock(&global_epoll_lock);
+ QUEUE_REMOVE(&lst->member);
+ uv_mutex_unlock(&global_epoll_lock);
+ uv__free(lst->items);
+ lst->items = NULL;
+}
+
+
+int nanosleep(const struct timespec* req, struct timespec* rem) {
+ unsigned nano;
+ unsigned seconds;
+ unsigned events;
+ unsigned secrem;
+ unsigned nanorem;
+ int rv;
+ int rc;
+ int rsn;
+
+ nano = (int)req->tv_nsec;
+ seconds = req->tv_sec;
+ events = CW_CONDVAR;
+
+#if defined(_LP64)
+ BPX4CTW(&seconds, &nano, &events, &secrem, &nanorem, &rv, &rc, &rsn);
+#else
+ BPX1CTW(&seconds, &nano, &events, &secrem, &nanorem, &rv, &rc, &rsn);
+#endif
+
+ assert(rv == -1 && errno == EAGAIN);
+
+ if(rem != NULL) {
+ rem->tv_nsec = nanorem;
+ rem->tv_sec = secrem;
+ }
+
+ return 0;
+}
+
+
+char* mkdtemp(char* path) {
+ static const char* tempchars =
+ "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789";
+ static const size_t num_chars = 62;
+ static const size_t num_x = 6;
+ char *ep, *cp;
+ unsigned int tries, i;
+ size_t len;
+ uint64_t v;
+ int fd;
+ int retval;
+ int saved_errno;
+
+ len = strlen(path);
+ ep = path + len;
+ if (len < num_x || strncmp(ep - num_x, "XXXXXX", num_x)) {
+ errno = EINVAL;
+ return NULL;
+ }
+
+ fd = open("/dev/urandom", O_RDONLY);
+ if (fd == -1)
+ return NULL;
+
+ tries = TMP_MAX;
+ retval = -1;
+ do {
+ if (read(fd, &v, sizeof(v)) != sizeof(v))
+ break;
+
+ cp = ep - num_x;
+ for (i = 0; i < num_x; i++) {
+ *cp++ = tempchars[v % num_chars];
+ v /= num_chars;
+ }
+
+ if (mkdir(path, S_IRWXU) == 0) {
+ retval = 0;
+ break;
+ }
+ else if (errno != EEXIST)
+ break;
+ } while (--tries);
+
+ saved_errno = errno;
+ uv__close(fd);
+ if (tries == 0) {
+ errno = EEXIST;
+ return NULL;
+ }
+
+ if (retval == -1) {
+ errno = saved_errno;
+ return NULL;
+ }
+
+ return path;
+}
diff --git a/deps/uv/src/unix/os390-syscalls.h b/deps/uv/src/unix/os390-syscalls.h
new file mode 100644
index 0000000000..61a7cee839
--- /dev/null
+++ b/deps/uv/src/unix/os390-syscalls.h
@@ -0,0 +1,69 @@
+/* Copyright libuv project 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_OS390_SYSCALL_H_
+#define UV_OS390_SYSCALL_H_
+
+#include "uv.h"
+#include "internal.h"
+#include <dirent.h>
+#include <poll.h>
+#include <pthread.h>
+
+#define EPOLL_CTL_ADD 1
+#define EPOLL_CTL_DEL 2
+#define EPOLL_CTL_MOD 3
+#define MAX_EPOLL_INSTANCES 256
+#define MAX_ITEMS_PER_EPOLL 1024
+
+#define UV__O_CLOEXEC 0x80000
+#define UV__EPOLL_CLOEXEC UV__O_CLOEXEC
+#define UV__EPOLL_CTL_ADD EPOLL_CTL_ADD
+#define UV__EPOLL_CTL_DEL EPOLL_CTL_DEL
+#define UV__EPOLL_CTL_MOD EPOLL_CTL_MOD
+
+struct epoll_event {
+ int events;
+ int fd;
+};
+
+typedef struct {
+ QUEUE member;
+ struct pollfd* items;
+ unsigned long size;
+} uv__os390_epoll;
+
+/* epoll api */
+uv__os390_epoll* epoll_create1(int flags);
+int epoll_ctl(uv__os390_epoll* ep, int op, int fd, struct epoll_event *event);
+int epoll_wait(uv__os390_epoll* ep, struct epoll_event *events, int maxevents, int timeout);
+int epoll_file_close(int fd);
+
+/* utility functions */
+int nanosleep(const struct timespec* req, struct timespec* rem);
+int scandir(const char* maindir, struct dirent*** namelist,
+ int (*filter)(const struct dirent *),
+ int (*compar)(const struct dirent **,
+ const struct dirent **));
+char *mkdtemp(char* path);
+
+#endif /* UV_OS390_SYSCALL_H_ */
diff --git a/deps/uv/src/unix/os390.c b/deps/uv/src/unix/os390.c
index bcdbc4b6a8..be325a9230 100644
--- a/deps/uv/src/unix/os390.c
+++ b/deps/uv/src/unix/os390.c
@@ -20,6 +20,628 @@
*/
#include "internal.h"
+#include <sys/ioctl.h>
+#include <net/if.h>
+#include <utmpx.h>
+#include <unistd.h>
+#include <sys/ps.h>
+#if defined(__clang__)
+#include "csrsic.h"
+#else
+#include "//'SYS1.SAMPLIB(CSRSIC)'"
+#endif
+
+#define CVT_PTR 0x10
+#define CSD_OFFSET 0x294
+
+/*
+ Long-term average CPU service used by this logical partition,
+ in millions of service units per hour. If this value is above
+ the partition's defined capacity, the partition will be capped.
+ It is calculated using the physical CPU adjustment factor
+ (RCTPCPUA) so it may not match other measures of service which
+ are based on the logical CPU adjustment factor. It is available
+ if the hardware supports LPAR cluster.
+*/
+#define RCTLACS_OFFSET 0xC4
+
+/* 32-bit count of alive CPUs. This includes both CPs and IFAs */
+#define CSD_NUMBER_ONLINE_CPUS 0xD4
+
+/* Address of system resources manager (SRM) control table */
+#define CVTOPCTP_OFFSET 0x25C
+
+/* Address of the RCT table */
+#define RMCTRCT_OFFSET 0xE4
+
+/* Address of the rsm control and enumeration area. */
+#define CVTRCEP_OFFSET 0x490
+
+/*
+ Number of frames currently available to system.
+ Excluded are frames backing perm storage, frames offline, and bad frames.
+*/
+#define RCEPOOL_OFFSET 0x004
+
+/* Total number of frames currently on all available frame queues. */
+#define RCEAFC_OFFSET 0x088
+
+/* CPC model length from the CSRSI Service. */
+#define CPCMODEL_LENGTH 16
+
+/* Thread Entry constants */
+#define PGTH_CURRENT 1
+#define PGTH_LEN 26
+#define PGTHAPATH 0x20
+#pragma linkage(BPX4GTH, OS)
+#pragma linkage(BPX1GTH, OS)
+
+typedef unsigned data_area_ptr_assign_type;
+
+typedef union {
+ struct {
+#if defined(_LP64)
+ data_area_ptr_assign_type lower;
+#endif
+ data_area_ptr_assign_type assign;
+ };
+ char* deref;
+} data_area_ptr;
+
+
+void uv_loadavg(double avg[3]) {
+ /* TODO: implement the following */
+ avg[0] = 0;
+ avg[1] = 0;
+ avg[2] = 0;
+}
+
+
+int uv__platform_loop_init(uv_loop_t* loop) {
+ uv__os390_epoll* ep;
+
+ ep = epoll_create1(UV__EPOLL_CLOEXEC);
+ loop->ep = ep;
+ if (ep == NULL)
+ return -errno;
+
+ return 0;
+}
+
+
+void uv__platform_loop_delete(uv_loop_t* loop) {
+ if (loop->ep != NULL) {
+ epoll_queue_close(loop->ep);
+ loop->ep = NULL;
+ }
+}
+
+
+uint64_t uv__hrtime(uv_clocktype_t type) {
+ struct timeval time;
+ gettimeofday(&time, NULL);
+ return (uint64_t) time.tv_sec * 1e9 + time.tv_usec * 1e3;
+}
+
+
+/*
+ Get the exe path using the thread entry information
+ in the address space.
+*/
+static int getexe(const int pid, char* buf, size_t len) {
+ struct {
+ int pid;
+ int thid[2];
+ char accesspid;
+ char accessthid;
+ char asid[2];
+ char loginname[8];
+ char flag;
+ char len;
+ } Input_data;
+
+ union {
+ struct {
+ char gthb[4];
+ int pid;
+ int thid[2];
+ char accesspid;
+ char accessthid[3];
+ int lenused;
+ int offsetProcess;
+ int offsetConTTY;
+ int offsetPath;
+ int offsetCommand;
+ int offsetFileData;
+ int offsetThread;
+ } Output_data;
+ char buf[2048];
+ } Output_buf;
+
+ struct Output_path_type {
+ char gthe[4];
+ short int len;
+ char path[1024];
+ };
+
+ int Input_length;
+ int Output_length;
+ void* Input_address;
+ void* Output_address;
+ struct Output_path_type* Output_path;
+ int rv;
+ int rc;
+ int rsn;
+
+ Input_length = PGTH_LEN;
+ Output_length = sizeof(Output_buf);
+ Output_address = &Output_buf;
+ Input_address = &Input_data;
+ memset(&Input_data, 0, sizeof Input_data);
+ Input_data.flag |= PGTHAPATH;
+ Input_data.pid = pid;
+ Input_data.accesspid = PGTH_CURRENT;
+
+#ifdef _LP64
+ BPX4GTH(&Input_length,
+ &Input_address,
+ &Output_length,
+ &Output_address,
+ &rv,
+ &rc,
+ &rsn);
+#else
+ BPX1GTH(&Input_length,
+ &Input_address,
+ &Output_length,
+ &Output_address,
+ &rv,
+ &rc,
+ &rsn);
+#endif
+
+ if (rv == -1) {
+ errno = rc;
+ return -1;
+ }
+
+ /* Check highest byte to ensure data availability */
+ assert(((Output_buf.Output_data.offsetPath >>24) & 0xFF) == 'A');
+
+ /* Get the offset from the lowest 3 bytes */
+ Output_path = (char*)(&Output_buf) +
+ (Output_buf.Output_data.offsetPath & 0x00FFFFFF);
+
+ if (Output_path->len >= len) {
+ errno = ENOBUFS;
+ return -1;
+ }
+
+ strncpy(buf, Output_path->path, len);
+
+ return 0;
+}
+
+
+/*
+ * We could use a static buffer for the path manipulations that we need outside
+ * of the function, but this function could be called by multiple consumers and
+ * we don't want to potentially create a race condition in the use of snprintf.
+ * There is no direct way of getting the exe path in zOS - either through /procfs
+ * or through some libc APIs. The below approach is to parse the argv[0]'s pattern
+ * and use it in conjunction with PATH environment variable to craft one.
+ */
+int uv_exepath(char* buffer, size_t* size) {
+ int res;
+ char args[PATH_MAX];
+ char abspath[PATH_MAX];
+ size_t abspath_size;
+ int pid;
+
+ if (buffer == NULL || size == NULL || *size == 0)
+ return -EINVAL;
+
+ pid = getpid();
+ res = getexe(pid, args, sizeof(args));
+ if (res < 0)
+ return -EINVAL;
+
+ /*
+ * Possibilities for args:
+ * i) an absolute path such as: /home/user/myprojects/nodejs/node
+ * ii) a relative path such as: ./node or ../myprojects/nodejs/node
+ * iii) a bare filename such as "node", after exporting PATH variable
+ * to its location.
+ */
+
+ /* Case i) and ii) absolute or relative paths */
+ if (strchr(args, '/') != NULL) {
+ if (realpath(args, abspath) != abspath)
+ return -errno;
+
+ abspath_size = strlen(abspath);
+
+ *size -= 1;
+ if (*size > abspath_size)
+ *size = abspath_size;
+
+ memcpy(buffer, abspath, *size);
+ buffer[*size] = '\0';
+
+ return 0;
+ } else {
+ /* Case iii). Search PATH environment variable */
+ char trypath[PATH_MAX];
+ char* clonedpath = NULL;
+ char* token = NULL;
+ char* path = getenv("PATH");
+
+ if (path == NULL)
+ return -EINVAL;
+
+ clonedpath = uv__strdup(path);
+ if (clonedpath == NULL)
+ return -ENOMEM;
+
+ token = strtok(clonedpath, ":");
+ while (token != NULL) {
+ snprintf(trypath, sizeof(trypath) - 1, "%s/%s", token, args);
+ if (realpath(trypath, abspath) == abspath) {
+ /* Check the match is executable */
+ if (access(abspath, X_OK) == 0) {
+ abspath_size = strlen(abspath);
+
+ *size -= 1;
+ if (*size > abspath_size)
+ *size = abspath_size;
+
+ memcpy(buffer, abspath, *size);
+ buffer[*size] = '\0';
+
+ uv__free(clonedpath);
+ return 0;
+ }
+ }
+ token = strtok(NULL, ":");
+ }
+ uv__free(clonedpath);
+
+ /* Out of tokens (path entries), and no match found */
+ return -EINVAL;
+ }
+}
+
+
+uint64_t uv_get_free_memory(void) {
+ uint64_t freeram;
+
+ data_area_ptr cvt = {0};
+ data_area_ptr rcep = {0};
+ cvt.assign = *(data_area_ptr_assign_type*)(CVT_PTR);
+ rcep.assign = *(data_area_ptr_assign_type*)(cvt.deref + CVTRCEP_OFFSET);
+ freeram = *((uint64_t*)(rcep.deref + RCEAFC_OFFSET)) * 4;
+ return freeram;
+}
+
+
+uint64_t uv_get_total_memory(void) {
+ uint64_t totalram;
+
+ data_area_ptr cvt = {0};
+ data_area_ptr rcep = {0};
+ cvt.assign = *(data_area_ptr_assign_type*)(CVT_PTR);
+ rcep.assign = *(data_area_ptr_assign_type*)(cvt.deref + CVTRCEP_OFFSET);
+ totalram = *((uint64_t*)(rcep.deref + RCEPOOL_OFFSET)) * 4;
+ return totalram;
+}
+
+
+int uv_resident_set_memory(size_t* rss) {
+ W_PSPROC buf;
+
+ memset(&buf, 0, sizeof(buf));
+ if (w_getpsent(0, &buf, sizeof(W_PSPROC)) == -1)
+ return -EINVAL;
+
+ *rss = buf.ps_size;
+ return 0;
+}
+
+
+int uv_uptime(double* uptime) {
+ struct utmpx u ;
+ struct utmpx *v;
+ time64_t t;
+
+ u.ut_type = BOOT_TIME;
+ v = getutxid(&u);
+ if (v == NULL)
+ return -1;
+ *uptime = difftime64(time64(&t), v->ut_tv.tv_sec);
+ return 0;
+}
+
+
+int uv_cpu_info(uv_cpu_info_t** cpu_infos, int* count) {
+ uv_cpu_info_t* cpu_info;
+ int result;
+ int idx;
+ siv1v2 info;
+ data_area_ptr cvt = {0};
+ data_area_ptr csd = {0};
+ data_area_ptr rmctrct = {0};
+ data_area_ptr cvtopctp = {0};
+ int cpu_usage_avg;
+
+ cvt.assign = *(data_area_ptr_assign_type*)(CVT_PTR);
+
+ csd.assign = *((data_area_ptr_assign_type *) (cvt.deref + CSD_OFFSET));
+ cvtopctp.assign = *((data_area_ptr_assign_type *) (cvt.deref + CVTOPCTP_OFFSET));
+ rmctrct.assign = *((data_area_ptr_assign_type *) (cvtopctp.deref + RMCTRCT_OFFSET));
+
+ *count = *((int*) (csd.deref + CSD_NUMBER_ONLINE_CPUS));
+ cpu_usage_avg = *((unsigned short int*) (rmctrct.deref + RCTLACS_OFFSET));
+
+ *cpu_infos = uv__malloc(*count * sizeof(uv_cpu_info_t));
+ if (!*cpu_infos)
+ return -ENOMEM;
+
+ cpu_info = *cpu_infos;
+ idx = 0;
+ while (idx < *count) {
+ cpu_info->speed = *(int*)(info.siv1v2si22v1.si22v1cpucapability);
+ cpu_info->model = uv__malloc(CPCMODEL_LENGTH + 1);
+ memset(cpu_info->model, '\0', CPCMODEL_LENGTH + 1);
+ memcpy(cpu_info->model, info.siv1v2si11v1.si11v1cpcmodel, CPCMODEL_LENGTH);
+ cpu_info->cpu_times.user = cpu_usage_avg;
+ /* TODO: implement the following */
+ cpu_info->cpu_times.sys = 0;
+ cpu_info->cpu_times.idle = 0;
+ cpu_info->cpu_times.irq = 0;
+ cpu_info->cpu_times.nice = 0;
+ ++cpu_info;
+ ++idx;
+ }
+
+ return 0;
+}
+
+
+void uv_free_cpu_info(uv_cpu_info_t* cpu_infos, int count) {
+ for (int i = 0; i < count; ++i)
+ uv__free(cpu_infos[i].model);
+ uv__free(cpu_infos);
+}
+
+
+static int uv__interface_addresses_v6(uv_interface_address_t** addresses,
+ int* count) {
+ uv_interface_address_t* address;
+ int sockfd;
+ int maxsize;
+ __net_ifconf6header_t ifc;
+ __net_ifconf6entry_t* ifr;
+ __net_ifconf6entry_t* p;
+ __net_ifconf6entry_t flg;
+
+ *count = 0;
+ /* Assume maximum buffer size allowable */
+ maxsize = 16384;
+
+ if (0 > (sockfd = socket(AF_INET, SOCK_DGRAM, IPPROTO_IP)))
+ return -errno;
+
+ ifc.__nif6h_version = 1;
+ ifc.__nif6h_buflen = maxsize;
+ ifc.__nif6h_buffer = uv__calloc(1, maxsize);;
+
+ if (ioctl(sockfd, SIOCGIFCONF6, &ifc) == -1) {
+ uv__close(sockfd);
+ return -errno;
+ }
+
+
+ *count = 0;
+ ifr = (__net_ifconf6entry_t*)(ifc.__nif6h_buffer);
+ while ((char*)ifr < (char*)ifc.__nif6h_buffer + ifc.__nif6h_buflen) {
+ p = ifr;
+ ifr = (__net_ifconf6entry_t*)((char*)ifr + ifc.__nif6h_entrylen);
+
+ if (!(p->__nif6e_addr.sin6_family == AF_INET6 ||
+ p->__nif6e_addr.sin6_family == AF_INET))
+ continue;
+
+ if (!(p->__nif6e_flags & _NIF6E_FLAGS_ON_LINK_ACTIVE))
+ continue;
+
+ ++(*count);
+ }
+
+ /* Alloc the return interface structs */
+ *addresses = uv__malloc(*count * sizeof(uv_interface_address_t));
+ if (!(*addresses)) {
+ uv__close(sockfd);
+ return -ENOMEM;
+ }
+ address = *addresses;
+
+ ifr = (__net_ifconf6entry_t*)(ifc.__nif6h_buffer);
+ while ((char*)ifr < (char*)ifc.__nif6h_buffer + ifc.__nif6h_buflen) {
+ p = ifr;
+ ifr = (__net_ifconf6entry_t*)((char*)ifr + ifc.__nif6h_entrylen);
+
+ if (!(p->__nif6e_addr.sin6_family == AF_INET6 ||
+ p->__nif6e_addr.sin6_family == AF_INET))
+ continue;
+
+ if (!(p->__nif6e_flags & _NIF6E_FLAGS_ON_LINK_ACTIVE))
+ continue;
+
+ /* All conditions above must match count loop */
+
+ address->name = uv__strdup(p->__nif6e_name);
+
+ if (p->__nif6e_addr.sin6_family == AF_INET6)
+ address->address.address6 = *((struct sockaddr_in6*) &p->__nif6e_addr);
+ else
+ address->address.address4 = *((struct sockaddr_in*) &p->__nif6e_addr);
+
+ /* TODO: Retrieve netmask using SIOCGIFNETMASK ioctl */
+
+ address->is_internal = flg.__nif6e_flags & _NIF6E_FLAGS_LOOPBACK ? 1 : 0;
+
+ address++;
+ }
+
+ uv__close(sockfd);
+ return 0;
+}
+
+
+int uv_interface_addresses(uv_interface_address_t** addresses, int* count) {
+ uv_interface_address_t* address;
+ int sockfd;
+ int maxsize;
+ struct ifconf ifc;
+ struct ifreq flg;
+ struct ifreq* ifr;
+ struct ifreq* p;
+ int count_v6;
+
+ /* get the ipv6 addresses first */
+ uv_interface_address_t* addresses_v6;
+ uv__interface_addresses_v6(&addresses_v6, &count_v6);
+
+ /* now get the ipv4 addresses */
+ *count = 0;
+
+ /* Assume maximum buffer size allowable */
+ maxsize = 16384;
+
+ sockfd = socket(AF_INET, SOCK_DGRAM, IPPROTO_IP);
+ if (0 > sockfd)
+ return -errno;
+
+ ifc.ifc_req = uv__calloc(1, maxsize);
+ ifc.ifc_len = maxsize;
+ if (ioctl(sockfd, SIOCGIFCONF, &ifc) == -1) {
+ uv__close(sockfd);
+ return -errno;
+ }
+
+#define MAX(a,b) (((a)>(b))?(a):(b))
+#define ADDR_SIZE(p) MAX((p).sa_len, sizeof(p))
+
+ /* Count all up and running ipv4/ipv6 addresses */
+ ifr = ifc.ifc_req;
+ while ((char*)ifr < (char*)ifc.ifc_req + ifc.ifc_len) {
+ p = ifr;
+ ifr = (struct ifreq*)
+ ((char*)ifr + sizeof(ifr->ifr_name) + ADDR_SIZE(ifr->ifr_addr));
+
+ if (!(p->ifr_addr.sa_family == AF_INET6 ||
+ p->ifr_addr.sa_family == AF_INET))
+ continue;
+
+ memcpy(flg.ifr_name, p->ifr_name, sizeof(flg.ifr_name));
+ if (ioctl(sockfd, SIOCGIFFLAGS, &flg) == -1) {
+ uv__close(sockfd);
+ return -errno;
+ }
+
+ if (!(flg.ifr_flags & IFF_UP && flg.ifr_flags & IFF_RUNNING))
+ continue;
+
+ (*count)++;
+ }
+
+ /* Alloc the return interface structs */
+ *addresses = uv__malloc((*count + count_v6) *
+ sizeof(uv_interface_address_t));
+
+ if (!(*addresses)) {
+ uv__close(sockfd);
+ return -ENOMEM;
+ }
+ address = *addresses;
+
+ /* copy over the ipv6 addresses */
+ memcpy(address, addresses_v6, count_v6 * sizeof(uv_interface_address_t));
+ address += count_v6;
+ *count += count_v6;
+ uv__free(addresses_v6);
+
+ ifr = ifc.ifc_req;
+ while ((char*)ifr < (char*)ifc.ifc_req + ifc.ifc_len) {
+ p = ifr;
+ ifr = (struct ifreq*)
+ ((char*)ifr + sizeof(ifr->ifr_name) + ADDR_SIZE(ifr->ifr_addr));
+
+ if (!(p->ifr_addr.sa_family == AF_INET6 ||
+ p->ifr_addr.sa_family == AF_INET))
+ continue;
+
+ memcpy(flg.ifr_name, p->ifr_name, sizeof(flg.ifr_name));
+ if (ioctl(sockfd, SIOCGIFFLAGS, &flg) == -1) {
+ uv__close(sockfd);
+ return -ENOSYS;
+ }
+
+ if (!(flg.ifr_flags & IFF_UP && flg.ifr_flags & IFF_RUNNING))
+ continue;
+
+ /* All conditions above must match count loop */
+
+ address->name = uv__strdup(p->ifr_name);
+
+ if (p->ifr_addr.sa_family == AF_INET6) {
+ address->address.address6 = *((struct sockaddr_in6*) &p->ifr_addr);
+ } else {
+ address->address.address4 = *((struct sockaddr_in*) &p->ifr_addr);
+ }
+
+ address->is_internal = flg.ifr_flags & IFF_LOOPBACK ? 1 : 0;
+ address++;
+ }
+
+#undef ADDR_SIZE
+#undef MAX
+
+ uv__close(sockfd);
+ 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);
+}
+
+
+void uv__platform_invalidate_fd(uv_loop_t* loop, int fd) {
+ struct epoll_event* events;
+ struct epoll_event dummy;
+ uintptr_t i;
+ uintptr_t nfds;
+
+ assert(loop->watchers != NULL);
+
+ events = (struct epoll_event*) loop->watchers[loop->nwatchers];
+ nfds = (uintptr_t) loop->watchers[loop->nwatchers + 1];
+ if (events != NULL)
+ /* Invalidate events with same file descriptor */
+ for (i = 0; i < nfds; i++)
+ if ((int) events[i].fd == fd)
+ events[i].fd = -1;
+
+ /* Remove the file descriptor from the epoll. */
+ if (loop->ep != NULL)
+ epoll_ctl(loop->ep, UV__EPOLL_CTL_DEL, fd, &dummy);
+}
+
int uv__io_check_fd(uv_loop_t* loop, int fd) {
struct pollfd p[1];
@@ -40,3 +662,204 @@ int uv__io_check_fd(uv_loop_t* loop, int fd) {
return 0;
}
+
+
+void uv__fs_event_close(uv_fs_event_t* handle) {
+ UNREACHABLE();
+}
+
+
+int uv_fs_event_init(uv_loop_t* loop, uv_fs_event_t* handle) {
+ return -ENOSYS;
+}
+
+
+int uv_fs_event_start(uv_fs_event_t* handle, uv_fs_event_cb cb,
+ const char* filename, unsigned int flags) {
+ return -ENOSYS;
+}
+
+
+int uv_fs_event_stop(uv_fs_event_t* handle) {
+ return -ENOSYS;
+}
+
+
+void uv__io_poll(uv_loop_t* loop, int timeout) {
+ static const int max_safe_timeout = 1789569;
+ struct epoll_event events[1024];
+ struct epoll_event* pe;
+ struct epoll_event e;
+ int real_timeout;
+ QUEUE* q;
+ uv__io_t* w;
+ uint64_t base;
+ int count;
+ int nfds;
+ int fd;
+ int op;
+ int i;
+
+ if (loop->nfds == 0) {
+ assert(QUEUE_EMPTY(&loop->watcher_queue));
+ return;
+ }
+
+ while (!QUEUE_EMPTY(&loop->watcher_queue)) {
+ uv_stream_t* stream;
+
+ q = QUEUE_HEAD(&loop->watcher_queue);
+ QUEUE_REMOVE(q);
+ QUEUE_INIT(q);
+ w = QUEUE_DATA(q, uv__io_t, watcher_queue);
+
+ assert(w->pevents != 0);
+ assert(w->fd >= 0);
+
+ stream= container_of(w, uv_stream_t, io_watcher);
+
+ assert(w->fd < (int) loop->nwatchers);
+
+ e.events = w->pevents;
+ e.fd = w->fd;
+
+ if (w->events == 0)
+ op = UV__EPOLL_CTL_ADD;
+ else
+ op = UV__EPOLL_CTL_MOD;
+
+ /* XXX Future optimization: do EPOLL_CTL_MOD lazily if we stop watching
+ * events, skip the syscall and squelch the events after epoll_wait().
+ */
+ if (epoll_ctl(loop->ep, op, w->fd, &e)) {
+ if (errno != EEXIST)
+ abort();
+
+ assert(op == UV__EPOLL_CTL_ADD);
+
+ /* We've reactivated a file descriptor that's been watched before. */
+ if (epoll_ctl(loop->ep, UV__EPOLL_CTL_MOD, w->fd, &e))
+ abort();
+ }
+
+ w->events = w->pevents;
+ }
+
+ assert(timeout >= -1);
+ base = loop->time;
+ count = 48; /* Benchmarks suggest this gives the best throughput. */
+ real_timeout = timeout;
+ int nevents = 0;
+
+ nfds = 0;
+ for (;;) {
+ if (sizeof(int32_t) == sizeof(long) && timeout >= max_safe_timeout)
+ timeout = max_safe_timeout;
+
+ nfds = epoll_wait(loop->ep, events,
+ ARRAY_SIZE(events), timeout);
+
+ /* Update loop->time unconditionally. It's tempting to skip the update when
+ * timeout == 0 (i.e. non-blocking poll) but there is no guarantee that the
+ * operating system didn't reschedule our process while in the syscall.
+ */
+ base = loop->time;
+ SAVE_ERRNO(uv__update_time(loop));
+ if (nfds == 0) {
+ assert(timeout != -1);
+ timeout = real_timeout - timeout;
+ if (timeout > 0)
+ continue;
+
+ return;
+ }
+
+ if (nfds == -1) {
+
+ if (errno != EINTR)
+ abort();
+
+ if (timeout == -1)
+ continue;
+
+ if (timeout == 0)
+ return;
+
+ /* Interrupted by a signal. Update timeout and poll again. */
+ goto update_timeout;
+ }
+
+
+ assert(loop->watchers != NULL);
+ loop->watchers[loop->nwatchers] = (void*) events;
+ loop->watchers[loop->nwatchers + 1] = (void*) (uintptr_t) nfds;
+ for (i = 0; i < nfds; i++) {
+ pe = events + i;
+ fd = pe->fd;
+
+ /* Skip invalidated events, see uv__platform_invalidate_fd */
+ if (fd == -1)
+ continue;
+
+ assert(fd >= 0);
+ assert((unsigned) fd < loop->nwatchers);
+
+ w = loop->watchers[fd];
+
+ if (w == NULL) {
+ /* File descriptor that we've stopped watching, disarm it.
+ *
+ * Ignore all errors because we may be racing with another thread
+ * when the file descriptor is closed.
+ */
+ epoll_ctl(loop->ep, UV__EPOLL_CTL_DEL, fd, pe);
+ continue;
+ }
+
+ /* Give users only events they're interested in. Prevents spurious
+ * callbacks when previous callback invocation in this loop has stopped
+ * the current watcher. Also, filters out events that users has not
+ * requested us to watch.
+ */
+ pe->events &= w->pevents | POLLERR | POLLHUP;
+
+ if (pe->events == POLLERR || pe->events == POLLHUP)
+ pe->events |= w->pevents & (POLLIN | POLLOUT);
+
+ if (pe->events != 0) {
+ w->cb(loop, w, pe->events);
+ nevents++;
+ }
+ }
+ loop->watchers[loop->nwatchers] = NULL;
+ loop->watchers[loop->nwatchers + 1] = NULL;
+
+ if (nevents != 0) {
+ if (nfds == ARRAY_SIZE(events) && --count != 0) {
+ /* Poll for more events but don't block this time. */
+ timeout = 0;
+ continue;
+ }
+ return;
+ }
+
+ if (timeout == 0)
+ return;
+
+ if (timeout == -1)
+ continue;
+
+update_timeout:
+ assert(timeout > 0);
+
+ real_timeout -= (loop->time - base);
+ if (real_timeout <= 0)
+ return;
+
+ timeout = real_timeout;
+ }
+}
+
+void uv__set_process_title(const char* title) {
+ /* do nothing */
+}
diff --git a/deps/uv/src/unix/process.c b/deps/uv/src/unix/process.c
index 45f5b4526b..f2fe30521c 100644
--- a/deps/uv/src/unix/process.c
+++ b/deps/uv/src/unix/process.c
@@ -323,7 +323,7 @@ static void uv__process_child_init(const uv_process_options_t* options,
}
if (fd == use_fd)
- uv__cloexec(use_fd, 0);
+ uv__cloexec_fcntl(use_fd, 0);
else
fd = dup2(use_fd, fd);
@@ -333,7 +333,7 @@ static void uv__process_child_init(const uv_process_options_t* options,
}
if (fd <= 2)
- uv__nonblock(fd, 0);
+ uv__nonblock_fcntl(fd, 0);
if (close_fd >= stdio_count)
uv__close(close_fd);
diff --git a/deps/uv/src/unix/proctitle.c b/deps/uv/src/unix/proctitle.c
index 08d875f7af..9160f7eafb 100644
--- a/deps/uv/src/unix/proctitle.c
+++ b/deps/uv/src/unix/proctitle.c
@@ -48,9 +48,15 @@ char** uv_setup_args(int argc, char** argv) {
for (i = 0; i < argc; i++)
size += strlen(argv[i]) + 1;
+#if defined(__MVS__)
+ /* argv is not adjacent. So just use argv[0] */
+ process_title.str = argv[0];
+ process_title.len = strlen(argv[0]);
+#else
process_title.str = argv[0];
process_title.len = argv[argc - 1] + strlen(argv[argc - 1]) - argv[0];
assert(process_title.len + 1 == size); /* argv memory should be adjacent. */
+#endif
/* Add space for the argv pointers. */
size += (argc + 1) * sizeof(char*);
diff --git a/deps/uv/src/unix/pthread-barrier.c b/deps/uv/src/unix/pthread-barrier.c
index f57bf25080..b6e604d46d 100644
--- a/deps/uv/src/unix/pthread-barrier.c
+++ b/deps/uv/src/unix/pthread-barrier.c
@@ -73,7 +73,8 @@ int pthread_barrier_wait(pthread_barrier_t* barrier) {
if (++b->in == b->threshold) {
b->in = 0;
b->out = b->threshold - 1;
- assert(pthread_cond_signal(&b->cond) == 0);
+ rc = pthread_cond_signal(&b->cond);
+ assert(rc == 0);
pthread_mutex_unlock(&b->mutex);
return PTHREAD_BARRIER_SERIAL_THREAD;
diff --git a/deps/uv/src/unix/stream.c b/deps/uv/src/unix/stream.c
index 86f4eb7a5c..7059df16a6 100644
--- a/deps/uv/src/unix/stream.c
+++ b/deps/uv/src/unix/stream.c
@@ -390,7 +390,7 @@ failed_malloc:
int uv__stream_open(uv_stream_t* stream, int fd, int flags) {
-#if defined(__APPLE__)
+#if defined(__APPLE__) || defined(__MVS__)
int enable;
#endif
@@ -409,7 +409,7 @@ int uv__stream_open(uv_stream_t* stream, int fd, int flags) {
return -errno;
}
-#if defined(__APPLE__)
+#if defined(__APPLE__) || defined(__MVS__)
enable = 1;
if (setsockopt(fd, SOL_SOCKET, SO_OOBINLINE, &enable, sizeof(enable)) &&
errno != ENOTSOCK &&
@@ -1194,6 +1194,30 @@ static void uv__read(uv_stream_t* stream) {
return;
}
}
+
+#if defined(__MVS__)
+ if (is_ipc && msg.msg_controllen > 0) {
+ uv_buf_t blankbuf;
+ int nread;
+ struct iovec *old;
+
+ blankbuf.base = 0;
+ blankbuf.len = 0;
+ old = msg.msg_iov;
+ msg.msg_iov = (struct iovec*) &blankbuf;
+ nread = 0;
+ do {
+ nread = uv__recvmsg(uv__stream_fd(stream), &msg, 0);
+ err = uv__stream_recv_cmsg(stream, &msg);
+ if (err != 0) {
+ stream->read_cb(stream, err, &buf);
+ msg.msg_iov = old;
+ return;
+ }
+ } while (nread == 0 && msg.msg_controllen > 0);
+ msg.msg_iov = old;
+ }
+#endif
stream->read_cb(stream, nread, &buf);
/* Return if we didn't fill the buffer, there is no more data to read. */
diff --git a/deps/uv/src/unix/sunos.c b/deps/uv/src/unix/sunos.c
index 3e7a7592d9..a43f7f1b1c 100644
--- a/deps/uv/src/unix/sunos.c
+++ b/deps/uv/src/unix/sunos.c
@@ -695,6 +695,11 @@ void uv_free_cpu_info(uv_cpu_info_t* cpu_infos, int count) {
uv__free(cpu_infos);
}
+#ifdef SUNOS_NO_IFADDRS
+int uv_interface_addresses(uv_interface_address_t** addresses, int* count) {
+ return -ENOSYS;
+}
+#else /* SUNOS_NO_IFADDRS */
/*
* Inspired By:
* https://blogs.oracle.com/paulie/entry/retrieving_mac_address_in_solaris
@@ -742,9 +747,6 @@ static int uv__set_phys_addr(uv_interface_address_t* address,
}
int uv_interface_addresses(uv_interface_address_t** addresses, int* count) {
-#ifdef SUNOS_NO_IFADDRS
- return -ENOSYS;
-#else
uv_interface_address_t* address;
struct ifaddrs* addrs;
struct ifaddrs* ent;
@@ -805,9 +807,8 @@ int uv_interface_addresses(uv_interface_address_t** addresses, int* count) {
freeifaddrs(addrs);
return 0;
-#endif /* SUNOS_NO_IFADDRS */
}
-
+#endif /* SUNOS_NO_IFADDRS */
void uv_free_interface_addresses(uv_interface_address_t* addresses,
int count) {
diff --git a/deps/uv/src/uv-common.c b/deps/uv/src/uv-common.c
index 46d954673a..bc7d1379d1 100644
--- a/deps/uv/src/uv-common.c
+++ b/deps/uv/src/uv-common.c
@@ -512,8 +512,18 @@ void uv__fs_scandir_cleanup(uv_fs_t* req) {
int uv_fs_scandir_next(uv_fs_t* req, uv_dirent_t* ent) {
uv__dirent_t** dents;
uv__dirent_t* dent;
+ unsigned int* nbufs;
- unsigned int* nbufs = uv__get_nbufs(req);
+ /* Check to see if req passed */
+ if (req->result < 0)
+ return req->result;
+
+ /* Ptr will be null if req was canceled or no files found */
+ if (!req->ptr)
+ return UV_EOF;
+
+ nbufs = uv__get_nbufs(req);
+ assert(nbufs);
dents = req->ptr;
diff --git a/deps/uv/src/win/signal.c b/deps/uv/src/win/signal.c
index 2c64a55dc3..af7974c364 100644
--- a/deps/uv/src/win/signal.c
+++ b/deps/uv/src/win/signal.c
@@ -30,12 +30,14 @@
RB_HEAD(uv_signal_tree_s, uv_signal_s);
static struct uv_signal_tree_s uv__signal_tree = RB_INITIALIZER(uv__signal_tree);
-static ssize_t volatile uv__signal_control_handler_refs = 0;
static CRITICAL_SECTION uv__signal_lock;
+static BOOL WINAPI uv__signal_control_handler(DWORD type);
void uv_signals_init() {
InitializeCriticalSection(&uv__signal_lock);
+ if (!SetConsoleCtrlHandler(uv__signal_control_handler, TRUE))
+ abort();
}
@@ -125,102 +127,6 @@ static BOOL WINAPI uv__signal_control_handler(DWORD type) {
}
-static int uv__signal_register_control_handler() {
- /* When this function is called, the uv__signal_lock must be held. */
-
- /* If the console control handler has already been hooked, just add a */
- /* reference. */
- if (uv__signal_control_handler_refs > 0) {
- uv__signal_control_handler_refs++;
- return 0;
- }
-
- if (!SetConsoleCtrlHandler(uv__signal_control_handler, TRUE))
- return GetLastError();
-
- uv__signal_control_handler_refs++;
-
- return 0;
-}
-
-
-static void uv__signal_unregister_control_handler() {
- /* When this function is called, the uv__signal_lock must be held. */
- BOOL r;
-
- /* Don't unregister if the number of console control handlers exceeds one. */
- /* Just remove a reference in that case. */
- if (uv__signal_control_handler_refs > 1) {
- uv__signal_control_handler_refs--;
- return;
- }
-
- assert(uv__signal_control_handler_refs == 1);
-
- r = SetConsoleCtrlHandler(uv__signal_control_handler, FALSE);
- /* This should never fail; if it does it is probably a bug in libuv. */
- assert(r);
-
- uv__signal_control_handler_refs--;
-}
-
-
-static int uv__signal_register(int signum) {
- switch (signum) {
- case SIGINT:
- case SIGBREAK:
- case SIGHUP:
- return uv__signal_register_control_handler();
-
- case SIGWINCH:
- /* SIGWINCH is generated in tty.c. No need to register anything. */
- return 0;
-
- case SIGILL:
- case SIGABRT_COMPAT:
- case SIGFPE:
- case SIGSEGV:
- case SIGTERM:
- case SIGABRT:
- /* Signal is never raised. */
- return 0;
-
- default:
- /* Invalid signal. */
- return ERROR_INVALID_PARAMETER;
- }
-}
-
-
-static void uv__signal_unregister(int signum) {
- switch (signum) {
- case SIGINT:
- case SIGBREAK:
- case SIGHUP:
- uv__signal_unregister_control_handler();
- return;
-
- case SIGWINCH:
- /* SIGWINCH is generated in tty.c. No need to unregister anything. */
- return;
-
- case SIGILL:
- case SIGABRT_COMPAT:
- case SIGFPE:
- case SIGSEGV:
- case SIGTERM:
- case SIGABRT:
- /* Nothing is registered for this signal. */
- return;
-
- default:
- /* Libuv bug. */
- assert(0 && "Invalid signum");
- return;
- }
-}
-
-
int uv_signal_init(uv_loop_t* loop, uv_signal_t* handle) {
uv_req_t* req;
@@ -247,8 +153,6 @@ int uv_signal_stop(uv_signal_t* handle) {
EnterCriticalSection(&uv__signal_lock);
- uv__signal_unregister(handle->signum);
-
removed_handle = RB_REMOVE(uv_signal_tree_s, &uv__signal_tree, handle);
assert(removed_handle == handle);
@@ -262,14 +166,9 @@ int uv_signal_stop(uv_signal_t* handle) {
int uv_signal_start(uv_signal_t* handle, uv_signal_cb signal_cb, int signum) {
- int err;
-
- /* If the user supplies signum == 0, then return an error already. If the */
- /* signum is otherwise invalid then uv__signal_register will find out */
- /* eventually. */
- if (signum == 0) {
+ /* Test for invalid signal values. */
+ if (signum != SIGWINCH && (signum <= 0 || signum >= NSIG))
return UV_EINVAL;
- }
/* Short circuit: if the signal watcher is already watching {signum} don't */
/* go through the process of deregistering and registering the handler. */
@@ -289,13 +188,6 @@ int uv_signal_start(uv_signal_t* handle, uv_signal_cb signal_cb, int signum) {
EnterCriticalSection(&uv__signal_lock);
- err = uv__signal_register(signum);
- if (err) {
- /* Uh-oh, didn't work. */
- LeaveCriticalSection(&uv__signal_lock);
- return uv_translate_sys_error(err);
- }
-
handle->signum = signum;
RB_INSERT(uv_signal_tree_s, &uv__signal_tree, handle);
diff --git a/deps/uv/src/win/winapi.h b/deps/uv/src/win/winapi.h
index 341fcd0842..9401676fbd 100644
--- a/deps/uv/src/win/winapi.h
+++ b/deps/uv/src/win/winapi.h
@@ -4606,6 +4606,10 @@ typedef NTSTATUS (NTAPI *sNtQueryDirectoryFile)
#endif
/* from winerror.h */
+#ifndef ERROR_ELEVATION_REQUIRED
+# define ERROR_ELEVATION_REQUIRED 740
+#endif
+
#ifndef ERROR_SYMLINK_NOT_SUPPORTED
# define ERROR_SYMLINK_NOT_SUPPORTED 1464
#endif
diff --git a/deps/uv/test/test-error.c b/deps/uv/test/test-error.c
index ff53eb1d77..a2d559a4ee 100644
--- a/deps/uv/test/test-error.c
+++ b/deps/uv/test/test-error.c
@@ -21,6 +21,9 @@
#include "uv.h"
#include "task.h"
+#if defined(_WIN32)
+# include "../src/win/winapi.h"
+#endif
#include <stdio.h>
#include <stdlib.h>
diff --git a/deps/uv/test/test-fs.c b/deps/uv/test/test-fs.c
index 70a2399962..030245eadc 100644
--- a/deps/uv/test/test-fs.c
+++ b/deps/uv/test/test-fs.c
@@ -510,6 +510,18 @@ static void empty_scandir_cb(uv_fs_t* req) {
scandir_cb_count++;
}
+static void non_existent_scandir_cb(uv_fs_t* req) {
+ uv_dirent_t dent;
+
+ ASSERT(req == &scandir_req);
+ ASSERT(req->fs_type == UV_FS_SCANDIR);
+ ASSERT(req->result == UV_ENOENT);
+ ASSERT(req->ptr == NULL);
+ ASSERT(UV_ENOENT == uv_fs_scandir_next(req, &dent));
+ uv_fs_req_cleanup(req);
+ scandir_cb_count++;
+}
+
static void file_scandir_cb(uv_fs_t* req) {
ASSERT(req == &scandir_req);
@@ -2175,6 +2187,39 @@ TEST_IMPL(fs_scandir_empty_dir) {
}
+TEST_IMPL(fs_scandir_non_existent_dir) {
+ const char* path;
+ uv_fs_t req;
+ uv_dirent_t dent;
+ int r;
+
+ path = "./non_existent_dir/";
+ loop = uv_default_loop();
+
+ uv_fs_rmdir(NULL, &req, path, NULL);
+ uv_fs_req_cleanup(&req);
+
+ /* Fill the req to ensure that required fields are cleaned up */
+ memset(&req, 0xdb, sizeof(req));
+
+ r = uv_fs_scandir(NULL, &req, path, 0, NULL);
+ ASSERT(r == UV_ENOENT);
+ ASSERT(req.result == UV_ENOENT);
+ ASSERT(req.ptr == NULL);
+ ASSERT(UV_ENOENT == uv_fs_scandir_next(&req, &dent));
+ uv_fs_req_cleanup(&req);
+
+ r = uv_fs_scandir(loop, &scandir_req, path, 0, non_existent_scandir_cb);
+ ASSERT(r == 0);
+
+ ASSERT(scandir_cb_count == 0);
+ uv_run(loop, UV_RUN_DEFAULT);
+ ASSERT(scandir_cb_count == 1);
+
+ MAKE_VALGRIND_HAPPY();
+ return 0;
+}
+
TEST_IMPL(fs_scandir_file) {
const char* path;
int r;
diff --git a/deps/uv/test/test-list.h b/deps/uv/test/test-list.h
index be3f9069cc..3a1e82a919 100644
--- a/deps/uv/test/test-list.h
+++ b/deps/uv/test/test-list.h
@@ -295,6 +295,7 @@ TEST_DECLARE (fs_event_start_and_close)
TEST_DECLARE (fs_event_error_reporting)
TEST_DECLARE (fs_event_getpath)
TEST_DECLARE (fs_scandir_empty_dir)
+TEST_DECLARE (fs_scandir_non_existent_dir)
TEST_DECLARE (fs_scandir_file)
TEST_DECLARE (fs_open_dir)
TEST_DECLARE (fs_rename_to_existing_file)
@@ -345,6 +346,7 @@ TEST_DECLARE (listen_no_simultaneous_accepts)
TEST_DECLARE (fs_stat_root)
TEST_DECLARE (spawn_with_an_odd_path)
TEST_DECLARE (ipc_listen_after_bind_twice)
+TEST_DECLARE (win32_signum_number)
#else
TEST_DECLARE (emfile)
TEST_DECLARE (close_fd)
@@ -694,6 +696,7 @@ TASK_LIST_START
TEST_ENTRY (fs_stat_root)
TEST_ENTRY (spawn_with_an_odd_path)
TEST_ENTRY (ipc_listen_after_bind_twice)
+ TEST_ENTRY (win32_signum_number)
#else
TEST_ENTRY (emfile)
TEST_ENTRY (close_fd)
@@ -751,6 +754,7 @@ TASK_LIST_START
TEST_ENTRY (fs_event_error_reporting)
TEST_ENTRY (fs_event_getpath)
TEST_ENTRY (fs_scandir_empty_dir)
+ TEST_ENTRY (fs_scandir_non_existent_dir)
TEST_ENTRY (fs_scandir_file)
TEST_ENTRY (fs_open_dir)
TEST_ENTRY (fs_rename_to_existing_file)
diff --git a/deps/uv/test/test-process-title.c b/deps/uv/test/test-process-title.c
index 21ab0ed4fd..5d5ede9d60 100644
--- a/deps/uv/test/test-process-title.c
+++ b/deps/uv/test/test-process-title.c
@@ -60,7 +60,7 @@ static void uv_get_process_title_edge_cases() {
TEST_IMPL(process_title) {
-#if defined(__sun) || defined(_AIX) || defined(__MVS__)
+#if defined(__sun)
RETURN_SKIP("uv_(get|set)_process_title is not implemented.");
#else
/* Check for format string vulnerabilities. */
diff --git a/deps/uv/test/test-signal.c b/deps/uv/test/test-signal.c
index fcdd8e4d2d..c0424c60a0 100644
--- a/deps/uv/test/test-signal.c
+++ b/deps/uv/test/test-signal.c
@@ -19,13 +19,40 @@
* IN THE SOFTWARE.
*/
-
-/* This test does not pretend to be cross-platform. */
-#ifndef _WIN32
-
#include "uv.h"
#include "task.h"
+/* For Windows we test only signum handling */
+#ifdef _WIN32
+static void signum_test_cb(uv_signal_t* handle, int signum) {
+ FATAL("signum_test_cb should not be called");
+}
+
+TEST_IMPL(win32_signum_number) {
+ uv_signal_t signal;
+ uv_loop_t* loop;
+
+ loop = uv_default_loop();
+ uv_signal_init(loop, &signal);
+
+ ASSERT(uv_signal_start(&signal, signum_test_cb, 0) == UV_EINVAL);
+ ASSERT(uv_signal_start(&signal, signum_test_cb, SIGINT) == 0);
+ ASSERT(uv_signal_start(&signal, signum_test_cb, SIGBREAK) == 0);
+ ASSERT(uv_signal_start(&signal, signum_test_cb, SIGHUP) == 0);
+ ASSERT(uv_signal_start(&signal, signum_test_cb, SIGWINCH) == 0);
+ ASSERT(uv_signal_start(&signal, signum_test_cb, SIGILL) == 0);
+ ASSERT(uv_signal_start(&signal, signum_test_cb, SIGABRT_COMPAT) == 0);
+ ASSERT(uv_signal_start(&signal, signum_test_cb, SIGFPE) == 0);
+ ASSERT(uv_signal_start(&signal, signum_test_cb, SIGSEGV) == 0);
+ ASSERT(uv_signal_start(&signal, signum_test_cb, SIGTERM) == 0);
+ ASSERT(uv_signal_start(&signal, signum_test_cb, SIGABRT) == 0);
+ ASSERT(uv_signal_start(&signal, signum_test_cb, -1) == UV_EINVAL);
+ ASSERT(uv_signal_start(&signal, signum_test_cb, NSIG) == UV_EINVAL);
+ ASSERT(uv_signal_start(&signal, signum_test_cb, 1024) == UV_EINVAL);
+ MAKE_VALGRIND_HAPPY();
+ return 0;
+}
+#else
#include <errno.h>
#include <signal.h>
#include <stdarg.h>
diff --git a/deps/uv/test/test-tty.c b/deps/uv/test/test-tty.c
index d1f7deb231..6fc2c95c98 100644
--- a/deps/uv/test/test-tty.c
+++ b/deps/uv/test/test-tty.c
@@ -287,6 +287,9 @@ TEST_IMPL(tty_large_write) {
r = uv_tty_init(uv_default_loop(), &tty_out, ttyout_fd, 0); /* Writable. */
ASSERT(r == 0);
+ memset(dummy, '.', sizeof(dummy) - 1);
+ dummy[sizeof(dummy) - 1] = '\n';
+
bufs[0] = uv_buf_init(dummy, sizeof(dummy));
r = uv_try_write((uv_stream_t*) &tty_out, bufs, 1);
diff --git a/deps/uv/uv.gyp b/deps/uv/uv.gyp
index b969a8cd5d..49d5d22f96 100644
--- a/deps/uv/uv.gyp
+++ b/deps/uv/uv.gyp
@@ -10,13 +10,14 @@
['OS=="solaris"', {
'cflags': [ '-pthreads' ],
}],
- ['OS not in "solaris android zos"', {
+ ['OS not in "solaris android os390"', {
'cflags': [ '-pthread' ],
}],
- ['OS in "zos"', {
+ ['OS in "os390"', {
'defines': [
'_UNIX03_THREADS',
'_UNIX03_SOURCE',
+ '_UNIX03_WITHDRAWN',
'_OPEN_SYS_IF_EXT',
'_OPEN_SYS_SOCK_IPV6',
'_OPEN_MSGQ_EXT',
@@ -28,6 +29,7 @@
'PATH_MAX=255'
],
'cflags': [ '-qxplink' ],
+ 'ldflags': [ '-qxplink' ],
}]
],
}],
@@ -170,10 +172,10 @@
['OS=="solaris"', {
'ldflags': [ '-pthreads' ],
}],
- [ 'OS=="zos" and uv_library=="shared_library"', {
+ [ 'OS=="os390" and uv_library=="shared_library"', {
'ldflags': [ '-Wl,DLL' ],
}],
- ['OS != "solaris" and OS != "android" and OS != "zos"', {
+ ['OS != "solaris" and OS != "android" and OS != "os390"', {
'ldflags': [ '-pthread' ],
}],
],
@@ -181,14 +183,14 @@
'conditions': [
['uv_library=="shared_library"', {
'conditions': [
- ['OS=="zos"', {
+ ['OS=="os390"', {
'cflags': [ '-qexportall' ],
}, {
'cflags': [ '-fPIC' ],
}],
],
}],
- ['uv_library=="shared_library" and OS!="mac" and OS!="zos"', {
+ ['uv_library=="shared_library" and OS!="mac" and OS!="os390"', {
# This will cause gyp to set soname
# Must correspond with UV_VERSION_MAJOR
# in include/uv-version.h
@@ -196,10 +198,10 @@
}],
],
}],
- [ 'OS in "linux mac ios android"', {
+ [ 'OS in "linux mac ios android os390"', {
'sources': [ 'src/unix/proctitle.c' ],
}],
- [ 'OS != "zos"', {
+ [ 'OS != "os390"', {
'cflags': [
'-fvisibility=hidden',
'-g',
@@ -222,7 +224,7 @@
'_DARWIN_UNLIMITED_SELECT=1',
]
}],
- [ 'OS!="mac" and OS!="zos"', {
+ [ 'OS!="mac" and OS!="os390"', {
# Enable on all platforms except OS X. The antique gcc/clang that
# ships with Xcode emits waaaay too many false positives.
'cflags': [ '-Wstrict-aliasing' ],
@@ -275,6 +277,7 @@
'_XOPEN_SOURCE=500',
'_LINUX_SOURCE_COMPAT',
'_THREAD_SAFE',
+ 'HAVE_SYS_AHAFS_EVPRODS_H',
],
'link_settings': {
'libraries': [
@@ -302,11 +305,12 @@
['uv_library=="shared_library"', {
'defines': [ 'BUILDING_UV_SHARED=1' ]
}],
- ['OS=="zos"', {
+ ['OS=="os390"', {
'sources': [
'src/unix/pthread-fixes.c',
- 'src/unix/pthread-barrier.c'
- 'src/unix/os390.c'
+ 'src/unix/pthread-barrier.c',
+ 'src/unix/os390.c',
+ 'src/unix/os390-syscalls.c'
]
}],
]
@@ -467,7 +471,7 @@
'test/runner-unix.h',
],
'conditions': [
- [ 'OS != "zos"', {
+ [ 'OS != "os390"', {
'defines': [ '_GNU_SOURCE' ],
'cflags': [ '-Wno-long-long' ],
'xcode_settings': {
@@ -496,7 +500,7 @@
['uv_library=="shared_library"', {
'defines': [ 'USING_UV_SHARED=1' ],
'conditions': [
- [ 'OS == "zos"', {
+ [ 'OS == "os390"', {
'cflags': [ '-Wc,DLL' ],
}],
],
@@ -557,7 +561,7 @@
['uv_library=="shared_library"', {
'defines': [ 'USING_UV_SHARED=1' ],
'conditions': [
- [ 'OS == "zos"', {
+ [ 'OS == "os390"', {
'cflags': [ '-Wc,DLL' ],
}],
],