From 73e9b0be725a73a489b29f3fe2df236c897ef3b5 Mon Sep 17 00:00:00 2001 From: Dan Lake Date: Wed, 17 Mar 2010 06:40:00 -0700 Subject: Inconsistent locking of ScenePresence array in SceneGraph. Fixed by eliminating option to return the actual list. Callers can now either request a copy of the array as a new List or ask the SceneGraph to call a delegate function on every ScenePresence. Iteration and locking of the ScenePresences now takes place only within the SceneGraph class. This patch also applies a fix to Combat/CombatModule.cs which had unlocked iteration of the ScenePresences and inconsistent try/catch around the use of those ScenePresences. --- OpenSim/Region/Framework/Scenes/Scene.cs | 52 ++++++++++++++++++++------------ 1 file changed, 32 insertions(+), 20 deletions(-) (limited to 'OpenSim/Region/Framework/Scenes/Scene.cs') diff --git a/OpenSim/Region/Framework/Scenes/Scene.cs b/OpenSim/Region/Framework/Scenes/Scene.cs index baa8759..a86a33c 100644 --- a/OpenSim/Region/Framework/Scenes/Scene.cs +++ b/OpenSim/Region/Framework/Scenes/Scene.cs @@ -3599,9 +3599,7 @@ namespace OpenSim.Region.Framework.Scenes public virtual void AgentCrossing(UUID agentID, Vector3 position, bool isFlying) { ScenePresence presence; - m_sceneGraph.TryGetAvatar(agentID, out presence); - - if (presence != null) + if(m_sceneGraph.TryGetAvatar(agentID, out presence)) { try { @@ -3776,9 +3774,7 @@ namespace OpenSim.Region.Framework.Scenes Vector3 lookAt, uint teleportFlags) { ScenePresence sp; - m_sceneGraph.TryGetAvatar(remoteClient.AgentId, out sp); - - if (sp != null) + if(m_sceneGraph.TryGetAvatar(remoteClient.AgentId, out sp)) { uint regionX = m_regInfo.RegionLocX; uint regionY = m_regInfo.RegionLocY; @@ -4134,6 +4130,11 @@ namespace OpenSim.Region.Framework.Scenes //The idea is to have a group of method that return a list of avatars meeting some requirement // ie it could be all m_scenePresences within a certain range of the calling prim/avatar. + // + // GetAvatars returns a new list of all root agent presences in the scene + // GetScenePresences returns a new list of all presences in the scene or a filter may be passed. + // GetScenePresence returns the presence with matching UUID or first/last name. + // ForEachScenePresence requests the Scene to run a delegate function against all presences. /// /// Return a list of all avatars in this region. @@ -4150,7 +4151,7 @@ namespace OpenSim.Region.Framework.Scenes /// This list is a new object, so it can be iterated over without locking. /// /// - public ScenePresence[] GetScenePresences() + public List GetScenePresences() { return m_sceneGraph.GetScenePresences(); } @@ -4176,6 +4177,28 @@ namespace OpenSim.Region.Framework.Scenes return m_sceneGraph.GetScenePresence(avatarID); } + /// + /// Request the ScenePresence in this region by first/last name. + /// Should normally only be a single match, but first is always returned + /// + /// + /// + /// + public ScenePresence GetScenePresence(string firstName, string lastName) + { + return m_sceneGraph.GetScenePresence(firstName, lastName); + } + + /// + /// Request the ScenePresence in this region by localID. + /// + /// + /// + public ScenePresence GetScenePresence(uint localID) + { + return m_sceneGraph.GetScenePresence(localID); + } + public override bool PresenceChildStatus(UUID avatarID) { ScenePresence cp = GetScenePresence(avatarID); @@ -4191,25 +4214,14 @@ namespace OpenSim.Region.Framework.Scenes } /// - /// + /// Performs action on all scene presences. /// /// public void ForEachScenePresence(Action action) { - // We don't want to try to send messages if there are no avatars. if (m_sceneGraph != null) { - try - { - ScenePresence[] presences = GetScenePresences(); - for (int i = 0; i < presences.Length; i++) - action(presences[i]); - } - catch (Exception e) - { - m_log.Info("[BUG] in " + RegionInfo.RegionName + ": " + e.ToString()); - m_log.Info("[BUG] Stack Trace: " + e.StackTrace); - } + m_sceneGraph.ForEachScenePresence(action); } } -- cgit v1.1