我正在运行一个PHP守护进程来进行分析。
启动的php进程加载所有必需的数据,forks本身用于在所有核心上分配工作负载,waits用于分叉的子项完成,并收集子项生成的结果。
由于我与其他用户共享CLI环境,我需要通过将php.ini值注入shell调用来启动xdebug profiling。
$ php -d xdebug.profiler_enable=1 -d xdebug.profiler_output_dir="/home/xxx" daemon.php
生成的cachegrind文件,如何配置父级,因此显示90%的睡眠。
有没有办法在不构建驱动程序的情况下对工作人员进行分析,直接加载它们?
由于
答案 0 :(得分:7)
我遇到了同样的问题并在没有XDebug的情况下解决了。不幸的是,我无法找到XDebug的方法。它不知何故它不关心任何分叉过程。
我解决了使用 Xhprof 分析和 Xhgui 来检查日志。 Xhprof是Facebook内部开发的一个很棒的工具,然后在开源之后发布。 很酷的是,您可以确定何时开始分析以及何时停止。这使您能够解决我们的问题。
首先让我们安装它!
sudo pecl install xhprof-beta
如果您正在使用基于debian的发行版,请确保您还安装了graphviz。
sudo apt-get install graphviz
现在让我们来看看代码。
$children = [];
do {
if (count($children) < $maxConsumers) {
$pid = pcntl_fork();
$children[] = $pid;
if ($pid == -1) {
throw new \RuntimeException('Could not fork process');
} else if ($pid === 0) {
// we are the child
if ($verbose) {
$output->writeln(sprintf('Child here (PID = %s)', posix_getpid()));
}
if ($xhProf) {
// here we enable xhprof thus the profiling starts
xhprof_enable(XHPROF_FLAGS_CPU + XHPROF_FLAGS_MEMORY);
}
// DO YOUR MAGIC HERE!
if ($xhProf) {
// and here we call the xhgui header file that will
// stop xhprof and write all the gathered data into
// mongo or into a dedicated file
require_once('/var/www/xhgui/external/header.php');
}
exit;
} else {
// we are the parent
if ($verbose) {
$output->writeln(sprintf('Parent here (PID = %s) spawned a new child (PID = %s)', posix_getpid(), $pid));
}
}
} else {
if ($verbose) {
$output->writeln(sprintf("Parent - spawned enough children, let's wait them..."));
}
$deadPID = pcntl_wait($status);
$children = array_diff($children, [$deadPID]);
} while (true);
// Waits for all remaining children
while (($pid = pcntl_waitpid(0, $status)) != -1) {
if ($verbose) {
$status = pcntl_wexitstatus($status);
$output->writeln(sprintf("Child (PID %d) terminated. Status is %s.", $pid, $status));
}
}
为了检查日志,您还需要正确配置Xhgui。您可能也需要虚拟主机。
对于所有需要的配置和参考: