aboutsummaryrefslogtreecommitdiffstatshomepage
path: root/OpenSim/Region/Framework/Scenes/EntityManager.cs
diff options
context:
space:
mode:
Diffstat (limited to 'OpenSim/Region/Framework/Scenes/EntityManager.cs')
-rw-r--r--OpenSim/Region/Framework/Scenes/EntityManager.cs261
1 files changed, 41 insertions, 220 deletions
diff --git a/OpenSim/Region/Framework/Scenes/EntityManager.cs b/OpenSim/Region/Framework/Scenes/EntityManager.cs
index c246e32..0defa93 100644
--- a/OpenSim/Region/Framework/Scenes/EntityManager.cs
+++ b/OpenSim/Region/Framework/Scenes/EntityManager.cs
@@ -34,227 +34,89 @@ using OpenMetaverse;
34 34
35namespace OpenSim.Region.Framework.Scenes 35namespace OpenSim.Region.Framework.Scenes
36{ 36{
37 public class EntityManager : IEnumerable<EntityBase> 37 public class EntityManager
38 { 38 {
39 private static readonly ILog m_log = LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType); 39 private static readonly ILog m_log = LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType);
40 private readonly Dictionary<UUID,EntityBase> m_eb_uuid = new Dictionary<UUID, EntityBase>(); 40 private readonly DoubleDictionary<UUID, uint, EntityBase> m_entities = new DoubleDictionary<UUID, uint, EntityBase>();
41 private readonly Dictionary<uint, EntityBase> m_eb_localID = new Dictionary<uint, EntityBase>();
42 //private readonly Dictionary<UUID, ScenePresence> m_pres_uuid = new Dictionary<UUID, ScenePresence>();
43 private System.Threading.ReaderWriterLockSlim m_lock = new System.Threading.ReaderWriterLockSlim();
44 41
45 [Obsolete("Use Add() instead.")] 42 public int Count
46 public void Add(UUID id, EntityBase eb)
47 { 43 {
48 Add(eb); 44 get { return m_entities.Count; }
49 } 45 }
50 46
51 public void Add(EntityBase entity) 47 public void Add(EntityBase entity)
52 { 48 {
53 m_lock.EnterWriteLock(); 49 m_entities.Add(entity.UUID, entity.LocalId, entity);
54 try
55 {
56 try
57 {
58 m_eb_uuid.Add(entity.UUID, entity);
59 m_eb_localID.Add(entity.LocalId, entity);
60 }
61 catch(Exception e)
62 {
63 m_log.ErrorFormat("Add Entity failed: {0}", e.Message);
64 }
65 }
66 finally
67 {
68 m_lock.ExitWriteLock();
69 }
70 }
71
72 public void InsertOrReplace(EntityBase entity)
73 {
74 m_lock.EnterWriteLock();
75 try
76 {
77 try
78 {
79 m_eb_uuid[entity.UUID] = entity;
80 m_eb_localID[entity.LocalId] = entity;
81 }
82 catch(Exception e)
83 {
84 m_log.ErrorFormat("Insert or Replace Entity failed: {0}", e.Message);
85 }
86 }
87 finally
88 {
89 m_lock.ExitWriteLock();
90 }
91 } 50 }
92 51
93 public void Clear() 52 public void Clear()
94 { 53 {
95 m_lock.EnterWriteLock(); 54 m_entities.Clear();
96 try
97 {
98 m_eb_uuid.Clear();
99 m_eb_localID.Clear();
100 }
101 finally
102 {
103 m_lock.ExitWriteLock();
104 }
105 }
106
107 public int Count
108 {
109 get
110 {
111 return m_eb_uuid.Count;
112 }
113 } 55 }
114 56
115 public bool ContainsKey(UUID id) 57 public bool ContainsKey(UUID id)
116 { 58 {
117 try 59 return m_entities.ContainsKey(id);
118 {
119 return m_eb_uuid.ContainsKey(id);
120 }
121 catch
122 {
123 return false;
124 }
125 } 60 }
126 61
127 public bool ContainsKey(uint localID) 62 public bool ContainsKey(uint localID)
128 { 63 {
129 try 64 return m_entities.ContainsKey(localID);
130 {
131 return m_eb_localID.ContainsKey(localID);
132 }
133 catch
134 {
135 return false;
136 }
137 } 65 }
138 66
139 public bool Remove(uint localID) 67 public bool Remove(uint localID)
140 { 68 {
141 m_lock.EnterWriteLock(); 69 return m_entities.Remove(localID);
142 try
143 {
144 try
145 {
146 bool a = false;
147 EntityBase entity;
148 if (m_eb_localID.TryGetValue(localID, out entity))
149 a = m_eb_uuid.Remove(entity.UUID);
150
151 bool b = m_eb_localID.Remove(localID);
152 return a && b;
153 }
154 catch (Exception e)
155 {
156 m_log.ErrorFormat("Remove Entity failed for {0}", localID, e);
157 return false;
158 }
159 }
160 finally
161 {
162 m_lock.ExitWriteLock();
163 }
164 } 70 }
165 71
166 public bool Remove(UUID id) 72 public bool Remove(UUID id)
167 { 73 {
168 m_lock.EnterWriteLock(); 74 return m_entities.Remove(id);
169 try
170 {
171 try
172 {
173 bool a = false;
174 EntityBase entity;
175 if (m_eb_uuid.TryGetValue(id, out entity))
176 a = m_eb_localID.Remove(entity.LocalId);
177
178 bool b = m_eb_uuid.Remove(id);
179 return a && b;
180 }
181 catch (Exception e)
182 {
183 m_log.ErrorFormat("Remove Entity failed for {0}", id, e);
184 return false;
185 }
186 }
187 finally
188 {
189 m_lock.ExitWriteLock();
190 }
191 } 75 }
192 76
193 public List<EntityBase> GetAllByType<T>() 77 public EntityBase[] GetAllByType<T>()
194 { 78 {
195 List<EntityBase> tmp = new List<EntityBase>(); 79 List<EntityBase> tmp = new List<EntityBase>();
196 80
197 m_lock.EnterReadLock(); 81 m_entities.ForEach(
198 try 82 delegate(EntityBase entity)
199 {
200 try
201 {
202 foreach (KeyValuePair<UUID, EntityBase> pair in m_eb_uuid)
203 {
204 if (pair.Value is T)
205 {
206 tmp.Add(pair.Value);
207 }
208 }
209 }
210 catch (Exception e)
211 { 83 {
212 m_log.ErrorFormat("GetAllByType failed for {0}", e); 84 if (entity is T)
213 tmp = null; 85 tmp.Add(entity);
214 } 86 }
215 } 87 );
216 finally
217 {
218 m_lock.ExitReadLock();
219 }
220 88
221 return tmp; 89 return tmp.ToArray();
222 } 90 }
223 91
224 public List<EntityBase> GetEntities() 92 public EntityBase[] GetEntities()
225 { 93 {
226 m_lock.EnterReadLock(); 94 List<EntityBase> tmp = new List<EntityBase>(m_entities.Count);
227 try 95 m_entities.ForEach(delegate(EntityBase entity) { tmp.Add(entity); });
228 { 96 return tmp.ToArray();
229 return new List<EntityBase>(m_eb_uuid.Values); 97 }
230 } 98
231 finally 99 public void ForEach(Action<EntityBase> action)
232 { 100 {
233 m_lock.ExitReadLock(); 101 m_entities.ForEach(action);
234 } 102 }
103
104 public EntityBase Find(Predicate<EntityBase> predicate)
105 {
106 return m_entities.FindValue(predicate);
235 } 107 }
236 108
237 public EntityBase this[UUID id] 109 public EntityBase this[UUID id]
238 { 110 {
239 get 111 get
240 { 112 {
241 m_lock.EnterReadLock(); 113 EntityBase entity;
242 try 114 m_entities.TryGetValue(id, out entity);
243 { 115 return entity;
244 EntityBase entity;
245 if (m_eb_uuid.TryGetValue(id, out entity))
246 return entity;
247 else
248 return null;
249 }
250 finally
251 {
252 m_lock.ExitReadLock();
253 }
254 } 116 }
255 set 117 set
256 { 118 {
257 InsertOrReplace(value); 119 Add(value);
258 } 120 }
259 } 121 }
260 122
@@ -262,65 +124,24 @@ namespace OpenSim.Region.Framework.Scenes
262 { 124 {
263 get 125 get
264 { 126 {
265 m_lock.EnterReadLock(); 127 EntityBase entity;
266 try 128 m_entities.TryGetValue(localID, out entity);
267 { 129 return entity;
268 EntityBase entity;
269 if (m_eb_localID.TryGetValue(localID, out entity))
270 return entity;
271 else
272 return null;
273 }
274 finally
275 {
276 m_lock.ExitReadLock();
277 }
278 } 130 }
279 set 131 set
280 { 132 {
281 InsertOrReplace(value); 133 Add(value);
282 } 134 }
283 } 135 }
284 136
285 public bool TryGetValue(UUID key, out EntityBase obj) 137 public bool TryGetValue(UUID key, out EntityBase obj)
286 { 138 {
287 m_lock.EnterReadLock(); 139 return m_entities.TryGetValue(key, out obj);
288 try
289 {
290 return m_eb_uuid.TryGetValue(key, out obj);
291 }
292 finally
293 {
294 m_lock.ExitReadLock();
295 }
296 } 140 }
297 141
298 public bool TryGetValue(uint key, out EntityBase obj) 142 public bool TryGetValue(uint key, out EntityBase obj)
299 { 143 {
300 m_lock.EnterReadLock(); 144 return m_entities.TryGetValue(key, out obj);
301 try
302 {
303 return m_eb_localID.TryGetValue(key, out obj);
304 }
305 finally
306 {
307 m_lock.ExitReadLock();
308 }
309 }
310
311 /// <summary>
312 /// This could be optimised to work on the list 'live' rather than making a safe copy and iterating that.
313 /// </summary>
314 /// <returns></returns>
315 public IEnumerator<EntityBase> GetEnumerator()
316 {
317 return GetEntities().GetEnumerator();
318 }
319
320 IEnumerator IEnumerable.GetEnumerator()
321 {
322 return GetEnumerator();
323 } 145 }
324
325 } 146 }
326} 147}