parent
b65a91dde3
commit
8c3837987b
@ -1,6 +1,6 @@
|
||||
/*
|
||||
** Lua binding: AllToLua
|
||||
** Generated automatically by tolua++-1.0.92 on 08/13/13 23:07:52.
|
||||
** Generated automatically by tolua++-1.0.92 on 08/14/13 08:14:03.
|
||||
*/
|
||||
|
||||
#ifndef __cplusplus
|
||||
@ -11295,14 +11295,14 @@ static int tolua_AllToLua_cServer_GetNumPlayers00(lua_State* tolua_S)
|
||||
#ifndef TOLUA_RELEASE
|
||||
tolua_Error tolua_err;
|
||||
if (
|
||||
!tolua_isusertype(tolua_S,1,"const cServer",0,&tolua_err) ||
|
||||
!tolua_isusertype(tolua_S,1,"cServer",0,&tolua_err) ||
|
||||
!tolua_isnoobj(tolua_S,2,&tolua_err)
|
||||
)
|
||||
goto tolua_lerror;
|
||||
else
|
||||
#endif
|
||||
{
|
||||
const cServer* self = (const cServer*) tolua_tousertype(tolua_S,1,0);
|
||||
cServer* self = (cServer*) tolua_tousertype(tolua_S,1,0);
|
||||
#ifndef TOLUA_RELEASE
|
||||
if (!self) tolua_error(tolua_S,"invalid 'self' in function 'GetNumPlayers'", NULL);
|
||||
#endif
|
||||
|
@ -1,6 +1,6 @@
|
||||
/*
|
||||
** Lua binding: AllToLua
|
||||
** Generated automatically by tolua++-1.0.92 on 08/13/13 23:07:53.
|
||||
** Generated automatically by tolua++-1.0.92 on 08/14/13 08:14:04.
|
||||
*/
|
||||
|
||||
/* Exported function */
|
||||
|
@ -275,7 +275,7 @@ void cClientHandle::Authenticate(void)
|
||||
|
||||
void cClientHandle::StreamChunks(void)
|
||||
{
|
||||
if ((m_State < csAuthenticating) || (m_State >= csDestroying))
|
||||
if ((m_State < csAuthenticated) || (m_State >= csDestroying))
|
||||
{
|
||||
return;
|
||||
}
|
||||
@ -1314,6 +1314,42 @@ void cClientHandle::SendData(const char * a_Data, int a_Size)
|
||||
|
||||
|
||||
|
||||
void cClientHandle::MoveToWorld(cWorld & a_World, bool a_SendRespawnPacket)
|
||||
{
|
||||
ASSERT(m_Player != NULL);
|
||||
|
||||
if (a_SendRespawnPacket)
|
||||
{
|
||||
SendRespawn();
|
||||
}
|
||||
|
||||
cWorld * World = m_Player->GetWorld();
|
||||
|
||||
// Remove all associated chunks:
|
||||
cChunkCoordsList Chunks;
|
||||
{
|
||||
cCSLock Lock(m_CSChunkLists);
|
||||
std::swap(Chunks, m_LoadedChunks);
|
||||
m_ChunksToSend.clear();
|
||||
}
|
||||
for (cChunkCoordsList::iterator itr = Chunks.begin(), end = Chunks.end(); itr != end; ++itr)
|
||||
{
|
||||
World->RemoveChunkClient(itr->m_ChunkX, itr->m_ChunkZ, this);
|
||||
m_Protocol->SendUnloadChunk(itr->m_ChunkX, itr->m_ChunkZ);
|
||||
} // for itr - Chunks[]
|
||||
|
||||
// Do NOT stream new chunks, the new world runs its own tick thread and may deadlock
|
||||
// Instead, the chunks will be streamed when the client is moved to the new world's Tick list,
|
||||
// by setting state to csAuthenticated
|
||||
m_State = csAuthenticated;
|
||||
m_LastStreamedChunkX = 0x7fffffff;
|
||||
m_LastStreamedChunkZ = 0x7fffffff;
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
bool cClientHandle::CheckBlockInteractionsRate(void)
|
||||
{
|
||||
ASSERT(m_Player != NULL);
|
||||
|
@ -32,6 +32,7 @@ class cRedstone;
|
||||
class cWindow;
|
||||
class cFallingBlock;
|
||||
class cItemHandler;
|
||||
class cWorld;
|
||||
|
||||
|
||||
|
||||
@ -194,6 +195,9 @@ public:
|
||||
|
||||
void SendData(const char * a_Data, int a_Size);
|
||||
|
||||
/// Called when the player moves into a different world; queues sreaming the new chunks
|
||||
void MoveToWorld(cWorld & a_World, bool a_SendRespawnPacket);
|
||||
|
||||
private:
|
||||
|
||||
int m_ViewDistance; // Number of chunks the player can see in each direction; 4 is the minimum ( http://wiki.vg/Protocol_FAQ#.E2.80.A6all_connecting_clients_spasm_and_jerk_uncontrollably.21 )
|
||||
|
@ -100,6 +100,8 @@ cPlayer::cPlayer(cClientHandle* a_Client, const AString & a_PlayerName)
|
||||
m_LastJumpHeight = (float)(GetPosY());
|
||||
m_LastGroundHeight = (float)(GetPosY());
|
||||
m_Stance = GetPosY() + 1.62;
|
||||
|
||||
cRoot::Get()->GetServer()->PlayerCreated(this);
|
||||
}
|
||||
|
||||
|
||||
@ -1120,20 +1122,15 @@ bool cPlayer::MoveToWorld(const char * a_WorldName)
|
||||
m_ClientHandle->RemoveFromAllChunks();
|
||||
m_World->RemoveEntity(this);
|
||||
|
||||
// If the dimension is different, we can send the respawn packet
|
||||
// http://wiki.vg/Protocol#0x09 says "don't send if dimension is the same" as of 2013_07_02
|
||||
m_ClientHandle->MoveToWorld(*World, (OldDimension != World->GetDimension()));
|
||||
|
||||
// Add player to all the necessary parts of the new world
|
||||
SetWorld(World);
|
||||
World->AddEntity(this);
|
||||
World->AddPlayer(this);
|
||||
|
||||
// If the dimension is different, we can send the respawn packet
|
||||
// http://wiki.vg/Protocol#0x09 says "don't send if dimension is the same" as of 2013_07_02
|
||||
if (OldDimension != World->GetDimension())
|
||||
{
|
||||
m_ClientHandle->SendRespawn();
|
||||
}
|
||||
|
||||
// Stream the new chunks:
|
||||
m_ClientHandle->StreamChunks();
|
||||
return true;
|
||||
}
|
||||
|
||||
|
@ -172,10 +172,34 @@ void cServer::ClientMovedToWorld(const cClientHandle * a_Client)
|
||||
|
||||
|
||||
|
||||
void cServer::PlayerCreated(const cPlayer * a_Player)
|
||||
{
|
||||
// To avoid deadlocks, the player count is not handled directly, but rather posted onto the tick thread
|
||||
cCSLock Lock(m_CSPlayerCountDiff);
|
||||
m_PlayerCountDiff += 1;
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
void cServer::PlayerDestroyed(const cPlayer * a_Player)
|
||||
{
|
||||
// To avoid deadlocks, the player count is not handled directly, but rather posted onto the tick thread
|
||||
cCSLock Lock(m_CSPlayerCountDiff);
|
||||
m_PlayerCountDiff -= 1;
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
bool cServer::InitServer(cIniFile & a_SettingsIni)
|
||||
{
|
||||
m_Description = a_SettingsIni.GetValue ("Server", "Description", "MCServer! - In C++!").c_str();
|
||||
m_MaxPlayers = a_SettingsIni.GetValueI("Server", "MaxPlayers", 100);
|
||||
m_PlayerCount = 0;
|
||||
m_PlayerCountDiff = 0;
|
||||
|
||||
if (m_bIsConnected)
|
||||
{
|
||||
@ -254,6 +278,16 @@ bool cServer::InitServer(cIniFile & a_SettingsIni)
|
||||
|
||||
|
||||
|
||||
int cServer::GetNumPlayers(void)
|
||||
{
|
||||
cCSLock Lock(m_CSPlayerCount);
|
||||
return m_PlayerCount;
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
void cServer::PrepareKeys(void)
|
||||
{
|
||||
// TODO: Save and load key for persistence across sessions
|
||||
@ -310,6 +344,17 @@ void cServer::OnConnectionAccepted(cSocket & a_Socket)
|
||||
|
||||
bool cServer::Tick(float a_Dt)
|
||||
{
|
||||
// Apply the queued playercount adjustments (postponed to avoid deadlocks)
|
||||
int PlayerCountDiff = 0;
|
||||
{
|
||||
cCSLock Lock(m_CSPlayerCountDiff);
|
||||
std::swap(PlayerCountDiff, m_PlayerCountDiff);
|
||||
}
|
||||
{
|
||||
cCSLock Lock(m_CSPlayerCount);
|
||||
m_PlayerCount += PlayerCountDiff;
|
||||
}
|
||||
|
||||
cRoot::Get()->TickCommands();
|
||||
|
||||
TickClients(a_Dt);
|
||||
|
@ -43,7 +43,7 @@ public: // tolua_export
|
||||
|
||||
// Player counts:
|
||||
int GetMaxPlayers(void) const {return m_MaxPlayers; }
|
||||
int GetNumPlayers(void) const { return m_NumPlayers; }
|
||||
int GetNumPlayers(void);
|
||||
void SetMaxPlayers(int a_MaxPlayers) { m_MaxPlayers = a_MaxPlayers; }
|
||||
|
||||
// tolua_end
|
||||
@ -78,6 +78,12 @@ public: // tolua_export
|
||||
/// Don't tick a_Client anymore, it will be ticked from its cPlayer instead
|
||||
void ClientMovedToWorld(const cClientHandle * a_Client);
|
||||
|
||||
/// Notifies the server that a player was created; the server uses this to adjust the number of players
|
||||
void PlayerCreated(const cPlayer * a_Player);
|
||||
|
||||
/// Notifies the server that a player was destroyed; the server uses this to adjust the number of players
|
||||
void PlayerDestroyed(const cPlayer * a_Player);
|
||||
|
||||
CryptoPP::RSA::PrivateKey & GetPrivateKey(void) { return m_PrivateKey; }
|
||||
CryptoPP::RSA::PublicKey & GetPublicKey (void) { return m_PublicKey; }
|
||||
|
||||
@ -135,6 +141,11 @@ private:
|
||||
cClientHandleList m_Clients; ///< Clients that are connected to the server and not yet assigned to a cWorld
|
||||
cClientHandleList m_ClientsToRemove; ///< Clients that have just been moved into a world and are to be removed from m_Clients in the next Tick()
|
||||
|
||||
cCriticalSection m_CSPlayerCount; ///< Locks the m_PlayerCount
|
||||
int m_PlayerCount; ///< Number of players currently playing in the server
|
||||
cCriticalSection m_CSPlayerCountDiff; ///< Locks the m_PlayerCountDiff
|
||||
int m_PlayerCountDiff; ///< Adjustment to m_PlayerCount to be applied in the Tick thread
|
||||
|
||||
cSocketThreads m_SocketThreads;
|
||||
|
||||
int m_ClientViewDistance; // The default view distance for clients; settable in Settings.ini
|
||||
@ -150,7 +161,6 @@ private:
|
||||
|
||||
AString m_Description;
|
||||
int m_MaxPlayers;
|
||||
int m_NumPlayers;
|
||||
|
||||
cTickThread m_TickThread;
|
||||
cEvent m_RestartEvent;
|
||||
|
Loading…
Reference in New Issue
Block a user