Kick idle player which has no network activity to server

This commit is contained in:
Benau 2018-12-05 11:12:44 +08:00
parent a7311238cf
commit 72f1dc66cc
6 changed files with 55 additions and 1 deletions

View File

@ -227,6 +227,7 @@ void GameProtocol::handleControllerAction(Event *event)
{
// Send update to all clients except the original sender if the event
// is after the server time
event->getPeer()->updateLastActivity();
if (!will_trigger_rewind)
STKHost::get()->sendPacketExcept(event->getPeer(), &data, false);

View File

@ -597,6 +597,29 @@ void ServerLobby::asynchronousUpdate()
*/
void ServerLobby::update(int ticks)
{
int sec = ServerConfig::m_kick_idle_player_seconds;
if (sec > 0 && m_state.load() >= WAIT_FOR_WORLD_LOADED &&
m_state.load() <= RACING && m_server_has_loaded_world.load() == true)
{
auto players = m_game_setup->getConnectedPlayers(true/*same_offset*/);
World* w = World::getWorld();
for (unsigned i = 0; i < players.size(); i++)
{
if (!players[i])
continue;
auto peer = players[i]->getPeer();
if (peer->idleForSeconds() > sec && !peer->isDisconnected())
{
if (w && w->getKart(i)->hasFinishedRace())
continue;
Log::info("ServerLobby", "%s has been idle for more than"
" %d seconds, kick.",
peer->getAddress().toString().c_str(), sec);
peer->kick();
}
}
}
// Reset server to initial state if no more connected players
if (m_waiting_for_reset)
{
@ -2117,6 +2140,11 @@ std::pair<int, float> ServerLobby::getHitCaptureLimit(float num_karts)
*/
void ServerLobby::finishedLoadingWorld()
{
for (auto p : m_peers_ready)
{
if (auto peer = p.first.lock())
peer->updateLastActivity();
}
m_server_has_loaded_world.store(true);
} // finishedLoadingWorld;
@ -2127,6 +2155,7 @@ void ServerLobby::finishedLoadingWorld()
void ServerLobby::finishedLoadingWorldClient(Event *event)
{
std::shared_ptr<STKPeer> peer = event->getPeerSP();
peer->updateLastActivity();
m_peers_ready.at(peer) = true;
Log::info("ServerLobby", "Peer %d has finished loading world at %lf",
peer->getHostId(), StkTime::getRealTime());

View File

@ -279,6 +279,13 @@ namespace ServerConfig
"kick-high-ping-players",
"Kick players whose ping is above max-ping."));
SERVER_CFG_PREFIX IntServerConfigParam m_kick_idle_player_seconds
SERVER_CFG_DEFAULT(IntServerConfigParam(60,
"kick-idle-player-seconds",
"Kick idle player which has no network activity to server for more "
"than some seconds during game, unless he has finished the race. "
"Negative value to disable."));
SERVER_CFG_PREFIX StringToUIntServerConfigParam m_server_ip_ban_list
SERVER_CFG_DEFAULT(StringToUIntServerConfigParam("server-ip-ban-list",
"ip: IP in X.X.X.X/Y (CIDR) format for banning, use Y of 32 for a "

View File

@ -768,6 +768,7 @@ void STKHost::mainLoop()
" than %d ms, kick.",
p.second->getAddress().toString().c_str(),
ap, max_ping);
p.second->setDisconnected(true);
std::lock_guard<std::mutex> lock(m_enet_cmd_mutex);
m_enet_cmd.emplace_back(p.second->getENetPeer(),
(ENetPacket*)NULL, PDI_BAD_CONNECTION,

View File

@ -43,6 +43,7 @@ STKPeer::STKPeer(ENetPeer *enet_peer, STKHost* host, uint32_t host_id)
m_waiting_for_game.store(true);
m_disconnected.store(false);
m_warned_for_high_ping.store(false);
m_last_activity.store((int64_t)StkTime::getRealTimeMs());
} // STKPeer
//-----------------------------------------------------------------------------

View File

@ -83,6 +83,8 @@ protected:
uint64_t m_connected_time;
std::atomic<int64_t> m_last_activity;
/** Available karts and tracks from this peer */
std::pair<std::set<std::string>, std::set<std::string> > m_available_kts;
@ -189,6 +191,8 @@ public:
// ------------------------------------------------------------------------
bool isDisconnected() const { return m_disconnected.load(); }
// ------------------------------------------------------------------------
void setDisconnected(bool val) { return m_disconnected.store(val); }
// ------------------------------------------------------------------------
bool hasWarnedForHighPing() const { return m_warned_for_high_ping.load(); }
// ------------------------------------------------------------------------
void setWarnedForHighPing(bool val) { m_warned_for_high_ping.store(val); }
@ -203,7 +207,18 @@ public:
void setUserVersion(const std::string& uv) { m_user_version = uv; }
// ------------------------------------------------------------------------
const std::string& getUserVersion() const { return m_user_version; }
// ------------------------------------------------------------------------
void updateLastActivity()
{ m_last_activity.store((int64_t)StkTime::getRealTimeMs()); }
// ------------------------------------------------------------------------
int idleForSeconds() const
{
int64_t diff =
(int64_t)StkTime::getRealTimeMs() - m_last_activity.load();
if (diff < 0)
return 0;
return (int)(diff / 1000);
}
}; // STKPeer
#endif // STK_PEER_HPP