PHP - Killing child process starts with pcntl_fork

I use pcntl_fork to start a child process to send email through SMTP.

The child process uses the PEAR Mail package to send e-mail, but the problem is that the remote server is not responding, the process just runs forever, waiting for a response, regardless of any time limit set in php.ini.

To get around this, I use the pcntl_alarm function to run the function after 30 seconds, which kills the child process if it is still running.

function handlesig($sig) { global $pid,$node,$resend; posix_kill($pid,SIGKILL); mysql_query("insert into log (event) values ('Timed out!')"); } 

When I kill a child process, although I remain with a non-existent process in the system.

Is there any other signal I should use that will still cause the child process to die without waiting for the connection (because the connection will never end) and avoid the growth of non-existent processes?

+7
linux php posix
source share
5 answers

You need to either wait as described above or make the child process disconnected from the parent using posix_setsid

+5
source share

If you have zombie children, that means you do not wait for them. Not a PHP expert, but a waitpid(2) system call. e.g. call

 waitpid(-1, NULL, WNOHANG); 

from time to time, or whenever you get SIGCHILD . Each call will get to one zombie. WNOHANG makes him return immediately, and not block if there are no children left.

The wait man page has a nice notes section on how this all works ...

+4
source share

A common solution to this problem is to use a good configured local repeater. I usually do localhost configuration using postfix.

He will then send an email to the local relay, which queues it and sends it to the recipient as soon as possible.

The good thing about sending it to a local relay is that you can configure it for scanned emails and other replies.

For you, the question of nonexistent, as far as I know, SIGKILL is a very tough method for cutting off the process, have you tried (SIGSTOP or SIGTSTP)?

+1
source share
 exec(PATH_TO_PHP . " email_script.php $params > /dev/null 2>&1 &"); 

Thus, the parent does not expect an answer from the child, and you do not have zombies. The email_script.php handles the sending of emails and logs the response to a file that you can parse from your parent script or not.

+1
source share

To complete Peter anwser, look at pcntl_waitpid

Just need to do this after the kill: pcntl_waitpid($pid)

+1
source share

All Articles