Merge branch 'dev' of ssh://island.sciencesim.com/home/sceneapi/sceneapi into dev

dsg
Dan Lake 2011-03-29 14:16:29 -07:00
commit 13057c3751
6 changed files with 122 additions and 29 deletions

View File

@ -393,7 +393,7 @@ namespace OpenSim.Region.CoreModules.RegionSync.RegionSyncModule
//The following Sendxxx calls,send out a message immediately, w/o putting it in the SyncConnector's outgoing queue. //The following Sendxxx calls,send out a message immediately, w/o putting it in the SyncConnector's outgoing queue.
//May need some optimization there on the priorities. //May need some optimization there on the priorities.
public void SendTerrainUpdates(string lastUpdateActorID) public void SendTerrainUpdates(long updateTimeStamp, string lastUpdateActorID)
{ {
if (!IsSyncingWithOtherActors()) if (!IsSyncingWithOtherActors())
{ {
@ -404,7 +404,7 @@ namespace OpenSim.Region.CoreModules.RegionSync.RegionSyncModule
{ {
//m_scene.Heightmap should have been updated already by the caller, send it out //m_scene.Heightmap should have been updated already by the caller, send it out
//SendSyncMessage(SymmetricSyncMessage.MsgType.Terrain, m_scene.Heightmap.SaveToXmlString()); //SendSyncMessage(SymmetricSyncMessage.MsgType.Terrain, m_scene.Heightmap.SaveToXmlString());
SendTerrainUpdateMessage(); SendTerrainUpdateMessage(updateTimeStamp, lastUpdateActorID);
} }
} }
@ -804,6 +804,8 @@ namespace OpenSim.Region.CoreModules.RegionSync.RegionSyncModule
data["actorID"] = OSD.FromString(lastUpdateActorID); data["actorID"] = OSD.FromString(lastUpdateActorID);
data["timeStamp"] = OSD.FromLong(lastUpdateTimeStamp); data["timeStamp"] = OSD.FromLong(lastUpdateTimeStamp);
//m_log.DebugFormat("{0}: Send out terrain with TS {1}, actorID {2}", LogHeader, lastUpdateTimeStamp, lastUpdateActorID);
SymmetricSyncMessage syncMsg = new SymmetricSyncMessage(SymmetricSyncMessage.MsgType.Terrain, OSDParser.SerializeJsonString(data)); SymmetricSyncMessage syncMsg = new SymmetricSyncMessage(SymmetricSyncMessage.MsgType.Terrain, OSDParser.SerializeJsonString(data));
connector.Send(syncMsg); connector.Send(syncMsg);
} }
@ -1051,6 +1053,18 @@ namespace OpenSim.Region.CoreModules.RegionSync.RegionSyncModule
return (m_syncConnectors.Count > 0); return (m_syncConnectors.Count > 0);
} }
private void SendTerrainUpdateToRelevantSyncConnectors(SymmetricSyncMessage syncMsg, string lastUpdateActorID)
{
List<SyncConnector> syncConnectors = GetSyncConnectorsForSceneEvents(lastUpdateActorID, syncMsg, null);
foreach (SyncConnector connector in syncConnectors)
{
m_log.DebugFormat("{0}: Send terrain update to {1}", LogHeader, connector.OtherSideActorID);
connector.Send(syncMsg);
}
}
//Object updates are sent by enqueuing into each connector's outQueue. //Object updates are sent by enqueuing into each connector's outQueue.
private void SendObjectUpdateToRelevantSyncConnectors(SceneObjectGroup sog, SymmetricSyncMessage syncMsg) private void SendObjectUpdateToRelevantSyncConnectors(SceneObjectGroup sog, SymmetricSyncMessage syncMsg)
{ {
@ -1761,14 +1775,19 @@ namespace OpenSim.Region.CoreModules.RegionSync.RegionSyncModule
} }
string msgData = data["terrain"].AsString(); string msgData = data["terrain"].AsString();
long lastUpdateTimeStamp = data["actorID"].AsLong(); long lastUpdateTimeStamp = data["timeStamp"].AsLong();
string lastUpdateActorID = data["timeStamp"].AsString(); string lastUpdateActorID = data["actorID"].AsString();
//set new terrain //m_log.DebugFormat("{0}: received Terrain update msg, with TS {1}, actorID {2}",LogHeader, lastUpdateTimeStamp, lastUpdateActorID);
m_scene.Heightmap.LoadFromXmlString(msgData);
m_scene.RequestModuleInterface<ITerrainModule>().TaintTerrianBySynchronization(lastUpdateTimeStamp, lastUpdateActorID); ; //update the terrain if the incoming terrain data has an more recent timestamp
if (m_scene.RequestModuleInterface<ITerrainModule>().UpdateTerrianBySync(lastUpdateTimeStamp, lastUpdateActorID, msgData))
{
//m_scene.Heightmap.LoadFromXmlString(msgData);
//CheckForTerrainUpdates(false, timeStamp, actorID);
m_log.DebugFormat("{0} : Synchronized terrain", LogHeader); m_log.DebugFormat("{0} : Synchronized terrain", LogHeader);
} }
}
private void HandleAddNewObject(SymmetricSyncMessage msg, string senderActorID) private void HandleAddNewObject(SymmetricSyncMessage msg, string senderActorID)
{ {
@ -1912,19 +1931,30 @@ namespace OpenSim.Region.CoreModules.RegionSync.RegionSyncModule
m_scene.UpdateObjectPartBucketProperties(bucketName, partUUID, data, rBucketSyncInfo); m_scene.UpdateObjectPartBucketProperties(bucketName, partUUID, data, rBucketSyncInfo);
} }
private void SendTerrainUpdateMessage() /// <summary>
/// Send out a sync message about the updated Terrain. If this is a relay node,
/// forward the sync message to all connectors except the one which initiated
/// the update.
/// </summary>
/// <param name="lastUpdateTimeStamp"></param>
/// <param name="lastUpdateActorID"></param>
private void SendTerrainUpdateMessage(long lastUpdateTimeStamp, string lastUpdateActorID)
{ {
string msgData = m_scene.Heightmap.SaveToXmlString(); string msgData = m_scene.Heightmap.SaveToXmlString();
long lastUpdateTimeStamp; //long lastUpdateTimeStamp;
string lastUpdateActorID; //string lastUpdateActorID;
m_scene.RequestModuleInterface<ITerrainModule>().GetSyncInfo(out lastUpdateTimeStamp, out lastUpdateActorID); //m_scene.RequestModuleInterface<ITerrainModule>().GetSyncInfo(out lastUpdateTimeStamp, out lastUpdateActorID);
OSDMap data = new OSDMap(3); OSDMap data = new OSDMap(3);
data["terrain"] = OSD.FromString(msgData); data["terrain"] = OSD.FromString(msgData);
data["actorID"] = OSD.FromString(lastUpdateActorID); data["actorID"] = OSD.FromString(lastUpdateActorID);
data["timeStamp"] = OSD.FromLong(lastUpdateTimeStamp); data["timeStamp"] = OSD.FromLong(lastUpdateTimeStamp);
SendSyncMessage(SymmetricSyncMessage.MsgType.Terrain, OSDParser.SerializeJsonString(data)); //m_log.DebugFormat("{0}: Ready to send terrain update with lastUpdateTimeStamp {1} and lastUpdateActorID {2}", LogHeader, lastUpdateTimeStamp, lastUpdateActorID);
SymmetricSyncMessage syncMsg = new SymmetricSyncMessage(SymmetricSyncMessage.MsgType.Terrain, OSDParser.SerializeJsonString(data));
SendTerrainUpdateToRelevantSyncConnectors(syncMsg, lastUpdateActorID);
//SendSyncMessage(SymmetricSyncMessage.MsgType.Terrain, OSDParser.SerializeJsonString(data));
} }

