public function start()
 {
     if (!ProcessContainer::dup2_available()) {
         $cmd = "{$this->process_path} {$this->process_params}";
         if ($this->is_php) {
             $cmd = "{$this->php_path} {$cmd}";
         }
         $descriptorspec = array(0 => array("pipe", "r"), 1 => array("pipe", "w"), 2 => array("pipe", "w"));
         $process = proc_open($cmd, $descriptorspec, $pipes, dirname($this->process_path));
         if (!is_resource($process)) {
             return FALSE;
         }
         $status = proc_get_status($process);
         $this->process_pid = $status['pid'];
         // 关闭输入
         fclose($pipes[0]);
         $this->process_stdout = $pipes[1];
         $this->process_stderr = $pipes[2];
         $this->process = $process;
         return TRUE;
     } else {
         $pipes = array(1 => $this->pipe_open('w+'), 2 => $this->pipe_open('w+'));
         // 利用 dup2 重定向管道
         $pid = pcntl_fork();
         if ($pid == -1) {
             return FALSE;
         } else {
             if ($pid) {
                 $this->process_pid = $pid;
                 $this->process_stdout = $pipes[1];
                 $this->process_stderr = $pipes[2];
                 return TRUE;
             }
         }
         // 子进程
         if ($this->child_init_handler) {
             call_user_func($this->child_init_handler);
         }
         $params = explode(' ', $this->process_params);
         if ($this->is_php) {
             $path = $this->php_path;
             array_unshift($params, $this->process_path);
         } else {
             $path = $this->process_path;
         }
         chdir(dirname($this->process_path));
         //fildes_dup2(fildes_fileno($pipes[0]), fildes_fileno(STDIN));
         fildes_dup2(fildes_fileno($pipes[1]), fildes_fileno(STDOUT));
         fildes_dup2(fildes_fileno($pipes[2]), fildes_fileno(STDERR));
         pcntl_exec($path, $params);
         exit;
     }
 }
 public function run()
 {
     if ($this->socket) {
         return TRUE;
     }
     if (!$this->listen()) {
         return FALSE;
     }
     if (!$this->init_shm()) {
         return FALSE;
     }
     if (!$this->init_config()) {
         return FALSE;
     }
     if ($this->event_handlers['server_inited']) {
         foreach ($this->event_handlers['server_inited'] as $handler) {
             if (!call_user_func($handler)) {
                 return FALSE;
             }
         }
     }
     // 关闭终端输出
     $this->server_muted = TRUE;
     if (function_exists('fildes_dup2')) {
         $errorlog_path = $this->log_path . '/server/error';
         if (!is_dir($errorlog_path)) {
             mkdir($errorlog_path, 0777);
         }
         $errorlog_fd = fopen($errorlog_path . '/error.log', 'a+');
         fildes_dup2(fildes_fileno($errorlog_fd), fildes_fileno(STDERR));
     }
     return $this->loop();
 }