Tweak INSTALL text
[oweals/busybox.git] / miscutils / setsid.c
index 127adf6f2822cc1bedfd6d4f99e1b51e3742389c..ad2c8a4de5bed83edbdd9374aa6e05a2a4ed1ba8 100644 (file)
  * - busyboxed
  */
 
+//usage:#define setsid_trivial_usage
+//usage:       "PROG ARGS"
+//usage:#define setsid_full_usage "\n\n"
+//usage:       "Run PROG in a new session. PROG will have no controlling terminal\n"
+//usage:       "and will not be affected by keyboard signals (Ctrl-C etc).\n"
+//usage:       "See setsid(2) for details."
+
 #include "libbb.h"
 
 int setsid_main(int argc, char **argv) MAIN_EXTERNALLY_VISIBLE;
@@ -25,11 +32,25 @@ int setsid_main(int argc UNUSED_PARAM, char **argv)
        /* setsid() is allowed only when we are not a process group leader.
         * Otherwise our PID serves as PGID of some existing process group
         * and cannot be used as PGID of a new process group. */
-       if (getpgrp() == getpid())
-               forkexit_or_rexec(argv);
+       if (setsid() < 0) {
+               pid_t pid = fork_or_rexec(argv);
+               if (pid != 0) {
+                       /* parent */
+                       /* TODO:
+                        * we can waitpid(pid, &status, 0) and then even
+                        * emulate exitcode, making the behavior consistent
+                        * in both forked and non forked cases.
+                        * However, the code is larger and upstream
+                        * does not do such trick.
+                        */
+                       exit(EXIT_SUCCESS);
+               }
 
-       setsid();  /* no error possible */
+               /* child */
+               /* now there should be no error: */
+               setsid();
+       }
 
-       BB_EXECVP(argv[1], argv + 1);
-       bb_simple_perror_msg_and_die(argv[1]);
+       argv++;
+       BB_EXECVP_or_die(argv);
 }