From 36c8fa16c012dd18012f0c8921fa93c4fbd53b5c Mon Sep 17 00:00:00 2001 From: Snoopy Pfeffer Date: Thu, 5 Apr 2012 00:53:40 +0200 Subject: Implements group based access restrictions for parcels of land. Because of caching there can be a delay of up to 30 seconds until the access rights are effectively changed for a user. --- .../Region/CoreModules/World/Land/LandObject.cs | 58 +++++++++++++++++++++- 1 file changed, 57 insertions(+), 1 deletion(-) (limited to 'OpenSim/Region/CoreModules/World') diff --git a/OpenSim/Region/CoreModules/World/Land/LandObject.cs b/OpenSim/Region/CoreModules/World/Land/LandObject.cs index a0ed5a5..9808ebf 100644 --- a/OpenSim/Region/CoreModules/World/Land/LandObject.cs +++ b/OpenSim/Region/CoreModules/World/Land/LandObject.cs @@ -56,6 +56,12 @@ namespace OpenSim.Region.CoreModules.World.Land protected List primsOverMe = new List(); protected Dictionary m_listTransactions = new Dictionary(); + protected IGroupsModule m_groupsModule; + protected const uint PARCEL_FLAG_USE_ACCESS_GROUP = 0x100; // parcel limits access to a group + protected Dictionary m_isGroupMemberCache = new Dictionary(); + protected Dictionary m_notGroupMemberCache = new Dictionary(); + protected const long m_groupMemberCacheTimeout = 30; // cache invalidation after 30 seconds + public bool[,] LandBitmap { get { return m_landBitmap; } @@ -132,6 +138,8 @@ namespace OpenSim.Region.CoreModules.World.Land else LandData.GroupID = UUID.Zero; LandData.IsGroupOwned = is_group_owned; + + m_groupsModule = scene.RequestModuleInterface(); } #endregion @@ -460,7 +468,55 @@ namespace OpenSim.Region.CoreModules.World.Land if ((LandData.Flags & (uint) ParcelFlags.UseAccessList) == 0) return false; - return (!IsInLandAccessList(avatar)); + if (IsInLandAccessList(avatar)) + return false; + + UUID groupID = LandData.GroupID; + + if ((m_groupsModule != null) && (groupID != UUID.Zero) && ((LandData.Flags & PARCEL_FLAG_USE_ACCESS_GROUP) == PARCEL_FLAG_USE_ACCESS_GROUP)) + { + long now = Util.UnixTimeSinceEpoch(); + + if (m_isGroupMemberCache.ContainsKey(avatar)) + { + if (now - m_isGroupMemberCache[avatar] <= m_groupMemberCacheTimeout) // invalid? + { + m_isGroupMemberCache[avatar] = now; + return false; + } + else + m_isGroupMemberCache.Remove(avatar); + } + + if (m_notGroupMemberCache.ContainsKey(avatar)) + { + if (now - m_notGroupMemberCache[avatar] <= m_groupMemberCacheTimeout) // invalid? + { + // m_notGroupMemberCache[avatar] = now; + return true; + } + else + m_notGroupMemberCache.Remove(avatar); + } + + GroupMembershipData[] GroupMembership = m_groupsModule.GetMembershipData(avatar); + + if (GroupMembership != null) + { + for (int i = 0; i < GroupMembership.Length; i++) + { + if (groupID == GroupMembership[i].GroupID) + { + m_isGroupMemberCache[avatar] = now; + return false; + } + } + } + + m_notGroupMemberCache[avatar] = now; + } + + return true; } public bool IsInLandAccessList(UUID avatar) -- cgit v1.1