View File

@ -105,7 +105,7 @@ namespace OpenSim.Region.CoreModules.RegionSync.RegionSyncModule
//InstallInterfaces(); //InstallInterfaces();
//Register for the OnPostSceneCreation event //Register for the OnPostSceneCreation event
//m_scene.EventManager.OnPostSceneCreation += OnPostSceneCreation; m_scene.EventManager.OnPostSceneCreation += OnPostSceneCreation;
//Register for Scene/SceneGraph events //Register for Scene/SceneGraph events
m_scene.SceneGraph.OnObjectCreate += new ObjectCreateDelegate(ScenePersistence_OnObjectCreate); m_scene.SceneGraph.OnObjectCreate += new ObjectCreateDelegate(ScenePersistence_OnObjectCreate);
@ -177,6 +177,7 @@ namespace OpenSim.Region.CoreModules.RegionSync.RegionSyncModule
//If this is the local scene the actor is working on, do something //If this is the local scene the actor is working on, do something
if (createdScene == m_scene) if (createdScene == m_scene)
{ {
m_scene.RequestModuleInterface<ITerrainModule>().SetSyncInfo(DateTime.Now.Ticks, m_scene.GetSyncActorID());
} }
} }

View File

@ -241,9 +241,9 @@ namespace OpenSim.Region.CoreModules.RegionSync.RegionSyncModule
} }
}, null); }, null);
} }
catch (IOException) catch (Exception e)
{ {
m_log.WarnFormat("{0}:{1} has disconnected.", Description, m_connectorNum); m_log.WarnFormat("{0}:Error in Send() {1} has disconnected -- error message: {2}.", Description, m_connectorNum, e.Message);
} }
} }
} }
@ -264,10 +264,10 @@ namespace OpenSim.Region.CoreModules.RegionSync.RegionSyncModule
//m_log.WarnFormat("{0} Received: {1}", LogHeader, msg.ToString()); //m_log.WarnFormat("{0} Received: {1}", LogHeader, msg.ToString());
} }
// If there is a problem reading from the client, shut 'er down. // If there is a problem reading from the client, shut 'er down.
catch catch (Exception e)
{ {
//ShutdownClient(); //ShutdownClient();
m_log.WarnFormat("{0}:{1} has disconnected.", Description, m_connectorNum); m_log.WarnFormat("{0}: ReceiveLoop error {1} has disconnected -- error message {2}.", Description, m_connectorNum, e.Message);
Shutdown(); Shutdown();
return; return;
} }

