In Scene.AddNewAgent(), avoid a situation where an exception can result in a client being added to the manager without IClientAPI.SceneAgent being set.

This is done by adjusting the order of code so that SceneAgent will always be set before adding the client.
Various parts of the code (rightly) assume that a a client registered to the manager will always have a SceneAgent set no matter what.
ghosts
Justin Clark-Casey (justincc) 2014-10-22 23:46:05 +01:00
parent 7d2aad3873
commit 6fa8ddf0fc
1 changed files with 23 additions and 11 deletions

View File

@ -2789,29 +2789,41 @@ namespace OpenSim.Region.Framework.Scenes
"[SCENE]: Adding new child scene presence {0} {1} to scene {2} at pos {3}", "[SCENE]: Adding new child scene presence {0} {1} to scene {2} at pos {3}",
client.Name, client.AgentId, RegionInfo.RegionName, client.StartPos); client.Name, client.AgentId, RegionInfo.RegionName, client.StartPos);
sp = m_sceneGraph.CreateAndAddChildScenePresence(client, aCircuit.Appearance, type);
// We must set this here so that TriggerOnNewClient and TriggerOnClientLogin can determine whether the
// client is for a root or child agent.
// We must also set this before adding the client to the client manager so that an exception later on
// does not leave a client manager entry without the scene agent set, which will cause other code
// to fail since any entry in the client manager should have a ScenePresence
//
// XXX: This may be better set for a new client before that client is added to the client manager.
// But need to know what happens in the case where a ScenePresence is already present (and if this
// actually occurs).
client.SceneAgent = sp;
m_clientManager.Add(client); m_clientManager.Add(client);
SubscribeToClientEvents(client); SubscribeToClientEvents(client);
sp = m_sceneGraph.CreateAndAddChildScenePresence(client, aCircuit.Appearance, type);
m_eventManager.TriggerOnNewPresence(sp); m_eventManager.TriggerOnNewPresence(sp);
sp.TeleportFlags = (TPFlags)aCircuit.teleportFlags; sp.TeleportFlags = (TPFlags)aCircuit.teleportFlags;
} }
else else
{ {
// We must set this here so that TriggerOnNewClient and TriggerOnClientLogin can determine whether the
// client is for a root or child agent.
// XXX: This may be better set for a new client before that client is added to the client manager.
// But need to know what happens in the case where a ScenePresence is already present (and if this
// actually occurs).
client.SceneAgent = sp;
m_log.WarnFormat( m_log.WarnFormat(
"[SCENE]: Already found {0} scene presence for {1} in {2} when asked to add new scene presence", "[SCENE]: Already found {0} scene presence for {1} in {2} when asked to add new scene presence",
sp.IsChildAgent ? "child" : "root", sp.Name, RegionInfo.RegionName); sp.IsChildAgent ? "child" : "root", sp.Name, RegionInfo.RegionName);
reallyNew = false; reallyNew = false;
} }
// We must set this here so that TriggerOnNewClient and TriggerOnClientLogin can determine whether the
// client is for a root or child agent.
// XXX: This may be better set for a new client before that client is added to the client manager.
// But need to know what happens in the case where a ScenePresence is already present (and if this
// actually occurs).
client.SceneAgent = sp;
// This is currently also being done earlier in NewUserConnection for real users to see if this // This is currently also being done earlier in NewUserConnection for real users to see if this
// resolves problems where HG agents are occasionally seen by others as "Unknown user" in chat and other // resolves problems where HG agents are occasionally seen by others as "Unknown user" in chat and other
// places. However, we still need to do it here for NPCs. // places. However, we still need to do it here for NPCs.