Daemon child can't execute library - c++

I am writing a Linux daemon to execute my code. My code makes a call to a third party library. If I execute my code from the parent then everything runs fine, but if I execute my code directly from a child the call to the third party library never returns. And if I create a second executable that executes my code and I have the daemon run the executable then everything runs fine.
Why can't I call my code from the child process?
int main(void)
{
// Our process ID and Session ID
pid_t pid, sid;
fflush(stdout);
// Fork off the parent process
pid = fork();
if (pid < 0)
exit(EXIT_FAILURE);
// If we got a good PID, then we can exit the parent process.
if (pid > 0)
exit(EXIT_SUCCESS);
// Change the file mode mask
umask(0);
// Open any logs here
close(STDIN_FILENO);
close(STDOUT_FILENO);
close(STDERR_FILENO);
if (open("/dev/null",O_RDONLY) == -1)
exit(EXIT_FAILURE);
if (open("/dev/null",O_WRONLY) == -1)
exit(EXIT_FAILURE);
if (open("/dev/null",O_WRONLY) == -1)
exit(EXIT_FAILURE);
// Create a new SID for the child process
sid = setsid();
if (sid < 0)
exit(EXIT_FAILURE);
// Change the current working directory
if ((chdir("/")) < 0)
exit(EXIT_FAILURE);
// doesn't work
MyObject ob;
ob.start();
// works
//execlp("/home/root/NextGenAutoGuidance", "NextGenAutoGuidance", (char*)NULL);
while(1)
{
sleep(60);
}
exit(EXIT_SUCCESS);
}
I have tried putting the object declaration of my object as a global and static global, I have also tried doing a new/delete of my object.
The only way the call to the third party library will return is if my object is started from the parent process.
How can I create the daemon so that I don't have to call an external binary to run correctly?
Edit
I need to add that I have also tried to not kill the parent and I have the same problem.

After many hours of digging I found the cause and solution of my problem.
Cause:
I had a private global static class object in the MyObject class that started a thread that called the third party library.
Because the class object was global it was created before the fork, even though I declared MyObject after the fork. As soon as the static class object was created it started a thread that called the third party library and in the library function it hit a mutex. When you fork threads are not copied, so after the fork the parent process was killed and the child process created a new static class object which started a new thread which called the library function and came to the same mutex. Because the mutex wasn't released by the parent because it was killed before leaving the library function, the child process was stuck waiting for the mutex to be released.
Solution:
Don't create threads on object creation and wait for child to create threads until after the fork.

Related

Use system() to create independent child process

