2

Is it possible from a C or C++ Linux program (say /usr/bin/foo), to programmatically launch another program (say /usr/bin/bar), and have foo exit normally and for bar to keep running?

system(3) isn't suitable as it blocks until the other program completes. I'd like something that returns immediately.

The programs are both GUI programs, but I suspect that isn't relevant.

Is there anything in Qt or boost::process that can help?

Is there any common Linux wrapper program I could run through system(3) to achieve this? I tried xdg-open but I don't think it's the right thing.

Basically I want the second program to "detach" from the first, and behave as if the user launched it via the system UI. (On MacOS, for example, there is an open command, so it would be like system("open /usr/bin/bar"))

Andrew Tomazos
  • 66,139
  • 40
  • 186
  • 319
  • 1
    A combination of `fork()` and `execv()` is how it is usually done. Alternatively, you can `system()` it with `&` in the end to run in the background, but that's nasty. – SergeyA Dec 02 '20 at 15:08
  • Since you mention `boost::process` you might want to take a look at [`boost::process::spawn`](https://www.boost.org/doc/libs/1_74_0/doc/html/boost/process/spawn.html) or the class [`boost::process::child`](https://www.boost.org/doc/libs/1_74_0/doc/html/boost/process/child.html) which allows you to set up and create a child process before [detaching](https://www.boost.org/doc/libs/1_74_0/doc/html/boost/process/child.html#idm45349852765600-bb) it. – G.M. Dec 02 '20 at 15:17
  • Since you mentioned Qt, there's [`QProcess::start`](https://doc.qt.io/qt-5/qprocess.html#start) that does this. – rustyx Dec 02 '20 at 15:19
  • @rustyx: Are we sure its ok for the parent process to exit while the process started with `QProcess::start` keeps running? – Andrew Tomazos Dec 02 '20 at 15:24
  • 2
    @rustyx: Maybe `QProcess::startDetached` looks like the right thing. – Andrew Tomazos Dec 02 '20 at 15:25

2 Answers2

1

With Qt, you can use bool QProcess::startDetached(const QString &program, const QStringList &arguments, const QString &workingDirectory = QString(), qint64 *pid = nullptr) as described here https://doc.qt.io/qt-5/qprocess.html#startDetached

Here is a minimal example of how to use it :

#include <QCoreApplication>
#include <QProcess>

int main(int argc, char *argv[])
{
    QCoreApplication a(argc, argv);

    /*
     * starting netstat with args
     * in case the main event loop is exited
     * netstat will be parented to init ( pid 1 ) and continue running
     */
    QProcess::startDetached("/bin/netstat", QStringList() << "-pla" << "-ntuc");

    return a.exec();
}
Fryz
  • 2,119
  • 2
  • 25
  • 45
1

The classic way is using Fork-Exec: https://en.wikipedia.org/wiki/Fork%E2%80%93exec which is available in any Unix derived OS, including Linux. No need to add any library, framework, etc.

cpp19
  • 76
  • 6