several changes relative to objects return and parcel prim counts: avoid null refs, report correct count of returned objects, make obkects counts by ownership coerent with return rules, etc

httptests
UbitUmarov 2017-01-27 20:21:24 +00:00
parent f76ea3bb76
commit 0091c37ed3
12 changed files with 75 additions and 69 deletions

View File

@ -107,7 +107,7 @@ namespace OpenSim.Framework
public delegate void GenericCall4(Packet packet, IClientAPI remoteClient);
public delegate void DeRezObject(
IClientAPI remoteClient, List<uint> localIDs, UUID groupID, DeRezAction action, UUID destinationID);
IClientAPI remoteClient, List<uint> localIDs, UUID groupID, DeRezAction action, UUID destinationID, bool AddToReturns = true);
public delegate void GenericCall5(IClientAPI remoteClient, bool status);

View File

@ -149,9 +149,11 @@ namespace OpenSim.Region.CoreModules.World.Land
parcelInfoCache.Size = 30; // the number of different parcel requests in this region to cache
parcelInfoCache.DefaultTTL = new TimeSpan(0, 5, 0);
m_scene.EventManager.OnObjectAddedToScene += EventManagerOnParcelPrimCountAdd;
m_scene.EventManager.OnParcelPrimCountAdd += EventManagerOnParcelPrimCountAdd;
m_scene.EventManager.OnParcelPrimCountUpdate += EventManagerOnParcelPrimCountUpdate;
m_scene.EventManager.OnObjectBeingRemovedFromScene += EventManagerOnObjectBeingRemovedFromScene;
m_scene.EventManager.OnParcelPrimCountUpdate += EventManagerOnParcelPrimCountUpdate;
m_scene.EventManager.OnRequestParcelPrimCountUpdate += EventManagerOnRequestParcelPrimCountUpdate;
m_scene.EventManager.OnAvatarEnteringNewParcel += EventManagerOnAvatarEnteringNewParcel;
@ -815,6 +817,9 @@ namespace OpenSim.Region.CoreModules.World.Land
throw new Exception("Error: Parcel not found at point " + x + ", " + y);
}
if(m_landList.Count == 0 || m_landIDList == null)
return null;
lock (m_landIDList)
{
try
@ -826,8 +831,6 @@ namespace OpenSim.Region.CoreModules.World.Land
return null;
}
}
return m_landList[m_landIDList[x / 4, y / 4]];
}
// Create a 'parcel is here' bitmap for the parcel identified by the passed landID
@ -1642,9 +1645,9 @@ namespace OpenSim.Region.CoreModules.World.Land
foreach (HashSet<SceneObjectGroup> objs in returns.Values)
{
List<SceneObjectGroup> objs2 = new List<SceneObjectGroup>(objs);
if (m_scene.Permissions.CanReturnObjects(null, remoteClient.AgentId, objs2))
if (m_scene.Permissions.CanReturnObjects(null, remoteClient, objs2))
{
m_scene.returnObjects(objs2.ToArray(), remoteClient.AgentId);
m_scene.returnObjects(objs2.ToArray(), remoteClient);
}
else
{
@ -2037,7 +2040,7 @@ namespace OpenSim.Region.CoreModules.World.Land
{
SceneObjectGroup[] objs = new SceneObjectGroup[1];
objs[0] = obj;
((Scene)client.Scene).returnObjects(objs, client.AgentId);
((Scene)client.Scene).returnObjects(objs, client);
}
Dictionary<UUID, System.Threading.Timer> Timers = new Dictionary<UUID, System.Threading.Timer>();

View File

@ -1664,7 +1664,7 @@ namespace OpenSim.Region.CoreModules.World.Land
{
SceneObjectGroup[] objs = new SceneObjectGroup[1];
objs[0] = obj;
m_scene.returnObjects(objs, obj.OwnerID);
m_scene.returnObjects(objs, null);
}
public void ReturnLandObjects(uint type, UUID[] owners, UUID[] tasks, IClientAPI remote_client)
@ -1695,6 +1695,8 @@ namespace OpenSim.Region.CoreModules.World.Land
{
if (obj.GroupID == LandData.GroupID)
{
if (obj.OwnerID == LandData.OwnerID)
continue;
if (!returns.ContainsKey(obj.OwnerID))
returns[obj.OwnerID] =
new List<SceneObjectGroup>();
@ -1736,8 +1738,8 @@ namespace OpenSim.Region.CoreModules.World.Land
foreach (List<SceneObjectGroup> ol in returns.Values)
{
if (m_scene.Permissions.CanReturnObjects(this, remote_client.AgentId, ol))
m_scene.returnObjects(ol.ToArray(), remote_client.AgentId);
if (m_scene.Permissions.CanReturnObjects(this, remote_client, ol))
m_scene.returnObjects(ol.ToArray(), remote_client);
}
}

View File

@ -92,10 +92,8 @@ namespace OpenSim.Region.CoreModules.World.Land
m_Scene.RegisterModuleInterface<IPrimCountModule>(this);
m_Scene.EventManager.OnObjectAddedToScene += OnParcelPrimCountAdd;
m_Scene.EventManager.OnObjectBeingRemovedFromScene +=
OnObjectBeingRemovedFromScene;
m_Scene.EventManager.OnParcelPrimCountTainted +=
OnParcelPrimCountTainted;
m_Scene.EventManager.OnObjectBeingRemovedFromScene += OnObjectBeingRemovedFromScene;
m_Scene.EventManager.OnParcelPrimCountTainted += OnParcelPrimCountTainted;
m_Scene.EventManager.OnLandObjectAdded += delegate(ILandObject lo) { OnParcelPrimCountTainted(); };
}
@ -215,30 +213,16 @@ namespace OpenSim.Region.CoreModules.World.Land
else
parcelCounts.Users[obj.OwnerID] = partCount;
if (obj.IsSelected)
{
if (obj.IsSelected || obj.GetSittingAvatarsCount() > 0)
parcelCounts.Selected += partCount;
}
else
{
if (landData.IsGroupOwned)
{
if (obj.OwnerID == landData.GroupID)
if (obj.OwnerID == landData.OwnerID)
parcelCounts.Owner += partCount;
else if (landData.GroupID != UUID.Zero && obj.GroupID == landData.GroupID)
parcelCounts.Group += partCount;
else
parcelCounts.Others += partCount;
}
else
{
if (obj.OwnerID == landData.OwnerID)
parcelCounts.Owner += partCount;
else
parcelCounts.Others += partCount;
}
}
}
}
// NOTE: Call under Taint Lock
@ -393,7 +377,6 @@ namespace OpenSim.Region.CoreModules.World.Land
count = counts.Owner;
count += counts.Group;
count += counts.Others;
count += counts.Selected;
}
}

