diff --git a/deps/uv/include/uv-private/ngx-queue.h b/deps/uv/include/uv-private/ngx-queue.h index 6fd0071ff0..08fd655a1a 100644 --- a/deps/uv/include/uv-private/ngx-queue.h +++ b/deps/uv/include/uv-private/ngx-queue.h @@ -101,7 +101,7 @@ struct ngx_queue_s { #define ngx_queue_foreach(q, h) \ for ((q) = ngx_queue_head(h); \ - (q) != ngx_queue_sentinel(h); \ + (q) != ngx_queue_sentinel(h) && !ngx_queue_empty(h); \ (q) = ngx_queue_next(q)) diff --git a/deps/uv/src/unix/linux/linux-core.c b/deps/uv/src/unix/linux/linux-core.c index bf6efd85b6..4259d17114 100644 --- a/deps/uv/src/unix/linux/linux-core.c +++ b/deps/uv/src/unix/linux/linux-core.c @@ -30,6 +30,7 @@ #include #include +#include #include #include #include @@ -167,6 +168,10 @@ uv_err_t uv_set_process_title(const char* title) { if (process_title.len) strncpy(process_title.str, title, process_title.len - 1); +#if defined(PR_SET_NAME) + prctl(PR_SET_NAME, title); +#endif + return uv_ok_; } @@ -320,10 +325,13 @@ uv_err_t uv_cpu_info(uv_cpu_info_t** cpu_infos, int* count) { if (ci == NULL) return uv__new_sys_error(ENOMEM); - read_speeds(numcpus, ci); read_models(numcpus, ci); read_times(numcpus, ci); + /* read_models() on x86 also reads the CPU speed from /proc/cpuinfo */ + if (ci[0].speed == 0) + read_speeds(numcpus, ci); + *cpu_infos = ci; *count = numcpus; @@ -339,18 +347,26 @@ static void read_speeds(unsigned int numcpus, uv_cpu_info_t* ci) { } +/* Also reads the CPU frequency on x86. The other architectures only have + * a BogoMIPS field, which may not be very accurate. + */ static void read_models(unsigned int numcpus, uv_cpu_info_t* ci) { #if defined(__i386__) || defined(__x86_64__) - static const char marker[] = "model name\t: "; + static const char model_marker[] = "model name\t: "; + static const char speed_marker[] = "cpu MHz\t\t: "; #elif defined(__arm__) - static const char marker[] = "Processor\t: "; + static const char model_marker[] = "Processor\t: "; + static const char speed_marker[] = ""; #elif defined(__mips__) - static const char marker[] = "cpu model\t\t: "; + static const char model_marker[] = "cpu model\t\t: "; + static const char speed_marker[] = ""; #else # warning uv_cpu_info() is not supported on this architecture. - static const char marker[] = "(dummy)"; + static const char model_marker[] = ""; + static const char speed_marker[] = ""; #endif - unsigned int num; + unsigned int model_idx; + unsigned int speed_idx; char buf[1024]; char* model; FILE* fp; @@ -359,18 +375,27 @@ static void read_models(unsigned int numcpus, uv_cpu_info_t* ci) { if (fp == NULL) return; - num = 0; + model_idx = 0; + speed_idx = 0; while (fgets(buf, sizeof(buf), fp)) { - if (num >= numcpus) - break; - - if (strncmp(buf, marker, sizeof(marker) - 1)) + if (model_marker[0] != '\0' && + model_idx < numcpus && + strncmp(buf, model_marker, sizeof(model_marker) - 1) == 0) + { + model = buf + sizeof(model_marker) - 1; + model = strndup(model, strlen(model) - 1); /* strip newline */ + ci[model_idx++].model = model; continue; + } - model = buf + sizeof(marker) - 1; - model = strndup(model, strlen(model) - 1); /* strip newline */ - ci[num++].model = model; + if (speed_marker[0] != '\0' && + speed_idx < numcpus && + strncmp(buf, speed_marker, sizeof(speed_marker) - 1) == 0) + { + ci[speed_idx++].speed = atoi(buf + sizeof(speed_marker) - 1); + continue; + } } fclose(fp); } diff --git a/deps/uv/src/unix/process.c b/deps/uv/src/unix/process.c index 4033064029..9b17479502 100644 --- a/deps/uv/src/unix/process.c +++ b/deps/uv/src/unix/process.c @@ -260,7 +260,9 @@ static void uv__process_child_init(uv_process_options_t options, _exit(127); } - environ = options.env; + if (options.env) { + environ = options.env; + } execvp(options.file, options.args); perror("execvp()"); diff --git a/deps/uv/src/win/core.c b/deps/uv/src/win/core.c index 5b47c2023b..d29a1300a1 100644 --- a/deps/uv/src/win/core.c +++ b/deps/uv/src/win/core.c @@ -55,7 +55,9 @@ static void uv_init(void) { /* Tell the CRT to not exit the application when an invalid parameter is */ /* passed. The main issue is that invalid FDs will trigger this behavior. */ +#ifdef _WRITE_ABORT_MSG _set_invalid_parameter_handler(uv__crt_invalid_parameter_handler); +#endif /* Fetch winapi function pointers. This must be done first because other */ /* intialization code might need these function pointers to be loaded. */ diff --git a/deps/uv/src/win/error.c b/deps/uv/src/win/error.c index 91f5111ed2..1d2d2513f5 100644 --- a/deps/uv/src/win/error.c +++ b/deps/uv/src/win/error.c @@ -74,6 +74,7 @@ uv_err_code uv_translate_sys_error(int sys_errno) { case ERROR_DISK_CORRUPT: return UV_EIO; case ERROR_EOM_OVERFLOW: return UV_EIO; case ERROR_FILEMARK_DETECTED: return UV_EIO; + case ERROR_GEN_FAILURE: return UV_EIO; case ERROR_INVALID_BLOCK_LENGTH: return UV_EIO; case ERROR_IO_DEVICE: return UV_EIO; case ERROR_NO_DATA_DETECTED: return UV_EIO; @@ -143,6 +144,7 @@ uv_err_code uv_translate_sys_error(int sys_errno) { case ERROR_BAD_PIPE: return UV_EPIPE; case ERROR_NO_DATA: return UV_EPIPE; case ERROR_PIPE_NOT_CONNECTED: return UV_EPIPE; + case WSAESHUTDOWN: return UV_EPIPE; case ERROR_PIPE_BUSY: return UV_EBUSY; case ERROR_SEM_TIMEOUT: return UV_ETIMEDOUT; case WSAETIMEDOUT: return UV_ETIMEDOUT; diff --git a/deps/uv/test/run-tests.c b/deps/uv/test/run-tests.c index fb16303753..d0e64f05d3 100644 --- a/deps/uv/test/run-tests.c +++ b/deps/uv/test/run-tests.c @@ -134,5 +134,18 @@ static int maybe_run_test(int argc, char **argv) { return 1; } + if (strcmp(argv[1], "spawn_helper7") == 0) { + int r; + char *test; + /* Test if the test value from the parent is still set */ + test = getenv("ENV_TEST"); + ASSERT(test != NULL); + + r = fprintf(stdout, "%s", test); + ASSERT(r > 0); + + return 1; + } + return run_test(argv[1], TEST_TIMEOUT, 0); } diff --git a/deps/uv/test/test-list.h b/deps/uv/test/test-list.h index 19670e5684..d37725885c 100644 --- a/deps/uv/test/test-list.h +++ b/deps/uv/test/test-list.h @@ -133,6 +133,7 @@ TEST_DECLARE (spawn_and_kill) TEST_DECLARE (spawn_detached) TEST_DECLARE (spawn_and_kill_with_std) TEST_DECLARE (spawn_and_ping) +TEST_DECLARE (spawn_preserve_env) TEST_DECLARE (spawn_setuid_fails) TEST_DECLARE (spawn_setgid_fails) TEST_DECLARE (spawn_stdout_to_file) @@ -362,6 +363,7 @@ TASK_LIST_START TEST_ENTRY (spawn_detached) TEST_ENTRY (spawn_and_kill_with_std) TEST_ENTRY (spawn_and_ping) + TEST_ENTRY (spawn_preserve_env) TEST_ENTRY (spawn_setuid_fails) TEST_ENTRY (spawn_setgid_fails) TEST_ENTRY (spawn_stdout_to_file) diff --git a/deps/uv/test/test-spawn.c b/deps/uv/test/test-spawn.c index 51ed2e59d7..43e8010079 100644 --- a/deps/uv/test/test-spawn.c +++ b/deps/uv/test/test-spawn.c @@ -373,6 +373,46 @@ TEST_IMPL(spawn_and_kill) { return 0; } + +TEST_IMPL(spawn_preserve_env) { + int r; + uv_pipe_t out; + uv_stdio_container_t stdio[2]; + + init_process_options("spawn_helper7", exit_cb); + + uv_pipe_init(uv_default_loop(), &out, 0); + options.stdio = stdio; + options.stdio[0].flags = UV_IGNORE; + options.stdio[1].flags = UV_CREATE_PIPE | UV_WRITABLE_PIPE; + options.stdio[1].data.stream = (uv_stream_t*) &out; + options.stdio_count = 2; + + r = putenv("ENV_TEST=testval"); + ASSERT(r == 0); + + /* Explicitly set options.env to NULL to test for env clobbering. */ + options.env = NULL; + + r = uv_spawn(uv_default_loop(), &process, options); + ASSERT(r == 0); + + r = uv_read_start((uv_stream_t*) &out, on_alloc, on_read); + ASSERT(r == 0); + + r = uv_run(uv_default_loop()); + ASSERT(r == 0); + + ASSERT(exit_cb_called == 1); + ASSERT(close_cb_called == 2); + + printf("output is: %s", output); + ASSERT(strcmp("testval", output) == 0); + + return 0; +} + + TEST_IMPL(spawn_detached) { int r; uv_err_t err; diff --git a/deps/uv/uv.gyp b/deps/uv/uv.gyp index 96c6b724c6..f288d92d31 100644 --- a/deps/uv/uv.gyp +++ b/deps/uv/uv.gyp @@ -10,11 +10,9 @@ ], 'conditions': [ ['OS=="solaris"', { - 'cflags': ['-pthreads'], - 'ldlags': ['-pthreads'], + 'cflags': [ '-pthreads' ], }, { - 'cflags': ['-pthread'], - 'ldlags': ['-pthread'], + 'cflags': [ '-pthread' ], }], ], }], @@ -32,13 +30,7 @@ ], 'direct_dependent_settings': { 'include_dirs': [ 'include' ], - 'conditions': [ - ['OS=="linux"', { - 'libraries': [ '-ldl' ], - }], - ], }, - 'defines': [ 'HAVE_CONFIG_H' ], @@ -214,12 +206,21 @@ 'src/unix/uv-eio.h', ], 'include_dirs': [ 'src/unix/ev', ], - 'libraries': [ '-lm' ] + 'link_settings': { + 'libraries': [ '-lm' ], + 'conditions': [ + ['OS=="solaris"', { + 'ldflags': [ '-pthreads' ], + }, { + 'ldflags': [ '-pthread' ], + }], + ], + }, }], [ 'OS=="mac"', { 'include_dirs': [ 'src/ares/config_darwin' ], 'sources': [ 'src/unix/darwin.c' ], - 'direct_dependent_settings': { + 'link_settings': { 'libraries': [ '$(SDKROOT)/System/Library/Frameworks/CoreServices.framework', ], @@ -242,8 +243,8 @@ 'EV_CONFIG_H="config_linux.h"', 'EIO_CONFIG_H="config_linux.h"', ], - 'direct_dependent_settings': { - 'libraries': [ '-lrt' ], + 'link_settings': { + 'libraries': [ '-ldl', '-lrt' ], }, }], [ 'OS=="solaris"', { @@ -255,7 +256,7 @@ 'EV_CONFIG_H="config_sunos.h"', 'EIO_CONFIG_H="config_sunos.h"', ], - 'direct_dependent_settings': { + 'link_settings': { 'libraries': [ '-lkstat', '-lsocket', @@ -270,7 +271,7 @@ 'EV_CONFIG_H="config_freebsd.h"', 'EIO_CONFIG_H="config_freebsd.h"', ], - 'direct_dependent_settings': { + 'link_settings': { 'libraries': [ '-lkvm', ],