I created a simple Process class that mimics std::thread. It is supposed to work on linux only.
struct Process
{
Process(/*...*/) { /* fork + join, initialize m_pid */ }
~Process() { assert(!joinable()); }
bool joinable() const { return m_pid != 0; }
void join()
{
assert (joinable());
int status;
waitpid(m_pid, &status, 0);
m_pid = 0;
}
private:
std::atomic<pid_t> m_pid;
};
I have an additional requirement: I need to be able to stop the process from another thread.
For example:
Process p(/* ... */ );
Thread 1:
p.join();
Thread 2:
p.interrupt();
How can I implement a thread-safe Process:interrupt? My first idea is something like this:
void Process::interrupt()
{
if (m_pid)
kill(m_pid, SIGTERM);
}
Unfortunately I am not sure that this works, because if interrupt is called between waitpid and m_pid = 0 in join() then I am killing a non-existent process, or worse a completely unrelated process that happen to have the same pid as the old one.
Swapping the m_pid = 0 and waitpid statements in join() would make the interruption quite useless, since you can expect that the first thread will spend most of its time inside waiting for the child process to terminate.
So what I need is a waitpid that waits for the child process termination but keeps the child process in a zombie state, so that no process with the same pid can be spawn in the meantime.
Is there such a thing or any other solution?
Aucun commentaire:
Enregistrer un commentaire