Revamp the permissions propagation. This MAY mess up. Please test.

Change the slam bit from 3 to 4. Assume the old slam bit is always set.
The new slam bit is a "changed owner" bit, correcting a bug where an item
passed from the creator to another with less than full perms, then back (sale
test) would arrive back full perm. Lots of in-code docs.
prebuild-update
Melanie 2010-07-13 20:45:16 +01:00
parent bed36901d1
commit dd14016885
6 changed files with 139 additions and 57 deletions

View File

@ -781,7 +781,7 @@ namespace OpenSim.Data.Tests
// Ownership changes when you drop an object into an object
// owned by someone else
Assert.That(t.OwnerID,Is.EqualTo(sog.RootPart.OwnerID), "Assert.That(t.OwnerID,Is.EqualTo(sog.RootPart.OwnerID))");
Assert.That(t.CurrentPermissions, Is.EqualTo(curperm | 8), "Assert.That(t.CurrentPermissions, Is.EqualTo(curperm | 8))");
Assert.That(t.CurrentPermissions, Is.EqualTo(curperm | 16), "Assert.That(t.CurrentPermissions, Is.EqualTo(curperm | 8))");
Assert.That(t.ParentID,Is.EqualTo(sog.RootPart.FolderID), "Assert.That(t.ParentID,Is.EqualTo(sog.RootPart.FolderID))");
Assert.That(t.ParentPartID,Is.EqualTo(sog.RootPart.UUID), "Assert.That(t.ParentPartID,Is.EqualTo(sog.RootPart.UUID))");
}

View File

