mirror of
https://github.com/pmmp/PocketMine-MP.git
synced 2025-07-06 01:51:51 +00:00
backport a753c1342: Clean up Query cache handling, remove useless timeouts
the timeout was entirely useless, because: - when shorter than 25.6 seconds (512 ticks) it would cause caches to be needlessly destroyed and regenerated - when longer than 25.6 seconds, just made outdated caches persist for longer, even after the query info was regenerated. This now uses a mark-dirty model to deal with caches, which means that plugin modifications to the query data will be reflected immediately, regardless of when they are made. Previously, modifying the result of Server->getQueryInformation() would have inconsistent results.
This commit is contained in:
parent
dbf4054b1f
commit
60b183b0d9
@ -1719,7 +1719,7 @@ class Server{
|
|||||||
|
|
||||||
register_shutdown_function([$this, "crashDump"]);
|
register_shutdown_function([$this, "crashDump"]);
|
||||||
|
|
||||||
$this->queryRegenerateTask = new QueryRegenerateEvent($this, 5);
|
$this->queryRegenerateTask = new QueryRegenerateEvent($this);
|
||||||
|
|
||||||
$this->pluginManager->loadPlugins($this->pluginPath);
|
$this->pluginManager->loadPlugins($this->pluginPath);
|
||||||
|
|
||||||
@ -2591,10 +2591,7 @@ class Server{
|
|||||||
}
|
}
|
||||||
|
|
||||||
if(($this->tickCounter & 0b111111111) === 0){
|
if(($this->tickCounter & 0b111111111) === 0){
|
||||||
($this->queryRegenerateTask = new QueryRegenerateEvent($this, 5))->call();
|
($this->queryRegenerateTask = new QueryRegenerateEvent($this))->call();
|
||||||
if($this->queryHandler !== null){
|
|
||||||
$this->queryHandler->regenerateInfo();
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if($this->autoSave and ++$this->autoSaveTicker >= $this->autoSaveTicks){
|
if($this->autoSave and ++$this->autoSaveTicker >= $this->autoSaveTicks){
|
||||||
|
@ -35,8 +35,6 @@ use function substr;
|
|||||||
class QueryRegenerateEvent extends ServerEvent{
|
class QueryRegenerateEvent extends ServerEvent{
|
||||||
public const GAME_ID = "MINECRAFTPE";
|
public const GAME_ID = "MINECRAFTPE";
|
||||||
|
|
||||||
/** @var int */
|
|
||||||
private $timeout;
|
|
||||||
/** @var string */
|
/** @var string */
|
||||||
private $serverName;
|
private $serverName;
|
||||||
/** @var bool */
|
/** @var bool */
|
||||||
@ -68,13 +66,16 @@ class QueryRegenerateEvent extends ServerEvent{
|
|||||||
/** @var array */
|
/** @var array */
|
||||||
private $extraData = [];
|
private $extraData = [];
|
||||||
|
|
||||||
|
/** @var string|null */
|
||||||
|
private $longQueryCache = null;
|
||||||
|
/** @var string|null */
|
||||||
|
private $shortQueryCache = null;
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @param Server $server
|
* @param Server $server
|
||||||
* @param int $timeout
|
|
||||||
*/
|
*/
|
||||||
public function __construct(Server $server, int $timeout = 5){
|
public function __construct(Server $server){
|
||||||
$this->timeout = $timeout;
|
|
||||||
$this->serverName = $server->getMotd();
|
$this->serverName = $server->getMotd();
|
||||||
$this->listPlugins = $server->getProperty("settings.query-plugins", true);
|
$this->listPlugins = $server->getProperty("settings.query-plugins", true);
|
||||||
$this->plugins = $server->getPluginManager()->getPlugins();
|
$this->plugins = $server->getPluginManager()->getPlugins();
|
||||||
@ -98,19 +99,25 @@ class QueryRegenerateEvent extends ServerEvent{
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Gets the min. timeout for Query Regeneration
|
* @deprecated
|
||||||
*
|
*
|
||||||
* @return int
|
* @return int
|
||||||
*/
|
*/
|
||||||
public function getTimeout() : int{
|
public function getTimeout() : int{
|
||||||
return $this->timeout;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* @deprecated
|
||||||
* @param int $timeout
|
* @param int $timeout
|
||||||
*/
|
*/
|
||||||
public function setTimeout(int $timeout) : void{
|
public function setTimeout(int $timeout) : void{
|
||||||
$this->timeout = $timeout;
|
|
||||||
|
}
|
||||||
|
|
||||||
|
private function destroyCache() : void{
|
||||||
|
$this->longQueryCache = null;
|
||||||
|
$this->shortQueryCache = null;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -125,6 +132,7 @@ class QueryRegenerateEvent extends ServerEvent{
|
|||||||
*/
|
*/
|
||||||
public function setServerName(string $serverName) : void{
|
public function setServerName(string $serverName) : void{
|
||||||
$this->serverName = $serverName;
|
$this->serverName = $serverName;
|
||||||
|
$this->destroyCache();
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -139,6 +147,7 @@ class QueryRegenerateEvent extends ServerEvent{
|
|||||||
*/
|
*/
|
||||||
public function setListPlugins(bool $value) : void{
|
public function setListPlugins(bool $value) : void{
|
||||||
$this->listPlugins = $value;
|
$this->listPlugins = $value;
|
||||||
|
$this->destroyCache();
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -153,6 +162,7 @@ class QueryRegenerateEvent extends ServerEvent{
|
|||||||
*/
|
*/
|
||||||
public function setPlugins(array $plugins) : void{
|
public function setPlugins(array $plugins) : void{
|
||||||
$this->plugins = $plugins;
|
$this->plugins = $plugins;
|
||||||
|
$this->destroyCache();
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -167,6 +177,7 @@ class QueryRegenerateEvent extends ServerEvent{
|
|||||||
*/
|
*/
|
||||||
public function setPlayerList(array $players) : void{
|
public function setPlayerList(array $players) : void{
|
||||||
$this->players = $players;
|
$this->players = $players;
|
||||||
|
$this->destroyCache();
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -181,6 +192,7 @@ class QueryRegenerateEvent extends ServerEvent{
|
|||||||
*/
|
*/
|
||||||
public function setPlayerCount(int $count) : void{
|
public function setPlayerCount(int $count) : void{
|
||||||
$this->numPlayers = $count;
|
$this->numPlayers = $count;
|
||||||
|
$this->destroyCache();
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -195,6 +207,7 @@ class QueryRegenerateEvent extends ServerEvent{
|
|||||||
*/
|
*/
|
||||||
public function setMaxPlayerCount(int $count) : void{
|
public function setMaxPlayerCount(int $count) : void{
|
||||||
$this->maxPlayers = $count;
|
$this->maxPlayers = $count;
|
||||||
|
$this->destroyCache();
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -209,6 +222,7 @@ class QueryRegenerateEvent extends ServerEvent{
|
|||||||
*/
|
*/
|
||||||
public function setWorld(string $world) : void{
|
public function setWorld(string $world) : void{
|
||||||
$this->map = $world;
|
$this->map = $world;
|
||||||
|
$this->destroyCache();
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -225,12 +239,16 @@ class QueryRegenerateEvent extends ServerEvent{
|
|||||||
*/
|
*/
|
||||||
public function setExtraData(array $extraData) : void{
|
public function setExtraData(array $extraData) : void{
|
||||||
$this->extraData = $extraData;
|
$this->extraData = $extraData;
|
||||||
|
$this->destroyCache();
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @return string
|
* @return string
|
||||||
*/
|
*/
|
||||||
public function getLongQuery() : string{
|
public function getLongQuery() : string{
|
||||||
|
if($this->longQueryCache !== null){
|
||||||
|
return $this->longQueryCache;
|
||||||
|
}
|
||||||
$query = "";
|
$query = "";
|
||||||
|
|
||||||
$plist = $this->server_engine;
|
$plist = $this->server_engine;
|
||||||
@ -273,13 +291,13 @@ class QueryRegenerateEvent extends ServerEvent{
|
|||||||
}
|
}
|
||||||
$query .= "\x00";
|
$query .= "\x00";
|
||||||
|
|
||||||
return $query;
|
return $this->longQueryCache = $query;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @return string
|
* @return string
|
||||||
*/
|
*/
|
||||||
public function getShortQuery() : string{
|
public function getShortQuery() : string{
|
||||||
return $this->serverName . "\x00" . $this->gametype . "\x00" . $this->map . "\x00" . $this->numPlayers . "\x00" . $this->maxPlayers . "\x00" . Binary::writeLShort($this->port) . $this->ip . "\x00";
|
return $this->shortQueryCache ?? ($this->shortQueryCache = $this->serverName . "\x00" . $this->gametype . "\x00" . $this->map . "\x00" . $this->numPlayers . "\x00" . $this->maxPlayers . "\x00" . Binary::writeLShort($this->port) . $this->ip . "\x00");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -33,7 +33,6 @@ use pocketmine\utils\Binary;
|
|||||||
use function base64_encode;
|
use function base64_encode;
|
||||||
use function chr;
|
use function chr;
|
||||||
use function hash;
|
use function hash;
|
||||||
use function microtime;
|
|
||||||
use function ord;
|
use function ord;
|
||||||
use function random_bytes;
|
use function random_bytes;
|
||||||
use function strlen;
|
use function strlen;
|
||||||
@ -46,12 +45,6 @@ class QueryHandler{
|
|||||||
private $lastToken;
|
private $lastToken;
|
||||||
/** @var string */
|
/** @var string */
|
||||||
private $token;
|
private $token;
|
||||||
/** @var string */
|
|
||||||
private $longData;
|
|
||||||
/** @var string */
|
|
||||||
private $shortData;
|
|
||||||
/** @var float */
|
|
||||||
private $timeout;
|
|
||||||
|
|
||||||
public const HANDSHAKE = 9;
|
public const HANDSHAKE = 9;
|
||||||
public const STATISTICS = 0;
|
public const STATISTICS = 0;
|
||||||
@ -73,7 +66,6 @@ class QueryHandler{
|
|||||||
|
|
||||||
$this->regenerateToken();
|
$this->regenerateToken();
|
||||||
$this->lastToken = $this->token;
|
$this->lastToken = $this->token;
|
||||||
$this->regenerateInfo();
|
|
||||||
$this->server->getLogger()->info($this->server->getLanguage()->translateString("pocketmine.server.query.running", [$addr, $port]));
|
$this->server->getLogger()->info($this->server->getLanguage()->translateString("pocketmine.server.query.running", [$addr, $port]));
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -82,11 +74,11 @@ class QueryHandler{
|
|||||||
$this->server->getLogger()->debug("[Query] $message");
|
$this->server->getLogger()->debug("[Query] $message");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @deprecated
|
||||||
|
*/
|
||||||
public function regenerateInfo(){
|
public function regenerateInfo(){
|
||||||
$ev = $this->server->getQueryInformation();
|
|
||||||
$this->longData = $ev->getLongQuery();
|
|
||||||
$this->shortData = $ev->getShortQuery();
|
|
||||||
$this->timeout = microtime(true) + $ev->getTimeout();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public function regenerateToken(){
|
public function regenerateToken(){
|
||||||
@ -122,14 +114,10 @@ class QueryHandler{
|
|||||||
$reply = chr(self::STATISTICS);
|
$reply = chr(self::STATISTICS);
|
||||||
$reply .= Binary::writeInt($sessionID);
|
$reply .= Binary::writeInt($sessionID);
|
||||||
|
|
||||||
if($this->timeout < microtime(true)){
|
|
||||||
$this->regenerateInfo();
|
|
||||||
}
|
|
||||||
|
|
||||||
if(strlen($payload) === 8){
|
if(strlen($payload) === 8){
|
||||||
$reply .= $this->longData;
|
$reply .= $this->server->getQueryInformation()->getLongQuery();
|
||||||
}else{
|
}else{
|
||||||
$reply .= $this->shortData;
|
$reply .= $this->server->getQueryInformation()->getShortQuery();
|
||||||
}
|
}
|
||||||
$interface->sendRawPacket($address, $port, $reply);
|
$interface->sendRawPacket($address, $port, $reply);
|
||||||
break;
|
break;
|
||||||
|
Loading…
x
Reference in New Issue
Block a user