diff options
Diffstat (limited to '')
-rw-r--r-- | OpenSim/Region/Framework/Scenes/Scene.Inventory.cs | 402 |
1 files changed, 168 insertions, 234 deletions
diff --git a/OpenSim/Region/Framework/Scenes/Scene.Inventory.cs b/OpenSim/Region/Framework/Scenes/Scene.Inventory.cs index 0b92818..c04bbb4 100644 --- a/OpenSim/Region/Framework/Scenes/Scene.Inventory.cs +++ b/OpenSim/Region/Framework/Scenes/Scene.Inventory.cs | |||
@@ -408,192 +408,198 @@ namespace OpenSim.Region.Framework.Scenes | |||
408 | InventoryItemBase item = new InventoryItemBase(itemId, senderId); | 408 | InventoryItemBase item = new InventoryItemBase(itemId, senderId); |
409 | item = InventoryService.GetItem(item); | 409 | item = InventoryService.GetItem(item); |
410 | 410 | ||
411 | if ((item != null) && (item.Owner == senderId)) | 411 | if (item == null) |
412 | { | 412 | { |
413 | IUserManagement uman = RequestModuleInterface<IUserManagement>(); | 413 | m_log.WarnFormat( |
414 | if (uman != null) | 414 | "[AGENT INVENTORY]: Failed to find item {0} sent by {1} to {2}", itemId, senderId, recipient); |
415 | uman.AddUser(item.CreatorIdAsUuid, item.CreatorData); | 415 | return null; |
416 | } | ||
416 | 417 | ||
417 | if (!Permissions.BypassPermissions()) | 418 | if (item.Owner != senderId) |
418 | { | 419 | { |
419 | if ((item.CurrentPermissions & (uint)PermissionMask.Transfer) == 0) | 420 | m_log.WarnFormat( |
420 | return null; | 421 | "[AGENT INVENTORY]: Attempt to send item {0} {1} to {2} failed because sender {3} did not match item owner {4}", |
421 | } | 422 | item.Name, item.ID, recipient, senderId, item.Owner); |
423 | return null; | ||
424 | } | ||
425 | |||
426 | IUserManagement uman = RequestModuleInterface<IUserManagement>(); | ||
427 | if (uman != null) | ||
428 | uman.AddUser(item.CreatorIdAsUuid, item.CreatorData); | ||
429 | |||
430 | if (!Permissions.BypassPermissions()) | ||
431 | { | ||
432 | if ((item.CurrentPermissions & (uint)PermissionMask.Transfer) == 0) | ||
433 | return null; | ||
434 | } | ||
422 | 435 | ||
423 | // Insert a copy of the item into the recipient | 436 | // Insert a copy of the item into the recipient |
424 | InventoryItemBase itemCopy = new InventoryItemBase(); | 437 | InventoryItemBase itemCopy = new InventoryItemBase(); |
425 | itemCopy.Owner = recipient; | 438 | itemCopy.Owner = recipient; |
426 | itemCopy.CreatorId = item.CreatorId; | 439 | itemCopy.CreatorId = item.CreatorId; |
427 | itemCopy.CreatorData = item.CreatorData; | 440 | itemCopy.CreatorData = item.CreatorData; |
428 | itemCopy.ID = UUID.Random(); | 441 | itemCopy.ID = UUID.Random(); |
429 | itemCopy.AssetID = item.AssetID; | 442 | itemCopy.AssetID = item.AssetID; |
430 | itemCopy.Description = item.Description; | 443 | itemCopy.Description = item.Description; |
431 | itemCopy.Name = item.Name; | 444 | itemCopy.Name = item.Name; |
432 | itemCopy.AssetType = item.AssetType; | 445 | itemCopy.AssetType = item.AssetType; |
433 | itemCopy.InvType = item.InvType; | 446 | itemCopy.InvType = item.InvType; |
434 | itemCopy.Folder = recipientFolderId; | 447 | itemCopy.Folder = recipientFolderId; |
435 | 448 | ||
436 | if (Permissions.PropagatePermissions() && recipient != senderId) | 449 | if (Permissions.PropagatePermissions() && recipient != senderId) |
450 | { | ||
451 | // Trying to do this right this time. This is evil. If | ||
452 | // you believe in Good, go elsewhere. Vampires and other | ||
453 | // evil creatores only beyond this point. You have been | ||
454 | // warned. | ||
455 | |||
456 | // We're going to mask a lot of things by the next perms | ||
457 | // Tweak the next perms to be nicer to our data | ||
458 | // | ||
459 | // In this mask, all the bits we do NOT want to mess | ||
460 | // with are set. These are: | ||
461 | // | ||
462 | // Transfer | ||
463 | // Copy | ||
464 | // Modufy | ||
465 | uint permsMask = ~ ((uint)PermissionMask.Copy | | ||
466 | (uint)PermissionMask.Transfer | | ||
467 | (uint)PermissionMask.Modify); | ||
468 | |||
469 | // Now, reduce the next perms to the mask bits | ||
470 | // relevant to the operation | ||
471 | uint nextPerms = permsMask | (item.NextPermissions & | ||
472 | ((uint)PermissionMask.Copy | | ||
473 | (uint)PermissionMask.Transfer | | ||
474 | (uint)PermissionMask.Modify)); | ||
475 | |||
476 | // nextPerms now has all bits set, except for the actual | ||
477 | // next permission bits. | ||
478 | |||
479 | // This checks for no mod, no copy, no trans. | ||
480 | // This indicates an error or messed up item. Do it like | ||
481 | // SL and assume trans | ||
482 | if (nextPerms == permsMask) | ||
483 | nextPerms |= (uint)PermissionMask.Transfer; | ||
484 | |||
485 | // Inventory owner perms are the logical AND of the | ||
486 | // folded perms and the root prim perms, however, if | ||
487 | // the root prim is mod, the inventory perms will be | ||
488 | // mod. This happens on "take" and is of little concern | ||
489 | // here, save for preventing escalation | ||
490 | |||
491 | // This hack ensures that items previously permalocked | ||
492 | // get unlocked when they're passed or rezzed | ||
493 | uint basePerms = item.BasePermissions | | ||
494 | (uint)PermissionMask.Move; | ||
495 | uint ownerPerms = item.CurrentPermissions; | ||
496 | |||
497 | // If this is an object, root prim perms may be more | ||
498 | // permissive than folded perms. Use folded perms as | ||
499 | // a mask | ||
500 | if (item.InvType == (int)InventoryType.Object) | ||
437 | { | 501 | { |
438 | // Trying to do this right this time. This is evil. If | 502 | // Create a safe mask for the current perms |
439 | // you believe in Good, go elsewhere. Vampires and other | 503 | uint foldedPerms = (item.CurrentPermissions & 7) << 13; |
440 | // evil creatores only beyond this point. You have been | 504 | foldedPerms |= permsMask; |
441 | // warned. | 505 | |
442 | 506 | bool isRootMod = (item.CurrentPermissions & | |
443 | // We're going to mask a lot of things by the next perms | 507 | (uint)PermissionMask.Modify) != 0 ? |
444 | // Tweak the next perms to be nicer to our data | 508 | true : false; |
445 | // | 509 | |
446 | // In this mask, all the bits we do NOT want to mess | 510 | // Mask the owner perms to the folded perms |
447 | // with are set. These are: | 511 | ownerPerms &= foldedPerms; |
448 | // | 512 | basePerms &= foldedPerms; |
449 | // Transfer | 513 | |
450 | // Copy | 514 | // If the root was mod, let the mask reflect that |
451 | // Modufy | 515 | // We also need to adjust the base here, because |
452 | uint permsMask = ~ ((uint)PermissionMask.Copy | | 516 | // we should be able to edit in-inventory perms |
453 | (uint)PermissionMask.Transfer | | 517 | // for the root prim, if it's mod. |
454 | (uint)PermissionMask.Modify); | 518 | if (isRootMod) |
455 | |||
456 | // Now, reduce the next perms to the mask bits | ||
457 | // relevant to the operation | ||
458 | uint nextPerms = permsMask | (item.NextPermissions & | ||
459 | ((uint)PermissionMask.Copy | | ||
460 | (uint)PermissionMask.Transfer | | ||
461 | (uint)PermissionMask.Modify)); | ||
462 | |||
463 | // nextPerms now has all bits set, except for the actual | ||
464 | // next permission bits. | ||
465 | |||
466 | // This checks for no mod, no copy, no trans. | ||
467 | // This indicates an error or messed up item. Do it like | ||
468 | // SL and assume trans | ||
469 | if (nextPerms == permsMask) | ||
470 | nextPerms |= (uint)PermissionMask.Transfer; | ||
471 | |||
472 | // Inventory owner perms are the logical AND of the | ||
473 | // folded perms and the root prim perms, however, if | ||
474 | // the root prim is mod, the inventory perms will be | ||
475 | // mod. This happens on "take" and is of little concern | ||
476 | // here, save for preventing escalation | ||
477 | |||
478 | // This hack ensures that items previously permalocked | ||
479 | // get unlocked when they're passed or rezzed | ||
480 | uint basePerms = item.BasePermissions | | ||
481 | (uint)PermissionMask.Move; | ||
482 | uint ownerPerms = item.CurrentPermissions; | ||
483 | |||
484 | // If this is an object, root prim perms may be more | ||
485 | // permissive than folded perms. Use folded perms as | ||
486 | // a mask | ||
487 | if (item.InvType == (int)InventoryType.Object) | ||
488 | { | 519 | { |
489 | // Create a safe mask for the current perms | 520 | ownerPerms |= (uint)PermissionMask.Modify; |
490 | uint foldedPerms = (item.CurrentPermissions & 7) << 13; | 521 | basePerms |= (uint)PermissionMask.Modify; |
491 | foldedPerms |= permsMask; | ||
492 | |||
493 | bool isRootMod = (item.CurrentPermissions & | ||
494 | (uint)PermissionMask.Modify) != 0 ? | ||
495 | true : false; | ||
496 | |||
497 | // Mask the owner perms to the folded perms | ||
498 | ownerPerms &= foldedPerms; | ||
499 | basePerms &= foldedPerms; | ||
500 | |||
501 | // If the root was mod, let the mask reflect that | ||
502 | // We also need to adjust the base here, because | ||
503 | // we should be able to edit in-inventory perms | ||
504 | // for the root prim, if it's mod. | ||
505 | if (isRootMod) | ||
506 | { | ||
507 | ownerPerms |= (uint)PermissionMask.Modify; | ||
508 | basePerms |= (uint)PermissionMask.Modify; | ||
509 | } | ||
510 | } | 522 | } |
523 | } | ||
511 | 524 | ||
512 | // These will be applied to the root prim at next rez. | 525 | // These will be applied to the root prim at next rez. |
513 | // The slam bit (bit 3) and folded permission (bits 0-2) | 526 | // The slam bit (bit 3) and folded permission (bits 0-2) |
514 | // are preserved due to the above mangling | 527 | // are preserved due to the above mangling |
515 | ownerPerms &= nextPerms; | 528 | ownerPerms &= nextPerms; |
516 | 529 | ||
517 | // Mask the base permissions. This is a conservative | 530 | // Mask the base permissions. This is a conservative |
518 | // approach altering only the three main perms | 531 | // approach altering only the three main perms |
519 | basePerms &= nextPerms; | 532 | basePerms &= nextPerms; |
520 | 533 | ||
521 | // Assign to the actual item. Make sure the slam bit is | 534 | // Assign to the actual item. Make sure the slam bit is |
522 | // set, if it wasn't set before. | 535 | // set, if it wasn't set before. |
523 | itemCopy.BasePermissions = basePerms; | 536 | itemCopy.BasePermissions = basePerms; |
524 | itemCopy.CurrentPermissions = ownerPerms; | 537 | itemCopy.CurrentPermissions = ownerPerms; |
525 | itemCopy.Flags |= (uint)InventoryItemFlags.ObjectSlamPerm; | 538 | itemCopy.Flags |= (uint)InventoryItemFlags.ObjectSlamPerm; |
526 | 539 | ||
527 | itemCopy.NextPermissions = item.NextPermissions; | 540 | itemCopy.NextPermissions = item.NextPermissions; |
528 | 541 | ||
529 | // This preserves "everyone can move" | 542 | // This preserves "everyone can move" |
530 | itemCopy.EveryOnePermissions = item.EveryOnePermissions & | 543 | itemCopy.EveryOnePermissions = item.EveryOnePermissions & |
531 | nextPerms; | 544 | nextPerms; |
532 | 545 | ||
533 | // Intentionally killing "share with group" here, as | 546 | // Intentionally killing "share with group" here, as |
534 | // the recipient will not have the group this is | 547 | // the recipient will not have the group this is |
535 | // set to | 548 | // set to |
536 | itemCopy.GroupPermissions = 0; | 549 | itemCopy.GroupPermissions = 0; |
537 | } | 550 | } |
538 | else | 551 | else |
552 | { | ||
553 | itemCopy.CurrentPermissions = item.CurrentPermissions; | ||
554 | itemCopy.NextPermissions = item.NextPermissions; | ||
555 | itemCopy.EveryOnePermissions = item.EveryOnePermissions & item.NextPermissions; | ||
556 | itemCopy.GroupPermissions = item.GroupPermissions & item.NextPermissions; | ||
557 | itemCopy.BasePermissions = item.BasePermissions; | ||
558 | } | ||
559 | |||
560 | if (itemCopy.Folder == UUID.Zero) | ||
561 | { | ||
562 | InventoryFolderBase folder = InventoryService.GetFolderForType(recipient, (AssetType)itemCopy.AssetType); | ||
563 | |||
564 | if (folder != null) | ||
539 | { | 565 | { |
540 | itemCopy.CurrentPermissions = item.CurrentPermissions; | 566 | itemCopy.Folder = folder.ID; |
541 | itemCopy.NextPermissions = item.NextPermissions; | ||
542 | itemCopy.EveryOnePermissions = item.EveryOnePermissions & item.NextPermissions; | ||
543 | itemCopy.GroupPermissions = item.GroupPermissions & item.NextPermissions; | ||
544 | itemCopy.BasePermissions = item.BasePermissions; | ||
545 | } | 567 | } |
546 | 568 | else | |
547 | if (itemCopy.Folder == UUID.Zero) | ||
548 | { | 569 | { |
549 | InventoryFolderBase folder = InventoryService.GetFolderForType(recipient, (AssetType)itemCopy.AssetType); | 570 | InventoryFolderBase root = InventoryService.GetRootFolder(recipient); |
550 | 571 | ||
551 | if (folder != null) | 572 | if (root != null) |
552 | { | 573 | itemCopy.Folder = root.ID; |
553 | itemCopy.Folder = folder.ID; | ||
554 | } | ||
555 | else | 574 | else |
556 | { | 575 | return null; // No destination |
557 | InventoryFolderBase root = InventoryService.GetRootFolder(recipient); | ||
558 | |||
559 | if (root != null) | ||
560 | itemCopy.Folder = root.ID; | ||
561 | else | ||
562 | return null; // No destination | ||
563 | } | ||
564 | } | 576 | } |
577 | } | ||
565 | 578 | ||
566 | itemCopy.GroupID = UUID.Zero; | 579 | itemCopy.GroupID = UUID.Zero; |
567 | itemCopy.GroupOwned = false; | 580 | itemCopy.GroupOwned = false; |
568 | itemCopy.Flags = item.Flags; | 581 | itemCopy.Flags = item.Flags; |
569 | itemCopy.SalePrice = item.SalePrice; | 582 | itemCopy.SalePrice = item.SalePrice; |
570 | itemCopy.SaleType = item.SaleType; | 583 | itemCopy.SaleType = item.SaleType; |
571 | 584 | ||
572 | if (AddInventoryItem(itemCopy)) | 585 | if (AddInventoryItem(itemCopy)) |
573 | { | 586 | { |
574 | IInventoryAccessModule invAccess = RequestModuleInterface<IInventoryAccessModule>(); | 587 | IInventoryAccessModule invAccess = RequestModuleInterface<IInventoryAccessModule>(); |
575 | if (invAccess != null) | 588 | if (invAccess != null) |
576 | invAccess.TransferInventoryAssets(itemCopy, senderId, recipient); | 589 | invAccess.TransferInventoryAssets(itemCopy, senderId, recipient); |
577 | } | 590 | } |
578 | 591 | ||
579 | if (!Permissions.BypassPermissions()) | 592 | if (!Permissions.BypassPermissions()) |
593 | { | ||
594 | if ((item.CurrentPermissions & (uint)PermissionMask.Copy) == 0) | ||
580 | { | 595 | { |
581 | if ((item.CurrentPermissions & (uint)PermissionMask.Copy) == 0) | 596 | List<UUID> items = new List<UUID>(); |
582 | { | 597 | items.Add(itemId); |
583 | List<UUID> items = new List<UUID>(); | 598 | InventoryService.DeleteItems(senderId, items); |
584 | items.Add(itemId); | ||
585 | InventoryService.DeleteItems(senderId, items); | ||
586 | } | ||
587 | } | 599 | } |
588 | |||
589 | return itemCopy; | ||
590 | } | ||
591 | else | ||
592 | { | ||
593 | m_log.WarnFormat("[AGENT INVENTORY]: Failed to find item {0} or item does not belong to giver ", itemId); | ||
594 | return null; | ||
595 | } | 600 | } |
596 | 601 | ||
602 | return itemCopy; | ||
597 | } | 603 | } |
598 | 604 | ||
599 | /// <summary> | 605 | /// <summary> |
@@ -781,7 +787,7 @@ namespace OpenSim.Region.Framework.Scenes | |||
781 | /// <param name="asset"></param> | 787 | /// <param name="asset"></param> |
782 | /// <param name="invType"></param> | 788 | /// <param name="invType"></param> |
783 | /// <param name="nextOwnerMask"></param> | 789 | /// <param name="nextOwnerMask"></param> |
784 | private void CreateNewInventoryItem(IClientAPI remoteClient, string creatorID, string creatorData, UUID folderID, string name, uint flags, uint callbackID, | 790 | public void CreateNewInventoryItem(IClientAPI remoteClient, string creatorID, string creatorData, UUID folderID, string name, uint flags, uint callbackID, |
785 | AssetBase asset, sbyte invType, uint nextOwnerMask, int creationDate) | 791 | AssetBase asset, sbyte invType, uint nextOwnerMask, int creationDate) |
786 | { | 792 | { |
787 | CreateNewInventoryItem( | 793 | CreateNewInventoryItem( |
@@ -836,78 +842,6 @@ namespace OpenSim.Region.Framework.Scenes | |||
836 | } | 842 | } |
837 | 843 | ||
838 | /// <summary> | 844 | /// <summary> |
839 | /// Create a new inventory item. Called when the client creates a new item directly within their | ||
840 | /// inventory (e.g. by selecting a context inventory menu option). | ||
841 | /// </summary> | ||
842 | /// <param name="remoteClient"></param> | ||
843 | /// <param name="transactionID"></param> | ||
844 | /// <param name="folderID"></param> | ||
845 | /// <param name="callbackID"></param> | ||
846 | /// <param name="description"></param> | ||
847 | /// <param name="name"></param> | ||
848 | /// <param name="invType"></param> | ||
849 | /// <param name="type"></param> | ||
850 | /// <param name="wearableType"></param> | ||
851 | /// <param name="nextOwnerMask"></param> | ||
852 | public void CreateNewInventoryItem(IClientAPI remoteClient, UUID transactionID, UUID folderID, | ||
853 | uint callbackID, string description, string name, sbyte invType, | ||
854 | sbyte assetType, | ||
855 | byte wearableType, uint nextOwnerMask, int creationDate) | ||
856 | { | ||
857 | m_log.DebugFormat("[AGENT INVENTORY]: Received request to create inventory item {0} in folder {1}", name, folderID); | ||
858 | |||
859 | if (!Permissions.CanCreateUserInventory(invType, remoteClient.AgentId)) | ||
860 | return; | ||
861 | |||
862 | InventoryFolderBase f = new InventoryFolderBase(folderID, remoteClient.AgentId); | ||
863 | InventoryFolderBase folder = InventoryService.GetFolder(f); | ||
864 | |||
865 | if (folder == null || folder.Owner != remoteClient.AgentId) | ||
866 | return; | ||
867 | |||
868 | if (transactionID == UUID.Zero) | ||
869 | { | ||
870 | ScenePresence presence; | ||
871 | if (TryGetScenePresence(remoteClient.AgentId, out presence)) | ||
872 | { | ||
873 | byte[] data = null; | ||
874 | |||
875 | if (invType == (sbyte)InventoryType.Landmark && presence != null) | ||
876 | { | ||
877 | Vector3 pos = presence.AbsolutePosition; | ||
878 | string strdata = String.Format( | ||
879 | "Landmark version 2\nregion_id {0}\nlocal_pos {1} {2} {3}\nregion_handle {4}\n", | ||
880 | presence.Scene.RegionInfo.RegionID, | ||
881 | pos.X, pos.Y, pos.Z, | ||
882 | presence.RegionHandle); | ||
883 | data = Encoding.ASCII.GetBytes(strdata); | ||
884 | } | ||
885 | |||
886 | AssetBase asset = CreateAsset(name, description, assetType, data, remoteClient.AgentId); | ||
887 | AssetService.Store(asset); | ||
888 | |||
889 | CreateNewInventoryItem(remoteClient, remoteClient.AgentId.ToString(), string.Empty, folderID, asset.Name, 0, callbackID, asset, invType, nextOwnerMask, creationDate); | ||
890 | } | ||
891 | else | ||
892 | { | ||
893 | m_log.ErrorFormat( | ||
894 | "ScenePresence for agent uuid {0} unexpectedly not found in CreateNewInventoryItem", | ||
895 | remoteClient.AgentId); | ||
896 | } | ||
897 | } | ||
898 | else | ||
899 | { | ||
900 | IAgentAssetTransactions agentTransactions = this.RequestModuleInterface<IAgentAssetTransactions>(); | ||
901 | if (agentTransactions != null) | ||
902 | { | ||
903 | agentTransactions.HandleItemCreationFromTransaction( | ||
904 | remoteClient, transactionID, folderID, callbackID, description, | ||
905 | name, invType, assetType, wearableType, nextOwnerMask); | ||
906 | } | ||
907 | } | ||
908 | } | ||
909 | |||
910 | /// <summary> | ||
911 | /// Link an inventory item to an existing item. | 845 | /// Link an inventory item to an existing item. |
912 | /// </summary> | 846 | /// </summary> |
913 | /// <remarks> | 847 | /// <remarks> |