- Why do I have to `wait()` for child processes?
- 5 Answers 5
- Linux fork() and wait()
- 4 Answers 4
- Wait for a process to finish
- 15 Answers 15
- To wait for any process to finish
- With timeout (seconds)
- Blocking solution
- Non-blocking solution
- Notes
- Linux child process wait
- 1. Verify that the child process will send a SIGCHLD signal to the parent process when it exits
- 2.The difference between wait() and waitpid()
- Intelligent Recommendation
- Asynchronous wait mode of child process
- Asynchronous wait mode of child process
- Linux signal (1)-asynchronous wait mode of child process
- Asynchronous wait of child process under Linux
- Asynchronous wait for child process
- More Recommendation
- About the child process asynchronous wait mode (SIGCHLD signal)
- Linux-Asynchronous Waiting for Child Process
- The asynchronous waiting mode of the child process-SIGCHLD signal
- Wait for the child process to exit
- Linux system programming 7.wait recycling child process
Why do I have to `wait()` for child processes?
Even though the linux man page for wait 1 explains very well that you need to wait() for child processes for them no to turn into zombies, it does not tell why at all.
I planned my program (which is my first multithreaded one, so excuse my naivity) around a for(;;) ever loop that starts child processes which get exec() ed away and are sure to terminate on their own.
I cannot use wait(NULL) because that makes parallel computation impossible, therefore I’ll probably have to add a process table that stores the child pids and have to use waitpid — not immideately, but after some time has passed — which is a problem, because the running time of the children varies from few microseconds to several minutes. If I use waitpid too early, my parent process will get blocked, when I use it too late, I get overwhelmed by zombies and cannot fork() anymore, which is not only bad for my process, but can cause unexpected problems on the whole system.
I’ll probably have to program some logic of using some maximum number of children and block the parent when that number is reached — but that should be not necessary because most of the children terminate quickly. The other solution that I can think of (creating a two-tiered parent process that spawns concurrent children which in turn concurrently spawn and wait for grandchildren) is too complicated for me right now. Possibly I could also find a non-blocking function to check for the children and use waitpid only when they have terminated.
Nevertheless the question:
Why does Linux keep zombies at all? Why do I have to wait for my children? Is this to enforce discipline on parent processes? In decades of using Linux I have never got anything useful out of zombie processes, I don’t quite get the usefulness of zombies as a «feature».
If the answer is that parent processes need to have a way to find out what happened to their children, then for god’s sake there is no reason to count zombies as normal processes and forbid the creation of non-zombie processes just because there are too many zombies. On the system I’m currently developing for I can only spawn 400 to 500 processes before everything grinds to halt (it’s a badly maintained CentOS system running on the cheapest VServer I could find — but still 400 zombies are less than a few kB of information)
5 Answers 5
I’ll probably have to add a process table that stores the child pids and have to use waitpid — not immideately, but after some time has passed — which is a problem, because the running time of the children varies from few microseconds to several minutes. If I use waitpid too early, my parent process will get blocked
Check out the documentation for waitpid . You can tell waitpid to NOT block (i.e., return immediately if there are no children to reap) using the WNOHANG option. Moreover, you don’t need to give waitpid a PID. You can specify -1 , and it will wait for any child. So calling waitpid as below fits your no-blocking constraint and no-saving-pids constraint:
If you really don’t want to properly handle process creation, then you can give the reaping responsibility to init by forking twice, reaping the child, and giving the exec to the grandchild:
In the above code snippet, the child process forks its own child, immediately exists, and then is immediately reaped by the parent. The grandchild is orphaned, adopted by init , and will be reaped automatically.
Why does Linux keep zombies at all? Why do I have to wait for my children? Is this to enforce discipline on parent processes? In decades of using Linux I have never got anything useful out of zombie processes, I don’t quite get the usefulness of zombies as a «feature». If the answer is that parent processes need to have a way to find out what happened to their children, then for god’s sake there is no reason to count zombies as normal processes and forbid the creation of non-zombie processes just because there are too many zombies.
How else do you propose one may efficiently retrieve the exit code of a process? The problem is that the mapping of PID exit code (et al.) must be one to one. If the kernel released the PID of a process as soon as it exits, reaped or not, and then a new process inherits that same PID and exits, how would you handle storing two codes for one PID? How would an interested process retrieve the exit code for the first process? Don’t assume that no one cares about exit codes simply because you don’t. What you consider to be a nuisance/bug is widely considered useful and clean.
On the system I’m currently developing for I can only spawn 400 to 500 processes before everything grinds to halt (it’s a badly maintained CentOS system running on the cheapest VServer I could find — but still 400 zombies are less than a few kB of information)
Something about making a widely accepted kernel behavior a scapegoat for what are clearly frustrations over a badly-maintained/cheap system doesn’t seem right.
Typically, your maximum number of processes is limited only by your memory. You can see your limit with:
Источник
Linux fork() and wait()
i have one, bad smelling problem 🙁
i have this code:
and output is similar to:
And i think that wait(0) not waiting for all subprocess but only wait for first exit and write all (Exit = . ).
Is any way to do this:
4 Answers 4
Here’s a demo of the easiest way to produce the output in the order you asked for. It uses 3 loops: one to create the child processes, one to wait for them and collect their exit statuses, and one to print the exit statuses.
This isn’t a problem with wait() , it’s a matter of synchronization — or lack thereof. Each time you call fork() , your child process sleeps for awhile, but the parent process continues executing. Your parent process finishes its fork loop and starts its wait loop while most of the children are still sleeping, so each time one of the children exits, the parent is already waiting for it. That’s why the parent process is able to print its exit message immediately after each child exits.
If you want your parent process to wait for all the children to finish sleeping before entering the wait() loop, you’ll need to need to use an IPC synchronization mechanism, such as POSIX semaphores, to make the parent process block until all children have signaled that they’re ready.
However, if your goal is simply to have all the exit messages appear on the screen after the child ID messages, you don’t really need to delay the wait() calls at all. Just change the wait loop to store the status values in an array instead of immediately printing them, and then after the wait loop finishes, run another loop to print the contents of the array.
Источник
Wait for a process to finish
Is there any builtin feature in Bash to wait for a process to finish?
The wait command only allows one to wait for child processes to finish. I would like to know if there is any way to wait for any process to finish before proceeding in any script.
A mechanical way to do this is as follows but I would like to know if there is any builtin feature in Bash.
15 Answers 15
To wait for any process to finish
Darwin (requires that $pid has open files):
With timeout (seconds)
Darwin (requires that $pid has open files):
There’s no builtin. Use kill -0 in a loop for a workable solution:
Or as a simpler oneliner for easy one time usage:
As noted by several commentators, if you want to wait for processes that you do not have the privilege to send signals to, you have find some other way to detect if the process is running to replace the kill -0 $pid call. On Linux, test -d «/proc/$pid» works, on other systems you might have to use pgrep (if available) or something like ps | grep «^$pid » .
I found «kill -0» does not work if the process is owned by root (or other), so I used pgrep and came up with:
This would have the disadvantage of probably matching zombie processes.
This bash script loop ends if the process does not exist, or it’s a zombie.
EDIT: The above script was given below by Rockallite. Thanks!
My orignal answer below works for Linux, relying on procfs i.e. /proc/ . I don’t know its portability:
It’s not limited to shell, but OS’s themselves do not have system calls to watch non-child process termination.
FreeBSD and Solaris have this handy pwait(1) utility, which does exactly, what you want.
I believe, other modern OSes also have the necessary system calls too (MacOS, for example, implements BSD’s kqueue ), but not all make it available from command-line.
From the bash manpage
All these solutions are tested in Ubuntu 14.04:
Solution 1 (by using ps command): Just to add up to Pierz answer, I would suggest:
In this case, grep -vw grep ensures that grep matches only process_name and not grep itself. It has the advantage of supporting the cases where the process_name is not at the end of a line at ps axg .
Solution 2 (by using top command and process name):
Replace process_name with the process name that appears in top -n 1 -b . Please keep the quotation marks.
To see the list of processes that you wait for them to be finished, you can run:
Solution 3 (by using top command and process ID):
Replace process_id with the process ID of your program.
Okay, so it seems the answer is — no, there is no built in tool.
After setting /proc/sys/kernel/yama/ptrace_scope to 0 , it is possible to use the strace program. Further switches can be used to make it silent, so that it really waits passively:
Blocking solution
Use the wait in a loop, for waiting for terminate all processes:
This function will exits immediately, when all processes was terminated. This is the most efficient solution.
Non-blocking solution
Use the kill -0 in a loop, for waiting for terminate all processes + do anything between checks:
The reaction time decreased to sleep time, because have to prevent high CPU usage.
A realistic usage:
Waiting for terminate all processes + inform user about all running PIDs.
Notes
These functions getting PIDs via arguments by $@ as BASH array.
There is no builtin feature to wait for any process to finish.
You could send kill -0 to any PID found, so you don’t get puzzled by zombies and stuff that will still be visible in ps (while still retrieving the PID list using ps ).
Had the same issue, I solved the issue killing the process and then waiting for each process to finish using the PROC filesystem:
Use inotifywait to monitor some file that gets closed, when your process terminates. Example (on Linux):
-e specifies the event to wait for, -q means minimal output only on termination. In this case it will be:
A single wait command can be used to wait for multiple processes:
The output string of inotifywait will tell you, which process terminated. This only works with ‘real’ files, not with something in /proc/
On a system like OSX you might not have pgrep so you can try this appraoch, when looking for processes by name:
The $ symbol at the end of the process name ensures that grep matches only process_name to the end of line in the ps output and not itself.
Rauno Palosaari’s solution for Timeout in Seconds Darwin , is an excellent workaround for a UNIX-like OS that does not have GNU tail (it is not specific to Darwin ). But, depending on the age of the UNIX-like operating system, the command-line offered is more complex than necessary, and can fail:
On at least one old UNIX, the lsof argument +r 1m%s fails (even for a superuser):
The m%s is an output format specification. A simpler post-processor does not require it. For example, the following command waits on PID 5959 for up to five seconds:
In this example, if PID 5959 exits of its own accord before the five seconds elapses, $ returns 1 after five seconds.
It may be worth expressly noting that in +r 1 , the 1 is the poll interval (in seconds), so it may be changed to suit the situation.
Источник
Linux child process wait
We know that when a parent process creates a child process, it is best to call the wait or waitpid function to wait for the child process, otherwise it will generate a zombie process and cause a memory leak. Generally, the parent process has two ways to wait when waiting for the child process. One is blocking waiting, when the parent process cannot handle its own work; the other is non-blocking waiting, the parent process is processing its own work, while Check regularly to see if there are any child processes waiting to be cleaned up.
1. Verify that the child process will send a SIGCHLD signal to the parent process when it exits
Under normal circumstances, the default processing of the parent process receiving this signal is to ignore this signal, that is, it does not do any processing, but we can use the system call API: signal() to customize the processing handle for verification. The specific code is as follows:
Simply analyze the code: the child process sleeps for 3 seconds after printing a sentence and exits. At this time, the parent process uses a for loop to traverse to capture 32 ordinary signals. The theoretical result is that after the child process sleeps for 3 seconds, the parent process sleeps for 5 seconds, and then prints When a signal is received, the results are as follows:
Execute the kill -l command to view all the signals and the results are as follows (obviously the 17th is SIGCHLD):
The result is in line with the theory, so we determine that the child process will send a SIGCHLD signal to the parent process when it is postponed for the parent process to perform related processing, but the parent process ignores this signal by default.
2.The difference between wait() and waitpid()
wait function:
- Used to wait for any child process to exit, called by the parent process.
- Return value: Return the pid of the waiting child process on success, and -1 on failure.
- status: output parameter, get back the exit information of the child process.
- Wait mode: blocking waiting, when the waiting child process does not exit, the parent process never exits.
- Purpose: Reclaim the child process, the system reclaims the space of the child process.
If the parameter status is not empty, the process termination status is stored in it.
According to tradition, the returned integer status word is implementation-defined. Some bits indicate exit status (normal return), other bits indicate signal number (abnormal return), and one bit indicates whether it is generated A core file and so on.
The termination status is the macros defined in sys/wait.h. There are four mutually exclusive macros that can be used to obtain the reason for the process termination.
WIFEXITED: True when returning normally, the macro function WEXITSTATUS can be executed to obtain the lower 8 bits of the parameter that the child process sends to exit, _exit or _Exit.
WIFSIGNALED: True when the exception returns, you can execute the macro function WTERMSIG to obtain the signal number of the child process termination. In addition, for some implementations, the macro WCOREDUMP macro is defined. If the process is terminated by the prosperity core file is true.
WIFSTOPPED: If it is the return state of the currently suspended child process, it is true, and WSTOPSIG can be executed to obtain the signal number that makes the child process pause.
WIFCONTINUED: If the child process that has continued after the job control is suspended returns status, it is true and only used for waitpid.
waitpid:
- pid parameter: It can be seen from the parameter name pid and type pid_t that what is needed here is a process ID. But when pid takes a different value, it has a different meaning here.
- When pid>0, only wait for the child process whose process ID is equal to pid, no matter how many other child processes have run and exit, as long as the specified child process has not ended, waitpid will wait forever.
- When pid=-1, wait for any child process to exit without any restriction. At this time, waitpid and wait have exactly the same functions.
- When the list content pid=0, wait for any child process in the same process group. If the child process has joined another process group, waitpid will not pay any attention to it.
- When pid
Intelligent Recommendation
Asynchronous wait mode of child process
We know that when a parent process creates a child process, it calls wait and waitpid functions to clean up the dead process. The process can block and wait for the end of the subprocess, or it can ch.
Asynchronous wait mode of child process
Wait: There are blocking waiting and non-blocking waiting for waiting. We use non-blocking wait to achieve asynchronous. 1. The SIGCHLD signal will be sent to the parent process when the child process.
Linux signal (1)-asynchronous wait mode of child process
1. Signal A signal (a software interrupt) is a message sent by the user, system, or process to the target process to notify the target process of a state change or system exception. 2. Si.
Asynchronous wait of child process under Linux
The zombie process can be cleaned up by the wait function or waitpid function. The parent process can wait for the child process in two ways, one is blocking and the other is non-blocking. No matter w.
Asynchronous wait for child process
An introduction to wait and waitpiwd wait: pid_t wait(int *status) Once the process calls wait, it immediately blocks itself, and wait automatically analyzes whether a child process of the curren.
More Recommendation
About the child process asynchronous wait mode (SIGCHLD signal)
Related blogs LinuxDown signal (1) http://blog.csdn.NET/double_happiness/article/details/72848372 Signal under Linux (2) http://blog.csdn.Net/double_happiness/article/details/72897148 Zombie process h.
Linux-Asynchronous Waiting for Child Process
1. About process waiting Related blogs: http://blog.csdn.net/rengui1228/article/details/73064852 2. Basic knowledge 1. Various statuses of the process &.
The asynchronous waiting mode of the child process-SIGCHLD signal
Zombie and Orphan Process Let’s learn two processes first: Orphan process: A parent process exits, and one or more of its child processes are still running, then those child processes will become orph.
Wait for the child process to exit
Wait until any child process exits and return the ID of the exiting process If the process has no child processes or all child processes have exited, return directly Must first determine whether the c.
Linux system programming 7.wait recycling child process
wait function: Recycling the child process exits the resource, blocking and reclaiming any one pid_t wait(int*status) Parameters: (outgoing) the status of the recovery process. Return value: Success: .
Источник