View File

@ -551,6 +551,15 @@ namespace OpenSim.Region.CoreModules.World.Terrain
m_scene.PhysicsScene.SetTerrain(m_channel.GetFloatsSerialised()); m_scene.PhysicsScene.SetTerrain(m_channel.GetFloatsSerialised());
m_scene.SaveTerrain(); m_scene.SaveTerrain();
//SYMMETRIC SYNC
//Terrain has been modified, send out sync message if needed
//if (m_scene.RegionSyncModule != null)
//{
//m_log.DebugFormat("EventManager_OnTerrainTick: To call SendTerrainUpdates with TS {0} and actorID {1}", m_lastUpdateTimeStamp, m_lastUpdateActorID);
//m_scene.RegionSyncModule.SendTerrainUpdates(m_lastUpdateTimeStamp, m_lastUpdateActorID);
//}
//end of SYMMETRIC SYNC
// Clients who look at the map will never see changes after they looked at the map, so i've commented this out. // Clients who look at the map will never see changes after they looked at the map, so i've commented this out.
//m_scene.CreateTerrainTexture(true); //m_scene.CreateTerrainTexture(true);
} }
@ -610,12 +619,41 @@ namespace OpenSim.Region.CoreModules.World.Terrain
{ {
m_lastUpdateTimeStamp = timeStamp; m_lastUpdateTimeStamp = timeStamp;
m_lastUpdateActorID = actorID; m_lastUpdateActorID = actorID;
// m_log.DebugFormat("TerrainModule: updated syncinfo -- TS {0}, actorID {1}", m_lastUpdateTimeStamp, m_lastUpdateActorID);
} }
public void TaintTerrianBySynchronization(long timeStamp, string actorID) /// <summary>
/// Invoked by receiving a terrain sync message. First, check if the
/// timestamp is more advance than the local copy. If so, update the
/// local terrain copy, update the sync info (timestamp and actorID).
/// <param name="timeStamp"></param>
/// <param name="actorID"></param>
/// <param name="terrainData"></param>
/// <returns></returns>
public bool UpdateTerrianBySync(long timeStamp, string actorID, string terrainData)
{ {
SyncInfoUpdate(timeStamp, actorID); if (timeStamp > m_lastUpdateTimeStamp)
{
if (actorID.Equals(m_lastUpdateActorID) && actorID.Equals(m_scene.GetSyncActorID()))
{
m_log.WarnFormat("TerrainModule: Received a Terrain sync message with a more recent timestamp, HOWEVER, actorID on the update is the same with local acotrID ({0})",
actorID);
}
//SyncInfoUpdate(timeStamp, actorID);
//m_log.DebugFormat("TerrainModule: to copy new terrain data with TS {0}, actorID {1}", timeStamp, actorID);
m_scene.Heightmap.LoadFromXmlString(terrainData);
CheckForTerrainUpdates(false, timeStamp, actorID); CheckForTerrainUpdates(false, timeStamp, actorID);
return true;
}
else if ((timeStamp == m_lastUpdateTimeStamp) && !actorID.Equals(m_lastUpdateActorID))
{
m_log.WarnFormat("TerrainModule: actors {0} and {1} have edited terrain with the same timestamp, TO DE DONE: need to pick a winner.",
actorID, m_lastUpdateActorID);
}
return false;
} }
public bool TerrianModifiedLocally(string localActorID) public bool TerrianModifiedLocally(string localActorID)
@ -631,6 +669,12 @@ namespace OpenSim.Region.CoreModules.World.Terrain
lastUpdateActorID = m_lastUpdateActorID; lastUpdateActorID = m_lastUpdateActorID;
} }
public void SetSyncInfo(long lastUpdateTimeStamp, string lastUpdateActorID)
{
m_lastUpdateTimeStamp = lastUpdateTimeStamp;
m_lastUpdateActorID = lastUpdateActorID;
}
//end of SYMMETRIC SYNC //end of SYMMETRIC SYNC
/// <summary> /// <summary>
@ -641,14 +685,14 @@ namespace OpenSim.Region.CoreModules.World.Terrain
private void CheckForTerrainUpdates() private void CheckForTerrainUpdates()
{ {
//SYMMETRIC SYNC //SYMMETRIC SYNC
m_log.DebugFormat("CheckForTerrainUpdates() called");
//Assumption: Thus function is only called when the terrain is updated by the local actor. //Assumption: Thus function is only called when the terrain is updated by the local actor.
// Updating terrain during receiving sync messages from another actor will call CheckForTerrainUpdates. // Updating terrain during receiving sync messages from another actor will call CheckForTerrainUpdates.
//Update the timestamp to the current time tick, and set the LastUpdateActorID to be self //Update the timestamp to the current time tick, and set the LastUpdateActorID to be self
long currentTimeTick = DateTime.Now.Ticks; long currentTimeTick = DateTime.Now.Ticks;
string localActorID = m_scene.GetSyncActorID(); string localActorID = m_scene.GetSyncActorID();
SyncInfoUpdate(currentTimeTick, localActorID); //SyncInfoUpdate(currentTimeTick, localActorID);
//Check if the terrain has been modified and send out sync message if modified. //Check if the terrain has been modified and send out sync message if modified.
CheckForTerrainUpdates(false, currentTimeTick, localActorID); CheckForTerrainUpdates(false, currentTimeTick, localActorID);
@ -698,10 +742,11 @@ namespace OpenSim.Region.CoreModules.World.Terrain
{ {
m_tainted = true; m_tainted = true;
//SYMMETRIC SYNC //SYMMETRIC SYNC
//Terrain has been modified, send out sync message if needed //Terrain has been modified, updated the sync info
if (m_scene.RegionSyncModule != null) if (m_scene.RegionSyncModule != null)
{ {
m_scene.RegionSyncModule.SendTerrainUpdates(m_lastUpdateActorID); SyncInfoUpdate(lastUpdateTimeStamp, lastUpdateActorID);
m_scene.RegionSyncModule.SendTerrainUpdates(lastUpdateTimeStamp, lastUpdateActorID);
} }
//end of SYMMETRIC SYNC //end of SYMMETRIC SYNC
} }

View File

@ -80,7 +80,7 @@ namespace OpenSim.Region.Framework.Interfaces
//In RegionSyncModule's implementation, //In RegionSyncModule's implementation,
//The following calls send out a message immediately, w/o putting it in the SyncConnector's outgoing queue. //The following calls send out a message immediately, w/o putting it in the SyncConnector's outgoing queue.
//May need some optimization there on the priorities. //May need some optimization there on the priorities.
void SendTerrainUpdates(string lastUpdateActorID); void SendTerrainUpdates(long updateTimeStamp, string lastUpdateActorID);
//For propogating scene events to other actors //For propogating scene events to other actors
void PublishSceneEvent(EventManager.EventNames ev, Object[] evArgs); void PublishSceneEvent(EventManager.EventNames ev, Object[] evArgs);

View File

@ -66,7 +66,16 @@ namespace OpenSim.Region.Framework.Interfaces
void UndoTerrain(ITerrainChannel channel); void UndoTerrain(ITerrainChannel channel);
//SYMMETRIC SYNC //SYMMETRIC SYNC
void TaintTerrianBySynchronization(long timeStamp, string actorID); /// <summary>
/// Invoked by receiving a terrain sync message. First, check if the
/// timestamp is more advance than the local copy. If so, update the
/// local terrain copy.
/// </summary>
/// <param name="timeStamp">The time that the updated terrain was
/// created</param>
/// <param name="actorID">The actor who created the update.</param>
/// <param name="terrainData">The updated terrain</param>
bool UpdateTerrianBySync(long timeStamp, string actorID, string terrainData);
/// <summary> /// <summary>
/// Return true if the most recent update on terrain is done locally (i.e. not by receiving a terrain-sync message). /// Return true if the most recent update on terrain is done locally (i.e. not by receiving a terrain-sync message).
/// </summary> /// </summary>
@ -79,6 +88,14 @@ namespace OpenSim.Region.Framework.Interfaces
/// <param name="lastUpdateTimeStamp"></param> /// <param name="lastUpdateTimeStamp"></param>
/// <param name="lastUpdateActorID"></param> /// <param name="lastUpdateActorID"></param>
void GetSyncInfo(out long lastUpdateTimeStamp, out string lastUpdateActorID); void GetSyncInfo(out long lastUpdateTimeStamp, out string lastUpdateActorID);
/// <summary>
/// This is only supposed to be called by Persistence actor, which will
/// set the timestamp and actorID values for terrain upon initialization time.
/// </summary>
/// <param name="lastUpdateTimeStamp"></param>
/// <param name="lastUpdateActorID"></param>
void SetSyncInfo(long lastUpdateTimeStamp, string lastUpdateActorID);
//end of SYMMETRIC SYNC //end of SYMMETRIC SYNC
} }
} }