workermand 4.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191
  1. #!/usr/bin/env php
  2. <?php
  3. error_reporting(E_ALL);
  4. ini_set('display_errors', 'on');
  5. ini_set('limit_memory','512M');
  6. date_default_timezone_set('Asia/Shanghai');
  7. if(empty($argv[1]))
  8. {
  9. echo "Usage: serverd {start|stop|restart|reload|kill|status}\n";
  10. exit;
  11. }
  12. $cmd = $argv[1];
  13. define('WORKERMAN_ROOT_DIR', realpath(__DIR__."/../")."/");
  14. // ==pid-file==
  15. require_once WORKERMAN_ROOT_DIR . 'man/Core/Lib/Config.php';
  16. Man\Core\Lib\Config::instance();
  17. if(!($pid_file = Man\Core\Lib\Config::get('workerman.pid_file')))
  18. {
  19. $pid_file = '/var/run/php-server.pid';
  20. }
  21. define('WORKERMAN_PID_FILE', $pid_file);
  22. // ==log-dir==
  23. if(!($log_dir = Man\Core\Lib\Config::get('workerman.log_dir')))
  24. {
  25. $log_dir = WORKERMAN_ROOT_DIR . 'logs/';
  26. }
  27. define('WORKERMAN_LOG_DIR', $log_dir . '/');
  28. // ==ipc-key==
  29. if(!($ipc_key = Man\Core\Lib\Config::get('workerman.ipc_key')))
  30. {
  31. $ipc_key = 0x70010a2e;
  32. }
  33. define('IPC_KEY', $ipc_key);
  34. // ==shm-size==
  35. if(!($shm_size = Man\Core\Lib\Config::get('workerman.shm_size')))
  36. {
  37. $shm_size = 393216;
  38. }
  39. define('DEFAULT_SHM_SIZE', $shm_size);
  40. require_once WORKERMAN_ROOT_DIR . "man/Core/Master.php";
  41. chdir(WORKERMAN_ROOT_DIR."Core");
  42. //检查pid对应的进程是否存在,不存在删除PID文件
  43. if($cmd != 'status' && is_file(WORKERMAN_PID_FILE))
  44. {
  45. //检查权限
  46. if(!posix_access(WORKERMAN_PID_FILE, POSIX_W_OK))
  47. {
  48. if($stat = stat(WORKERMAN_PID_FILE))
  49. {
  50. if(($start_pwuid = posix_getpwuid($stat['uid'])) && ($current_pwuid = posix_getpwuid(posix_getuid())))
  51. {
  52. exit("\n\033[31;40mServer is started by user {$start_pwuid['name']}, {$current_pwuid['name']} can not $cmd Server, Permission denied\033[0m\n\n\033[31;40mServer $cmd failed\033[0m\n\n");
  53. }
  54. }
  55. exit("Can not $cmd Server, Permission denied\n");
  56. }
  57. //检查pid进程是否存在
  58. if($pid = @file_get_contents(WORKERMAN_PID_FILE))
  59. {
  60. if(false === posix_kill($pid, 0))
  61. {
  62. if(!unlink(WORKERMAN_PID_FILE))
  63. {
  64. exit("Can not $cmd Server\n\n");
  65. }
  66. }
  67. }
  68. }
  69. switch($cmd)
  70. {
  71. case 'start':
  72. $worker_user = isset($argv[2]) ? $argv[2] : '';
  73. Man\Core\Master::run($worker_user);
  74. break;
  75. case 'stop':
  76. $pid = @file_get_contents(WORKERMAN_PID_FILE);
  77. if(empty($pid))
  78. {
  79. exit("Server not running?\n");
  80. }
  81. stop_and_wait();
  82. break;
  83. case 'restart':
  84. stop_and_wait();
  85. $worker_user = isset($argv[2]) ? $argv[2] : '';
  86. Man\Core\Master::run();
  87. break;
  88. case 'reload':
  89. $pid = @file_get_contents(WORKERMAN_PID_FILE);
  90. if(empty($pid))
  91. {
  92. exit("server not running?\n");
  93. }
  94. posix_kill($pid, SIGHUP);
  95. echo "reload PHP-Server\n";
  96. break;
  97. case 'kill':
  98. force_kill();
  99. force_kill();
  100. break;
  101. case 'status':
  102. $address = Man\Core\Lib\Config::get('Monitor.listen');
  103. $sock = @stream_socket_client($address);
  104. if(!$sock)
  105. {
  106. exit("\n\033[31;40mcan not connect to $address \033[0m\n\n\033[31;40mServer not running\033[0m\n\n");
  107. }
  108. fwrite($sock, 'status');
  109. $read_fds = array($sock);
  110. $write_fds = $except_fds = array();
  111. while($ret = stream_select($read_fds, $write_fds, $except_fds, 1))
  112. {
  113. if(!$ret)break;
  114. foreach($read_fds as $fd)
  115. {
  116. if($ret_str = fread($fd, 8192))
  117. {
  118. echo $ret_str;
  119. }
  120. else
  121. {
  122. exit;
  123. }
  124. }
  125. }
  126. break;
  127. default:
  128. echo "Usage: serverd {start|stop|restart|reload|kill|status}\n";
  129. exit;
  130. }
  131. function force_kill()
  132. {
  133. $ret = $match = array();
  134. exec("ps aux | grep -E '".Man\Core\Master::NAME.":|serverd' | grep -v grep", $ret);
  135. $this_pid = posix_getpid();
  136. $this_ppid = posix_getppid();
  137. foreach($ret as $line)
  138. {
  139. if(preg_match("/^[\S]+\s+(\d+)\s+/", $line, $match))
  140. {
  141. $tmp_pid = $match[1];
  142. if($this_pid != $tmp_pid && $this_ppid != $tmp_pid)
  143. {
  144. posix_kill($tmp_pid, SIGKILL);
  145. }
  146. }
  147. }
  148. }
  149. function stop_and_wait($wait_time = 6)
  150. {
  151. $pid = @file_get_contents(WORKERMAN_PID_FILE);
  152. if(empty($pid))
  153. {
  154. //exit("server not running?\n");
  155. }
  156. else
  157. {
  158. $start_time = time();
  159. posix_kill($pid, SIGINT);
  160. while(is_file(WORKERMAN_PID_FILE))
  161. {
  162. clearstatcache();
  163. usleep(1000);
  164. if(time()-$start_time >= $wait_time)
  165. {
  166. force_kill();
  167. force_kill();
  168. unlink(WORKERMAN_PID_FILE);
  169. usleep(500000);
  170. break;
  171. }
  172. }
  173. echo "PHP-Server stoped\n";
  174. }
  175. }