Skip to content

Commit

Permalink
reproc: add multithreaded option and fix link orders (#3323)
Browse files Browse the repository at this point in the history
* reproc: add multithreaded option and fix link orders

* Update xmake.lua

---------

Co-authored-by: ruki <[email protected]>
  • Loading branch information
paul-reilly and waruqi authored Mar 1, 2024
1 parent a608962 commit 719c801
Show file tree
Hide file tree
Showing 2 changed files with 302 additions and 5 deletions.
289 changes: 289 additions & 0 deletions packages/r/reproc/patches/0001-to-head.diff
Original file line number Diff line number Diff line change
@@ -0,0 +1,289 @@
diff --git a/.clang-tidy b/.clang-tidy
index 35bb58f..de92997 100644
--- a/.clang-tidy
+++ b/.clang-tidy
@@ -34,6 +34,7 @@ Checks:
-performance-no-int-to-ptr,
-readability-else-after-return,
-readability-function-cognitive-complexity,
+-readability-identifier-length,
-readability-magic-numbers,
'
HeaderFilterRegex: '.*reproc\+\+.*$'
diff --git a/.github/workflows/main.yml b/.github/workflows/main.yml
index 4000454..3858f59 100644
--- a/.github/workflows/main.yml
+++ b/.github/workflows/main.yml
@@ -74,7 +74,7 @@ jobs:
- name: Install (Windows)
if: runner.os == 'Windows'
run: |
- Invoke-Expression (New-Object System.Net.WebClient).DownloadString('https://get.scoop.sh')
+ iex "& {$(irm get.scoop.sh)} -RunAsAdmin"
scoop install ninja llvm --global

if ("${{ matrix.compiler }}" -eq "gcc") {
diff --git a/README.md b/README.md
index 62cc299..e7e940d 100644
--- a/README.md
+++ b/README.md
@@ -225,6 +225,16 @@ occurred. You can test against these error codes using values from the

See the examples for more information on how to handle errors when using reproc.

+Note:
+
+Both reproc and reproc++ APIs take `options` argument that may define one or more
+`stop` actions such as `terminate` or `kill`.
+For that reason if the child process is being terminated or killed using a signal
+on POSIX, the error code will **not** reflect an error.
+
+It's up to the downstream project to *interpret* status codes reflecting unexpected
+behaviors alongside error codes (see this [example](https://github.com/DaanDeMeyer/reproc/issues/68#issuecomment-959074504)).
+
## Multithreading

Don't call the same operation on the same child process from more than one
diff --git a/reproc++/include/reproc++/reproc.hpp b/reproc++/include/reproc++/reproc.hpp
index ab6f139..f722245 100644
--- a/reproc++/include/reproc++/reproc.hpp
+++ b/reproc++/include/reproc++/reproc.hpp
@@ -88,18 +88,18 @@ struct redirect {

struct options {
struct {
- env::type behavior;
+ reproc::env::type behavior;
/*! Implicitly converts from any STL container of string pairs to the
environment format expected by `reproc_start`. */
- class env extra;
+ reproc::env extra;
} env = {};

const char *working_directory = nullptr;

struct {
- redirect in;
- redirect out;
- redirect err;
+ struct redirect in;
+ struct redirect out;
+ struct redirect err;
bool parent;
bool discard;
FILE *file;
@@ -138,30 +138,12 @@ enum class stream {
err,
};

-class process;
-
namespace event {

-enum {
- in = 1 << 0,
- out = 1 << 1,
- err = 1 << 2,
- exit = 1 << 3,
- deadline = 1 << 4,
-};
-
-struct source {
- class process &process;
- int interests;
- int events;
-};
+struct source;

}

-REPROCXX_EXPORT std::error_code poll(event::source *sources,
- size_t num_sources,
- milliseconds timeout = infinite);
-
/*! Improves on reproc's API by adding RAII and changing the API of some
functions to be more idiomatic C++. */
class process {
@@ -220,4 +202,26 @@ private:
std::unique_ptr<reproc_t, reproc_t *(*) (reproc_t *)> impl_;
};

+namespace event {
+
+enum {
+ in = 1 << 0,
+ out = 1 << 1,
+ err = 1 << 2,
+ exit = 1 << 3,
+ deadline = 1 << 4,
+};
+
+struct source {
+ class process process;
+ int interests;
+ int events;
+};
+
+}
+
+REPROCXX_EXPORT std::error_code poll(event::source *sources,
+ size_t num_sources,
+ milliseconds timeout = infinite);
+
}
diff --git a/reproc++/src/reproc.cpp b/reproc++/src/reproc.cpp
index e4eed1a..534e9fb 100644
--- a/reproc++/src/reproc.cpp
+++ b/reproc++/src/reproc.cpp
@@ -86,8 +86,9 @@ std::pair<bool, std::error_code> process::fork(const options &options) noexcept
std::pair<int, std::error_code> process::poll(int interests,
milliseconds timeout)
{
- event::source source{ *this, interests, 0 };
+ event::source source{ std::move(*this), interests, 0 };
std::error_code ec = ::reproc::poll(&source, 1, timeout);
+ *this = std::move(source.process);
return { source.events, ec };
}

diff --git a/reproc/CMakeLists.txt b/reproc/CMakeLists.txt
index 949cc88..1bb4798 100644
--- a/reproc/CMakeLists.txt
+++ b/reproc/CMakeLists.txt
@@ -1,6 +1,6 @@
if(WIN32)
set(REPROC_WINSOCK_LIBRARY ws2_32)
-elseif(NOT APPLE)
+elseif(CMAKE_SYSTEM_NAME MATCHES Linux)
set(REPROC_RT_LIBRARY rt) # clock_gettime
endif()

diff --git a/reproc/src/clock.windows.c b/reproc/src/clock.windows.c
index 3130f85..8c6c85a 100644
--- a/reproc/src/clock.windows.c
+++ b/reproc/src/clock.windows.c
@@ -1,4 +1,8 @@
-#define _WIN32_WINNT _WIN32_WINNT_VISTA
+#ifndef _WIN32_WINNT
+ #define _WIN32_WINNT 0x0600 // _WIN32_WINNT_VISTA
+#elif _WIN32_WINNT < 0x0600
+ #error "_WIN32_WINNT must be greater than _WIN32_WINNT_VISTA (0x0600)"
+#endif

#include "clock.h"

diff --git a/reproc/src/error.windows.c b/reproc/src/error.windows.c
index b8d8234..9459027 100644
--- a/reproc/src/error.windows.c
+++ b/reproc/src/error.windows.c
@@ -1,4 +1,8 @@
-#define _WIN32_WINNT _WIN32_WINNT_VISTA
+#ifndef _WIN32_WINNT
+ #define _WIN32_WINNT 0x0600 // _WIN32_WINNT_VISTA
+#elif _WIN32_WINNT < 0x0600
+ #error "_WIN32_WINNT must be greater than _WIN32_WINNT_VISTA (0x0600)"
+#endif

#include "error.h"

diff --git a/reproc/src/handle.windows.c b/reproc/src/handle.windows.c
index e0cd500..f0fbe56 100644
--- a/reproc/src/handle.windows.c
+++ b/reproc/src/handle.windows.c
@@ -1,4 +1,8 @@
-#define _WIN32_WINNT _WIN32_WINNT_VISTA
+#ifndef _WIN32_WINNT
+ #define _WIN32_WINNT 0x0600 // _WIN32_WINNT_VISTA
+#elif _WIN32_WINNT < 0x0600
+ #error "_WIN32_WINNT must be greater than _WIN32_WINNT_VISTA (0x0600)"
+#endif

#include "handle.h"

diff --git a/reproc/src/init.windows.c b/reproc/src/init.windows.c
index 8357b7c..52519bf 100644
--- a/reproc/src/init.windows.c
+++ b/reproc/src/init.windows.c
@@ -1,4 +1,8 @@
-#define _WIN32_WINNT _WIN32_WINNT_VISTA
+#ifndef _WIN32_WINNT
+ #define _WIN32_WINNT 0x0600 // _WIN32_WINNT_VISTA
+#elif _WIN32_WINNT < 0x0600
+ #error "_WIN32_WINNT must be greater than _WIN32_WINNT_VISTA (0x0600)"
+#endif

#include "init.h"

diff --git a/reproc/src/pipe.windows.c b/reproc/src/pipe.windows.c
index bb355be..befeaf1 100644
--- a/reproc/src/pipe.windows.c
+++ b/reproc/src/pipe.windows.c
@@ -1,4 +1,8 @@
-#define _WIN32_WINNT _WIN32_WINNT_VISTA
+#ifndef _WIN32_WINNT
+ #define _WIN32_WINNT 0x0600 // _WIN32_WINNT_VISTA
+#elif _WIN32_WINNT < 0x0600
+ #error "_WIN32_WINNT must be greater than _WIN32_WINNT_VISTA (0x0600)"
+#endif

#include "pipe.h"

diff --git a/reproc/src/process.posix.c b/reproc/src/process.posix.c
index 0f0fe0d..8dcbfd1 100644
--- a/reproc/src/process.posix.c
+++ b/reproc/src/process.posix.c
@@ -17,6 +17,8 @@
#include "pipe.h"
#include "strv.h"

+#define CWD_BUF_SIZE_INCREMENT 4096
+
const pid_t PROCESS_INVALID = -1;

static int signal_mask(int how, const sigset_t *newmask, sigset_t *oldmask)
@@ -51,7 +53,7 @@ static char *path_prepend_cwd(const char *path)
ASSERT(path);

size_t path_size = strlen(path);
- size_t cwd_size = PATH_MAX;
+ size_t cwd_size = CWD_BUF_SIZE_INCREMENT;

// We always allocate sufficient space for `path` but do not include this
// space in `cwd_size` so we can be sure that when `getcwd` succeeds there is
@@ -70,7 +72,7 @@ static char *path_prepend_cwd(const char *path)
return NULL;
}

- cwd_size += PATH_MAX;
+ cwd_size += CWD_BUF_SIZE_INCREMENT;

char *result = realloc(cwd, cwd_size + path_size + 1);
if (result == NULL) {
diff --git a/reproc/src/process.windows.c b/reproc/src/process.windows.c
index 666f3cb..6e28589 100644
--- a/reproc/src/process.windows.c
+++ b/reproc/src/process.windows.c
@@ -1,4 +1,8 @@
-#define _WIN32_WINNT _WIN32_WINNT_VISTA
+#ifndef _WIN32_WINNT
+ #define _WIN32_WINNT 0x0600 // _WIN32_WINNT_VISTA
+#elif _WIN32_WINNT < 0x0600
+ #error "_WIN32_WINNT must be greater than _WIN32_WINNT_VISTA (0x0600)"
+#endif

#include "process.h"

diff --git a/reproc/src/redirect.windows.c b/reproc/src/redirect.windows.c
index c634145..151f407 100644
--- a/reproc/src/redirect.windows.c
+++ b/reproc/src/redirect.windows.c
@@ -1,4 +1,8 @@
-#define _WIN32_WINNT _WIN32_WINNT_VISTA
+#ifndef _WIN32_WINNT
+ #define _WIN32_WINNT 0x0600 // _WIN32_WINNT_VISTA
+#elif _WIN32_WINNT < 0x0600
+ #error "_WIN32_WINNT must be greater than _WIN32_WINNT_VISTA (0x0600)"
+#endif

#include "redirect.h"

18 changes: 13 additions & 5 deletions packages/r/reproc/xmake.lua
Original file line number Diff line number Diff line change
Expand Up @@ -7,26 +7,34 @@ package("reproc")
add_urls("https://github.com/DaanDeMeyer/reproc/archive/refs/tags/$(version).tar.gz",
"https://github.com/DaanDeMeyer/reproc.git")
add_versions("v14.2.4", "55c780f7faa5c8cabd83ebbb84b68e5e0e09732de70a129f6b3c801e905415dd")
add_patches("v14.2.4", path.join(os.scriptdir(), "patches", "0001-to-head.diff"),
"a5ed818fc36a93bf1f146e6b993e7d0e78daac9c3e5c005f7c84d3e7441f80bb")

add_deps("cmake")

if is_plat("linux") or is_plat("mingw") then
add_syslinks("pthread")
end
if is_plat("windows") or is_plat("mingw") then
if is_plat("windows", "mingw") then
add_syslinks("ws2_32")
end

add_configs("c++", { description = "Build reproc C++ library.", default = true, type = "boolean" })
add_configs("multithreaded", { description = "Enable multithreading.", default = true, type = "boolean" })

on_install(function(package)
local configs = {}
table.insert(configs, "-DCMAKE_BUILD_TYPE=" .. (package:debug() and "Debug" or "RelWithDebInfo"))
table.insert(configs, "-DBUILD_SHARED_LIBS=" .. (package:config("shared") and "ON" or "OFF"))
table.insert(configs, "-DREPROC++=" .. (package:config("c++") and "ON" or "OFF"))
import("package.tools.cmake").install(package, configs, { buildir = "build" })
table.insert(configs, "-DREPROC_MULTITHREADED=" .. (package:config("multithreaded") and "ON" or "OFF"))

if package:config("multithreaded") and not package:is_plat("windows", "android") then
package:add("syslinks", "pthread")
end

import("package.tools.cmake").install(package, configs)
package:add("linkorders", {"reproc++", "reproc"})
end)

on_test(function(package)
assert(package:has_cfuncs("reproc_run", { includes = "reproc/run.h" }))
end)

0 comments on commit 719c801

Please sign in to comment.