@ -381,12 +381,27 @@ namespace OpenSim.Region.CoreModules.Framework.InventoryAccess
if ((nextPerms & (uint)PermissionMask.Modify) == 0)
perms &= ~(uint)PermissionMask.Modify;
// Make sure all bits but the ones we want are clear
// on take.
// This will be applied to the current perms, so
// it will do what we want.
objectGroup.RootPart.NextOwnerMask &=
((uint)PermissionMask.Copy |
(uint)PermissionMask.Transfer |
(uint)PermissionMask.Modify);
objectGroup.RootPart.NextOwnerMask |=
(uint)PermissionMask.Move;
item.BasePermissions = perms & objectGroup.RootPart.NextOwnerMask;
item.CurrentPermissions = item.BasePermissions;
item.NextPermissions = objectGroup.RootPart.NextOwnerMask;
item.EveryOnePermissions = objectGroup.RootPart.EveryoneMask & objectGroup.RootPart.NextOwnerMask;
item.GroupPermissions = objectGroup.RootPart.GroupMask & objectGroup.RootPart.NextOwnerMask;
item.CurrentPermissions |= 8; // Slam!
// Magic number badness. Maybe this deserves an enum.
// bit 4 (16) is the "Slam" bit, it means treat as passed
// and apply next owner perms on rez
item.CurrentPermissions |= 16; // Slam!
}
else
{
@ -396,7 +411,12 @@ namespace OpenSim.Region.CoreModules.Framework.InventoryAccess
item.EveryOnePermissions = objectGroup.RootPart.EveryoneMask;
item.GroupPermissions = objectGroup.RootPart.GroupMask;
item.CurrentPermissions |= 8; // Slam!
item.CurrentPermissions &=
((uint)PermissionMask.Copy |
(uint)PermissionMask.Transfer |
(uint)PermissionMask.Modify |
(uint)PermissionMask.Move |
7); // Preserve folded permissions
}
// TODO: add the new fields (Flags, Sale info, etc)
@ -498,7 +518,12 @@ namespace OpenSim.Region.CoreModules.Framework.InventoryAccess
= SceneObjectSerializer.FromOriginalXmlFormat(itemId, xmlData);
group.RootPart.FromFolderID = item.Folder;
group.RootPart.CreateSelected = true
// If it's rezzed in world, select it. Much easier to
// find small items.
//
if (!attachment)
group.RootPart.CreateSelected = true;
if (!m_Scene.Permissions.CanRezObject(
group.Children.Count, remoteClient.AgentId, pos)
@ -572,7 +597,7 @@ namespace OpenSim.Region.CoreModules.Framework.InventoryAccess
List<SceneObjectPart> partList = new List<SceneObjectPart>(group.Children.Values);
group.SetGroup(remoteClient.ActiveGroupId, remoteClient);
if (rootPart.OwnerID != item.Owner)
if ((rootPart.OwnerID != item.Owner) || (item.CurrentPermissions & 16) != 0)
{
//Need to kill the for sale here
rootPart.ObjectSaleType = 0;
@ -580,14 +605,11 @@ namespace OpenSim.Region.CoreModules.Framework.InventoryAccess
if (m_Scene.Permissions.PropagatePermissions())
{
if ((item.CurrentPermissions & 8) != 0)
foreach (SceneObjectPart part in partList)
{
foreach (SceneObjectPart part in partList)
{
part.EveryoneMask = item.EveryOnePermissions;
part.NextOwnerMask = item.NextPermissions;
part.GroupMask = 0; // DO NOT propagate here
}
part.EveryoneMask = item.EveryOnePermissions;
part.NextOwnerMask = item.NextPermissions;
part.GroupMask = 0; // DO NOT propagate here
}
group.ApplyNextOwnerPermissions();
@ -596,19 +618,15 @@ namespace OpenSim.Region.CoreModules.Framework.InventoryAccess
foreach (SceneObjectPart part in partList)
{
if (part.OwnerID != item.Owner)
if ((part.OwnerID != item.Owner) || (item.CurrentPermissions & 16) != 0)
{
part.LastOwnerID = part.OwnerID;
part.OwnerID = item.Owner;
part.Inventory.ChangeInventoryOwner(item.Owner);
}
else if (((item.CurrentPermissions & 8) != 0) && (!attachment)) // Slam!
{
part.EveryoneMask = item.EveryOnePermissions;
part.NextOwnerMask = item.NextPermissions;
part.GroupMask = 0; // DO NOT propagate here
}
part.EveryoneMask = item.EveryOnePermissions;
part.NextOwnerMask = item.NextPermissions;
}
rootPart.TrimPermissions();

View File

@ -265,6 +265,10 @@ namespace OpenSim.Region.Framework.Scenes
public void UpdateInventoryItemAsset(IClientAPI remoteClient, UUID transactionID,
UUID itemID, InventoryItemBase itemUpd)
{
// This one will let people set next perms on items in agent
// inventory. Rut-Roh. Whatever. Make this secure. Yeah.
//
// Passing something to another avatar or a an object will already
InventoryItemBase item = new InventoryItemBase(itemID, remoteClient.AgentId);
item = InventoryService.GetItem(item);
@ -274,11 +278,9 @@ namespace OpenSim.Region.Framework.Scenes
{
item.Name = itemUpd.Name;
item.Description = itemUpd.Description;
item.NextPermissions = itemUpd.NextPermissions;
item.CurrentPermissions |= 8; // Slam!
item.EveryOnePermissions = itemUpd.EveryOnePermissions;
item.GroupPermissions = itemUpd.GroupPermissions;
item.NextPermissions = itemUpd.NextPermissions & item.BasePermissions;
item.EveryOnePermissions = itemUpd.EveryOnePermissions & item.BasePermissions;
item.GroupPermissions = itemUpd.GroupPermissions & item.BasePermissions;
item.GroupID = itemUpd.GroupID;
item.GroupOwned = itemUpd.GroupOwned;
item.CreationDate = itemUpd.CreationDate;
@ -384,28 +386,96 @@ namespace OpenSim.Region.Framework.Scenes
if (Permissions.PropagatePermissions() && recipient != senderId)
{
// First, make sore base is limited to the next perms
itemCopy.BasePermissions = item.BasePermissions & (item.NextPermissions | (uint)PermissionMask.Move);
// By default, current equals base
itemCopy.CurrentPermissions = itemCopy.BasePermissions & item.CurrentPermissions;
// Trying to do this right this time. This is evil. If
// you believe in Good, go elsewhere. Vampires and other
// evil creatores only beyond this point. You have been
// warned.
// If this is an object, replace current perms
// with folded perms
// We're going to mask a lot of things by the next perms
// Tweak the next perms to be nicer to our data
//
// In this mask, all the bits we do NOT want to mess
// with are set. These are:
//
// Transfer
// Copy
// Modufy
uint permsMask = ~ ((uint)PermissionMask.Copy |
(uint)PermissionMask.Transfer |
(uint)PermissionMask.Modify);
// Now, reduce the next perms to the mask bits
// relevant to the operation
uint nextPerms = permsMask | (item.NextPermissions &
((uint)PermissionMask.Copy |
(uint)PermissionMask.Transfer |
(uint)PermissionMask.Modify));
// nextPerms now has all bits set, except for the actual
// next permission bits.
// This checks for no mod, no copy, no trans.
// This indicates an error or messed up item. Do it like
// SL and assume trans
if (nextPerms == permsMask)
nextPerms |= (uint)PermissionMask.Transfer;
// Inventory owner perms are the logical AND of the
// folded perms and the root prim perms, however, if
// the root prim is mod, the inventory perms will be
// mod. This happens on "take" and is of little concern
// here, save for preventing escalation
// This hack ensures that items previously permalocked
// get unlocked when they're passed or rezzed
uint basePerms = item.BasePermissions |
(uint)PermissionMask.Move;
uint ownerPerms = item.CurrentPermissions;
// Mask the base permissions. This is a conservative
// approach altering only the three main perms
basePerms &= nextPerms;
// If this is an object, root prim perms may be more
// permissive than folded perms. Use folded perms as
// a mask
if (item.InvType == (int)InventoryType.Object)
{
itemCopy.CurrentPermissions &= ~(uint)(PermissionMask.Copy | PermissionMask.Modify | PermissionMask.Transfer);
itemCopy.CurrentPermissions |= (item.CurrentPermissions & 7) << 13;
// Create a safe mask for the current perms
uint foldedPerms = (item.CurrentPermissions & 7) << 13;
foldedPerms |= permsMask;
bool isRootMod = (item.CurrentPermissions &
(uint)PermissionMask.Modify) != 0 ?
true : false;
// Mask the owner perms to the folded perms
ownerPerms &= foldedPerms;
// If the root was mod, let the mask reflect that
if (isRootMod)
ownerPerms |= (uint)PermissionMask.Modify;
}
// Ensure there is no escalation
itemCopy.CurrentPermissions &= (item.NextPermissions | (uint)PermissionMask.Move);
// These will be applied to the root prim at next rez.
// The slam bit (bit 3) and folded permission (bits 0-2)
// are preserved due to the above mangling
ownerPerms &= nextPerms;
// Need slam bit on xfer
itemCopy.CurrentPermissions |= 8;
// Assign to the actual item. Make sure the slam bit is
// set, if it wasn't set before.
itemCopy.BasePermissions = basePerms;
itemCopy.CurrentPermissions = ownerPerms | 16; // Slam
itemCopy.NextPermissions = item.NextPermissions;
itemCopy.EveryOnePermissions = 0;
// This preserves "everyone can move"
itemCopy.EveryOnePermissions = item.EveryOnePermissions &
nextPerms;
// Intentionally killing "share with group" here, as
// the recipient will not have the group this is
// set to
itemCopy.GroupPermissions = 0;
}
else
@ -903,7 +973,7 @@ namespace OpenSim.Region.Framework.Scenes
else
agentItem.CurrentPermissions = agentItem.BasePermissions & taskItem.CurrentPermissions;
agentItem.CurrentPermissions |= 8;
agentItem.CurrentPermissions |= 16; // Slam
agentItem.NextPermissions = taskItem.NextPermissions;
agentItem.EveryOnePermissions = taskItem.EveryonePermissions & (taskItem.NextPermissions | (uint)PermissionMask.Move);
agentItem.GroupPermissions = taskItem.GroupPermissions & taskItem.NextPermissions;
@ -1094,7 +1164,7 @@ namespace OpenSim.Region.Framework.Scenes
(srcTaskItem.NextPermissions | (uint)PermissionMask.Move);
destTaskItem.BasePermissions = srcTaskItem.BasePermissions &
(srcTaskItem.NextPermissions | (uint)PermissionMask.Move);
destTaskItem.CurrentPermissions |= 8; // Slam!
destTaskItem.CurrentPermissions |= 16; // Slam!
}
}
@ -1478,7 +1548,7 @@ namespace OpenSim.Region.Framework.Scenes
srcTaskItem.NextPermissions;
destTaskItem.BasePermissions = srcTaskItem.BasePermissions &
srcTaskItem.NextPermissions;
destTaskItem.CurrentPermissions |= 8; // Slam!
destTaskItem.CurrentPermissions |= 16; // Slam!
}
}
@ -1864,17 +1934,14 @@ namespace OpenSim.Region.Framework.Scenes
group.SetGroup(sourcePart.GroupID, null);
if (rootPart.OwnerID != item.OwnerID)
if ((rootPart.OwnerID != item.OwnerID) || (item.CurrentPermissions & 16) != 0)
{
if (Permissions.PropagatePermissions())
{
if ((item.CurrentPermissions & 8) != 0)
foreach (SceneObjectPart part in partList)
{
foreach (SceneObjectPart part in partList)
{
part.EveryoneMask = item.EveryonePermissions;
part.NextOwnerMask = item.NextPermissions;
}
part.EveryoneMask = item.EveryonePermissions;
part.NextOwnerMask = item.NextPermissions;
}
group.ApplyNextOwnerPermissions();
}
@ -1882,17 +1949,14 @@ namespace OpenSim.Region.Framework.Scenes
foreach (SceneObjectPart part in partList)
{
if (part.OwnerID != item.OwnerID)
if ((part.OwnerID != item.OwnerID) || (item.CurrentPermissions & 16) != 0)
{
part.LastOwnerID = part.OwnerID;
part.OwnerID = item.OwnerID;
part.Inventory.ChangeInventoryOwner(item.OwnerID);
}
else if ((item.CurrentPermissions & 8) != 0) // Slam!
{
part.EveryoneMask = item.EveryonePermissions;
part.NextOwnerMask = item.NextPermissions;
}
part.EveryoneMask = item.EveryonePermissions;
part.NextOwnerMask = item.NextPermissions;
}
rootPart.TrimPermissions();

View File

@ -4731,7 +4731,7 @@ namespace OpenSim.Region.Framework.Scenes
part.NextOwnerMask;
item.GroupPermissions = part.GroupMask &
part.NextOwnerMask;
item.CurrentPermissions |= 8; // Slam!
item.CurrentPermissions |= 16; // Slam!
item.CreationDate = Util.UnixTimeSinceEpoch();
if (InventoryService.AddItem(item))

View File

@ -172,13 +172,14 @@ namespace OpenSim.Region.Framework.Scenes
taskItem.GroupPermissions = item.GroupPermissions &
item.NextPermissions;
taskItem.NextPermissions = item.NextPermissions;
taskItem.CurrentPermissions |= 8;
// We're adding this to a prim we don't own. Force
// owner change
taskItem.CurrentPermissions |= 16; // Slam
}
else
{
taskItem.BasePermissions = item.BasePermissions;
taskItem.CurrentPermissions = item.CurrentPermissions;
taskItem.CurrentPermissions |= 8;
taskItem.EveryonePermissions = item.EveryOnePermissions;
taskItem.GroupPermissions = item.GroupPermissions;
taskItem.NextPermissions = item.NextPermissions;

View File

@ -952,7 +952,6 @@ namespace OpenSim.Region.Framework.Scenes
item.CurrentPermissions &= ~(uint)PermissionMask.Transfer;
if ((item.CurrentPermissions & ((uint)PermissionMask.Modify >> 13)) == 0)
item.CurrentPermissions &= ~(uint)PermissionMask.Modify;
item.CurrentPermissions |= 8;
}
item.CurrentPermissions &= item.NextPermissions;
item.BasePermissions &= item.NextPermissions;