View File

@ -282,9 +282,10 @@ namespace OpenSim.Region.CoreModules.World.Permissions
scenePermissions.OnTerraformLand += CanTerraformLand;
scenePermissions.OnBuyLand += CanBuyLand;
scenePermissions.OnReturnObjects += CanReturnObjects;
scenePermissions.OnRezObject += CanRezObject;
scenePermissions.OnObjectEntry += CanObjectEntry;
scenePermissions.OnReturnObjects += CanReturnObjects;
scenePermissions.OnDuplicateObject += CanDuplicateObject;
scenePermissions.OnDeleteObjectByIDs += CanDeleteObjectByIDs;
@ -1621,19 +1622,20 @@ namespace OpenSim.Region.CoreModules.World.Permissions
return false;
}
private bool CanReturnObjects(ILandObject land, UUID user, List<SceneObjectGroup> objects)
private bool CanReturnObjects(ILandObject land, ScenePresence sp, List<SceneObjectGroup> objects)
{
DebugPermissionInformation(MethodInfo.GetCurrentMethod().Name);
if (m_bypassPermissions) return m_bypassPermissionsValue;
ScenePresence sp = m_scene.GetScenePresence(user);
if (sp == null)
return false;
if(sp == null)
return true; // assuming that in this case rights are as owner
bool isPrivUser = sp.IsGod || IsEstateManager(user);
UUID userID = sp.UUID;
bool isPrivUser = sp.IsGod || IsEstateManager(userID);
IClientAPI client = sp.ControllingClient;
GroupPowers powers;
ulong powers = 0;
ILandObject l;
foreach (SceneObjectGroup g in new List<SceneObjectGroup>(objects))
@ -1644,7 +1646,7 @@ namespace OpenSim.Region.CoreModules.World.Permissions
continue;
}
if (isPrivUser || g.OwnerID == user)
if (isPrivUser || g.OwnerID == userID)
continue;
// This is a short cut for efficiency. If land is non-null,
@ -1671,7 +1673,7 @@ namespace OpenSim.Region.CoreModules.World.Permissions
LandData ldata = l.LandData;
// If we own the land outright, then allow
//
if (ldata.OwnerID == user)
if (ldata.OwnerID == userID)
continue;
// Group voodoo
@ -1679,10 +1681,10 @@ namespace OpenSim.Region.CoreModules.World.Permissions
if (ldata.IsGroupOwned)
{
UUID lGroupID = ldata.GroupID;
powers = (GroupPowers)client.GetGroupPowers(lGroupID);
// Not a group member, or no rights at all
//
if (powers == (GroupPowers)0)
powers = client.GetGroupPowers(lGroupID);
if(powers == 0)
{
objects.Remove(g);
continue;
@ -1691,7 +1693,7 @@ namespace OpenSim.Region.CoreModules.World.Permissions
// Group deeded object?
//
if (g.OwnerID == lGroupID &&
(powers & GroupPowers.ReturnGroupOwned) == (GroupPowers)0)
(powers & (ulong)GroupPowers.ReturnGroupOwned) == 0)
{
objects.Remove(g);
continue;
@ -1700,13 +1702,13 @@ namespace OpenSim.Region.CoreModules.World.Permissions
// Group set object?
//
if (g.GroupID == lGroupID &&
(powers & GroupPowers.ReturnGroupSet) == (GroupPowers)0)
(powers & (ulong)GroupPowers.ReturnGroupSet) == 0)
{
objects.Remove(g);
continue;
}
if ((powers & GroupPowers.ReturnNonGroup) == (GroupPowers)0)
if ((powers & (ulong)GroupPowers.ReturnNonGroup) == 0)
{
objects.Remove(g);
continue;

View File

@ -105,8 +105,9 @@ namespace OpenSim.Region.CoreModules.World.Vegetation
if (rootPart.Shape.PCode != (byte)PCode.Grass)
AdaptTree(ref shape);
m_scene.AddNewSceneObject(sceneObject, true);
sceneObject.SetGroup(groupID, null);
m_scene.AddNewSceneObject(sceneObject, true);
sceneObject.AggregatePerms();
return sceneObject;
}

View File

@ -2085,7 +2085,7 @@ namespace OpenSim.Region.Framework.Scenes
/// <param name='action'>DeRezAction</param>
/// <param name='destinationID'>User folder ID to place derezzed object</param>
public virtual void DeRezObjects(
IClientAPI remoteClient, List<uint> localIDs, UUID groupID, DeRezAction action, UUID destinationID)
IClientAPI remoteClient, List<uint> localIDs, UUID groupID, DeRezAction action, UUID destinationID, bool AddToReturns = true)
{
// First, see of we can perform the requested action and
// build a list of eligible objects
@ -2094,7 +2094,11 @@ namespace OpenSim.Region.Framework.Scenes
List<SceneObjectGroup> takeGroups = new List<SceneObjectGroup>();
List<SceneObjectGroup> takeDeleteGroups = new List<SceneObjectGroup>();
ScenePresence sp = remoteClient.SceneAgent as ScenePresence;
ScenePresence sp = null;
if(remoteClient != null)
sp = remoteClient.SceneAgent as ScenePresence;
else if(action != DeRezAction.Return)
return; // only Return can be called without a client
// Start with true for both, then remove the flags if objects
// that we can't derez are part of the selection
@ -2201,13 +2205,14 @@ namespace OpenSim.Region.Framework.Scenes
{
if (Permissions.CanReturnObjects(
null,
remoteClient.AgentId,
remoteClient,
new List<SceneObjectGroup>() {grp}))
{
permissionToTake = true;
permissionToDelete = true;
AddReturn(grp.OwnerID == grp.GroupID ? grp.LastOwnerID : grp.OwnerID, grp.Name, grp.AbsolutePosition, "parcel owner return");
if(AddToReturns)
AddReturn(grp.OwnerID == grp.GroupID ? grp.LastOwnerID : grp.OwnerID, grp.Name, grp.AbsolutePosition,
"parcel owner return");
}
}
else // Auto return passes through here with null agent
@ -2641,7 +2646,7 @@ namespace OpenSim.Region.Framework.Scenes
}
public virtual bool returnObjects(SceneObjectGroup[] returnobjects,
UUID AgentId)
IClientAPI client)
{
List<uint> localIDs = new List<uint>();
@ -2651,8 +2656,8 @@ namespace OpenSim.Region.Framework.Scenes
"parcel owner return");
localIDs.Add(grp.RootPart.LocalId);
}
DeRezObjects(null, localIDs, UUID.Zero, DeRezAction.Return,
UUID.Zero);
DeRezObjects(client, localIDs, UUID.Zero, DeRezAction.Return,
UUID.Zero, false);
return true;
}

