public void AggregatePerms() { lock (m_PermissionsLock) { // aux const uint allmask = (uint)PermissionMask.AllEffective; const uint movemodmask = (uint)(PermissionMask.Move | PermissionMask.Modify); const uint copytransfermast = (uint)(PermissionMask.Copy | PermissionMask.Transfer); uint basePerms = (RootPart.BaseMask & allmask) | (uint)PermissionMask.Move; bool noBaseTransfer = (basePerms & (uint)PermissionMask.Transfer) == 0; uint rootOwnerPerms = RootPart.OwnerMask; uint owner = rootOwnerPerms; uint rootGroupPerms = RootPart.GroupMask; uint group = rootGroupPerms; uint rootEveryonePerms = RootPart.EveryoneMask; uint everyone = rootEveryonePerms; bool needUpdate = false; // date is time of writing april 30th 2017 bool newobj = (RootPart.CreationDate == 0 || RootPart.CreationDate > 1493574994); SceneObjectPart[] parts = m_parts.GetArray(); for (int i = 0; i < parts.Length; i++) { SceneObjectPart part = parts[i]; if (m_DeepEffectivePermsInvalid) { part.AggregateInnerPerms(); } owner &= part.AggregatedInnerOwnerPerms; group &= part.AggregatedInnerGroupPerms; if (newobj) { group &= part.AggregatedInnerGroupPerms; } if (newobj) { everyone &= part.AggregatedInnerEveryonePerms; } } // recover modify and move rootOwnerPerms &= movemodmask; owner |= rootOwnerPerms; if ((owner & copytransfermast) == 0) { owner |= (uint)PermissionMask.Transfer; } owner &= basePerms; if (owner != m_EffectiveOwnerPerms) { needUpdate = true; m_EffectiveOwnerPerms = owner; } uint ownertransfermask = owner & (uint)PermissionMask.Transfer; // recover modify and move rootGroupPerms &= movemodmask; group |= rootGroupPerms; if (noBaseTransfer) { group &= ~(uint)PermissionMask.Copy; } else { group |= ownertransfermask; } uint groupOrEveryone = group; uint tmpPerms = group & owner; if (tmpPerms != m_EffectiveGroupPerms) { needUpdate = true; m_EffectiveGroupPerms = tmpPerms; } // recover move rootEveryonePerms &= (uint)PermissionMask.Move; everyone |= rootEveryonePerms; everyone &= ~(uint)PermissionMask.Modify; if (noBaseTransfer) { everyone &= ~(uint)PermissionMask.Copy; } else { everyone |= ownertransfermask; } groupOrEveryone |= everyone; tmpPerms = everyone & owner; if (tmpPerms != m_EffectiveEveryOnePerms) { needUpdate = true; m_EffectiveEveryOnePerms = tmpPerms; } tmpPerms = groupOrEveryone & owner; if (tmpPerms != m_EffectiveGroupOrEveryOnePerms) { needUpdate = true; m_EffectiveGroupOrEveryOnePerms = tmpPerms; } m_DeepEffectivePermsInvalid = false; m_EffectivePermsInvalid = false; if (needUpdate) { RootPart.ScheduleFullUpdate(); } } }
// aggregates perms scanning parts and their contents // AggregatePerms does same using cached parts content perms public void AggregateDeepPerms() { lock (PermissionsLock) { // aux const uint allmask = (uint)PermissionMask.AllEffective; const uint movemodmask = (uint)(PermissionMask.Move | PermissionMask.Modify); const uint copytransfermast = (uint)(PermissionMask.Copy | PermissionMask.Transfer); uint basePerms = (RootPart.BaseMask & allmask) | (uint)PermissionMask.Move; bool noBaseTransfer = (basePerms & (uint)PermissionMask.Transfer) == 0; uint rootOwnerPerms = RootPart.OwnerMask; uint owner = rootOwnerPerms; uint rootGroupPerms = RootPart.GroupMask; uint group = rootGroupPerms; uint rootEveryonePerms = RootPart.EveryoneMask; uint everyone = rootEveryonePerms; SceneObjectPart[] parts = m_parts.GetArray(); for (int i = 0; i < parts.Length; i++) { SceneObjectPart part = parts[i]; part.AggregateInnerPerms(); owner &= part.AggregatedInnerOwnerPerms; group &= part.AggregatedInnerGroupPerms; everyone &= part.AggregatedInnerEveryonePerms; } // recover modify and move rootOwnerPerms &= movemodmask; owner |= rootOwnerPerms; if ((owner & copytransfermast) == 0) { owner |= (uint)PermissionMask.Transfer; } owner &= basePerms; m_EffectiveOwnerPerms = owner; uint ownertransfermask = owner & (uint)PermissionMask.Transfer; // recover modify and move rootGroupPerms &= movemodmask; group |= rootGroupPerms; if (noBaseTransfer) { group &= ~(uint)PermissionMask.Copy; } else { group |= ownertransfermask; } uint groupOrEveryone = group; m_EffectiveGroupPerms = group & owner; // recover move rootEveryonePerms &= (uint)PermissionMask.Move; everyone |= rootEveryonePerms; everyone &= ~(uint)PermissionMask.Modify; if (noBaseTransfer) { everyone &= ~(uint)PermissionMask.Copy; } else { everyone |= ownertransfermask; } groupOrEveryone |= everyone; m_EffectiveEveryOnePerms = everyone & owner; m_EffectiveGroupOrEveryOnePerms = groupOrEveryone & owner; } }