From ae3adf23c8beb4b015dc92cc07438b6d54a642e5 Mon Sep 17 00:00:00 2001 From: Luck Date: Tue, 24 Jul 2018 21:21:05 -0700 Subject: [PATCH] Fail silently when plugins use reflection to add to dummy permissibles (#1117) --- .../model/dummy/DummyPermissibleBase.java | 45 +++++++++++++------ .../model/dummy/DummyPermissibleBase.java | 43 ++++++++++++------ 2 files changed, 60 insertions(+), 28 deletions(-) diff --git a/bukkit/src/main/java/me/lucko/luckperms/bukkit/model/dummy/DummyPermissibleBase.java b/bukkit/src/main/java/me/lucko/luckperms/bukkit/model/dummy/DummyPermissibleBase.java index 88cd1082..c3e4a7e9 100644 --- a/bukkit/src/main/java/me/lucko/luckperms/bukkit/model/dummy/DummyPermissibleBase.java +++ b/bukkit/src/main/java/me/lucko/luckperms/bukkit/model/dummy/DummyPermissibleBase.java @@ -32,8 +32,14 @@ import org.bukkit.permissions.PermissionAttachmentInfo; import org.bukkit.plugin.Plugin; import java.lang.reflect.Field; +import java.util.ArrayList; +import java.util.Collection; import java.util.Collections; +import java.util.HashMap; +import java.util.Map; import java.util.Set; +import java.util.function.BiFunction; +import java.util.function.Function; public class DummyPermissibleBase extends PermissibleBase { private static final Field ATTACHMENTS_FIELD; @@ -51,19 +57,6 @@ public class DummyPermissibleBase extends PermissibleBase { } } - public static void nullFields(PermissibleBase permissibleBase) { - try { - ATTACHMENTS_FIELD.set(permissibleBase, Collections.emptyList()); - } catch (Exception e) { - // ignore - } - try { - PERMISSIONS_FIELD.set(permissibleBase, Collections.emptyMap()); - } catch (Exception e) { - // ignore - } - } - public static void copyFields(PermissibleBase from, PermissibleBase to) { try { ATTACHMENTS_FIELD.set(to, ATTACHMENTS_FIELD.get(from)); @@ -81,7 +74,31 @@ public class DummyPermissibleBase extends PermissibleBase { private DummyPermissibleBase() { super(null); - nullFields(this); + + // we want the singleton dummy attachment to be stateless + // the behaviour of this class is to fail silently, so we can't use Collections.emptyX + try { + ATTACHMENTS_FIELD.set(this, new ArrayList(){ + @Override public boolean add(PermissionAttachment permissionAttachment) { return true; } + @Override public void add(int index, PermissionAttachment element) { } + @Override public boolean addAll(Collection c) { return true; } + @Override public boolean addAll(int index, Collection c) { return true; } + }); + } catch (Exception e) { + // ignore + } + try { + PERMISSIONS_FIELD.set(this, new HashMap() { + @Override public PermissionAttachmentInfo put(String key, PermissionAttachmentInfo value) { return null; } + @Override public void putAll(Map m) { } + @Override public PermissionAttachmentInfo putIfAbsent(String key, PermissionAttachmentInfo value) { return null; } + @Override public PermissionAttachmentInfo compute(String key, BiFunction remappingFunction) { return null; } + @Override public PermissionAttachmentInfo computeIfPresent(String key, BiFunction remappingFunction) { return null; } + @Override public PermissionAttachmentInfo computeIfAbsent(String key, Function mappingFunction) { return null; } + }); + } catch (Exception e) { + // ignore + } } @Override public boolean isOp() { return false; } diff --git a/nukkit/src/main/java/me/lucko/luckperms/nukkit/model/dummy/DummyPermissibleBase.java b/nukkit/src/main/java/me/lucko/luckperms/nukkit/model/dummy/DummyPermissibleBase.java index d9dc48d7..599643da 100644 --- a/nukkit/src/main/java/me/lucko/luckperms/nukkit/model/dummy/DummyPermissibleBase.java +++ b/nukkit/src/main/java/me/lucko/luckperms/nukkit/model/dummy/DummyPermissibleBase.java @@ -33,11 +33,15 @@ import cn.nukkit.plugin.Plugin; import java.lang.reflect.Field; import java.util.AbstractList; +import java.util.ArrayList; import java.util.Collection; import java.util.Collections; +import java.util.HashMap; import java.util.List; import java.util.Map; import java.util.RandomAccess; +import java.util.function.BiFunction; +import java.util.function.Function; public class DummyPermissibleBase extends PermissibleBase { private static final Field ATTACHMENTS_FIELD; @@ -55,19 +59,6 @@ public class DummyPermissibleBase extends PermissibleBase { } } - public static void nullFields(PermissibleBase permissibleBase) { - try { - ATTACHMENTS_FIELD.set(permissibleBase, EMPTY_LIST); - } catch (Exception e) { - // ignore - } - try { - PERMISSIONS_FIELD.set(permissibleBase, Collections.emptyMap()); - } catch (Exception e) { - // ignore - } - } - public static void copyFields(PermissibleBase from, PermissibleBase to) { try { ATTACHMENTS_FIELD.set(to, ATTACHMENTS_FIELD.get(from)); @@ -85,7 +76,31 @@ public class DummyPermissibleBase extends PermissibleBase { private DummyPermissibleBase() { super(null); - nullFields(this); + + // we want the singleton dummy attachment to be stateless + // the behaviour of this class is to fail silently, so we can't use Collections.emptyX + try { + ATTACHMENTS_FIELD.set(this, new ArrayList(){ + @Override public boolean add(PermissionAttachment permissionAttachment) { return true; } + @Override public void add(int index, PermissionAttachment element) { } + @Override public boolean addAll(Collection c) { return true; } + @Override public boolean addAll(int index, Collection c) { return true; } + }); + } catch (Exception e) { + // ignore + } + try { + PERMISSIONS_FIELD.set(this, new HashMap() { + @Override public PermissionAttachmentInfo put(String key, PermissionAttachmentInfo value) { return null; } + @Override public void putAll(Map m) { } + @Override public PermissionAttachmentInfo putIfAbsent(String key, PermissionAttachmentInfo value) { return null; } + @Override public PermissionAttachmentInfo compute(String key, BiFunction remappingFunction) { return null; } + @Override public PermissionAttachmentInfo computeIfPresent(String key, BiFunction remappingFunction) { return null; } + @Override public PermissionAttachmentInfo computeIfAbsent(String key, Function mappingFunction) { return null; } + }); + } catch (Exception e) { + // ignore + } } @Override public boolean isOp() { return false; }