Add naive implementation of controlled incoming HG attachments to manage load.
Instead of processing all incoming attachment scene object concurrently, process them consecutively to eliminate potential overload from this source. This is a naive implementation because it does not currently account for slow foreign asset services. Although it may take longer, this approach may also improve attachment visibility for HG avatars since the scene object is now always added to the scene after receiving assets from the foreign service and not before.mb-throttle-test
parent
ec8d21c434
commit
1d19e1bbd0
|
@ -2700,5 +2700,69 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer
|
||||||
}
|
}
|
||||||
#endregion
|
#endregion
|
||||||
|
|
||||||
|
public virtual bool HandleIncomingSceneObject(SceneObjectGroup so, Vector3 newPosition)
|
||||||
|
{
|
||||||
|
// If the user is banned, we won't let any of their objects
|
||||||
|
// enter. Period.
|
||||||
|
//
|
||||||
|
if (Scene.RegionInfo.EstateSettings.IsBanned(so.OwnerID))
|
||||||
|
{
|
||||||
|
m_log.DebugFormat(
|
||||||
|
"[ENTITY TRANSFER MODULE]: Denied prim crossing of {0} {1} into {2} for banned avatar {3}",
|
||||||
|
so.Name, so.UUID, Scene.Name, so.OwnerID);
|
||||||
|
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (newPosition != Vector3.Zero)
|
||||||
|
so.RootPart.GroupPosition = newPosition;
|
||||||
|
|
||||||
|
if (!Scene.AddSceneObject(so))
|
||||||
|
{
|
||||||
|
m_log.DebugFormat(
|
||||||
|
"[ENTITY TRANSFER MODULE]: Problem adding scene object {0} {1} into {2} ",
|
||||||
|
so.Name, so.UUID, Scene.Name);
|
||||||
|
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!so.IsAttachment)
|
||||||
|
{
|
||||||
|
// FIXME: It would be better to never add the scene object at all rather than add it and then delete
|
||||||
|
// it
|
||||||
|
if (!Scene.Permissions.CanObjectEntry(so.UUID, true, so.AbsolutePosition))
|
||||||
|
{
|
||||||
|
// Deny non attachments based on parcel settings
|
||||||
|
//
|
||||||
|
m_log.Info("[ENTITY TRANSFER MODULE]: Denied prim crossing because of parcel settings");
|
||||||
|
|
||||||
|
Scene.DeleteSceneObject(so, false);
|
||||||
|
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
// For attachments, we need to wait until the agent is root
|
||||||
|
// before we restart the scripts, or else some functions won't work.
|
||||||
|
so.RootPart.ParentGroup.CreateScriptInstances(
|
||||||
|
0, false, Scene.DefaultScriptEngine, GetStateSource(so));
|
||||||
|
|
||||||
|
so.ResumeScripts();
|
||||||
|
|
||||||
|
if (so.RootPart.KeyframeMotion != null)
|
||||||
|
so.RootPart.KeyframeMotion.UpdateSceneObject(so);
|
||||||
|
}
|
||||||
|
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
private int GetStateSource(SceneObjectGroup sog)
|
||||||
|
{
|
||||||
|
ScenePresence sp = Scene.GetScenePresence(sog.OwnerID);
|
||||||
|
|
||||||
|
if (sp != null)
|
||||||
|
return sp.GetStateSource();
|
||||||
|
|
||||||
|
return 2; // StateSource.PrimCrossing
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -153,33 +153,9 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer
|
||||||
if (m_Enabled)
|
if (m_Enabled)
|
||||||
{
|
{
|
||||||
scene.RegisterModuleInterface<IUserAgentVerificationModule>(this);
|
scene.RegisterModuleInterface<IUserAgentVerificationModule>(this);
|
||||||
scene.EventManager.OnIncomingSceneObject += OnIncomingSceneObject;
|
//scene.EventManager.OnIncomingSceneObject += OnIncomingSceneObject;
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void OnIncomingSceneObject(SceneObjectGroup so)
|
m_incomingSceneObjectEngine.Start();
|
||||||
{
|
|
||||||
if (!so.IsAttachment)
|
|
||||||
return;
|
|
||||||
|
|
||||||
if (so.AttachedAvatar == UUID.Zero || Scene.UserManagementModule.IsLocalGridUser(so.AttachedAvatar))
|
|
||||||
return;
|
|
||||||
|
|
||||||
// foreign user
|
|
||||||
AgentCircuitData aCircuit = Scene.AuthenticateHandler.GetAgentCircuitData(so.AttachedAvatar);
|
|
||||||
if (aCircuit != null && (aCircuit.teleportFlags & (uint)Constants.TeleportFlags.ViaHGLogin) != 0)
|
|
||||||
{
|
|
||||||
if (aCircuit.ServiceURLs != null && aCircuit.ServiceURLs.ContainsKey("AssetServRezerURI"))
|
|
||||||
{
|
|
||||||
string url = aCircuit.ServiceURLs["AssetServerURI"].ToString();
|
|
||||||
m_log.DebugFormat("[HG ENTITY TRANSFER MODULE]: Incoming attachment {0} for HG user {1} with asset server {2}", so.Name, so.AttachedAvatar, url);
|
|
||||||
Dictionary<UUID, sbyte> ids = new Dictionary<UUID, sbyte>();
|
|
||||||
HGUuidGatherer uuidGatherer = new HGUuidGatherer(Scene.AssetService, url);
|
|
||||||
uuidGatherer.GatherAssetUuids(so, ids);
|
|
||||||
|
|
||||||
foreach (KeyValuePair<UUID, sbyte> kvp in ids)
|
|
||||||
uuidGatherer.FetchAsset(kvp.Key);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -209,12 +185,15 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer
|
||||||
base.RemoveRegion(scene);
|
base.RemoveRegion(scene);
|
||||||
|
|
||||||
if (m_Enabled)
|
if (m_Enabled)
|
||||||
|
{
|
||||||
scene.UnregisterModuleInterface<IUserAgentVerificationModule>(this);
|
scene.UnregisterModuleInterface<IUserAgentVerificationModule>(this);
|
||||||
|
m_incomingSceneObjectEngine.Stop();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
#endregion
|
#endregion
|
||||||
|
|
||||||
#region HG overrides of IEntiryTransferModule
|
#region HG overrides of IEntityTransferModule
|
||||||
|
|
||||||
protected override GridRegion GetFinalDestination(GridRegion region, UUID agentID, string agentHomeURI, out string message)
|
protected override GridRegion GetFinalDestination(GridRegion region, UUID agentID, string agentHomeURI, out string message)
|
||||||
{
|
{
|
||||||
|
@ -561,6 +540,53 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private HGIncomingSceneObjectEngine m_incomingSceneObjectEngine = new HGIncomingSceneObjectEngine();
|
||||||
|
|
||||||
|
public override bool HandleIncomingSceneObject(SceneObjectGroup so, Vector3 newPosition)
|
||||||
|
{
|
||||||
|
// FIXME: We must make it so that we can use SOG.IsAttachment here. At the moment it is always null!
|
||||||
|
if (!so.IsAttachmentCheckFull())
|
||||||
|
return base.HandleIncomingSceneObject(so, newPosition);
|
||||||
|
|
||||||
|
// Equally, we can't use so.AttachedAvatar here.
|
||||||
|
if (so.OwnerID == UUID.Zero || Scene.UserManagementModule.IsLocalGridUser(so.OwnerID))
|
||||||
|
return base.HandleIncomingSceneObject(so, newPosition);
|
||||||
|
|
||||||
|
// foreign user
|
||||||
|
AgentCircuitData aCircuit = Scene.AuthenticateHandler.GetAgentCircuitData(so.OwnerID);
|
||||||
|
if (aCircuit != null && (aCircuit.teleportFlags & (uint)Constants.TeleportFlags.ViaHGLogin) != 0)
|
||||||
|
{
|
||||||
|
if (aCircuit.ServiceURLs != null && aCircuit.ServiceURLs.ContainsKey("AssetServerURI"))
|
||||||
|
{
|
||||||
|
m_incomingSceneObjectEngine.QueueRequest(
|
||||||
|
string.Format("HG UUID Gather for attachment {0} for {1}", so.Name, aCircuit.Name),
|
||||||
|
o =>
|
||||||
|
{
|
||||||
|
string url = aCircuit.ServiceURLs["AssetServerURI"].ToString();
|
||||||
|
m_log.DebugFormat(
|
||||||
|
"[HG ENTITY TRANSFER MODULE]: Incoming attachment {0} for HG user {1} with asset server {2}",
|
||||||
|
so.Name, so.AttachedAvatar, url);
|
||||||
|
|
||||||
|
Dictionary<UUID, sbyte> ids = new Dictionary<UUID, sbyte>();
|
||||||
|
HGUuidGatherer uuidGatherer = new HGUuidGatherer(Scene.AssetService, url);
|
||||||
|
uuidGatherer.GatherAssetUuids(so, ids);
|
||||||
|
|
||||||
|
foreach (KeyValuePair<UUID, sbyte> kvp in ids)
|
||||||
|
uuidGatherer.FetchAsset(kvp.Key);
|
||||||
|
|
||||||
|
base.HandleIncomingSceneObject(so, newPosition);
|
||||||
|
|
||||||
|
m_log.DebugFormat(
|
||||||
|
"[HG ENTITY TRANSFER MODULE]: Completed incoming attachment {0} for HG user {1} with asset server {2}",
|
||||||
|
so.Name, so.OwnerID, url);
|
||||||
|
},
|
||||||
|
null);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
#endregion
|
#endregion
|
||||||
|
|
||||||
#region IUserAgentVerificationModule
|
#region IUserAgentVerificationModule
|
||||||
|
|
|
@ -98,6 +98,8 @@ namespace OpenSim.Region.Framework.Interfaces
|
||||||
void Cross(SceneObjectGroup sog, Vector3 position, bool silent);
|
void Cross(SceneObjectGroup sog, Vector3 position, bool silent);
|
||||||
|
|
||||||
ScenePresence CrossAgentToNewRegionAsync(ScenePresence agent, Vector3 pos, GridRegion neighbourRegion, bool isFlying, string version);
|
ScenePresence CrossAgentToNewRegionAsync(ScenePresence agent, Vector3 pos, GridRegion neighbourRegion, bool isFlying, string version);
|
||||||
|
|
||||||
|
bool HandleIncomingSceneObject(SceneObjectGroup so, Vector3 newPosition);
|
||||||
}
|
}
|
||||||
|
|
||||||
public interface IUserAgentVerificationModule
|
public interface IUserAgentVerificationModule
|
||||||
|
|
|
@ -2623,48 +2623,8 @@ namespace OpenSim.Region.Framework.Scenes
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
// If the user is banned, we won't let any of their objects
|
if (!EntityTransferModule.HandleIncomingSceneObject(newObject, newPosition))
|
||||||
// enter. Period.
|
return false;
|
||||||
//
|
|
||||||
if (RegionInfo.EstateSettings.IsBanned(newObject.OwnerID))
|
|
||||||
{
|
|
||||||
m_log.InfoFormat("[INTERREGION]: Denied prim crossing for banned avatar {0}", newObject.OwnerID);
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (newPosition != Vector3.Zero)
|
|
||||||
newObject.RootPart.GroupPosition = newPosition;
|
|
||||||
|
|
||||||
if (!AddSceneObject(newObject))
|
|
||||||
{
|
|
||||||
m_log.DebugFormat(
|
|
||||||
"[INTERREGION]: Problem adding scene object {0} in {1} ", newObject.UUID, RegionInfo.RegionName);
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (!newObject.IsAttachment)
|
|
||||||
{
|
|
||||||
// FIXME: It would be better to never add the scene object at all rather than add it and then delete
|
|
||||||
// it
|
|
||||||
if (!Permissions.CanObjectEntry(newObject.UUID, true, newObject.AbsolutePosition))
|
|
||||||
{
|
|
||||||
// Deny non attachments based on parcel settings
|
|
||||||
//
|
|
||||||
m_log.Info("[INTERREGION]: Denied prim crossing because of parcel settings");
|
|
||||||
|
|
||||||
DeleteSceneObject(newObject, false);
|
|
||||||
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
// For attachments, we need to wait until the agent is root
|
|
||||||
// before we restart the scripts, or else some functions won't work.
|
|
||||||
newObject.RootPart.ParentGroup.CreateScriptInstances(0, false, DefaultScriptEngine, GetStateSource(newObject));
|
|
||||||
newObject.ResumeScripts();
|
|
||||||
|
|
||||||
if (newObject.RootPart.KeyframeMotion != null)
|
|
||||||
newObject.RootPart.KeyframeMotion.UpdateSceneObject(newObject);
|
|
||||||
}
|
|
||||||
|
|
||||||
// Do this as late as possible so that listeners have full access to the incoming object
|
// Do this as late as possible so that listeners have full access to the incoming object
|
||||||
EventManager.TriggerOnIncomingSceneObject(newObject);
|
EventManager.TriggerOnIncomingSceneObject(newObject);
|
||||||
|
@ -2733,16 +2693,6 @@ namespace OpenSim.Region.Framework.Scenes
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
private int GetStateSource(SceneObjectGroup sog)
|
|
||||||
{
|
|
||||||
ScenePresence sp = GetScenePresence(sog.OwnerID);
|
|
||||||
|
|
||||||
if (sp != null)
|
|
||||||
return sp.GetStateSource();
|
|
||||||
|
|
||||||
return 2; // StateSource.PrimCrossing
|
|
||||||
}
|
|
||||||
|
|
||||||
#endregion
|
#endregion
|
||||||
|
|
||||||
#region Add/Remove Avatar Methods
|
#region Add/Remove Avatar Methods
|
||||||
|
|
Loading…
Reference in New Issue