MCPcopy Create free account
hub / github.com/ElementsProject/elements / fork_daemon

Function fork_daemon

src/bitcoind.cpp:50–107  ·  view source on GitHub ↗

Custom implementation of daemon(). This implements the same order of operations as glibc. * Opens a pipe to the child process to be able to wait for an event to occur. * * @returns 0 if successful, and in child process. * >0 if successful, and in parent process. * -1 in case of error (in parent process). * * In case of success, endpoint will be one end of a pipe f

Source from the content-addressed store, hash-verified

48 * which can be used with TokenWrite (in the child) or TokenRead (in the parent).
49 */
50int fork_daemon(bool nochdir, bool noclose, TokenPipeEnd& endpoint)
51{
52 // communication pipe with child process
53 std::optional<TokenPipe> umbilical = TokenPipe::Make();
54 if (!umbilical) {
55 return -1; // pipe or pipe2 failed.
56 }
57
58 int pid = fork();
59 if (pid < 0) {
60 return -1; // fork failed.
61 }
62 if (pid != 0) {
63 // Parent process gets read end, closes write end.
64 endpoint = umbilical->TakeReadEnd();
65 umbilical->TakeWriteEnd().Close();
66
67 int status = endpoint.TokenRead();
68 if (status != 0) { // Something went wrong while setting up child process.
69 endpoint.Close();
70 return -1;
71 }
72
73 return pid;
74 }
75 // Child process gets write end, closes read end.
76 endpoint = umbilical->TakeWriteEnd();
77 umbilical->TakeReadEnd().Close();
78
79#if HAVE_DECL_SETSID
80 if (setsid() < 0) {
81 exit(1); // setsid failed.
82 }
83#endif
84
85 if (!nochdir) {
86 if (chdir("/") != 0) {
87 exit(1); // chdir failed.
88 }
89 }
90 if (!noclose) {
91 // Open /dev/null, and clone it into STDIN, STDOUT and STDERR to detach
92 // from terminal.
93 int fd = open("/dev/null", O_RDWR);
94 if (fd >= 0) {
95 bool err = dup2(fd, STDIN_FILENO) < 0 || dup2(fd, STDOUT_FILENO) < 0 || dup2(fd, STDERR_FILENO) < 0;
96 // Don't close if fd<=2 to try to handle the case where the program was invoked without any file descriptors open.
97 if (fd > 2) close(fd);
98 if (err) {
99 exit(1); // dup2 failed.
100 }
101 } else {
102 exit(1); // open /dev/null failed.
103 }
104 }
105 endpoint.TokenWrite(0); // Success
106 return 0;
107}

Callers 1

AppInitFunction · 0.85

Calls 5

TakeReadEndMethod · 0.80
TakeWriteEndMethod · 0.80
TokenReadMethod · 0.80
TokenWriteMethod · 0.80
CloseMethod · 0.45

Tested by

no test coverage detected