v2: BOOST_PROCESS_V2_DISABLE_SIGNALSET does not compile with the signal-based process handle
評価
調査の方向性
The compile error is in the #else branch of async_wait() in include/boost/process/v2/detail/process_handle_signal.hpp, around line 350. Compare it with async_wait in process_handle_fd_or_signal.hpp, which completes with operation_not_supported. Build the reproducer with BOOST_PROCESS_V2_DISABLE_SIGNALSET and BOOST_PROCESS_V2_DISABLE_PIDFD_OPEN on Linux, then add test/v2/disable_signalset.cpp. Done means it compiles, the new test passes under b2, and the CMake target builds if develop's removed test_impl target is fixed.
索引モデルが issue の本文から書いたものです。
説明
With BOOST_PROCESS_V2_DISABLE_SIGNALSET defined, any use of process fails to compile where basic_process_handle_signal is used: macOS, the BSDs without pdfork, and Linux with BOOST_PROCESS_V2_DISABLE_PIDFD_OPEN. Affects 1.89 to 1.92 and develop.
#define BOOST_PROCESS_V2_DISABLE_SIGNALSET
#include <boost/asio/io_context.hpp>
#include <boost/process/v2/process.hpp>
int main()
{
boost::asio::io_context ctx;
boost::process::v2::process proc(ctx, "/bin/sh", {"-c", "exit 3"});
return proc.wait();
}
On Linux, add -DBOOST_PROCESS_V2_DISABLE_PIDFD_OPEN to get the signal handle.
GCC 15: process_handle_signal.hpp:373:68: error: too many initializers for '...::async_wait_op_'
clang 17: process_handle_signal.hpp:374:55: error: excess elements in struct initializer
31d6b5c9f82b0b1fd0fbd25f7f1af58d51d6e49f changed async_wait() to initialize async_wait_op_{signal_set_, pid_, exit_code} and the operation to complete with (Self&&, error_code), but the #else branch for the disabled signal set still has two members and dispatches the old (exit_code, ec) completion. Since the initializer is in the trailing return type of async_wait(), the error appears as soon as the class is instantiated.
Fix, matching process_handle_fd_or_signal.hpp (async_wait completes with operation_not_supported):
--- a/include/boost/process/v2/detail/process_handle_signal.hpp
+++ b/include/boost/process/v2/detail/process_handle_signal.hpp
@@ -348,15 +348,17 @@ struct basic_process_handle_signal
net::dispatch(exec, net::append(std::move(self), ec));
}
#else
- signal_set_dummy_ dummy_;
- pid_t pid;
+ signal_set_dummy_ &handle;
+ pid_type pid_;
+ native_exit_code_type & exit_code;
+
template<typename Self>
void operator()(Self &&self)
{
- auto exec = net::get_associated_immediate_executor(self, dummy_.get_executor());
+ auto exec = net::get_associated_immediate_executor(self, handle.get_executor());
error_code ec;
BOOST_PROCESS_V2_ASSIGN_EC(ec, net::error::operation_not_supported);
- net::dispatch(exec, net::append(std::move(self), native_exit_code_type(), ec));
+ net::dispatch(exec, net::append(std::move(self), ec));
}
#endif
A test, also run on Linux with BOOST_PROCESS_V2_DISABLE_PIDFD_OPEN so CI covers the signal handle. Passes with b2 on Linux (GCC 15) and macOS (Apple clang 17); without the fix it fails to compile. I can open a PR with both.
Test
--- a/test/v2/Jamfile.jam
+++ b/test/v2/Jamfile.jam
@@ -58,5 +58,8 @@ test-suite with_target :
[ run process.cpp $(test_impl) : --log_level=all --catch_system_errors=no -- : target ]
[ run windows.cpp $(test_impl) : --log_level=all --catch_system_errors=no -- : target : <build>no <target-os>windows:<build>yes <target-os>windows:<source>Advapi32 ]
[ run ext.cpp $(test_impl) : --log_level=all --catch_system_errors=no -- : target : <target-os>darwin:<build>no ]
+ [ run disable_signalset.cpp $(test_impl) : --log_level=all --catch_system_errors=no -- : target ]
+ [ run disable_signalset.cpp $(test_impl) : --log_level=all --catch_system_errors=no -- : target
+ : <build>no <target-os>linux:<build>yes <define>BOOST_PROCESS_V2_DISABLE_PIDFD_OPEN=1 : disable_signalset_no_pidfd ]
;
--- a/test/v2/CMakeLists.txt
+++ b/test/v2/CMakeLists.txt
@@ -34,3 +34,14 @@ endfunction()
boost_process_v2_test_with_target(process)
boost_process_v2_test_with_target(ext)
+boost_process_v2_test_with_target(disable_signalset)
+
+if (CMAKE_SYSTEM_NAME STREQUAL "Linux")
+ # The signal-based process handle that macOS and the BSDs use.
+ add_executable(boost_process_v2_disable_signalset_no_pidfd disable_signalset.cpp)
+ target_link_libraries(boost_process_v2_disable_signalset_no_pidfd PUBLIC Boost::process Boost::system Boost::filesystem boost_process_v2_test_impl)
+ target_compile_definitions(boost_process_v2_disable_signalset_no_pidfd PRIVATE BOOST_PROCESS_V2_DISABLE_PIDFD_OPEN=1)
+ add_dependencies(boost_process_v2_disable_signalset_no_pidfd boost_process_v2_test_target)
+ add_test(NAME boost_process_v2_disable_signalset_no_pidfd COMMAND $<TARGET_FILE:boost_process_v2_disable_signalset_no_pidfd>
+ -- $<TARGET_FILE:boost_process_v2_test_target>)
+endif()
--- /dev/null
+++ b/test/v2/disable_signalset.cpp
@@ -0,0 +1,69 @@
+// Copyright (c) 2026 Stefan Dinkelacker
+//
+// Distributed under the Boost Software License, Version 1.0. (See accompanying
+// file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
+
+// Disable autolinking for unit tests.
+#if !defined(BOOST_ALL_NO_LIB)
+#define BOOST_ALL_NO_LIB 1
+#endif // !defined(BOOST_ALL_NO_LIB)
+
+// An application that handles SIGCHLD itself must keep asio from installing
+// a handler for it.
+#define BOOST_PROCESS_V2_DISABLE_SIGNALSET 1
+
+#include <boost/process/v2/process.hpp>
+
+#include <boost/asio/io_context.hpp>
+#include <boost/test/unit_test.hpp>
+
+namespace bpv = boost::process::v2;
+namespace asio = boost::asio;
+
+BOOST_AUTO_TEST_SUITE(disable_signalset);
+
+BOOST_AUTO_TEST_CASE(wait)
+{
+ using boost::unit_test::framework::master_test_suite;
+ const auto pth = master_test_suite().argv[1];
+
+ asio::io_context ctx;
+ BOOST_CHECK_EQUAL(bpv::process(ctx, pth, {"exit-code", "42"}).wait(), 42);
+}
+
+BOOST_AUTO_TEST_CASE(async_wait)
+{
+ using boost::unit_test::framework::master_test_suite;
+ const auto pth = master_test_suite().argv[1];
+
+ asio::io_context ctx;
+ bpv::process proc(ctx, pth, {"exit-code", "42"});
+
+ bool called = false;
+ boost::system::error_code ec;
+ int code = -1;
+
+ proc.async_wait(
+ [&](boost::system::error_code ec_, int code_)
+ {
+ called = true;
+ ec = ec_;
+ code = code_;
+ });
+
+ ctx.run();
+ BOOST_CHECK(called);
+
+#if defined(BOOST_PROCESS_V2_WINDOWS) || defined(BOOST_PROCESS_V2_PIDFD_OPEN) \
+ || defined(BOOST_PROCESS_V2_PDFORK) || defined(BOOST_PROCESS_V2_PIPEFORK)
+ // These handles wait on a handle or descriptor, which needs no signal set.
+ BOOST_CHECK_MESSAGE(!ec, ec.message());
+ BOOST_CHECK_EQUAL(code, 42);
+#else
+ // The signal-based handle has nothing to wait on, but wait() still works.
+ BOOST_CHECK_EQUAL(ec, asio::error::operation_not_supported);
+ BOOST_CHECK_EQUAL(proc.wait(), 42);
+#endif
+}
+
+BOOST_AUTO_TEST_SUITE_END();
The CMake part follows boost_process_v2_test_with_target, which links boost_process_v2_test_impl, a target removed in 01c9a5b60f3e25f49e619df34178498e79f463e4. So on develop the CMake test build fails for all tests with a target, this one included; b2 is fine.
- 主要言語
- C++
- スター
- 145
- フォーク
- 151
- PR マージ指標
- 30日以内にマージされた PR はありません
環境構築
このプロジェクトには開発コンテナ、Dockerfile、コントリビューションガイドがありません。まず README を読み、一般的な手順ははじめてのコントリビューションガイドを参照してください。
はじめの一歩
- issue を最後まで読み、次にプロジェクトのコントリビューションガイドを読みます。
- 着手することを issue にコメントします — 二人が同じ作業をするのを防げます。
- リポジトリをフォークし、ブランチを切って変更します。
- issue 番号を参照したプルリクエストを送ります。
boostorg/process のほかの issue
-
難易度 2/5 1〜3時間 初心者へのやさしさ 88/100
-
難易度 2/5 1〜3時間 初心者へのやさしさ 68/100
-
難易度 1/5 1時間未満 初心者へのやさしさ 72/100
-
難易度 1/5 1時間未満 初心者へのやさしさ 68/100
-
難易度 4/5 3〜5日 初心者へのやさしさ 45/100
boostorg/process の issue をすべて見る
似ている issue
-
Mac mini M6 (16 GB): Q2_0 streaming works - measured 11.7->27.2 tok/s + arena fix for sub-32 GB Macsオープン
難易度 2/5 1〜3時間 初心者へのやさしさ 68/100
メンテナーはふだん 1 日以内に返信
-
champion good first issue remake source/qq
難易度 2/5 1〜3時間 初心者へのやさしさ 65/100
metasequoiaime/msime-windows#1025 ·
メンテナーはふだん 1 日以内に返信
-
backlog bug
難易度 2/5 1〜3時間 初心者へのやさしさ 75/100
EchoTools/nevr-runtime#653 ·
メンテナーはふだん 1 日以内に返信
-
`--fail-require-skip` never fires: run_tests.py searches stdout, but the unittest binary writes the skip summary to stderr対応中かも このイシューにリンクされたプルリクエストがオープン中、またはマージ済みです。 オープン
難易度 2/5 1〜3時間 初心者へのやさしさ 72/100
メンテナーはふだん 1 日以内に返信
-
難易度 2/5 1〜3時間 初心者へのやさしさ 75/100
InfiniTimeOrg/InfiniTime#2492 ·