aboutsummaryrefslogtreecommitdiffstatshomepage
path: root/OpenSim/Region/Framework/Scenes/SceneObjectPartInventory.cs
diff options
context:
space:
mode:
Diffstat (limited to 'OpenSim/Region/Framework/Scenes/SceneObjectPartInventory.cs')
-rw-r--r--OpenSim/Region/Framework/Scenes/SceneObjectPartInventory.cs767
1 files changed, 465 insertions, 302 deletions
diff --git a/OpenSim/Region/Framework/Scenes/SceneObjectPartInventory.cs b/OpenSim/Region/Framework/Scenes/SceneObjectPartInventory.cs
index 380e402..b4fc472 100644
--- a/OpenSim/Region/Framework/Scenes/SceneObjectPartInventory.cs
+++ b/OpenSim/Region/Framework/Scenes/SceneObjectPartInventory.cs
@@ -49,6 +49,9 @@ namespace OpenSim.Region.Framework.Scenes
49 private string m_inventoryFileName = String.Empty; 49 private string m_inventoryFileName = String.Empty;
50 private byte[] m_inventoryFileData = new byte[0]; 50 private byte[] m_inventoryFileData = new byte[0];
51 private uint m_inventoryFileNameSerial = 0; 51 private uint m_inventoryFileNameSerial = 0;
52 private bool m_inventoryPrivileged = false;
53
54 private Dictionary<UUID, ArrayList> m_scriptErrors = new Dictionary<UUID, ArrayList>();
52 55
53 /// <value> 56 /// <value>
54 /// The part to which the inventory belongs. 57 /// The part to which the inventory belongs.
@@ -85,7 +88,9 @@ namespace OpenSim.Region.Framework.Scenes
85 /// </value> 88 /// </value>
86 protected internal TaskInventoryDictionary Items 89 protected internal TaskInventoryDictionary Items
87 { 90 {
88 get { return m_items; } 91 get {
92 return m_items;
93 }
89 set 94 set
90 { 95 {
91 m_items = value; 96 m_items = value;
@@ -134,38 +139,45 @@ namespace OpenSim.Region.Framework.Scenes
134 public void ResetInventoryIDs() 139 public void ResetInventoryIDs()
135 { 140 {
136 if (null == m_part) 141 if (null == m_part)
137 return; 142 m_items.LockItemsForWrite(true);
138 143
139 lock (m_items) 144 if (Items.Count == 0)
140 { 145 {
141 if (0 == m_items.Count) 146 m_items.LockItemsForWrite(false);
142 return; 147 return;
148 }
143 149
144 IList<TaskInventoryItem> items = GetInventoryItems(); 150 IList<TaskInventoryItem> items = new List<TaskInventoryItem>(Items.Values);
145 m_items.Clear(); 151 Items.Clear();
146 152
147 foreach (TaskInventoryItem item in items) 153 foreach (TaskInventoryItem item in items)
148 { 154 {
149 item.ResetIDs(m_part.UUID); 155 item.ResetIDs(m_part.UUID);
150 m_items.Add(item.ItemID, item); 156 Items.Add(item.ItemID, item);
151 }
152 } 157 }
158 m_items.LockItemsForWrite(false);
153 } 159 }
154 160
155 public void ResetObjectID() 161 public void ResetObjectID()
156 { 162 {
157 lock (Items) 163 m_items.LockItemsForWrite(true);
164
165 if (Items.Count == 0)
158 { 166 {
159 IList<TaskInventoryItem> items = new List<TaskInventoryItem>(Items.Values); 167 m_items.LockItemsForWrite(false);
160 Items.Clear(); 168 return;
161
162 foreach (TaskInventoryItem item in items)
163 {
164 item.ParentPartID = m_part.UUID;
165 item.ParentID = m_part.UUID;
166 Items.Add(item.ItemID, item);
167 }
168 } 169 }
170
171 IList<TaskInventoryItem> items = new List<TaskInventoryItem>(Items.Values);
172 Items.Clear();
173
174 foreach (TaskInventoryItem item in items)
175 {
176 item.ParentPartID = m_part.UUID;
177 item.ParentID = m_part.UUID;
178 Items.Add(item.ItemID, item);
179 }
180 m_items.LockItemsForWrite(false);
169 } 181 }
170 182
171 /// <summary> 183 /// <summary>
@@ -174,17 +186,14 @@ namespace OpenSim.Region.Framework.Scenes
174 /// <param name="ownerId"></param> 186 /// <param name="ownerId"></param>
175 public void ChangeInventoryOwner(UUID ownerId) 187 public void ChangeInventoryOwner(UUID ownerId)
176 { 188 {
177 lock (Items) 189 List<TaskInventoryItem> items = GetInventoryItems();
178 { 190
179 if (0 == Items.Count) 191 if (items.Count == 0)
180 { 192 return;
181 return;
182 }
183 }
184 193
194 m_items.LockItemsForWrite(true);
185 HasInventoryChanged = true; 195 HasInventoryChanged = true;
186 m_part.ParentGroup.HasGroupChanged = true; 196 m_part.ParentGroup.HasGroupChanged = true;
187 List<TaskInventoryItem> items = GetInventoryItems();
188 foreach (TaskInventoryItem item in items) 197 foreach (TaskInventoryItem item in items)
189 { 198 {
190 if (ownerId != item.OwnerID) 199 if (ownerId != item.OwnerID)
@@ -195,6 +204,7 @@ namespace OpenSim.Region.Framework.Scenes
195 item.PermsGranter = UUID.Zero; 204 item.PermsGranter = UUID.Zero;
196 item.OwnerChanged = true; 205 item.OwnerChanged = true;
197 } 206 }
207 m_items.LockItemsForWrite(false);
198 } 208 }
199 209
200 /// <summary> 210 /// <summary>
@@ -203,12 +213,11 @@ namespace OpenSim.Region.Framework.Scenes
203 /// <param name="groupID"></param> 213 /// <param name="groupID"></param>
204 public void ChangeInventoryGroup(UUID groupID) 214 public void ChangeInventoryGroup(UUID groupID)
205 { 215 {
206 lock (Items) 216 m_items.LockItemsForWrite(true);
217 if (0 == Items.Count)
207 { 218 {
208 if (0 == Items.Count) 219 m_items.LockItemsForWrite(false);
209 { 220 return;
210 return;
211 }
212 } 221 }
213 222
214 // Don't let this set the HasGroupChanged flag for attachments 223 // Don't let this set the HasGroupChanged flag for attachments
@@ -220,12 +229,15 @@ namespace OpenSim.Region.Framework.Scenes
220 m_part.ParentGroup.HasGroupChanged = true; 229 m_part.ParentGroup.HasGroupChanged = true;
221 } 230 }
222 231
223 List<TaskInventoryItem> items = GetInventoryItems(); 232 IList<TaskInventoryItem> items = new List<TaskInventoryItem>(Items.Values);
224 foreach (TaskInventoryItem item in items) 233 foreach (TaskInventoryItem item in items)
225 { 234 {
226 if (groupID != item.GroupID) 235 if (groupID != item.GroupID)
236 {
227 item.GroupID = groupID; 237 item.GroupID = groupID;
238 }
228 } 239 }
240 m_items.LockItemsForWrite(false);
229 } 241 }
230 242
231 private void QueryScriptStates() 243 private void QueryScriptStates()
@@ -233,15 +245,18 @@ namespace OpenSim.Region.Framework.Scenes
233 if (m_part == null || m_part.ParentGroup == null || m_part.ParentGroup.Scene == null) 245 if (m_part == null || m_part.ParentGroup == null || m_part.ParentGroup.Scene == null)
234 return; 246 return;
235 247
236 lock (Items) 248 Items.LockItemsForRead(true);
249 foreach (TaskInventoryItem item in Items.Values)
237 { 250 {
238 foreach (TaskInventoryItem item in Items.Values) 251 if (item.InvType == (int)InventoryType.LSL)
239 { 252 {
240 bool running; 253 bool running;
241 if (TryGetScriptInstanceRunning(m_part.ParentGroup.Scene, item, out running)) 254 if (TryGetScriptInstanceRunning(m_part.ParentGroup.Scene, item, out running))
242 item.ScriptRunning = running; 255 item.ScriptRunning = running;
243 } 256 }
244 } 257 }
258
259 Items.LockItemsForRead(false);
245 } 260 }
246 261
247 public bool TryGetScriptInstanceRunning(UUID itemId, out bool running) 262 public bool TryGetScriptInstanceRunning(UUID itemId, out bool running)
@@ -318,7 +333,10 @@ namespace OpenSim.Region.Framework.Scenes
318 { 333 {
319 List<TaskInventoryItem> scripts = GetInventoryItems(InventoryType.LSL); 334 List<TaskInventoryItem> scripts = GetInventoryItems(InventoryType.LSL);
320 foreach (TaskInventoryItem item in scripts) 335 foreach (TaskInventoryItem item in scripts)
336 {
321 RemoveScriptInstance(item.ItemID, sceneObjectBeingDeleted); 337 RemoveScriptInstance(item.ItemID, sceneObjectBeingDeleted);
338 m_part.RemoveScriptEvents(item.ItemID);
339 }
322 } 340 }
323 341
324 /// <summary> 342 /// <summary>
@@ -340,7 +358,10 @@ namespace OpenSim.Region.Framework.Scenes
340// item.Name, item.ItemID, m_part.Name, m_part.UUID, m_part.ParentGroup.Scene.RegionInfo.RegionName); 358// item.Name, item.ItemID, m_part.Name, m_part.UUID, m_part.ParentGroup.Scene.RegionInfo.RegionName);
341 359
342 if (!m_part.ParentGroup.Scene.Permissions.CanRunScript(item.ItemID, m_part.UUID, item.OwnerID)) 360 if (!m_part.ParentGroup.Scene.Permissions.CanRunScript(item.ItemID, m_part.UUID, item.OwnerID))
361 {
362 StoreScriptError(item.ItemID, "no permission");
343 return false; 363 return false;
364 }
344 365
345 m_part.AddFlag(PrimFlags.Scripted); 366 m_part.AddFlag(PrimFlags.Scripted);
346 367
@@ -350,14 +371,13 @@ namespace OpenSim.Region.Framework.Scenes
350 if (stateSource == 2 && // Prim crossing 371 if (stateSource == 2 && // Prim crossing
351 m_part.ParentGroup.Scene.m_trustBinaries) 372 m_part.ParentGroup.Scene.m_trustBinaries)
352 { 373 {
353 lock (m_items) 374 m_items.LockItemsForWrite(true);
354 { 375 m_items[item.ItemID].PermsMask = 0;
355 m_items[item.ItemID].PermsMask = 0; 376 m_items[item.ItemID].PermsGranter = UUID.Zero;
356 m_items[item.ItemID].PermsGranter = UUID.Zero; 377 m_items.LockItemsForWrite(false);
357 }
358
359 m_part.ParentGroup.Scene.EventManager.TriggerRezScript( 378 m_part.ParentGroup.Scene.EventManager.TriggerRezScript(
360 m_part.LocalId, item.ItemID, String.Empty, startParam, postOnRez, engine, stateSource); 379 m_part.LocalId, item.ItemID, String.Empty, startParam, postOnRez, engine, stateSource);
380 StoreScriptErrors(item.ItemID, null);
361 m_part.ParentGroup.AddActiveScriptCount(1); 381 m_part.ParentGroup.AddActiveScriptCount(1);
362 m_part.ScheduleFullUpdate(); 382 m_part.ScheduleFullUpdate();
363 return true; 383 return true;
@@ -366,6 +386,8 @@ namespace OpenSim.Region.Framework.Scenes
366 AssetBase asset = m_part.ParentGroup.Scene.AssetService.Get(item.AssetID.ToString()); 386 AssetBase asset = m_part.ParentGroup.Scene.AssetService.Get(item.AssetID.ToString());
367 if (null == asset) 387 if (null == asset)
368 { 388 {
389 string msg = String.Format("asset ID {0} could not be found", item.AssetID);
390 StoreScriptError(item.ItemID, msg);
369 m_log.ErrorFormat( 391 m_log.ErrorFormat(
370 "[PRIM INVENTORY]: Couldn't start script {0}, {1} at {2} in {3} since asset ID {4} could not be found", 392 "[PRIM INVENTORY]: Couldn't start script {0}, {1} at {2} in {3} since asset ID {4} could not be found",
371 item.Name, item.ItemID, m_part.AbsolutePosition, 393 item.Name, item.ItemID, m_part.AbsolutePosition,
@@ -378,16 +400,18 @@ namespace OpenSim.Region.Framework.Scenes
378 if (m_part.ParentGroup.m_savedScriptState != null) 400 if (m_part.ParentGroup.m_savedScriptState != null)
379 item.OldItemID = RestoreSavedScriptState(item.LoadedItemID, item.OldItemID, item.ItemID); 401 item.OldItemID = RestoreSavedScriptState(item.LoadedItemID, item.OldItemID, item.ItemID);
380 402
381 lock (m_items) 403 m_items.LockItemsForWrite(true);
382 { 404
383 m_items[item.ItemID].OldItemID = item.OldItemID; 405 m_items[item.ItemID].OldItemID = item.OldItemID;
384 m_items[item.ItemID].PermsMask = 0; 406 m_items[item.ItemID].PermsMask = 0;
385 m_items[item.ItemID].PermsGranter = UUID.Zero; 407 m_items[item.ItemID].PermsGranter = UUID.Zero;
386 }
387 408
409 m_items.LockItemsForWrite(false);
410
388 string script = Utils.BytesToString(asset.Data); 411 string script = Utils.BytesToString(asset.Data);
389 m_part.ParentGroup.Scene.EventManager.TriggerRezScript( 412 m_part.ParentGroup.Scene.EventManager.TriggerRezScript(
390 m_part.LocalId, item.ItemID, script, startParam, postOnRez, engine, stateSource); 413 m_part.LocalId, item.ItemID, script, startParam, postOnRez, engine, stateSource);
414 StoreScriptErrors(item.ItemID, null);
391 if (!item.ScriptRunning) 415 if (!item.ScriptRunning)
392 m_part.ParentGroup.Scene.EventManager.TriggerStopScript( 416 m_part.ParentGroup.Scene.EventManager.TriggerStopScript(
393 m_part.LocalId, item.ItemID); 417 m_part.LocalId, item.ItemID);
@@ -460,22 +484,149 @@ namespace OpenSim.Region.Framework.Scenes
460 return stateID; 484 return stateID;
461 } 485 }
462 486
487 /// <summary>
488 /// Start a script which is in this prim's inventory.
489 /// Some processing may occur in the background, but this routine returns asap.
490 /// </summary>
491 /// <param name="itemId">
492 /// A <see cref="UUID"/>
493 /// </param>
463 public bool CreateScriptInstance(UUID itemId, int startParam, bool postOnRez, string engine, int stateSource) 494 public bool CreateScriptInstance(UUID itemId, int startParam, bool postOnRez, string engine, int stateSource)
464 { 495 {
465 TaskInventoryItem item = GetInventoryItem(itemId); 496 lock (m_scriptErrors)
466 if (item != null)
467 { 497 {
468 return CreateScriptInstance(item, startParam, postOnRez, engine, stateSource); 498 // Indicate to CreateScriptInstanceInternal() we don't want it to wait for completion
499 m_scriptErrors.Remove(itemId);
500 }
501 CreateScriptInstanceInternal(itemId, startParam, postOnRez, engine, stateSource);
502 return true;
503 }
504
505 private void CreateScriptInstanceInternal(UUID itemId, int startParam, bool postOnRez, string engine, int stateSource)
506 {
507 m_items.LockItemsForRead(true);
508 if (m_items.ContainsKey(itemId))
509 {
510 if (m_items.ContainsKey(itemId))
511 {
512 m_items.LockItemsForRead(false);
513 CreateScriptInstance(m_items[itemId], startParam, postOnRez, engine, stateSource);
514 }
515 else
516 {
517 m_items.LockItemsForRead(false);
518 string msg = String.Format("couldn't be found for prim {0}, {1} at {2} in {3}", m_part.Name, m_part.UUID,
519 m_part.AbsolutePosition, m_part.ParentGroup.Scene.RegionInfo.RegionName);
520 StoreScriptError(itemId, msg);
521 m_log.ErrorFormat(
522 "[PRIM INVENTORY]: " +
523 "Couldn't start script with ID {0} since it {1}", itemId, msg);
524 }
469 } 525 }
470 else 526 else
471 { 527 {
528 m_items.LockItemsForRead(false);
529 string msg = String.Format("couldn't be found for prim {0}, {1}", m_part.Name, m_part.UUID);
530 StoreScriptError(itemId, msg);
472 m_log.ErrorFormat( 531 m_log.ErrorFormat(
473 "[PRIM INVENTORY]: Couldn't start script with ID {0} since it couldn't be found for prim {1}, {2} at {3} in {4}", 532 "[PRIM INVENTORY]: Couldn't start script with ID {0} since it couldn't be found for prim {1}, {2} at {3} in {4}",
474 itemId, m_part.Name, m_part.UUID, 533 itemId, m_part.Name, m_part.UUID,
475 m_part.AbsolutePosition, m_part.ParentGroup.Scene.RegionInfo.RegionName); 534 m_part.AbsolutePosition, m_part.ParentGroup.Scene.RegionInfo.RegionName);
535 }
536
537 }
476 538
477 return false; 539 /// <summary>
540 /// Start a script which is in this prim's inventory and return any compilation error messages.
541 /// </summary>
542 /// <param name="itemId">
543 /// A <see cref="UUID"/>
544 /// </param>
545 public ArrayList CreateScriptInstanceEr(UUID itemId, int startParam, bool postOnRez, string engine, int stateSource)
546 {
547 ArrayList errors;
548
549 // Indicate to CreateScriptInstanceInternal() we want it to
550 // post any compilation/loading error messages
551 lock (m_scriptErrors)
552 {
553 m_scriptErrors[itemId] = null;
554 }
555
556 // Perform compilation/loading
557 CreateScriptInstanceInternal(itemId, startParam, postOnRez, engine, stateSource);
558
559 // Wait for and retrieve any errors
560 lock (m_scriptErrors)
561 {
562 while ((errors = m_scriptErrors[itemId]) == null)
563 {
564 if (!System.Threading.Monitor.Wait(m_scriptErrors, 15000))
565 {
566 m_log.ErrorFormat(
567 "[PRIM INVENTORY]: " +
568 "timedout waiting for script {0} errors", itemId);
569 errors = m_scriptErrors[itemId];
570 if (errors == null)
571 {
572 errors = new ArrayList(1);
573 errors.Add("timedout waiting for errors");
574 }
575 break;
576 }
577 }
578 m_scriptErrors.Remove(itemId);
478 } 579 }
580 return errors;
581 }
582
583 // Signal to CreateScriptInstanceEr() that compilation/loading is complete
584 private void StoreScriptErrors(UUID itemId, ArrayList errors)
585 {
586 lock (m_scriptErrors)
587 {
588 // If compilation/loading initiated via CreateScriptInstance(),
589 // it does not want the errors, so just get out
590 if (!m_scriptErrors.ContainsKey(itemId))
591 {
592 return;
593 }
594
595 // Initiated via CreateScriptInstanceEr(), if we know what the
596 // errors are, save them and wake CreateScriptInstanceEr().
597 if (errors != null)
598 {
599 m_scriptErrors[itemId] = errors;
600 System.Threading.Monitor.PulseAll(m_scriptErrors);
601 return;
602 }
603 }
604
605 // Initiated via CreateScriptInstanceEr() but we don't know what
606 // the errors are yet, so retrieve them from the script engine.
607 // This may involve some waiting internal to GetScriptErrors().
608 errors = GetScriptErrors(itemId);
609
610 // Get a default non-null value to indicate success.
611 if (errors == null)
612 {
613 errors = new ArrayList();
614 }
615
616 // Post to CreateScriptInstanceEr() and wake it up
617 lock (m_scriptErrors)
618 {
619 m_scriptErrors[itemId] = errors;
620 System.Threading.Monitor.PulseAll(m_scriptErrors);
621 }
622 }
623
624 // Like StoreScriptErrors(), but just posts a single string message
625 private void StoreScriptError(UUID itemId, string message)
626 {
627 ArrayList errors = new ArrayList(1);
628 errors.Add(message);
629 StoreScriptErrors(itemId, errors);
479 } 630 }
480 631
481 /// <summary> 632 /// <summary>
@@ -488,15 +639,7 @@ namespace OpenSim.Region.Framework.Scenes
488 /// </param> 639 /// </param>
489 public void RemoveScriptInstance(UUID itemId, bool sceneObjectBeingDeleted) 640 public void RemoveScriptInstance(UUID itemId, bool sceneObjectBeingDeleted)
490 { 641 {
491 bool scriptPresent = false; 642 if (m_items.ContainsKey(itemId))
492
493 lock (m_items)
494 {
495 if (m_items.ContainsKey(itemId))
496 scriptPresent = true;
497 }
498
499 if (scriptPresent)
500 { 643 {
501 if (!sceneObjectBeingDeleted) 644 if (!sceneObjectBeingDeleted)
502 m_part.RemoveScriptEvents(itemId); 645 m_part.RemoveScriptEvents(itemId);
@@ -567,14 +710,16 @@ namespace OpenSim.Region.Framework.Scenes
567 /// <returns></returns> 710 /// <returns></returns>
568 private bool InventoryContainsName(string name) 711 private bool InventoryContainsName(string name)
569 { 712 {
570 lock (m_items) 713 m_items.LockItemsForRead(true);
714 foreach (TaskInventoryItem item in m_items.Values)
571 { 715 {
572 foreach (TaskInventoryItem item in m_items.Values) 716 if (item.Name == name)
573 { 717 {
574 if (item.Name == name) 718 m_items.LockItemsForRead(false);
575 return true; 719 return true;
576 } 720 }
577 } 721 }
722 m_items.LockItemsForRead(false);
578 return false; 723 return false;
579 } 724 }
580 725
@@ -616,8 +761,9 @@ namespace OpenSim.Region.Framework.Scenes
616 /// <param name="item"></param> 761 /// <param name="item"></param>
617 public void AddInventoryItemExclusive(TaskInventoryItem item, bool allowedDrop) 762 public void AddInventoryItemExclusive(TaskInventoryItem item, bool allowedDrop)
618 { 763 {
619 List<TaskInventoryItem> il = GetInventoryItems(); 764 m_items.LockItemsForRead(true);
620 765 List<TaskInventoryItem> il = new List<TaskInventoryItem>(m_items.Values);
766 m_items.LockItemsForRead(false);
621 foreach (TaskInventoryItem i in il) 767 foreach (TaskInventoryItem i in il)
622 { 768 {
623 if (i.Name == item.Name) 769 if (i.Name == item.Name)
@@ -655,14 +801,14 @@ namespace OpenSim.Region.Framework.Scenes
655 item.Name = name; 801 item.Name = name;
656 item.GroupID = m_part.GroupID; 802 item.GroupID = m_part.GroupID;
657 803
658 lock (m_items) 804 m_items.LockItemsForWrite(true);
659 m_items.Add(item.ItemID, item); 805 m_items.Add(item.ItemID, item);
660 806 m_items.LockItemsForWrite(false);
661 if (allowedDrop) 807 if (allowedDrop)
662 m_part.TriggerScriptChangedEvent(Changed.ALLOWED_DROP); 808 m_part.TriggerScriptChangedEvent(Changed.ALLOWED_DROP);
663 else 809 else
664 m_part.TriggerScriptChangedEvent(Changed.INVENTORY); 810 m_part.TriggerScriptChangedEvent(Changed.INVENTORY);
665 811
666 m_inventorySerial++; 812 m_inventorySerial++;
667 //m_inventorySerial += 2; 813 //m_inventorySerial += 2;
668 HasInventoryChanged = true; 814 HasInventoryChanged = true;
@@ -678,15 +824,15 @@ namespace OpenSim.Region.Framework.Scenes
678 /// <param name="items"></param> 824 /// <param name="items"></param>
679 public void RestoreInventoryItems(ICollection<TaskInventoryItem> items) 825 public void RestoreInventoryItems(ICollection<TaskInventoryItem> items)
680 { 826 {
681 lock (m_items) 827 m_items.LockItemsForWrite(true);
828 foreach (TaskInventoryItem item in items)
682 { 829 {
683 foreach (TaskInventoryItem item in items) 830 m_items.Add(item.ItemID, item);
684 { 831// m_part.TriggerScriptChangedEvent(Changed.INVENTORY);
685 m_items.Add(item.ItemID, item);
686// m_part.TriggerScriptChangedEvent(Changed.INVENTORY);
687 }
688 m_inventorySerial++;
689 } 832 }
833 m_items.LockItemsForWrite(false);
834
835 m_inventorySerial++;
690 } 836 }
691 837
692 /// <summary> 838 /// <summary>
@@ -697,23 +843,24 @@ namespace OpenSim.Region.Framework.Scenes
697 public TaskInventoryItem GetInventoryItem(UUID itemId) 843 public TaskInventoryItem GetInventoryItem(UUID itemId)
698 { 844 {
699 TaskInventoryItem item; 845 TaskInventoryItem item;
700 846 m_items.LockItemsForRead(true);
701 lock (m_items) 847 m_items.TryGetValue(itemId, out item);
702 m_items.TryGetValue(itemId, out item); 848 m_items.LockItemsForRead(false);
703
704 return item; 849 return item;
705 } 850 }
706 851
707 public TaskInventoryItem GetInventoryItem(string name) 852 public TaskInventoryItem GetInventoryItem(string name)
708 { 853 {
709 lock (m_items) 854 m_items.LockItemsForRead(true);
855 foreach (TaskInventoryItem item in m_items.Values)
710 { 856 {
711 foreach (TaskInventoryItem item in m_items.Values) 857 if (item.Name == name)
712 { 858 {
713 if (item.Name == name) 859 m_items.LockItemsForRead(false);
714 return item; 860 return item;
715 } 861 }
716 } 862 }
863 m_items.LockItemsForRead(false);
717 864
718 return null; 865 return null;
719 } 866 }
@@ -722,15 +869,16 @@ namespace OpenSim.Region.Framework.Scenes
722 { 869 {
723 List<TaskInventoryItem> items = new List<TaskInventoryItem>(); 870 List<TaskInventoryItem> items = new List<TaskInventoryItem>();
724 871
725 lock (m_items) 872 m_items.LockItemsForRead(true);
873
874 foreach (TaskInventoryItem item in m_items.Values)
726 { 875 {
727 foreach (TaskInventoryItem item in m_items.Values) 876 if (item.Name == name)
728 { 877 items.Add(item);
729 if (item.Name == name)
730 items.Add(item);
731 }
732 } 878 }
733 879
880 m_items.LockItemsForRead(false);
881
734 return items; 882 return items;
735 } 883 }
736 884
@@ -757,6 +905,10 @@ namespace OpenSim.Region.Framework.Scenes
757 { 905 {
758 SceneObjectGroup group = objlist[i]; 906 SceneObjectGroup group = objlist[i];
759 907
908 group.RootPart.AttachPoint = group.RootPart.Shape.State;
909 group.RootPart.AttachOffset = group.AbsolutePosition;
910 group.RootPart.AttachRotation = group.GroupRotation;
911
760 group.ResetIDs(); 912 group.ResetIDs();
761 913
762 SceneObjectPart rootPart = group.GetPart(group.UUID); 914 SceneObjectPart rootPart = group.GetPart(group.UUID);
@@ -832,8 +984,9 @@ namespace OpenSim.Region.Framework.Scenes
832 984
833 public bool UpdateInventoryItem(TaskInventoryItem item, bool fireScriptEvents, bool considerChanged) 985 public bool UpdateInventoryItem(TaskInventoryItem item, bool fireScriptEvents, bool considerChanged)
834 { 986 {
835 TaskInventoryItem it = GetInventoryItem(item.ItemID); 987 m_items.LockItemsForWrite(true);
836 if (it != null) 988
989 if (m_items.ContainsKey(item.ItemID))
837 { 990 {
838// m_log.DebugFormat("[PRIM INVENTORY]: Updating item {0} in {1}", item.Name, m_part.Name); 991// m_log.DebugFormat("[PRIM INVENTORY]: Updating item {0} in {1}", item.Name, m_part.Name);
839 992
@@ -846,14 +999,10 @@ namespace OpenSim.Region.Framework.Scenes
846 item.GroupID = m_part.GroupID; 999 item.GroupID = m_part.GroupID;
847 1000
848 if (item.AssetID == UUID.Zero) 1001 if (item.AssetID == UUID.Zero)
849 item.AssetID = it.AssetID; 1002 item.AssetID = m_items[item.ItemID].AssetID;
850 1003
851 lock (m_items) 1004 m_items[item.ItemID] = item;
852 { 1005 m_inventorySerial++;
853 m_items[item.ItemID] = item;
854 m_inventorySerial++;
855 }
856
857 if (fireScriptEvents) 1006 if (fireScriptEvents)
858 m_part.TriggerScriptChangedEvent(Changed.INVENTORY); 1007 m_part.TriggerScriptChangedEvent(Changed.INVENTORY);
859 1008
@@ -862,7 +1011,7 @@ namespace OpenSim.Region.Framework.Scenes
862 HasInventoryChanged = true; 1011 HasInventoryChanged = true;
863 m_part.ParentGroup.HasGroupChanged = true; 1012 m_part.ParentGroup.HasGroupChanged = true;
864 } 1013 }
865 1014 m_items.LockItemsForWrite(false);
866 return true; 1015 return true;
867 } 1016 }
868 else 1017 else
@@ -873,8 +1022,9 @@ namespace OpenSim.Region.Framework.Scenes
873 item.ItemID, m_part.Name, m_part.UUID, 1022 item.ItemID, m_part.Name, m_part.UUID,
874 m_part.AbsolutePosition, m_part.ParentGroup.Scene.RegionInfo.RegionName); 1023 m_part.AbsolutePosition, m_part.ParentGroup.Scene.RegionInfo.RegionName);
875 } 1024 }
876 return false; 1025 m_items.LockItemsForWrite(false);
877 1026
1027 return false;
878 } 1028 }
879 1029
880 /// <summary> 1030 /// <summary>
@@ -885,43 +1035,59 @@ namespace OpenSim.Region.Framework.Scenes
885 /// in this prim's inventory.</returns> 1035 /// in this prim's inventory.</returns>
886 public int RemoveInventoryItem(UUID itemID) 1036 public int RemoveInventoryItem(UUID itemID)
887 { 1037 {
888 TaskInventoryItem item = GetInventoryItem(itemID); 1038 m_items.LockItemsForRead(true);
889 if (item != null) 1039
1040 if (m_items.ContainsKey(itemID))
890 { 1041 {
891 int type = m_items[itemID].InvType; 1042 int type = m_items[itemID].InvType;
1043 m_items.LockItemsForRead(false);
892 if (type == 10) // Script 1044 if (type == 10) // Script
893 { 1045 {
894 m_part.RemoveScriptEvents(itemID);
895 m_part.ParentGroup.Scene.EventManager.TriggerRemoveScript(m_part.LocalId, itemID); 1046 m_part.ParentGroup.Scene.EventManager.TriggerRemoveScript(m_part.LocalId, itemID);
896 } 1047 }
1048 m_items.LockItemsForWrite(true);
897 m_items.Remove(itemID); 1049 m_items.Remove(itemID);
1050 m_items.LockItemsForWrite(false);
898 m_inventorySerial++; 1051 m_inventorySerial++;
899 m_part.TriggerScriptChangedEvent(Changed.INVENTORY); 1052 m_part.TriggerScriptChangedEvent(Changed.INVENTORY);
900 1053
901 HasInventoryChanged = true; 1054 HasInventoryChanged = true;
902 m_part.ParentGroup.HasGroupChanged = true; 1055 m_part.ParentGroup.HasGroupChanged = true;
903 1056
904 if (!ContainsScripts()) 1057 int scriptcount = 0;
1058 m_items.LockItemsForRead(true);
1059 foreach (TaskInventoryItem item in m_items.Values)
1060 {
1061 if (item.Type == 10)
1062 {
1063 scriptcount++;
1064 }
1065 }
1066 m_items.LockItemsForRead(false);
1067
1068
1069 if (scriptcount <= 0)
1070 {
905 m_part.RemFlag(PrimFlags.Scripted); 1071 m_part.RemFlag(PrimFlags.Scripted);
1072 }
906 1073
907 m_part.ScheduleFullUpdate(); 1074 m_part.ScheduleFullUpdate();
908 1075
909 return type; 1076 return type;
910
911 } 1077 }
912 else 1078 else
913 { 1079 {
1080 m_items.LockItemsForRead(false);
914 m_log.ErrorFormat( 1081 m_log.ErrorFormat(
915 "[PRIM INVENTORY]: " + 1082 "[PRIM INVENTORY]: " +
916 "Tried to remove item ID {0} from prim {1}, {2} at {3} in {4} but the item does not exist in this inventory", 1083 "Tried to remove item ID {0} from prim {1}, {2} but the item does not exist in this inventory",
917 itemID, m_part.Name, m_part.UUID, 1084 itemID, m_part.Name, m_part.UUID);
918 m_part.AbsolutePosition, m_part.ParentGroup.Scene.RegionInfo.RegionName);
919 } 1085 }
920 1086
921 return -1; 1087 return -1;
922 } 1088 }
923 1089
924 private bool CreateInventoryFile() 1090 private bool CreateInventoryFileName()
925 { 1091 {
926// m_log.DebugFormat( 1092// m_log.DebugFormat(
927// "[PRIM INVENTORY]: Creating inventory file for {0} {1} {2}, serial {3}", 1093// "[PRIM INVENTORY]: Creating inventory file for {0} {1} {2}, serial {3}",
@@ -930,70 +1096,12 @@ namespace OpenSim.Region.Framework.Scenes
930 if (m_inventoryFileName == String.Empty || 1096 if (m_inventoryFileName == String.Empty ||
931 m_inventoryFileNameSerial < m_inventorySerial) 1097 m_inventoryFileNameSerial < m_inventorySerial)
932 { 1098 {
933 // Something changed, we need to create a new file
934 m_inventoryFileName = "inventory_" + UUID.Random().ToString() + ".tmp"; 1099 m_inventoryFileName = "inventory_" + UUID.Random().ToString() + ".tmp";
935 m_inventoryFileNameSerial = m_inventorySerial; 1100 m_inventoryFileNameSerial = m_inventorySerial;
936 1101
937 InventoryStringBuilder invString = new InventoryStringBuilder(m_part.UUID, UUID.Zero);
938
939 lock (m_items)
940 {
941 foreach (TaskInventoryItem item in m_items.Values)
942 {
943// m_log.DebugFormat(
944// "[PRIM INVENTORY]: Adding item {0} {1} for serial {2} on prim {3} {4} {5}",
945// item.Name, item.ItemID, m_inventorySerial, m_part.Name, m_part.UUID, m_part.LocalId);
946
947 UUID ownerID = item.OwnerID;
948 uint everyoneMask = 0;
949 uint baseMask = item.BasePermissions;
950 uint ownerMask = item.CurrentPermissions;
951 uint groupMask = item.GroupPermissions;
952
953 invString.AddItemStart();
954 invString.AddNameValueLine("item_id", item.ItemID.ToString());
955 invString.AddNameValueLine("parent_id", m_part.UUID.ToString());
956
957 invString.AddPermissionsStart();
958
959 invString.AddNameValueLine("base_mask", Utils.UIntToHexString(baseMask));
960 invString.AddNameValueLine("owner_mask", Utils.UIntToHexString(ownerMask));
961 invString.AddNameValueLine("group_mask", Utils.UIntToHexString(groupMask));
962 invString.AddNameValueLine("everyone_mask", Utils.UIntToHexString(everyoneMask));
963 invString.AddNameValueLine("next_owner_mask", Utils.UIntToHexString(item.NextPermissions));
964
965 invString.AddNameValueLine("creator_id", item.CreatorID.ToString());
966 invString.AddNameValueLine("owner_id", ownerID.ToString());
967
968 invString.AddNameValueLine("last_owner_id", item.LastOwnerID.ToString());
969
970 invString.AddNameValueLine("group_id", item.GroupID.ToString());
971 invString.AddSectionEnd();
972
973 invString.AddNameValueLine("asset_id", item.AssetID.ToString());
974 invString.AddNameValueLine("type", Utils.AssetTypeToString((AssetType)item.Type));
975 invString.AddNameValueLine("inv_type", Utils.InventoryTypeToString((InventoryType)item.InvType));
976 invString.AddNameValueLine("flags", Utils.UIntToHexString(item.Flags));
977
978 invString.AddSaleStart();
979 invString.AddNameValueLine("sale_type", "not");
980 invString.AddNameValueLine("sale_price", "0");
981 invString.AddSectionEnd();
982
983 invString.AddNameValueLine("name", item.Name + "|");
984 invString.AddNameValueLine("desc", item.Description + "|");
985
986 invString.AddNameValueLine("creation_date", item.CreationDate.ToString());
987 invString.AddSectionEnd();
988 }
989 }
990
991 m_inventoryFileData = Utils.StringToBytes(invString.BuildString);
992
993 return true; 1102 return true;
994 } 1103 }
995 1104
996 // No need to recreate, the existing file is fine
997 return false; 1105 return false;
998 } 1106 }
999 1107
@@ -1003,43 +1111,110 @@ namespace OpenSim.Region.Framework.Scenes
1003 /// <param name="xferManager"></param> 1111 /// <param name="xferManager"></param>
1004 public void RequestInventoryFile(IClientAPI client, IXfer xferManager) 1112 public void RequestInventoryFile(IClientAPI client, IXfer xferManager)
1005 { 1113 {
1006 lock (m_items) 1114 bool changed = CreateInventoryFileName();
1007 {
1008 // Don't send a inventory xfer name if there are no items. Doing so causes viewer 3 to crash when rezzing
1009 // a new script if any previous deletion has left the prim inventory empty.
1010 if (m_items.Count == 0) // No inventory
1011 {
1012// m_log.DebugFormat(
1013// "[PRIM INVENTORY]: Not sending inventory data for part {0} {1} {2} for {3} since no items",
1014// m_part.Name, m_part.LocalId, m_part.UUID, client.Name);
1015 1115
1016 client.SendTaskInventory(m_part.UUID, 0, new byte[0]); 1116 bool includeAssets = false;
1017 return; 1117 if (m_part.ParentGroup.Scene.Permissions.CanEditObjectInventory(m_part.UUID, client.AgentId))
1018 } 1118 includeAssets = true;
1119
1120 if (m_inventoryPrivileged != includeAssets)
1121 changed = true;
1122
1123 InventoryStringBuilder invString = new InventoryStringBuilder(m_part.UUID, UUID.Zero);
1019 1124
1020 CreateInventoryFile(); 1125 Items.LockItemsForRead(true);
1126
1127 if (m_inventorySerial == 0) // No inventory
1128 {
1129 client.SendTaskInventory(m_part.UUID, 0, new byte[0]);
1130 Items.LockItemsForRead(false);
1131 return;
1132 }
1133
1134 if (m_items.Count == 0) // No inventory
1135 {
1136 client.SendTaskInventory(m_part.UUID, 0, new byte[0]);
1137 Items.LockItemsForRead(false);
1138 return;
1139 }
1021 1140
1022 // In principle, we should only do the rest if the inventory changed; 1141 if (!changed)
1023 // by sending m_inventorySerial to the client, it ought to know 1142 {
1024 // that nothing changed and that it doesn't need to request the file.
1025 // Unfortunately, it doesn't look like the client optimizes this;
1026 // the client seems to always come back and request the Xfer,
1027 // no matter what value m_inventorySerial has.
1028 // FIXME: Could probably be > 0 here rather than > 2
1029 if (m_inventoryFileData.Length > 2) 1143 if (m_inventoryFileData.Length > 2)
1030 { 1144 {
1031 // Add the file for Xfer 1145 xferManager.AddNewFile(m_inventoryFileName,
1032 // m_log.DebugFormat( 1146 m_inventoryFileData);
1033 // "[PRIM INVENTORY]: Adding inventory file {0} (length {1}) for transfer on {2} {3} {4}", 1147 client.SendTaskInventory(m_part.UUID, (short)m_inventorySerial,
1034 // m_inventoryFileName, m_inventoryFileData.Length, m_part.Name, m_part.UUID, m_part.LocalId); 1148 Util.StringToBytes256(m_inventoryFileName));
1035 1149
1036 xferManager.AddNewFile(m_inventoryFileName, m_inventoryFileData); 1150 Items.LockItemsForRead(false);
1151 return;
1037 } 1152 }
1038
1039 // Tell the client we're ready to Xfer the file
1040 client.SendTaskInventory(m_part.UUID, (short)m_inventorySerial,
1041 Util.StringToBytes256(m_inventoryFileName));
1042 } 1153 }
1154
1155 m_inventoryPrivileged = includeAssets;
1156
1157 foreach (TaskInventoryItem item in m_items.Values)
1158 {
1159 UUID ownerID = item.OwnerID;
1160 uint everyoneMask = 0;
1161 uint baseMask = item.BasePermissions;
1162 uint ownerMask = item.CurrentPermissions;
1163 uint groupMask = item.GroupPermissions;
1164
1165 invString.AddItemStart();
1166 invString.AddNameValueLine("item_id", item.ItemID.ToString());
1167 invString.AddNameValueLine("parent_id", m_part.UUID.ToString());
1168
1169 invString.AddPermissionsStart();
1170
1171 invString.AddNameValueLine("base_mask", Utils.UIntToHexString(baseMask));
1172 invString.AddNameValueLine("owner_mask", Utils.UIntToHexString(ownerMask));
1173 invString.AddNameValueLine("group_mask", Utils.UIntToHexString(groupMask));
1174 invString.AddNameValueLine("everyone_mask", Utils.UIntToHexString(everyoneMask));
1175 invString.AddNameValueLine("next_owner_mask", Utils.UIntToHexString(item.NextPermissions));
1176
1177 invString.AddNameValueLine("creator_id", item.CreatorID.ToString());
1178 invString.AddNameValueLine("owner_id", ownerID.ToString());
1179
1180 invString.AddNameValueLine("last_owner_id", item.LastOwnerID.ToString());
1181
1182 invString.AddNameValueLine("group_id", item.GroupID.ToString());
1183 invString.AddSectionEnd();
1184
1185 if (includeAssets)
1186 invString.AddNameValueLine("asset_id", item.AssetID.ToString());
1187 else
1188 invString.AddNameValueLine("asset_id", UUID.Zero.ToString());
1189 invString.AddNameValueLine("type", Utils.AssetTypeToString((AssetType)item.Type));
1190 invString.AddNameValueLine("inv_type", Utils.InventoryTypeToString((InventoryType)item.InvType));
1191 invString.AddNameValueLine("flags", Utils.UIntToHexString(item.Flags));
1192
1193 invString.AddSaleStart();
1194 invString.AddNameValueLine("sale_type", "not");
1195 invString.AddNameValueLine("sale_price", "0");
1196 invString.AddSectionEnd();
1197
1198 invString.AddNameValueLine("name", item.Name + "|");
1199 invString.AddNameValueLine("desc", item.Description + "|");
1200
1201 invString.AddNameValueLine("creation_date", item.CreationDate.ToString());
1202 invString.AddSectionEnd();
1203 }
1204
1205 Items.LockItemsForRead(false);
1206
1207 m_inventoryFileData = Utils.StringToBytes(invString.BuildString);
1208
1209 if (m_inventoryFileData.Length > 2)
1210 {
1211 xferManager.AddNewFile(m_inventoryFileName, m_inventoryFileData);
1212 client.SendTaskInventory(m_part.UUID, (short)m_inventorySerial,
1213 Util.StringToBytes256(m_inventoryFileName));
1214 return;
1215 }
1216
1217 client.SendTaskInventory(m_part.UUID, 0, new byte[0]);
1043 } 1218 }
1044 1219
1045 /// <summary> 1220 /// <summary>
@@ -1048,13 +1223,19 @@ namespace OpenSim.Region.Framework.Scenes
1048 /// <param name="datastore"></param> 1223 /// <param name="datastore"></param>
1049 public void ProcessInventoryBackup(ISimulationDataService datastore) 1224 public void ProcessInventoryBackup(ISimulationDataService datastore)
1050 { 1225 {
1051 if (HasInventoryChanged) 1226// Removed this because linking will cause an immediate delete of the new
1052 { 1227// child prim from the database and the subsequent storing of the prim sees
1053 HasInventoryChanged = false; 1228// the inventory of it as unchanged and doesn't store it at all. The overhead
1054 List<TaskInventoryItem> items = GetInventoryItems(); 1229// of storing prim inventory needlessly is much less than the aggravation
1055 datastore.StorePrimInventory(m_part.UUID, items); 1230// of prim inventory loss.
1231// if (HasInventoryChanged)
1232// {
1233 Items.LockItemsForRead(true);
1234 datastore.StorePrimInventory(m_part.UUID, Items.Values);
1235 Items.LockItemsForRead(false);
1056 1236
1057 } 1237 HasInventoryChanged = false;
1238// }
1058 } 1239 }
1059 1240
1060 public class InventoryStringBuilder 1241 public class InventoryStringBuilder
@@ -1120,87 +1301,63 @@ namespace OpenSim.Region.Framework.Scenes
1120 { 1301 {
1121 uint mask=0x7fffffff; 1302 uint mask=0x7fffffff;
1122 1303
1123 lock (m_items) 1304 foreach (TaskInventoryItem item in m_items.Values)
1124 { 1305 {
1125 foreach (TaskInventoryItem item in m_items.Values) 1306 if ((item.CurrentPermissions & item.NextPermissions & (uint)PermissionMask.Copy) == 0)
1307 mask &= ~((uint)PermissionMask.Copy >> 13);
1308 if ((item.CurrentPermissions & item.NextPermissions & (uint)PermissionMask.Transfer) == 0)
1309 mask &= ~((uint)PermissionMask.Transfer >> 13);
1310 if ((item.CurrentPermissions & item.NextPermissions & (uint)PermissionMask.Modify) == 0)
1311 mask &= ~((uint)PermissionMask.Modify >> 13);
1312
1313 if (item.InvType == (int)InventoryType.Object)
1126 { 1314 {
1127 if ((item.CurrentPermissions & item.NextPermissions & (uint)PermissionMask.Copy) == 0) 1315 if ((item.CurrentPermissions & ((uint)PermissionMask.Copy >> 13)) == 0)
1128 mask &= ~((uint)PermissionMask.Copy >> 13); 1316 mask &= ~((uint)PermissionMask.Copy >> 13);
1129 if ((item.CurrentPermissions & item.NextPermissions & (uint)PermissionMask.Transfer) == 0) 1317 if ((item.CurrentPermissions & ((uint)PermissionMask.Transfer >> 13)) == 0)
1130 mask &= ~((uint)PermissionMask.Transfer >> 13); 1318 mask &= ~((uint)PermissionMask.Transfer >> 13);
1131 if ((item.CurrentPermissions & item.NextPermissions & (uint)PermissionMask.Modify) == 0) 1319 if ((item.CurrentPermissions & ((uint)PermissionMask.Modify >> 13)) == 0)
1132 mask &= ~((uint)PermissionMask.Modify >> 13); 1320 mask &= ~((uint)PermissionMask.Modify >> 13);
1133
1134 if (item.InvType != (int)InventoryType.Object)
1135 {
1136 if ((item.CurrentPermissions & item.NextPermissions & (uint)PermissionMask.Copy) == 0)
1137 mask &= ~((uint)PermissionMask.Copy >> 13);
1138 if ((item.CurrentPermissions & item.NextPermissions & (uint)PermissionMask.Transfer) == 0)
1139 mask &= ~((uint)PermissionMask.Transfer >> 13);
1140 if ((item.CurrentPermissions & item.NextPermissions & (uint)PermissionMask.Modify) == 0)
1141 mask &= ~((uint)PermissionMask.Modify >> 13);
1142 }
1143 else
1144 {
1145 if ((item.CurrentPermissions & ((uint)PermissionMask.Copy >> 13)) == 0)
1146 mask &= ~((uint)PermissionMask.Copy >> 13);
1147 if ((item.CurrentPermissions & ((uint)PermissionMask.Transfer >> 13)) == 0)
1148 mask &= ~((uint)PermissionMask.Transfer >> 13);
1149 if ((item.CurrentPermissions & ((uint)PermissionMask.Modify >> 13)) == 0)
1150 mask &= ~((uint)PermissionMask.Modify >> 13);
1151 }
1152
1153 if ((item.CurrentPermissions & (uint)PermissionMask.Copy) == 0)
1154 mask &= ~(uint)PermissionMask.Copy;
1155 if ((item.CurrentPermissions & (uint)PermissionMask.Transfer) == 0)
1156 mask &= ~(uint)PermissionMask.Transfer;
1157 if ((item.CurrentPermissions & (uint)PermissionMask.Modify) == 0)
1158 mask &= ~(uint)PermissionMask.Modify;
1159 } 1321 }
1322
1323 if ((item.CurrentPermissions & (uint)PermissionMask.Copy) == 0)
1324 mask &= ~(uint)PermissionMask.Copy;
1325 if ((item.CurrentPermissions & (uint)PermissionMask.Transfer) == 0)
1326 mask &= ~(uint)PermissionMask.Transfer;
1327 if ((item.CurrentPermissions & (uint)PermissionMask.Modify) == 0)
1328 mask &= ~(uint)PermissionMask.Modify;
1160 } 1329 }
1161
1162 return mask; 1330 return mask;
1163 } 1331 }
1164 1332
1165 public void ApplyNextOwnerPermissions() 1333 public void ApplyNextOwnerPermissions()
1166 { 1334 {
1167 lock (m_items) 1335 foreach (TaskInventoryItem item in m_items.Values)
1168 { 1336 {
1169 foreach (TaskInventoryItem item in m_items.Values) 1337 if (item.InvType == (int)InventoryType.Object && (item.CurrentPermissions & 7) != 0)
1170 { 1338 {
1171// m_log.DebugFormat ( 1339 if ((item.CurrentPermissions & ((uint)PermissionMask.Copy >> 13)) == 0)
1172// "[SCENE OBJECT PART INVENTORY]: Applying next permissions {0} to {1} in {2} with current {3}, base {4}, everyone {5}", 1340 item.CurrentPermissions &= ~(uint)PermissionMask.Copy;
1173// item.NextPermissions, item.Name, m_part.Name, item.CurrentPermissions, item.BasePermissions, item.EveryonePermissions); 1341 if ((item.CurrentPermissions & ((uint)PermissionMask.Transfer >> 13)) == 0)
1174 1342 item.CurrentPermissions &= ~(uint)PermissionMask.Transfer;
1175 if (item.InvType == (int)InventoryType.Object && (item.CurrentPermissions & 7) != 0) 1343 if ((item.CurrentPermissions & ((uint)PermissionMask.Modify >> 13)) == 0)
1176 { 1344 item.CurrentPermissions &= ~(uint)PermissionMask.Modify;
1177 if ((item.CurrentPermissions & ((uint)PermissionMask.Copy >> 13)) == 0)
1178 item.CurrentPermissions &= ~(uint)PermissionMask.Copy;
1179 if ((item.CurrentPermissions & ((uint)PermissionMask.Transfer >> 13)) == 0)
1180 item.CurrentPermissions &= ~(uint)PermissionMask.Transfer;
1181 if ((item.CurrentPermissions & ((uint)PermissionMask.Modify >> 13)) == 0)
1182 item.CurrentPermissions &= ~(uint)PermissionMask.Modify;
1183 }
1184
1185 item.CurrentPermissions &= item.NextPermissions;
1186 item.BasePermissions &= item.NextPermissions;
1187 item.EveryonePermissions &= item.NextPermissions;
1188 item.OwnerChanged = true;
1189 item.PermsMask = 0;
1190 item.PermsGranter = UUID.Zero;
1191 } 1345 }
1346 item.CurrentPermissions &= item.NextPermissions;
1347 item.BasePermissions &= item.NextPermissions;
1348 item.EveryonePermissions &= item.NextPermissions;
1349 item.OwnerChanged = true;
1350 item.PermsMask = 0;
1351 item.PermsGranter = UUID.Zero;
1192 } 1352 }
1193 } 1353 }
1194 1354
1195 public void ApplyGodPermissions(uint perms) 1355 public void ApplyGodPermissions(uint perms)
1196 { 1356 {
1197 lock (m_items) 1357 foreach (TaskInventoryItem item in m_items.Values)
1198 { 1358 {
1199 foreach (TaskInventoryItem item in m_items.Values) 1359 item.CurrentPermissions = perms;
1200 { 1360 item.BasePermissions = perms;
1201 item.CurrentPermissions = perms;
1202 item.BasePermissions = perms;
1203 }
1204 } 1361 }
1205 1362
1206 m_inventorySerial++; 1363 m_inventorySerial++;
@@ -1213,14 +1370,11 @@ namespace OpenSim.Region.Framework.Scenes
1213 /// <returns></returns> 1370 /// <returns></returns>
1214 public bool ContainsScripts() 1371 public bool ContainsScripts()
1215 { 1372 {
1216 lock (m_items) 1373 foreach (TaskInventoryItem item in m_items.Values)
1217 { 1374 {
1218 foreach (TaskInventoryItem item in m_items.Values) 1375 if (item.InvType == (int)InventoryType.LSL)
1219 { 1376 {
1220 if (item.InvType == (int)InventoryType.LSL) 1377 return true;
1221 {
1222 return true;
1223 }
1224 } 1378 }
1225 } 1379 }
1226 1380
@@ -1234,17 +1388,15 @@ namespace OpenSim.Region.Framework.Scenes
1234 public int ScriptCount() 1388 public int ScriptCount()
1235 { 1389 {
1236 int count = 0; 1390 int count = 0;
1237 lock (m_items) 1391 Items.LockItemsForRead(true);
1392 foreach (TaskInventoryItem item in m_items.Values)
1238 { 1393 {
1239 foreach (TaskInventoryItem item in m_items.Values) 1394 if (item.InvType == (int)InventoryType.LSL)
1240 { 1395 {
1241 if (item.InvType == (int)InventoryType.LSL) 1396 count++;
1242 {
1243 count++;
1244 }
1245 } 1397 }
1246 } 1398 }
1247 1399 Items.LockItemsForRead(false);
1248 return count; 1400 return count;
1249 } 1401 }
1250 /// <summary> 1402 /// <summary>
@@ -1280,11 +1432,8 @@ namespace OpenSim.Region.Framework.Scenes
1280 { 1432 {
1281 List<UUID> ret = new List<UUID>(); 1433 List<UUID> ret = new List<UUID>();
1282 1434
1283 lock (m_items) 1435 foreach (TaskInventoryItem item in m_items.Values)
1284 { 1436 ret.Add(item.ItemID);
1285 foreach (TaskInventoryItem item in m_items.Values)
1286 ret.Add(item.ItemID);
1287 }
1288 1437
1289 return ret; 1438 return ret;
1290 } 1439 }
@@ -1293,8 +1442,9 @@ namespace OpenSim.Region.Framework.Scenes
1293 { 1442 {
1294 List<TaskInventoryItem> ret = new List<TaskInventoryItem>(); 1443 List<TaskInventoryItem> ret = new List<TaskInventoryItem>();
1295 1444
1296 lock (m_items) 1445 Items.LockItemsForRead(true);
1297 ret = new List<TaskInventoryItem>(m_items.Values); 1446 ret = new List<TaskInventoryItem>(m_items.Values);
1447 Items.LockItemsForRead(false);
1298 1448
1299 return ret; 1449 return ret;
1300 } 1450 }
@@ -1303,18 +1453,24 @@ namespace OpenSim.Region.Framework.Scenes
1303 { 1453 {
1304 List<TaskInventoryItem> ret = new List<TaskInventoryItem>(); 1454 List<TaskInventoryItem> ret = new List<TaskInventoryItem>();
1305 1455
1306 lock (m_items) 1456 Items.LockItemsForRead(true);
1307 { 1457
1308 foreach (TaskInventoryItem item in m_items.Values) 1458 foreach (TaskInventoryItem item in m_items.Values)
1309 if (item.InvType == (int)type) 1459 if (item.InvType == (int)type)
1310 ret.Add(item); 1460 ret.Add(item);
1311 } 1461
1462 Items.LockItemsForRead(false);
1312 1463
1313 return ret; 1464 return ret;
1314 } 1465 }
1315 1466
1316 public Dictionary<UUID, string> GetScriptStates() 1467 public Dictionary<UUID, string> GetScriptStates()
1317 { 1468 {
1469 return GetScriptStates(false);
1470 }
1471
1472 public Dictionary<UUID, string> GetScriptStates(bool oldIDs)
1473 {
1318 Dictionary<UUID, string> ret = new Dictionary<UUID, string>(); 1474 Dictionary<UUID, string> ret = new Dictionary<UUID, string>();
1319 1475
1320 if (m_part.ParentGroup.Scene == null) // Group not in a scene 1476 if (m_part.ParentGroup.Scene == null) // Group not in a scene
@@ -1340,14 +1496,21 @@ namespace OpenSim.Region.Framework.Scenes
1340 string n = e.GetXMLState(item.ItemID); 1496 string n = e.GetXMLState(item.ItemID);
1341 if (n != String.Empty) 1497 if (n != String.Empty)
1342 { 1498 {
1343 if (!ret.ContainsKey(item.ItemID)) 1499 if (oldIDs)
1344 ret[item.ItemID] = n; 1500 {
1501 if (!ret.ContainsKey(item.OldItemID))
1502 ret[item.OldItemID] = n;
1503 }
1504 else
1505 {
1506 if (!ret.ContainsKey(item.ItemID))
1507 ret[item.ItemID] = n;
1508 }
1345 break; 1509 break;
1346 } 1510 }
1347 } 1511 }
1348 } 1512 }
1349 } 1513 }
1350
1351 return ret; 1514 return ret;
1352 } 1515 }
1353 1516