1

Is is possible to check if process terminated?

I don't want to call .wait(), because it's blocking, and I want to manage a timeout, after which I will terminate the process.

Now I have the following code:

child c = launch(exec, args, ctx);
auto timeout = boost::posix_time::seconds(3);
boost::this_thread::sleep(timeout);
c.terminate();

but it does not wait for termination and does not check if process temrinated gracefully.

fferri
  • 18,285
  • 5
  • 46
  • 95
  • how about using the [async API](http://www.highscore.de/boost/process0.5/boost_process/tutorial.html#boost_process.tutorial.waiting_for_a_program_to_exit) via boost::asio? – m.s. Feb 12 '16 at 16:58

1 Answers1

2

That's not in boost.process 0.5 (in 0.6 it is) so you'd need to implement it yourself. That can be done like this:

#if defined (BOOST_WINDOWS_API)

template<typename Child>
inline bool is_running(const Child &p, int & exit_code)
{
    DWORD code;
    //single value, not needed in the winapi.
    if (!GetExitCodeProcess(p.proc_info.hProcess, &code))
        throw runtime_error("GetExitCodeProcess() failed");

    if (code == 259) //arbitrary windows constant
        return true;
    else
    {
        exit_code = code;
        return false;
    }    
}

#elif defined(BOOST_POSIX_API)

tempalte<typename Child>
inline bool is_running(const Child&p, int & exit_code)
{
    int status; 
    auto ret = ::waitpid(p.pid, &status, WNOHANG|WUNTRACED);

    if (ret == -1)
    {
        if (errno != ECHILD) //because it no child is running, than this one isn't either, obviously.
            throw std::runtime_error("is_running error");

        return false;
    }
    else if (ret == 0)
        return true;
    else //exited
    {
        if (WIFEXITED(status))
            exit_code = status;
        return false;
    }
}

#endif

Or just use boost.process 0.6, if you have C++11 available.