From a4caedceae4e4ceb4a2987b392a5aa8abc83a8c6 Mon Sep 17 00:00:00 2001 From: UbitUmarov Date: Sun, 31 Jul 2016 01:56:44 +0100 Subject: [PATCH 1/6] rename a few things to reduce confusion between regions wold location and grid location (a lot more elsewhere) --- OpenSim/Framework/Util.cs | 8 +++++--- .../Framework/EntityTransfer/EntityTransferModule.cs | 2 +- .../Shared/Api/Implementation/OSSL_Api.cs | 12 ++++++------ 3 files changed, 12 insertions(+), 10 deletions(-) diff --git a/OpenSim/Framework/Util.cs b/OpenSim/Framework/Util.cs index 1b3a4c3599..ccbe75efc6 100644 --- a/OpenSim/Framework/Util.cs +++ b/OpenSim/Framework/Util.cs @@ -377,9 +377,11 @@ namespace OpenSim.Framework return Utils.UIntsToLong(X, Y); } - public static ulong RegionLocToHandle(uint X, uint Y) + public static ulong RegionGridLocToHandle(uint X, uint Y) { - return Utils.UIntsToLong(Util.RegionToWorldLoc(X), Util.RegionToWorldLoc(Y)); + ulong handle = X << 40; // shift to higher half and mult by 256) + handle |= (Y << 8); // mult by 256) + return handle; } public static void RegionHandleToWorldLoc(ulong handle, out uint X, out uint Y) @@ -1303,7 +1305,7 @@ namespace OpenSim.Framework } catch (Exception e) { - m_log.WarnFormat("[UTILS]: Exception copying configuration file {0} to {1}: {2}", exampleConfigFile, configFile, e.Message); + m_log.WarnFormat("[UTILS]: Exception copying configuration file {0} to {1}: {2}", configFile, exampleConfigFile, e.Message); return false; } } diff --git a/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferModule.cs b/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferModule.cs index efc714fae0..9ee23d65bb 100644 --- a/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferModule.cs +++ b/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferModule.cs @@ -1588,7 +1588,7 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer agent.Scene.RequestTeleportLocation( agent.ControllingClient, - Util.RegionLocToHandle(regionX, regionY), + Util.RegionGridLocToHandle(regionX, regionY), position, agent.Lookat, (uint)Constants.TeleportFlags.ViaLocation); diff --git a/OpenSim/Region/ScriptEngine/Shared/Api/Implementation/OSSL_Api.cs b/OpenSim/Region/ScriptEngine/Shared/Api/Implementation/OSSL_Api.cs index 319f14c3bf..e525a2e134 100644 --- a/OpenSim/Region/ScriptEngine/Shared/Api/Implementation/OSSL_Api.cs +++ b/OpenSim/Region/ScriptEngine/Shared/Api/Implementation/OSSL_Api.cs @@ -852,19 +852,19 @@ namespace OpenSim.Region.ScriptEngine.Shared.Api } } - public void osTeleportAgent(string agent, int regionX, int regionY, LSL_Types.Vector3 position, LSL_Types.Vector3 lookat) + public void osTeleportAgent(string agent, int regionGridX, int regionGridY, LSL_Types.Vector3 position, LSL_Types.Vector3 lookat) { // High because there is no security check. High griefer potential // CheckThreatLevel(ThreatLevel.Severe, "osTeleportAgent"); - TeleportAgent(agent, regionX, regionY, position, lookat, false); + TeleportAgent(agent, regionGridX, regionGridY, position, lookat, false); } - private void TeleportAgent(string agent, int regionX, int regionY, + private void TeleportAgent(string agent, int regionGridX, int regionGridY, LSL_Types.Vector3 position, LSL_Types.Vector3 lookat, bool relaxRestrictions) { - ulong regionHandle = Util.RegionLocToHandle((uint)regionX, (uint)regionY); + ulong regionHandle = Util.RegionGridLocToHandle((uint)regionGridX, (uint)regionGridY); m_host.AddScriptLPS(1); UUID agentId = new UUID(); @@ -917,11 +917,11 @@ namespace OpenSim.Region.ScriptEngine.Shared.Api osTeleportOwner(World.RegionInfo.RegionName, position, lookat); } - public void osTeleportOwner(int regionX, int regionY, LSL_Types.Vector3 position, LSL_Types.Vector3 lookat) + public void osTeleportOwner(int regionGridX, int regionGridY, LSL_Types.Vector3 position, LSL_Types.Vector3 lookat) { CheckThreatLevel(ThreatLevel.None, "osTeleportOwner"); - TeleportAgent(m_host.OwnerID.ToString(), regionX, regionY, position, lookat, true); + TeleportAgent(m_host.OwnerID.ToString(), regionGridX, regionGridY, position, lookat, true); } /// From 598e4ed7c98e6eb07f9aaba7a5a9068ff9a4d099 Mon Sep 17 00:00:00 2001 From: UbitUmarov Date: Sun, 31 Jul 2016 02:53:35 +0100 Subject: [PATCH 2/6] rearrange handlers convertion math, harcoding the grid unit size of 256m, also inviting jit to use cpu barrel shifters. --- OpenSim/Framework/Util.cs | 34 +++++++++++++++++----------------- 1 file changed, 17 insertions(+), 17 deletions(-) diff --git a/OpenSim/Framework/Util.cs b/OpenSim/Framework/Util.cs index ccbe75efc6..5250d30483 100644 --- a/OpenSim/Framework/Util.cs +++ b/OpenSim/Framework/Util.cs @@ -368,13 +368,16 @@ namespace OpenSim.Framework return Utils.UIntsToLong(X, Y); } - // Regions are identified with a 'handle' made up of its region coordinates packed into a ulong. - // Several places rely on the ability to extract a region's location from its handle. - // Note the location is in 'world coordinates' (see below). - // Region handles are based on the lowest coordinate of the region so trim the passed x,y to be the regions 0,0. + // Regions are identified with a 'handle' made up of its world coordinates packed into a ulong. + // Region handles are based on the coordinate of the region corner with lower X and Y + // var regions need more work than this to get that right corner from a generic world position + // this corner must be on a grid point public static ulong RegionWorldLocToHandle(uint X, uint Y) { - return Utils.UIntsToLong(X, Y); + ulong handle = X & 0xffffff00; // make sure it matchs grid coord points. + handle <<= 32; // to higher half + handle |= (Y & 0xffffff00); + return handle; } public static ulong RegionGridLocToHandle(uint X, uint Y) @@ -387,30 +390,27 @@ namespace OpenSim.Framework public static void RegionHandleToWorldLoc(ulong handle, out uint X, out uint Y) { X = (uint)(handle >> 32); - Y = (uint)(handle & (ulong)uint.MaxValue); + Y = (uint)(handle & 0xfffffffful); } public static void RegionHandleToRegionLoc(ulong handle, out uint X, out uint Y) { - uint worldX, worldY; - RegionHandleToWorldLoc(handle, out worldX, out worldY); - X = WorldToRegionLoc(worldX); - Y = WorldToRegionLoc(worldY); + X = (uint)(handle >> 40) & 0x00ffffffu; // bring from higher half, divide by 256 and clean + Y = (uint)(handle >> 8) & 0x00ffffffu; // divide by 256 and clean + // if you trust the uint cast then the clean can be removed. } - // A region location can be 'world coordinates' (meters from zero) or 'region coordinates' - // (number of regions from zero). This measurement of regions relies on the legacy 256 region size. - // These routines exist to make what is being converted explicit so the next person knows what was meant. - // Convert a region's 'world coordinate' to its 'region coordinate'. + // A region location can be 'world coordinates' (meters) or 'region grid coordinates' + // grid coordinates have a fixed step of 256m as defined by viewers public static uint WorldToRegionLoc(uint worldCoord) { - return worldCoord / Constants.RegionSize; + return worldCoord >> 8; } - // Convert a region's 'region coordinate' to its 'world coordinate'. + // Convert a region's 'region grid coordinate' to its 'world coordinate'. public static uint RegionToWorldLoc(uint regionCoord) { - return regionCoord * Constants.RegionSize; + return regionCoord << 8; } public static T Clamp(T x, T min, T max) From 703e96b4cbaec3b499284accaeb1f6242e71d7e5 Mon Sep 17 00:00:00 2001 From: UbitUmarov Date: Sun, 31 Jul 2016 19:08:35 +0100 Subject: [PATCH 3/6] Change RegionInfoCache again... --- .../Grid/LocalGridServiceConnector.cs | 14 +- .../Grid/RegionInfoCache.cs | 684 ++++++++++-------- .../Grid/RemoteGridServiceConnector.cs | 14 +- 3 files changed, 401 insertions(+), 311 deletions(-) diff --git a/OpenSim/Region/CoreModules/ServiceConnectorsOut/Grid/LocalGridServiceConnector.cs b/OpenSim/Region/CoreModules/ServiceConnectorsOut/Grid/LocalGridServiceConnector.cs index d38ac9bc9b..7d8ae575ce 100644 --- a/OpenSim/Region/CoreModules/ServiceConnectorsOut/Grid/LocalGridServiceConnector.cs +++ b/OpenSim/Region/CoreModules/ServiceConnectorsOut/Grid/LocalGridServiceConnector.cs @@ -166,7 +166,7 @@ namespace OpenSim.Region.CoreModules.ServiceConnectorsOut.Grid if (!m_Enabled) return; - m_RegionInfoCache.Remove(scene.RegionInfo.ScopeID, scene.RegionInfo.RegionID); + m_RegionInfoCache.Remove(scene.RegionInfo.ScopeID, scene.RegionInfo.RegionHandle); scene.EventManager.OnRegionUp -= OnRegionUp; } @@ -220,16 +220,16 @@ namespace OpenSim.Region.CoreModules.ServiceConnectorsOut.Grid // be the base coordinate of the region. public GridRegion GetRegionByPosition(UUID scopeID, int x, int y) { + // try in cache by handler first - ulong regionHandle = Util.RegionWorldLocToHandle((uint)x, (uint)y); +// ulong regionHandle = Util.RegionWorldLocToHandle((uint)x, (uint)y); bool inCache = false; - GridRegion rinfo = m_RegionInfoCache.Get(scopeID, regionHandle, out inCache); - if (inCache) - return rinfo; +// GridRegion rinfo = m_RegionInfoCache.Get(scopeID, regionHandle, out inCache); +// if (inCache) +// return rinfo; - // try in cache by slower position next - rinfo = m_RegionInfoCache.Get(scopeID, x, y, out inCache); + GridRegion rinfo = m_RegionInfoCache.Get(scopeID, (uint)x, (uint)y, out inCache); if (inCache) return rinfo; diff --git a/OpenSim/Region/CoreModules/ServiceConnectorsOut/Grid/RegionInfoCache.cs b/OpenSim/Region/CoreModules/ServiceConnectorsOut/Grid/RegionInfoCache.cs index 8f3dfc1a2c..03fc9eae51 100644 --- a/OpenSim/Region/CoreModules/ServiceConnectorsOut/Grid/RegionInfoCache.cs +++ b/OpenSim/Region/CoreModules/ServiceConnectorsOut/Grid/RegionInfoCache.cs @@ -44,11 +44,14 @@ namespace OpenSim.Region.CoreModules.ServiceConnectorsOut.Grid // LogManager.GetLogger( // MethodBase.GetCurrentMethod().DeclaringType); - private RegionsExpiringCache m_Cache; + private static RegionsExpiringCache m_Cache; + private int numberInstances; public RegionInfoCache() { - m_Cache = new RegionsExpiringCache(); + if(m_Cache == null) + m_Cache = new RegionsExpiringCache(); + numberInstances++; } public void Cache(GridRegion rinfo) @@ -78,8 +81,7 @@ namespace OpenSim.Region.CoreModules.ServiceConnectorsOut.Grid if (rinfo == null) return; -// m_Cache.AddOrUpdate(scopeID, rinfo, CACHE_EXPIRATION_SECONDS); - m_Cache.Add(scopeID, rinfo, CACHE_EXPIRATION_SECONDS); // don't override local regions + m_Cache.AddOrUpdate(scopeID, rinfo, CACHE_EXPIRATION_SECONDS); } public void Cache(UUID scopeID, GridRegion rinfo, float expireSeconds) @@ -90,9 +92,14 @@ namespace OpenSim.Region.CoreModules.ServiceConnectorsOut.Grid m_Cache.AddOrUpdate(scopeID, rinfo, expireSeconds); } - public void Remove(UUID scopeID, UUID regionID) + public void Remove(UUID scopeID, GridRegion rinfo) { - m_Cache.Remove(scopeID, regionID); + m_Cache.Remove(scopeID, rinfo); + } + + public void Remove(UUID scopeID, ulong regionHandle) + { + m_Cache.Remove(scopeID, regionHandle); } public GridRegion Get(UUID scopeID, UUID regionID, out bool inCache) @@ -137,7 +144,7 @@ namespace OpenSim.Region.CoreModules.ServiceConnectorsOut.Grid return null; } - public GridRegion Get(UUID scopeID, int x, int y, out bool inCache) + public GridRegion Get(UUID scopeID, uint x, uint y, out bool inCache) { inCache = false; @@ -152,109 +159,281 @@ namespace OpenSim.Region.CoreModules.ServiceConnectorsOut.Grid } } - - // following code partialy adapted from lib OpenMetaverse - public class RegionKey + public class RegionInfoForScope { - public UUID ScopeID; - public UUID RegionID; + public const ulong HANDLEMASH = 0xffffff00ffffff00ul; + public const ulong HANDLECOORDMASH = 0xffffff00ul; - public RegionKey(UUID scopeID, UUID id) + private Dictionary storage; + private Dictionary expires; + private Dictionary byname; + private Dictionary byuuid; + + public RegionInfoForScope() { - ScopeID = scopeID; - RegionID = id; - } - - public override int GetHashCode() - { - int hash = ScopeID.GetHashCode(); - hash += hash * 23 + RegionID.GetHashCode(); - return hash; + storage = new Dictionary(); + expires = new Dictionary(); + byname = new Dictionary(); + byuuid = new Dictionary(); } - public override bool Equals(Object b) + public RegionInfoForScope(GridRegion region, DateTime expire) { - if(b == null) - return false; - RegionKey kb = b as RegionKey; - return (ScopeID == kb.ScopeID && RegionID == kb.RegionID); - } - } + storage = new Dictionary(); + expires = new Dictionary(); + byname = new Dictionary(); + byuuid = new Dictionary(); - class RegionKeyEqual : EqualityComparer - { - public override int GetHashCode(RegionKey rk) - { - return rk.GetHashCode(); + ulong handle = region.RegionHandle & HANDLEMASH; + storage[handle] = region; + expires[handle] = expire; + byname[region.RegionName] = handle; + byuuid[region.RegionID] = handle; } - public override bool Equals(RegionKey a, RegionKey b) + public void Add(GridRegion region, DateTime expire) { - return (a.ScopeID == b.ScopeID && a.RegionID == b.RegionID); - } - } + ulong handle = region.RegionHandle & HANDLEMASH; - public class RegionInfoByScope - { - private Dictionary byname; - private Dictionary byhandle; + if(storage != null && storage.ContainsKey(handle)) + return; - public RegionInfoByScope() - { - byname = new Dictionary(); - byhandle = new Dictionary(); - } - - public RegionInfoByScope(GridRegion region, RegionKey key) - { - byname = new Dictionary(); - byhandle = new Dictionary(); - - byname[region.RegionName] = key; - byhandle[region.RegionHandle] = key; - } - - public void AddRegion(GridRegion region, RegionKey key) - { + if(storage == null) + storage = new Dictionary(); + if(expires == null) + expires = new Dictionary(); if(byname == null) - byname = new Dictionary(); - if(byhandle == null) - byhandle = new Dictionary(); + byname = new Dictionary(); + if(byuuid == null) + byuuid = new Dictionary(); - byname[region.RegionName] = key; - byhandle[region.RegionHandle] = key; + storage[handle] = region; + expires[handle] = expire; + byname[region.RegionName] = handle; + byuuid[region.RegionID] = handle; } - public void RemoveRegion(GridRegion region) + public void AddUpdate(GridRegion region, DateTime expire) { + if(storage == null) + storage = new Dictionary(); + if(expires == null) + expires = new Dictionary(); + if(byname == null) + byname = new Dictionary(); + if(byuuid == null) + byuuid = new Dictionary(); + + ulong handle = region.RegionHandle & HANDLEMASH; + + storage[handle] = region; + if(expires.ContainsKey(handle)) + { + if(expires[handle] < expire) + expires[handle] = expire; + } + else + expires[handle] = expire; + byname[region.RegionName] = handle; + byuuid[region.RegionID] = handle; + } + + public void Remove(GridRegion region) + { + if(region == null) + return; + if(byname != null) byname.Remove(region.RegionName); - if(byhandle != null) - byhandle.Remove(region.RegionHandle); + if(byuuid != null) + byuuid.Remove(region.RegionID); + + ulong handle = region.RegionHandle & HANDLEMASH; + if(storage != null) + storage.Remove(handle); + if(expires != null) + { + expires.Remove(handle); + if(expires.Count == 0) + Clear(); + } + } + + public void Remove(ulong handle) + { + handle &= HANDLEMASH; + + if(storage != null) + { + if(storage.ContainsKey(handle)) + { + GridRegion r = storage[handle]; + if(byname != null) + byname.Remove(r.RegionName); + if(byuuid != null) + byuuid.Remove(r.RegionID); + } + storage.Remove(handle); + } + if(expires != null) + { + expires.Remove(handle); + if(expires.Count == 0) + Clear(); + } } public void Clear() { + if(expires != null) + expires.Clear(); + if(storage != null) + storage.Clear(); if(byname != null) byname.Clear(); - if(byhandle != null) - byhandle.Clear(); + if(byuuid != null) + byuuid.Clear(); byname = null; - byhandle = null; + byuuid = null; + storage = null; + expires = null; } - public RegionKey get(string name) + public bool Contains(GridRegion region) + { + if(storage == null) + return false; + if(region == null) + return false; + + ulong handle = region.RegionHandle & HANDLEMASH; + return storage.ContainsKey(handle); + } + + public bool Contains(ulong handle) + { + if(storage == null) + return false; + + handle &= HANDLEMASH; + return storage.ContainsKey(handle); + } + + public GridRegion get(ulong handle) + { + if(storage == null) + return null; + + handle &= HANDLEMASH; + if(storage.ContainsKey(handle)) + return storage[handle]; + + return null; + } + + public GridRegion get(string name) { if(byname == null || !byname.ContainsKey(name)) return null; - return byname[name]; + + ulong handle = byname[name]; + if(storage.ContainsKey(handle)) + return storage[handle]; + return null; } - public RegionKey get(ulong handle) + public GridRegion get(UUID id) { - if(byhandle == null || !byhandle.ContainsKey(handle)) + if(byuuid == null || !byuuid.ContainsKey(id)) return null; - return byhandle[handle]; + + ulong handle = byuuid[id]; + if(storage.ContainsKey(handle)) + return storage[handle]; + return null; + } + + public GridRegion get(uint x, uint y) + { + if(storage == null) + return null; + + // look for a handle first this should find normal size regions + ulong handle = (ulong)x & HANDLECOORDMASH; + handle <<= 32; + handle |= ((ulong)y & HANDLECOORDMASH); + + if(storage.ContainsKey(handle)) + return storage[handle]; + + // next do the harder work + foreach(KeyValuePair kvp in storage) + { + GridRegion r = kvp.Value; + if(r == null) // ?? + continue; + + if(handle < r.RegionHandle) + continue; + int test = r.RegionLocX + r.RegionSizeX; + if(x >= test) + continue; + test = r.RegionLocY + r.RegionSizeY; + if (y < test) + return r; + } + return null; + } + + public int expire(DateTime now ) + { + if(expires == null || expires.Count == 0) + return 0; + + List toexpire = new List(); + foreach(KeyValuePair kvp in expires) + { + if(kvp.Value < now) + toexpire.Add(kvp.Key); + } + + if(toexpire.Count == 0) + return expires.Count; + + if(toexpire.Count == expires.Count) + { + Clear(); + return 0; + } + + foreach(ulong h in toexpire) + { + if(storage != null) + { + if(storage.ContainsKey(h)) + { + GridRegion r = storage[h]; + if(byname != null) + byname.Remove(r.RegionName); + if(byuuid != null) + byuuid.Remove(r.RegionID); + } + storage.Remove(h); + } + if(expires != null) + expires.Remove(h); + } + + if(expires.Count == 0) + { + byname = null; + byuuid = null; + storage = null; + expires = null; + return 0; + } + + return expires.Count; } public int Count() @@ -276,10 +455,7 @@ namespace OpenSim.Region.CoreModules.ServiceConnectorsOut.Grid /// For thread safety object isPurging = new object(); - static RegionKeyEqual keyequal = new RegionKeyEqual(); - Dictionary timedStorage = new Dictionary(keyequal); - Dictionary timedExpires = new Dictionary(); - Dictionary InfobyScope = new Dictionary(); + Dictionary InfobyScope = new Dictionary(); private System.Timers.Timer timer = new System.Timers.Timer(TimeSpan.FromSeconds(CACHE_PURGE_HZ).TotalMilliseconds); public RegionsExpiringCache() @@ -288,74 +464,29 @@ namespace OpenSim.Region.CoreModules.ServiceConnectorsOut.Grid timer.Start(); } - public bool Add(UUID scope, GridRegion region, float expirationSeconds) + public bool AddOrUpdate(UUID scope, GridRegion region, float expirationSeconds) { + if(region == null) + return false; + if (!Monitor.TryEnter(syncRoot, MAX_LOCK_WAIT)) throw new ApplicationException("Lock could not be acquired after " + MAX_LOCK_WAIT + "ms"); - RegionKey key = new RegionKey(scope , region.RegionID); - try { - if (timedStorage.ContainsKey(key)) - return false; - DateTime expire = DateTime.UtcNow + TimeSpan.FromSeconds(expirationSeconds); - timedStorage[key] = region; - timedExpires[key] = expire; - RegionInfoByScope ris = null; + RegionInfoForScope ris = null; if(!InfobyScope.TryGetValue(scope, out ris) || ris == null) { - ris = new RegionInfoByScope(region, key); + ris = new RegionInfoForScope(region, expire); InfobyScope[scope] = ris; } else - ris.AddRegion(region, key); + ris.AddUpdate(region, expire); return true; } - finally { Monitor.Exit(syncRoot);} - } - - public bool AddOrUpdate(UUID scope, GridRegion region, float expirationSeconds) - { - if (!Monitor.TryEnter(syncRoot, MAX_LOCK_WAIT)) - throw new ApplicationException("Lock could not be acquired after " + MAX_LOCK_WAIT + "ms"); - - try - { - RegionKey key = new RegionKey(scope, region.RegionID); - DateTime expire = DateTime.UtcNow + TimeSpan.FromSeconds(expirationSeconds); - - if (timedStorage.ContainsKey(key)) - { - timedStorage[key] = region; - if(expire > timedExpires[key]) - timedExpires[key] = expire; - - if(!InfobyScope.ContainsKey(scope)) - { - RegionInfoByScope ris = new RegionInfoByScope(region, key); - InfobyScope[scope] = ris; - } - return false; - } - else - { - timedStorage[key] = region; - timedExpires[key] = expire; - RegionInfoByScope ris = null; - if(!InfobyScope.TryGetValue(scope, out ris) || ris == null) - { - ris = new RegionInfoByScope(region,key); - InfobyScope[scope] = ris; - } - else - ris.AddRegion(region,key); - return true; - } - } finally { Monitor.Exit(syncRoot); } } @@ -365,8 +496,8 @@ namespace OpenSim.Region.CoreModules.ServiceConnectorsOut.Grid throw new ApplicationException("Lock could not be acquired after " + MAX_LOCK_WAIT + "ms"); try { - timedStorage.Clear(); - timedExpires.Clear(); + foreach(RegionInfoForScope ris in InfobyScope.Values) + ris.Clear(); InfobyScope.Clear(); } finally { Monitor.Exit(syncRoot); } @@ -374,211 +505,184 @@ namespace OpenSim.Region.CoreModules.ServiceConnectorsOut.Grid public bool Contains(UUID scope, GridRegion region) { - RegionKey key = new RegionKey(scope, region.RegionID); - return Contains(key); - } + if(region == null) + return false; - public bool Contains(RegionKey key) - { if (!Monitor.TryEnter(syncRoot, MAX_LOCK_WAIT)) throw new ApplicationException("Lock could not be acquired after " + MAX_LOCK_WAIT + "ms"); + try - { - return timedStorage.ContainsKey(key); + { + RegionInfoForScope ris = null; + if(!InfobyScope.TryGetValue(scope, out ris) || ris == null) + return false; + + return ris.Contains(region); } finally { Monitor.Exit(syncRoot); } } - public int Count + public bool Contains(UUID scope, ulong handle) { - get - { - return timedStorage.Count; + if (!Monitor.TryEnter(syncRoot, MAX_LOCK_WAIT)) + throw new ApplicationException("Lock could not be acquired after " + MAX_LOCK_WAIT + "ms"); + + try + { + RegionInfoForScope ris = null; + if(!InfobyScope.TryGetValue(scope, out ris) || ris == null) + return false; + + return ris.Contains(handle); } + finally { Monitor.Exit(syncRoot); } } + + public int Count() + { + if (!Monitor.TryEnter(syncRoot, MAX_LOCK_WAIT)) + throw new ApplicationException("Lock could not be acquired after " + MAX_LOCK_WAIT + "ms"); + + try + { + int count = 0; + foreach(RegionInfoForScope ris in InfobyScope.Values) + count += ris.Count(); + return count; + } + finally { Monitor.Exit(syncRoot); } + } + + public bool Remove(UUID scope, ulong handle) + { + if (!Monitor.TryEnter(syncRoot, MAX_LOCK_WAIT)) + throw new ApplicationException("Lock could not be acquired after " + MAX_LOCK_WAIT + "ms"); + try + { + RegionInfoForScope ris = null; + if(!InfobyScope.TryGetValue(scope, out ris) || ris == null) + return false; + + ris.Remove(handle); + if(ris.Count() == 0) + InfobyScope.Remove(scope); + return true; + } + finally { Monitor.Exit(syncRoot); } + } + public bool Remove(UUID scope, GridRegion region) { - return Remove(scope, region.RegionID); - } - public bool Remove(UUID scope, UUID regionID) - { - RegionKey key = new RegionKey(scope, regionID); + if(region == null) + return false; if (!Monitor.TryEnter(syncRoot, MAX_LOCK_WAIT)) throw new ApplicationException("Lock could not be acquired after " + MAX_LOCK_WAIT + "ms"); try { - if (timedStorage.ContainsKey(key)) - { - RegionInfoByScope ris = null; - if(InfobyScope.TryGetValue(scope, out ris) && ris != null) - { - GridRegion r = timedStorage[key]; - if(r != null) - ris.RemoveRegion(r); - if(ris.Count() == 0) - InfobyScope.Remove(scope); - } - timedStorage.Remove(key); - timedExpires.Remove(key); - return true; - } - else - return false; - } - finally { Monitor.Exit(syncRoot); } - } - - public bool TryGetValue(RegionKey key, out GridRegion value) - { - if (!Monitor.TryEnter(syncRoot, MAX_LOCK_WAIT)) - throw new ApplicationException("Lock could not be acquired after " + MAX_LOCK_WAIT + "ms"); - try - { - if (timedStorage.ContainsKey(key)) - { - value = timedStorage[key]; - return true; - } - } - finally { Monitor.Exit(syncRoot); } - - value = null; - return false; - } - - public bool TryGetValue(UUID scope, UUID id, out GridRegion value) - { - if (!Monitor.TryEnter(syncRoot, MAX_LOCK_WAIT)) - throw new ApplicationException("Lock could not be acquired after " + MAX_LOCK_WAIT + "ms"); - try - { - RegionKey rk = new RegionKey(scope, id); - if(timedStorage.ContainsKey(rk)) - { - value = timedStorage[rk]; - return true; - } - } - finally { Monitor.Exit(syncRoot); } - - value = null; - return false; - } - - public bool TryGetValue(UUID scope, string name, out GridRegion value) - { - if (!Monitor.TryEnter(syncRoot, MAX_LOCK_WAIT)) - throw new ApplicationException("Lock could not be acquired after " + MAX_LOCK_WAIT + "ms"); - try - { - value = null; - RegionInfoByScope ris = null; + RegionInfoForScope ris = null; if(!InfobyScope.TryGetValue(scope, out ris) || ris == null) return false; - RegionKey key = ris.get(name); - if(key == null) - return false; - - if(timedStorage.ContainsKey(key)) - { - value = timedStorage[key]; - return true; - } + ris.Remove(region); + if(ris.Count() == 0) + InfobyScope.Remove(scope); + return true; } finally { Monitor.Exit(syncRoot); } - - return false; } public bool TryGetValue(UUID scope, ulong handle, out GridRegion value) { if (!Monitor.TryEnter(syncRoot, MAX_LOCK_WAIT)) throw new ApplicationException("Lock could not be acquired after " + MAX_LOCK_WAIT + "ms"); + + value = null; try { - value = null; - RegionInfoByScope ris = null; + RegionInfoForScope ris = null; if(!InfobyScope.TryGetValue(scope, out ris) || ris == null) return false; - - RegionKey key = ris.get(handle); - if(key == null) - return false; - - if(timedStorage.ContainsKey(key)) - { - value = timedStorage[key]; - return true; - } + value = ris.get(handle); } finally { Monitor.Exit(syncRoot); } + return value != null; + } + + public bool TryGetValue(UUID scope, string name, out GridRegion value) + { + if (!Monitor.TryEnter(syncRoot, MAX_LOCK_WAIT)) + throw new ApplicationException("Lock could not be acquired after " + MAX_LOCK_WAIT + "ms"); + value = null; - return false; + try + { + RegionInfoForScope ris = null; + if(!InfobyScope.TryGetValue(scope, out ris) || ris == null) + return false; + value = ris.get(name); + } + finally { Monitor.Exit(syncRoot); } + + return value != null; + } + + public bool TryGetValue(UUID scope, UUID id, out GridRegion value) + { + if (!Monitor.TryEnter(syncRoot, MAX_LOCK_WAIT)) + throw new ApplicationException("Lock could not be acquired after " + MAX_LOCK_WAIT + "ms"); + + value = null; + try + { + RegionInfoForScope ris = null; + if(!InfobyScope.TryGetValue(scope, out ris) || ris == null) + return false; + value = ris.get(id); + } + finally { Monitor.Exit(syncRoot); } + + return value != null; } // gets a region that contains world position (x,y) // hopefull will not take ages - public bool TryGetValue(UUID scope, int x, int y, out GridRegion value) + public bool TryGetValue(UUID scope, uint x, uint y, out GridRegion value) { if (!Monitor.TryEnter(syncRoot, MAX_LOCK_WAIT)) throw new ApplicationException("Lock could not be acquired after " + MAX_LOCK_WAIT + "ms"); + + value = null; try { - value = null; - - if(timedStorage.Count == 0) + RegionInfoForScope ris = null; + if(!InfobyScope.TryGetValue(scope, out ris) || ris == null) return false; - foreach(KeyValuePair kvp in timedStorage) - { - if(kvp.Key.ScopeID != scope) - continue; - - GridRegion r = kvp.Value; - if(r == null) // ?? - continue; - int test = r.RegionLocX; - if(x < test) - continue; - test += r.RegionSizeX; - if(x >= test) - continue; - test = r.RegionLocY; - if(y < test) - continue; - test += r.RegionSizeY; - if (y < test) - { - value = r; - return true; - } - } + value = ris.get(x, y); } finally { Monitor.Exit(syncRoot); } - value = null; - return false; + return value != null; } public bool Update(UUID scope, GridRegion region, double expirationSeconds) { + if(region == null) + return false; + if (!Monitor.TryEnter(syncRoot, MAX_LOCK_WAIT)) throw new ApplicationException("Lock could not be acquired after " + MAX_LOCK_WAIT + "ms"); - RegionKey key = new RegionKey(scope, region.RegionID); try { - if (!timedStorage.ContainsKey(key)) + RegionInfoForScope ris = null; + if(!InfobyScope.TryGetValue(scope, out ris) || ris == null) return false; DateTime expire = DateTime.UtcNow + TimeSpan.FromSeconds(expirationSeconds); - timedStorage[key] = region; - if(expire > timedExpires[key]) - timedExpires[key] = expire; - + ris.AddUpdate(region,expire); return true; } finally { Monitor.Exit(syncRoot); } @@ -595,7 +699,7 @@ namespace OpenSim.Region.CoreModules.ServiceConnectorsOut.Grid if (!Monitor.TryEnter(isPurging)) return; - DateTime signalTime = DateTime.UtcNow; + DateTime now = DateTime.UtcNow; try { @@ -604,32 +708,18 @@ namespace OpenSim.Region.CoreModules.ServiceConnectorsOut.Grid return; try { - List expiredkeys = new List(); + List expiredscopes = new List(); - foreach (KeyValuePair kvp in timedExpires) + foreach (KeyValuePair kvp in InfobyScope) { - if (kvp.Value < signalTime) - expiredkeys.Add(kvp.Key); + if (kvp.Value.expire(now) == 0) + expiredscopes.Add(kvp.Key); } - if (expiredkeys.Count > 0) + if (expiredscopes.Count > 0) { - RegionInfoByScope ris; - foreach (RegionKey key in expiredkeys) - { - ris = null; - if(InfobyScope.TryGetValue(key.ScopeID, out ris) && ris != null) - { - GridRegion r = timedStorage[key]; - if(r != null) - ris.RemoveRegion(r); - - if(ris.Count() == 0) - InfobyScope.Remove(key.ScopeID); - } - timedStorage.Remove(key); - timedExpires.Remove(key); - } + foreach (UUID sid in expiredscopes) + InfobyScope.Remove(sid); } } finally { Monitor.Exit(syncRoot); } diff --git a/OpenSim/Region/CoreModules/ServiceConnectorsOut/Grid/RemoteGridServiceConnector.cs b/OpenSim/Region/CoreModules/ServiceConnectorsOut/Grid/RemoteGridServiceConnector.cs index 96ff4b3bc4..e6e3abb61e 100644 --- a/OpenSim/Region/CoreModules/ServiceConnectorsOut/Grid/RemoteGridServiceConnector.cs +++ b/OpenSim/Region/CoreModules/ServiceConnectorsOut/Grid/RemoteGridServiceConnector.cs @@ -204,8 +204,8 @@ namespace OpenSim.Region.CoreModules.ServiceConnectorsOut.Grid GridRegion rinfo = m_LocalGridService.GetRegionByPosition(scopeID, x, y); if (rinfo != null) { - m_log.DebugFormat("[REMOTE GRID CONNECTOR]: GetRegionByPosition. Added region {0} to the cache from local. Pos=<{1},{2}>, RegionHandle={3}", - rinfo.RegionName, rinfo.RegionCoordX, rinfo.RegionCoordY, rinfo.RegionHandle); +// m_log.DebugFormat("[REMOTE GRID CONNECTOR]: GetRegionByPosition. Found region {0} on local. Pos=<{1},{2}>, RegionHandle={3}", +// rinfo.RegionName, rinfo.RegionCoordX, rinfo.RegionCoordY, rinfo.RegionHandle); return rinfo; } @@ -213,16 +213,16 @@ namespace OpenSim.Region.CoreModules.ServiceConnectorsOut.Grid if (rinfo == null) { - uint regionX = Util.WorldToRegionLoc((uint)x); - uint regionY = Util.WorldToRegionLoc((uint)y); - m_log.WarnFormat("[REMOTE GRID CONNECTOR]: Requested region {0}-{1} not found", regionX, regionY); +// uint regionX = Util.WorldToRegionLoc((uint)x); +// uint regionY = Util.WorldToRegionLoc((uint)y); +// m_log.WarnFormat("[REMOTE GRID CONNECTOR]: Requested region {0}-{1} not found", regionX, regionY); } else { m_RegionInfoCache.Cache(scopeID, rinfo); - m_log.DebugFormat("[REMOTE GRID CONNECTOR]: GetRegionByPosition. Added region {0} to the cache. Pos=<{1},{2}>, RegionHandle={3}", - rinfo.RegionName, rinfo.RegionCoordX, rinfo.RegionCoordY, rinfo.RegionHandle); +// m_log.DebugFormat("[REMOTE GRID CONNECTOR]: GetRegionByPosition. Added region {0} to the cache. Pos=<{1},{2}>, RegionHandle={3}", +// rinfo.RegionName, rinfo.RegionCoordX, rinfo.RegionCoordY, rinfo.RegionHandle); } return rinfo; } From 722b7cfbb2e1919f5d88be4574b4ae9edade25ba Mon Sep 17 00:00:00 2001 From: UbitUmarov Date: Sun, 31 Jul 2016 19:35:10 +0100 Subject: [PATCH 4/6] bug fix --- .../ServiceConnectorsOut/Grid/RegionInfoCache.cs | 10 +++++++--- 1 file changed, 7 insertions(+), 3 deletions(-) diff --git a/OpenSim/Region/CoreModules/ServiceConnectorsOut/Grid/RegionInfoCache.cs b/OpenSim/Region/CoreModules/ServiceConnectorsOut/Grid/RegionInfoCache.cs index 03fc9eae51..6db9515729 100644 --- a/OpenSim/Region/CoreModules/ServiceConnectorsOut/Grid/RegionInfoCache.cs +++ b/OpenSim/Region/CoreModules/ServiceConnectorsOut/Grid/RegionInfoCache.cs @@ -373,12 +373,16 @@ namespace OpenSim.Region.CoreModules.ServiceConnectorsOut.Grid if(r == null) // ?? continue; - if(handle < r.RegionHandle) + int test = r.RegionLocX; + if(x < test) continue; - int test = r.RegionLocX + r.RegionSizeX; + test += r.RegionSizeX; if(x >= test) continue; - test = r.RegionLocY + r.RegionSizeY; + test = r.RegionLocY; + if (y < test) + continue; + test += r.RegionSizeY; if (y < test) return r; } From c0eae1f8f99c1919338813c150e22a1d91d874ad Mon Sep 17 00:00:00 2001 From: UbitUmarov Date: Sun, 31 Jul 2016 22:39:01 +0100 Subject: [PATCH 5/6] simply NotFoundLocationCache, comment out some debug messages --- .../EntityTransfer/EntityTransferModule.cs | 101 +++++++----------- .../EntityTransferStateMachine.cs | 28 ++--- 2 files changed, 55 insertions(+), 74 deletions(-) diff --git a/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferModule.cs b/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferModule.cs index 9ee23d65bb..c6cabf1cae 100644 --- a/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferModule.cs +++ b/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferModule.cs @@ -1537,8 +1537,6 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer public ScenePresence CrossAsync(ScenePresence agent, bool isFlying) { - uint x; - uint y; Vector3 newpos; EntityTransferContext ctx = new EntityTransferContext(); string failureReason; @@ -1814,7 +1812,7 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer // In any case agent.IsInTransit = false; - m_log.DebugFormat("[ENTITY TRANSFER MODULE]: Crossing agent {0} {1} completed.", agent.Firstname, agent.Lastname); +// m_log.DebugFormat("[ENTITY TRANSFER MODULE]: Crossing agent {0} {1} completed.", agent.Firstname, agent.Lastname); } #endregion @@ -2115,79 +2113,62 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer // contains that point. A conservitive estimate. private class NotFoundLocationCache { - private struct NotFoundLocation - { - public double minX, maxX, minY, maxY; - public DateTime expireTime; - } - private List m_notFoundLocations = new List(); + private Dictionary m_notFoundLocations = new Dictionary(); public NotFoundLocationCache() { } - // Add an area to the list of 'not found' places. The area is the snapped region - // area around the added point. + // just use normal regions handlers and sizes public void Add(double pX, double pY) { + ulong psh = (ulong)pX & 0xffffff00ul; + psh <<= 32; + psh |= (ulong)pY & 0xffffff00ul; + lock (m_notFoundLocations) - { - if (!LockedContains(pX, pY)) - { - NotFoundLocation nfl = new NotFoundLocation(); - // A not found location is not found for at least a whole region sized area - nfl.minX = pX - (pX % (double)Constants.RegionSize); - nfl.minY = pY - (pY % (double)Constants.RegionSize); - nfl.maxX = nfl.minX + (double)Constants.RegionSize; - nfl.maxY = nfl.minY + (double)Constants.RegionSize; - nfl.expireTime = DateTime.Now + TimeSpan.FromSeconds(30); - m_notFoundLocations.Add(nfl); - } - } - + m_notFoundLocations[psh] = DateTime.Now + TimeSpan.FromSeconds(30);; } // Test to see of this point is in any of the 'not found' areas. // Return 'true' if the point is found inside the 'not found' areas. public bool Contains(double pX, double pY) { - bool ret = false; + ulong psh = (ulong)pX & 0xffffff00ul; + psh <<= 32; + psh |= (ulong)pY & 0xffffff00ul; + lock (m_notFoundLocations) - ret = LockedContains(pX, pY); - return ret; - } - private bool LockedContains(double pX, double pY) - { - bool ret = false; - this.DoExpiration(); - foreach (NotFoundLocation nfl in m_notFoundLocations) { - if (pX >= nfl.minX && pX < nfl.maxX && pY >= nfl.minY && pY < nfl.maxY) + if(m_notFoundLocations.ContainsKey(psh)) { - ret = true; - break; + if(m_notFoundLocations[psh] > DateTime.UtcNow) + return true; + m_notFoundLocations.Remove(psh); } + return false; } - return ret; } + private void DoExpiration() { - List m_toRemove = null; - DateTime now = DateTime.Now; - foreach (NotFoundLocation nfl in m_notFoundLocations) + List m_toRemove = new List();; + DateTime now = DateTime.UtcNow; + lock (m_notFoundLocations) { - if (nfl.expireTime < now) + foreach (KeyValuePair kvp in m_notFoundLocations) { - if (m_toRemove == null) - m_toRemove = new List(); - m_toRemove.Add(nfl); + if (kvp.Value < now) + m_toRemove.Add(kvp.Key); + } + + if (m_toRemove.Count > 0) + { + foreach (ulong u in m_toRemove) + m_notFoundLocations.Remove(u); + m_toRemove.Clear(); } - } - if (m_toRemove != null) - { - foreach (NotFoundLocation nfl in m_toRemove) - m_notFoundLocations.Remove(nfl); - m_toRemove.Clear(); } } } + #endregion // NotFoundLocationCache class private NotFoundLocationCache m_notFoundLocationCache = new NotFoundLocationCache(); @@ -2202,7 +2183,7 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer // Given a world position, get the GridRegion info for // the region containing that point. - // Someday this should be a method on GridService. + // Not needed on 0.9 grids // 'pSizeHint' is the size of the source region but since the destination point can be anywhere // the size of the target region is unknown thus the search area might have to be very large. // Return 'null' if no such region exists. @@ -2233,8 +2214,8 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer ret = pGridService.GetRegionByPosition(pScopeID, (int)possibleX, (int)possibleY); if (ret != null) { - m_log.DebugFormat("{0} GetRegionContainingWorldLocation: Found region using legacy size. rloc=<{1},{2}>. Rname={3}", - LogHeader, possibleX, possibleY, ret.RegionName); +// m_log.DebugFormat("{0} GetRegionContainingWorldLocation: Found region using legacy size. rloc=<{1},{2}>. Rname={3}", +// LogHeader, possibleX, possibleY, ret.RegionName); } if (ret == null) @@ -2248,21 +2229,21 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer List possibleRegions = pGridService.GetRegionRange(pScopeID, (int)(px - range), (int)(px), (int)(py - range), (int)(py)); - m_log.DebugFormat("{0} GetRegionContainingWorldLocation: possibleRegions cnt={1}, range={2}", - LogHeader, possibleRegions.Count, range); +// m_log.DebugFormat("{0} GetRegionContainingWorldLocation: possibleRegions cnt={1}, range={2}", +// LogHeader, possibleRegions.Count, range); if (possibleRegions != null && possibleRegions.Count > 0) { // If we found some regions, check to see if the point is within foreach (GridRegion gr in possibleRegions) { - m_log.DebugFormat("{0} GetRegionContainingWorldLocation: possibleRegion nm={1}, regionLoc=<{2},{3}>, regionSize=<{4},{5}>", - LogHeader, gr.RegionName, gr.RegionLocX, gr.RegionLocY, gr.RegionSizeX, gr.RegionSizeY); +// m_log.DebugFormat("{0} GetRegionContainingWorldLocation: possibleRegion nm={1}, regionLoc=<{2},{3}>, regionSize=<{4},{5}>", +// LogHeader, gr.RegionName, gr.RegionLocX, gr.RegionLocY, gr.RegionSizeX, gr.RegionSizeY); if (px >= (double)gr.RegionLocX && px < (double)(gr.RegionLocX + gr.RegionSizeX) && py >= (double)gr.RegionLocY && py < (double)(gr.RegionLocY + gr.RegionSizeY)) { // Found a region that contains the point ret = gr; - m_log.DebugFormat("{0} GetRegionContainingWorldLocation: found. RegionName={1}", LogHeader, ret.RegionName); +// m_log.DebugFormat("{0} GetRegionContainingWorldLocation: found. RegionName={1}", LogHeader, ret.RegionName); break; } } @@ -2276,7 +2257,7 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer { // remember this location was not found so we can quickly not find it next time m_notFoundLocationCache.Add(px, py); - m_log.DebugFormat("{0} GetRegionContainingWorldLocation: Not found. Remembering loc=<{1},{2}>", LogHeader, px, py); +// m_log.DebugFormat("{0} GetRegionContainingWorldLocation: Not found. Remembering loc=<{1},{2}>", LogHeader, px, py); } return ret; diff --git a/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferStateMachine.cs b/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferStateMachine.cs index e3c6c0d0b6..acfdaef8ef 100644 --- a/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferStateMachine.cs +++ b/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferStateMachine.cs @@ -101,7 +101,7 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer /// true if the agent was not already in transit, false if it was internal bool SetInTransit(UUID id) { - m_log.DebugFormat("{0} SetInTransit. agent={1}, newState=Preparing", LogHeader, id); +// m_log.DebugFormat("{0} SetInTransit. agent={1}, newState=Preparing", LogHeader, id); lock (m_agentsInTransit) { if (!m_agentsInTransit.ContainsKey(id)) @@ -123,7 +123,7 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer /// Illegal transitions will throw an Exception internal bool UpdateInTransit(UUID id, AgentTransferState newState) { - m_log.DebugFormat("{0} UpdateInTransit. agent={1}, newState={2}", LogHeader, id, newState); + // m_log.DebugFormat("{0} UpdateInTransit. agent={1}, newState={2}", LogHeader, id, newState); bool transitionOkay = false; @@ -247,32 +247,32 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer { AgentTransferState state = m_agentsInTransit[id]; - if (state == AgentTransferState.Transferring || state == AgentTransferState.ReceivedAtDestination) - { +// if (state == AgentTransferState.Transferring || state == AgentTransferState.ReceivedAtDestination) +// { // FIXME: For now, we allow exit from any state since a thrown exception in teleport is now guranteed // to be handled properly - ResetFromTransit() could be invoked at any step along the process - m_log.WarnFormat( - "[ENTITY TRANSFER STATE MACHINE]: Agent with ID {0} should not exit directly from state {1}, should go to {2} state first in {3}", - id, state, AgentTransferState.CleaningUp, m_mod.Scene.RegionInfo.RegionName); +// m_log.WarnFormat( +// "[ENTITY TRANSFER STATE MACHINE]: Agent with ID {0} should not exit directly from state {1}, should go to {2} state first in {3}", +// id, state, AgentTransferState.CleaningUp, m_mod.Scene.RegionInfo.RegionName); // throw new Exception( // "Agent with ID {0} cannot exit directly from state {1}, it must go to {2} state first", // state, AgentTransferState.CleaningUp); - } +// } m_agentsInTransit.Remove(id); - m_log.DebugFormat( - "[ENTITY TRANSFER STATE MACHINE]: Agent {0} cleared from transit in {1}", - id, m_mod.Scene.RegionInfo.RegionName); +// m_log.DebugFormat( +// "[ENTITY TRANSFER STATE MACHINE]: Agent {0} cleared from transit in {1}", +// id, m_mod.Scene.RegionInfo.RegionName); return true; } } - m_log.WarnFormat( - "[ENTITY TRANSFER STATE MACHINE]: Agent {0} requested to clear from transit in {1} but was already cleared", - id, m_mod.Scene.RegionInfo.RegionName); +// m_log.WarnFormat( +// "[ENTITY TRANSFER STATE MACHINE]: Agent {0} requested to clear from transit in {1} but was already cleared", +// id, m_mod.Scene.RegionInfo.RegionName); return false; } From 159d7229661cd1b0bc300dd8b6a6772bd0b5a8d5 Mon Sep 17 00:00:00 2001 From: UbitUmarov Date: Sun, 31 Jul 2016 23:12:09 +0100 Subject: [PATCH 6/6] on 0.8 grids compatibility code just do a BIG range request. It whould be done in most cases (open borders) plus 4 more. In future this code should not be used if the grid is >=0.9 --- .../EntityTransfer/EntityTransferModule.cs | 74 +++++++------------ 1 file changed, 25 insertions(+), 49 deletions(-) diff --git a/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferModule.cs b/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferModule.cs index c6cabf1cae..980d3cc47c 100644 --- a/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferModule.cs +++ b/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferModule.cs @@ -2183,10 +2183,6 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer // Given a world position, get the GridRegion info for // the region containing that point. - // Not needed on 0.9 grids - // 'pSizeHint' is the size of the source region but since the destination point can be anywhere - // the size of the target region is unknown thus the search area might have to be very large. - // Return 'null' if no such region exists. protected GridRegion GetRegionContainingWorldLocation(IGridService pGridService, UUID pScopeID, double px, double py, uint pSizeHint) { @@ -2194,11 +2190,6 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer GridRegion ret = null; const double fudge = 2.0; - // One problem with this routine is negative results. That is, this can be called lots of times - // for regions that don't exist. m_notFoundLocationCache remembers 'not found' results so they - // will be quick 'not found's next time. - // NotFoundLocationCache is an expiring cache so it will eventually forget about 'not found' and - // thus re-ask the GridService about the location. if (m_notFoundLocationCache.Contains(px, py)) { // m_log.DebugFormat("{0} GetRegionContainingWorldLocation: Not found via cache. loc=<{1},{2}>", LogHeader, px, py); @@ -2207,60 +2198,45 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer // As an optimization, since most regions will be legacy sized regions (256x256), first try to get // the region at the appropriate legacy region location. - uint possibleX = (uint)Math.Floor(px); - possibleX -= possibleX % Constants.RegionSize; - uint possibleY = (uint)Math.Floor(py); - possibleY -= possibleY % Constants.RegionSize; + // this is all that is needed on 0.9 grids + uint possibleX = (uint)px & 0xffffff00u; + uint possibleY = (uint)py & 0xffffff00u; ret = pGridService.GetRegionByPosition(pScopeID, (int)possibleX, (int)possibleY); if (ret != null) { // m_log.DebugFormat("{0} GetRegionContainingWorldLocation: Found region using legacy size. rloc=<{1},{2}>. Rname={3}", // LogHeader, possibleX, possibleY, ret.RegionName); + return ret; } - if (ret == null) + // for 0.8 regions just make a BIG area request. old code whould do it plus 4 more smaller on region open edges + // this is what 0.9 grids now do internally + List possibleRegions = pGridService.GetRegionRange(pScopeID, + (int)(px - Constants.MaximumRegionSize), (int)(px + 1), // +1 bc left mb not part of range + (int)(py - Constants.MaximumRegionSize), (int)(py + 1)); +// m_log.DebugFormat("{0} GetRegionContainingWorldLocation: possibleRegions cnt={1}, range={2}", +// LogHeader, possibleRegions.Count, range); + if (possibleRegions != null && possibleRegions.Count > 0) { - // If the simple lookup failed, search the larger area for a region that contains this point - double range = (double)pSizeHint + fudge; - while (ret == null && range <= (Constants.MaximumRegionSize + Constants.RegionSize)) + // If we found some regions, check to see if the point is within + foreach (GridRegion gr in possibleRegions) { - // Get from the grid service a list of regions that might contain this point. - // The region origin will be in the zero direction so only subtract the range. - List possibleRegions = pGridService.GetRegionRange(pScopeID, - (int)(px - range), (int)(px), - (int)(py - range), (int)(py)); -// m_log.DebugFormat("{0} GetRegionContainingWorldLocation: possibleRegions cnt={1}, range={2}", -// LogHeader, possibleRegions.Count, range); - if (possibleRegions != null && possibleRegions.Count > 0) - { - // If we found some regions, check to see if the point is within - foreach (GridRegion gr in possibleRegions) - { -// m_log.DebugFormat("{0} GetRegionContainingWorldLocation: possibleRegion nm={1}, regionLoc=<{2},{3}>, regionSize=<{4},{5}>", -// LogHeader, gr.RegionName, gr.RegionLocX, gr.RegionLocY, gr.RegionSizeX, gr.RegionSizeY); - if (px >= (double)gr.RegionLocX && px < (double)(gr.RegionLocX + gr.RegionSizeX) +// m_log.DebugFormat("{0} GetRegionContainingWorldLocation: possibleRegion nm={1}, regionLoc=<{2},{3}>, regionSize=<{4},{5}>", +// LogHeader, gr.RegionName, gr.RegionLocX, gr.RegionLocY, gr.RegionSizeX, gr.RegionSizeY); + if (px >= (double)gr.RegionLocX && px < (double)(gr.RegionLocX + gr.RegionSizeX) && py >= (double)gr.RegionLocY && py < (double)(gr.RegionLocY + gr.RegionSizeY)) - { - // Found a region that contains the point - ret = gr; -// m_log.DebugFormat("{0} GetRegionContainingWorldLocation: found. RegionName={1}", LogHeader, ret.RegionName); - break; - } - } + { + // Found a region that contains the point + return gr; +// m_log.DebugFormat("{0} GetRegionContainingWorldLocation: found. RegionName={1}", LogHeader, ret.RegionName); } - // Larger search area for next time around if not found - range *= 2; } } - if (ret == null) - { - // remember this location was not found so we can quickly not find it next time - m_notFoundLocationCache.Add(px, py); -// m_log.DebugFormat("{0} GetRegionContainingWorldLocation: Not found. Remembering loc=<{1},{2}>", LogHeader, px, py); - } - - return ret; + // remember this location was not found so we can quickly not find it next time + m_notFoundLocationCache.Add(px, py); +// m_log.DebugFormat("{0} GetRegionContainingWorldLocation: Not found. Remembering loc=<{1},{2}>", LogHeader, px, py); + return null; } private void InformClientOfNeighbourCompleted(IAsyncResult iar)