我有一段PHP代码,它是一个非常基本的UDP服务器。问题是它有内存泄漏让我疯了。
事实/意见: - 如果只是自己启动,脚本将耗尽内存。 - 当我输出内存使用量或while循环中的任何文本时,它不会崩溃并显示一致的内存使用情况。 - 但是,当客户端连接到服务器时,while循环的每次迭代都会消耗额外的96字节内存,直到崩溃为止。客户甚至不需要发送数据。实际上,大多数迭代都是由process()函数中的第一个IF语句(如果缓冲区为空)处理,后跟返回。 - 为脚本/进程分配更多内存只会将不可避免的崩溃延迟一段时间。 - 从CentOS 6上的PHP5.3.3升级到5.4无济于事。
任何帮助或指示都将不胜感激!
<?php
ini_set( 'display_errors', true );
class UDP_Server {
protected $_socket = null;
protected $_host = '';
protected $_port = 0;
protected $_clients = array();
protected $_debug = false;
public function __construct( $host = '', $port = 0 ) {
$this->_host = $host;
$this->_port = $port;
$this->_socket = $this->_create_udp_server( $host, $port );
}
public function set_debug( $value = false ) {
$this->_debug = $value;
}
public function process() {
$buffer = stream_socket_recvfrom( $this->_socket, 1024, 0, $remote_host );
if( empty( $buffer ) ) {
return;
}
if( $this->_debug ) {
echo $remote_host, ': ', $buffer, "\n";
}
if( strpos( $buffer, 'udp.register.ip' ) !== false ) {
if( ! in_array( $remote_host, $this->_clients ) ) {
$this->_clients[] = $remote_host;
}
stream_socket_sendto( $this->_socket, 'udp.register.complete', 0, $remote_host );
return;
}
foreach( $this->_clients as $client ) {
if( $client === $remote_host ) {
continue;
}
stream_socket_sendto( $this->_socket, $buffer, 0, $client );
}
}
public function __destruct() {
fclose( $this->_socket );
}
protected static function _create_udp_server( $host = '0.0.0.0', $port = 0 ) {
$address = 'udp://' . $host . ':' . $port;
$socket = stream_socket_server( $address, $error_number, $error_message, STREAM_SERVER_BIND );
if( ! $socket ) {
die( 'could not create UDP server for ' . $address . '; Reason: [' . $error_number . '] - ' . $error_message );
}
stream_set_blocking( $socket, 0 );
return $socket;
}
}
$at_data_server = new UDP_Server( '0.0.0.0', 5556 );
$at_data_server->set_debug( true );
while( 1 ) {
$at_data_server->process();
}
答案 0 :(得分:0)
您的代码似乎符合此错误报告中的条件 - https://bugs.php.net/bug.php?id=71613
如果可能,请避免使用stream_socket_recvfrom()
的第四个参数。