|
Boost-Commit : |
Subject: [Boost-commit] svn:boost r66258 - in sandbox/SOC/2010/process: boost/process/detail libs/process/test libs/process/test/util
From: boris_at_[hidden]
Date: 2010-10-29 18:22:07
Author: bschaeling
Date: 2010-10-29 18:22:04 EDT (Fri, 29 Oct 2010)
New Revision: 66258
URL: http://svn.boost.org/trac/boost/changeset/66258
Log:
Fixed bug in worker thread of status service and added test case
Text files modified:
sandbox/SOC/2010/process/boost/process/detail/basic_status_service.hpp | 21 +++++++++++-------
sandbox/SOC/2010/process/boost/process/detail/status_impl.hpp | 5 +++
sandbox/SOC/2010/process/libs/process/test/util/boost.hpp | 1
sandbox/SOC/2010/process/libs/process/test/util/helpers.cpp | 16 ++++++++++++++
sandbox/SOC/2010/process/libs/process/test/wait.cpp | 45 ++++++++++++++++++++++++++++++++++++++++
5 files changed, 79 insertions(+), 9 deletions(-)
Modified: sandbox/SOC/2010/process/boost/process/detail/basic_status_service.hpp
==============================================================================
--- sandbox/SOC/2010/process/boost/process/detail/basic_status_service.hpp (original)
+++ sandbox/SOC/2010/process/boost/process/detail/basic_status_service.hpp 2010-10-29 18:22:04 EDT (Fri, 29 Oct 2010)
@@ -186,10 +186,11 @@
else
{
boost::unique_lock<boost::mutex> lock(work_thread_mutex_);
+ bool regchild = false;
for (typename std::vector<implementation_type>::iterator it =
impls_.begin(); it != impls_.end(); ++it)
- (*it)->complete(pid, status);
- if (--pids_ == 0)
+ regchild |= (*it)->complete(pid, status);
+ if (regchild && --pids_ == 0)
{
work_.reset();
break;
@@ -220,14 +221,18 @@
BOOST_PROCESS_THROW_LAST_SYSTEM_ERROR(
"GetExitCodeProcess() failed");
boost::unique_lock<boost::mutex> lock(work_thread_mutex_);
+ bool regchild = false;
for (std::vector<implementation_type>::iterator it =
impls_.begin(); it != impls_.end(); ++it)
- (*it)->complete(handle, exit_code);
- std::vector<HANDLE>::iterator it = handles_.begin();
- std::advance(it, res - WAIT_OBJECT_0);
- handles_.erase(it);
- if (handles_.size() == 1)
- work_.reset();
+ regchild |= (*it)->complete(handle, exit_code);
+ if (regchild)
+ {
+ std::vector<HANDLE>::iterator it = handles_.begin();
+ std::advance(it, res - WAIT_OBJECT_0);
+ handles_.erase(it);
+ if (handles_.size() == 1)
+ work_.reset();
+ }
}
}
#endif
Modified: sandbox/SOC/2010/process/boost/process/detail/status_impl.hpp
==============================================================================
--- sandbox/SOC/2010/process/boost/process/detail/status_impl.hpp (original)
+++ sandbox/SOC/2010/process/boost/process/detail/status_impl.hpp 2010-10-29 18:22:04 EDT (Fri, 29 Oct 2010)
@@ -161,10 +161,12 @@
ops_.insert(ph, new wrapped_handler<Handler>(handler));
}
- void complete(phandle ph, int exit_code)
+ bool complete(phandle ph, int exit_code)
{
boost::iterator_range<operations_type::iterator> r =
ops_.equal_range(ph);
+ if (r.begin() == r.end())
+ return false;
for (operations_type::iterator it = r.begin(); it != r.end(); ++it)
(*it->second)(exit_code);
ops_.erase(r.begin(), r.end());
@@ -172,6 +174,7 @@
if (!CloseHandle(ph))
BOOST_PROCESS_THROW_LAST_SYSTEM_ERROR("CloseHandle() failed");
#endif
+ return true;
}
private:
Modified: sandbox/SOC/2010/process/libs/process/test/util/boost.hpp
==============================================================================
--- sandbox/SOC/2010/process/libs/process/test/util/boost.hpp (original)
+++ sandbox/SOC/2010/process/libs/process/test/util/boost.hpp 2010-10-29 18:22:04 EDT (Fri, 29 Oct 2010)
@@ -19,6 +19,7 @@
#include <boost/test/included/unit_test.hpp>
#include <boost/filesystem.hpp>
#include <boost/asio.hpp>
+#include <boost/thread.hpp>
#include <boost/bind.hpp>
#include <boost/ref.hpp>
#include <boost/lexical_cast.hpp>
Modified: sandbox/SOC/2010/process/libs/process/test/util/helpers.cpp
==============================================================================
--- sandbox/SOC/2010/process/libs/process/test/util/helpers.cpp (original)
+++ sandbox/SOC/2010/process/libs/process/test/util/helpers.cpp 2010-10-29 18:22:04 EDT (Fri, 29 Oct 2010)
@@ -14,6 +14,7 @@
#include <boost/process/config.hpp>
#if defined(BOOST_POSIX_API)
+# include <unistd.h>
# include <stdlib.h>
#elif defined(BOOST_WINDOWS_API)
# include <windows.h>
@@ -23,6 +24,7 @@
#include <boost/process/detail/systembuf.hpp>
#include <boost/filesystem.hpp>
+#include <boost/lexical_cast.hpp>
#include <iostream>
#include <string>
#include <cstdlib>
@@ -69,6 +71,19 @@
return EXIT_SUCCESS;
}
+int h_wait_exit(int argc, char *argv[])
+{
+ int sec = boost::lexical_cast<int>(argv[1]);
+
+#if defined(BOOST_POSIX_API)
+ sleep(sec);
+#elif defined(BOOST_WINDOWS_API)
+ Sleep(sec * 1000);
+#endif
+
+ return EXIT_SUCCESS;
+}
+
int h_is_closed_stdin(int argc, char *argv[])
{
std::string word;
@@ -243,6 +258,7 @@
{ "echo-stdout-stderr", h_echo_stdout_stderr, 2, "message" },
{ "exit-failure", h_exit_failure, 1, "" },
{ "exit-success", h_exit_success, 1, "" },
+ { "wait-exit", h_wait_exit, 2, "integer" },
{ "is-closed-stdin", h_is_closed_stdin, 1, "" },
{ "is-closed-stdout", h_is_closed_stdout, 1, "" },
{ "is-closed-stderr", h_is_closed_stderr, 1, "" },
Modified: sandbox/SOC/2010/process/libs/process/test/wait.cpp
==============================================================================
--- sandbox/SOC/2010/process/libs/process/test/wait.cpp (original)
+++ sandbox/SOC/2010/process/libs/process/test/wait.cpp 2010-10-29 18:22:04 EDT (Fri, 29 Oct 2010)
@@ -130,6 +130,51 @@
ioservice.run();
}
+void start_child()
+{
+ std::vector<std::string> args;
+ args.push_back("wait-exit");
+ args.push_back("1");
+
+ bp::child c = bp::create_child(get_helpers_path(), args);
+ c.wait();
+}
+
+void handler2(boost::system::error_code ec, int exit_code, bool &called)
+{
+ called = true;
+ BOOST_REQUIRE_EQUAL(ec, boost::system::error_code());
+#if defined(BOOST_POSIX_API)
+ BOOST_REQUIRE(WIFEXITED(exit_code));
+ BOOST_CHECK_EQUAL(WEXITSTATUS(exit_code), EXIT_SUCCESS);
+#elif defined(BOOST_WINDOWS_API)
+ BOOST_CHECK_EQUAL(exit_code, EXIT_SUCCESS);
+#endif
+}
+
+BOOST_AUTO_TEST_CASE(test_status_sync_and_async_wait)
+{
+ check_helpers();
+
+ bool called = false;
+
+ ba::io_service ioservice;
+ bp::status s(ioservice);
+
+ std::vector<std::string> args;
+ args.push_back("wait-exit");
+ args.push_back("2");
+
+ bp::child c = bp::create_child(get_helpers_path(), args);
+ s.async_wait(c.get_id(), boost::bind(handler2, _1, _2, boost::ref(called)));
+
+ boost::thread(start_child);
+
+ ioservice.run();
+
+ BOOST_CHECK_EQUAL(called, true);
+}
+
BOOST_AUTO_TEST_CASE(test_status_async_wait_shutdown)
{
check_helpers();
Boost-Commit list run by bdawes at acm.org, david.abrahams at rcn.com, gregod at cs.rpi.edu, cpdaniel at pacbell.net, john at johnmaddock.co.uk