I have written a program where I create a thread in the main and use system() to start another process from the thread. Also I start the same process using the system() in the main function also. The process started from the thread seems to stay alive even when the parent process dies. But the one called from the main function dies with the parent. Any ideas why this is happening.
Please find the code structure below:
void *thread_func(void *arg)
{
system(command.c_str());
}
int main()
{
pthread_create(&thread_id, NULL, thread_func, NULL);
....
system(command.c_str());
while (true)
{
....
}
pthread_join(thread_id, NULL);
return 0;
}
My suggestion is: Don't do what you do. If you want to create an independently running child-process, research the fork and exec family functions. Which is what system will use "under the hood".
Threads aren't really independent the same way processes are. When your "main" process ends, all threads end as well. In your specific case the thread seems to continue to run while the main process seems to end because of the pthread_join call, it will simply wait for the thread to exit. If you remove the join call the thread (and your "command") will be terminated.
There are ways to detach threads so they can run a little more independently (for example you don't have to join a detached thread) but the main process still can't end, instead you have to end the main thread, which will keep the process running for as long as there are detached threads running.
Using fork and exec is actually quite simple, and not very complex:
int pid = fork();
if (pid == 0)
{
// We are in the child process, execute the command
execl(command.c_str(), command.c_str(), nullptr);
// If execl returns, there was an error
std::cout << "Exec error: " << errno << ", " << strerror(errno) << '\n';
// Exit child process
exit(1);
}
else if (pid > 0)
{
// The parent process, do whatever is needed
// The parent process can even exit while the child process is running, since it's independent
}
else
{
// Error forking, still in parent process (there are no child process at this point)
std::cout << "Fork error: " << errno << ", " << strerror(errno) << '\n';
}
The exact variant of exec to use depends on command. If it's a valid path (absolute or relative) to an executable program then execl works well. If it's a "command" in the PATH then use execlp.
There are two points here that I think you've missed:
First, system is a synchronous call. That means, your program (or, at least, the thread calling system) waits for the child to complete. So, if your command is long-running, both your main thread and your worker thread will be blocked until it completes.
Secondly, you are "joining" the worker thread at the end of main. This is the right thing to do, because unless you join or detach the thread you have undefined behaviour. However, it's not what you really intended to do. The end result is not that the child process continues after your main process ends... your main process is still alive! It is blocked on the pthread_join call, which is trying to wrap up the worker thread, which is still running command.
In general, assuming you wish to spawn a new process entirely unrelated to your main process, threads are not the way to do it. Even if you were to detach your thread, it still belongs to your process, and you are still required to let it finish before your process terminates. You can't detach from the process using threads.
Instead, you'll need OS features such as fork and exec (or a friendly C++ wrapper around this functionality, such as Boost.Subprocess). This is the only way to truly spawn a new process from within your program.
But, you can cheat! If command is a shell command, and your shell supports background jobs, you could put & at the end of the command (this is an example for Bash syntax) to make the system call:
Ask the shell to spin off a new process
Wait for it to do that
The new process will now continue to run in the background
For example:
const std::string command = "./myLongProgram &";
// ^
However, again, this is kind of a hack and proper fork mechanisms that reside within your program's logic should be preferred for maximum portability and predictability.

Child process is able to change parent epoll state

I am trying to figure out why a child process is able to change a parent epoll state.
I have program that declare a static epoll object (an object that wraps epoll):
static EventManager* evMgrPtr = NULL;
The parent process initialized it and use it to watch a listening socket (The parent is basically a daemon that occasionally need to respond to health check request by accepting these request through the listening socket).
The children does totally different thing, however, the program DOES NOT do a fork/exec, rather, the children carry on and run a piece of code in the same translation unit.
pid_t pid = fork();
switch(pid) {
case -1:
YREPL_LOG_FATAL("Couldn't start server process ");
exit(EXIT_OK);
case 0:
#ifndef __FreeBSD__
assert( closeThisFd != -1 );
evMgr.unregisterSocketEvent( closeThisFd );
close( closeThisFd );
#endif
close(outpipe[0]);
close(errpipe[0]);
dup2(outpipe[1], 1);
dup2(errpipe[1], 2);
close(outpipe[1]);
close(errpipe[1]);
The problem is that after I do evMgrPtr->unregisterSocketEvent( closeThisFd ) in the child process, I found out the parent stop watching for the listening socket as well!!!
Can anyone shed some light on why this is happening. I thought once a fork is executed the parent and children will do COW. So whatever children does to its copy of the epoll object should not get reflected in the parent right?
It seems that you use EPOLL-based event loop. So, since file descriptor for epoll-object itself is shared between child and parent, removing file descriptor from epoll()-based descriptor in child also affects parent process :). Please read man epoll, man epoll_create.

Waiting in Background process in C program in Unix

Im trying to emulate shell through C program. In my program whenever I run any normal (foreground) commands it works fine. Also I have handled background process with commands ending with '&'. Now to handle this I have avoided the parent waiting for a child process.
The problem is whenever for the first time in my shell I run any background command(i.e ending in '&') then it works fine. But then after that each command(normal) doesnot terminate. I guess it waits for the previously opened process. How to rectify. Please you can ask questions so that i can make myself more clear to you. This is the snippet which is doing the above mentioned task.
child_id=fork();
if(child_id==0){
//logic fo creating command
int ret=execvp(subcomm[0],subcomm);
}
//Child will never come here if execvp executed successfully
if(proc_sate!='&'){
for(i=0;i<count_pipe+1;i++){
waitpid(0,&flag,0);
}
//something to add to make it not wait for other process in my scenario for second time
}
Here proc_state just determines whether it is background or foreground.It is just a character. count_pipe is just a variable holding number of pipes (e.g ls -l|wc|wc this contains 2 pipes). Dont worry this all is working fine.
waitpid(0, &flag, 0) waits for any child process whose process group ID is equal to that of your shell. So if you have not called setsid() after the fork() of the disconnected child process, the code above will wait for that too.
pid_t pid = fork();
if (pid == 0) { /* child process */
setsid(); /* Child creates new process group */
... /* redirections, etc */
execvp(...);
}

c++ fork() & execl() dont wait, detach completely

So I have a simple fork and exec program. It works pretty good but I want to be able to detach the process that is started, I try a fork with no wait:
if((pid = fork()) < 0)
perror("Error with Fork()");
else if(pid > 0) {
return "";
}
else {
if(execl("/bin/bash", "/bin/bash", "-c", cmddo, (char*) 0) < 0) perror("execl()");
exit(0);
}
It starts the proc fine but when my main app is closed - so is my forked proc.
How do I keep the forked process running after the main proc (that started it) closes?
Thanks :D
Various things to do if you want to start a detached/daemon process:
fork again and exit the first child (so the second child process no longer has the original process as its parent pid)
call setsid(2) to get a new session and process group
reopen stdin/stdout/stderr to dereference the controlling tty, if there was one. Or, for example, you might have inherited a pipe stdout that will be broken and give you SIGPIPE if you try to write it.
chdir to / to get away from the ancestor's current directory
Probably all you really want is to ignore SIGHUP in your fork()ed process as this is normally the one which brings the program down. That is, what you need to do is
signal(SIGHUP, SIG_IGN);
Using nohup arranges for a reader to be present which would avoid possibly writing to close pipe. To avoid this you could either arrange for standard outputs not to be available or to also ignore SIGPIPE. There are a number of signals which terminate your program when not ignore (see man signal; some signals can't be ignored) but the one which will be sent to the child is is SIGHUP.

child waiting for another child

is there a way for a forked child to examine another forked child so that, if the other forked child takes more time than usual to perform its chores, the first child may perform predefined steps?
if so, sample code will be greatly appreciated.
Yes. Simply fork the process to be watched, from the process to watch it.
if (fork() == 0) {
// we are the watcher
pid_t watchee_pid = fork();
if (watchee_pid != 0) {
// wait and/or handle timeout
int status;
waitpid(watchee_pid, &status, WNOHANG);
} else {
// we're being watched. do stuff
}
} else {
// original process
}
To emphasise: There are 3 processes. The original, the watcher process (that handles timeout etc.) and the actual watched process.
To do this, you'll need to use some form of IPC, and named shared memory segments makes perfect sense here. Your first child could read a value in a named segment which the other child will set once it has completed it's work. Your first child could set a time out and once that time out expires, check for the value - if the value is not set, then do what you need to do.
The code can vary greatly depending on C or C++, you need to select which. If C++, you can use boost::interprocess for this - which has lots of examples of shared memory usage. If C, then you'll have to put this together using native calls for your OS - again this should be fairly straightforward - start at shmget()
This is some orientative code that could help you to solve the problem in a Linux environment.
pid_t pid = fork();
if (pid == -1) {
printf("fork: %s", strerror(errno));
exit(1);
} else if (pid > 0) {
/* parent process */
int i = 0;
int secs = 60; /* 60 secs for the process to finish */
while(1) {
/* check if process with pid exists */
if (exist(pid) && i > secs) {
/* do something accordingly */
}
sleep(1);
i++;
}
} else {
/* child process */
/* child logic here */
exit(0);
}
... those 60 seconds are not very strict. you could better use a timer if you want more strict timing measurement. But if your system doesn't need critical real time processing should be just fine like this.
exist(pid) refers to a function that you should have code that looks into proc/pid where pid is the process id of the child process.
Optionally, you can implement the function exist(pid) using other libraries designed to extract information from the /proc directory like procps
The only processes you can wait on are your own direct child processes - not siblings, not your parent, not grandchildren, etc. Depending on your program's needs, Matt's solution may work for you. If not, here are some other alternatives:
Forget about waiting and use another form of IPC. For robustness, it needs to be something where unexpected termination of the process you're waiting on results in your receiving an event. The best one I can think of is opening a pipe which both processes share, and giving the writing end of the pipe to the process you want to wait for (make sure no other processes keep the writing end open!). When the process holding the writing end terminates, it will be closed, and the reading end will then indicate EOF (read will block on it until the writing end is closed, then return a zero-length read).
Forget about IPC and use threads. One advantage of threads is that the atomicity of a "process" is preserved. It's impossible for individual threads to be killed or otherwise terminate outside of the control of your program, so you don't have to worry about race conditions with process ids and shared resource allocation in the system-global namespace (IPC objects, filenames, sockets, etc.). All synchronization primitives exist purely within your process's address space.