Hacktoberfest 2026:维护者为十月标记出来的 issue,仍然开放、适合新手。 浏览 Hacktoberfest issue

v2: BOOST_PROCESS_V2_DISABLE_SIGNALSET does not compile with the signal-based process handle

未关闭
#568 1 条评论 0 个 reaction 已指派 0 人 在 GitHub 查看

还没有人认领这个 Issue。

评估

难度
3/5
预计耗时
半天
新手友好度
62/100
Issue 类型
缺陷
描述清晰度
描述清楚
活跃度
活跃
技术栈
cmake, cpp
领域
backend

调研方向

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,通用步骤见我们的新手贡献指南。

从这里开始

  1. 先读完整个 Issue,再读项目的贡献指南。
  2. 在 Issue 下留言说明你要接手 —— 这能避免两个人做同样的事。
  3. Fork 仓库,在一个分支上完成修改。
  4. 提交 Pull Request,并在描述里引用这个 Issue 编号。

boostorg/process 的其他 Issue

查看 boostorg/process 的全部 Issue

相似的 Issue

更多 C++ Issue

把新 issue 发到你的邮箱

精选适合新手参与的 GitHub issue 摘要。