View File

@ -185,7 +185,9 @@ namespace OpenSim.Region.Framework.Scenes
// A prim is only tainted if it's allowed to be edited by the person clicking it.
if (Permissions.CanChangeSelectedState(part, (ScenePresence)remoteClient.SceneAgent))
{
bool oldsel = part.IsSelected;
part.IsSelected = true;
if(!oldsel)
EventManager.TriggerParcelPrimCountTainted();
}
@ -228,6 +230,7 @@ namespace OpenSim.Region.Framework.Scenes
if (so.OwnerID == remoteClient.AgentId)
{
so.SetGroup(groupID, remoteClient);
EventManager.TriggerParcelPrimCountTainted();
}
}
}

View File

@ -54,7 +54,7 @@ namespace OpenSim.Region.Framework.Scenes
public delegate bool EditObjectInventoryHandler(UUID objectID, UUID editorID);
public delegate bool MoveObjectHandler(SceneObjectGroup sog, ScenePresence sp);
public delegate bool ObjectEntryHandler(SceneObjectGroup sog, bool enteringRegion, Vector3 newPoint);
public delegate bool ReturnObjectsHandler(ILandObject land, UUID user, List<SceneObjectGroup> objects);
public delegate bool ReturnObjectsHandler(ILandObject land, ScenePresence sp, List<SceneObjectGroup> objects);
public delegate bool InstantMessageHandler(UUID user, UUID target);
public delegate bool InventoryTransferHandler(UUID user, UUID target);
public delegate bool ViewScriptHandler(UUID script, UUID objectID, UUID user);
@ -556,17 +556,24 @@ namespace OpenSim.Region.Framework.Scenes
#endregion
#region RETURN OBJECT
public bool CanReturnObjects(ILandObject land, UUID user, List<SceneObjectGroup> objects)
public bool CanReturnObjects(ILandObject land, IClientAPI client, List<SceneObjectGroup> objects)
{
bool result = true;
ReturnObjectsHandler handler = OnReturnObjects;
if (handler != null)
{
if(objects == null)
return false;
ScenePresence sp = null;
if(client != null && client.SceneAgent != null)
sp = client.SceneAgent as ScenePresence;
Delegate[] list = handler.GetInvocationList();
foreach (ReturnObjectsHandler h in list)
{
if (h(land, user, objects) == false)
if (h(land, sp, objects) == false)
{
result = false;
break;

View File

@ -2604,8 +2604,8 @@ namespace OpenSim.Region.Framework.Scenes
{
// Otherwise, use this default creation code;
sceneObject = new SceneObjectGroup(ownerID, pos, rot, shape);
AddNewSceneObject(sceneObject, true);
sceneObject.SetGroup(groupID, null);
AddNewSceneObject(sceneObject, true);
if (AgentPreferencesService != null) // This will override the brave new full perm world!
{
@ -2784,7 +2784,7 @@ namespace OpenSim.Region.Framework.Scenes
}
if (toReturn.Count > 0)
{
returnObjects(toReturn.ToArray(), UUID.Zero);
returnObjects(toReturn.ToArray(), null);
}
}

View File

@ -645,7 +645,7 @@ namespace OpenSim.Region.Framework.Scenes
localIDs.Add(sog.RootPart.LocalId);
sogScene.AddReturn(sog.OwnerID, sog.Name, sog.AbsolutePosition,
"Returned at region cross");
sogScene.DeRezObjects(null, localIDs, UUID.Zero, DeRezAction.Return, UUID.Zero);
sogScene.DeRezObjects(null, localIDs, UUID.Zero, DeRezAction.Return, UUID.Zero, false);
}
catch (Exception)
{
@ -2254,7 +2254,7 @@ namespace OpenSim.Region.Framework.Scenes
RootPart.UUID);
m_scene.AddReturn(OwnerID == GroupID ? LastOwnerID : OwnerID, Name, AbsolutePosition, "parcel autoreturn");
m_scene.DeRezObjects(null, new List<uint>() { RootPart.LocalId }, UUID.Zero,
DeRezAction.Return, UUID.Zero);
DeRezAction.Return, UUID.Zero, false);
return;
}

View File

@ -523,8 +523,8 @@ namespace OpenSim.Region.OptionalModules.World.TreePopulator
rootPart.AddFlag(PrimFlags.Phantom);
m_scene.AddNewSceneObject(sceneObject, true);
sceneObject.SetGroup(groupID, null);
m_scene.AddNewSceneObject(sceneObject, true);
sceneObject.AggregatePerms();
return sceneObject;
}