aboutsummaryrefslogtreecommitdiffstatshomepage
diff options
context:
space:
mode:
-rwxr-xr-xOpenSim/Region/Framework/Scenes/SceneGraph.cs121
1 files changed, 69 insertions, 52 deletions
diff --git a/OpenSim/Region/Framework/Scenes/SceneGraph.cs b/OpenSim/Region/Framework/Scenes/SceneGraph.cs
index 51392ae..e37841f 100755
--- a/OpenSim/Region/Framework/Scenes/SceneGraph.cs
+++ b/OpenSim/Region/Framework/Scenes/SceneGraph.cs
@@ -150,21 +150,28 @@ namespace OpenSim.Region.Framework.Scenes
150 150
151 protected internal void Close() 151 protected internal void Close()
152 { 152 {
153 m_scenePresencesLock.EnterWriteLock(); 153 bool entered = false;
154 try 154 try
155 { 155 {
156 m_scenePresenceMap = new ConcurrentDictionary<UUID, ScenePresence>(); 156 try { }
157 m_scenePresenceLocalIDMap = new ConcurrentDictionary<uint, ScenePresence>(); 157 finally
158 m_scenePresenceArray = new List<ScenePresence>(); 158 {
159 m_spArrayLastVersion = 0; 159 m_scenePresencesLock.EnterWriteLock();
160 m_spArrayVersion = 0; 160 entered = true;
161 if (_PhyScene != null) 161 m_scenePresenceMap = new ConcurrentDictionary<UUID, ScenePresence>();
162 _PhyScene.OnPhysicsCrash -= physicsBasedCrash; 162 m_scenePresenceLocalIDMap = new ConcurrentDictionary<uint, ScenePresence>();
163 _PhyScene = null; 163 m_scenePresenceArray = new List<ScenePresence>();
164 m_spArrayLastVersion = 0;
165 m_spArrayVersion = 0;
166 if (_PhyScene != null)
167 _PhyScene.OnPhysicsCrash -= physicsBasedCrash;
168 _PhyScene = null;
169 }
164 } 170 }
165 finally 171 finally
166 { 172 {
167 m_scenePresencesLock.ExitWriteLock(); 173 if(entered)
174 m_scenePresencesLock.ExitWriteLock();
168 } 175 }
169 176
170 lock (SceneObjectGroupsByFullID) 177 lock (SceneObjectGroupsByFullID)
@@ -708,32 +715,36 @@ namespace OpenSim.Region.Framework.Scenes
708 715
709 try 716 try
710 { 717 {
711 m_scenePresencesLock.EnterWriteLock(); 718 try{ }
712 entered = true; 719 finally
720 {
721 m_scenePresencesLock.EnterWriteLock();
722 entered = true;
713 723
714 m_numChildAgents++; 724 m_numChildAgents++;
715 725
716 if (!m_scenePresenceMap.ContainsKey(presence.UUID)) 726 if (!m_scenePresenceMap.ContainsKey(presence.UUID))
717 {
718 m_scenePresenceMap[presence.UUID] = presence;
719 m_scenePresenceLocalIDMap[presence.LocalId] = presence;
720 }
721 else
722 {
723 // Remember the old presence reference from the dictionary
724 ScenePresence oldref = m_scenePresenceMap[presence.UUID];
725 uint oldLocalID = oldref.LocalId;
726 // Replace the presence reference in the dictionary with the new value
727 m_scenePresenceMap[presence.UUID] = presence;
728 if(presence.LocalId != oldLocalID)
729 { 727 {
730 m_scenePresenceLocalIDMap.TryRemove(oldLocalID, out oldref); 728 m_scenePresenceMap[presence.UUID] = presence;
731 m_scenePresenceLocalIDMap[presence.LocalId] = presence; 729 m_scenePresenceLocalIDMap[presence.LocalId] = presence;
732 } 730 }
733 // Find the index in the list where the old ref was stored and update the reference 731 else
734 } 732 {
733 // Remember the old presence reference from the dictionary
734 ScenePresence oldref = m_scenePresenceMap[presence.UUID];
735 uint oldLocalID = oldref.LocalId;
736 // Replace the presence reference in the dictionary with the new value
737 m_scenePresenceMap[presence.UUID] = presence;
738 if(presence.LocalId != oldLocalID)
739 {
740 m_scenePresenceLocalIDMap.TryRemove(oldLocalID, out oldref);
741 m_scenePresenceLocalIDMap[presence.LocalId] = presence;
742 }
743 // Find the index in the list where the old ref was stored and update the reference
744 }
735 745
736 ++m_spArrayVersion; 746 ++m_spArrayVersion;
747 }
737 } 748 }
738 finally 749 finally
739 { 750 {
@@ -759,19 +770,23 @@ namespace OpenSim.Region.Framework.Scenes
759 bool entered = false; 770 bool entered = false;
760 try 771 try
761 { 772 {
762 m_scenePresencesLock.EnterWriteLock(); 773 try { }
763 entered = true; 774 finally
764 // Remove the presence reference from the dictionary
765 ScenePresence oldref;
766 if(m_scenePresenceMap.TryRemove(agentID, out oldref))
767 { 775 {
768 // Find the index in the list where the old ref was stored and remove the reference 776 m_scenePresencesLock.EnterWriteLock();
769 m_scenePresenceLocalIDMap.TryRemove(oldref.LocalId, out oldref); 777 entered = true;
770 ++m_spArrayVersion; 778 // Remove the presence reference from the dictionary
771 } 779 ScenePresence oldref;
772 else 780 if(m_scenePresenceMap.TryRemove(agentID, out oldref))
773 { 781 {
774 m_log.WarnFormat("[SCENE GRAPH]: Tried to remove non-existent scene presence with agent ID {0} from scene ScenePresences list", agentID); 782 // Find the index in the list where the old ref was stored and remove the reference
783 m_scenePresenceLocalIDMap.TryRemove(oldref.LocalId, out oldref);
784 ++m_spArrayVersion;
785 }
786 else
787 {
788 m_log.WarnFormat("[SCENE GRAPH]: Tried to remove non-existent scene presence with agent ID {0} from scene ScenePresences list", agentID);
789 }
775 } 790 }
776 } 791 }
777 finally 792 finally
@@ -905,26 +920,28 @@ namespace OpenSim.Region.Framework.Scenes
905 protected internal List<ScenePresence> GetScenePresences() 920 protected internal List<ScenePresence> GetScenePresences()
906 { 921 {
907 bool entered = false; 922 bool entered = false;
923 List<ScenePresence> ret = new List<ScenePresence>();
908 try 924 try
909 { 925 {
910 m_scenePresencesLock.EnterWriteLock(); 926 try{ }
911 entered = true; 927 finally
912 if(m_spArrayLastVersion != m_spArrayVersion)
913 { 928 {
914 m_scenePresenceArray = new List<ScenePresence>(m_scenePresenceMap.Values); 929 m_scenePresencesLock.EnterWriteLock();
915 m_spArrayLastVersion = m_spArrayVersion; 930 entered = true;
931 if(m_spArrayLastVersion != m_spArrayVersion)
932 {
933 m_scenePresenceArray = new List<ScenePresence>(m_scenePresenceMap.Values);
934 m_spArrayLastVersion = m_spArrayVersion;
935 }
936 ret = m_scenePresenceArray;
916 } 937 }
917 return m_scenePresenceArray;
918 }
919 catch
920 {
921 return new List<ScenePresence>();
922 } 938 }
923 finally 939 finally
924 { 940 {
925 if(entered) 941 if(entered)
926 m_scenePresencesLock.ExitWriteLock(); 942 m_scenePresencesLock.ExitWriteLock();
927 } 943 }
944 return ret;
928 } 945 }
929 946
930 /// <summary> 947 /// <summary>