c++ - Problems with QProcess after fork() and execv() -


i have program launches worker process, waits finish (listens sigchld signal) , launches worker process. inside worker processes launch qprocess calls program. in test case call touch - standard linux command.

i use fork() , execv() launch worker processes.

the problem qprocess finishes in first worker process only. after new worker processes spawned, qprocess never says finished. touch command job fine time. in worker processes except first 1 becomes zombie in end.

here's minimal test program:

#include <qcoreapplication> #include <qprocess> #include <qdebug>  #include <signal.h> #include <wait.h>  void spawnworkerprocess(); void launchqprocess(); void catchsigchild(int i); void execchild();  int main(int argc, char *argv[]) {     qcoreapplication app(argc, argv);      if (argc > 1) // worker process     {         launchqprocess();     }     else // main process     {         if (signal(sigchld, catchsigchild) == sig_err)         {             qfatal("could not attach sigchld");         }          spawnworkerprocess();          return app.exec();     } }  void spawnworkerprocess() {     pid_t pid = fork();     if (pid == -1)     {         qcritical() << "fork error";         exit(1);     }     else if (pid == 0)     {         /* child process */         execchild();         exit(1);     }     else     {         qwarning() << "fork ok";     } }   void execchild() {     unsigned = 0;     const char **argv = new const char *[3];      qbytearray ba = qapp->applicationfilepath().tolocal8bit();     argv[i++] = ba.data();     argv[i++] = "worker";     argv[i++] = 0;      qwarning() << "execv ..."  << argv;     execv(argv[0], const_cast<char *const *>(argv));     qwarning() << "execv ok";      delete[] argv; }  void catchsigchild(int i) {     qcritical() << q_func_info << i;      pid_t cpid;     int stat;      while ((cpid = waitpid(0, &stat, wnohang)) > 0)     {         static int counter = 0;          counter++;          if (counter < 5)         {             qdebug() << "spawn:" << counter;             spawnworkerprocess();         }         else         {             qcritical() << "respawn limit reached! bye-bye!";             exit(0);         }     } } void launchqprocess() {     qprocess pr;      qwarning() << "start qprocess " << qapp->applicationpid();     pr.start(qstring("touch /tmp/test/%1").arg(qapp->applicationpid()), 0);      if (! pr.waitforfinished(3000))     {         qwarning() << "qprocess fail" << qapp->applicationpid() << pr.state() << "\n";          delete (int*) 1; // don't want wait qprocess timeout, doing crash     }     else     {         qwarning() << "qprocess ok" << qapp->applicationpid() << pr.state() << "\n";     } } 

you should never make calls glibc within signal handler. handlers called asynchronously, means can interrupt system calls. calls may not reentrant. learn more this, check following page:

http://www.gnu.org/software/libc/manual/html_node/nonreentrancy.html


Comments

Popular posts from this blog

google api - Incomplete response from Gmail API threads.list -

Installing Android SQLite Asset Helper -

Qt Creator - Searching files with Locator including folder -