main() for the child thread. In * nix everything is not so, because I will talk a little about this system multiprocess. * nixoids can safely skip this part, if they already know everything.pcntl_fork . Oddly enough, she takes no arguments. What to do?pcntl_fork , the script starts schizophrenia: the code seems to be the same, but is executed by two parallel processes. However, if you simply insert the pcntl_fork into the script, you will not see anything visual, except that access to resources conflicts.pcntl_fork returns 0 to the child process and the PID of the child process to the parent. Here is the usual pcntl_fork usage pcntl_fork : $ pid = pcntl_fork ();
if ($ pid == -1) {
//mistake
} elseif ($ pid) {
// parent process gets here
} else {
// and here is a child process
}
// and both processes will get here
pcntl_fork works only in CGI and CLI modes. From under the Apache - it is impossible. Is logical. // create a child process
$ child_pid = pcntl_fork ();
if ($ child_pid) {
// exit the parent console-bound process
exit;
}
// make the main process a child.
// After that, he, too, can produce children.
// The harsh life of these processes ...
posix_setsid ();
while (! $ stop_server) {
// TODO: doing something
}
$ child_processes = array ();
while (! $ stop_server) {
if (! $ stop_server and (count ($ child_processes) <MAX_CHILD_PROCESSES)) {
// TODO: get the task
// fetch child process
$ pid = pcntl_fork ();
if ($ pid == -1) {
// TODO: error - could not create process
} elseif ($ pid) {
// process created
$ child_processes [$ pid] = true;
} else {
$ pid = getmypid ();
// TODO: child process - here is the workload
exit;
}
} else {
// so as not to drive the cycle at idle
sleep (SOME_DELAY);
}
// check if one of the children died
while ($ signaled_pid = pcntl_waitpid (-1, $ status, WNOHANG)) {
if ($ signaled_pid == -1) {
// no children left
$ child_processes = array ();
break;
} else {
unset ($ child_processes [$ signaled_pid]);
}
}
}
kill -SIGKILL . This is bad. This is very bad - SIGKILL will interrupt the processes in the middle. In addition, he can not pass information.SIGTERM - the signal of proper completion of work. // Without this directive, PHP will not intercept signals
declare (ticks = 1);
// Handler
function sigHandler ($ signo) {
global $ stop_server;
switch ($ signo) {
case SIGTERM: {
$ stop_server = true;
break;
}
default: {
// all other signals
}
}
}
// register handler
pcntl_signal (SIGTERM, "sig_handler");
function isDaemonActive ($ pid_file) {
if (is_file ($ pid_file)) {
$ pid = file_get_contents ($ pid_file);
// check for process
if (posix_kill ($ pid, 0)) {
// daemon already running
return true;
} else {
// there is a pid file, but there is no process
if (! unlink ($ pid_file)) {
// I can not destroy the pid-file. mistake
exit (-1);
}
}
}
return false;
}
if (isDaemonActive ('/ tmp / my_pid_file.pid')) {
echo 'Daemon already active';
exit;
}
PID daemon should be written to the pid-file. file_put_contents ('/ tmp / my_pid_file.pid', getmypid ());
Source: https://habr.com/ru/post/40432/
All Articles