diff options
Diffstat (limited to 'OpenSim/Framework')
-rw-r--r-- | OpenSim/Framework/MinHeap.cs | 36 | ||||
-rw-r--r-- | OpenSim/Framework/PriorityQueue.cs | 61 |
2 files changed, 45 insertions, 52 deletions
diff --git a/OpenSim/Framework/MinHeap.cs b/OpenSim/Framework/MinHeap.cs index 2149b8a..2731e99 100644 --- a/OpenSim/Framework/MinHeap.cs +++ b/OpenSim/Framework/MinHeap.cs | |||
@@ -65,7 +65,7 @@ namespace OpenSim.Framework | |||
65 | { | 65 | { |
66 | if (handle != null) | 66 | if (handle != null) |
67 | { | 67 | { |
68 | handle.Clear(); | 68 | handle.heap = null; |
69 | handle = null; | 69 | handle = null; |
70 | } | 70 | } |
71 | value = default(T); | 71 | value = default(T); |
@@ -96,8 +96,8 @@ namespace OpenSim.Framework | |||
96 | public MinHeap(Comparison<T> comparison) : this(DEFAULT_CAPACITY, comparison) { } | 96 | public MinHeap(Comparison<T> comparison) : this(DEFAULT_CAPACITY, comparison) { } |
97 | public MinHeap(int _capacity, Comparison<T> _comparison) | 97 | public MinHeap(int _capacity, Comparison<T> _comparison) |
98 | { | 98 | { |
99 | minCapacity = _capacity; | 99 | minCapacity = 16; |
100 | items = new HeapItem[minCapacity]; | 100 | items = new HeapItem[_capacity]; |
101 | comparison = _comparison; | 101 | comparison = _comparison; |
102 | size = version = 0; | 102 | size = version = 0; |
103 | } | 103 | } |
@@ -169,8 +169,8 @@ namespace OpenSim.Framework | |||
169 | int current, parent; | 169 | int current, parent; |
170 | 170 | ||
171 | for (current = index, parent = (current - 1) / 2; | 171 | for (current = index, parent = (current - 1) / 2; |
172 | (current > 0) && (comparison(items[parent].value, item.value)) > 0; | 172 | (current > 0) && (comparison(items[parent].value, item.value)) > 0; |
173 | current = parent, parent = (current - 1) / 2) | 173 | current = parent, parent = (current - 1) / 2) |
174 | { | 174 | { |
175 | Set(items[parent], current); | 175 | Set(items[parent], current); |
176 | } | 176 | } |
@@ -187,11 +187,12 @@ namespace OpenSim.Framework | |||
187 | private void BubbleDown(int index) | 187 | private void BubbleDown(int index) |
188 | { | 188 | { |
189 | HeapItem item = items[index]; | 189 | HeapItem item = items[index]; |
190 | int current, child; | 190 | int current; |
191 | int child; | ||
191 | 192 | ||
192 | for (current = index, child = (2 * current) + 1; | 193 | for(current = index , child = (2 * current) + 1; |
193 | current < size / 2; | 194 | current < size / 2; |
194 | current = child, child = (2 * current) + 1) | 195 | current = child, child = (2 * current) + 1) |
195 | { | 196 | { |
196 | if ((child < size - 1) && comparison(items[child].value, items[child + 1].value) > 0) | 197 | if ((child < size - 1) && comparison(items[child].value, items[child + 1].value) > 0) |
197 | ++child; | 198 | ++child; |
@@ -293,14 +294,17 @@ namespace OpenSim.Framework | |||
293 | throw new ArgumentOutOfRangeException("index"); | 294 | throw new ArgumentOutOfRangeException("index"); |
294 | 295 | ||
295 | items[index].Clear(); | 296 | items[index].Clear(); |
296 | if (--size > 0 && index != size) | 297 | --size; |
297 | { | 298 | if (size > 0) |
298 | Set(items[size], index); | 299 | { if(index != size) |
299 | items[size].ClearRef(); | 300 | { |
300 | if (!BubbleUp(index)) | 301 | Set(items[size], index); |
301 | BubbleDown(index); | 302 | items[size].ClearRef(); |
303 | if (!BubbleUp(index)) | ||
304 | BubbleDown(index); | ||
305 | } | ||
302 | } | 306 | } |
303 | if(size == 0 && items.Length > 4 * minCapacity) | 307 | else if(items.Length > 4 * minCapacity) |
304 | items = new HeapItem[minCapacity]; | 308 | items = new HeapItem[minCapacity]; |
305 | } | 309 | } |
306 | 310 | ||
diff --git a/OpenSim/Framework/PriorityQueue.cs b/OpenSim/Framework/PriorityQueue.cs index 20d2049..53b4f8c 100644 --- a/OpenSim/Framework/PriorityQueue.cs +++ b/OpenSim/Framework/PriorityQueue.cs | |||
@@ -46,14 +46,14 @@ namespace OpenSim.Framework | |||
46 | /// Total number of queues (priorities) available | 46 | /// Total number of queues (priorities) available |
47 | /// </summary> | 47 | /// </summary> |
48 | 48 | ||
49 | public const uint NumberOfQueues = 12; // includes immediate queues, m_queueCounts need to be set acording | 49 | public const uint NumberOfQueues = 13; // includes immediate queues, m_queueCounts need to be set acording |
50 | 50 | ||
51 | /// <summary> | 51 | /// <summary> |
52 | /// Number of queuest (priorities) that are processed immediately | 52 | /// Number of queuest (priorities) that are processed immediately |
53 | /// </summary. | 53 | /// </summary. |
54 | public const uint NumberOfImmediateQueues = 2; | 54 | public const uint NumberOfImmediateQueues = 2; |
55 | // first queues are immediate, so no counts | 55 | // first queues are immediate, so no counts |
56 | private static readonly uint[] m_queueCounts = {0, 0, 8, 8, 5, 4, 3, 2, 1, 1, 1, 1}; | 56 | private static readonly uint[] m_queueCounts = {0, 0, 8, 8, 5, 4, 3, 2, 1, 1, 1, 1, 1 }; |
57 | // this is ava, ava, attach, <10m, 20,40,80,160m,320,640,1280, + | 57 | // this is ava, ava, attach, <10m, 20,40,80,160m,320,640,1280, + |
58 | 58 | ||
59 | private MinHeap<MinHeapItem>[] m_heaps = new MinHeap<MinHeapItem>[NumberOfQueues]; | 59 | private MinHeap<MinHeapItem>[] m_heaps = new MinHeap<MinHeapItem>[NumberOfQueues]; |
@@ -85,7 +85,7 @@ namespace OpenSim.Framework | |||
85 | 85 | ||
86 | public PriorityQueue(int capacity) | 86 | public PriorityQueue(int capacity) |
87 | { | 87 | { |
88 | m_capacity = capacity; | 88 | m_capacity = 16; |
89 | capacity /= 4; | 89 | capacity /= 4; |
90 | 90 | ||
91 | for (int i = 0; i < m_heaps.Length; ++i) | 91 | for (int i = 0; i < m_heaps.Length; ++i) |
@@ -137,14 +137,24 @@ namespace OpenSim.Framework | |||
137 | { | 137 | { |
138 | lookupH = lookup.Handle; | 138 | lookupH = lookup.Handle; |
139 | entry = lookup.Heap[lookupH].EntryOrder; | 139 | entry = lookup.Heap[lookupH].EntryOrder; |
140 | EntityUpdate up = lookup.Heap[lookupH].Value; | ||
140 | value.Update(lookup.Heap[lookupH].Value); | 141 | value.Update(lookup.Heap[lookupH].Value); |
141 | lookup.Heap.Remove(lookupH); | 142 | lookup.Heap.Remove(lookupH); |
143 | |||
144 | if((up.Flags & PrimUpdateFlags.CancelKill) != 0) | ||
145 | entry = m_nextRequest++; | ||
146 | |||
147 | pqueue = Util.Clamp<uint>(pqueue, 0, NumberOfQueues - 1); | ||
148 | lookup.Heap = m_heaps[pqueue]; | ||
149 | lookup.Heap.Add(new MinHeapItem(pqueue, entry, value), ref lookup.Handle); | ||
150 | m_lookupTable[localid] = lookup; | ||
151 | return true; | ||
142 | } | 152 | } |
143 | else | 153 | |
144 | { | 154 | value.Update(); |
145 | entry = m_nextRequest++; | 155 | |
146 | ++m_added; | 156 | entry = m_nextRequest++; |
147 | } | 157 | ++m_added; |
148 | 158 | ||
149 | pqueue = Util.Clamp<uint>(pqueue, 0, NumberOfQueues - 1); | 159 | pqueue = Util.Clamp<uint>(pqueue, 0, NumberOfQueues - 1); |
150 | lookup.Heap = m_heaps[pqueue]; | 160 | lookup.Heap = m_heaps[pqueue]; |
@@ -178,7 +188,7 @@ namespace OpenSim.Framework | |||
178 | /// oldest item from the next queue in order to provide fair access to | 188 | /// oldest item from the next queue in order to provide fair access to |
179 | /// all of the queues | 189 | /// all of the queues |
180 | /// </summary> | 190 | /// </summary> |
181 | public bool TryDequeue(out EntityUpdate value, out Int32 timeinqueue) | 191 | public bool TryDequeue(out EntityUpdate value) |
182 | { | 192 | { |
183 | // If there is anything in immediate queues, return it first no | 193 | // If there is anything in immediate queues, return it first no |
184 | // matter what else. Breaks fairness. But very useful. | 194 | // matter what else. Breaks fairness. But very useful. |
@@ -189,7 +199,6 @@ namespace OpenSim.Framework | |||
189 | { | 199 | { |
190 | MinHeapItem item = m_heaps[iq].RemoveMin(); | 200 | MinHeapItem item = m_heaps[iq].RemoveMin(); |
191 | m_lookupTable.Remove(item.Value.Entity.LocalId); | 201 | m_lookupTable.Remove(item.Value.Entity.LocalId); |
192 | timeinqueue = Util.EnvironmentTickCountSubtract(item.EntryTime); | ||
193 | value = item.Value; | 202 | value = item.Value; |
194 | 203 | ||
195 | return true; | 204 | return true; |
@@ -210,9 +219,7 @@ namespace OpenSim.Framework | |||
210 | 219 | ||
211 | MinHeapItem item = curheap.RemoveMin(); | 220 | MinHeapItem item = curheap.RemoveMin(); |
212 | m_lookupTable.Remove(item.Value.Entity.LocalId); | 221 | m_lookupTable.Remove(item.Value.Entity.LocalId); |
213 | timeinqueue = Util.EnvironmentTickCountSubtract(item.EntryTime); | ||
214 | value = item.Value; | 222 | value = item.Value; |
215 | |||
216 | return true; | 223 | return true; |
217 | } | 224 | } |
218 | 225 | ||
@@ -232,12 +239,10 @@ namespace OpenSim.Framework | |||
232 | 239 | ||
233 | MinHeapItem item = curheap.RemoveMin(); | 240 | MinHeapItem item = curheap.RemoveMin(); |
234 | m_lookupTable.Remove(item.Value.Entity.LocalId); | 241 | m_lookupTable.Remove(item.Value.Entity.LocalId); |
235 | timeinqueue = Util.EnvironmentTickCountSubtract(item.EntryTime); | ||
236 | value = item.Value; | 242 | value = item.Value; |
237 | return true; | 243 | return true; |
238 | } | 244 | } |
239 | 245 | ||
240 | timeinqueue = 0; | ||
241 | value = default(EntityUpdate); | 246 | value = default(EntityUpdate); |
242 | if(m_lookupTable.Count == 0 && m_added > 8 * m_capacity) | 247 | if(m_lookupTable.Count == 0 && m_added > 8 * m_capacity) |
243 | { | 248 | { |
@@ -247,23 +252,20 @@ namespace OpenSim.Framework | |||
247 | return false; | 252 | return false; |
248 | } | 253 | } |
249 | 254 | ||
250 | public bool TryOrderedDequeue(out EntityUpdate value, out Int32 timeinqueue) | 255 | public bool TryOrderedDequeue(out EntityUpdate value) |
251 | { | 256 | { |
252 | MinHeap<MinHeapItem> curheap; | ||
253 | for (int iq = 0; iq < NumberOfQueues; ++iq) | 257 | for (int iq = 0; iq < NumberOfQueues; ++iq) |
254 | { | 258 | { |
255 | curheap = m_heaps[iq]; | 259 | MinHeap<MinHeapItem> curheap = m_heaps[iq]; |
256 | if (curheap.Count > 0) | 260 | if (curheap.Count > 0) |
257 | { | 261 | { |
258 | MinHeapItem item = curheap.RemoveMin(); | 262 | MinHeapItem item = curheap.RemoveMin(); |
259 | m_lookupTable.Remove(item.Value.Entity.LocalId); | 263 | m_lookupTable.Remove(item.Value.Entity.LocalId); |
260 | timeinqueue = Util.EnvironmentTickCountSubtract(item.EntryTime); | ||
261 | value = item.Value; | 264 | value = item.Value; |
262 | return true; | 265 | return true; |
263 | } | 266 | } |
264 | } | 267 | } |
265 | 268 | ||
266 | timeinqueue = 0; | ||
267 | value = default(EntityUpdate); | 269 | value = default(EntityUpdate); |
268 | if(m_lookupTable.Count == 0 && m_added > 8 * m_capacity) | 270 | if(m_lookupTable.Count == 0 && m_added > 8 * m_capacity) |
269 | { | 271 | { |
@@ -280,13 +282,11 @@ namespace OpenSim.Framework | |||
280 | public void Reprioritize(UpdatePriorityHandler handler) | 282 | public void Reprioritize(UpdatePriorityHandler handler) |
281 | { | 283 | { |
282 | MinHeapItem item; | 284 | MinHeapItem item; |
285 | uint pqueue = 0; | ||
283 | foreach (LookupItem lookup in new List<LookupItem>(m_lookupTable.Values)) | 286 | foreach (LookupItem lookup in new List<LookupItem>(m_lookupTable.Values)) |
284 | { | 287 | { |
285 | if (lookup.Heap.TryGetValue(lookup.Handle, out item)) | 288 | if (lookup.Heap.TryGetValue(lookup.Handle, out item)) |
286 | { | 289 | { |
287 | uint pqueue = item.PriorityQueue; | ||
288 | uint localid = item.Value.Entity.LocalId; | ||
289 | |||
290 | if (handler(ref pqueue, item.Value.Entity)) | 290 | if (handler(ref pqueue, item.Value.Entity)) |
291 | { | 291 | { |
292 | // unless the priority queue has changed, there is no need to modify | 292 | // unless the priority queue has changed, there is no need to modify |
@@ -299,14 +299,14 @@ namespace OpenSim.Framework | |||
299 | LookupItem litem = lookup; | 299 | LookupItem litem = lookup; |
300 | litem.Heap = m_heaps[pqueue]; | 300 | litem.Heap = m_heaps[pqueue]; |
301 | litem.Heap.Add(new MinHeapItem(pqueue, item), ref litem.Handle); | 301 | litem.Heap.Add(new MinHeapItem(pqueue, item), ref litem.Handle); |
302 | m_lookupTable[localid] = litem; | 302 | m_lookupTable[item.Value.Entity.LocalId] = litem; |
303 | } | 303 | } |
304 | } | 304 | } |
305 | else | 305 | else |
306 | { | 306 | { |
307 | // m_log.WarnFormat("[PQUEUE]: UpdatePriorityHandler returned false for {0}",item.Value.Entity.UUID); | 307 | // m_log.WarnFormat("[PQUEUE]: UpdatePriorityHandler returned false for {0}",item.Value.Entity.UUID); |
308 | lookup.Heap.Remove(lookup.Handle); | 308 | lookup.Heap.Remove(lookup.Handle); |
309 | m_lookupTable.Remove(localid); | 309 | m_lookupTable.Remove(item.Value.Entity.LocalId); |
310 | } | 310 | } |
311 | } | 311 | } |
312 | } | 312 | } |
@@ -318,7 +318,7 @@ namespace OpenSim.Framework | |||
318 | { | 318 | { |
319 | string s = ""; | 319 | string s = ""; |
320 | for (int i = 0; i < NumberOfQueues; i++) | 320 | for (int i = 0; i < NumberOfQueues; i++) |
321 | s += String.Format("{0,7} ",m_heaps[i].Count); | 321 | s += String.Format("{0,7} ", m_heaps[i].Count); |
322 | return s; | 322 | return s; |
323 | } | 323 | } |
324 | 324 | ||
@@ -345,15 +345,6 @@ namespace OpenSim.Framework | |||
345 | } | 345 | } |
346 | } | 346 | } |
347 | 347 | ||
348 | private Int32 entrytime; | ||
349 | internal Int32 EntryTime | ||
350 | { | ||
351 | get | ||
352 | { | ||
353 | return entrytime; | ||
354 | } | ||
355 | } | ||
356 | |||
357 | private UInt64 entryorder; | 348 | private UInt64 entryorder; |
358 | internal UInt64 EntryOrder | 349 | internal UInt64 EntryOrder |
359 | { | 350 | { |
@@ -365,7 +356,6 @@ namespace OpenSim.Framework | |||
365 | 356 | ||
366 | internal MinHeapItem(uint _pqueue, MinHeapItem other) | 357 | internal MinHeapItem(uint _pqueue, MinHeapItem other) |
367 | { | 358 | { |
368 | entrytime = other.entrytime; | ||
369 | entryorder = other.entryorder; | 359 | entryorder = other.entryorder; |
370 | value = other.value; | 360 | value = other.value; |
371 | pqueue = _pqueue; | 361 | pqueue = _pqueue; |
@@ -373,7 +363,6 @@ namespace OpenSim.Framework | |||
373 | 363 | ||
374 | internal MinHeapItem(uint _pqueue, UInt64 _entryorder, EntityUpdate _value) | 364 | internal MinHeapItem(uint _pqueue, UInt64 _entryorder, EntityUpdate _value) |
375 | { | 365 | { |
376 | entrytime = Util.EnvironmentTickCount(); | ||
377 | entryorder = _entryorder; | 366 | entryorder = _entryorder; |
378 | value = _value; | 367 | value = _value; |
379 | pqueue = _pqueue; | 368 | pqueue = _pqueue; |