From 93206ef0fa6dffe93313455b3354ce3787e7262d Mon Sep 17 00:00:00 2001 From: "Justin Clark-Casey (justincc)" Date: Sat, 23 Mar 2013 00:39:03 +0000 Subject: [PATCH 01/40] Add "show borders" command to show the borders of a region. This is relevant to mega-regions where the borders are very different to a regular region. Also adds some method doc and other code comments. --- .../EntityTransfer/EntityTransferModule.cs | 4 +++ OpenSim/Region/Framework/Scenes/Border.cs | 7 +++-- OpenSim/Region/Framework/Scenes/Scene.cs | 1 - .../Region/Framework/Scenes/ScenePresence.cs | 14 +++++++-- .../SceneCommands/SceneCommandsModule.cs | 31 +++++++++++++++++++ .../RegionCombinerModule.cs | 8 ++--- 6 files changed, 54 insertions(+), 11 deletions(-) diff --git a/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferModule.cs b/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferModule.cs index 26267e27a1..136caad36b 100644 --- a/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferModule.cs +++ b/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferModule.cs @@ -994,6 +994,10 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer { Scene scene = agent.Scene; Vector3 pos = agent.AbsolutePosition; + +// m_log.DebugFormat( +// "[ENTITY TRANSFER MODULE]: Crossing agent {0} at pos {1} in {2}", agent.Name, pos, scene.Name); + Vector3 newpos = new Vector3(pos.X, pos.Y, pos.Z); uint neighbourx = scene.RegionInfo.RegionLocX; uint neighboury = scene.RegionInfo.RegionLocY; diff --git a/OpenSim/Region/Framework/Scenes/Border.cs b/OpenSim/Region/Framework/Scenes/Border.cs index c6a6511046..08c0c31009 100644 --- a/OpenSim/Region/Framework/Scenes/Border.cs +++ b/OpenSim/Region/Framework/Scenes/Border.cs @@ -33,8 +33,7 @@ using OpenMetaverse; namespace OpenSim.Region.Framework.Scenes { public class Border - { - + { /// /// Line perpendicular to the Direction Cardinal. Z value is the /// @@ -81,6 +80,10 @@ namespace OpenSim.Region.Framework.Scenes TriggerRegionY = triggerRegionY; } + /// + /// Tests to see if the given position would cross this border. + /// + /// public bool TestCross(Vector3 position) { bool result = false; diff --git a/OpenSim/Region/Framework/Scenes/Scene.cs b/OpenSim/Region/Framework/Scenes/Scene.cs index c9c0662228..e8f00a4d90 100644 --- a/OpenSim/Region/Framework/Scenes/Scene.cs +++ b/OpenSim/Region/Framework/Scenes/Scene.cs @@ -2541,7 +2541,6 @@ namespace OpenSim.Region.Framework.Scenes } } - return null; } diff --git a/OpenSim/Region/Framework/Scenes/ScenePresence.cs b/OpenSim/Region/Framework/Scenes/ScenePresence.cs index 6d96c936a5..f7ae3a219f 100644 --- a/OpenSim/Region/Framework/Scenes/ScenePresence.cs +++ b/OpenSim/Region/Framework/Scenes/ScenePresence.cs @@ -442,9 +442,9 @@ namespace OpenSim.Region.Framework.Scenes { m_pos = PhysicsActor.Position; - //m_log.DebugFormat( - // "[SCENE PRESENCE]: Set position {0} for {1} in {2} via getting AbsolutePosition!", - // m_pos, Name, Scene.RegionInfo.RegionName); +// m_log.DebugFormat( +// "[SCENE PRESENCE]: Set position of {0} in {1} to {2} via getting AbsolutePosition!", +// Name, Scene.Name, m_pos); } else { @@ -471,6 +471,9 @@ namespace OpenSim.Region.Framework.Scenes } set { +// m_log.DebugFormat("[SCENE PRESENCE]: Setting position of {0} in {1} to {2}", Name, Scene.Name, value); +// Util.PrintCallStack(); + if (PhysicsActor != null) { try @@ -878,6 +881,7 @@ namespace OpenSim.Region.Framework.Scenes // before the inventory is processed in MakeRootAgent. This fixes a race condition // related to the handling of attachments //m_scene.GetAvatarAppearance(ControllingClient, out Appearance); + if (m_scene.TestBorderCross(pos, Cardinals.E)) { Border crossedBorder = m_scene.GetCrossedBorder(pos, Cardinals.E); @@ -2909,6 +2913,10 @@ namespace OpenSim.Region.Framework.Scenes if (!IsInTransit) { +// m_log.DebugFormat( +// "[SCENE PRESENCE]: Testing border check for projected position {0} of {1} in {2}", +// pos2, Name, Scene.Name); + // Checks if where it's headed exists a region bool needsTransit = false; if (m_scene.TestBorderCross(pos2, Cardinals.W)) diff --git a/OpenSim/Region/OptionalModules/World/SceneCommands/SceneCommandsModule.cs b/OpenSim/Region/OptionalModules/World/SceneCommands/SceneCommandsModule.cs index 5fb74b01ea..29b39e031a 100644 --- a/OpenSim/Region/OptionalModules/World/SceneCommands/SceneCommandsModule.cs +++ b/OpenSim/Region/OptionalModules/World/SceneCommands/SceneCommandsModule.cs @@ -116,6 +116,37 @@ namespace OpenSim.Region.OptionalModules.Avatar.Attachments + "If teleport is true then some extra teleport debug information is logged.\n" + "If updates is true then any frame which exceeds double the maximum desired frame time is logged.", HandleDebugSceneSetCommand); + + scene.AddCommand( + "Regions", + this, "show borders", "show borders", "Show border information for regions", HandleShowBordersCommand); + } + + private void HandleShowBordersCommand(string module, string[] args) + { + StringBuilder sb = new StringBuilder(); + sb.AppendFormat("Borders for {0}:\n", m_scene.Name); + + ConsoleDisplayTable cdt = new ConsoleDisplayTable(); + cdt.AddColumn("Cross Direction", 15); + cdt.AddColumn("Line", 34); + cdt.AddColumn("Trigger Region", 14); + + foreach (Border b in m_scene.NorthBorders) + cdt.AddRow(b.CrossDirection, b.BorderLine, string.Format("{0}, {1}", b.TriggerRegionX, b.TriggerRegionY)); + + foreach (Border b in m_scene.EastBorders) + cdt.AddRow(b.CrossDirection, b.BorderLine, string.Format("{0}, {1}", b.TriggerRegionX, b.TriggerRegionY)); + + foreach (Border b in m_scene.SouthBorders) + cdt.AddRow(b.CrossDirection, b.BorderLine, string.Format("{0}, {1}", b.TriggerRegionX, b.TriggerRegionY)); + + foreach (Border b in m_scene.WestBorders) + cdt.AddRow(b.CrossDirection, b.BorderLine, string.Format("{0}, {1}", b.TriggerRegionX, b.TriggerRegionY)); + + cdt.AddToStringBuilder(sb); + + MainConsole.Instance.Output(sb.ToString()); } private void HandleDebugSceneGetCommand(string module, string[] args) diff --git a/OpenSim/Region/RegionCombinerModule/RegionCombinerModule.cs b/OpenSim/Region/RegionCombinerModule/RegionCombinerModule.cs index 905540d36e..7127c73c18 100644 --- a/OpenSim/Region/RegionCombinerModule/RegionCombinerModule.cs +++ b/OpenSim/Region/RegionCombinerModule/RegionCombinerModule.cs @@ -415,18 +415,17 @@ namespace OpenSim.Region.RegionCombinerModule */ #endregion - // If we're one region over +x y + // If we're one region over +x y (i.e. root region is to the west) //xxx //xxy //xxx - if (rootConn.PosX + rootConn.XEnd >= newConn.PosX && rootConn.PosY >= newConn.PosY) { connectedYN = DoWorkForOneRegionOverPlusXY(rootConn, newConn, scene); break; } - // If we're one region over x +y + // If we're one region over x +y (i.e. root region is to the south) //xyx //xxx //xxx @@ -436,7 +435,7 @@ namespace OpenSim.Region.RegionCombinerModule break; } - // If we're one region over +x +y + // If we're one region over +x +y (i.e. root region is to the south-west) //xxy //xxx //xxx @@ -646,7 +645,6 @@ namespace OpenSim.Region.RegionCombinerModule { if (rootConn.RegionScene.EastBorders.Count == 1)// && conn.RegionScene.EastBorders.Count == 2) { - rootConn.RegionScene.EastBorders[0].BorderLine.Z += (int)Constants.RegionSize; lock (rootConn.RegionScene.NorthBorders) From 01636ca90015561366130a3db9b19e4eb976b80a Mon Sep 17 00:00:00 2001 From: "Justin Clark-Casey (justincc)" Date: Sat, 23 Mar 2013 00:47:59 +0000 Subject: [PATCH 02/40] Fix teleporting into the non-SW 256x256 corner of a megaregion, though currently with a 10 second delay before auto-reteleport to the correct location. This now does a check for border crossing (required to trigger the teleport) immediately in SP.MakeRootAgent(). If left any later, it looks like the physics scene changes the position and stops the cross happening. If done any earlier, nothing happens because the cross-code currently requires a PhysicsActor to be in place, thuogh it's probably not necessary for this case. --- OpenSim/Region/Framework/Scenes/ScenePresence.cs | 7 +++++++ 1 file changed, 7 insertions(+) diff --git a/OpenSim/Region/Framework/Scenes/ScenePresence.cs b/OpenSim/Region/Framework/Scenes/ScenePresence.cs index f7ae3a219f..f3b923f338 100644 --- a/OpenSim/Region/Framework/Scenes/ScenePresence.cs +++ b/OpenSim/Region/Framework/Scenes/ScenePresence.cs @@ -925,6 +925,13 @@ namespace OpenSim.Region.Framework.Scenes AddToPhysicalScene(isFlying); + // XXX: This is to trigger any secondary teleport needed for a megaregion when the user has teleported to a + // location outside the 'root region' (the south-west 256x256 corner). This is the earlist we can do it + // since it requires a physics actor to be present. If it is left any later, then physics appears to reset + // the value to a negative position which does not trigger the border cross. + // This may not be the best location for this. + CheckForBorderCrossing(); + if (ForceFly) { Flying = true; From 128c72a23437423d87cc9b10815f96d7362bddd1 Mon Sep 17 00:00:00 2001 From: "Justin Clark-Casey (justincc)" Date: Mon, 25 Mar 2013 21:24:21 +0000 Subject: [PATCH 03/40] Start recording inter-region teleport attempts, aborts, cancels and failures in statistics for monitoring/debugging purposes These are recorded as 'entitytransfer' stats as seen by the "show stats entitytransfer" console command. --- .../EntityTransfer/EntityTransferModule.cs | 119 ++++++++++++++++-- 1 file changed, 109 insertions(+), 10 deletions(-) diff --git a/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferModule.cs b/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferModule.cs index 136caad36b..4cf7645376 100644 --- a/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferModule.cs +++ b/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferModule.cs @@ -33,6 +33,7 @@ using System.Threading; using OpenSim.Framework; using OpenSim.Framework.Capabilities; using OpenSim.Framework.Client; +using OpenSim.Framework.Monitoring; using OpenSim.Region.Framework.Interfaces; using OpenSim.Region.Framework.Scenes; using OpenSim.Region.Physics.Manager; @@ -77,6 +78,31 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer /// public bool DisableInterRegionTeleportCancellation { get; set; } + /// + /// Number of times inter-region teleport was attempted. + /// + private Stat m_interRegionTeleportAttempts; + + /// + /// Number of times inter-region teleport was aborted (due to simultaneous client logout). + /// + private Stat m_interRegionTeleportAborts; + + /// + /// Number of times inter-region teleport was successfully cancelled by the client. + /// + private Stat m_interRegionTeleportCancels; + + /// + /// Number of times inter-region teleport failed due to server/client/network problems (e.g. viewer failed to + /// connect with destination region). + /// + /// + /// This is not necessarily a problem for this simulator - in open-grid/hg conditions, viewer connectivity to + /// destination simulator is unknown. + /// + private Stat m_interRegionTeleportFailures; + protected bool m_Enabled = false; public Scene Scene { get; private set; } @@ -156,6 +182,60 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer Scene = scene; + m_interRegionTeleportAttempts = + new Stat( + "InterRegionTeleportAttempts", + "Number of inter-region teleports attempted.", + "This does not count attempts which failed due to pre-conditions (e.g. target simulator refused access).\n" + + "You can get successfully teleports by subtracting aborts, cancels and teleport failures from this figure.", + "", + "entitytransfer", + Scene.Name, + StatType.Push, + null, + StatVerbosity.Debug); + + m_interRegionTeleportAborts = + new Stat( + "InterRegionTeleportAborts", + "Number of inter-region teleports aborted due to client actions.", + "The chief action is simultaneous logout whilst teleporting.", + "", + "entitytransfer", + Scene.Name, + StatType.Push, + null, + StatVerbosity.Debug); + + m_interRegionTeleportCancels = + new Stat( + "InterRegionTeleportCancels", + "Number of inter-region teleports cancelled by the client.", + null, + "", + "entitytransfer", + Scene.Name, + StatType.Push, + null, + StatVerbosity.Debug); + + m_interRegionTeleportFailures = + new Stat( + "InterRegionTeleportFailures", + "Number of inter-region teleports that failed due to server/client/network issues.", + "This number may not be very helpful in open-grid/hg situations as the network connectivity/quality of destinations is uncontrollable.", + "", + "entitytransfer", + Scene.Name, + StatType.Push, + null, + StatVerbosity.Debug); + + StatsManager.RegisterStat(m_interRegionTeleportAttempts); + StatsManager.RegisterStat(m_interRegionTeleportAborts); + StatsManager.RegisterStat(m_interRegionTeleportCancels); + StatsManager.RegisterStat(m_interRegionTeleportFailures); + scene.RegisterModuleInterface(this); scene.EventManager.OnNewClient += OnNewClient; } @@ -173,7 +253,13 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer public virtual void Close() {} - public virtual void RemoveRegion(Scene scene) {} + public virtual void RemoveRegion(Scene scene) + { + StatsManager.DeregisterStat(m_interRegionTeleportAttempts); + StatsManager.DeregisterStat(m_interRegionTeleportAborts); + StatsManager.DeregisterStat(m_interRegionTeleportCancels); + StatsManager.DeregisterStat(m_interRegionTeleportFailures); + } public virtual void RegionLoaded(Scene scene) { @@ -545,6 +631,11 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer return; } + // Before this point, teleport 'failure' is due to checkable pre-conditions such as whether the target + // simulator can be found and is explicitly prepared to allow access. Therefore, we will not count these + // as server attempts. + m_interRegionTeleportAttempts.Value++; + m_log.DebugFormat("[ENTITY TRANSFER MODULE]: Destination is running version {0}", version); // Fixing a bug where teleporting while sitting results in the avatar ending up removed from @@ -595,6 +686,8 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer bool logout = false; if (!CreateAgent(sp, reg, finalDestination, agentCircuit, teleportFlags, out reason, out logout)) { + m_interRegionTeleportFailures.Value++; + sp.ControllingClient.SendTeleportFailed(String.Format("Teleport refused: {0}", reason)); m_log.DebugFormat( @@ -606,6 +699,8 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer if (m_entityTransferStateMachine.GetAgentTransferState(sp.UUID) == AgentTransferState.Cancelling) { + m_interRegionTeleportCancels.Value++; + m_log.DebugFormat( "[ENTITY TRANSFER MODULE]: Cancelled teleport of {0} to {1} from {2} after CreateAgent on client request", sp.Name, finalDestination.RegionName, sp.Scene.Name); @@ -614,6 +709,8 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer } else if (m_entityTransferStateMachine.GetAgentTransferState(sp.UUID) == AgentTransferState.Aborting) { + m_interRegionTeleportAborts.Value++; + m_log.DebugFormat( "[ENTITY TRANSFER MODULE]: Aborted teleport of {0} to {1} from {2} after CreateAgent due to previous client close.", sp.Name, finalDestination.RegionName, sp.Scene.Name); @@ -683,6 +780,8 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer // establish th econnection to the destination which makes it return true. if (m_entityTransferStateMachine.GetAgentTransferState(sp.UUID) == AgentTransferState.Aborting) { + m_interRegionTeleportAborts.Value++; + m_log.DebugFormat( "[ENTITY TRANSFER MODULE]: Aborted teleport of {0} to {1} from {2} before UpdateAgent", sp.Name, finalDestination.RegionName, sp.Scene.Name); @@ -698,6 +797,8 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer { if (m_entityTransferStateMachine.GetAgentTransferState(sp.UUID) == AgentTransferState.Aborting) { + m_interRegionTeleportAborts.Value++; + m_log.DebugFormat( "[ENTITY TRANSFER MODULE]: Aborted teleport of {0} to {1} from {2} after UpdateAgent due to previous client close.", sp.Name, finalDestination.RegionName, sp.Scene.Name); @@ -715,6 +816,8 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer if (m_entityTransferStateMachine.GetAgentTransferState(sp.UUID) == AgentTransferState.Cancelling) { + m_interRegionTeleportCancels.Value++; + m_log.DebugFormat( "[ENTITY TRANSFER MODULE]: Cancelled teleport of {0} to {1} from {2} after UpdateAgent on client request", sp.Name, finalDestination.RegionName, sp.Scene.Name); @@ -750,6 +853,8 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer { if (m_entityTransferStateMachine.GetAgentTransferState(sp.UUID) == AgentTransferState.Aborting) { + m_interRegionTeleportAborts.Value++; + m_log.DebugFormat( "[ENTITY TRANSFER MODULE]: Aborted teleport of {0} to {1} from {2} after WaitForAgentArrivedAtDestination due to previous client close.", sp.Name, finalDestination.RegionName, sp.Scene.Name); @@ -762,6 +867,7 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer sp.Name, finalDestination.RegionName, sp.Scene.RegionInfo.RegionName); Fail(sp, finalDestination, logout, "Destination region did not signal teleport completion."); + return; } @@ -803,15 +909,6 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer // now we have a child agent in this region. sp.Reset(); } - - // Commented pending deletion since this method no longer appears to do anything at all -// // REFACTORING PROBLEM. Well, not a problem, but this method is HORRIBLE! -// if (sp.Scene.NeedSceneCacheClear(sp.UUID)) -// { -// m_log.DebugFormat( -// "[ENTITY TRANSFER MODULE]: User {0} is going to another region, profile cache removed", -// sp.UUID); -// } } /// @@ -847,6 +944,8 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer { CleanupFailedInterRegionTeleport(sp, finalDestination); + m_interRegionTeleportFailures.Value++; + sp.ControllingClient.SendTeleportFailed( string.Format( "Problems connecting to destination {0}, reason: {1}", finalDestination.RegionName, reason)); From f783b9169fbc0544ec6c634900cb34bf48c6b2a9 Mon Sep 17 00:00:00 2001 From: Robert Adams Date: Fri, 22 Mar 2013 16:50:56 -0700 Subject: [PATCH 04/40] BulletSim: parameterize C# HACD hull creation. Add feature of reducing max hull count for simple (non-cut prims) meshes. --- .../Region/Physics/BulletSPlugin/BSParam.cs | 33 +++++++++++ .../BulletSPlugin/BSShapeCollection.cs | 55 ++++++++++++++----- 2 files changed, 74 insertions(+), 14 deletions(-) diff --git a/OpenSim/Region/Physics/BulletSPlugin/BSParam.cs b/OpenSim/Region/Physics/BulletSPlugin/BSParam.cs index 4d89a88778..26d2d60e9f 100755 --- a/OpenSim/Region/Physics/BulletSPlugin/BSParam.cs +++ b/OpenSim/Region/Physics/BulletSPlugin/BSParam.cs @@ -142,6 +142,14 @@ public static class BSParam public static float VehicleAngularBankingTimescaleFudge { get; private set; } public static bool VehicleDebuggingEnabled { get; private set; } + // Convex Hulls + public static int CSHullMaxDepthSplit { get; private set; } + public static int CSHullMaxDepthSplitForSimpleShapes { get; private set; } + public static float CSHullConcavityThresholdPercent { get; private set; } + public static float CSHullVolumeConservationThresholdPercent { get; private set; } + public static int CSHullMaxVertices { get; private set; } + public static float CSHullMaxSkinWidth { get; private set; } + // Linkset implementation parameters public static float LinksetImplementation { get; private set; } public static bool LinkConstraintUseFrameOffset { get; private set; } @@ -623,6 +631,31 @@ public static class BSParam (s) => { return GlobalContactBreakingThreshold; }, (s,v) => { GlobalContactBreakingThreshold = v; s.UnmanagedParams[0].globalContactBreakingThreshold = v; } ), + new ParameterDefn("CSHullMaxDepthSplit", "CS impl: max depth to split for hull. 1-10 but > 7 is iffy", + 7, + (s) => { return CSHullMaxDepthSplit; }, + (s,v) => { CSHullMaxDepthSplit = v; } ), + new ParameterDefn("CSHullMaxDepthSplitForSimpleShapes", "CS impl: max depth setting for simple prim shapes", + 2, + (s) => { return CSHullMaxDepthSplitForSimpleShapes; }, + (s,v) => { CSHullMaxDepthSplitForSimpleShapes = v; } ), + new ParameterDefn("CSHullConcavityThresholdPercent", "CS impl: concavity threshold percent (0-20)", + 5f, + (s) => { return CSHullConcavityThresholdPercent; }, + (s,v) => { CSHullConcavityThresholdPercent = v; } ), + new ParameterDefn("CSHullVolumeConservationThresholdPercent", "percent volume conservation to collapse hulls (0-30)", + 5f, + (s) => { return CSHullVolumeConservationThresholdPercent; }, + (s,v) => { CSHullVolumeConservationThresholdPercent = v; } ), + new ParameterDefn("CSHullMaxVertices", "CS impl: maximum number of vertices in output hulls. Keep < 50.", + 32, + (s) => { return CSHullMaxVertices; }, + (s,v) => { CSHullMaxVertices = v; } ), + new ParameterDefn("CSHullMaxSkinWidth", "CS impl: skin width to apply to output hulls.", + 0, + (s) => { return CSHullMaxSkinWidth; }, + (s,v) => { CSHullMaxSkinWidth = v; } ), + new ParameterDefn("LinksetImplementation", "Type of linkset implementation (0=Constraint, 1=Compound, 2=Manual)", (float)BSLinkset.LinksetImplementation.Compound, (s) => { return LinksetImplementation; }, diff --git a/OpenSim/Region/Physics/BulletSPlugin/BSShapeCollection.cs b/OpenSim/Region/Physics/BulletSPlugin/BSShapeCollection.cs index b16bc10b9c..457f204a8e 100755 --- a/OpenSim/Region/Physics/BulletSPlugin/BSShapeCollection.cs +++ b/OpenSim/Region/Physics/BulletSPlugin/BSShapeCollection.cs @@ -447,17 +447,10 @@ public sealed class BSShapeCollection : IDisposable // If the prim attributes are simple, this could be a simple Bullet native shape if (!haveShape + && nativeShapePossible && pbs != null && !pbs.SculptEntry - && nativeShapePossible - && ((pbs.SculptEntry && !BSParam.ShouldMeshSculptedPrim) - || (pbs.ProfileBegin == 0 && pbs.ProfileEnd == 0 - && pbs.ProfileHollow == 0 - && pbs.PathTwist == 0 && pbs.PathTwistBegin == 0 - && pbs.PathBegin == 0 && pbs.PathEnd == 0 - && pbs.PathTaperX == 0 && pbs.PathTaperY == 0 - && pbs.PathScaleX == 100 && pbs.PathScaleY == 100 - && pbs.PathShearX == 0 && pbs.PathShearY == 0) ) ) + && ((pbs.SculptEntry && !BSParam.ShouldMeshSculptedPrim) || PrimHasNoCuts(pbs)) ) { // Get the scale of any existing shape so we can see if the new shape is same native type and same size. OMV.Vector3 scaleOfExistingShape = OMV.Vector3.Zero; @@ -508,6 +501,18 @@ public sealed class BSShapeCollection : IDisposable return ret; } + // return 'true' if this shape description does not include any cutting or twisting. + private bool PrimHasNoCuts(PrimitiveBaseShape pbs) + { + return pbs.ProfileBegin == 0 && pbs.ProfileEnd == 0 + && pbs.ProfileHollow == 0 + && pbs.PathTwist == 0 && pbs.PathTwistBegin == 0 + && pbs.PathBegin == 0 && pbs.PathEnd == 0 + && pbs.PathTaperX == 0 && pbs.PathTaperY == 0 + && pbs.PathScaleX == 100 && pbs.PathScaleY == 100 + && pbs.PathShearX == 0 && pbs.PathShearY == 0; + } + // return 'true' if the prim's shape was changed. public bool CreateGeomMeshOrHull(BSPhysObject prim, ShapeDestructionCallback shapeCallback) { @@ -518,7 +523,7 @@ public sealed class BSShapeCollection : IDisposable if (prim.IsPhysical && BSParam.ShouldUseHullsForPhysicalObjects) { // Update prim.BSShape to reference a hull of this shape. - ret = GetReferenceToHull(prim,shapeCallback); + ret = GetReferenceToHull(prim, shapeCallback); if (DDetail) DetailLog("{0},BSShapeCollection.CreateGeom,hull,shape={1},key={2}", prim.LocalID, prim.PhysShape, prim.PhysShape.shapeKey.ToString("X")); } @@ -697,6 +702,7 @@ public sealed class BSShapeCollection : IDisposable // See that hull shape exists in the physical world and update prim.BSShape. // We could be creating the hull because scale changed or whatever. + // Return 'true' if a new hull was built. Otherwise, returning a shared hull instance. private bool GetReferenceToHull(BSPhysObject prim, ShapeDestructionCallback shapeCallback) { BulletShape newShape; @@ -715,6 +721,7 @@ public sealed class BSShapeCollection : IDisposable DereferenceShape(prim.PhysShape, shapeCallback); newShape = CreatePhysicalHull(prim.PhysObjectName, newHullKey, prim.BaseShape, prim.Size, lod); + // It might not have been created if we're waiting for an asset. newShape = VerifyMeshCreated(newShape, prim); ReferenceShape(newShape); @@ -733,14 +740,14 @@ public sealed class BSShapeCollection : IDisposable HullDesc hullDesc; if (Hulls.TryGetValue(newHullKey, out hullDesc)) { - // If the hull shape already is created, just use it. + // If the hull shape already has been created, just use the one shared instance. newShape = hullDesc.shape.Clone(); } else { - // Build a new hull in the physical world - // Pass true for physicalness as this creates some sort of bounding box which we don't need - IMesh meshData = PhysicsScene.mesher.CreateMesh(objName, pbs, size, lod, true, false); + // Build a new hull in the physical world. + // Pass true for physicalness as this prevents the creation of bounding box which is not needed + IMesh meshData = PhysicsScene.mesher.CreateMesh(objName, pbs, size, lod, true /* isPhysical */, false /* shouldCache */); if (meshData != null) { @@ -759,15 +766,35 @@ public sealed class BSShapeCollection : IDisposable convVertices.Add(new float3(vv.X, vv.Y, vv.Z)); } + uint maxDepthSplit = (uint)BSParam.CSHullMaxDepthSplit; + if (BSParam.CSHullMaxDepthSplit != BSParam.CSHullMaxDepthSplitForSimpleShapes) + { + // Simple primitive shapes we know are convex so they are better implemented with + // fewer hulls. + // Check for simple shape (prim without cuts) and reduce split parameter if so. + if (PrimHasNoCuts(pbs)) + { + maxDepthSplit = (uint)BSParam.CSHullMaxDepthSplitForSimpleShapes; + } + } + // setup and do convex hull conversion m_hulls = new List(); DecompDesc dcomp = new DecompDesc(); dcomp.mIndices = convIndices; dcomp.mVertices = convVertices; + dcomp.mDepth = maxDepthSplit; + dcomp.mCpercent = BSParam.CSHullConcavityThresholdPercent; + dcomp.mPpercent = BSParam.CSHullVolumeConservationThresholdPercent; + dcomp.mMaxVertices = (uint)BSParam.CSHullMaxVertices; + dcomp.mSkinWidth = BSParam.CSHullMaxSkinWidth; ConvexBuilder convexBuilder = new ConvexBuilder(HullReturn); // create the hull into the _hulls variable convexBuilder.process(dcomp); + DetailLog("{0},BSShapeCollection.CreatePhysicalHull,key={1},inVert={2},inInd={3},split={4},hulls={5}", + BSScene.DetailLogZero, newHullKey, indices.GetLength(0), vertices.Count, maxDepthSplit, m_hulls.Count); + // Convert the vertices and indices for passing to unmanaged. // The hull information is passed as a large floating point array. // The format is: From 953090fd62c2f8647d0e04bc3890a04a7076dbad Mon Sep 17 00:00:00 2001 From: Robert Adams Date: Sat, 23 Mar 2013 11:00:52 -0700 Subject: [PATCH 05/40] BulletSim: fix possible race condition where an prim's asset can be requested quicker than the asset fetcher returns and thus falsely reporting that an asset was not fetched and defaulting the assset to a bounding box. --- .../Physics/BulletSPlugin/BSPhysObject.cs | 12 +++++++---- .../Region/Physics/BulletSPlugin/BSPrim.cs | 2 +- .../BulletSPlugin/BSShapeCollection.cs | 21 +++++++++++++------ 3 files changed, 24 insertions(+), 11 deletions(-) diff --git a/OpenSim/Region/Physics/BulletSPlugin/BSPhysObject.cs b/OpenSim/Region/Physics/BulletSPlugin/BSPhysObject.cs index f953c1e085..6bb88c77f3 100755 --- a/OpenSim/Region/Physics/BulletSPlugin/BSPhysObject.cs +++ b/OpenSim/Region/Physics/BulletSPlugin/BSPhysObject.cs @@ -86,7 +86,7 @@ public abstract class BSPhysObject : PhysicsActor PhysBody = new BulletBody(localID); PhysShape = new BulletShape(); - LastAssetBuildFailed = false; + PrimAssetState = PrimAssetCondition.Unknown; // Default material type. Also sets Friction, Restitution and Density. SetMaterial((int)MaterialAttributes.Material.Wood); @@ -133,9 +133,13 @@ public abstract class BSPhysObject : PhysicsActor // Reference to the physical shape (btCollisionShape) of this object public BulletShape PhysShape; - // 'true' if the mesh's underlying asset failed to build. - // This will keep us from looping after the first time the build failed. - public bool LastAssetBuildFailed { get; set; } + // The physical representation of the prim might require an asset fetch. + // The asset state is first 'Unknown' then 'Waiting' then either 'Failed' or 'Fetched'. + public enum PrimAssetCondition + { + Unknown, Waiting, Failed, Fetched + } + public PrimAssetCondition PrimAssetState { get; set; } // The objects base shape information. Null if not a prim type shape. public PrimitiveBaseShape BaseShape { get; protected set; } diff --git a/OpenSim/Region/Physics/BulletSPlugin/BSPrim.cs b/OpenSim/Region/Physics/BulletSPlugin/BSPrim.cs index 2cbbe9a3fd..6a5461a4e8 100644 --- a/OpenSim/Region/Physics/BulletSPlugin/BSPrim.cs +++ b/OpenSim/Region/Physics/BulletSPlugin/BSPrim.cs @@ -155,7 +155,7 @@ public class BSPrim : BSPhysObject public override PrimitiveBaseShape Shape { set { BaseShape = value; - LastAssetBuildFailed = false; + PrimAssetState = PrimAssetCondition.Unknown; ForceBodyShapeRebuild(false); } } diff --git a/OpenSim/Region/Physics/BulletSPlugin/BSShapeCollection.cs b/OpenSim/Region/Physics/BulletSPlugin/BSShapeCollection.cs index 457f204a8e..a6e20a8230 100755 --- a/OpenSim/Region/Physics/BulletSPlugin/BSShapeCollection.cs +++ b/OpenSim/Region/Physics/BulletSPlugin/BSShapeCollection.cs @@ -930,11 +930,15 @@ public sealed class BSShapeCollection : IDisposable return newShape; // If this mesh has an underlying asset and we have not failed getting it before, fetch the asset - if (prim.BaseShape.SculptEntry && !prim.LastAssetBuildFailed && prim.BaseShape.SculptTexture != OMV.UUID.Zero) + if (prim.BaseShape.SculptEntry + && prim.PrimAssetState != BSPhysObject.PrimAssetCondition.Failed + && prim.PrimAssetState != BSPhysObject.PrimAssetCondition.Waiting + && prim.BaseShape.SculptTexture != OMV.UUID.Zero + ) { - DetailLog("{0},BSShapeCollection.VerifyMeshCreated,fetchAsset,lastFailed={1}", prim.LocalID, prim.LastAssetBuildFailed); - // This will prevent looping through this code as we keep trying to get the failed shape - prim.LastAssetBuildFailed = true; + DetailLog("{0},BSShapeCollection.VerifyMeshCreated,fetchAsset", prim.LocalID); + // Multiple requestors will know we're waiting for this asset + prim.PrimAssetState = BSPhysObject.PrimAssetCondition.Waiting; BSPhysObject xprim = prim; Util.FireAndForget(delegate @@ -945,7 +949,7 @@ public sealed class BSShapeCollection : IDisposable BSPhysObject yprim = xprim; // probably not necessary, but, just in case. assetProvider(yprim.BaseShape.SculptTexture, delegate(AssetBase asset) { - bool assetFound = false; // DEBUG DEBUG + bool assetFound = false; string mismatchIDs = String.Empty; // DEBUG DEBUG if (asset != null && yprim.BaseShape.SculptEntry) { @@ -963,6 +967,10 @@ public sealed class BSShapeCollection : IDisposable mismatchIDs = yprim.BaseShape.SculptTexture.ToString() + "/" + asset.ID; } } + if (assetFound) + yprim.PrimAssetState = BSPhysObject.PrimAssetCondition.Fetched; + else + yprim.PrimAssetState = BSPhysObject.PrimAssetCondition.Failed; DetailLog("{0},BSShapeCollection,fetchAssetCallback,found={1},isSculpt={2},ids={3}", yprim.LocalID, assetFound, yprim.BaseShape.SculptEntry, mismatchIDs ); @@ -970,6 +978,7 @@ public sealed class BSShapeCollection : IDisposable } else { + xprim.PrimAssetState = BSPhysObject.PrimAssetCondition.Failed; PhysicsScene.Logger.ErrorFormat("{0} Physical object requires asset but no asset provider. Name={1}", LogHeader, PhysicsScene.Name); } @@ -977,7 +986,7 @@ public sealed class BSShapeCollection : IDisposable } else { - if (prim.LastAssetBuildFailed) + if (prim.PrimAssetState == BSPhysObject.PrimAssetCondition.Failed) { PhysicsScene.Logger.ErrorFormat("{0} Mesh failed to fetch asset. lID={1}, texture={2}", LogHeader, prim.LocalID, prim.BaseShape.SculptTexture); From c96a6f1de6d5e66dd2055365c26144d7a92f2fc5 Mon Sep 17 00:00:00 2001 From: Robert Adams Date: Sat, 23 Mar 2013 11:03:59 -0700 Subject: [PATCH 06/40] BulletSim: small tweaks and formatting in the parameter fetching code. --- .../Region/Physics/BulletSPlugin/BSParam.cs | 21 ++++++++++++++----- 1 file changed, 16 insertions(+), 5 deletions(-) diff --git a/OpenSim/Region/Physics/BulletSPlugin/BSParam.cs b/OpenSim/Region/Physics/BulletSPlugin/BSParam.cs index 26d2d60e9f..f3454c8daf 100755 --- a/OpenSim/Region/Physics/BulletSPlugin/BSParam.cs +++ b/OpenSim/Region/Physics/BulletSPlugin/BSParam.cs @@ -203,10 +203,10 @@ public static class BSParam public delegate void PSetOnObject(BSScene scene, BSPhysObject obj); public sealed class ParameterDefn : ParameterDefnBase { - T defaultValue; - PSetValue setter; - PGetValue getter; - PSetOnObject objectSet; + private T defaultValue; + private PSetValue setter; + private PGetValue getter; + private PSetOnObject objectSet; public ParameterDefn(string pName, string pDesc, T pDefault, PGetValue pGetter, PSetValue pSetter) : base(pName, pDesc) { @@ -223,13 +223,23 @@ public static class BSParam getter = pGetter; objectSet = pObjSetter; } + /* Wish I could simplify using this definition but CLR doesn't store references so closure around delegates of references won't work + public ParameterDefn(string pName, string pDesc, T pDefault, ref T loc) + : base(pName, pDesc) + { + defaultValue = pDefault; + setter = (s, v) => { loc = v; }; + getter = (s) => { return loc; }; + objectSet = null; + } + */ public override void AssignDefault(BSScene s) { setter(s, defaultValue); } public override string GetValue(BSScene s) { - return String.Format("{0}", getter(s)); + return getter(s).ToString(); } public override void SetValue(BSScene s, string valAsString) { @@ -252,6 +262,7 @@ public static class BSParam try { T setValue = (T)parser.Invoke(genericType, new Object[] { valAsString }); + // Store the parsed value setter(s, setValue); // s.Logger.DebugFormat("{0} Parameter {1} = {2}", LogHeader, name, setValue); } From 285dc554ece0b504cb549193096f84c9c0cfe89f Mon Sep 17 00:00:00 2001 From: Robert Adams Date: Mon, 25 Mar 2013 15:19:55 -0700 Subject: [PATCH 07/40] BulletSim: new algorithm for vertical attraction which uses quaternion arithmetic to compute the shortest path between the current tilt and vertical. --- .../Physics/BulletSPlugin/BSDynamics.cs | 48 +++++++++++++++++-- 1 file changed, 45 insertions(+), 3 deletions(-) diff --git a/OpenSim/Region/Physics/BulletSPlugin/BSDynamics.cs b/OpenSim/Region/Physics/BulletSPlugin/BSDynamics.cs index 5549984d65..65df741962 100644 --- a/OpenSim/Region/Physics/BulletSPlugin/BSDynamics.cs +++ b/OpenSim/Region/Physics/BulletSPlugin/BSDynamics.cs @@ -321,7 +321,7 @@ namespace OpenSim.Region.Physics.BulletSPlugin } } - internal void ProcessTypeChange(Vehicle pType) + public void ProcessTypeChange(Vehicle pType) { VDetailLog("{0},ProcessTypeChange,type={1}", Prim.LocalID, pType); // Set Defaults For Type @@ -1301,14 +1301,52 @@ namespace OpenSim.Region.Physics.BulletSPlugin // efficiency of 1.0 will cause the spring to reach its equilibrium with exponential decay. public void ComputeAngularVerticalAttraction() { + // If vertical attaction timescale is reasonable if (enableAngularVerticalAttraction && m_verticalAttractionTimescale < m_verticalAttractionCutoff) { + // Possible solution derived from a discussion at: + // http://stackoverflow.com/questions/14939657/computing-vector-from-quaternion-works-computing-quaternion-from-vector-does-no + + // Create a rotation that is only the vehicle's rotation around Z + Vector3 currentEuler = Vector3.Zero; + VehicleOrientation.GetEulerAngles(out currentEuler.X, out currentEuler.Y, out currentEuler.Z); + Quaternion justZOrientation = Quaternion.CreateFromAxisAngle(Vector3.UnitZ, currentEuler.Z); + + // Create the axis that is perpendicular to the up vector and the rotated up vector. + Vector3 differenceAxis = Vector3.Cross(Vector3.UnitZ * justZOrientation, Vector3.UnitZ * VehicleOrientation); + // Compute the angle between those to vectors. + double differenceAngle = Math.Acos((double)Vector3.Dot(Vector3.UnitZ, Vector3.Normalize(Vector3.UnitZ * VehicleOrientation))); + // 'differenceAngle' is the angle to rotate and 'differenceAxis' is the plane to rotate in to get the vehicle vertical + + // Reduce the change by the time period it is to change in. Timestep is handled when velocity is applied. + // TODO: add 'efficiency'. + differenceAngle /= m_verticalAttractionTimescale; + + // Create the quaterian representing the correction angle + Quaternion correctionRotation = Quaternion.CreateFromAxisAngle(differenceAxis, (float)differenceAngle); + + // Turn that quaternion into Euler values to make it into velocities to apply. + Vector3 vertContributionV = Vector3.Zero; + correctionRotation.GetEulerAngles(out vertContributionV.X, out vertContributionV.Y, out vertContributionV.Z); + vertContributionV *= -1f; + + VehicleRotationalVelocity += vertContributionV; + + VDetailLog("{0}, MoveAngular,verticalAttraction,diffAxis={1},diffAng={2},corrRot={3},contrib={4}", + Prim.LocalID, + differenceAxis, + differenceAngle, + correctionRotation, + vertContributionV); + + // =================================================================== + /* Vector3 vertContributionV = Vector3.Zero; Vector3 origRotVelW = VehicleRotationalVelocity; // DEBUG DEBUG // Take a vector pointing up and convert it from world to vehicle relative coords. - Vector3 verticalError = Vector3.UnitZ * VehicleOrientation; + Vector3 verticalError = Vector3.Normalize(Vector3.UnitZ * VehicleOrientation); // If vertical attraction correction is needed, the vector that was pointing up (UnitZ) // is now: @@ -1334,13 +1372,17 @@ namespace OpenSim.Region.Physics.BulletSPlugin // 'vertContrbution' is now the necessary angular correction to correct tilt in one second. // Correction happens over a number of seconds. Vector3 unscaledContribVerticalErrorV = vertContributionV; // DEBUG DEBUG + + // The correction happens over the user's time period vertContributionV /= m_verticalAttractionTimescale; - VehicleRotationalVelocity += vertContributionV; + // Rotate the vehicle rotation to the world coordinates. + VehicleRotationalVelocity += (vertContributionV * VehicleOrientation); VDetailLog("{0}, MoveAngular,verticalAttraction,,origRotVW={1},vertError={2},unscaledV={3},eff={4},ts={5},vertContribV={6}", Prim.LocalID, origRotVelW, verticalError, unscaledContribVerticalErrorV, m_verticalAttractionEfficiency, m_verticalAttractionTimescale, vertContributionV); + */ } } From 5f4c4df227025c6b6156ce8238b56553dca4b5ae Mon Sep 17 00:00:00 2001 From: Melanie Date: Tue, 26 Mar 2013 03:40:06 +0000 Subject: [PATCH 08/40] Phase 1 of implementing a transfer permission. Overwrite libOMV's PermissionMask with our own and add export permissions as well as a new definition for "All" as meaning "all conventional permissions" rather than "all possible permissions" --- .../RemoteController/RemoteAdminPlugin.cs | 1 + OpenSim/Framework/Util.cs | 15 +++++++++++++++ .../Linden/Caps/BunchOfCaps/BunchOfCaps.cs | 5 +++-- .../NewFileAgentInventoryVariablePriceModule.cs | 1 + .../Region/ClientStack/Linden/UDP/LLClientView.cs | 8 +++++--- .../Agent/AssetTransaction/AssetXferUploader.cs | 5 +++-- .../Avatar/AvatarFactory/AvatarFactoryModule.cs | 1 + .../Avatar/Friends/CallingCardModule.cs | 1 + .../InventoryAccess/InventoryAccessModule.cs | 9 ++++++--- .../Framework/Library/LibraryModule.cs | 1 + .../World/Archiver/ArchiveWriteRequest.cs | 1 + .../World/Objects/BuySell/BuySellModule.cs | 1 + .../World/Permissions/PermissionsModule.cs | 1 + .../Region/Framework/Scenes/Scene.Inventory.cs | 7 ++++--- OpenSim/Region/Framework/Scenes/Scene.cs | 1 + .../Scenes/SceneObjectGroup.Inventory.cs | 1 + .../Region/Framework/Scenes/SceneObjectGroup.cs | 1 + .../Region/Framework/Scenes/SceneObjectPart.cs | 1 + .../Framework/Scenes/SceneObjectPartInventory.cs | 1 + .../Avatar/Attachments/TempAttachmentsModule.cs | 1 + .../Scripting/JsonStore/JsonStoreScriptModule.cs | 3 ++- .../Shared/Api/Implementation/LSL_Api.cs | 1 + .../Shared/Api/Implementation/OSSL_Api.cs | 5 +++-- .../SimianGrid/SimianInventoryServiceConnector.cs | 3 +++ .../Services/InventoryService/LibraryService.cs | 1 + .../UserAccountService/UserAccountService.cs | 3 ++- OpenSim/Tools/pCampBot/Bot.cs | 5 +++-- 27 files changed, 65 insertions(+), 19 deletions(-) diff --git a/OpenSim/ApplicationPlugins/RemoteController/RemoteAdminPlugin.cs b/OpenSim/ApplicationPlugins/RemoteController/RemoteAdminPlugin.cs index a75d10d417..69834793c1 100644 --- a/OpenSim/ApplicationPlugins/RemoteController/RemoteAdminPlugin.cs +++ b/OpenSim/ApplicationPlugins/RemoteController/RemoteAdminPlugin.cs @@ -50,6 +50,7 @@ using OpenSim.Region.Framework.Scenes; using OpenSim.Services.Interfaces; using PresenceInfo = OpenSim.Services.Interfaces.PresenceInfo; using GridRegion = OpenSim.Services.Interfaces.GridRegion; +using PermissionMask = OpenSim.Framework.PermissionMask; namespace OpenSim.ApplicationPlugins.RemoteController { diff --git a/OpenSim/Framework/Util.cs b/OpenSim/Framework/Util.cs index 94a172c399..bde46731a1 100644 --- a/OpenSim/Framework/Util.cs +++ b/OpenSim/Framework/Util.cs @@ -54,6 +54,21 @@ using Amib.Threading; namespace OpenSim.Framework { + [Flags] + public enum PermissionMask : uint + { + None = 0, + Transfer = 1 << 13, + Modify = 1 << 14, + Copy = 1 << 15, + Export = 1 << 16, + Move = 1 << 19, + Damage = 1 << 20, + // All does not contain Export, which is special and must be + // explicitly given + All = (1 << 13) | (1 << 14) | (1 << 15) | (1 << 19) + } + /// /// The method used by Util.FireAndForget for asynchronously firing events /// diff --git a/OpenSim/Region/ClientStack/Linden/Caps/BunchOfCaps/BunchOfCaps.cs b/OpenSim/Region/ClientStack/Linden/Caps/BunchOfCaps/BunchOfCaps.cs index 20df8a6a2e..87524043c9 100644 --- a/OpenSim/Region/ClientStack/Linden/Caps/BunchOfCaps/BunchOfCaps.cs +++ b/OpenSim/Region/ClientStack/Linden/Caps/BunchOfCaps/BunchOfCaps.cs @@ -49,6 +49,7 @@ using OpenSim.Services.Interfaces; using Caps = OpenSim.Framework.Capabilities.Caps; using OSDArray = OpenMetaverse.StructuredData.OSDArray; using OSDMap = OpenMetaverse.StructuredData.OSDMap; +using PermissionMask = OpenSim.Framework.PermissionMask; namespace OpenSim.Region.ClientStack.Linden { @@ -705,9 +706,9 @@ namespace OpenSim.Region.ClientStack.Linden // If we set PermissionMask.All then when we rez the item the next permissions will replace the current // (owner) permissions. This becomes a problem if next permissions are changed. item.CurrentPermissions - = (uint)(PermissionMask.Move | PermissionMask.Copy | PermissionMask.Modify | PermissionMask.Transfer); + = (uint)(PermissionMask.Move | PermissionMask.Copy | PermissionMask.Modify | PermissionMask.Transfer | PermissionMask.Export); - item.BasePermissions = (uint)PermissionMask.All; + item.BasePermissions = (uint)PermissionMask.All | (uint)PermissionMask.Export; item.EveryOnePermissions = 0; item.NextPermissions = (uint)PermissionMask.All; item.CreationDate = Util.UnixTimeSinceEpoch(); diff --git a/OpenSim/Region/ClientStack/Linden/Caps/NewFileAgentInventoryVariablePriceModule.cs b/OpenSim/Region/ClientStack/Linden/Caps/NewFileAgentInventoryVariablePriceModule.cs index 5529550fe1..f69a0bb596 100644 --- a/OpenSim/Region/ClientStack/Linden/Caps/NewFileAgentInventoryVariablePriceModule.cs +++ b/OpenSim/Region/ClientStack/Linden/Caps/NewFileAgentInventoryVariablePriceModule.cs @@ -44,6 +44,7 @@ using OpenSim.Region.Framework.Scenes; using OpenSim.Services.Interfaces; using Caps = OpenSim.Framework.Capabilities.Caps; using OpenSim.Framework.Capabilities; +using PermissionMask = OpenSim.Framework.PermissionMask; namespace OpenSim.Region.ClientStack.Linden { diff --git a/OpenSim/Region/ClientStack/Linden/UDP/LLClientView.cs b/OpenSim/Region/ClientStack/Linden/UDP/LLClientView.cs index 7ea538c907..110e50e32c 100644 --- a/OpenSim/Region/ClientStack/Linden/UDP/LLClientView.cs +++ b/OpenSim/Region/ClientStack/Linden/UDP/LLClientView.cs @@ -51,6 +51,7 @@ using RegionFlags = OpenMetaverse.RegionFlags; using Nini.Config; using System.IO; +using PermissionMask = OpenSim.Framework.PermissionMask; namespace OpenSim.Region.ClientStack.LindenUDP { @@ -1808,7 +1809,8 @@ namespace OpenSim.Region.ClientStack.LindenUDP public void SendInventoryItemDetails(UUID ownerID, InventoryItemBase item) { - const uint FULL_MASK_PERMISSIONS = (uint)PermissionMask.All; + // Fudge this value. It's only needed to make the CRC anyway + const uint FULL_MASK_PERMISSIONS = (uint)0x7fffffff; FetchInventoryReplyPacket inventoryReply = (FetchInventoryReplyPacket)PacketPool.Instance.GetPacket(PacketType.FetchInventoryReply); // TODO: don't create new blocks if recycling an old packet @@ -2013,7 +2015,7 @@ namespace OpenSim.Region.ClientStack.LindenUDP protected void SendBulkUpdateInventoryItem(InventoryItemBase item) { - const uint FULL_MASK_PERMISSIONS = (uint)PermissionMask.All; + const uint FULL_MASK_PERMISSIONS = (uint)0x7ffffff; BulkUpdateInventoryPacket bulkUpdate = (BulkUpdateInventoryPacket)PacketPool.Instance.GetPacket(PacketType.BulkUpdateInventory); @@ -2067,7 +2069,7 @@ namespace OpenSim.Region.ClientStack.LindenUDP /// IClientAPI.SendInventoryItemCreateUpdate(InventoryItemBase) public void SendInventoryItemCreateUpdate(InventoryItemBase Item, uint callbackId) { - const uint FULL_MASK_PERMISSIONS = (uint)PermissionMask.All; + const uint FULL_MASK_PERMISSIONS = (uint)0x7fffffff; UpdateCreateInventoryItemPacket InventoryReply = (UpdateCreateInventoryItemPacket)PacketPool.Instance.GetPacket( diff --git a/OpenSim/Region/CoreModules/Agent/AssetTransaction/AssetXferUploader.cs b/OpenSim/Region/CoreModules/Agent/AssetTransaction/AssetXferUploader.cs index 11efe6df67..5e772e6e4a 100644 --- a/OpenSim/Region/CoreModules/Agent/AssetTransaction/AssetXferUploader.cs +++ b/OpenSim/Region/CoreModules/Agent/AssetTransaction/AssetXferUploader.cs @@ -33,6 +33,7 @@ using OpenMetaverse; using OpenSim.Framework; using OpenSim.Region.Framework.Scenes; using OpenSim.Services.Interfaces; +using PermissionMask = OpenSim.Framework.PermissionMask; namespace OpenSim.Region.CoreModules.Agent.AssetTransaction { @@ -406,8 +407,8 @@ namespace OpenSim.Region.CoreModules.Agent.AssetTransaction item.AssetType = type; item.InvType = invType; item.Folder = InventFolder; - item.BasePermissions = 0x7fffffff; - item.CurrentPermissions = 0x7fffffff; + item.BasePermissions = (uint)(PermissionMask.All | PermissionMask.Export); + item.CurrentPermissions = item.BasePermissions; item.GroupPermissions=0; item.EveryOnePermissions=0; item.NextPermissions = nextPerm; diff --git a/OpenSim/Region/CoreModules/Avatar/AvatarFactory/AvatarFactoryModule.cs b/OpenSim/Region/CoreModules/Avatar/AvatarFactory/AvatarFactoryModule.cs index ff5bf9f99c..c7ac7c4ef5 100644 --- a/OpenSim/Region/CoreModules/Avatar/AvatarFactory/AvatarFactoryModule.cs +++ b/OpenSim/Region/CoreModules/Avatar/AvatarFactory/AvatarFactoryModule.cs @@ -40,6 +40,7 @@ using OpenSim.Region.Framework.Scenes; using OpenSim.Services.Interfaces; using Mono.Addins; +using PermissionMask = OpenSim.Framework.PermissionMask; namespace OpenSim.Region.CoreModules.Avatar.AvatarFactory { diff --git a/OpenSim/Region/CoreModules/Avatar/Friends/CallingCardModule.cs b/OpenSim/Region/CoreModules/Avatar/Friends/CallingCardModule.cs index 5ec0ea94b4..b44a5c9514 100644 --- a/OpenSim/Region/CoreModules/Avatar/Friends/CallingCardModule.cs +++ b/OpenSim/Region/CoreModules/Avatar/Friends/CallingCardModule.cs @@ -36,6 +36,7 @@ using OpenSim.Region.Framework.Interfaces; using OpenSim.Region.Framework.Scenes; using OpenSim.Services.Interfaces; using Mono.Addins; +using PermissionMask = OpenSim.Framework.PermissionMask; namespace OpenSim.Region.CoreModules.Avatar.Friends { diff --git a/OpenSim/Region/CoreModules/Framework/InventoryAccess/InventoryAccessModule.cs b/OpenSim/Region/CoreModules/Framework/InventoryAccess/InventoryAccessModule.cs index 8b7c16e1ca..eaf4ce2740 100644 --- a/OpenSim/Region/CoreModules/Framework/InventoryAccess/InventoryAccessModule.cs +++ b/OpenSim/Region/CoreModules/Framework/InventoryAccess/InventoryAccessModule.cs @@ -47,6 +47,7 @@ using OpenMetaverse; using log4net; using Nini.Config; using Mono.Addins; +using PermissionMask = OpenSim.Framework.PermissionMask; namespace OpenSim.Region.CoreModules.Framework.InventoryAccess { @@ -377,7 +378,8 @@ namespace OpenSim.Region.CoreModules.Framework.InventoryAccess objectGroup.RootPart.NextOwnerMask &= ((uint)PermissionMask.Copy | (uint)PermissionMask.Transfer | - (uint)PermissionMask.Modify); + (uint)PermissionMask.Modify | + (uint)PermissionMask.Export); objectGroup.RootPart.NextOwnerMask |= (uint)PermissionMask.Move; @@ -485,7 +487,7 @@ namespace OpenSim.Region.CoreModules.Framework.InventoryAccess InventoryItemBase item, SceneObjectGroup so, List objsForEffectivePermissions, IClientAPI remoteClient) { - uint effectivePerms = (uint)(PermissionMask.Copy | PermissionMask.Transfer | PermissionMask.Modify | PermissionMask.Move) | 7; + uint effectivePerms = (uint)(PermissionMask.Copy | PermissionMask.Transfer | PermissionMask.Modify | PermissionMask.Move | PermissionMask.Export) | 7; foreach (SceneObjectGroup grp in objsForEffectivePermissions) effectivePerms &= grp.GetEffectivePermissions(); effectivePerms |= (uint)PermissionMask.Move; @@ -525,6 +527,7 @@ namespace OpenSim.Region.CoreModules.Framework.InventoryAccess (uint)PermissionMask.Transfer | (uint)PermissionMask.Modify | (uint)PermissionMask.Move | + (uint)PermissionMask.Export | 7); // Preserve folded permissions } @@ -1150,4 +1153,4 @@ namespace OpenSim.Region.CoreModules.Framework.InventoryAccess #endregion } -} \ No newline at end of file +} diff --git a/OpenSim/Region/CoreModules/Framework/Library/LibraryModule.cs b/OpenSim/Region/CoreModules/Framework/Library/LibraryModule.cs index ec22146dbf..d07cff4d28 100644 --- a/OpenSim/Region/CoreModules/Framework/Library/LibraryModule.cs +++ b/OpenSim/Region/CoreModules/Framework/Library/LibraryModule.cs @@ -43,6 +43,7 @@ using OpenMetaverse; using log4net; using Mono.Addins; using Nini.Config; +using PermissionMask = OpenSim.Framework.PermissionMask; namespace OpenSim.Region.CoreModules.Framework.Library { diff --git a/OpenSim/Region/CoreModules/World/Archiver/ArchiveWriteRequest.cs b/OpenSim/Region/CoreModules/World/Archiver/ArchiveWriteRequest.cs index 367693d00d..a990898570 100644 --- a/OpenSim/Region/CoreModules/World/Archiver/ArchiveWriteRequest.cs +++ b/OpenSim/Region/CoreModules/World/Archiver/ArchiveWriteRequest.cs @@ -44,6 +44,7 @@ using Ionic.Zlib; using GZipStream = Ionic.Zlib.GZipStream; using CompressionMode = Ionic.Zlib.CompressionMode; using OpenSim.Framework.Serialization.External; +using PermissionMask = OpenSim.Framework.PermissionMask; namespace OpenSim.Region.CoreModules.World.Archiver { diff --git a/OpenSim/Region/CoreModules/World/Objects/BuySell/BuySellModule.cs b/OpenSim/Region/CoreModules/World/Objects/BuySell/BuySellModule.cs index 1e4f0a4e93..22a53a84f4 100644 --- a/OpenSim/Region/CoreModules/World/Objects/BuySell/BuySellModule.cs +++ b/OpenSim/Region/CoreModules/World/Objects/BuySell/BuySellModule.cs @@ -38,6 +38,7 @@ using OpenSim.Region.Framework; using OpenSim.Region.Framework.Interfaces; using OpenSim.Region.Framework.Scenes; using OpenSim.Region.Framework.Scenes.Serialization; +using PermissionMask = OpenSim.Framework.PermissionMask; namespace OpenSim.Region.CoreModules.World.Objects.BuySell { diff --git a/OpenSim/Region/CoreModules/World/Permissions/PermissionsModule.cs b/OpenSim/Region/CoreModules/World/Permissions/PermissionsModule.cs index 121fb2aaae..79dd4a09d2 100644 --- a/OpenSim/Region/CoreModules/World/Permissions/PermissionsModule.cs +++ b/OpenSim/Region/CoreModules/World/Permissions/PermissionsModule.cs @@ -38,6 +38,7 @@ using OpenSim.Region.Framework.Scenes; using OpenSim.Services.Interfaces; using Mono.Addins; +using PermissionMask = OpenSim.Framework.PermissionMask; namespace OpenSim.Region.CoreModules.World.Permissions { diff --git a/OpenSim/Region/Framework/Scenes/Scene.Inventory.cs b/OpenSim/Region/Framework/Scenes/Scene.Inventory.cs index 6808017624..2ce778db8f 100644 --- a/OpenSim/Region/Framework/Scenes/Scene.Inventory.cs +++ b/OpenSim/Region/Framework/Scenes/Scene.Inventory.cs @@ -39,6 +39,7 @@ using OpenSim.Region.Framework; using OpenSim.Framework.Client; using OpenSim.Region.Framework.Interfaces; using OpenSim.Region.Framework.Scenes.Serialization; +using PermissionMask = OpenSim.Framework.PermissionMask; namespace OpenSim.Region.Framework.Scenes { @@ -892,7 +893,7 @@ namespace OpenSim.Region.Framework.Scenes { CreateNewInventoryItem( remoteClient, creatorID, creatorData, folderID, name, description, flags, callbackID, asset, invType, - (uint)PermissionMask.All, (uint)PermissionMask.All, 0, nextOwnerMask, 0, creationDate); + (uint)PermissionMask.All | (uint)PermissionMask.Export, (uint)PermissionMask.All | (uint)PermissionMask.Export, 0, nextOwnerMask, 0, creationDate); } /// @@ -1010,8 +1011,8 @@ namespace OpenSim.Region.Framework.Scenes CreateNewInventoryItem( remoteClient, remoteClient.AgentId.ToString(), string.Empty, folderID, name, description, 0, callbackID, asset, invType, - (uint)PermissionMask.All, (uint)PermissionMask.All, (uint)PermissionMask.All, - (uint)PermissionMask.All, (uint)PermissionMask.All, Util.UnixTimeSinceEpoch()); + (uint)PermissionMask.All | (uint)PermissionMask.Export, (uint)PermissionMask.All | (uint)PermissionMask.Export, (uint)PermissionMask.All, + (uint)PermissionMask.All | (uint)PermissionMask.Export, (uint)PermissionMask.All | (uint)PermissionMask.Export, Util.UnixTimeSinceEpoch()); } else { diff --git a/OpenSim/Region/Framework/Scenes/Scene.cs b/OpenSim/Region/Framework/Scenes/Scene.cs index e8f00a4d90..45cbdd574d 100644 --- a/OpenSim/Region/Framework/Scenes/Scene.cs +++ b/OpenSim/Region/Framework/Scenes/Scene.cs @@ -51,6 +51,7 @@ using OpenSim.Region.Physics.Manager; using Timer=System.Timers.Timer; using TPFlags = OpenSim.Framework.Constants.TeleportFlags; using GridRegion = OpenSim.Services.Interfaces.GridRegion; +using PermissionMask = OpenSim.Framework.PermissionMask; namespace OpenSim.Region.Framework.Scenes { diff --git a/OpenSim/Region/Framework/Scenes/SceneObjectGroup.Inventory.cs b/OpenSim/Region/Framework/Scenes/SceneObjectGroup.Inventory.cs index ddf5da0ba4..dcb62f88e8 100644 --- a/OpenSim/Region/Framework/Scenes/SceneObjectGroup.Inventory.cs +++ b/OpenSim/Region/Framework/Scenes/SceneObjectGroup.Inventory.cs @@ -34,6 +34,7 @@ using OpenSim.Framework; using OpenSim.Region.Framework.Interfaces; using System.Collections.Generic; using System.Xml; +using PermissionMask = OpenSim.Framework.PermissionMask; namespace OpenSim.Region.Framework.Scenes { diff --git a/OpenSim/Region/Framework/Scenes/SceneObjectGroup.cs b/OpenSim/Region/Framework/Scenes/SceneObjectGroup.cs index 15795e5a64..0621e2a2f6 100644 --- a/OpenSim/Region/Framework/Scenes/SceneObjectGroup.cs +++ b/OpenSim/Region/Framework/Scenes/SceneObjectGroup.cs @@ -40,6 +40,7 @@ using OpenSim.Framework; using OpenSim.Region.Framework.Interfaces; using OpenSim.Region.Physics.Manager; using OpenSim.Region.Framework.Scenes.Serialization; +using PermissionMask = OpenSim.Framework.PermissionMask; namespace OpenSim.Region.Framework.Scenes { diff --git a/OpenSim/Region/Framework/Scenes/SceneObjectPart.cs b/OpenSim/Region/Framework/Scenes/SceneObjectPart.cs index a8b63fedeb..27325c554c 100644 --- a/OpenSim/Region/Framework/Scenes/SceneObjectPart.cs +++ b/OpenSim/Region/Framework/Scenes/SceneObjectPart.cs @@ -43,6 +43,7 @@ using OpenSim.Region.Framework.Interfaces; using OpenSim.Region.Framework.Scenes.Scripting; using OpenSim.Region.Framework.Scenes.Serialization; using OpenSim.Region.Physics.Manager; +using PermissionMask = OpenSim.Framework.PermissionMask; namespace OpenSim.Region.Framework.Scenes { diff --git a/OpenSim/Region/Framework/Scenes/SceneObjectPartInventory.cs b/OpenSim/Region/Framework/Scenes/SceneObjectPartInventory.cs index db723fa481..7dba7c8e62 100644 --- a/OpenSim/Region/Framework/Scenes/SceneObjectPartInventory.cs +++ b/OpenSim/Region/Framework/Scenes/SceneObjectPartInventory.cs @@ -38,6 +38,7 @@ using OpenSim.Framework; using OpenSim.Region.Framework.Interfaces; using OpenSim.Region.Framework.Scenes.Scripting; using OpenSim.Region.Framework.Scenes.Serialization; +using PermissionMask = OpenSim.Framework.PermissionMask; namespace OpenSim.Region.Framework.Scenes { diff --git a/OpenSim/Region/OptionalModules/Avatar/Attachments/TempAttachmentsModule.cs b/OpenSim/Region/OptionalModules/Avatar/Attachments/TempAttachmentsModule.cs index e9ddbbe958..54c86ae82d 100644 --- a/OpenSim/Region/OptionalModules/Avatar/Attachments/TempAttachmentsModule.cs +++ b/OpenSim/Region/OptionalModules/Avatar/Attachments/TempAttachmentsModule.cs @@ -40,6 +40,7 @@ using OpenSim.Framework.Monitoring; using OpenSim.Region.ClientStack.LindenUDP; using OpenSim.Region.Framework.Interfaces; using OpenSim.Region.Framework.Scenes; +using PermissionMask = OpenSim.Framework.PermissionMask; namespace OpenSim.Region.OptionalModules.Avatar.Attachments { diff --git a/OpenSim/Region/OptionalModules/Scripting/JsonStore/JsonStoreScriptModule.cs b/OpenSim/Region/OptionalModules/Scripting/JsonStore/JsonStoreScriptModule.cs index 4a754a915b..1bb5aee796 100644 --- a/OpenSim/Region/OptionalModules/Scripting/JsonStore/JsonStoreScriptModule.cs +++ b/OpenSim/Region/OptionalModules/Scripting/JsonStore/JsonStoreScriptModule.cs @@ -42,6 +42,7 @@ using OpenSim.Region.Framework.Scenes; using OpenSim.Region.Framework.Scenes.Scripting; using System.Collections.Generic; using System.Text.RegularExpressions; +using PermissionMask = OpenSim.Framework.PermissionMask; namespace OpenSim.Region.OptionalModules.Scripting.JsonStore { @@ -643,4 +644,4 @@ namespace OpenSim.Region.OptionalModules.Scripting.JsonStore } } -} \ No newline at end of file +} diff --git a/OpenSim/Region/ScriptEngine/Shared/Api/Implementation/LSL_Api.cs b/OpenSim/Region/ScriptEngine/Shared/Api/Implementation/LSL_Api.cs index e1f0071293..aab41f505b 100644 --- a/OpenSim/Region/ScriptEngine/Shared/Api/Implementation/LSL_Api.cs +++ b/OpenSim/Region/ScriptEngine/Shared/Api/Implementation/LSL_Api.cs @@ -67,6 +67,7 @@ using LSL_Rotation = OpenSim.Region.ScriptEngine.Shared.LSL_Types.Quaternion; using LSL_String = OpenSim.Region.ScriptEngine.Shared.LSL_Types.LSLString; using LSL_Vector = OpenSim.Region.ScriptEngine.Shared.LSL_Types.Vector3; using System.Reflection; +using PermissionMask = OpenSim.Framework.PermissionMask; namespace OpenSim.Region.ScriptEngine.Shared.Api { diff --git a/OpenSim/Region/ScriptEngine/Shared/Api/Implementation/OSSL_Api.cs b/OpenSim/Region/ScriptEngine/Shared/Api/Implementation/OSSL_Api.cs index bf1b45b3a6..415166a8c6 100644 --- a/OpenSim/Region/ScriptEngine/Shared/Api/Implementation/OSSL_Api.cs +++ b/OpenSim/Region/ScriptEngine/Shared/Api/Implementation/OSSL_Api.cs @@ -62,6 +62,7 @@ using LSL_List = OpenSim.Region.ScriptEngine.Shared.LSL_Types.list; using LSL_Rotation = OpenSim.Region.ScriptEngine.Shared.LSL_Types.Quaternion; using LSL_String = OpenSim.Region.ScriptEngine.Shared.LSL_Types.LSLString; using LSL_Vector = OpenSim.Region.ScriptEngine.Shared.LSL_Types.Vector3; +using PermissionMask = OpenSim.Framework.PermissionMask; namespace OpenSim.Region.ScriptEngine.Shared.Api { @@ -1787,8 +1788,8 @@ namespace OpenSim.Region.ScriptEngine.Shared.Api taskItem.InvType = (int)InventoryType.Notecard; taskItem.OwnerID = m_host.OwnerID; taskItem.CreatorID = m_host.OwnerID; - taskItem.BasePermissions = (uint)PermissionMask.All; - taskItem.CurrentPermissions = (uint)PermissionMask.All; + taskItem.BasePermissions = (uint)PermissionMask.All | (uint)PermissionMask.Export; + taskItem.CurrentPermissions = (uint)PermissionMask.All | (uint)PermissionMask.Export; taskItem.EveryonePermissions = 0; taskItem.NextPermissions = (uint)PermissionMask.All; taskItem.GroupID = m_host.GroupID; diff --git a/OpenSim/Services/Connectors/SimianGrid/SimianInventoryServiceConnector.cs b/OpenSim/Services/Connectors/SimianGrid/SimianInventoryServiceConnector.cs index a3912758aa..36325ce483 100644 --- a/OpenSim/Services/Connectors/SimianGrid/SimianInventoryServiceConnector.cs +++ b/OpenSim/Services/Connectors/SimianGrid/SimianInventoryServiceConnector.cs @@ -38,12 +38,14 @@ using OpenSim.Framework; using OpenSim.Region.Framework.Interfaces; using OpenSim.Region.Framework.Scenes; using OpenSim.Services.Interfaces; +using PermissionMask = OpenSim.Framework.PermissionMask; namespace OpenSim.Services.Connectors.SimianGrid { /// /// Permissions bitflags /// + /* [Flags] public enum PermissionMask : uint { @@ -55,6 +57,7 @@ namespace OpenSim.Services.Connectors.SimianGrid Damage = 1 << 20, All = 0x7FFFFFFF } + */ /// /// Connects avatar inventories to the SimianGrid backend diff --git a/OpenSim/Services/InventoryService/LibraryService.cs b/OpenSim/Services/InventoryService/LibraryService.cs index f90895b203..c4a557284a 100644 --- a/OpenSim/Services/InventoryService/LibraryService.cs +++ b/OpenSim/Services/InventoryService/LibraryService.cs @@ -38,6 +38,7 @@ using OpenSim.Services.Interfaces; using log4net; using Nini.Config; using OpenMetaverse; +using PermissionMask = OpenSim.Framework.PermissionMask; namespace OpenSim.Services.InventoryService { diff --git a/OpenSim/Services/UserAccountService/UserAccountService.cs b/OpenSim/Services/UserAccountService/UserAccountService.cs index 5b4d040f35..1852e4fe1f 100644 --- a/OpenSim/Services/UserAccountService/UserAccountService.cs +++ b/OpenSim/Services/UserAccountService/UserAccountService.cs @@ -36,6 +36,7 @@ using OpenSim.Framework; using OpenSim.Services.Interfaces; using OpenSim.Framework.Console; using GridRegion = OpenSim.Services.Interfaces.GridRegion; +using PermissionMask = OpenSim.Framework.PermissionMask; namespace OpenSim.Services.UserAccountService { @@ -665,4 +666,4 @@ namespace OpenSim.Services.UserAccountService } } } -} \ No newline at end of file +} diff --git a/OpenSim/Tools/pCampBot/Bot.cs b/OpenSim/Tools/pCampBot/Bot.cs index daaa3c0070..9821180bc6 100644 --- a/OpenSim/Tools/pCampBot/Bot.cs +++ b/OpenSim/Tools/pCampBot/Bot.cs @@ -40,6 +40,7 @@ using OpenSim.Framework; using OpenSim.Framework.Console; using pCampBot.Interfaces; using Timer = System.Timers.Timer; +using PermissionMask = OpenSim.Framework.PermissionMask; namespace pCampBot { @@ -362,7 +363,7 @@ namespace pCampBot asset.Encode(); transid = Client.Assets.RequestUpload(asset,true); Client.Inventory.RequestCreateItem(clothfolder.UUID, "MyClothing" + i.ToString(), "MyClothing", AssetType.Clothing, - transid, InventoryType.Wearable, asset.WearableType, PermissionMask.All, delegate(bool success, InventoryItem item) + transid, InventoryType.Wearable, asset.WearableType, (OpenMetaverse.PermissionMask)PermissionMask.All, delegate(bool success, InventoryItem item) { if (success) { @@ -386,7 +387,7 @@ namespace pCampBot asset.Encode(); transid = Client.Assets.RequestUpload(asset,true); Client.Inventory.RequestCreateItem(clothfolder.UUID, "MyBodyPart" + i.ToString(), "MyBodyPart", AssetType.Bodypart, - transid, InventoryType.Wearable, asset.WearableType, PermissionMask.All, delegate(bool success, InventoryItem item) + transid, InventoryType.Wearable, asset.WearableType, (OpenMetaverse.PermissionMask)PermissionMask.All, delegate(bool success, InventoryItem item) { if (success) { From e82fab34d7377a7d9bfc223f093ac67b393677cc Mon Sep 17 00:00:00 2001 From: Melanie Date: Tue, 26 Mar 2013 19:00:30 +0000 Subject: [PATCH 09/40] Implement a pref to turn on the simulator ExportSupported feature entry. This tells the viewer to enable the UI for export permissions. WARNING: If your inventory store contains invalid flags data, this will result in items becoming exportable! Don't turn this on in production until it's complete! --- .../ClientStack/Linden/Caps/SimulatorFeaturesModule.cs | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/OpenSim/Region/ClientStack/Linden/Caps/SimulatorFeaturesModule.cs b/OpenSim/Region/ClientStack/Linden/Caps/SimulatorFeaturesModule.cs index 6ef8815026..7d9f935d42 100644 --- a/OpenSim/Region/ClientStack/Linden/Caps/SimulatorFeaturesModule.cs +++ b/OpenSim/Region/ClientStack/Linden/Caps/SimulatorFeaturesModule.cs @@ -70,6 +70,7 @@ namespace OpenSim.Region.ClientStack.Linden private string m_MapImageServerURL = string.Empty; private string m_SearchURL = string.Empty; + private bool m_ExportSupported = false; #region ISharedRegionModule Members @@ -87,6 +88,8 @@ namespace OpenSim.Region.ClientStack.Linden } m_SearchURL = config.GetString("SearchServerURI", string.Empty); + + m_ExportSupported = config.GetBoolean("ExportSupported", m_ExportSupported); } AddDefaultFeatures(); @@ -152,6 +155,9 @@ namespace OpenSim.Region.ClientStack.Linden if (m_SearchURL != string.Empty) gridServicesMap["search"] = m_SearchURL; m_features["GridServices"] = gridServicesMap; + + if (m_ExportSupported) + m_features["ExportSupported"] = true; } } From 3f0f313a764213e928aeb57968efbdd0e4c851cd Mon Sep 17 00:00:00 2001 From: "Justin Clark-Casey (justincc)" Date: Tue, 26 Mar 2013 20:25:58 +0000 Subject: [PATCH 10/40] Make llGetLinkPrimitiveParams() and llGetPrimitiveParams() work for avatars in a linkset. llGetPrimitiveParams() works through PRIM_LINK_TARGET Setting via llSetLinkPrimitiveParams(), etc. not yet implemented --- .../Shared/Api/Implementation/LSL_Api.cs | 236 +++++++++++++++--- 1 file changed, 200 insertions(+), 36 deletions(-) diff --git a/OpenSim/Region/ScriptEngine/Shared/Api/Implementation/LSL_Api.cs b/OpenSim/Region/ScriptEngine/Shared/Api/Implementation/LSL_Api.cs index e1f0071293..bf3d8ab969 100644 --- a/OpenSim/Region/ScriptEngine/Shared/Api/Implementation/LSL_Api.cs +++ b/OpenSim/Region/ScriptEngine/Shared/Api/Implementation/LSL_Api.cs @@ -5923,8 +5923,9 @@ namespace OpenSim.Region.ScriptEngine.Shared.Api } else { - agentSize = new LSL_Vector(0.45, 0.6, avatar.Appearance.AvatarHeight); + agentSize = GetAgentSize(avatar); } + return agentSize; } @@ -7948,61 +7949,224 @@ namespace OpenSim.Region.ScriptEngine.Shared.Api return new LSL_Vector(m_host.GetGeometricCenter()); } + public LSL_List GetEntityParams(ISceneEntity entity, LSL_List rules) + { + LSL_List result = new LSL_List(); + LSL_List remaining = null; + + while (true) + { + if (entity is SceneObjectPart) + remaining = GetPrimParams((SceneObjectPart)entity, rules, ref result); + else + remaining = GetAgentParams((ScenePresence)entity, rules, ref result); + + if (remaining == null || remaining.Length <= 2) + return result; + + int linknumber = remaining.GetLSLIntegerItem(0); + rules = remaining.GetSublist(1, -1); + entity = GetLinkEntity(linknumber); + } + } + public LSL_List llGetPrimitiveParams(LSL_List rules) { m_host.AddScriptLPS(1); - LSL_List result = new LSL_List(); - - LSL_List remaining = GetPrimParams(m_host, rules, ref result); - - while (remaining != null && remaining.Length > 2) - { - int linknumber = remaining.GetLSLIntegerItem(0); - rules = remaining.GetSublist(1, -1); - List parts = GetLinkParts(linknumber); - - foreach (SceneObjectPart part in parts) - remaining = GetPrimParams(part, rules, ref result); - } - - return result; + return GetEntityParams(m_host, rules); } public LSL_List llGetLinkPrimitiveParams(int linknumber, LSL_List rules) { m_host.AddScriptLPS(1); - List parts = GetLinkParts(linknumber); + return GetEntityParams(GetLinkEntity(linknumber), rules); + } - LSL_List res = new LSL_List(); - LSL_List remaining = null; + public LSL_Vector GetAgentSize(ScenePresence sp) + { + return new LSL_Vector(0.45, 0.6, sp.Appearance.AvatarHeight); + } - foreach (SceneObjectPart part in parts) + /// + /// Gets params for a seated avatar in a linkset. + /// + /// + /// + /// + /// + public LSL_List GetAgentParams(ScenePresence sp, LSL_List rules, ref LSL_List res) + { + int idx = 0; + while (idx < rules.Length) { - remaining = GetPrimParams(part, rules, ref res); + int code = (int)rules.GetLSLIntegerItem(idx++); + int remain = rules.Length-idx; + + switch (code) + { + case (int)ScriptBaseClass.PRIM_MATERIAL: + res.Add(new LSL_Integer(ScriptBaseClass.PRIM_MATERIAL_FLESH)); + break; + + case (int)ScriptBaseClass.PRIM_PHYSICS: + res.Add(ScriptBaseClass.FALSE); + break; + + case (int)ScriptBaseClass.PRIM_TEMP_ON_REZ: + res.Add(ScriptBaseClass.FALSE); + break; + + case (int)ScriptBaseClass.PRIM_PHANTOM: + res.Add(ScriptBaseClass.FALSE); + break; + + case (int)ScriptBaseClass.PRIM_POSITION: + res.Add(new LSL_Vector(sp.AbsolutePosition)); + break; + + case (int)ScriptBaseClass.PRIM_SIZE: + res.Add(GetAgentSize(sp)); + break; + + case (int)ScriptBaseClass.PRIM_ROTATION: + res.Add(sp.GetWorldRotation()); + break; + + case (int)ScriptBaseClass.PRIM_TYPE: + res.Add(new LSL_Integer(ScriptBaseClass.PRIM_TYPE_BOX)); + res.Add(new LSL_Integer(ScriptBaseClass.PRIM_HOLE_DEFAULT)); + res.Add(new LSL_Vector(0, 1, 0)); + res.Add(new LSL_Float(0)); + res.Add(new LSL_Vector(0, 0, 0)); + res.Add(new LSL_Vector(1, 1, 0)); + res.Add(new LSL_Vector(0, 0, 0)); + break; + + case (int)ScriptBaseClass.PRIM_TEXTURE: + if (remain < 1) + return null; + + int face = (int)rules.GetLSLIntegerItem(idx++); + if (face > 21) + break; + + res.Add(new LSL_String("")); + res.Add(ScriptBaseClass.ZERO_VECTOR); + res.Add(ScriptBaseClass.ZERO_VECTOR); + res.Add(new LSL_Float(0)); + break; + + case (int)ScriptBaseClass.PRIM_COLOR: + if (remain < 1) + return null; + + face = (int)rules.GetLSLIntegerItem(idx++); + if (face > 21) + break; + + res.Add(ScriptBaseClass.ZERO_VECTOR); + res.Add(new LSL_Float(0)); + break; + + case (int)ScriptBaseClass.PRIM_BUMP_SHINY: + if (remain < 1) + return null; + + face = (int)rules.GetLSLIntegerItem(idx++); + if (face > 21) + break; + + res.Add(ScriptBaseClass.PRIM_SHINY_NONE); + res.Add(ScriptBaseClass.PRIM_BUMP_NONE); + break; + + case (int)ScriptBaseClass.PRIM_FULLBRIGHT: + if (remain < 1) + return null; + + face = (int)rules.GetLSLIntegerItem(idx++); + if (face > 21) + break; + + res.Add(ScriptBaseClass.FALSE); + break; + + case (int)ScriptBaseClass.PRIM_FLEXIBLE: + res.Add(ScriptBaseClass.FALSE); + res.Add(new LSL_Integer(0)); + res.Add(new LSL_Float(0)); + res.Add(new LSL_Float(0)); + res.Add(new LSL_Float(0)); + res.Add(new LSL_Float(0)); + res.Add(ScriptBaseClass.ZERO_VECTOR); + break; + + case (int)ScriptBaseClass.PRIM_TEXGEN: + if (remain < 1) + return null; + + face = (int)rules.GetLSLIntegerItem(idx++); + if (face > 21) + break; + + res.Add(ScriptBaseClass.PRIM_TEXGEN_DEFAULT); + break; + + case (int)ScriptBaseClass.PRIM_POINT_LIGHT: + res.Add(ScriptBaseClass.FALSE); + res.Add(ScriptBaseClass.ZERO_VECTOR); + res.Add(ScriptBaseClass.ZERO_VECTOR); + break; + + case (int)ScriptBaseClass.PRIM_GLOW: + if (remain < 1) + return null; + + face = (int)rules.GetLSLIntegerItem(idx++); + if (face > 21) + break; + + res.Add(new LSL_Float(0)); + break; + + case (int)ScriptBaseClass.PRIM_TEXT: + res.Add(new LSL_String("")); + res.Add(ScriptBaseClass.ZERO_VECTOR); + res.Add(new LSL_Float(1)); + break; + + case (int)ScriptBaseClass.PRIM_ROT_LOCAL: + res.Add(new LSL_Rotation(sp.Rotation)); + break; + + case (int)ScriptBaseClass.PRIM_POS_LOCAL: + res.Add(new LSL_Vector(sp.OffsetPosition)); + break; + + case (int)ScriptBaseClass.PRIM_SLICE: + res.Add(new LSL_Vector(0, 1, 0)); + break; + + case (int)ScriptBaseClass.PRIM_LINK_TARGET: + if(remain < 3) + return null; + + return rules.GetSublist(idx, -1); + } } - while (remaining != null && remaining.Length > 2) - { - linknumber = remaining.GetLSLIntegerItem(0); - rules = remaining.GetSublist(1, -1); - parts = GetLinkParts(linknumber); - - foreach (SceneObjectPart part in parts) - remaining = GetPrimParams(part, rules, ref res); - } - - return res; + return null; } public LSL_List GetPrimParams(SceneObjectPart part, LSL_List rules, ref LSL_List res) { - int idx=0; + int idx = 0; while (idx < rules.Length) { - int code=(int)rules.GetLSLIntegerItem(idx++); - int remain=rules.Length-idx; + int code = (int)rules.GetLSLIntegerItem(idx++); + int remain = rules.Length-idx; switch (code) { @@ -8245,7 +8409,7 @@ namespace OpenSim.Region.ScriptEngine.Shared.Api if (remain < 1) return null; - face=(int)rules.GetLSLIntegerItem(idx++); + face = (int)rules.GetLSLIntegerItem(idx++); tex = part.Shape.Textures; if (face == ScriptBaseClass.ALL_SIDES) From abde0d4efb897581df2a6a7be591de2224611b90 Mon Sep 17 00:00:00 2001 From: Robert Adams Date: Tue, 26 Mar 2013 15:02:10 -0700 Subject: [PATCH 11/40] BulletSim: prevent asset fetching loop when the fetched asset fails to mesh. Check for the case where the fetched mesh asset fails meshing (degenerate triangles or no physical mesh). In this case, the asset is marked 'failed' and BulletSim doesn't keep trying to fetch over-and-over trying to get a good asset. --- .../BulletSPlugin/BSShapeCollection.cs | 124 ++++++++++-------- 1 file changed, 68 insertions(+), 56 deletions(-) diff --git a/OpenSim/Region/Physics/BulletSPlugin/BSShapeCollection.cs b/OpenSim/Region/Physics/BulletSPlugin/BSShapeCollection.cs index a6e20a8230..b6ac23d6a0 100755 --- a/OpenSim/Region/Physics/BulletSPlugin/BSShapeCollection.cs +++ b/OpenSim/Region/Physics/BulletSPlugin/BSShapeCollection.cs @@ -929,67 +929,79 @@ public sealed class BSShapeCollection : IDisposable if (newShape.HasPhysicalShape) return newShape; - // If this mesh has an underlying asset and we have not failed getting it before, fetch the asset - if (prim.BaseShape.SculptEntry - && prim.PrimAssetState != BSPhysObject.PrimAssetCondition.Failed - && prim.PrimAssetState != BSPhysObject.PrimAssetCondition.Waiting - && prim.BaseShape.SculptTexture != OMV.UUID.Zero - ) + // VerifyMeshCreated is called after trying to create the mesh. If we think the asset had been + // fetched but we end up here again, the meshing of the asset must have failed. + // Prevent trying to keep fetching the mesh by declaring failure. + if (prim.PrimAssetState == BSPhysObject.PrimAssetCondition.Fetched) { - DetailLog("{0},BSShapeCollection.VerifyMeshCreated,fetchAsset", prim.LocalID); - // Multiple requestors will know we're waiting for this asset - prim.PrimAssetState = BSPhysObject.PrimAssetCondition.Waiting; - - BSPhysObject xprim = prim; - Util.FireAndForget(delegate - { - RequestAssetDelegate assetProvider = PhysicsScene.RequestAssetMethod; - if (assetProvider != null) - { - BSPhysObject yprim = xprim; // probably not necessary, but, just in case. - assetProvider(yprim.BaseShape.SculptTexture, delegate(AssetBase asset) - { - bool assetFound = false; - string mismatchIDs = String.Empty; // DEBUG DEBUG - if (asset != null && yprim.BaseShape.SculptEntry) - { - if (yprim.BaseShape.SculptTexture.ToString() == asset.ID) - { - yprim.BaseShape.SculptData = asset.Data; - // This will cause the prim to see that the filler shape is not the right - // one and try again to build the object. - // No race condition with the normal shape setting since the rebuild is at taint time. - yprim.ForceBodyShapeRebuild(false /* inTaintTime */); - assetFound = true; - } - else - { - mismatchIDs = yprim.BaseShape.SculptTexture.ToString() + "/" + asset.ID; - } - } - if (assetFound) - yprim.PrimAssetState = BSPhysObject.PrimAssetCondition.Fetched; - else - yprim.PrimAssetState = BSPhysObject.PrimAssetCondition.Failed; - DetailLog("{0},BSShapeCollection,fetchAssetCallback,found={1},isSculpt={2},ids={3}", - yprim.LocalID, assetFound, yprim.BaseShape.SculptEntry, mismatchIDs ); - - }); - } - else - { - xprim.PrimAssetState = BSPhysObject.PrimAssetCondition.Failed; - PhysicsScene.Logger.ErrorFormat("{0} Physical object requires asset but no asset provider. Name={1}", - LogHeader, PhysicsScene.Name); - } - }); + prim.PrimAssetState = BSPhysObject.PrimAssetCondition.Failed; + PhysicsScene.Logger.WarnFormat("{0} Fetched asset would not mesh. {1}, texture={2}", + LogHeader, prim.PhysObjectName, prim.BaseShape.SculptTexture); } else { - if (prim.PrimAssetState == BSPhysObject.PrimAssetCondition.Failed) + // If this mesh has an underlying asset and we have not failed getting it before, fetch the asset + if (prim.BaseShape.SculptEntry + && prim.PrimAssetState != BSPhysObject.PrimAssetCondition.Failed + && prim.PrimAssetState != BSPhysObject.PrimAssetCondition.Waiting + && prim.BaseShape.SculptTexture != OMV.UUID.Zero + ) { - PhysicsScene.Logger.ErrorFormat("{0} Mesh failed to fetch asset. lID={1}, texture={2}", - LogHeader, prim.LocalID, prim.BaseShape.SculptTexture); + DetailLog("{0},BSShapeCollection.VerifyMeshCreated,fetchAsset", prim.LocalID); + // Multiple requestors will know we're waiting for this asset + prim.PrimAssetState = BSPhysObject.PrimAssetCondition.Waiting; + + BSPhysObject xprim = prim; + Util.FireAndForget(delegate + { + RequestAssetDelegate assetProvider = PhysicsScene.RequestAssetMethod; + if (assetProvider != null) + { + BSPhysObject yprim = xprim; // probably not necessary, but, just in case. + assetProvider(yprim.BaseShape.SculptTexture, delegate(AssetBase asset) + { + bool assetFound = false; + string mismatchIDs = String.Empty; // DEBUG DEBUG + if (asset != null && yprim.BaseShape.SculptEntry) + { + if (yprim.BaseShape.SculptTexture.ToString() == asset.ID) + { + yprim.BaseShape.SculptData = asset.Data; + // This will cause the prim to see that the filler shape is not the right + // one and try again to build the object. + // No race condition with the normal shape setting since the rebuild is at taint time. + yprim.ForceBodyShapeRebuild(false /* inTaintTime */); + assetFound = true; + } + else + { + mismatchIDs = yprim.BaseShape.SculptTexture.ToString() + "/" + asset.ID; + } + } + if (assetFound) + yprim.PrimAssetState = BSPhysObject.PrimAssetCondition.Fetched; + else + yprim.PrimAssetState = BSPhysObject.PrimAssetCondition.Failed; + DetailLog("{0},BSShapeCollection,fetchAssetCallback,found={1},isSculpt={2},ids={3}", + yprim.LocalID, assetFound, yprim.BaseShape.SculptEntry, mismatchIDs ); + + }); + } + else + { + xprim.PrimAssetState = BSPhysObject.PrimAssetCondition.Failed; + PhysicsScene.Logger.ErrorFormat("{0} Physical object requires asset but no asset provider. Name={1}", + LogHeader, PhysicsScene.Name); + } + }); + } + else + { + if (prim.PrimAssetState == BSPhysObject.PrimAssetCondition.Failed) + { + PhysicsScene.Logger.WarnFormat("{0} Mesh failed to fetch asset. obj={1}, texture={2}", + LogHeader, prim.PhysObjectName, prim.BaseShape.SculptTexture); + } } } From da5dbaf1d0729b254e1a2123d90f8c11e2c692a3 Mon Sep 17 00:00:00 2001 From: "Justin Clark-Casey (justincc)" Date: Tue, 26 Mar 2013 23:02:13 +0000 Subject: [PATCH 12/40] Add admin_get_agents xmlrpc method. This allows one to retrieve information about agents from a particular region (name, id, position, etc.) Similar to output from "show users" See http://opensimulator.org/wiki/Remoteadmin:admin_get_agents for more details --- .../RemoteController/RemoteAdminPlugin.cs | 66 +++++++++++++++++++ 1 file changed, 66 insertions(+) diff --git a/OpenSim/ApplicationPlugins/RemoteController/RemoteAdminPlugin.cs b/OpenSim/ApplicationPlugins/RemoteController/RemoteAdminPlugin.cs index 69834793c1..5d44b2aea6 100644 --- a/OpenSim/ApplicationPlugins/RemoteController/RemoteAdminPlugin.cs +++ b/OpenSim/ApplicationPlugins/RemoteController/RemoteAdminPlugin.cs @@ -137,6 +137,7 @@ namespace OpenSim.ApplicationPlugins.RemoteController availableMethods["admin_save_heightmap"] = (req, ep) => InvokeXmlRpcMethod(req, ep, XmlRpcSaveHeightmapMethod); // Agent management + availableMethods["admin_get_agents"] = (req, ep) => InvokeXmlRpcMethod(req, ep, XmlRpcGetAgentsMethod); availableMethods["admin_teleport_agent"] = (req, ep) => InvokeXmlRpcMethod(req, ep, XmlRpcTeleportAgentMethod); // User management @@ -1760,6 +1761,71 @@ namespace OpenSim.ApplicationPlugins.RemoteController m_log.Info("[RADMIN]: Access List List Request complete"); } + private void XmlRpcGetAgentsMethod(XmlRpcRequest request, XmlRpcResponse response, IPEndPoint remoteClient) + { + Hashtable responseData = (Hashtable)response.Value; + Hashtable requestData = (Hashtable)request.Params[0]; + + bool includeChildren = false; + + if (requestData.Contains("include_children")) + bool.TryParse((string)requestData["include_children"], out includeChildren); + + Scene scene; + GetSceneFromRegionParams(requestData, responseData, out scene); + + ArrayList xmlRpcRegions = new ArrayList(); + responseData["regions"] = xmlRpcRegions; + + Hashtable xmlRpcRegion = new Hashtable(); + xmlRpcRegions.Add(xmlRpcRegion); + + xmlRpcRegion["name"] = scene.Name; + xmlRpcRegion["id"] = scene.RegionInfo.RegionID.ToString(); + + List agents = scene.GetScenePresences(); + ArrayList xmlrpcAgents = new ArrayList(); + + foreach (ScenePresence agent in agents) + { + if (agent.IsChildAgent && !includeChildren) + continue; + + Hashtable xmlRpcAgent = new Hashtable(); + xmlRpcAgent.Add("name", agent.Name); + xmlRpcAgent.Add("id", agent.UUID.ToString()); + xmlRpcAgent.Add("type", agent.PresenceType.ToString()); + xmlRpcAgent.Add("current_parcel_id", agent.currentParcelUUID.ToString()); + + Vector3 pos = agent.AbsolutePosition; + xmlRpcAgent.Add("pos_x", pos.X.ToString()); + xmlRpcAgent.Add("pos_y", pos.Y.ToString()); + xmlRpcAgent.Add("pos_z", pos.Z.ToString()); + + Vector3 lookAt = agent.Lookat; + xmlRpcAgent.Add("lookat_x", lookAt.X.ToString()); + xmlRpcAgent.Add("lookat_y", lookAt.Y.ToString()); + xmlRpcAgent.Add("lookat_z", lookAt.Z.ToString()); + + Vector3 vel = agent.Velocity; + xmlRpcAgent.Add("vel_x", vel.X.ToString()); + xmlRpcAgent.Add("vel_y", vel.Y.ToString()); + xmlRpcAgent.Add("vel_z", vel.Z.ToString()); + + xmlRpcAgent.Add("is_flying", agent.Flying.ToString()); + xmlRpcAgent.Add("is_sat_on_ground", agent.SitGround.ToString()); + xmlRpcAgent.Add("is_sat_on_object", agent.IsSatOnObject.ToString()); + + xmlrpcAgents.Add(xmlRpcAgent); + } + + m_log.DebugFormat( + "[REMOTE ADMIN]: XmlRpcGetAgents found {0} agents in {1}", xmlrpcAgents.Count, scene.Name); + + xmlRpcRegion["agents"] = xmlrpcAgents; + responseData["success"] = true; + } + private void XmlRpcTeleportAgentMethod(XmlRpcRequest request, XmlRpcResponse response, IPEndPoint remoteClient) { Hashtable responseData = (Hashtable)response.Value; From dd7d7683c914f5b16d8b87434bccea3fe74d9bab Mon Sep 17 00:00:00 2001 From: "Justin Clark-Casey (justincc)" Date: Thu, 28 Mar 2013 00:12:48 +0000 Subject: [PATCH 13/40] Fix problem with megaregions where teleporting into a different region which already had a child agent would stop the eq working for the agent in the new region. This was because the calculation as to whether a new agent was needed in the receiving region did not take megaregions into account, unlike the original calculation when the user first teleported into the region. This meant that on teleport, entity transfer would create a new CAP but this would be ignored by the viewer and receiving region, meaning that the EQ could no longer be used. This would prevent subsequent teleport, amongst other things. Currently, regions up to 512m from a megaregion are considered neighbours. --- .../EntityTransfer/EntityTransferModule.cs | 45 ++++++++++++++++++- 1 file changed, 44 insertions(+), 1 deletion(-) diff --git a/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferModule.cs b/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferModule.cs index 4cf7645376..8af236e2f8 100644 --- a/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferModule.cs +++ b/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferModule.cs @@ -727,6 +727,10 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer IClientIPEndpoint ipepClient; if (NeedsNewAgent(sp.DrawDistance, oldRegionX, newRegionX, oldRegionY, newRegionY)) { + m_log.DebugFormat( + "[ENTITY TRANSFER MODULE]: Determined that region {0} at {1},{2} needs new child agent for incoming agent {3} from {4}", + finalDestination.RegionName, newRegionX, newRegionY, sp.Name, Scene.Name); + //sp.ControllingClient.SendTeleportProgress(teleportFlags, "Creating agent..."); #region IP Translation for NAT // Uses ipepClient above @@ -1001,7 +1005,46 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer protected virtual bool NeedsNewAgent(float drawdist, uint oldRegionX, uint newRegionX, uint oldRegionY, uint newRegionY) { - return Util.IsOutsideView(drawdist, oldRegionX, newRegionX, oldRegionY, newRegionY); + Border[] northBorders = Scene.NorthBorders.ToArray(); + Border[] southBorders = Scene.SouthBorders.ToArray(); + Border[] eastBorders = Scene.EastBorders.ToArray(); + Border[] westBorders = Scene.WestBorders.ToArray(); + + // Leaving this as a "megaregions" computation vs "non-megaregions" computation; it isn't + // clear what should be done with a "far view" given that megaregions already extended the + // view to include everything in the megaregion + if (northBorders.Length > 1 || southBorders.Length > 1 || eastBorders.Length > 1 || westBorders.Length > 1) + { + Vector2 extent = Vector2.Zero; + for (int i = 0; i < eastBorders.Length; i++) + { + extent.X = (eastBorders[i].BorderLine.Z > extent.X) ? eastBorders[i].BorderLine.Z : extent.X; + } + for (int i = 0; i < northBorders.Length; i++) + { + extent.Y = (northBorders[i].BorderLine.Z > extent.Y) ? northBorders[i].BorderLine.Z : extent.Y; + } + + // Loss of fraction on purpose + extent.X = ((int)extent.X / (int)Constants.RegionSize) + 1; + extent.Y = ((int)extent.Y / (int)Constants.RegionSize) + 1; + + uint startX = oldRegionX - 1; + uint startY = oldRegionY - 1; + + uint endX = oldRegionX + (uint)extent.X; + uint endY = oldRegionY + (uint)extent.Y; + + m_log.DebugFormat( + "[ENTITY TRANSFER MODULE]: Megaregion view of {0} is from {1},{2} to {3},{4} with new agent check for {5},{6}", + Scene.Name, startX, startY, endX, endY, newRegionX, newRegionY); + + return !(newRegionX >= startX && newRegionX <= endX && newRegionY >= startY && newRegionY <= endY); + } + else + { + return Util.IsOutsideView(drawdist, oldRegionX, newRegionX, oldRegionY, newRegionY); + } } protected virtual bool NeedsClosing(float drawdist, uint oldRegionX, uint newRegionX, uint oldRegionY, uint newRegionY, GridRegion reg) From cfb20f09a967ede0a64e7151c3430f74362aec99 Mon Sep 17 00:00:00 2001 From: "Justin Clark-Casey (justincc)" Date: Thu, 28 Mar 2013 00:57:43 +0000 Subject: [PATCH 14/40] refactor: combine the checks for megaregion view range into a single place. --- .../EntityTransfer/EntityTransferModule.cs | 102 +++++++++--------- 1 file changed, 51 insertions(+), 51 deletions(-) diff --git a/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferModule.cs b/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferModule.cs index 8af236e2f8..f5ffef2e1c 100644 --- a/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferModule.cs +++ b/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferModule.cs @@ -117,6 +117,7 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer new ExpiringCache>(); private IEventQueue m_eqModule; + private IRegionCombinerModule m_regionCombinerModule; #region ISharedRegionModule @@ -267,6 +268,7 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer return; m_eqModule = Scene.RequestModuleInterface(); + m_regionCombinerModule = Scene.RequestModuleInterface(); } #endregion @@ -1005,41 +1007,16 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer protected virtual bool NeedsNewAgent(float drawdist, uint oldRegionX, uint newRegionX, uint oldRegionY, uint newRegionY) { - Border[] northBorders = Scene.NorthBorders.ToArray(); - Border[] southBorders = Scene.SouthBorders.ToArray(); - Border[] eastBorders = Scene.EastBorders.ToArray(); - Border[] westBorders = Scene.WestBorders.ToArray(); - - // Leaving this as a "megaregions" computation vs "non-megaregions" computation; it isn't - // clear what should be done with a "far view" given that megaregions already extended the - // view to include everything in the megaregion - if (northBorders.Length > 1 || southBorders.Length > 1 || eastBorders.Length > 1 || westBorders.Length > 1) + if (m_regionCombinerModule != null && m_regionCombinerModule.IsRootForMegaregion(Scene.RegionInfo.RegionID)) { - Vector2 extent = Vector2.Zero; - for (int i = 0; i < eastBorders.Length; i++) - { - extent.X = (eastBorders[i].BorderLine.Z > extent.X) ? eastBorders[i].BorderLine.Z : extent.X; - } - for (int i = 0; i < northBorders.Length; i++) - { - extent.Y = (northBorders[i].BorderLine.Z > extent.Y) ? northBorders[i].BorderLine.Z : extent.Y; - } - - // Loss of fraction on purpose - extent.X = ((int)extent.X / (int)Constants.RegionSize) + 1; - extent.Y = ((int)extent.Y / (int)Constants.RegionSize) + 1; - - uint startX = oldRegionX - 1; - uint startY = oldRegionY - 1; - - uint endX = oldRegionX + (uint)extent.X; - uint endY = oldRegionY + (uint)extent.Y; + Vector2 swCorner, neCorner; + GetMegaregionViewRange(out swCorner, out neCorner); m_log.DebugFormat( - "[ENTITY TRANSFER MODULE]: Megaregion view of {0} is from {1},{2} to {3},{4} with new agent check for {5},{6}", - Scene.Name, startX, startY, endX, endY, newRegionX, newRegionY); + "[ENTITY TRANSFER MODULE]: Megaregion view of {0} is from {1} to {2} with new agent check for {3},{4}", + Scene.Name, swCorner, neCorner, newRegionX, newRegionY); - return !(newRegionX >= startX && newRegionX <= endX && newRegionY >= startY && newRegionY <= endY); + return !(newRegionX >= swCorner.X && newRegionX <= neCorner.X && newRegionY >= swCorner.Y && newRegionY <= neCorner.Y); } else { @@ -1902,6 +1879,37 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer reg.RegionName, sp.Name, sp.UUID, reason); } + /// + /// Gets the range considered in view of this megaregion (assuming this is a megaregion). + /// + /// Expressed in 256m units + /// + /// + private void GetMegaregionViewRange(out Vector2 swCorner, out Vector2 neCorner) + { + Border[] northBorders = Scene.NorthBorders.ToArray(); + Border[] eastBorders = Scene.EastBorders.ToArray(); + + Vector2 extent = Vector2.Zero; + for (int i = 0; i < eastBorders.Length; i++) + { + extent.X = (eastBorders[i].BorderLine.Z > extent.X) ? eastBorders[i].BorderLine.Z : extent.X; + } + for (int i = 0; i < northBorders.Length; i++) + { + extent.Y = (northBorders[i].BorderLine.Z > extent.Y) ? northBorders[i].BorderLine.Z : extent.Y; + } + + // Loss of fraction on purpose + extent.X = ((int)extent.X / (int)Constants.RegionSize) + 1; + extent.Y = ((int)extent.Y / (int)Constants.RegionSize) + 1; + + swCorner.X = Scene.RegionInfo.RegionLocX - 1; + swCorner.Y = Scene.RegionInfo.RegionLocY - 1; + neCorner.X = Scene.RegionInfo.RegionLocX + extent.X; + neCorner.Y = Scene.RegionInfo.RegionLocY + extent.Y; + } + /// /// Return the list of regions that are considered to be neighbours to the given scene. /// @@ -1922,8 +1930,9 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer // Leaving this as a "megaregions" computation vs "non-megaregions" computation; it isn't // clear what should be done with a "far view" given that megaregions already extended the // view to include everything in the megaregion - if (northBorders.Length <= 1 && southBorders.Length <= 1 && eastBorders.Length <= 1 && westBorders.Length <= 1) + if (m_regionCombinerModule == null || !m_regionCombinerModule.IsRootForMegaregion(Scene.RegionInfo.RegionID)) { + Console.WriteLine("NOT MEGA"); int dd = avatar.DrawDistance < Constants.RegionSize ? (int)Constants.RegionSize : (int)avatar.DrawDistance; int startX = (int)pRegionLocX * (int)Constants.RegionSize - dd + (int)(Constants.RegionSize/2); @@ -1940,27 +1949,18 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer } else { - Vector2 extent = Vector2.Zero; - for (int i = 0; i < eastBorders.Length; i++) - { - extent.X = (eastBorders[i].BorderLine.Z > extent.X) ? eastBorders[i].BorderLine.Z : extent.X; - } - for (int i = 0; i < northBorders.Length; i++) - { - extent.Y = (northBorders[i].BorderLine.Z > extent.Y) ? northBorders[i].BorderLine.Z : extent.Y; - } + Console.WriteLine("MEGA"); + Vector2 swCorner, neCorner; + GetMegaregionViewRange(out swCorner, out neCorner); - // Loss of fraction on purpose - extent.X = ((int)extent.X / (int)Constants.RegionSize) + 1; - extent.Y = ((int)extent.Y / (int)Constants.RegionSize) + 1; + List neighbours + = pScene.GridService.GetRegionRange( + m_regionInfo.ScopeID, + (int)swCorner.X * (int)Constants.RegionSize, + (int)neCorner.X * (int)Constants.RegionSize, + (int)swCorner.Y * (int)Constants.RegionSize, + (int)neCorner.Y * (int)Constants.RegionSize); - int startX = (int)(pRegionLocX - 1) * (int)Constants.RegionSize; - int startY = (int)(pRegionLocY - 1) * (int)Constants.RegionSize; - - int endX = ((int)pRegionLocX + (int)extent.X) * (int)Constants.RegionSize; - int endY = ((int)pRegionLocY + (int)extent.Y) * (int)Constants.RegionSize; - - List neighbours = pScene.GridService.GetRegionRange(m_regionInfo.ScopeID, startX, endX, startY, endY); neighbours.RemoveAll(delegate(GridRegion r) { return r.RegionID == m_regionInfo.RegionID; }); return neighbours; From f32027f3b53e8ad4f0b9fed0fee65a7e46ec91b0 Mon Sep 17 00:00:00 2001 From: "Justin Clark-Casey (justincc)" Date: Thu, 28 Mar 2013 01:08:47 +0000 Subject: [PATCH 15/40] Remove some Console.WriteLines accidentally left in last commit cfb20f09 --- .../Framework/EntityTransfer/EntityTransferModule.cs | 2 -- 1 file changed, 2 deletions(-) diff --git a/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferModule.cs b/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferModule.cs index f5ffef2e1c..dc6a2a0725 100644 --- a/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferModule.cs +++ b/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferModule.cs @@ -1932,7 +1932,6 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer // view to include everything in the megaregion if (m_regionCombinerModule == null || !m_regionCombinerModule.IsRootForMegaregion(Scene.RegionInfo.RegionID)) { - Console.WriteLine("NOT MEGA"); int dd = avatar.DrawDistance < Constants.RegionSize ? (int)Constants.RegionSize : (int)avatar.DrawDistance; int startX = (int)pRegionLocX * (int)Constants.RegionSize - dd + (int)(Constants.RegionSize/2); @@ -1949,7 +1948,6 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer } else { - Console.WriteLine("MEGA"); Vector2 swCorner, neCorner; GetMegaregionViewRange(out swCorner, out neCorner); From 876d0d310f3c7248a4a6fc29d8babe55a7b1e570 Mon Sep 17 00:00:00 2001 From: "Justin Clark-Casey (justincc)" Date: Thu, 28 Mar 2013 01:36:34 +0000 Subject: [PATCH 16/40] Add "show eq" console command to show numbers of messages in agent event queues. For debugging purposes. --- .../Caps/EventQueue/EventQueueGetModule.cs | 23 +++++++++++++++++++ 1 file changed, 23 insertions(+) diff --git a/OpenSim/Region/ClientStack/Linden/Caps/EventQueue/EventQueueGetModule.cs b/OpenSim/Region/ClientStack/Linden/Caps/EventQueue/EventQueueGetModule.cs index 3cc395016f..624378ea98 100644 --- a/OpenSim/Region/ClientStack/Linden/Caps/EventQueue/EventQueueGetModule.cs +++ b/OpenSim/Region/ClientStack/Linden/Caps/EventQueue/EventQueueGetModule.cs @@ -97,6 +97,14 @@ namespace OpenSim.Region.ClientStack.Linden + " >= 1 - turns on outgoing event logging\n" + " >= 2 - turns on poll notification", HandleDebugEq); + + MainConsole.Instance.Commands.AddCommand( + "Debug", + false, + "show eq", + "show eq", + "Show contents of event queues for logged in avatars. Used for debugging.", + HandleShowEq); } public void RemoveRegion(Scene scene) @@ -148,6 +156,21 @@ namespace OpenSim.Region.ClientStack.Linden } } + protected void HandleShowEq(string module, string[] args) + { + MainConsole.Instance.OutputFormat("For scene {0}", m_scene.Name); + + lock (queues) + { + foreach (KeyValuePair> kvp in queues) + { + MainConsole.Instance.OutputFormat( + "For agent {0} there are {1} messages queued for send.", + kvp.Key, kvp.Value.Count); + } + } + } + /// /// Always returns a valid queue /// From b5b01e5bb59656078012c12146ea6f9e71589d43 Mon Sep 17 00:00:00 2001 From: "Justin Clark-Casey (justincc)" Date: Thu, 28 Mar 2013 01:37:52 +0000 Subject: [PATCH 17/40] Make HGLureModule track god like lures as well as normal lures, to see if this fixes issues where second megaregion auto-teleport hangs on black teleport screen when HG is active. --- OpenSim/Region/CoreModules/Avatar/Lure/HGLureModule.cs | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/OpenSim/Region/CoreModules/Avatar/Lure/HGLureModule.cs b/OpenSim/Region/CoreModules/Avatar/Lure/HGLureModule.cs index 6c9fd86689..a34f2d21fb 100644 --- a/OpenSim/Region/CoreModules/Avatar/Lure/HGLureModule.cs +++ b/OpenSim/Region/CoreModules/Avatar/Lure/HGLureModule.cs @@ -154,7 +154,8 @@ namespace OpenSim.Region.CoreModules.Avatar.Lure void OnIncomingInstantMessage(GridInstantMessage im) { - if (im.dialog == (byte)InstantMessageDialog.RequestTeleport) + if (im.dialog == (byte)InstantMessageDialog.RequestTeleport + || im.dialog == (byte)InstantMessageDialog.GodLikeRequestTeleport) { UUID sessionID = new UUID(im.imSessionID); From 617637c788045f5776d21fc4ce246f3a8d6ecfb8 Mon Sep 17 00:00:00 2001 From: "Justin Clark-Casey (justincc)" Date: Thu, 28 Mar 2013 01:41:23 +0000 Subject: [PATCH 18/40] minor: Fix usage error message for "debug eq" console command --- .../ClientStack/Linden/Caps/EventQueue/EventQueueGetModule.cs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/OpenSim/Region/ClientStack/Linden/Caps/EventQueue/EventQueueGetModule.cs b/OpenSim/Region/ClientStack/Linden/Caps/EventQueue/EventQueueGetModule.cs index 624378ea98..c7d4283b1a 100644 --- a/OpenSim/Region/ClientStack/Linden/Caps/EventQueue/EventQueueGetModule.cs +++ b/OpenSim/Region/ClientStack/Linden/Caps/EventQueue/EventQueueGetModule.cs @@ -146,7 +146,7 @@ namespace OpenSim.Region.ClientStack.Linden if (!(args.Length == 3 && int.TryParse(args[2], out debugLevel))) { - MainConsole.Instance.OutputFormat("Usage: debug eq [0|1]"); + MainConsole.Instance.OutputFormat("Usage: debug eq [0|1|2]"); } else { From 506d5e41bf3fff8acb78002e565eab96beede370 Mon Sep 17 00:00:00 2001 From: "Justin Clark-Casey (justincc)" Date: Thu, 28 Mar 2013 01:54:11 +0000 Subject: [PATCH 19/40] On the North and East sides of a megaregion, only consider regions within 256m to be neighbours rather than regions up to 512 distant. This looks like an off-by-one bug since the view distance was already only 256 on the west and south sides. This reduces the number of child agents being logged into regions neighbouring a megaregion. --- .../Framework/EntityTransfer/EntityTransferModule.cs | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferModule.cs b/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferModule.cs index dc6a2a0725..8da76dfc49 100644 --- a/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferModule.cs +++ b/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferModule.cs @@ -1901,8 +1901,8 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer } // Loss of fraction on purpose - extent.X = ((int)extent.X / (int)Constants.RegionSize) + 1; - extent.Y = ((int)extent.Y / (int)Constants.RegionSize) + 1; + extent.X = ((int)extent.X / (int)Constants.RegionSize); + extent.Y = ((int)extent.Y / (int)Constants.RegionSize); swCorner.X = Scene.RegionInfo.RegionLocX - 1; swCorner.Y = Scene.RegionInfo.RegionLocY - 1; From b05ed4ffa693f3481f97a197de7e582492dc7271 Mon Sep 17 00:00:00 2001 From: "Justin Clark-Casey (justincc)" Date: Thu, 28 Mar 2013 02:17:32 +0000 Subject: [PATCH 20/40] Instead of going via GodLikeRequestTeleport, auto-teleport the agent directly in a megaregion, in the same manner at the "teleport user" console command. This is to bypass an issue with the HGLureModule which stops the auto-teleport from happening. --- .../Region/CoreModules/Avatar/Lure/LureModule.cs | 2 +- .../EntityTransfer/EntityTransferModule.cs | 15 ++++++++++++--- 2 files changed, 13 insertions(+), 4 deletions(-) diff --git a/OpenSim/Region/CoreModules/Avatar/Lure/LureModule.cs b/OpenSim/Region/CoreModules/Avatar/Lure/LureModule.cs index e4b0cfa734..7f4606b366 100644 --- a/OpenSim/Region/CoreModules/Avatar/Lure/LureModule.cs +++ b/OpenSim/Region/CoreModules/Avatar/Lure/LureModule.cs @@ -165,7 +165,7 @@ namespace OpenSim.Region.CoreModules.Avatar.Lure (uint)presence.AbsolutePosition.Y, (uint)Math.Ceiling(presence.AbsolutePosition.Z)); - m_log.DebugFormat("TP invite with message {0}", message); + m_log.DebugFormat("TP invite with message {0}, type {1}", message, lureType); GridInstantMessage m = new GridInstantMessage(scene, client.AgentId, client.FirstName+" "+client.LastName, targetid, diff --git a/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferModule.cs b/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferModule.cs index 8da76dfc49..8a1694396d 100644 --- a/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferModule.cs +++ b/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferModule.cs @@ -379,8 +379,8 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer Vector3 emergencyPos = new Vector3(128, 128, 128); m_log.WarnFormat( - "[ENTITY TRANSFER MODULE]: RequestTeleportToLocation() was given an illegal position of {0} for avatar {1}, {2}. Substituting {3}", - position, sp.Name, sp.UUID, emergencyPos); + "[ENTITY TRANSFER MODULE]: RequestTeleportToLocation() was given an illegal position of {0} for avatar {1}, {2} in {3}. Substituting {4}", + position, sp.Name, sp.UUID, Scene.Name, emergencyPos); position = emergencyPos; } @@ -1346,7 +1346,15 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer Scene initiatingScene) { Thread.Sleep(10000); - + + agent.Scene.RequestTeleportLocation( + agent.ControllingClient, + Utils.UIntsToLong(regionX * (uint)Constants.RegionSize, regionY * (uint)Constants.RegionSize), + position, + agent.Lookat, + (uint)Constants.TeleportFlags.ViaLocation); + + /* IMessageTransferModule im = initiatingScene.RequestModuleInterface(); if (im != null) { @@ -1381,6 +1389,7 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer }); } + */ } private void InformClientToInitiateTeleportToLocationCompleted(IAsyncResult iar) From d9c049fd9f1a78d73931f6aaa4cf9e6c512ba576 Mon Sep 17 00:00:00 2001 From: "Justin Clark-Casey (justincc)" Date: Thu, 28 Mar 2013 02:20:43 +0000 Subject: [PATCH 21/40] Fix a bug in HGEntityTransferModule to call base.RemoveRegion() when a region is removed rather than base.AddRegion() --- .../Framework/EntityTransfer/HGEntityTransferModule.cs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/OpenSim/Region/CoreModules/Framework/EntityTransfer/HGEntityTransferModule.cs b/OpenSim/Region/CoreModules/Framework/EntityTransfer/HGEntityTransferModule.cs index b1887418ee..33ea063600 100644 --- a/OpenSim/Region/CoreModules/Framework/EntityTransfer/HGEntityTransferModule.cs +++ b/OpenSim/Region/CoreModules/Framework/EntityTransfer/HGEntityTransferModule.cs @@ -199,7 +199,7 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer public override void RemoveRegion(Scene scene) { - base.AddRegion(scene); + base.RemoveRegion(scene); if (m_Enabled) scene.UnregisterModuleInterface(this); From afd0d6af0710375bf566ef5a6fcf00e7d1c5ca0f Mon Sep 17 00:00:00 2001 From: "Justin Clark-Casey (justincc)" Date: Thu, 28 Mar 2013 02:23:09 +0000 Subject: [PATCH 22/40] minor: Only try to deregister stats in EntityTransferModule.RemoveRegion() if module was enabled. --- .../Framework/EntityTransfer/EntityTransferModule.cs | 11 +++++++---- 1 file changed, 7 insertions(+), 4 deletions(-) diff --git a/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferModule.cs b/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferModule.cs index 8a1694396d..f351da6d78 100644 --- a/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferModule.cs +++ b/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferModule.cs @@ -256,10 +256,13 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer public virtual void RemoveRegion(Scene scene) { - StatsManager.DeregisterStat(m_interRegionTeleportAttempts); - StatsManager.DeregisterStat(m_interRegionTeleportAborts); - StatsManager.DeregisterStat(m_interRegionTeleportCancels); - StatsManager.DeregisterStat(m_interRegionTeleportFailures); + if (m_Enabled) + { + StatsManager.DeregisterStat(m_interRegionTeleportAttempts); + StatsManager.DeregisterStat(m_interRegionTeleportAborts); + StatsManager.DeregisterStat(m_interRegionTeleportCancels); + StatsManager.DeregisterStat(m_interRegionTeleportFailures); + } } public virtual void RegionLoaded(Scene scene) From 9ca54d00d8b1ca6181392d027077e82e64c53c3d Mon Sep 17 00:00:00 2001 From: "Justin Clark-Casey (justincc)" Date: Thu, 28 Mar 2013 02:29:34 +0000 Subject: [PATCH 23/40] Add back a log message when we attempt a megaregion auto-reteleport --- .../Framework/EntityTransfer/EntityTransferModule.cs | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferModule.cs b/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferModule.cs index f351da6d78..035632b39b 100644 --- a/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferModule.cs +++ b/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferModule.cs @@ -1350,6 +1350,10 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer { Thread.Sleep(10000); + m_log.DebugFormat( + "[ENTITY TRANSFER MODULE]: Auto-reteleporting {0} to correct megaregion location {1},{2},{3} from {4}", + agent.Name, regionX, regionY, position, initiatingScene.Name); + agent.Scene.RequestTeleportLocation( agent.ControllingClient, Utils.UIntsToLong(regionX * (uint)Constants.RegionSize, regionY * (uint)Constants.RegionSize), From 3f9b274180acb4499b878e9acad461811f11eb1f Mon Sep 17 00:00:00 2001 From: Robert Adams Date: Wed, 27 Mar 2013 16:59:13 -0700 Subject: [PATCH 24/40] BulletSim: tweaks to terrain boundry computation. No functional changes. --- .../Physics/BulletSPlugin/BSTerrainManager.cs | 50 +++++++++++-------- 1 file changed, 29 insertions(+), 21 deletions(-) diff --git a/OpenSim/Region/Physics/BulletSPlugin/BSTerrainManager.cs b/OpenSim/Region/Physics/BulletSPlugin/BSTerrainManager.cs index a60946dbbd..d4aecbc4ce 100755 --- a/OpenSim/Region/Physics/BulletSPlugin/BSTerrainManager.cs +++ b/OpenSim/Region/Physics/BulletSPlugin/BSTerrainManager.cs @@ -343,37 +343,35 @@ public sealed class BSTerrainManager : IDisposable { Vector3 ret = pPos; + // First, base addresses are never negative so correct for that possible problem. + if (ret.X < 0f || ret.Y < 0f) + { + ret.X = Util.Clamp(ret.X, 0f, 1000000f); + ret.Y = Util.Clamp(ret.Y, 0f, 1000000f); + DetailLog("{0},BSTerrainManager.ClampPositionToKnownTerrain,zeroingNegXorY,oldPos={1},newPos={2}", + BSScene.DetailLogZero, pPos, ret); + } + // Can't do this function if we don't know about any terrain. if (m_terrains.Count == 0) return ret; - int loopPrevention = 5; + int loopPrevention = 10; Vector3 terrainBaseXYZ; BSTerrainPhys physTerrain; while (!GetTerrainPhysicalAtXYZ(ret, out physTerrain, out terrainBaseXYZ)) { // The passed position is not within a known terrain area. + // NOTE that GetTerrainPhysicalAtXYZ will set 'terrainBaseXYZ' to the base of the unfound region. - // First, base addresses are never negative so correct for that possible problem. - if (ret.X < 0f || ret.Y < 0f) - { - if (ret.X < 0f) - ret.X = 0f; - if (ret.Y < 0f) - ret.Y = 0f; - DetailLog("{0},BSTerrainManager.ClampPositionToKnownTerrain,zeroingNegXorY,oldPos={1},newPos={2}", - BSScene.DetailLogZero, pPos, ret); - } - else - { - // Must be off the top of a region. Find an adjacent region to move into. - Vector3 adjacentTerrainBase = FindAdjacentTerrainBase(terrainBaseXYZ); + // Must be off the top of a region. Find an adjacent region to move into. + Vector3 adjacentTerrainBase = FindAdjacentTerrainBase(terrainBaseXYZ); + + ret.X = Math.Min(ret.X, adjacentTerrainBase.X + (ret.X % DefaultRegionSize.X)); + ret.Y = Math.Min(ret.Y, adjacentTerrainBase.Y + (ret.X % DefaultRegionSize.Y)); + DetailLog("{0},BSTerrainManager.ClampPositionToKnownTerrain,findingAdjacentRegion,adjacentRegBase={1},oldPos={2},newPos={3}", + BSScene.DetailLogZero, adjacentTerrainBase, pPos, ret); - ret.X = Math.Min(ret.X, adjacentTerrainBase.X + DefaultRegionSize.X); - ret.Y = Math.Min(ret.Y, adjacentTerrainBase.Y + DefaultRegionSize.Y); - DetailLog("{0},BSTerrainManager.ClampPositionToKnownTerrain,findingAdjacentRegion,adjacentRegBase={1},oldPos={2},newPos={3}", - BSScene.DetailLogZero, adjacentTerrainBase, pPos, ret); - } if (loopPrevention-- < 0f) { // The 'while' is a little dangerous so this prevents looping forever if the @@ -383,6 +381,7 @@ public sealed class BSTerrainManager : IDisposable break; } } + return ret; } @@ -479,11 +478,20 @@ public sealed class BSTerrainManager : IDisposable private Vector3 FindAdjacentTerrainBase(Vector3 pTerrainBase) { Vector3 ret = pTerrainBase; + + // Can't do this function if we don't know about any terrain. + if (m_terrains.Count == 0) + return ret; + + // Just some sanity + ret.X = Util.Clamp(ret.X, 0f, 1000000f); + ret.Y = Util.Clamp(ret.Y, 0f, 1000000f); ret.Z = 0f; + lock (m_terrains) { // Once down to the <0,0> region, we have to be done. - while (ret.X > 0f && ret.Y > 0f) + while (ret.X > 0f || ret.Y > 0f) { if (ret.X > 0f) { From 6a9630d2bdc27ed702936f4c44e6978f728a9ef0 Mon Sep 17 00:00:00 2001 From: Robert Adams Date: Thu, 28 Mar 2013 10:56:21 -0700 Subject: [PATCH 25/40] BulletSim: fix race condition when creating very large mega-regions. The symptom was exceptions while creating physical terrain. Reduce default terrain mesh magnification to 2 from 3 because the higher resolution uses a lot of memory and doesn't solve the terrain smoothness for vehicles. Added comments here and there and improved some debugging log messages. --- .../Physics/BulletSPlugin/BSCharacter.cs | 4 +- .../Physics/BulletSPlugin/BSMaterials.cs | 3 ++ .../Region/Physics/BulletSPlugin/BSParam.cs | 2 +- .../Physics/BulletSPlugin/BSTerrainManager.cs | 38 ++++++++++++------- .../Physics/BulletSPlugin/BSTerrainMesh.cs | 10 ++--- 5 files changed, 35 insertions(+), 22 deletions(-) diff --git a/OpenSim/Region/Physics/BulletSPlugin/BSCharacter.cs b/OpenSim/Region/Physics/BulletSPlugin/BSCharacter.cs index e208d3a9e0..90c2d9cf46 100644 --- a/OpenSim/Region/Physics/BulletSPlugin/BSCharacter.cs +++ b/OpenSim/Region/Physics/BulletSPlugin/BSCharacter.cs @@ -479,7 +479,7 @@ public sealed class BSCharacter : BSPhysObject // The character is out of the known/simulated area. // Force the avatar position to be within known. ScenePresence will use the position // plus the velocity to decide if the avatar is moving out of the region. - RawPosition = PhysicsScene.TerrainManager.ClampPositionIntoKnownTerrain(RawPosition); + RawPosition = PhysicsScene.TerrainManager.ClampPositionIntoKnownTerrain(RawPosition); DetailLog("{0},BSCharacter.PositionSanityCheck,notWithinKnownTerrain,clampedPos={1}", LocalID, RawPosition); return true; } @@ -898,7 +898,7 @@ public sealed class BSCharacter : BSPhysObject // Do some sanity checking for the avatar. Make sure it's above ground and inbounds. if (PositionSanityCheck(true)) { - DetailLog("{0},BSCharacter.UpdateProperties,updatePosForSanity,pos={1}", LocalID, _position); + DetailLog("{0},BSCharacter.UpdateProperties,updatePosForSanity,pos={1}", LocalID, _position); entprop.Position = _position; } diff --git a/OpenSim/Region/Physics/BulletSPlugin/BSMaterials.cs b/OpenSim/Region/Physics/BulletSPlugin/BSMaterials.cs index 92d62ff9ea..ee77d6e3f8 100755 --- a/OpenSim/Region/Physics/BulletSPlugin/BSMaterials.cs +++ b/OpenSim/Region/Physics/BulletSPlugin/BSMaterials.cs @@ -180,11 +180,14 @@ public static class BSMaterials // Use reflection to set the value in the attribute structure. private static void SetAttributeValue(int matType, string attribName, float val) { + // Get the current attribute values for this material MaterialAttributes thisAttrib = Attributes[matType]; + // Find the field for the passed attribute name (eg, find field named 'friction') FieldInfo fieldInfo = thisAttrib.GetType().GetField(attribName.ToLower()); if (fieldInfo != null) { fieldInfo.SetValue(thisAttrib, val); + // Copy new attributes back to array -- since MaterialAttributes is 'struct', passed by value, not reference. Attributes[matType] = thisAttrib; } } diff --git a/OpenSim/Region/Physics/BulletSPlugin/BSParam.cs b/OpenSim/Region/Physics/BulletSPlugin/BSParam.cs index f3454c8daf..385ed9e9bc 100755 --- a/OpenSim/Region/Physics/BulletSPlugin/BSParam.cs +++ b/OpenSim/Region/Physics/BulletSPlugin/BSParam.cs @@ -482,7 +482,7 @@ public static class BSParam (s) => { return TerrainImplementation; }, (s,v) => { TerrainImplementation = v; } ), new ParameterDefn("TerrainMeshMagnification", "Number of times the 256x256 heightmap is multiplied to create the terrain mesh" , - 3, + 2, (s) => { return TerrainMeshMagnification; }, (s,v) => { TerrainMeshMagnification = v; } ), new ParameterDefn("TerrainFriction", "Factor to reduce movement against terrain surface" , diff --git a/OpenSim/Region/Physics/BulletSPlugin/BSTerrainManager.cs b/OpenSim/Region/Physics/BulletSPlugin/BSTerrainManager.cs index d4aecbc4ce..b2fb8354ac 100755 --- a/OpenSim/Region/Physics/BulletSPlugin/BSTerrainManager.cs +++ b/OpenSim/Region/Physics/BulletSPlugin/BSTerrainManager.cs @@ -132,6 +132,7 @@ public sealed class BSTerrainManager : IDisposable // safe to call Bullet in real time. We hope no one is moving prims around yet. public void CreateInitialGroundPlaneAndTerrain() { + DetailLog("{0},BSTerrainManager.CreateInitialGroundPlaneAndTerrain,region={1}", BSScene.DetailLogZero, PhysicsScene.RegionName); // The ground plane is here to catch things that are trying to drop to negative infinity BulletShape groundPlaneShape = PhysicsScene.PE.CreateGroundPlaneShape(BSScene.GROUNDPLANE_ID, 1f, BSParam.TerrainCollisionMargin); m_groundPlane = PhysicsScene.PE.CreateBodyWithDefaultMotionState(groundPlaneShape, @@ -145,14 +146,18 @@ public sealed class BSTerrainManager : IDisposable m_groundPlane.collisionType = CollisionType.Groundplane; m_groundPlane.ApplyCollisionMask(PhysicsScene); - // Build an initial terrain and put it in the world. This quickly gets replaced by the real region terrain. BSTerrainPhys initialTerrain = new BSTerrainHeightmap(PhysicsScene, Vector3.Zero, BSScene.TERRAIN_ID, DefaultRegionSize); - m_terrains.Add(Vector3.Zero, initialTerrain); + lock (m_terrains) + { + // Build an initial terrain and put it in the world. This quickly gets replaced by the real region terrain. + m_terrains.Add(Vector3.Zero, initialTerrain); + } } // Release all the terrain structures we might have allocated public void ReleaseGroundPlaneAndTerrain() { + DetailLog("{0},BSTerrainManager.ReleaseGroundPlaneAndTerrain,region={1}", BSScene.DetailLogZero, PhysicsScene.RegionName); if (m_groundPlane.HasPhysicalBody) { if (PhysicsScene.PE.RemoveObjectFromWorld(PhysicsScene.World, m_groundPlane)) @@ -193,11 +198,16 @@ public sealed class BSTerrainManager : IDisposable // the terrain is added to our parent if (MegaRegionParentPhysicsScene is BSScene) { - DetailLog("{0},SetTerrain.ToParent,offset={1},worldMax={2}", - BSScene.DetailLogZero, m_worldOffset, m_worldMax); - ((BSScene)MegaRegionParentPhysicsScene).TerrainManager.UpdateTerrain( - BSScene.CHILDTERRAIN_ID, localHeightMap, - m_worldOffset, m_worldOffset + DefaultRegionSize, true); + DetailLog("{0},SetTerrain.ToParent,offset={1},worldMax={2}", BSScene.DetailLogZero, m_worldOffset, m_worldMax); + // This looks really odd but this region is passing its terrain to its mega-region root region + // and the creation of the terrain must happen on the root region's taint thread and not + // my taint thread. + ((BSScene)MegaRegionParentPhysicsScene).PostTaintObject("TerrainManager.SetTerrain.Mega-" + m_worldOffset.ToString(), 0, delegate() + { + ((BSScene)MegaRegionParentPhysicsScene).TerrainManager.UpdateTerrain( + BSScene.CHILDTERRAIN_ID, localHeightMap, + m_worldOffset, m_worldOffset + DefaultRegionSize, true /* inTaintTime */); + }); } } else @@ -206,16 +216,16 @@ public sealed class BSTerrainManager : IDisposable DetailLog("{0},SetTerrain.Existing", BSScene.DetailLogZero); UpdateTerrain(BSScene.TERRAIN_ID, localHeightMap, - m_worldOffset, m_worldOffset + DefaultRegionSize, true); + m_worldOffset, m_worldOffset + DefaultRegionSize, true /* inTaintTime */); } }); } - // If called with no mapInfo for the terrain, this will create a new mapInfo and terrain + // If called for terrain has has not been previously allocated, a new terrain will be built // based on the passed information. The 'id' should be either the terrain id or // BSScene.CHILDTERRAIN_ID. If the latter, a new child terrain ID will be allocated and used. // The latter feature is for creating child terrains for mega-regions. - // If called with a mapInfo in m_heightMaps and there is an existing terrain body, a new + // If there is an existing terrain body, a new // terrain shape is created and added to the body. // This call is most often used to update the heightMap and parameters of the terrain. // (The above does suggest that some simplification/refactoring is in order.) @@ -223,8 +233,8 @@ public sealed class BSTerrainManager : IDisposable private void UpdateTerrain(uint id, float[] heightMap, Vector3 minCoords, Vector3 maxCoords, bool inTaintTime) { - DetailLog("{0},BSTerrainManager.UpdateTerrain,call,minC={1},maxC={2},inTaintTime={3}", - BSScene.DetailLogZero, minCoords, maxCoords, inTaintTime); + DetailLog("{0},BSTerrainManager.UpdateTerrain,call,id={1},minC={2},maxC={3},inTaintTime={4}", + BSScene.DetailLogZero, id, minCoords, maxCoords, inTaintTime); // Find high and low points of passed heightmap. // The min and max passed in is usually the area objects can be in (maximum @@ -253,7 +263,7 @@ public sealed class BSTerrainManager : IDisposable if (m_terrains.TryGetValue(terrainRegionBase, out terrainPhys)) { // There is already a terrain in this spot. Free the old and build the new. - DetailLog("{0},UpdateTerrain:UpdateExisting,call,id={1},base={2},minC={3},maxC={4}", + DetailLog("{0},BSTErrainManager.UpdateTerrain:UpdateExisting,call,id={1},base={2},minC={3},maxC={4}", BSScene.DetailLogZero, id, terrainRegionBase, minCoords, minCoords); // Remove old terrain from the collection @@ -292,7 +302,7 @@ public sealed class BSTerrainManager : IDisposable if (newTerrainID >= BSScene.CHILDTERRAIN_ID) newTerrainID = ++m_terrainCount; - DetailLog("{0},UpdateTerrain:NewTerrain,taint,newID={1},minCoord={2},maxCoord={3}", + DetailLog("{0},BSTerrainManager.UpdateTerrain:NewTerrain,taint,newID={1},minCoord={2},maxCoord={3}", BSScene.DetailLogZero, newTerrainID, minCoords, minCoords); BSTerrainPhys newTerrainPhys = BuildPhysicalTerrain(terrainRegionBase, id, heightMap, minCoords, maxCoords); m_terrains.Add(terrainRegionBase, newTerrainPhys); diff --git a/OpenSim/Region/Physics/BulletSPlugin/BSTerrainMesh.cs b/OpenSim/Region/Physics/BulletSPlugin/BSTerrainMesh.cs index a9cd8a1578..2ce1513d54 100755 --- a/OpenSim/Region/Physics/BulletSPlugin/BSTerrainMesh.cs +++ b/OpenSim/Region/Physics/BulletSPlugin/BSTerrainMesh.cs @@ -98,20 +98,20 @@ public sealed class BSTerrainMesh : BSTerrainPhys if (!meshCreationSuccess) { // DISASTER!! - PhysicsScene.DetailLog("{0},BSTerrainMesh.create,failedConversionOfHeightmap", ID); + PhysicsScene.DetailLog("{0},BSTerrainMesh.create,failedConversionOfHeightmap,id={1}", BSScene.DetailLogZero, ID); PhysicsScene.Logger.ErrorFormat("{0} Failed conversion of heightmap to mesh! base={1}", LogHeader, TerrainBase); // Something is very messed up and a crash is in our future. return; } - PhysicsScene.DetailLog("{0},BSTerrainMesh.create,meshed,indices={1},indSz={2},vertices={3},vertSz={4}", - ID, indicesCount, indices.Length, verticesCount, vertices.Length); + PhysicsScene.DetailLog("{0},BSTerrainMesh.create,meshed,id={1},indices={2},indSz={3},vertices={4},vertSz={5}", + BSScene.DetailLogZero, ID, indicesCount, indices.Length, verticesCount, vertices.Length); m_terrainShape = PhysicsScene.PE.CreateMeshShape(PhysicsScene.World, indicesCount, indices, verticesCount, vertices); if (!m_terrainShape.HasPhysicalShape) { // DISASTER!! - PhysicsScene.DetailLog("{0},BSTerrainMesh.create,failedCreationOfShape", ID); + PhysicsScene.DetailLog("{0},BSTerrainMesh.create,failedCreationOfShape,id={1}", BSScene.DetailLogZero, ID); PhysicsScene.Logger.ErrorFormat("{0} Failed creation of terrain mesh! base={1}", LogHeader, TerrainBase); // Something is very messed up and a crash is in our future. return; @@ -151,7 +151,7 @@ public sealed class BSTerrainMesh : BSTerrainPhys if (BSParam.UseSingleSidedMeshes) { - PhysicsScene.DetailLog("{0},BSTerrainMesh.settingCustomMaterial", id); + PhysicsScene.DetailLog("{0},BSTerrainMesh.settingCustomMaterial,id={1}", BSScene.DetailLogZero, id); PhysicsScene.PE.AddToCollisionFlags(m_terrainBody, CollisionFlags.CF_CUSTOM_MATERIAL_CALLBACK); } From c2093ccce16cd5210c8e0759f23b5b4bd205b7af Mon Sep 17 00:00:00 2001 From: "Justin Clark-Casey (justincc)" Date: Thu, 28 Mar 2013 22:07:58 +0000 Subject: [PATCH 26/40] Move the simulator-side RezAttachments call on login to SP.MakeRootAgent with the other attachments code, using TeleportFlags.ViaLogin check to fire if necessary. This is to simplify the code (no tricky 'wasChild' signalling required) and to reduce the risk of a thread clash between simulator-side attaching (necessary for v1 viewers) and the viewer-side attaching the v3 viewers perform. --- .../Avatar/Attachments/AttachmentsModule.cs | 2 +- OpenSim/Region/Framework/Scenes/Scene.cs | 28 ------------- .../Region/Framework/Scenes/ScenePresence.cs | 41 ++++++++++++++----- 3 files changed, 32 insertions(+), 39 deletions(-) diff --git a/OpenSim/Region/CoreModules/Avatar/Attachments/AttachmentsModule.cs b/OpenSim/Region/CoreModules/Avatar/Attachments/AttachmentsModule.cs index ad17aa9ab8..a46834c1f4 100644 --- a/OpenSim/Region/CoreModules/Avatar/Attachments/AttachmentsModule.cs +++ b/OpenSim/Region/CoreModules/Avatar/Attachments/AttachmentsModule.cs @@ -197,7 +197,7 @@ namespace OpenSim.Region.CoreModules.Avatar.Attachments return; } -// m_log.DebugFormat("[ATTACHMENTS MODULE]: Rezzing any attachments for {0}", sp.Name); +// m_log.DebugFormat("[ATTACHMENTS MODULE]: Rezzing any attachments for {0} from simulator-side", sp.Name); List attachments = sp.Appearance.GetAttachments(); foreach (AvatarAttachment attach in attachments) diff --git a/OpenSim/Region/Framework/Scenes/Scene.cs b/OpenSim/Region/Framework/Scenes/Scene.cs index 45cbdd574d..0ac4027032 100644 --- a/OpenSim/Region/Framework/Scenes/Scene.cs +++ b/OpenSim/Region/Framework/Scenes/Scene.cs @@ -2820,34 +2820,6 @@ namespace OpenSim.Region.Framework.Scenes m_eventManager.TriggerOnNewPresence(sp); sp.TeleportFlags = (TPFlags)aCircuit.teleportFlags; - - // The first agent upon login is a root agent by design. - // For this agent we will have to rez the attachments. - // All other AddNewClient calls find aCircuit.child to be true. - if (aCircuit.child == false) - { - // We have to set SP to be a root agent here so that SP.MakeRootAgent() will later not try to - // start the scripts again (since this is done in RezAttachments()). - // XXX: This is convoluted. - sp.IsChildAgent = false; - - // We leave a 5 second pause before attempting to rez attachments to avoid a clash with - // version 3 viewers that maybe doing their own attachment rezzing related to their current - // outfit folder on startup. If these operations do clash, then the symptoms are invisible - // attachments until one zooms in on the avatar. - // - // We do not pause if we are launching on the same thread anyway in order to avoid pointlessly - // delaying any attachment related regression tests. - if (AttachmentsModule != null) - Util.FireAndForget( - o => - { - if (Util.FireAndForgetMethod != FireAndForgetMethod.None) - Thread.Sleep(5000); - - AttachmentsModule.RezAttachments(sp); - }); - } } else { diff --git a/OpenSim/Region/Framework/Scenes/ScenePresence.cs b/OpenSim/Region/Framework/Scenes/ScenePresence.cs index f3b923f338..4fb9a1b55a 100644 --- a/OpenSim/Region/Framework/Scenes/ScenePresence.cs +++ b/OpenSim/Region/Framework/Scenes/ScenePresence.cs @@ -866,7 +866,6 @@ namespace OpenSim.Region.Framework.Scenes //m_log.DebugFormat("[SCENE]: known regions in {0}: {1}", Scene.RegionInfo.RegionName, KnownChildRegionHandles.Count); - bool wasChild = IsChildAgent; IsChildAgent = false; IGroupsModule gm = m_scene.RequestModuleInterface(); @@ -952,18 +951,40 @@ namespace OpenSim.Region.Framework.Scenes // and it has already rezzed the attachments and started their scripts. // We do the following only for non-login agents, because their scripts // haven't started yet. - lock (m_attachments) + if ((TeleportFlags & TeleportFlags.ViaLogin) != 0) { - if (wasChild && HasAttachments()) + // We leave a 5 second pause before attempting to rez attachments to avoid a clash with + // version 3 viewers that maybe doing their own attachment rezzing related to their current + // outfit folder on startup. If these operations do clash, then the symptoms are invisible + // attachments until one zooms in on the avatar. + // + // We do not pause if we are launching on the same thread anyway in order to avoid pointlessly + // delaying any attachment related regression tests. + if (Scene.AttachmentsModule != null) + Util.FireAndForget( + o => + { + if (Util.FireAndForgetMethod != FireAndForgetMethod.None) + System.Threading.Thread.Sleep(5000); + + Scene.AttachmentsModule.RezAttachments(this); + }); + } + else + { + lock (m_attachments) { - m_log.DebugFormat( - "[SCENE PRESENCE]: Restarting scripts in attachments for {0} in {1}", Name, Scene.Name); - - // Resume scripts - foreach (SceneObjectGroup sog in m_attachments) + if (HasAttachments()) { - sog.RootPart.ParentGroup.CreateScriptInstances(0, false, m_scene.DefaultScriptEngine, GetStateSource()); - sog.ResumeScripts(); + m_log.DebugFormat( + "[SCENE PRESENCE]: Restarting scripts in attachments for {0} in {1}", Name, Scene.Name); + + // Resume scripts + foreach (SceneObjectGroup sog in m_attachments) + { + sog.RootPart.ParentGroup.CreateScriptInstances(0, false, m_scene.DefaultScriptEngine, GetStateSource()); + sog.ResumeScripts(); + } } } } From 3b377f16b29a6395d73af1cc987cb9abf9935376 Mon Sep 17 00:00:00 2001 From: "Justin Clark-Casey (justincc)" Date: Thu, 28 Mar 2013 22:44:59 +0000 Subject: [PATCH 27/40] Fix regression tests by making a new NPC always trigger simulator side attachment code when created. Regression from previous commit c2093ccc. Failed because NPCs don't set the ViaLogin flag --- OpenSim/Region/Framework/Scenes/ScenePresence.cs | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/OpenSim/Region/Framework/Scenes/ScenePresence.cs b/OpenSim/Region/Framework/Scenes/ScenePresence.cs index 4fb9a1b55a..3a1e7589d9 100644 --- a/OpenSim/Region/Framework/Scenes/ScenePresence.cs +++ b/OpenSim/Region/Framework/Scenes/ScenePresence.cs @@ -951,7 +951,7 @@ namespace OpenSim.Region.Framework.Scenes // and it has already rezzed the attachments and started their scripts. // We do the following only for non-login agents, because their scripts // haven't started yet. - if ((TeleportFlags & TeleportFlags.ViaLogin) != 0) + if (PresenceType == PresenceType.Npc || (TeleportFlags & TeleportFlags.ViaLogin) != 0) { // We leave a 5 second pause before attempting to rez attachments to avoid a clash with // version 3 viewers that maybe doing their own attachment rezzing related to their current @@ -964,7 +964,7 @@ namespace OpenSim.Region.Framework.Scenes Util.FireAndForget( o => { - if (Util.FireAndForgetMethod != FireAndForgetMethod.None) + if (PresenceType != PresenceType.Npc && Util.FireAndForgetMethod != FireAndForgetMethod.None) System.Threading.Thread.Sleep(5000); Scene.AttachmentsModule.RezAttachments(this); From 4ad9b275302ee109937512963eab095ff542a0c7 Mon Sep 17 00:00:00 2001 From: "Justin Clark-Casey (justincc)" Date: Thu, 28 Mar 2013 22:51:59 +0000 Subject: [PATCH 28/40] If the viewer has already rezzed any attachments itself, then ignore the simulator-side rez attachments call. This is a further effort to reduce v3 viewer race conditions where this call may clash with the viewer signalling attachment wearing from its current outfit folder. --- .../Avatar/Attachments/AttachmentsModule.cs | 14 ++++++++++---- .../Framework/Interfaces/IAttachmentsModule.cs | 4 ++++ OpenSim/Region/Framework/Scenes/ScenePresence.cs | 12 +++++------- 3 files changed, 19 insertions(+), 11 deletions(-) diff --git a/OpenSim/Region/CoreModules/Avatar/Attachments/AttachmentsModule.cs b/OpenSim/Region/CoreModules/Avatar/Attachments/AttachmentsModule.cs index a46834c1f4..55c5422820 100644 --- a/OpenSim/Region/CoreModules/Avatar/Attachments/AttachmentsModule.cs +++ b/OpenSim/Region/CoreModules/Avatar/Attachments/AttachmentsModule.cs @@ -182,10 +182,6 @@ namespace OpenSim.Region.CoreModules.Avatar.Attachments } } - /// - /// RezAttachments. This should only be called upon login on the first region. - /// Attachment rezzings on crossings and TPs are done in a different way. - /// public void RezAttachments(IScenePresence sp) { if (!Enabled) @@ -194,9 +190,19 @@ namespace OpenSim.Region.CoreModules.Avatar.Attachments if (null == sp.Appearance) { m_log.WarnFormat("[ATTACHMENTS MODULE]: Appearance has not been initialized for agent {0}", sp.UUID); + return; } + if (sp.GetAttachments().Count > 0) + { +// m_log.DebugFormat( +// "[ATTACHMENTS MODULE]: Not doing simulator-side attachment rez for {0} in {1} as their viewer has already rezzed attachments", +// m_scene.Name, sp.Name); + + return; + } + // m_log.DebugFormat("[ATTACHMENTS MODULE]: Rezzing any attachments for {0} from simulator-side", sp.Name); List attachments = sp.Appearance.GetAttachments(); diff --git a/OpenSim/Region/Framework/Interfaces/IAttachmentsModule.cs b/OpenSim/Region/Framework/Interfaces/IAttachmentsModule.cs index 46daab3e35..156a09d3ff 100644 --- a/OpenSim/Region/Framework/Interfaces/IAttachmentsModule.cs +++ b/OpenSim/Region/Framework/Interfaces/IAttachmentsModule.cs @@ -53,6 +53,10 @@ namespace OpenSim.Region.Framework.Interfaces /// RezAttachments. This should only be called upon login on the first region. /// Attachment rezzings on crossings and TPs are done in a different way. /// + /// + /// This is only actually necessary for viewers which do not have a current outfit folder (these viewers make + /// their own attachment calls on login) and agents which have attachments but no viewer (e.g. NPCs). + /// /// void RezAttachments(IScenePresence sp); diff --git a/OpenSim/Region/Framework/Scenes/ScenePresence.cs b/OpenSim/Region/Framework/Scenes/ScenePresence.cs index 3a1e7589d9..fcb2f6d1f2 100644 --- a/OpenSim/Region/Framework/Scenes/ScenePresence.cs +++ b/OpenSim/Region/Framework/Scenes/ScenePresence.cs @@ -953,13 +953,11 @@ namespace OpenSim.Region.Framework.Scenes // haven't started yet. if (PresenceType == PresenceType.Npc || (TeleportFlags & TeleportFlags.ViaLogin) != 0) { - // We leave a 5 second pause before attempting to rez attachments to avoid a clash with - // version 3 viewers that maybe doing their own attachment rezzing related to their current - // outfit folder on startup. If these operations do clash, then the symptoms are invisible - // attachments until one zooms in on the avatar. - // - // We do not pause if we are launching on the same thread anyway in order to avoid pointlessly - // delaying any attachment related regression tests. + // Viewers which have a current outfit folder will actually rez their own attachments. However, + // viewers without (e.g. v1 viewers) will not, so we still need to make this call. + // + // However, we leave a 5 second pause to try and avoid a clash with viewers that are rezzing + // attachments themselves. This should then mean that this call ends up doing nothing. if (Scene.AttachmentsModule != null) Util.FireAndForget( o => From 03e421bf3d796bf3498f4f3311c59ce04fb1fea1 Mon Sep 17 00:00:00 2001 From: "Justin Clark-Casey (justincc)" Date: Thu, 28 Mar 2013 22:55:13 +0000 Subject: [PATCH 29/40] minor: comment out unused Scene.AgentCrossing() to reduce code complexity --- OpenSim/Region/Framework/Scenes/Scene.cs | 54 ++++++++++++------------ 1 file changed, 27 insertions(+), 27 deletions(-) diff --git a/OpenSim/Region/Framework/Scenes/Scene.cs b/OpenSim/Region/Framework/Scenes/Scene.cs index 0ac4027032..5337835325 100644 --- a/OpenSim/Region/Framework/Scenes/Scene.cs +++ b/OpenSim/Region/Framework/Scenes/Scene.cs @@ -4103,33 +4103,33 @@ namespace OpenSim.Region.Framework.Scenes // } // } - /// - /// Triggered when an agent crosses into this sim. Also happens on initial login. - /// - /// - /// - /// - public virtual void AgentCrossing(UUID agentID, Vector3 position, bool isFlying) - { - ScenePresence presence = GetScenePresence(agentID); - if (presence != null) - { - try - { - presence.MakeRootAgent(position, isFlying); - } - catch (Exception e) - { - m_log.ErrorFormat("[SCENE]: Unable to do agent crossing, exception {0}{1}", e.Message, e.StackTrace); - } - } - else - { - m_log.ErrorFormat( - "[SCENE]: Could not find presence for agent {0} crossing into scene {1}", - agentID, RegionInfo.RegionName); - } - } +// /// +// /// Triggered when an agent crosses into this sim. Also happens on initial login. +// /// +// /// +// /// +// /// +// public virtual void AgentCrossing(UUID agentID, Vector3 position, bool isFlying) +// { +// ScenePresence presence = GetScenePresence(agentID); +// if (presence != null) +// { +// try +// { +// presence.MakeRootAgent(position, isFlying); +// } +// catch (Exception e) +// { +// m_log.ErrorFormat("[SCENE]: Unable to do agent crossing, exception {0}{1}", e.Message, e.StackTrace); +// } +// } +// else +// { +// m_log.ErrorFormat( +// "[SCENE]: Could not find presence for agent {0} crossing into scene {1}", +// agentID, RegionInfo.RegionName); +// } +// } /// /// We've got an update about an agent that sees into this region, From feffc8081dc5ab2889a7ea4b96b2befaed0c3f95 Mon Sep 17 00:00:00 2001 From: "Justin Clark-Casey (justincc)" Date: Thu, 28 Mar 2013 22:56:30 +0000 Subject: [PATCH 30/40] minor: remove some mono compiler warnings from EntityTransferModule --- .../Framework/EntityTransfer/EntityTransferModule.cs | 5 ----- 1 file changed, 5 deletions(-) diff --git a/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferModule.cs b/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferModule.cs index 035632b39b..764c98216c 100644 --- a/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferModule.cs +++ b/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferModule.cs @@ -1938,11 +1938,6 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer Scene pScene = avatar.Scene; RegionInfo m_regionInfo = pScene.RegionInfo; - Border[] northBorders = pScene.NorthBorders.ToArray(); - Border[] southBorders = pScene.SouthBorders.ToArray(); - Border[] eastBorders = pScene.EastBorders.ToArray(); - Border[] westBorders = pScene.WestBorders.ToArray(); - // Leaving this as a "megaregions" computation vs "non-megaregions" computation; it isn't // clear what should be done with a "far view" given that megaregions already extended the // view to include everything in the megaregion From 2b142f2f9e888d5cb7317cc51c12ac7152c54459 Mon Sep 17 00:00:00 2001 From: "Justin Clark-Casey (justincc)" Date: Thu, 28 Mar 2013 23:09:35 +0000 Subject: [PATCH 31/40] Add "debug attachments" console command to allow highly verbose attachment logging to be switched on and off. Default is off. --- .../Avatar/Attachments/AttachmentsModule.cs | 170 +++++++++++------- 1 file changed, 109 insertions(+), 61 deletions(-) diff --git a/OpenSim/Region/CoreModules/Avatar/Attachments/AttachmentsModule.cs b/OpenSim/Region/CoreModules/Avatar/Attachments/AttachmentsModule.cs index 55c5422820..c78f5b321e 100644 --- a/OpenSim/Region/CoreModules/Avatar/Attachments/AttachmentsModule.cs +++ b/OpenSim/Region/CoreModules/Avatar/Attachments/AttachmentsModule.cs @@ -48,6 +48,8 @@ namespace OpenSim.Region.CoreModules.Avatar.Attachments { #region INonSharedRegionModule private static readonly ILog m_log = LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType); + + public int DebugLevel { get; set; } private Scene m_scene; private IInventoryAccessModule m_invAccessModule; @@ -79,11 +81,37 @@ namespace OpenSim.Region.CoreModules.Avatar.Attachments m_scene.EventManager.OnNewClient += SubscribeToClientEvents; m_scene.EventManager.OnStartScript += (localID, itemID) => HandleScriptStateChange(localID, true); m_scene.EventManager.OnStopScript += (localID, itemID) => HandleScriptStateChange(localID, false); + + MainConsole.Instance.Commands.AddCommand( + "Debug", + false, + "debug attachments", + "debug attachments [0|1]", + "Turn on attachments debugging\n" + + " <= 0 - turns off debugging\n" + + " >= 1 - turns on attachment message logging\n", + HandleDebugAttachments); } // TODO: Should probably be subscribing to CloseClient too, but this doesn't yet give us IClientAPI } + private void HandleDebugAttachments(string module, string[] args) + { + int debugLevel; + + if (!(args.Length == 3 && int.TryParse(args[2], out debugLevel))) + { + MainConsole.Instance.OutputFormat("Usage: debug attachments [0|1]"); + } + else + { + DebugLevel = debugLevel; + MainConsole.Instance.OutputFormat( + "Set event queue debug level to {0} in {1}", DebugLevel, m_scene.Name); + } + } + /// /// Listen for client triggered running state changes so that we can persist the script's object if necessary. /// @@ -196,14 +224,16 @@ namespace OpenSim.Region.CoreModules.Avatar.Attachments if (sp.GetAttachments().Count > 0) { -// m_log.DebugFormat( -// "[ATTACHMENTS MODULE]: Not doing simulator-side attachment rez for {0} in {1} as their viewer has already rezzed attachments", -// m_scene.Name, sp.Name); + if (DebugLevel > 0) + m_log.DebugFormat( + "[ATTACHMENTS MODULE]: Not doing simulator-side attachment rez for {0} in {1} as their viewer has already rezzed attachments", + m_scene.Name, sp.Name); return; } -// m_log.DebugFormat("[ATTACHMENTS MODULE]: Rezzing any attachments for {0} from simulator-side", sp.Name); + if (DebugLevel > 0) + m_log.DebugFormat("[ATTACHMENTS MODULE]: Rezzing any attachments for {0} from simulator-side", sp.Name); List attachments = sp.Appearance.GetAttachments(); foreach (AvatarAttachment attach in attachments) @@ -245,7 +275,8 @@ namespace OpenSim.Region.CoreModules.Avatar.Attachments if (!Enabled) return; -// m_log.DebugFormat("[ATTACHMENTS MODULE]: Saving changed attachments for {0}", sp.Name); + if (DebugLevel > 0) + m_log.DebugFormat("[ATTACHMENTS MODULE]: Saving changed attachments for {0}", sp.Name); List attachments = sp.GetAttachments(); @@ -278,9 +309,10 @@ namespace OpenSim.Region.CoreModules.Avatar.Attachments if (!Enabled) return; -// m_log.DebugFormat( -// "[ATTACHMENTS MODULE]: Deleting attachments from scene {0} for {1}, silent = {2}", -// m_scene.RegionInfo.RegionName, sp.Name, silent); + if (DebugLevel > 0) + m_log.DebugFormat( + "[ATTACHMENTS MODULE]: Deleting attachments from scene {0} for {1}, silent = {2}", + m_scene.RegionInfo.RegionName, sp.Name, silent); foreach (SceneObjectGroup sop in sp.GetAttachments()) { @@ -313,9 +345,10 @@ namespace OpenSim.Region.CoreModules.Avatar.Attachments { if (group.GetSittingAvatarsCount() != 0) { -// m_log.WarnFormat( -// "[ATTACHMENTS MODULE]: Ignoring request to attach {0} {1} to {2} on {3} since {4} avatars are still sitting on it", -// group.Name, group.LocalId, sp.Name, attachmentPt, group.GetSittingAvatarsCount()); + if (DebugLevel > 0) + m_log.WarnFormat( + "[ATTACHMENTS MODULE]: Ignoring request to attach {0} {1} to {2} on {3} since {4} avatars are still sitting on it", + group.Name, group.LocalId, sp.Name, attachmentPt, group.GetSittingAvatarsCount()); return false; } @@ -351,9 +384,10 @@ namespace OpenSim.Region.CoreModules.Avatar.Attachments if (attachments.Contains(group)) { -// m_log.WarnFormat( -// "[ATTACHMENTS MODULE]: Ignoring request to attach {0} {1} to {2} on {3} since it's already attached", -// group.Name, group.LocalId, sp.Name, AttachmentPt); + if (DebugLevel > 0) + m_log.WarnFormat( + "[ATTACHMENTS MODULE]: Ignoring request to attach {0} {1} to {2} on {3} since it's already attached", + group.Name, group.LocalId, sp.Name, attachmentPt); return false; } @@ -418,9 +452,10 @@ namespace OpenSim.Region.CoreModules.Avatar.Attachments if (!Enabled) return null; -// m_log.DebugFormat( -// "[ATTACHMENTS MODULE]: RezSingleAttachmentFromInventory to point {0} from item {1} for {2} in {3}", -// (AttachmentPoint)AttachmentPt, itemID, sp.Name, m_scene.Name); + if (DebugLevel > 0) + m_log.DebugFormat( + "[ATTACHMENTS MODULE]: RezSingleAttachmentFromInventory to point {0} from item {1} for {2} in {3}", + (AttachmentPoint)AttachmentPt, itemID, sp.Name, m_scene.Name); bool append = (AttachmentPt & 0x80) != 0; AttachmentPt &= 0x7f; @@ -444,9 +479,10 @@ namespace OpenSim.Region.CoreModules.Avatar.Attachments // if (sp.Appearance.GetAttachmentForItem(itemID) != null) if (alreadyOn) { -// m_log.WarnFormat( -// "[ATTACHMENTS MODULE]: Ignoring request by {0} to wear item {1} at {2} since it is already worn", -// sp.Name, itemID, AttachmentPt); + if (DebugLevel > 0) + m_log.DebugFormat( + "[ATTACHMENTS MODULE]: Ignoring request by {0} to wear item {1} at {2} since it is already worn", + sp.Name, itemID, AttachmentPt); return null; } @@ -459,7 +495,8 @@ namespace OpenSim.Region.CoreModules.Avatar.Attachments if (!Enabled) return; - // m_log.DebugFormat("[ATTACHMENTS MODULE]: Rezzing multiple attachments from inventory for {0}", sp.Name); + if (DebugLevel > 0) + m_log.DebugFormat("[ATTACHMENTS MODULE]: Rezzing multiple attachments from inventory for {0}", sp.Name); foreach (KeyValuePair rez in rezlist) { @@ -477,9 +514,10 @@ namespace OpenSim.Region.CoreModules.Avatar.Attachments if (!Enabled) return; -// m_log.DebugFormat( -// "[ATTACHMENTS MODULE]: DetachSingleAttachmentToGround() for {0}, object {1}", -// sp.UUID, soLocalId); + if (DebugLevel > 0) + m_log.DebugFormat( + "[ATTACHMENTS MODULE]: DetachSingleAttachmentToGround() for {0}, object {1}", + sp.UUID, soLocalId); SceneObjectGroup so = m_scene.GetGroupByPrim(soLocalId); @@ -495,9 +533,10 @@ namespace OpenSim.Region.CoreModules.Avatar.Attachments if (inventoryID == UUID.Zero) return; -// m_log.DebugFormat( -// "[ATTACHMENTS MODULE]: In DetachSingleAttachmentToGround(), object is {0} {1}, associated item is {2}", -// so.Name, so.LocalId, inventoryID); + if (DebugLevel > 0) + m_log.DebugFormat( + "[ATTACHMENTS MODULE]: In DetachSingleAttachmentToGround(), object is {0} {1}, associated item is {2}", + so.Name, so.LocalId, inventoryID); lock (sp.AttachmentsSyncLock) { @@ -552,9 +591,10 @@ namespace OpenSim.Region.CoreModules.Avatar.Attachments return; } -// m_log.DebugFormat( -// "[ATTACHMENTS MODULE]: Detaching object {0} {1} (FromItemID {2}) for {3} in {4}", -// so.Name, so.LocalId, so.FromItemID, sp.Name, m_scene.Name); + if (DebugLevel > 0) + m_log.DebugFormat( + "[ATTACHMENTS MODULE]: Detaching object {0} {1} (FromItemID {2}) for {3} in {4}", + so.Name, so.LocalId, so.FromItemID, sp.Name, m_scene.Name); // Scripts MUST be snapshotted before the object is // removed from the scene because doing otherwise will @@ -680,12 +720,12 @@ namespace OpenSim.Region.CoreModules.Avatar.Attachments grp.HasGroupChanged = false; // Prevent it being saved over and over } -// else -// { -// m_log.DebugFormat( -// "[ATTACHMENTS MODULE]: Don't need to update asset for unchanged attachment {0}, attachpoint {1}", -// grp.UUID, grp.AttachmentPoint); -// } + else if (DebugLevel > 0) + { + m_log.DebugFormat( + "[ATTACHMENTS MODULE]: Don't need to update asset for unchanged attachment {0}, attachpoint {1}", + grp.UUID, grp.AttachmentPoint); + } } /// @@ -703,9 +743,10 @@ namespace OpenSim.Region.CoreModules.Avatar.Attachments private void AttachToAgent( IScenePresence sp, SceneObjectGroup so, uint attachmentpoint, Vector3 attachOffset, bool silent) { -// m_log.DebugFormat( -// "[ATTACHMENTS MODULE]: Adding attachment {0} to avatar {1} in pt {2} pos {3} {4}", -// so.Name, sp.Name, attachmentpoint, attachOffset, so.RootPart.AttachedPos); + if (DebugLevel > 0) + m_log.DebugFormat( + "[ATTACHMENTS MODULE]: Adding attachment {0} to avatar {1} in pt {2} pos {3} {4}", + so.Name, sp.Name, attachmentpoint, attachOffset, so.RootPart.AttachedPos); so.DetachFromBackup(); @@ -730,9 +771,10 @@ namespace OpenSim.Region.CoreModules.Avatar.Attachments { if (so.HasPrivateAttachmentPoint) { -// m_log.DebugFormat( -// "[ATTACHMENTS MODULE]: Killing private HUD {0} for avatars other than {1} at attachment point {2}", -// so.Name, sp.Name, so.AttachmentPoint); + if (DebugLevel > 0) + m_log.DebugFormat( + "[ATTACHMENTS MODULE]: Killing private HUD {0} for avatars other than {1} at attachment point {2}", + so.Name, sp.Name, so.AttachmentPoint); // As this scene object can now only be seen by the attaching avatar, tell everybody else in the // scene that it's no longer in their awareness. @@ -766,9 +808,10 @@ namespace OpenSim.Region.CoreModules.Avatar.Attachments if (m_invAccessModule == null) return null; - // m_log.DebugFormat( - // "[ATTACHMENTS MODULE]: Called AddSceneObjectAsAttachment for object {0} {1} for {2}", - // grp.Name, grp.LocalId, remoteClient.Name); + if (DebugLevel > 0) + m_log.DebugFormat( + "[ATTACHMENTS MODULE]: Called AddSceneObjectAsAttachment for object {0} {1} for {2}", + grp.Name, grp.LocalId, sp.Name); InventoryItemBase newItem = m_invAccessModule.CopyToInventory( @@ -877,9 +920,10 @@ namespace OpenSim.Region.CoreModules.Avatar.Attachments return null; } -// m_log.DebugFormat( -// "[ATTACHMENTS MODULE]: Rezzed single object {0} for attachment to {1} on point {2} in {3}", -// objatt.Name, sp.Name, attachmentPt, m_scene.Name); + if (DebugLevel > 0) + m_log.DebugFormat( + "[ATTACHMENTS MODULE]: Rezzed single object {0} for attachment to {1} on point {2} in {3}", + objatt.Name, sp.Name, attachmentPt, m_scene.Name); // HasGroupChanged is being set from within RezObject. Ideally it would be set by the caller. objatt.HasGroupChanged = false; @@ -949,9 +993,10 @@ namespace OpenSim.Region.CoreModules.Avatar.Attachments bool changed = sp.Appearance.SetAttachment((int)AttachmentPt | attFlag, itemID, item.AssetID); if (changed && m_scene.AvatarFactory != null) { -// m_log.DebugFormat( -// "[ATTACHMENTS MODULE]: Queueing appearance save for {0}, attachment {1} point {2} in ShowAttachInUserInventory()", -// sp.Name, att.Name, AttachmentPt); + if (DebugLevel > 0) + m_log.DebugFormat( + "[ATTACHMENTS MODULE]: Queueing appearance save for {0}, attachment {1} point {2} in ShowAttachInUserInventory()", + sp.Name, att.Name, AttachmentPt); m_scene.AvatarFactory.QueueAppearanceSave(sp.UUID); } @@ -966,9 +1011,10 @@ namespace OpenSim.Region.CoreModules.Avatar.Attachments if (!Enabled) return null; - // m_log.DebugFormat( - // "[ATTACHMENTS MODULE]: Rezzing attachment to point {0} from item {1} for {2}", - // (AttachmentPoint)AttachmentPt, itemID, remoteClient.Name); + if (DebugLevel > 0) + m_log.DebugFormat( + "[ATTACHMENTS MODULE]: Rezzing attachment to point {0} from item {1} for {2}", + (AttachmentPoint)AttachmentPt, itemID, remoteClient.Name); ScenePresence sp = m_scene.GetScenePresence(remoteClient.AgentId); @@ -999,9 +1045,10 @@ namespace OpenSim.Region.CoreModules.Avatar.Attachments private void Client_OnObjectAttach(IClientAPI remoteClient, uint objectLocalID, uint AttachmentPt, bool silent) { -// m_log.DebugFormat( -// "[ATTACHMENTS MODULE]: Attaching object local id {0} to {1} point {2} from ground (silent = {3})", -// objectLocalID, remoteClient.Name, AttachmentPt, silent); + if (DebugLevel > 0) + m_log.DebugFormat( + "[ATTACHMENTS MODULE]: Attaching object local id {0} to {1} point {2} from ground (silent = {3})", + objectLocalID, remoteClient.Name, AttachmentPt, silent); if (!Enabled) return; @@ -1036,9 +1083,10 @@ namespace OpenSim.Region.CoreModules.Avatar.Attachments // Calls attach with a Zero position if (AttachObject(sp, part.ParentGroup, AttachmentPt, false, false, append)) { -// m_log.Debug( -// "[ATTACHMENTS MODULE]: Saving avatar attachment. AgentID: " + remoteClient.AgentId -// + ", AttachmentPoint: " + AttachmentPt); + if (DebugLevel > 0) + m_log.Debug( + "[ATTACHMENTS MODULE]: Saving avatar attachment. AgentID: " + remoteClient.AgentId + + ", AttachmentPoint: " + AttachmentPt); // Save avatar attachment information m_scene.EventManager.TriggerOnAttach(objectLocalID, part.ParentGroup.FromItemID, remoteClient.AgentId); @@ -1095,4 +1143,4 @@ namespace OpenSim.Region.CoreModules.Avatar.Attachments #endregion } -} +} \ No newline at end of file From c92654fb43f303da8e1623f9fff8a404aad72374 Mon Sep 17 00:00:00 2001 From: "Justin Clark-Casey (justincc)" Date: Thu, 28 Mar 2013 23:57:35 +0000 Subject: [PATCH 32/40] Stop attempts to update/add existing attachments in user inventory when teleporting between regions. This appears to resolve issues on teleport where attachments disappear or become labelled as invalid within user inventory. --- .../Avatar/Attachments/AttachmentsModule.cs | 31 +++++++++---------- .../Tests/AttachmentsModuleTests.cs | 10 +++--- .../Interfaces/IAttachmentsModule.cs | 6 ++-- .../Attachments/TempAttachmentsModule.cs | 2 +- 4 files changed, 25 insertions(+), 24 deletions(-) diff --git a/OpenSim/Region/CoreModules/Avatar/Attachments/AttachmentsModule.cs b/OpenSim/Region/CoreModules/Avatar/Attachments/AttachmentsModule.cs index c78f5b321e..b7f4303ec1 100644 --- a/OpenSim/Region/CoreModules/Avatar/Attachments/AttachmentsModule.cs +++ b/OpenSim/Region/CoreModules/Avatar/Attachments/AttachmentsModule.cs @@ -322,12 +322,13 @@ namespace OpenSim.Region.CoreModules.Avatar.Attachments sp.ClearAttachments(); } - public bool AttachObject(IScenePresence sp, SceneObjectGroup group, uint attachmentPt, bool silent, bool temp, bool append) + public bool AttachObject( + IScenePresence sp, SceneObjectGroup group, uint attachmentPt, bool silent, bool addToInventory, bool append) { if (!Enabled) return false; - return AttachObjectInternal(sp, group, attachmentPt, silent, temp, true, append); + return AttachObjectInternal(sp, group, attachmentPt, silent, addToInventory, true, append); } /// @@ -338,10 +339,11 @@ namespace OpenSim.Region.CoreModules.Avatar.Attachments /// The object to attach. /// /// - /// + /// If true then add object to user inventory. /// If true then scripts are resumed on the attached object. + /// Append to attachment point rather than replace. private bool AttachObjectInternal( - IScenePresence sp, SceneObjectGroup group, uint attachmentPt, bool silent, bool temp, bool resumeScripts, bool append) + IScenePresence sp, SceneObjectGroup group, uint attachmentPt, bool silent, bool addToInventory, bool resumeScripts, bool append) { if (group.GetSittingAvatarsCount() != 0) { @@ -412,8 +414,8 @@ namespace OpenSim.Region.CoreModules.Avatar.Attachments lock (sp.AttachmentsSyncLock) { - if (sp.PresenceType != PresenceType.Npc) - UpdateUserInventoryWithAttachment(sp, group, attachmentPt, temp, append); + if (addToInventory && sp.PresenceType != PresenceType.Npc) + UpdateUserInventoryWithAttachment(sp, group, attachmentPt, append); AttachToAgent(sp, group, attachmentPt, attachPos, silent); @@ -432,19 +434,16 @@ namespace OpenSim.Region.CoreModules.Avatar.Attachments return true; } - private void UpdateUserInventoryWithAttachment(IScenePresence sp, SceneObjectGroup group, uint attachmentPt, bool temp, bool append) + private void UpdateUserInventoryWithAttachment(IScenePresence sp, SceneObjectGroup group, uint attachmentPt, bool append) { List attachments = sp.GetAttachments(attachmentPt); // Add the new attachment to inventory if we don't already have it. - if (!temp) - { - UUID newAttachmentItemID = group.FromItemID; - if (newAttachmentItemID == UUID.Zero) - newAttachmentItemID = AddSceneObjectAsNewAttachmentInInv(sp, group).ID; + UUID newAttachmentItemID = group.FromItemID; + if (newAttachmentItemID == UUID.Zero) + newAttachmentItemID = AddSceneObjectAsNewAttachmentInInv(sp, group).ID; - ShowAttachInUserInventory(sp, attachmentPt, newAttachmentItemID, group, append); - } + ShowAttachInUserInventory(sp, attachmentPt, newAttachmentItemID, group, append); } public SceneObjectGroup RezSingleAttachmentFromInventory(IScenePresence sp, UUID itemID, uint AttachmentPt) @@ -939,7 +938,7 @@ namespace OpenSim.Region.CoreModules.Avatar.Attachments // This will throw if the attachment fails try { - AttachObjectInternal(sp, objatt, attachmentPt, false, false, true, append); + AttachObjectInternal(sp, objatt, attachmentPt, false, true, true, append); } catch (Exception e) { @@ -1081,7 +1080,7 @@ namespace OpenSim.Region.CoreModules.Avatar.Attachments AttachmentPt &= 0x7f; // Calls attach with a Zero position - if (AttachObject(sp, part.ParentGroup, AttachmentPt, false, false, append)) + if (AttachObject(sp, part.ParentGroup, AttachmentPt, false, true, append)) { if (DebugLevel > 0) m_log.Debug( diff --git a/OpenSim/Region/CoreModules/Avatar/Attachments/Tests/AttachmentsModuleTests.cs b/OpenSim/Region/CoreModules/Avatar/Attachments/Tests/AttachmentsModuleTests.cs index c8c594d99d..6e4262e405 100644 --- a/OpenSim/Region/CoreModules/Avatar/Attachments/Tests/AttachmentsModuleTests.cs +++ b/OpenSim/Region/CoreModules/Avatar/Attachments/Tests/AttachmentsModuleTests.cs @@ -197,7 +197,7 @@ namespace OpenSim.Region.CoreModules.Avatar.Attachments.Tests SceneObjectGroup so = SceneHelpers.AddSceneObject(scene, attName, sp.UUID); m_numberOfAttachEventsFired = 0; - scene.AttachmentsModule.AttachObject(sp, so, (uint)AttachmentPoint.Chest, false, false, false); + scene.AttachmentsModule.AttachObject(sp, so, (uint)AttachmentPoint.Chest, false, true, false); // Check status on scene presence Assert.That(sp.HasAttachments(), Is.True); @@ -244,7 +244,7 @@ namespace OpenSim.Region.CoreModules.Avatar.Attachments.Tests SceneObjectGroup so = SceneHelpers.AddSceneObject(scene, "att1", sp.UUID); m_numberOfAttachEventsFired = 0; - scene.AttachmentsModule.AttachObject(sp, so, (uint)AttachmentPoint.Default, false, false, false); + scene.AttachmentsModule.AttachObject(sp, so, (uint)AttachmentPoint.Default, false, true, false); // Check status on scene presence Assert.That(sp.HasAttachments(), Is.True); @@ -277,7 +277,7 @@ namespace OpenSim.Region.CoreModules.Avatar.Attachments.Tests // Test wearing a different attachment from the ground. { - scene.AttachmentsModule.AttachObject(sp, so2, (uint)AttachmentPoint.Default, false, false, false); + scene.AttachmentsModule.AttachObject(sp, so2, (uint)AttachmentPoint.Default, false, true, false); // Check status on scene presence Assert.That(sp.HasAttachments(), Is.True); @@ -310,7 +310,7 @@ namespace OpenSim.Region.CoreModules.Avatar.Attachments.Tests // Test rewearing an already worn attachment from ground. Nothing should happen. { - scene.AttachmentsModule.AttachObject(sp, so2, (uint)AttachmentPoint.Default, false, false, false); + scene.AttachmentsModule.AttachObject(sp, so2, (uint)AttachmentPoint.Default, false, true, false); // Check status on scene presence Assert.That(sp.HasAttachments(), Is.True); @@ -368,7 +368,7 @@ namespace OpenSim.Region.CoreModules.Avatar.Attachments.Tests sp2.AbsolutePosition = new Vector3(0, 0, 0); sp2.HandleAgentRequestSit(sp2.ControllingClient, sp2.UUID, so.UUID, Vector3.Zero); - scene.AttachmentsModule.AttachObject(sp, so, (uint)AttachmentPoint.Chest, false, false, false); + scene.AttachmentsModule.AttachObject(sp, so, (uint)AttachmentPoint.Chest, false, true, false); Assert.That(sp.HasAttachments(), Is.False); Assert.That(scene.GetSceneObjectGroups().Count, Is.EqualTo(1)); diff --git a/OpenSim/Region/Framework/Interfaces/IAttachmentsModule.cs b/OpenSim/Region/Framework/Interfaces/IAttachmentsModule.cs index 156a09d3ff..d9901bde79 100644 --- a/OpenSim/Region/Framework/Interfaces/IAttachmentsModule.cs +++ b/OpenSim/Region/Framework/Interfaces/IAttachmentsModule.cs @@ -80,14 +80,16 @@ namespace OpenSim.Region.Framework.Interfaces void DeleteAttachmentsFromScene(IScenePresence sp, bool silent); /// - /// Attach an object to an avatar + /// Attach an object to an avatar. /// /// /// /// /// + /// If true then add object to user inventory + /// Append to attachment point rather than replace. /// true if the object was successfully attached, false otherwise - bool AttachObject(IScenePresence sp, SceneObjectGroup grp, uint AttachmentPt, bool silent, bool temp, bool append); + bool AttachObject(IScenePresence sp, SceneObjectGroup grp, uint AttachmentPt, bool silent, bool addToInventory, bool append); /// /// Rez an attachment from user inventory and change inventory status to match. diff --git a/OpenSim/Region/OptionalModules/Avatar/Attachments/TempAttachmentsModule.cs b/OpenSim/Region/OptionalModules/Avatar/Attachments/TempAttachmentsModule.cs index 54c86ae82d..535bf67e2d 100644 --- a/OpenSim/Region/OptionalModules/Avatar/Attachments/TempAttachmentsModule.cs +++ b/OpenSim/Region/OptionalModules/Avatar/Attachments/TempAttachmentsModule.cs @@ -184,7 +184,7 @@ namespace OpenSim.Region.OptionalModules.Avatar.Attachments hostPart.ParentGroup.RootPart.ScheduleFullUpdate(); } - return attachmentsModule.AttachObject(target, hostPart.ParentGroup, (uint)attachmentPoint, false, true, true) ? 1 : 0; + return attachmentsModule.AttachObject(target, hostPart.ParentGroup, (uint)attachmentPoint, false, false, true) ? 1 : 0; } } } From 285bd3abc87aced43efa9519a5760d9dae3f50d9 Mon Sep 17 00:00:00 2001 From: "Justin Clark-Casey (justincc)" Date: Fri, 29 Mar 2013 00:49:55 +0000 Subject: [PATCH 33/40] Eliminate code which tries to restart attachment scripts in ScenePresence.MakeRootAgent(), since this is already done in AttachmentsModule --- .../Region/Framework/Scenes/ScenePresence.cs | 18 ------------------ 1 file changed, 18 deletions(-) diff --git a/OpenSim/Region/Framework/Scenes/ScenePresence.cs b/OpenSim/Region/Framework/Scenes/ScenePresence.cs index fcb2f6d1f2..6591fef7b5 100644 --- a/OpenSim/Region/Framework/Scenes/ScenePresence.cs +++ b/OpenSim/Region/Framework/Scenes/ScenePresence.cs @@ -968,24 +968,6 @@ namespace OpenSim.Region.Framework.Scenes Scene.AttachmentsModule.RezAttachments(this); }); } - else - { - lock (m_attachments) - { - if (HasAttachments()) - { - m_log.DebugFormat( - "[SCENE PRESENCE]: Restarting scripts in attachments for {0} in {1}", Name, Scene.Name); - - // Resume scripts - foreach (SceneObjectGroup sog in m_attachments) - { - sog.RootPart.ParentGroup.CreateScriptInstances(0, false, m_scene.DefaultScriptEngine, GetStateSource()); - sog.ResumeScripts(); - } - } - } - } // send the animations of the other presences to me m_scene.ForEachRootScenePresence(delegate(ScenePresence presence) From d87ddf50fcd674fbd9aa8b8556bf57f2d285a3ba Mon Sep 17 00:00:00 2001 From: "Justin Clark-Casey (justincc)" Date: Fri, 29 Mar 2013 01:16:29 +0000 Subject: [PATCH 34/40] Try eliminating the pause before auto-reteleporting for a megaregion now that we're telepoting in a different way. On my own system, I can now eliminate the pause entirely and the reteleport happens whilst the teleport screen is still up. Trying this change to see if this is true for other people. --- .../Framework/EntityTransfer/EntityTransferModule.cs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferModule.cs b/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferModule.cs index 764c98216c..495b0a0f4d 100644 --- a/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferModule.cs +++ b/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferModule.cs @@ -1348,7 +1348,7 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer public void InformClientToInitiateTeleportToLocationAsync(ScenePresence agent, uint regionX, uint regionY, Vector3 position, Scene initiatingScene) { - Thread.Sleep(10000); +// Thread.Sleep(10000); m_log.DebugFormat( "[ENTITY TRANSFER MODULE]: Auto-reteleporting {0} to correct megaregion location {1},{2},{3} from {4}", From 4dfffa1df325c4b27a79e995585696cc20b6d905 Mon Sep 17 00:00:00 2001 From: "Justin Clark-Casey (justincc)" Date: Fri, 29 Mar 2013 01:31:37 +0000 Subject: [PATCH 35/40] Add Location (relative), Rotation (Relative) and Rotation (World) to "show part" and other related console commands --- .../CoreModules/World/Objects/Commands/ObjectCommandsModule.cs | 3 +++ 1 file changed, 3 insertions(+) diff --git a/OpenSim/Region/CoreModules/World/Objects/Commands/ObjectCommandsModule.cs b/OpenSim/Region/CoreModules/World/Objects/Commands/ObjectCommandsModule.cs index 28db407a47..e434b2eb69 100644 --- a/OpenSim/Region/CoreModules/World/Objects/Commands/ObjectCommandsModule.cs +++ b/OpenSim/Region/CoreModules/World/Objects/Commands/ObjectCommandsModule.cs @@ -597,6 +597,7 @@ namespace OpenSim.Region.CoreModules.World.Objects.Commands cdl.AddRow("LightFalloff", s.LightFalloff); cdl.AddRow("LightIntensity", s.LightIntensity); cdl.AddRow("LightRadius", s.LightRadius); + cdl.AddRow("Location (relative)", sop.RelativePosition); cdl.AddRow("Media", string.Format("{0} entries", s.Media != null ? s.Media.Count.ToString() : "n/a")); cdl.AddRow("PathBegin", s.PathBegin); cdl.AddRow("PathEnd", s.PathEnd); @@ -619,6 +620,8 @@ namespace OpenSim.Region.CoreModules.World.Objects.Commands cdl.AddRow("ProjectionFocus", s.ProjectionFocus); cdl.AddRow("ProjectionFOV", s.ProjectionFOV); cdl.AddRow("ProjectionTextureUUID", s.ProjectionTextureUUID); + cdl.AddRow("Rotation (Relative)", sop.RotationOffset); + cdl.AddRow("Rotation (World)", sop.GetWorldRotation()); cdl.AddRow("Scale", s.Scale); cdl.AddRow( "SculptData", From e89bcf4f773d95492b168376599f7530a6044e8f Mon Sep 17 00:00:00 2001 From: "Justin Clark-Casey (justincc)" Date: Fri, 29 Mar 2013 01:34:31 +0000 Subject: [PATCH 36/40] Revert "Try eliminating the pause before auto-reteleporting for a megaregion now that we're telepoting in a different way." Unfortunately fails on Nebadon's system right now. Needs investigation. May put in a temproary option for experimentation soon. This reverts commit d87ddf50fcd674fbd9aa8b8556bf57f2d285a3ba. --- .../Framework/EntityTransfer/EntityTransferModule.cs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferModule.cs b/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferModule.cs index 495b0a0f4d..764c98216c 100644 --- a/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferModule.cs +++ b/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferModule.cs @@ -1348,7 +1348,7 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer public void InformClientToInitiateTeleportToLocationAsync(ScenePresence agent, uint regionX, uint regionY, Vector3 position, Scene initiatingScene) { -// Thread.Sleep(10000); + Thread.Sleep(10000); m_log.DebugFormat( "[ENTITY TRANSFER MODULE]: Auto-reteleporting {0} to correct megaregion location {1},{2},{3} from {4}", From 23ae4c0a4d813763bcc39db7693850a21727d7f2 Mon Sep 17 00:00:00 2001 From: "Justin Clark-Casey (justincc)" Date: Fri, 29 Mar 2013 02:21:38 +0000 Subject: [PATCH 37/40] Fix bug where CHANGED_REGION and/or CHANGED_TELEPORT weren't firing for scripts in attachments. This was because the script resumption in AttachmentsModule was firing the attach event instead. Had to reinstate the code in 285bd3a do we can resume the scripts there instead, though the bug existed before its removal. This is to resolve http://opensimulator.org/mantis/view.php?id=6578 --- .../Avatar/Attachments/AttachmentsModule.cs | 2 +- OpenSim/Region/Framework/Scenes/Scene.cs | 5 ++++- .../Framework/Scenes/SceneObjectPart.cs | 4 ++++ .../Region/Framework/Scenes/ScenePresence.cs | 22 +++++++++++++++++++ 4 files changed, 31 insertions(+), 2 deletions(-) diff --git a/OpenSim/Region/CoreModules/Avatar/Attachments/AttachmentsModule.cs b/OpenSim/Region/CoreModules/Avatar/Attachments/AttachmentsModule.cs index b7f4303ec1..29a6478e62 100644 --- a/OpenSim/Region/CoreModules/Avatar/Attachments/AttachmentsModule.cs +++ b/OpenSim/Region/CoreModules/Avatar/Attachments/AttachmentsModule.cs @@ -328,7 +328,7 @@ namespace OpenSim.Region.CoreModules.Avatar.Attachments if (!Enabled) return false; - return AttachObjectInternal(sp, group, attachmentPt, silent, addToInventory, true, append); + return AttachObjectInternal(sp, group, attachmentPt, silent, addToInventory, false, append); } /// diff --git a/OpenSim/Region/Framework/Scenes/Scene.cs b/OpenSim/Region/Framework/Scenes/Scene.cs index 5337835325..911a3e4fc9 100644 --- a/OpenSim/Region/Framework/Scenes/Scene.cs +++ b/OpenSim/Region/Framework/Scenes/Scene.cs @@ -2739,7 +2739,10 @@ namespace OpenSim.Region.Framework.Scenes // "[ATTACHMENT]: Attach to avatar {0} at position {1}", sp.UUID, grp.AbsolutePosition); RootPrim.RemFlag(PrimFlags.TemporaryOnRez); - + + // We must currently not resume scripts at this stage since AttachmentsModule does not have the + // information that this is due to a teleport/border cross rather than an ordinary attachment. + // We currently do this in Scene.MakeRootAgent() instead. if (AttachmentsModule != null) AttachmentsModule.AttachObject(sp, grp, 0, false, false, true); } diff --git a/OpenSim/Region/Framework/Scenes/SceneObjectPart.cs b/OpenSim/Region/Framework/Scenes/SceneObjectPart.cs index 27325c554c..847df03bce 100644 --- a/OpenSim/Region/Framework/Scenes/SceneObjectPart.cs +++ b/OpenSim/Region/Framework/Scenes/SceneObjectPart.cs @@ -3203,6 +3203,10 @@ namespace OpenSim.Region.Framework.Scenes /// public void SetScriptEvents(UUID scriptid, int events) { +// m_log.DebugFormat( +// "[SCENE OBJECT PART]: Set script events for script with id {0} on {1}/{2} to {3} in {4}", +// scriptid, Name, ParentGroup.Name, events, ParentGroup.Scene.Name); + // scriptEvents oldparts; lock (m_scriptEvents) { diff --git a/OpenSim/Region/Framework/Scenes/ScenePresence.cs b/OpenSim/Region/Framework/Scenes/ScenePresence.cs index 6591fef7b5..4930a396ba 100644 --- a/OpenSim/Region/Framework/Scenes/ScenePresence.cs +++ b/OpenSim/Region/Framework/Scenes/ScenePresence.cs @@ -968,6 +968,28 @@ namespace OpenSim.Region.Framework.Scenes Scene.AttachmentsModule.RezAttachments(this); }); } + else + { + // We need to restart scripts here so that they receive the correct changed events (CHANGED_TELEPORT + // and CHANGED_REGION) when the attachments have been rezzed in the new region. This cannot currently + // be done in AttachmentsModule.CopyAttachments(AgentData ad, IScenePresence sp) itself since we are + // not transporting the required data. + lock (m_attachments) + { + if (HasAttachments()) + { + m_log.DebugFormat( + "[SCENE PRESENCE]: Restarting scripts in attachments for {0} in {1}", Name, Scene.Name); + + // Resume scripts + foreach (SceneObjectGroup sog in m_attachments) + { + sog.RootPart.ParentGroup.CreateScriptInstances(0, false, m_scene.DefaultScriptEngine, GetStateSource()); + sog.ResumeScripts(); + } + } + } + } // send the animations of the other presences to me m_scene.ForEachRootScenePresence(delegate(ScenePresence presence) From 023faa227ef72a3701dc5fbfc46ab5f831c54953 Mon Sep 17 00:00:00 2001 From: "Justin Clark-Casey (justincc)" Date: Fri, 29 Mar 2013 23:10:28 +0000 Subject: [PATCH 38/40] Check viewer 2/3 attachment calls against avatar appearance attachment data rather than actually attached objects By checking against the grid's Avatar data, we can ignore viewer side attachments but still initiate these calls simulator-side. Initiating simulator-side is always necessary for version 1 viewers. This is a further commit to resolve http://opensimulator.org/mantis/view.php?id=6581 --- .../Avatar/Attachments/AttachmentsModule.cs | 36 +++++++++---------- .../Tests/AttachmentsModuleTests.cs | 6 ++-- .../Region/Framework/Scenes/ScenePresence.cs | 7 ++-- 3 files changed, 23 insertions(+), 26 deletions(-) diff --git a/OpenSim/Region/CoreModules/Avatar/Attachments/AttachmentsModule.cs b/OpenSim/Region/CoreModules/Avatar/Attachments/AttachmentsModule.cs index 29a6478e62..4b53ee0fe4 100644 --- a/OpenSim/Region/CoreModules/Avatar/Attachments/AttachmentsModule.cs +++ b/OpenSim/Region/CoreModules/Avatar/Attachments/AttachmentsModule.cs @@ -256,10 +256,8 @@ namespace OpenSim.Region.CoreModules.Avatar.Attachments { // If we're an NPC then skip all the item checks and manipulations since we don't have an // inventory right now. - if (sp.PresenceType == PresenceType.Npc) - RezSingleAttachmentFromInventoryInternal(sp, UUID.Zero, attach.AssetID, p, true); - else - RezSingleAttachmentFromInventory(sp, attach.ItemID, p | (uint)0x80); + RezSingleAttachmentFromInventoryInternal( + sp, sp.PresenceType == PresenceType.Npc ? UUID.Zero : attach.ItemID, attach.AssetID, p | (uint)0x80); } catch (Exception e) { @@ -456,26 +454,21 @@ namespace OpenSim.Region.CoreModules.Avatar.Attachments "[ATTACHMENTS MODULE]: RezSingleAttachmentFromInventory to point {0} from item {1} for {2} in {3}", (AttachmentPoint)AttachmentPt, itemID, sp.Name, m_scene.Name); - bool append = (AttachmentPt & 0x80) != 0; - AttachmentPt &= 0x7f; - - // Viewer 2/3 sometimes asks to re-wear items that are already worn (and show up in it's inventory as such). - // This often happens during login - not sure the exact reason. - // For now, we will ignore the request. Unfortunately, this means that we need to dig through all the - // ScenePresence attachments. We can't use the data in AvatarAppearance because that's present at login - // before anything has actually been attached. + // We check the attachments in the avatar appearance here rather than the objects attached to the + // ScenePresence itself so that we can ignore calls by viewer 2/3 to attach objects on startup. We are + // already doing this in ScenePresence.MakeRootAgent(). Simulator-side attaching needs to be done + // because pre-outfit folder viewers (most version 1 viewers) require it. bool alreadyOn = false; - List existingAttachments = sp.GetAttachments(); - foreach (SceneObjectGroup so in existingAttachments) + List existingAttachments = sp.Appearance.GetAttachments(); + foreach (AvatarAttachment existingAttachment in existingAttachments) { - if (so.FromItemID == itemID) + if (existingAttachment.ItemID == itemID) { alreadyOn = true; break; } } -// if (sp.Appearance.GetAttachmentForItem(itemID) != null) if (alreadyOn) { if (DebugLevel > 0) @@ -486,7 +479,7 @@ namespace OpenSim.Region.CoreModules.Avatar.Attachments return null; } - return RezSingleAttachmentFromInventoryInternal(sp, itemID, UUID.Zero, AttachmentPt, append); + return RezSingleAttachmentFromInventoryInternal(sp, itemID, UUID.Zero, AttachmentPt); } public void RezMultipleAttachmentsFromInventory(IScenePresence sp, List> rezlist) @@ -495,7 +488,9 @@ namespace OpenSim.Region.CoreModules.Avatar.Attachments return; if (DebugLevel > 0) - m_log.DebugFormat("[ATTACHMENTS MODULE]: Rezzing multiple attachments from inventory for {0}", sp.Name); + m_log.DebugFormat( + "[ATTACHMENTS MODULE]: Rezzing {0} attachments from inventory for {1} in {2}", + rezlist.Count, sp.Name, m_scene.Name); foreach (KeyValuePair rez in rezlist) { @@ -894,11 +889,14 @@ namespace OpenSim.Region.CoreModules.Avatar.Attachments } protected SceneObjectGroup RezSingleAttachmentFromInventoryInternal( - IScenePresence sp, UUID itemID, UUID assetID, uint attachmentPt, bool append) + IScenePresence sp, UUID itemID, UUID assetID, uint attachmentPt) { if (m_invAccessModule == null) return null; + bool append = (attachmentPt & 0x80) != 0; + attachmentPt &= 0x7f; + SceneObjectGroup objatt; if (itemID != UUID.Zero) diff --git a/OpenSim/Region/CoreModules/Avatar/Attachments/Tests/AttachmentsModuleTests.cs b/OpenSim/Region/CoreModules/Avatar/Attachments/Tests/AttachmentsModuleTests.cs index 6e4262e405..25444e5171 100644 --- a/OpenSim/Region/CoreModules/Avatar/Attachments/Tests/AttachmentsModuleTests.cs +++ b/OpenSim/Region/CoreModules/Avatar/Attachments/Tests/AttachmentsModuleTests.cs @@ -130,7 +130,9 @@ namespace OpenSim.Region.CoreModules.Avatar.Attachments.Tests config.AddConfig("Modules"); config.Configs["Modules"].Set("InventoryAccessModule", "BasicInventoryAccessModule"); - modules.Add(new AttachmentsModule()); + AttachmentsModule attMod = new AttachmentsModule(); + attMod.DebugLevel = 1; + modules.Add(attMod); modules.Add(new BasicInventoryAccessModule()); } @@ -728,7 +730,7 @@ namespace OpenSim.Region.CoreModules.Avatar.Attachments.Tests public void TestRezAttachmentsOnAvatarEntrance() { TestHelpers.InMethod(); -// log4net.Config.XmlConfigurator.Configure(); +// TestHelpers.EnableLogging(); Scene scene = CreateTestScene(); UserAccount ua1 = UserAccountHelpers.CreateUserWithInventory(scene, 0x1); diff --git a/OpenSim/Region/Framework/Scenes/ScenePresence.cs b/OpenSim/Region/Framework/Scenes/ScenePresence.cs index 4930a396ba..215a6893df 100644 --- a/OpenSim/Region/Framework/Scenes/ScenePresence.cs +++ b/OpenSim/Region/Framework/Scenes/ScenePresence.cs @@ -955,15 +955,12 @@ namespace OpenSim.Region.Framework.Scenes { // Viewers which have a current outfit folder will actually rez their own attachments. However, // viewers without (e.g. v1 viewers) will not, so we still need to make this call. - // - // However, we leave a 5 second pause to try and avoid a clash with viewers that are rezzing - // attachments themselves. This should then mean that this call ends up doing nothing. if (Scene.AttachmentsModule != null) Util.FireAndForget( o => { - if (PresenceType != PresenceType.Npc && Util.FireAndForgetMethod != FireAndForgetMethod.None) - System.Threading.Thread.Sleep(5000); +// if (PresenceType != PresenceType.Npc && Util.FireAndForgetMethod != FireAndForgetMethod.None) +// System.Threading.Thread.Sleep(7000); Scene.AttachmentsModule.RezAttachments(this); }); From cbc9ae898c474295567532c668644d09b698d59b Mon Sep 17 00:00:00 2001 From: Kevin Cozens Date: Wed, 27 Mar 2013 17:26:17 -0400 Subject: [PATCH 39/40] Added missing functionality (mainly custom headers) to llHTTPRequest. --- .../HttpRequest/ScriptsHttpRequests.cs | 73 +++++++- .../Framework/Interfaces/IHttpRequests.cs | 3 + .../Shared/Api/Implementation/LSL_Api.cs | 169 ++++++++++++------ .../Shared/Api/Runtime/LSL_Constants.cs | 15 +- prebuild.xml | 1 + 5 files changed, 196 insertions(+), 65 deletions(-) diff --git a/OpenSim/Region/CoreModules/Scripting/HttpRequest/ScriptsHttpRequests.cs b/OpenSim/Region/CoreModules/Scripting/HttpRequest/ScriptsHttpRequests.cs index a676971a28..c2e37c44dd 100644 --- a/OpenSim/Region/CoreModules/Scripting/HttpRequest/ScriptsHttpRequests.cs +++ b/OpenSim/Region/CoreModules/Scripting/HttpRequest/ScriptsHttpRequests.cs @@ -187,6 +187,45 @@ namespace OpenSim.Region.CoreModules.Scripting.HttpRequest case (int)HttpRequestConstants.HTTP_VERIFY_CERT: htc.HttpVerifyCert = (int.Parse(parms[i + 1]) != 0); break; + + case (int)HttpRequestConstants.HTTP_VERBOSE_THROTTLE: + + // TODO implement me + break; + + case (int)HttpRequestConstants.HTTP_CUSTOM_HEADER: + //Parameters are in pairs and custom header takes + //arguments in pairs so adjust for header marker. + ++i; + + //Maximum of 8 headers are allowed based on the + //Second Life documentation for llHTTPRequest. + for (int count = 1; count <= 8; ++count) + { + //Not enough parameters remaining for a header? + if (parms.Length - i < 2) + break; + + //Have we reached the end of the list of headers? + //End is marked by a string with a single digit. + //We already know we have at least one parameter + //so it is safe to do this check at top of loop. + if (Char.IsDigit(parms[i][0])) + break; + + if (htc.HttpCustomHeaders == null) + htc.HttpCustomHeaders = new List(); + + htc.HttpCustomHeaders.Add(parms[i]); + htc.HttpCustomHeaders.Add(parms[i+1]); + + i += 2; + } + break; + + case (int)HttpRequestConstants.HTTP_PRAGMA_NO_CACHE: + htc.HttpPragmaNoCache = (int.Parse(parms[i + 1]) != 0); + break; } } } @@ -328,9 +367,12 @@ namespace OpenSim.Region.CoreModules.Scripting.HttpRequest // public const int HTTP_METHOD = 0; // public const int HTTP_MIMETYPE = 1; // public const int HTTP_VERIFY_CERT = 3; + // public const int HTTP_VERBOSE_THROTTLE = 4; + // public const int HTTP_CUSTOM_HEADER = 5; + // public const int HTTP_PRAGMA_NO_CACHE = 6; private bool _finished; public bool Finished - { + { get { return _finished; } } // public int HttpBodyMaxLen = 2048; // not implemented @@ -340,11 +382,14 @@ namespace OpenSim.Region.CoreModules.Scripting.HttpRequest public string HttpMIMEType = "text/plain;charset=utf-8"; public int HttpTimeout; public bool HttpVerifyCert = true; + //public bool HttpVerboseThrottle = true; // not implemented + public List HttpCustomHeaders = null; + public bool HttpPragmaNoCache = true; private Thread httpThread; // Request info private UUID _itemID; - public UUID ItemID + public UUID ItemID { get { return _itemID; } set { _itemID = value; } @@ -360,7 +405,7 @@ namespace OpenSim.Region.CoreModules.Scripting.HttpRequest public string proxyexcepts; public string OutboundBody; private UUID _reqID; - public UUID ReqID + public UUID ReqID { get { return _reqID; } set { _reqID = value; } @@ -401,7 +446,7 @@ namespace OpenSim.Region.CoreModules.Scripting.HttpRequest Request.Method = HttpMethod; Request.ContentType = HttpMIMEType; - if(!HttpVerifyCert) + if (!HttpVerifyCert) { // We could hijack Connection Group Name to identify // a desired security exception. But at the moment we'll use a dummy header instead. @@ -412,14 +457,24 @@ namespace OpenSim.Region.CoreModules.Scripting.HttpRequest // { // Request.ConnectionGroupName="Verify"; // } - if (proxyurl != null && proxyurl.Length > 0) + if (!HttpPragmaNoCache) { - if (proxyexcepts != null && proxyexcepts.Length > 0) + Request.Headers.Add("Pragma", "no-cache"); + } + if (HttpCustomHeaders != null) + { + for (int i = 0; i < HttpCustomHeaders.Count; i += 2) + Request.Headers.Add(HttpCustomHeaders[i], + HttpCustomHeaders[i+1]); + } + if (proxyurl != null && proxyurl.Length > 0) + { + if (proxyexcepts != null && proxyexcepts.Length > 0) { string[] elist = proxyexcepts.Split(';'); Request.Proxy = new WebProxy(proxyurl, true, elist); - } - else + } + else { Request.Proxy = new WebProxy(proxyurl, true); } @@ -432,7 +487,7 @@ namespace OpenSim.Region.CoreModules.Scripting.HttpRequest Request.Headers[entry.Key] = entry.Value; // Encode outbound data - if (OutboundBody.Length > 0) + if (OutboundBody.Length > 0) { byte[] data = Util.UTF8.GetBytes(OutboundBody); diff --git a/OpenSim/Region/Framework/Interfaces/IHttpRequests.cs b/OpenSim/Region/Framework/Interfaces/IHttpRequests.cs index de0f2a32aa..eb6c5ac56c 100644 --- a/OpenSim/Region/Framework/Interfaces/IHttpRequests.cs +++ b/OpenSim/Region/Framework/Interfaces/IHttpRequests.cs @@ -36,6 +36,9 @@ namespace OpenSim.Region.Framework.Interfaces HTTP_MIMETYPE = 1, HTTP_BODY_MAXLENGTH = 2, HTTP_VERIFY_CERT = 3, + HTTP_VERBOSE_THROTTLE = 4, + HTTP_CUSTOM_HEADER = 5, + HTTP_PRAGMA_NO_CACHE = 6 } public interface IHttpRequestModule diff --git a/OpenSim/Region/ScriptEngine/Shared/Api/Implementation/LSL_Api.cs b/OpenSim/Region/ScriptEngine/Shared/Api/Implementation/LSL_Api.cs index bf84b16e19..969243c8ae 100644 --- a/OpenSim/Region/ScriptEngine/Shared/Api/Implementation/LSL_Api.cs +++ b/OpenSim/Region/ScriptEngine/Shared/Api/Implementation/LSL_Api.cs @@ -67,6 +67,7 @@ using LSL_Rotation = OpenSim.Region.ScriptEngine.Shared.LSL_Types.Quaternion; using LSL_String = OpenSim.Region.ScriptEngine.Shared.LSL_Types.LSLString; using LSL_Vector = OpenSim.Region.ScriptEngine.Shared.LSL_Types.Vector3; using System.Reflection; +using System.Linq; using PermissionMask = OpenSim.Framework.PermissionMask; namespace OpenSim.Region.ScriptEngine.Shared.Api @@ -92,8 +93,8 @@ namespace OpenSim.Region.ScriptEngine.Shared.Api /// /// Used for script sleeps when we are using co-operative script termination. /// - /// null if co-operative script termination is not active - WaitHandle m_coopSleepHandle; + /// null if co-operative script termination is not active + WaitHandle m_coopSleepHandle; /// /// The item that hosts this script @@ -119,6 +120,23 @@ namespace OpenSim.Region.ScriptEngine.Shared.Api protected int EMAIL_PAUSE_TIME = 20; // documented delay value for smtp. protected ISoundModule m_SoundModule = null; + //An array of HTTP/1.1 headers that are not allowed to be used + //as custom headers by llHTTPRequest. + private string[] HttpStandardHeaders = + { + "Accept", "Accept-Charset", "Accept-Encoding", "Accept-Language", + "Accept-Ranges", "Age", "Allow", "Authorization", "Cache-Control", + "Connection", "Content-Encoding", "Content-Language", + "Content-Length", "Content-Location", "Content-MD5", + "Content-Range", "Content-Type", "Date", "ETag", "Expect", + "Expires", "From", "Host", "If-Match", "If-Modified-Since", + "If-None-Match", "If-Range", "If-Unmodified-Since", "Last-Modified", + "Location", "Max-Forwards", "Pragma", "Proxy-Authenticate", + "Proxy-Authorization", "Range", "Referer", "Retry-After", "Server", + "TE", "Trailer", "Transfer-Encoding", "Upgrade", "User-Agent", + "Vary", "Via", "Warning", "WWW-Authenticate" + }; + public void Initialize( IScriptEngine scriptEngine, SceneObjectPart host, TaskInventoryItem item, WaitHandle coopSleepHandle) { @@ -303,7 +321,7 @@ namespace OpenSim.Region.ScriptEngine.Shared.Api /// If the linkset has more than one entity and a linknum greater than zero but equal to or less than the number /// of entities, then the entity which corresponds to that linknum is returned. /// Otherwise, if a positive linknum is given which is greater than the number of entities in the linkset, then - /// null is returned. + /// null is returned. /// public ISceneEntity GetLinkEntity(int linknum) { @@ -1557,7 +1575,7 @@ namespace OpenSim.Region.ScriptEngine.Shared.Api if (tex.FaceTextures[i] != null) { tex.FaceTextures[i].Shiny = sval; - tex.FaceTextures[i].Bump = bump;; + tex.FaceTextures[i].Bump = bump; } tex.DefaultTexture.Shiny = sval; tex.DefaultTexture.Bump = bump; @@ -1666,7 +1684,7 @@ namespace OpenSim.Region.ScriptEngine.Shared.Api texcolor.A = Util.Clip((float)alpha, 0.0f, 1.0f); tex.DefaultTexture.RGBA = texcolor; } - + part.UpdateTextureEntry(tex.GetBytes()); return; } @@ -1787,7 +1805,7 @@ namespace OpenSim.Region.ScriptEngine.Shared.Api rgb.x = texcolor.R; rgb.y = texcolor.G; rgb.z = texcolor.B; - + return rgb; } else @@ -1819,12 +1837,12 @@ namespace OpenSim.Region.ScriptEngine.Shared.Api { UUID textureID = new UUID(); - textureID = ScriptUtils.GetAssetIdFromItemName(m_host, texture, (int)AssetType.Texture); - if (textureID == UUID.Zero) - { - if (!UUID.TryParse(texture, out textureID)) - return; - } + textureID = ScriptUtils.GetAssetIdFromItemName(m_host, texture, (int)AssetType.Texture); + if (textureID == UUID.Zero) + { + if (!UUID.TryParse(texture, out textureID)) + return; + } Primitive.TextureEntry tex = part.Shape.Textures; @@ -2021,7 +2039,7 @@ namespace OpenSim.Region.ScriptEngine.Shared.Api // IF YOU GET REGION CROSSINGS WORKING WITH THIS FUNCTION, REPLACE THE WORKAROUND. // // This workaround is to prevent silent failure of this function. - // According to the specification on the SL Wiki, providing a position outside of the + // According to the specification on the SL Wiki, providing a position outside of the if (pos.x < 0 || pos.x > Constants.RegionSize || pos.y < 0 || pos.y > Constants.RegionSize) { return 0; @@ -2230,7 +2248,7 @@ namespace OpenSim.Region.ScriptEngine.Shared.Api { return llGetRootRotation(); } - + m_host.AddScriptLPS(1); Quaternion q = m_host.GetWorldRotation(); return new LSL_Rotation(q.X, q.Y, q.Z, q.W); @@ -2919,7 +2937,7 @@ namespace OpenSim.Region.ScriptEngine.Shared.Api // we need to convert from a vector describing // the angles of rotation in radians into rotation value LSL_Rotation rot = llEuler2Rot(angle); - + // Per discussion with Melanie, for non-physical objects llLookAt appears to simply // set the rotation of the object, copy that behavior PhysicsActor pa = m_host.PhysActor; @@ -2996,7 +3014,7 @@ namespace OpenSim.Region.ScriptEngine.Shared.Api if (!UUID.TryParse(id, out objectID)) objectID = UUID.Zero; - + if (objectID == UUID.Zero && name == "") return; @@ -3182,19 +3200,19 @@ namespace OpenSim.Region.ScriptEngine.Shared.Api msg.RegionID = World.RegionInfo.RegionID.Guid;//RegionID.Guid; Vector3 pos = m_host.AbsolutePosition; - msg.binaryBucket + msg.binaryBucket = Util.StringToBytes256( - "{0}/{1}/{2}/{3}", - World.RegionInfo.RegionName, - (int)Math.Floor(pos.X), - (int)Math.Floor(pos.Y), + "{0}/{1}/{2}/{3}", + World.RegionInfo.RegionName, + (int)Math.Floor(pos.X), + (int)Math.Floor(pos.Y), (int)Math.Floor(pos.Z)); if (m_TransferModule != null) { m_TransferModule.SendInstantMessage(msg, delegate(bool success) {}); } - + ScriptSleep(2000); } @@ -3319,7 +3337,7 @@ namespace OpenSim.Region.ScriptEngine.Shared.Api public void llRotLookAt(LSL_Rotation target, double strength, double damping) { m_host.AddScriptLPS(1); - + // Per discussion with Melanie, for non-physical objects llLookAt appears to simply // set the rotation of the object, copy that behavior PhysicsActor pa = m_host.PhysActor; @@ -4313,7 +4331,7 @@ namespace OpenSim.Region.ScriptEngine.Shared.Api public void llCollisionSound(string impact_sound, double impact_volume) { m_host.AddScriptLPS(1); - + // TODO: Parameter check logic required. m_host.CollisionSound = ScriptUtils.GetAssetIdFromKeyOrItemName(m_host, impact_sound, AssetType.Sound); m_host.CollisionSoundVolume = (float)impact_volume; @@ -5008,7 +5026,7 @@ namespace OpenSim.Region.ScriptEngine.Shared.Api // SL spits out an empty string for types other than key & string // At the time of patching, LSL_Key is currently LSL_String, // so the OR check may be a little redundant, but it's being done - // for completion and should LSL_Key ever be implemented + // for completion and should LSL_Key ever be implemented // as it's own struct else if (!(src.Data[index] is LSL_String || src.Data[index] is LSL_Key)) @@ -5144,8 +5162,8 @@ namespace OpenSim.Region.ScriptEngine.Shared.Api { m_host.AddScriptLPS(1); - return string.Join(", ", - (new List(src.Data)).ConvertAll(o => + return string.Join(", ", + (new List(src.Data)).ConvertAll(o => { return o.ToString(); }).ToArray()); @@ -6188,7 +6206,7 @@ namespace OpenSim.Region.ScriptEngine.Shared.Api SetParticleSystem(m_host, rules); } - private void SetParticleSystem(SceneObjectPart part, LSL_List rules) + private void SetParticleSystem(SceneObjectPart part, LSL_List rules) { if (rules.Length == 0) { @@ -6425,7 +6443,7 @@ namespace OpenSim.Region.ScriptEngine.Shared.Api m_host.OwnerID, m_host.Name, destID, (byte)InstantMessageDialog.TaskInventoryOffered, false, string.Format("'{0}'", category), -// We won't go so far as to add a SLURL, but this is the format used by LL as of 2012-10-06 +// We won't go so far as to add a SLURL, but this is the format used by LL as of 2012-10-06 // false, string.Format("'{0}' ( http://slurl.com/secondlife/{1}/{2}/{3}/{4} )", category, World.Name, (int)pos.X, (int)pos.Y, (int)pos.Z), folderID, false, pos, bucket, false); @@ -6540,12 +6558,12 @@ namespace OpenSim.Region.ScriptEngine.Shared.Api public LSL_String llAvatarOnLinkSitTarget(int linknum) { m_host.AddScriptLPS(1); - if(linknum == ScriptBaseClass.LINK_SET || + if(linknum == ScriptBaseClass.LINK_SET || linknum == ScriptBaseClass.LINK_ALL_CHILDREN || linknum == ScriptBaseClass.LINK_ALL_OTHERS) return UUID.Zero.ToString(); - + List parts = GetLinkParts(linknum); - if (parts.Count == 0) return UUID.Zero.ToString(); + if (parts.Count == 0) return UUID.Zero.ToString(); return parts[0].SitTargetAvatar.ToString(); } @@ -6922,7 +6940,7 @@ namespace OpenSim.Region.ScriptEngine.Shared.Api hollow = 0.70f; } } - // Otherwise, hollow is limited to 95%. + // Otherwise, hollow is limited to 95%. else { if (hollow > 0.95f) @@ -7956,8 +7974,8 @@ namespace OpenSim.Region.ScriptEngine.Shared.Api LSL_List remaining = null; while (true) - { - if (entity is SceneObjectPart) + { + if (entity is SceneObjectPart) remaining = GetPrimParams((SceneObjectPart)entity, rules, ref result); else remaining = GetAgentParams((ScenePresence)entity, rules, ref result); @@ -8138,7 +8156,7 @@ namespace OpenSim.Region.ScriptEngine.Shared.Api res.Add(new LSL_Float(1)); break; - case (int)ScriptBaseClass.PRIM_ROT_LOCAL: + case (int)ScriptBaseClass.PRIM_ROT_LOCAL: res.Add(new LSL_Rotation(sp.Rotation)); break; @@ -8282,16 +8300,16 @@ namespace OpenSim.Region.ScriptEngine.Shared.Api res.Add(new LSL_Vector(Shape.PathTaperX / 100.0, Shape.PathTaperY / 100.0, 0)); // float revolutions - res.Add(new LSL_Float(Math.Round(Shape.PathRevolutions * 0.015d, 2, MidpointRounding.AwayFromZero)) + 1.0d); + res.Add(new LSL_Float(Math.Round(Shape.PathRevolutions * 0.015d, 2, MidpointRounding.AwayFromZero)) + 1.0d); // Slightly inaccurate, because an unsigned byte is being used to represent - // the entire range of floating-point values from 1.0 through 4.0 (which is how + // the entire range of floating-point values from 1.0 through 4.0 (which is how // SL does it). // - // Using these formulas to store and retrieve PathRevolutions, it is not - // possible to use all values between 1.00 and 4.00. For instance, you can't + // Using these formulas to store and retrieve PathRevolutions, it is not + // possible to use all values between 1.00 and 4.00. For instance, you can't // represent 1.10. You can represent 1.09 and 1.11, but not 1.10. So, if you // use llSetPrimitiveParams to set revolutions to 1.10 and then retreive them - // with llGetPrimitiveParams, you'll retrieve 1.09. You can also see a similar + // with llGetPrimitiveParams, you'll retrieve 1.09. You can also see a similar // behavior in the viewer as you cannot set 1.10. The viewer jumps to 1.11. // In SL, llSetPrimitveParams and llGetPrimitiveParams can set and get a value // such as 1.10. So, SL must store and retreive the actual user input rather @@ -8528,7 +8546,7 @@ namespace OpenSim.Region.ScriptEngine.Shared.Api case (int)ScriptBaseClass.PRIM_DESC: res.Add(new LSL_String(part.Description)); break; - case (int)ScriptBaseClass.PRIM_ROT_LOCAL: + case (int)ScriptBaseClass.PRIM_ROT_LOCAL: res.Add(new LSL_Rotation(part.RotationOffset)); break; case (int)ScriptBaseClass.PRIM_POS_LOCAL: @@ -10415,9 +10433,60 @@ namespace OpenSim.Region.ScriptEngine.Shared.Api IHttpRequestModule httpScriptMod = m_ScriptEngine.World.RequestModuleInterface(); List param = new List(); - foreach (object o in parameters.Data) + bool ok; + Int32 flag; + + for (int i = 0; i < parameters.Data.Length; i += 2) { - param.Add(o.ToString()); + ok = Int32.TryParse(parameters.Data[i].ToString(), out flag); + if (!ok || flag < 0 || + flag > (int)HttpRequestConstants.HTTP_PRAGMA_NO_CACHE) + { + throw new ScriptException("Parameter " + i.ToString() + " is an invalid flag"); + } + + param.Add(parameters.Data[i].ToString()); //Add parameter flag + + if (flag != (int)HttpRequestConstants.HTTP_CUSTOM_HEADER) + { + param.Add(parameters.Data[i+1].ToString()); //Add parameter value + } + else + { + //Parameters are in pairs and custom header takes + //arguments in pairs so adjust for header marker. + ++i; + + //Maximum of 8 headers are allowed based on the + //Second Life documentation for llHTTPRequest. + for (int count = 1; count <= 8; ++count) + { + //Enough parameters remaining for (another) header? + if (parameters.Data.Length - i < 2) + { + //There must be at least one name/value pair for custom header + if (count == 1) + throw new ScriptException("Missing name/value for custom header at parameter " + i.ToString()); + break; + } + + if (HttpStandardHeaders.Contains(parameters.Data[i].ToString(), StringComparer.OrdinalIgnoreCase)) + throw new ScriptException("Name is invalid as a custom header at parameter " + i.ToString()); + + param.Add(parameters.Data[i].ToString()); + param.Add(parameters.Data[i+1].ToString()); + + //Have we reached the end of the list of headers? + //End is marked by a string with a single digit. + if (i+2 >= parameters.Data.Length || + Char.IsDigit(parameters.Data[i].ToString()[0])) + { + break; + } + + i += 2; + } + } } Vector3 position = m_host.AbsolutePosition; @@ -10527,12 +10596,12 @@ namespace OpenSim.Region.ScriptEngine.Shared.Api public LSL_Integer llGetParcelPrimCount(LSL_Vector pos, int category, int sim_wide) { m_host.AddScriptLPS(1); - + ILandObject lo = World.LandChannel.GetLandObject((float)pos.x, (float)pos.y); if (lo == null) return 0; - + IPrimCounts pc = lo.PrimCounts; if (sim_wide != ScriptBaseClass.FALSE) @@ -10562,7 +10631,7 @@ namespace OpenSim.Region.ScriptEngine.Shared.Api else if (category == ScriptBaseClass.PARCEL_COUNT_TEMP) return 0; // counts not implemented yet } - + return 0; } @@ -10905,7 +10974,7 @@ namespace OpenSim.Region.ScriptEngine.Shared.Api return ret; } } - + return new LSL_List(); } @@ -11282,7 +11351,7 @@ namespace OpenSim.Region.ScriptEngine.Shared.Api // Vector3 bc = group.AbsolutePosition - rayEnd; double d = Math.Abs(Vector3.Mag(Vector3.Cross(ab, ac)) / Vector3.Distance(rayStart, rayEnd)); - + // Too far off ray, don't bother if (d > radius) return; @@ -11611,7 +11680,7 @@ namespace OpenSim.Region.ScriptEngine.Shared.Api else { ScenePresence sp = World.GetScenePresence(result.ConsumerID); - /// It it a boy? a girl? + /// It it a boy? a girl? if (sp != null) itemID = sp.UUID; } diff --git a/OpenSim/Region/ScriptEngine/Shared/Api/Runtime/LSL_Constants.cs b/OpenSim/Region/ScriptEngine/Shared/Api/Runtime/LSL_Constants.cs index bd66ba3700..dc5ef139e7 100644 --- a/OpenSim/Region/ScriptEngine/Shared/Api/Runtime/LSL_Constants.cs +++ b/OpenSim/Region/ScriptEngine/Shared/Api/Runtime/LSL_Constants.cs @@ -355,6 +355,9 @@ namespace OpenSim.Region.ScriptEngine.Shared.ScriptBase public const int HTTP_MIMETYPE = 1; public const int HTTP_BODY_MAXLENGTH = 2; public const int HTTP_VERIFY_CERT = 3; + public const int HTTP_VERBOSE_THROTTLE = 4; + public const int HTTP_CUSTOM_HEADER = 5; + public const int HTTP_PRAGMA_NO_CACHE = 6; public const int PRIM_MATERIAL = 2; public const int PRIM_PHYSICS = 3; @@ -635,7 +638,7 @@ namespace OpenSim.Region.ScriptEngine.Shared.ScriptBase public const int TOUCH_INVALID_FACE = -1; public static readonly vector TOUCH_INVALID_TEXCOORD = new vector(-1.0, -1.0, 0.0); public static readonly vector TOUCH_INVALID_VECTOR = ZERO_VECTOR; - + // constants for llGetPrimMediaParams/llSetPrimMediaParams public const int PRIM_MEDIA_ALT_IMAGE_ENABLE = 0; public const int PRIM_MEDIA_CONTROLS = 1; @@ -652,15 +655,15 @@ namespace OpenSim.Region.ScriptEngine.Shared.ScriptBase public const int PRIM_MEDIA_WHITELIST = 12; public const int PRIM_MEDIA_PERMS_INTERACT = 13; public const int PRIM_MEDIA_PERMS_CONTROL = 14; - + public const int PRIM_MEDIA_CONTROLS_STANDARD = 0; public const int PRIM_MEDIA_CONTROLS_MINI = 1; - + public const int PRIM_MEDIA_PERM_NONE = 0; public const int PRIM_MEDIA_PERM_OWNER = 1; public const int PRIM_MEDIA_PERM_GROUP = 2; public const int PRIM_MEDIA_PERM_ANYONE = 4; - + public const int PRIM_PHYSICS_SHAPE_TYPE = 30; public const int PRIM_PHYSICS_SHAPE_PRIM = 0; public const int PRIM_PHYSICS_SHAPE_CONVEX = 2; @@ -688,7 +691,7 @@ namespace OpenSim.Region.ScriptEngine.Shared.ScriptBase public const string TEXTURE_PLYWOOD = "89556747-24cb-43ed-920b-47caed15465f"; public const string TEXTURE_TRANSPARENT = "8dcd4a48-2d37-4909-9f78-f7a9eb4ef903"; public const string TEXTURE_MEDIA = "8b5fec65-8d8d-9dc5-cda8-8fdf2716e361"; - + // Constants for osGetRegionStats public const int STATS_TIME_DILATION = 0; public const int STATS_SIM_FPS = 1; @@ -741,7 +744,7 @@ namespace OpenSim.Region.ScriptEngine.Shared.ScriptBase public static readonly LSLInteger RC_GET_ROOT_KEY = 2; public static readonly LSLInteger RC_GET_LINK_NUM = 4; - public static readonly LSLInteger RCERR_UNKNOWN = -1; + public static readonly LSLInteger RCERR_UNKNOWN = -1; public static readonly LSLInteger RCERR_SIM_PERF_LOW = -2; public static readonly LSLInteger RCERR_CAST_TIME_EXCEEDED = 3; diff --git a/prebuild.xml b/prebuild.xml index 7a4455d0a6..050fe0f401 100644 --- a/prebuild.xml +++ b/prebuild.xml @@ -2183,6 +2183,7 @@ ../../../../../../bin/ + From 76629289f001ef4bd0bac204e0f46907ebe5df5e Mon Sep 17 00:00:00 2001 From: "Justin Clark-Casey (justincc)" Date: Fri, 29 Mar 2013 23:59:21 +0000 Subject: [PATCH 40/40] refactor: move the append magic number processing for attachments back up into RezSingleAttachmentFromInventory from RezSingleAttachmentFromInventoryInternal() done in commit 023faa2 --- .../Avatar/Attachments/AttachmentsModule.cs | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/OpenSim/Region/CoreModules/Avatar/Attachments/AttachmentsModule.cs b/OpenSim/Region/CoreModules/Avatar/Attachments/AttachmentsModule.cs index 4b53ee0fe4..eec7ee54a5 100644 --- a/OpenSim/Region/CoreModules/Avatar/Attachments/AttachmentsModule.cs +++ b/OpenSim/Region/CoreModules/Avatar/Attachments/AttachmentsModule.cs @@ -257,7 +257,7 @@ namespace OpenSim.Region.CoreModules.Avatar.Attachments // If we're an NPC then skip all the item checks and manipulations since we don't have an // inventory right now. RezSingleAttachmentFromInventoryInternal( - sp, sp.PresenceType == PresenceType.Npc ? UUID.Zero : attach.ItemID, attach.AssetID, p | (uint)0x80); + sp, sp.PresenceType == PresenceType.Npc ? UUID.Zero : attach.ItemID, attach.AssetID, p, true); } catch (Exception e) { @@ -479,7 +479,10 @@ namespace OpenSim.Region.CoreModules.Avatar.Attachments return null; } - return RezSingleAttachmentFromInventoryInternal(sp, itemID, UUID.Zero, AttachmentPt); + bool append = (AttachmentPt & 0x80) != 0; + AttachmentPt &= 0x7f; + + return RezSingleAttachmentFromInventoryInternal(sp, itemID, UUID.Zero, AttachmentPt, append); } public void RezMultipleAttachmentsFromInventory(IScenePresence sp, List> rezlist) @@ -889,14 +892,11 @@ namespace OpenSim.Region.CoreModules.Avatar.Attachments } protected SceneObjectGroup RezSingleAttachmentFromInventoryInternal( - IScenePresence sp, UUID itemID, UUID assetID, uint attachmentPt) + IScenePresence sp, UUID itemID, UUID assetID, uint attachmentPt, bool append) { if (m_invAccessModule == null) return null; - bool append = (attachmentPt & 0x80) != 0; - attachmentPt &= 0x7f; - SceneObjectGroup objatt; if (itemID != UUID.Zero)