From 4fba286e4d013734aa3f1ddb7d0554e596b88a2c Mon Sep 17 00:00:00 2001 From: "Nicolas \"Pixel\" Noble" Date: Sun, 31 Jan 2016 07:00:53 +0100 Subject: [PATCH] Adding windows support for gpr subprocesses. --- BUILD | 2 + Makefile | 1 + binding.gyp | 1 + build.yaml | 1 + gRPC.podspec | 1 + grpc.gemspec | 1 + include/grpc/impl/codegen/port_platform.h | 1 + package.json | 1 + src/core/support/subprocess_windows.c | 141 ++++++++++++++++++++ src/python/grpcio/grpc_core_dependencies.py | 1 + tools/doxygen/Doxyfile.core.internal | 1 + tools/run_tests/sources_and_headers.json | 1 + vsprojects/vcxproj/gpr/gpr.vcxproj | 2 + vsprojects/vcxproj/gpr/gpr.vcxproj.filters | 3 + 14 files changed, 158 insertions(+) create mode 100644 src/core/support/subprocess_windows.c diff --git a/BUILD b/BUILD index 459aebd820d..727b137321c 100644 --- a/BUILD +++ b/BUILD @@ -84,6 +84,7 @@ cc_library( "src/core/support/string_posix.c", "src/core/support/string_win32.c", "src/core/support/subprocess_posix.c", + "src/core/support/subprocess_windows.c", "src/core/support/sync.c", "src/core/support/sync_posix.c", "src/core/support/sync_win32.c", @@ -1154,6 +1155,7 @@ objc_library( "src/core/support/string_posix.c", "src/core/support/string_win32.c", "src/core/support/subprocess_posix.c", + "src/core/support/subprocess_windows.c", "src/core/support/sync.c", "src/core/support/sync_posix.c", "src/core/support/sync_win32.c", diff --git a/Makefile b/Makefile index 31559d5c652..a0be756c476 100644 --- a/Makefile +++ b/Makefile @@ -2231,6 +2231,7 @@ LIBGPR_SRC = \ src/core/support/string_posix.c \ src/core/support/string_win32.c \ src/core/support/subprocess_posix.c \ + src/core/support/subprocess_windows.c \ src/core/support/sync.c \ src/core/support/sync_posix.c \ src/core/support/sync_win32.c \ diff --git a/binding.gyp b/binding.gyp index 651c2e13af3..ad8015dc85b 100644 --- a/binding.gyp +++ b/binding.gyp @@ -516,6 +516,7 @@ 'src/core/support/string_posix.c', 'src/core/support/string_win32.c', 'src/core/support/subprocess_posix.c', + 'src/core/support/subprocess_windows.c', 'src/core/support/sync.c', 'src/core/support/sync_posix.c', 'src/core/support/sync_win32.c', diff --git a/build.yaml b/build.yaml index 1b3cb792028..b20f915c54c 100644 --- a/build.yaml +++ b/build.yaml @@ -497,6 +497,7 @@ libs: - src/core/support/string_posix.c - src/core/support/string_win32.c - src/core/support/subprocess_posix.c + - src/core/support/subprocess_windows.c - src/core/support/sync.c - src/core/support/sync_posix.c - src/core/support/sync_win32.c diff --git a/gRPC.podspec b/gRPC.podspec index 922b246c54c..0bce6bdd212 100644 --- a/gRPC.podspec +++ b/gRPC.podspec @@ -151,6 +151,7 @@ Pod::Spec.new do |s| 'src/core/support/string_posix.c', 'src/core/support/string_win32.c', 'src/core/support/subprocess_posix.c', + 'src/core/support/subprocess_windows.c', 'src/core/support/sync.c', 'src/core/support/sync_posix.c', 'src/core/support/sync_win32.c', diff --git a/grpc.gemspec b/grpc.gemspec index 7f11ec778a5..ccd647113aa 100755 --- a/grpc.gemspec +++ b/grpc.gemspec @@ -134,6 +134,7 @@ Gem::Specification.new do |s| s.files += %w( src/core/support/string_posix.c ) s.files += %w( src/core/support/string_win32.c ) s.files += %w( src/core/support/subprocess_posix.c ) + s.files += %w( src/core/support/subprocess_windows.c ) s.files += %w( src/core/support/sync.c ) s.files += %w( src/core/support/sync_posix.c ) s.files += %w( src/core/support/sync_win32.c ) diff --git a/include/grpc/impl/codegen/port_platform.h b/include/grpc/impl/codegen/port_platform.h index 7333405db3d..ad1cd8594dd 100644 --- a/include/grpc/impl/codegen/port_platform.h +++ b/include/grpc/impl/codegen/port_platform.h @@ -80,6 +80,7 @@ #define GPR_ARCH_64 1 #define GPR_GETPID_IN_PROCESS_H 1 #define GPR_WINSOCK_SOCKET 1 +#define GPR_WINDOWS_SUBPROCESS 1 #ifdef __GNUC__ #define GPR_GCC_ATOMIC 1 #define GPR_GCC_TLS 1 diff --git a/package.json b/package.json index f02a100bc7a..a0a44e1bd6b 100644 --- a/package.json +++ b/package.json @@ -489,6 +489,7 @@ "src/core/support/string_posix.c", "src/core/support/string_win32.c", "src/core/support/subprocess_posix.c", + "src/core/support/subprocess_windows.c", "src/core/support/sync.c", "src/core/support/sync_posix.c", "src/core/support/sync_win32.c", diff --git a/src/core/support/subprocess_windows.c b/src/core/support/subprocess_windows.c new file mode 100644 index 00000000000..b4b86565949 --- /dev/null +++ b/src/core/support/subprocess_windows.c @@ -0,0 +1,141 @@ +/* + * + * Copyright 2015, Google Inc. + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions are + * met: + * + * * Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above + * copyright notice, this list of conditions and the following disclaimer + * in the documentation and/or other materials provided with the + * distribution. + * * Neither the name of Google Inc. nor the names of its + * contributors may be used to endorse or promote products derived from + * this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR + * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT + * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, + * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT + * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY + * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE + * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + * + */ + +#include + +#ifdef GPR_WINDOWS_SUBPROCESS + +#include +#include +#include + +#include +#include +#include +#include "src/core/support/string.h" +#include "src/core/support/string_win32.h" + +struct gpr_subprocess { + PROCESS_INFORMATION pi; + int joined; + int interrupted; +}; + +const char *gpr_subprocess_binary_extension() { return ".exe"; } + +gpr_subprocess *gpr_subprocess_create(int argc, const char **argv) { + gpr_subprocess *r; + + STARTUPINFO si; + PROCESS_INFORMATION pi; + + char *args = gpr_strjoin_sep(argv, argc, " ", NULL); + TCHAR *args_tchar; + + args_tchar = gpr_char_to_tchar(args); + gpr_free(args); + + memset(&si, 0, sizeof(si)); + si.cb = sizeof(si); + memset(&pi, 0, sizeof(pi)); + + if (!CreateProcess(NULL, args_tchar, NULL, NULL, FALSE, + CREATE_NEW_PROCESS_GROUP, NULL, NULL, &si, &pi)) { + gpr_free(args_tchar); + return NULL; + } + gpr_free(args_tchar); + + r = gpr_malloc(sizeof(gpr_subprocess)); + memset(r, 0, sizeof(*r)); + r->pi = pi; + return r; +} + +void gpr_subprocess_destroy(gpr_subprocess *p) { + if (p) { + if (!p->joined) { + gpr_subprocess_interrupt(p); + gpr_subprocess_join(p); + } + if (p->pi.hProcess) { + CloseHandle(p->pi.hProcess); + } + if (p->pi.hThread) { + CloseHandle(p->pi.hThread); + } + gpr_free(p); + } +} + +int gpr_subprocess_join(gpr_subprocess *p) { + DWORD dwExitCode; + if (GetExitCodeProcess(p->pi.hProcess, &dwExitCode)) { + if (dwExitCode == STILL_ACTIVE) { + if (WaitForSingleObject(p->pi.hProcess, INFINITE) == WAIT_OBJECT_0) { + p->joined = 1; + goto getExitCode; + } + return -1; // failed to join + } else { + goto getExitCode; + } + } else { + return -1; // failed to get exit code + } + +getExitCode: + if (p->interrupted) { + return 0; + } + if (GetExitCodeProcess(p->pi.hProcess, &dwExitCode)) { + return dwExitCode; + } else { + return -1; // failed to get exit code + } +} + +void gpr_subprocess_interrupt(gpr_subprocess *p) { + DWORD dwExitCode; + if (GetExitCodeProcess(p->pi.hProcess, &dwExitCode)) { + if (dwExitCode == STILL_ACTIVE) { + gpr_log(GPR_INFO, "sending ctrl-break"); + GenerateConsoleCtrlEvent(CTRL_BREAK_EVENT, p->pi.dwProcessId); + p->joined = 1; + p->interrupted = 1; + } + } + return; +} + +#endif /* GPR_WINDOWS_SUBPROCESS */ diff --git a/src/python/grpcio/grpc_core_dependencies.py b/src/python/grpcio/grpc_core_dependencies.py index 98ab1ff7f0e..04ed27002b6 100644 --- a/src/python/grpcio/grpc_core_dependencies.py +++ b/src/python/grpcio/grpc_core_dependencies.py @@ -60,6 +60,7 @@ CORE_SOURCE_FILES = [ 'src/core/support/string_posix.c', 'src/core/support/string_win32.c', 'src/core/support/subprocess_posix.c', + 'src/core/support/subprocess_windows.c', 'src/core/support/sync.c', 'src/core/support/sync_posix.c', 'src/core/support/sync_win32.c', diff --git a/tools/doxygen/Doxyfile.core.internal b/tools/doxygen/Doxyfile.core.internal index 11dc33a4630..76b66442738 100644 --- a/tools/doxygen/Doxyfile.core.internal +++ b/tools/doxygen/Doxyfile.core.internal @@ -1137,6 +1137,7 @@ src/core/support/string.c \ src/core/support/string_posix.c \ src/core/support/string_win32.c \ src/core/support/subprocess_posix.c \ +src/core/support/subprocess_windows.c \ src/core/support/sync.c \ src/core/support/sync_posix.c \ src/core/support/sync_win32.c \ diff --git a/tools/run_tests/sources_and_headers.json b/tools/run_tests/sources_and_headers.json index 9113f1ca057..1e1d2bb788e 100644 --- a/tools/run_tests/sources_and_headers.json +++ b/tools/run_tests/sources_and_headers.json @@ -2902,6 +2902,7 @@ "src/core/support/string_win32.c", "src/core/support/string_win32.h", "src/core/support/subprocess_posix.c", + "src/core/support/subprocess_windows.c", "src/core/support/sync.c", "src/core/support/sync_posix.c", "src/core/support/sync_win32.c", diff --git a/vsprojects/vcxproj/gpr/gpr.vcxproj b/vsprojects/vcxproj/gpr/gpr.vcxproj index cba35888905..b20d6ff77f5 100644 --- a/vsprojects/vcxproj/gpr/gpr.vcxproj +++ b/vsprojects/vcxproj/gpr/gpr.vcxproj @@ -269,6 +269,8 @@ + + diff --git a/vsprojects/vcxproj/gpr/gpr.vcxproj.filters b/vsprojects/vcxproj/gpr/gpr.vcxproj.filters index 1f8b09a1e9a..85d8ec86729 100644 --- a/vsprojects/vcxproj/gpr/gpr.vcxproj.filters +++ b/vsprojects/vcxproj/gpr/gpr.vcxproj.filters @@ -91,6 +91,9 @@ src\core\support + + src\core\support + src\core\support