From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
From: tr7zw <tr7zw@live.de>
Date: Wed, 5 Aug 2020 08:05:10 -0500
Subject: [PATCH] Yatopia configuration

also some basic settings that dont deserve a patch

diff --git a/src/main/java/co/aikar/timings/TimingsExport.java b/src/main/java/co/aikar/timings/TimingsExport.java
index 55b67f1057224101272f9d6023a93872c4423405..3ec187f39250214a7a72b1d7ef7b3e2ec0c09cfa 100644
--- a/src/main/java/co/aikar/timings/TimingsExport.java
+++ b/src/main/java/co/aikar/timings/TimingsExport.java
@@ -234,6 +234,7 @@ public class TimingsExport extends Thread {
                 pair("paper", mapAsJSON(Bukkit.spigot().getPaperConfig(), null)),
                 pair("tuinity", mapAsJSON(Bukkit.spigot().getTuinityConfig(), null)), // Tuinity - add config to timings report
                 pair("purpur", mapAsJSON(Bukkit.spigot().getPurpurConfig(), null))
+                , pair("yatopia", mapAsJSON(Bukkit.spigot().getYatopiaConfig(), null)) // Yatopia - add config to timings report
                 // Purpur end
         ));
 
@@ -324,7 +325,7 @@ public class TimingsExport extends Thread {
         String response = null;
         String timingsURL = null;
         try {
-            HttpURLConnection con = (HttpURLConnection) new URL(net.pl3x.purpur.PurpurConfig.timingsUrl + "/post").openConnection(); // Purpur
+            HttpURLConnection con = (HttpURLConnection) new URL("http://timings.aikar.co/post").openConnection(); // Purpur // Yatopia
             con.setDoOutput(true);
             String hostName = "BrokenHost";
             try {
diff --git a/src/main/java/net/minecraft/server/DedicatedServer.java b/src/main/java/net/minecraft/server/DedicatedServer.java
index a85a844a4766cde16eea9e814abfec29d8935c0f..b55d73e39b5665f5444497e54e940e172109a76b 100644
--- a/src/main/java/net/minecraft/server/DedicatedServer.java
+++ b/src/main/java/net/minecraft/server/DedicatedServer.java
@@ -189,6 +189,15 @@ public class DedicatedServer extends MinecraftServer implements IMinecraftServer
         gg.airplane.commands.AirplaneCommands.init(); // Airplane - command
         gg.airplane.flare.FlareSetup.init(); // Airplane
 
+        // Yatopia start
+        try {
+            org.yatopiamc.yatopia.server.YatopiaConfig.init((java.io.File) options.valueOf("yatopia-settings"));
+        } catch (Exception e) {
+            DedicatedServer.LOGGER.error("Unable to load server configuration", e);
+            return false;
+        }
+        // Yatopia end
+
         this.setPVP(dedicatedserverproperties.pvp);
         this.setAllowFlight(dedicatedserverproperties.allowFlight);
         this.setResourcePack(dedicatedserverproperties.resourcePack, this.ba());
diff --git a/src/main/java/net/minecraft/server/EntityLiving.java b/src/main/java/net/minecraft/server/EntityLiving.java
index 7535a6689f8e67af97bff9643fabd3c615222f99..424e0a1c31561aa06229a13b68d0cc367f392545 100644
--- a/src/main/java/net/minecraft/server/EntityLiving.java
+++ b/src/main/java/net/minecraft/server/EntityLiving.java
@@ -271,6 +271,7 @@ public abstract class EntityLiving extends Entity {
         this.world.getMethodProfiler().enter("livingEntityBaseTick");
         boolean flag = this instanceof EntityHuman;
 
+        if (!org.yatopiamc.yatopia.server.YatopiaConfig.disableEntityStuckChecks) { // Yatopia
         if (this.isAlive()) {
             if (this.inBlock()) {
                 this.damageEntity(DamageSource.STUCK, 1.0F);
@@ -287,6 +288,7 @@ public abstract class EntityLiving extends Entity {
                 }
             }
         }
+        } // Yatopia
 
         if (this.isFireProof() || this.world.isClientSide) {
             this.extinguish();
diff --git a/src/main/java/net/minecraft/server/PlayerList.java b/src/main/java/net/minecraft/server/PlayerList.java
index f80371ce1665d0760ad0553a2a057a955c56669c..7aee575ab7bffe8eda4a9fc8c06e580340893fdd 100644
--- a/src/main/java/net/minecraft/server/PlayerList.java
+++ b/src/main/java/net/minecraft/server/PlayerList.java
@@ -187,7 +187,7 @@ public abstract class PlayerList {
         // Spigot - view distance
         playerconnection.sendPacket(new PacketPlayOutLogin(entityplayer.getId(), entityplayer.playerInteractManager.getGameMode(), entityplayer.playerInteractManager.c(), BiomeManager.a(worldserver1.getSeed()), worlddata.isHardcore(), this.server.F(), this.s, worldserver1.getDimensionManager(), worldserver1.getDimensionKey(), this.getMaxPlayers(), worldserver1.getChunkProvider().playerChunkMap.getLoadViewDistance(), flag1, !flag, worldserver1.isDebugWorld(), worldserver1.isFlatWorld())); // Paper - no-tick view distance
         entityplayer.getBukkitEntity().sendSupportedChannels(); // CraftBukkit
-        playerconnection.sendPacket(new PacketPlayOutCustomPayload(PacketPlayOutCustomPayload.a, (new PacketDataSerializer(Unpooled.buffer())).a(this.getServer().getServerModName())));
+        playerconnection.sendPacket(new PacketPlayOutCustomPayload(PacketPlayOutCustomPayload.a, (new PacketDataSerializer(Unpooled.buffer())).a(org.yatopiamc.yatopia.server.YatopiaConfig.brandName))); // Yatopia
         playerconnection.sendPacket(new PacketPlayOutServerDifficulty(worlddata.getDifficulty(), worlddata.isDifficultyLocked()));
         playerconnection.sendPacket(new PacketPlayOutAbilities(entityplayer.abilities));
         playerconnection.sendPacket(new PacketPlayOutHeldItemSlot(entityplayer.inventory.itemInHandIndex));
diff --git a/src/main/java/org/bukkit/craftbukkit/CraftServer.java b/src/main/java/org/bukkit/craftbukkit/CraftServer.java
index e9d3883f5c322ad8437c87aa2ccc0ecaa6f01bae..89456056da3420055a9366fdddfa858e78664329 100644
--- a/src/main/java/org/bukkit/craftbukkit/CraftServer.java
+++ b/src/main/java/org/bukkit/craftbukkit/CraftServer.java
@@ -860,6 +860,7 @@ public final class CraftServer implements Server {
             playerList.getProfileBans().load();
         } catch (IOException ex) {
             logger.log(Level.WARNING, "Failed to load banned-players.json, " + ex.getMessage());
+        org.yatopiamc.yatopia.server.YatopiaConfig.init((File) console.options.valueOf("yatopia-settings")); // Yatopia
         }
 
         org.spigotmc.SpigotConfig.init((File) console.options.valueOf("spigot-settings")); // Spigot
@@ -2380,6 +2381,13 @@ public final class CraftServer implements Server {
             org.spigotmc.RestartCommand.restart();
         }
 
+        // Yatopia start
+        @Override
+        public YamlConfiguration getYatopiaConfig() {
+            return org.yatopiamc.yatopia.server.YatopiaConfig.config;
+        }
+        // Yatopia end
+
         @Override
         public void broadcast(BaseComponent component) {
             for (Player player : getOnlinePlayers()) {
diff --git a/src/main/java/org/bukkit/craftbukkit/Main.java b/src/main/java/org/bukkit/craftbukkit/Main.java
index e51dcb259d511c369806a83b96c2820f316e1401..e65f4b990c24e6cee850521f9ad02c2bf4c85ad6 100644
--- a/src/main/java/org/bukkit/craftbukkit/Main.java
+++ b/src/main/java/org/bukkit/craftbukkit/Main.java
@@ -162,6 +162,14 @@ public class Main {
                         .describedAs("Yml file");
                 // Origami end - Server Config
 
+                // Yatopia start
+                acceptsAll(asList("yatopia", "yatopia-settings"), "File for yatopia settings")
+                        .withRequiredArg()
+                        .ofType(File.class)
+                        .defaultsTo(new File("yatopia.yml"))
+                        .describedAs("Yml file");
+                // Yatopia end
+
                 // Paper start
                 acceptsAll(asList("server-name"), "Name of the server")
                         .withRequiredArg()
diff --git a/src/main/java/org/yatopiamc/yatopia/server/YatopiaConfig.java b/src/main/java/org/yatopiamc/yatopia/server/YatopiaConfig.java
new file mode 100644
index 0000000000000000000000000000000000000000..f5a43e607f9c13e07a0f5e7e139eed93f159185b
--- /dev/null
+++ b/src/main/java/org/yatopiamc/yatopia/server/YatopiaConfig.java
@@ -0,0 +1,192 @@
+package org.yatopiamc.yatopia.server;
+
+import com.google.common.base.Throwables;
+import java.io.File;
+import java.io.IOException;
+import java.lang.reflect.InvocationTargetException;
+import java.lang.reflect.Method;
+import java.lang.reflect.Modifier;
+import java.util.List;
+import java.util.concurrent.TimeUnit;
+import java.util.logging.Level;
+import java.util.regex.Pattern;
+import org.bukkit.Bukkit;
+import org.bukkit.configuration.InvalidConfigurationException;
+import org.bukkit.configuration.file.YamlConfiguration;
+
+public class YatopiaConfig {
+
+    public static File CONFIG_FILE;
+    private static final String HEADER = "This is the main configuration file for Yatopia.\n"
+                        + "Yatopia contains many breaking changes and settings, so know what you are doing!\n"
+                        + "You have been warned!\n";
+    /*========================================================================*/
+    public static YamlConfiguration config;
+    public static int version; // since we're remapping sidestreams' configs we need this public
+    public static boolean verbose; // since we're remapping sidestreams' configs we need this public
+    /*========================================================================*/
+
+    public static void init(File configFile) {
+        CONFIG_FILE = configFile;
+        config = new YamlConfiguration();
+        try {
+            config.load(CONFIG_FILE);
+        } catch (IOException ex) {
+        } catch (InvalidConfigurationException ex) {
+            Bukkit.getLogger().log(Level.SEVERE, "Could not load yatopia.yml, please correct your syntax errors", ex);
+            throw Throwables.propagate(ex);
+        }
+        config.options().header(HEADER);
+        config.options().copyDefaults(true);
+        verbose = getBoolean("verbose", false);
+
+        version = getInt("config-version", 1);
+        set("config-version", 1);
+        removeLeftovers();
+        readConfig(YatopiaConfig.class, null);
+    }
+
+    private static void removeLeftovers() {
+        // this method is only to remove non-used values in the config
+
+        // leftover from rainforest
+        if (config.get("world-settings") != null) {
+            set("world-settings", null);
+        }
+        if (config.get("allow-player-item-duplication") != null) {
+            set("allow-player-item-duplication", null);
+        }
+        if (config.get("allow-ridable-chestable-duping") != null) {
+            set("allow-ridable-chestable-duping", null);
+        }
+        if (config.get("allow-sand-duping") != null) {
+            set("allow-sand-duping", null);
+        }
+    }
+
+    protected static void logError(String s) {
+        Bukkit.getLogger().severe(s);
+    }
+
+    protected static void log(String s) {
+        if (verbose) {
+            Bukkit.getLogger().info(s);
+        }
+    }
+
+    static void readConfig(Class<?> clazz, Object instance) {
+        for (Method method : clazz.getDeclaredMethods()) {
+            if (Modifier.isPrivate(method.getModifiers())) {
+                if (method.getParameterTypes().length == 0 && method.getReturnType() == Void.TYPE) {
+                    try {
+                        method.setAccessible(true);
+                        method.invoke(instance);
+                    } catch (InvocationTargetException ex) {
+                        throw Throwables.propagate(ex.getCause());
+                    } catch (Exception ex) {
+                        Bukkit.getLogger().log(Level.SEVERE, "Error invoking " + method, ex);
+                    }
+                }
+            }
+        }
+
+        try {
+            config.save(CONFIG_FILE);
+        } catch (IOException ex) {
+            Bukkit.getLogger().log(Level.SEVERE, "Could not save " + CONFIG_FILE, ex);
+        }
+    }
+
+    private static final Pattern SPACE = Pattern.compile(" ");
+    private static final Pattern NOT_NUMERIC = Pattern.compile("[^-\\d.]");
+
+    public static int getSeconds(String str) {
+        str = SPACE.matcher(str).replaceAll("");
+        final char unit = str.charAt(str.length() - 1);
+        str = NOT_NUMERIC.matcher(str).replaceAll("");
+        double num;
+        try {
+            num = Double.parseDouble(str);
+        } catch (Exception e) {
+            num = 0D;
+        }
+        switch (unit) {
+            case 'd':
+                num *= (double) 60 * 60 * 24;
+                break;
+            case 'h':
+                num *= (double) 60 * 60;
+                break;
+            case 'm':
+                num *= 60;
+                break;
+            default:
+            case 's':
+                break;
+        }
+        return (int) num;
+    }
+
+    protected static String timeSummary(int seconds) {
+        String time = "";
+
+        if (seconds > 60 * 60 * 24) {
+            time += TimeUnit.SECONDS.toDays(seconds) + "d";
+            seconds %= 60 * 60 * 24;
+        }
+
+        if (seconds > 60 * 60) {
+            time += TimeUnit.SECONDS.toHours(seconds) + "h";
+            seconds %= 60 * 60;
+        }
+
+        if (seconds > 0) {
+            time += TimeUnit.SECONDS.toMinutes(seconds) + "m";
+        }
+        return time;
+    }
+
+    private static void set(String path, Object val) {
+        config.set(path, val);
+    }
+
+    private static boolean getBoolean(String path, boolean def) {
+        config.addDefault(path, def);
+        return config.getBoolean(path, config.getBoolean(path));
+    }
+
+    private static double getDouble(String path, double def) {
+        config.addDefault(path, def);
+        return config.getDouble(path, config.getDouble(path));
+    }
+
+    private static float getFloat(String path, float def) {
+        // TODO: Figure out why getFloat() always returns the default value.
+        return (float) getDouble(path, (double) def);
+    }
+
+    private static int getInt(String path, int def) {
+        config.addDefault(path, def);
+        return config.getInt(path, config.getInt(path));
+    }
+
+    private static <T> List<T> getList(String path, List<T> def) {
+        config.addDefault(path, def);
+        return (List<T>) config.getList(path, config.getList(path));
+    }
+
+    private static String getString(String path, String def) {
+        config.addDefault(path, def);
+        return config.getString(path, config.getString(path));
+    }
+
+    public static boolean disableEntityStuckChecks = false;
+    private static void disableEntityStuckChecks() {
+        disableEntityStuckChecks = getBoolean("settings.disableEntityStuckChecks", false);
+    }
+
+    public static String brandName = "Yatopia";
+    private static void brandName() {
+        brandName = getString("brand-name", brandName);
+    }
+}
