diff --git a/bukkit/src/main/java/me/lucko/luckperms/bukkit/calculator/BukkitCalculatorFactory.java b/bukkit/src/main/java/me/lucko/luckperms/bukkit/calculator/BukkitCalculatorFactory.java index c65666f05..5233544dd 100644 --- a/bukkit/src/main/java/me/lucko/luckperms/bukkit/calculator/BukkitCalculatorFactory.java +++ b/bukkit/src/main/java/me/lucko/luckperms/bukkit/calculator/BukkitCalculatorFactory.java @@ -25,8 +25,6 @@ package me.lucko.luckperms.bukkit.calculator; -import com.google.common.collect.ImmutableList; - import me.lucko.luckperms.bukkit.LPBukkitPlugin; import me.lucko.luckperms.bukkit.context.BukkitContextManager; import me.lucko.luckperms.common.cacheddata.CacheMetadata; @@ -42,6 +40,9 @@ import me.lucko.luckperms.common.model.HolderType; import net.luckperms.api.query.QueryOptions; +import java.util.ArrayList; +import java.util.List; + public class BukkitCalculatorFactory implements CalculatorFactory { private final LPBukkitPlugin plugin; @@ -51,7 +52,7 @@ public class BukkitCalculatorFactory implements CalculatorFactory { @Override public PermissionCalculator build(QueryOptions queryOptions, CacheMetadata metadata) { - ImmutableList.Builder processors = ImmutableList.builder(); + List processors = new ArrayList<>(7); processors.add(new DirectProcessor()); @@ -81,6 +82,6 @@ public class BukkitCalculatorFactory implements CalculatorFactory { processors.add(OpProcessor.INSTANCE); } - return new PermissionCalculator(this.plugin, metadata, processors.build()); + return new PermissionCalculator(this.plugin, metadata, processors); } } diff --git a/bungee/src/main/java/me/lucko/luckperms/bungee/calculator/BungeeCalculatorFactory.java b/bungee/src/main/java/me/lucko/luckperms/bungee/calculator/BungeeCalculatorFactory.java index 4bc026559..f52a00f39 100644 --- a/bungee/src/main/java/me/lucko/luckperms/bungee/calculator/BungeeCalculatorFactory.java +++ b/bungee/src/main/java/me/lucko/luckperms/bungee/calculator/BungeeCalculatorFactory.java @@ -25,8 +25,6 @@ package me.lucko.luckperms.bungee.calculator; -import com.google.common.collect.ImmutableList; - import me.lucko.luckperms.bungee.LPBungeePlugin; import me.lucko.luckperms.common.cacheddata.CacheMetadata; import me.lucko.luckperms.common.calculator.CalculatorFactory; @@ -40,6 +38,9 @@ import me.lucko.luckperms.common.config.ConfigKeys; import net.luckperms.api.query.QueryOptions; +import java.util.ArrayList; +import java.util.List; + public class BungeeCalculatorFactory implements CalculatorFactory { private final LPBungeePlugin plugin; @@ -49,7 +50,7 @@ public class BungeeCalculatorFactory implements CalculatorFactory { @Override public PermissionCalculator build(QueryOptions queryOptions, CacheMetadata metadata) { - ImmutableList.Builder processors = ImmutableList.builder(); + List processors = new ArrayList<>(4); processors.add(new DirectProcessor()); @@ -65,6 +66,6 @@ public class BungeeCalculatorFactory implements CalculatorFactory { processors.add(new SpongeWildcardProcessor()); } - return new PermissionCalculator(this.plugin, metadata, processors.build()); + return new PermissionCalculator(this.plugin, metadata, processors); } } diff --git a/common/src/main/java/me/lucko/luckperms/common/calculator/PermissionCalculator.java b/common/src/main/java/me/lucko/luckperms/common/calculator/PermissionCalculator.java index af84a7fc2..bde9a65bb 100644 --- a/common/src/main/java/me/lucko/luckperms/common/calculator/PermissionCalculator.java +++ b/common/src/main/java/me/lucko/luckperms/common/calculator/PermissionCalculator.java @@ -25,8 +25,6 @@ package me.lucko.luckperms.common.calculator; -import com.google.common.collect.ImmutableList; - import me.lucko.luckperms.common.cache.LoadingMap; import me.lucko.luckperms.common.cacheddata.CacheMetadata; import me.lucko.luckperms.common.calculator.processor.PermissionProcessor; @@ -37,7 +35,7 @@ import me.lucko.luckperms.common.verbose.event.PermissionCheckEvent; import org.checkerframework.checker.nullness.qual.NonNull; -import java.util.List; +import java.util.Collection; import java.util.Map; import java.util.function.Function; @@ -53,7 +51,7 @@ public class PermissionCalculator implements Function { private final CacheMetadata metadata; /** The processors which back this calculator */ - private final ImmutableList processors; + private final PermissionProcessor[] processors; /** Loading cache for permission checks */ private final LoadingMap lookupCache = LoadingMap.of(this); @@ -61,10 +59,10 @@ public class PermissionCalculator implements Function { /** The object name passed to the verbose handler when checks are made */ private final String verboseCheckTarget; - public PermissionCalculator(LuckPermsPlugin plugin, CacheMetadata metadata, ImmutableList processors) { + public PermissionCalculator(LuckPermsPlugin plugin, CacheMetadata metadata, Collection processors) { this.plugin = plugin; this.metadata = metadata; - this.processors = processors; + this.processors = processors.toArray(new PermissionProcessor[0]); if (this.metadata.getHolderType() == HolderType.GROUP) { this.verboseCheckTarget = "group/" + this.metadata.getObjectName(); @@ -124,10 +122,6 @@ public class PermissionCalculator implements Function { } } - public List getProcessors() { - return this.processors; - } - public void invalidateCache() { for (PermissionProcessor processor : this.processors) { processor.invalidate(); diff --git a/common/src/main/java/me/lucko/luckperms/common/context/ContextManager.java b/common/src/main/java/me/lucko/luckperms/common/context/ContextManager.java index 731cb37f6..779763ae2 100644 --- a/common/src/main/java/me/lucko/luckperms/common/context/ContextManager.java +++ b/common/src/main/java/me/lucko/luckperms/common/context/ContextManager.java @@ -31,6 +31,7 @@ import me.lucko.luckperms.common.context.contextset.ImmutableContextSetImpl; import me.lucko.luckperms.common.plugin.LuckPermsPlugin; import net.luckperms.api.context.ContextCalculator; +import net.luckperms.api.context.ContextConsumer; import net.luckperms.api.context.ContextSet; import net.luckperms.api.context.ImmutableContextSet; import net.luckperms.api.context.StaticContextCalculator; @@ -38,9 +39,9 @@ import net.luckperms.api.query.QueryOptions; import org.checkerframework.checker.nullness.qual.NonNull; +import java.util.ArrayList; import java.util.List; import java.util.UUID; -import java.util.concurrent.CopyOnWriteArrayList; import java.util.concurrent.TimeUnit; /** @@ -54,8 +55,7 @@ public abstract class ContextManager { private final Class subjectClass; private final Class

playerClass; - private final List> calculators = new CopyOnWriteArrayList<>(); - private final List staticCalculators = new CopyOnWriteArrayList<>(); + private final CalculatorList calculators = new CalculatorList(); // caches static context lookups private final StaticLookupCache staticLookupCache = new StaticLookupCache(); @@ -115,49 +115,47 @@ public abstract class ContextManager { protected abstract void invalidateCache(S subject); public void registerCalculator(ContextCalculator calculator) { - // calculators registered first should have priority (and be checked last.) - this.calculators.add(0, calculator); - - if (calculator instanceof StaticContextCalculator) { - StaticContextCalculator staticCalculator = (StaticContextCalculator) calculator; - this.staticCalculators.add(0, staticCalculator); - } + this.calculators.add(calculator); } public void unregisterCalculator(ContextCalculator calculator) { this.calculators.remove(calculator); - if (calculator instanceof StaticContextCalculator) { - this.staticCalculators.remove(calculator); - } } protected QueryOptions calculate(S subject) { ImmutableContextSet.Builder accumulator = new ImmutableContextSetImpl.BuilderImpl(); - for (ContextCalculator calculator : this.calculators) { + ContextConsumer consumer = accumulator::add; + + for (ContextCalculator calculator : this.calculators.calculators()) { try { - calculator.calculate(subject, accumulator::add); + calculator.calculate(subject, consumer); } catch (Throwable e) { this.plugin.getLogger().warn("An exception was thrown by " + getCalculatorClass(calculator) + " whilst calculating the context of subject " + subject, e); } } + return formQueryOptions(subject, accumulator.build()); } private QueryOptions calculateStatic() { ImmutableContextSet.Builder accumulator = new ImmutableContextSetImpl.BuilderImpl(); - for (StaticContextCalculator calculator : this.staticCalculators) { + ContextConsumer consumer = accumulator::add; + + for (StaticContextCalculator calculator : this.calculators.staticCalculators()) { try { - calculator.calculate(accumulator::add); + calculator.calculate(consumer); } catch (Throwable e) { this.plugin.getLogger().warn("An exception was thrown by " + getCalculatorClass(calculator) + " whilst calculating static contexts", e); } } + return formQueryOptions(accumulator.build()); } public ImmutableContextSet getPotentialContexts() { ImmutableContextSet.Builder builder = new ImmutableContextSetImpl.BuilderImpl(); - for (ContextCalculator calculator : this.calculators) { + + for (ContextCalculator calculator : this.calculators.calculators()) { ContextSet potentialContexts; try { potentialContexts = calculator.estimatePotentialContexts(); @@ -167,6 +165,7 @@ public abstract class ContextManager { } builder.addAll(potentialContexts); } + return builder.build(); } @@ -191,4 +190,57 @@ public abstract class ContextManager { return calculatorClass.getName(); } + private final class CalculatorList { + private final List> calculators; + private final List staticCalculators; + + private volatile ContextCalculator[] calculatorsArray; + private volatile StaticContextCalculator[] staticCalculatorsArray; + + CalculatorList() { + this.calculators = new ArrayList<>(); + this.staticCalculators = new ArrayList<>(); + bake(); + } + + @SuppressWarnings("unchecked") + private void bake() { + this.calculatorsArray = this.calculators.toArray(new ContextCalculator[0]); + this.staticCalculatorsArray = this.staticCalculators.toArray(new StaticContextCalculator[0]); + } + + public void add(ContextCalculator calculator) { + synchronized (this) { + // calculators registered first should have priority (and be checked last.) + this.calculators.add(0, calculator); + + if (calculator instanceof StaticContextCalculator) { + StaticContextCalculator staticCalculator = (StaticContextCalculator) calculator; + this.staticCalculators.add(0, staticCalculator); + } + + bake(); + } + } + + public void remove(ContextCalculator calculator) { + synchronized (this) { + this.calculators.remove(calculator); + if (calculator instanceof StaticContextCalculator) { + this.staticCalculators.remove(calculator); + } + + bake(); + } + } + + public ContextCalculator[] calculators() { + return this.calculatorsArray; + } + + public StaticContextCalculator[] staticCalculators() { + return this.staticCalculatorsArray; + } + } + } diff --git a/fabric/src/main/java/me/lucko/luckperms/fabric/FabricCalculatorFactory.java b/fabric/src/main/java/me/lucko/luckperms/fabric/FabricCalculatorFactory.java index e77bf2345..3c78fa39e 100644 --- a/fabric/src/main/java/me/lucko/luckperms/fabric/FabricCalculatorFactory.java +++ b/fabric/src/main/java/me/lucko/luckperms/fabric/FabricCalculatorFactory.java @@ -25,8 +25,6 @@ package me.lucko.luckperms.fabric; -import com.google.common.collect.ImmutableList; - import me.lucko.luckperms.common.cacheddata.CacheMetadata; import me.lucko.luckperms.common.calculator.CalculatorFactory; import me.lucko.luckperms.common.calculator.PermissionCalculator; @@ -41,6 +39,9 @@ import me.lucko.luckperms.fabric.context.FabricContextManager; import net.luckperms.api.query.QueryOptions; +import java.util.ArrayList; +import java.util.List; + public class FabricCalculatorFactory implements CalculatorFactory { private final LPFabricPlugin plugin; @@ -50,7 +51,7 @@ public class FabricCalculatorFactory implements CalculatorFactory { @Override public PermissionCalculator build(QueryOptions queryOptions, CacheMetadata metadata) { - ImmutableList.Builder processors = ImmutableList.builder(); + List processors = new ArrayList<>(5); processors.add(new DirectProcessor()); @@ -71,6 +72,6 @@ public class FabricCalculatorFactory implements CalculatorFactory { processors.add(new ServerOwnerProcessor()); } - return new PermissionCalculator(this.plugin, metadata, processors.build()); + return new PermissionCalculator(this.plugin, metadata, processors); } } diff --git a/nukkit/src/main/java/me/lucko/luckperms/nukkit/calculator/NukkitCalculatorFactory.java b/nukkit/src/main/java/me/lucko/luckperms/nukkit/calculator/NukkitCalculatorFactory.java index 756c1c7c7..564282c3c 100644 --- a/nukkit/src/main/java/me/lucko/luckperms/nukkit/calculator/NukkitCalculatorFactory.java +++ b/nukkit/src/main/java/me/lucko/luckperms/nukkit/calculator/NukkitCalculatorFactory.java @@ -25,8 +25,6 @@ package me.lucko.luckperms.nukkit.calculator; -import com.google.common.collect.ImmutableList; - import me.lucko.luckperms.common.cacheddata.CacheMetadata; import me.lucko.luckperms.common.calculator.CalculatorFactory; import me.lucko.luckperms.common.calculator.PermissionCalculator; @@ -42,6 +40,9 @@ import me.lucko.luckperms.nukkit.context.NukkitContextManager; import net.luckperms.api.query.QueryOptions; +import java.util.ArrayList; +import java.util.List; + public class NukkitCalculatorFactory implements CalculatorFactory { private final LPNukkitPlugin plugin; @@ -51,7 +52,7 @@ public class NukkitCalculatorFactory implements CalculatorFactory { @Override public PermissionCalculator build(QueryOptions queryOptions, CacheMetadata metadata) { - ImmutableList.Builder processors = ImmutableList.builder(); + List processors = new ArrayList<>(7); processors.add(new DirectProcessor()); @@ -81,6 +82,6 @@ public class NukkitCalculatorFactory implements CalculatorFactory { processors.add(OpProcessor.INSTANCE); } - return new PermissionCalculator(this.plugin, metadata, processors.build()); + return new PermissionCalculator(this.plugin, metadata, processors); } } diff --git a/sponge/src/main/java/me/lucko/luckperms/sponge/calculator/SpongeCalculatorFactory.java b/sponge/src/main/java/me/lucko/luckperms/sponge/calculator/SpongeCalculatorFactory.java index a1311a89b..89ade487a 100644 --- a/sponge/src/main/java/me/lucko/luckperms/sponge/calculator/SpongeCalculatorFactory.java +++ b/sponge/src/main/java/me/lucko/luckperms/sponge/calculator/SpongeCalculatorFactory.java @@ -25,8 +25,6 @@ package me.lucko.luckperms.sponge.calculator; -import com.google.common.collect.ImmutableList; - import me.lucko.luckperms.common.cacheddata.CacheMetadata; import me.lucko.luckperms.common.calculator.CalculatorFactory; import me.lucko.luckperms.common.calculator.PermissionCalculator; @@ -41,6 +39,9 @@ import me.lucko.luckperms.sponge.LPSpongePlugin; import net.luckperms.api.query.QueryOptions; +import java.util.ArrayList; +import java.util.List; + public class SpongeCalculatorFactory implements CalculatorFactory { private final LPSpongePlugin plugin; @@ -50,7 +51,7 @@ public class SpongeCalculatorFactory implements CalculatorFactory { @Override public PermissionCalculator build(QueryOptions queryOptions, CacheMetadata metadata) { - ImmutableList.Builder processors = ImmutableList.builder(); + List processors = new ArrayList<>(6); processors.add(new DirectProcessor()); @@ -75,6 +76,6 @@ public class SpongeCalculatorFactory implements CalculatorFactory { } } - return new PermissionCalculator(this.plugin, metadata, processors.build()); + return new PermissionCalculator(this.plugin, metadata, processors); } } diff --git a/sponge/src/main/java/me/lucko/luckperms/sponge/service/model/calculated/CalculatedSubjectCachedDataManager.java b/sponge/src/main/java/me/lucko/luckperms/sponge/service/model/calculated/CalculatedSubjectCachedDataManager.java index fe9acd712..389192480 100644 --- a/sponge/src/main/java/me/lucko/luckperms/sponge/service/model/calculated/CalculatedSubjectCachedDataManager.java +++ b/sponge/src/main/java/me/lucko/luckperms/sponge/service/model/calculated/CalculatedSubjectCachedDataManager.java @@ -46,6 +46,8 @@ import net.luckperms.api.metastacking.MetaStackDefinition; import net.luckperms.api.node.ChatMetaType; import net.luckperms.api.query.QueryOptions; +import java.util.ArrayList; +import java.util.List; import java.util.Map; import java.util.function.IntFunction; @@ -97,7 +99,7 @@ public class CalculatedSubjectCachedDataManager extends AbstractCachedDataManage @Override public PermissionCalculator build(QueryOptions queryOptions, CacheMetadata metadata) { - ImmutableList.Builder processors = ImmutableList.builder(); + List processors = new ArrayList<>(4); processors.add(new DirectProcessor()); processors.add(new SpongeWildcardProcessor()); processors.add(new WildcardProcessor()); @@ -106,6 +108,6 @@ public class CalculatedSubjectCachedDataManager extends AbstractCachedDataManage processors.add(new FixedDefaultsProcessor(this.subject.getService(), queryOptions, this.subject.getDefaults(), true)); } - return new PermissionCalculator(getPlugin(), metadata, processors.build()); + return new PermissionCalculator(getPlugin(), metadata, processors); } } diff --git a/velocity/src/main/java/me/lucko/luckperms/velocity/calculator/VelocityCalculatorFactory.java b/velocity/src/main/java/me/lucko/luckperms/velocity/calculator/VelocityCalculatorFactory.java index 70a0df280..694eebf39 100644 --- a/velocity/src/main/java/me/lucko/luckperms/velocity/calculator/VelocityCalculatorFactory.java +++ b/velocity/src/main/java/me/lucko/luckperms/velocity/calculator/VelocityCalculatorFactory.java @@ -25,8 +25,6 @@ package me.lucko.luckperms.velocity.calculator; -import com.google.common.collect.ImmutableList; - import me.lucko.luckperms.common.cacheddata.CacheMetadata; import me.lucko.luckperms.common.calculator.CalculatorFactory; import me.lucko.luckperms.common.calculator.PermissionCalculator; @@ -40,6 +38,9 @@ import me.lucko.luckperms.velocity.LPVelocityPlugin; import net.luckperms.api.query.QueryOptions; +import java.util.ArrayList; +import java.util.List; + public class VelocityCalculatorFactory implements CalculatorFactory { private final LPVelocityPlugin plugin; @@ -49,7 +50,7 @@ public class VelocityCalculatorFactory implements CalculatorFactory { @Override public PermissionCalculator build(QueryOptions queryOptions, CacheMetadata metadata) { - ImmutableList.Builder processors = ImmutableList.builder(); + List processors = new ArrayList<>(4); processors.add(new DirectProcessor()); @@ -65,6 +66,6 @@ public class VelocityCalculatorFactory implements CalculatorFactory { processors.add(new SpongeWildcardProcessor()); } - return new PermissionCalculator(this.plugin, metadata, processors.build()); + return new PermissionCalculator(this.plugin, metadata, processors); } }