From 50a7722242197f9a3b4300e154c1e66d1177839a Mon Sep 17 00:00:00 2001 From: faketruth Date: Thu, 19 Jan 2012 18:12:39 +0000 Subject: Terrain generation is synchronous again, async generation has bugs. Made some funky smart pointer things for chunks. Fixed a bug where the client would override the player position on the server and back again, resulting in sending too many chunks to the client which it doesn't even need. Fixed some compiler warnings in cPickup.cpp git-svn-id: http://mc-server.googlecode.com/svn/trunk@164 0a769ca7-a7f5-676a-18bf-c427514a06d6 --- source/cWorld.cpp | 56 ++++++++++++++++++++++++++++--------------------------- 1 file changed, 29 insertions(+), 27 deletions(-) (limited to 'source/cWorld.cpp') diff --git a/source/cWorld.cpp b/source/cWorld.cpp index d10d01a0d..fc7447c1d 100644 --- a/source/cWorld.cpp +++ b/source/cWorld.cpp @@ -45,6 +45,8 @@ #include "packets/cPacket_NewInvalidState.h" #include "packets/cPacket_Thunderbolt.h" +#include "ptr_cChunk.h" + #include "Vector3d.h" #include @@ -430,12 +432,11 @@ void cWorld::Tick(float a_Dt) int TimesSpreaded = 0; while( !m_pState->SpreadQueue.empty() && TimesSpreaded < 50 ) // Spread a max of 50 times each tick, otherwise server will hang { - cChunk* Chunk = (*m_pState->SpreadQueue.begin()); + ptr_cChunk& Chunk = *m_pState->SpreadQueue.begin(); //LOG("Spreading: %p", Chunk ); Chunk->SpreadLight( Chunk->pGetSkyLight() ); Chunk->SpreadLight( Chunk->pGetLight() ); m_pState->SpreadQueue.remove( Chunk ); - Chunk->RemoveReference(); TimesSpreaded++; } if( TimesSpreaded >= 50 ) @@ -494,7 +495,7 @@ void cWorld::Tick(float a_Dt) FastSetBlock( SetBlockData.x, SetBlockData.y, SetBlockData.z, SetBlockData.BlockID, SetBlockData.BlockMeta ); // If unable to set block, it's added to FastSetBlockQueue again } if( FastSetBlockQueueCopy.size() != m_pState->FastSetBlockQueue.size() ) - LOG(" Before: %i, after %i" , FastSetBlockQueueCopy.size(), m_pState->FastSetBlockQueue.size() ); + LOG(" Before: %i, after %i" , FastSetBlockQueueCopy.size(), m_pState->FastSetBlockQueue.size() ); if( m_Time - m_LastSave > 60*5 ) // Save each 5 minutes { @@ -712,20 +713,36 @@ cChunk* cWorld::GetChunk( int a_X, int a_Y, int a_Z ) cChunk* Chunk = GetChunkUnreliable( a_X, a_Y, a_Z ); if( Chunk ) return Chunk; +#if 1 // Current thread chunk generation + + // Found nothing, create a chunk + Chunk = new cChunk( a_X, a_Y, a_Z, this ); + if(Chunk) + { + LOGWARN("Created new chunk! %i %i", a_X, a_Z); + LockChunks(); + m_ChunkMap->AddChunk( Chunk ); + UnlockChunks(); + Chunk->Initialize(); + return Chunk; + } + return 0; +#else // Async thread generation + // Generate new chunk asynchronously m_pState->pChunkGenerator->GenerateChunk( a_X, a_Z ); // Could not find chunk, it's being generated, so return 0 return 0; +#endif } -cChunk* cWorld::GetChunkUnreliable( int a_X, int a_Y, int a_Z ) +ptr_cChunk cWorld::GetChunkUnreliable( int a_X, int a_Y, int a_Z ) { LockChunks(); - cChunk* Chunk = m_ChunkMap->GetChunk( a_X, a_Y, a_Z ); + ptr_cChunk Chunk( m_ChunkMap->GetChunk( a_X, a_Y, a_Z ) ); UnlockChunks(); - if( Chunk ) return Chunk; - return 0; + return Chunk; } cChunk* cWorld::GetChunkOfBlock( int a_X, int a_Y, int a_Z ) @@ -761,18 +778,6 @@ void cWorld::FastSetBlock( int a_X, int a_Y, int a_Z, char a_BlockType, char a_B return; } - // Could not find chunk, so it has been pushed into the generate chunks queue - // Check if currently generating the target chunk - m_pState->pChunkGenerator->Lock(); - Chunk = m_pState->pChunkGenerator->GetCurrentlyGenerating(); - if( Chunk && Chunk->GetPosX() == ChunkX && Chunk->GetPosZ() == ChunkZ ) - { - Chunk->FastSetBlock(X, Y, Z, a_BlockType, a_BlockMeta ); - m_pState->pChunkGenerator->Unlock(); - return; - } - m_pState->pChunkGenerator->Unlock(); - // Unable to set block right now, try again later m_pState->FastSetBlockQueue.push_back( sSetBlockData( a_X, a_Y, a_Z, a_BlockType, a_BlockMeta ) ); } @@ -1052,23 +1057,20 @@ void cWorld::UnlockChunks() m_ChunksCriticalSection->Unlock(); } -void cWorld::ReSpreadLighting( cChunk* a_Chunk ) +void cWorld::ReSpreadLighting( const ptr_cChunk& a_Chunk ) { LockChunks(); - m_pState->SpreadQueue.remove( a_Chunk ); + m_pState->SpreadQueue.remove( a_Chunk ); m_pState->SpreadQueue.push_back( a_Chunk ); -#define STRINGIZE(x) #x - a_Chunk->AddReference( __FILE__ ": " STRINGIZE(__LINE__) ); + //#define STRINGIZE(x) #x + //a_Chunk->AddReference( __FILE__ ": " STRINGIZE(__LINE__) ); UnlockChunks(); } -void cWorld::RemoveSpread( cChunk* a_Chunk ) +void cWorld::RemoveSpread( const ptr_cChunk& a_Chunk ) { LockChunks(); - size_t SizeBefore = m_pState->SpreadQueue.size(); m_pState->SpreadQueue.remove( a_Chunk ); - if( SizeBefore != m_pState->SpreadQueue.size() ) - a_Chunk->RemoveReference(); UnlockChunks(); } -- cgit v1.2.3