From 46c84495fd1e78303f34db70034c1e7d56291655 Mon Sep 17 00:00:00 2001
From: Shane Freeder
Date: Sat, 29 Aug 2020 12:12:21 +0100
Subject: [PATCH 001/499] Updated Upstream (Waterfall)
Upstream has released updates that appears to apply and compile correctly.
This update has not been tested by PaperMC and as with ANY update, please do your own testing
Waterfall Changes:
8075dbe Updated Upstream (BungeeCord)
---
Waterfall | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/Waterfall b/Waterfall
index 056d6687..8075dbe9 160000
--- a/Waterfall
+++ b/Waterfall
@@ -1 +1 @@
-Subproject commit 056d6687ef3c6ce080bac254ba86b306a4d233d4
+Subproject commit 8075dbe95dbc5da9dd9fecd61263a5ce85d3c4e3
From e92af6a3c71d1e2fc30b459610354f22859b11f6 Mon Sep 17 00:00:00 2001
From: "Five (Xer)"
Date: Thu, 10 Sep 2020 18:03:11 +0200
Subject: [PATCH 002/499] 1.16.3-patch
---
.../0004-Travertine-1.16.3-Patch.patch | 31 +++++++++++++++++++
1 file changed, 31 insertions(+)
create mode 100644 Waterfall-Proxy-Patches/0004-Travertine-1.16.3-Patch.patch
diff --git a/Waterfall-Proxy-Patches/0004-Travertine-1.16.3-Patch.patch b/Waterfall-Proxy-Patches/0004-Travertine-1.16.3-Patch.patch
new file mode 100644
index 00000000..fee863ad
--- /dev/null
+++ b/Waterfall-Proxy-Patches/0004-Travertine-1.16.3-Patch.patch
@@ -0,0 +1,31 @@
+From e8c93c149c23d9d6d57acee204780c952a3394bf Mon Sep 17 00:00:00 2001
+From: "Five (Xer)"
+Date: Thu, 10 Sep 2020 17:59:48 +0200
+Subject: [PATCH] Travertine-1.16.3-Patch
+
+
+diff --git a/protocol/src/main/java/net/md_5/bungee/protocol/ProtocolConstants.java b/protocol/src/main/java/net/md_5/bungee/protocol/ProtocolConstants.java
+index 6f72983f..659382c0 100644
+--- a/protocol/src/main/java/net/md_5/bungee/protocol/ProtocolConstants.java
++++ b/protocol/src/main/java/net/md_5/bungee/protocol/ProtocolConstants.java
+@@ -33,6 +33,7 @@ public class ProtocolConstants
+ public static final int MINECRAFT_1_16 = 735;
+ public static final int MINECRAFT_1_16_1 = 736;
+ public static final int MINECRAFT_1_16_2 = 751;
++ public static final int MINECRAFT_1_16_3 = 753;
+ public static final List SUPPORTED_VERSIONS = Arrays.asList(
+ "1.7.x",
+ "1.8.x",
+@@ -72,7 +73,8 @@ public class ProtocolConstants
+ ProtocolConstants.MINECRAFT_1_15_2,
+ ProtocolConstants.MINECRAFT_1_16,
+ ProtocolConstants.MINECRAFT_1_16_1,
+- ProtocolConstants.MINECRAFT_1_16_2
++ ProtocolConstants.MINECRAFT_1_16_2,
++ ProtocolConstants.MINECRAFT_1_16_3
+ );
+
+ public static final boolean isBeforeOrEq(int before, int other)
+--
+2.24.0
+
From 55f272fc4babf07526f398ef6557e6e933cedadf Mon Sep 17 00:00:00 2001
From: Shane Freeder
Date: Fri, 11 Sep 2020 00:47:38 +0100
Subject: [PATCH 003/499] Updated Upstream (Waterfall)
Upstream has released updates that appears to apply and compile correctly.
This update has not been tested by PaperMC and as with ANY update, please do your own testing
Waterfall Changes:
5aa8f70 Updated Upstream (BungeeCord)
61700eb Preliminary 1.16.3 support (#566)
---
Waterfall | 2 +-
.../0003-1.7.x-Protocol-Patch.patch | 16 +++++-----
.../0004-Travertine-1.16.3-Patch.patch | 31 -------------------
3 files changed, 9 insertions(+), 40 deletions(-)
delete mode 100644 Waterfall-Proxy-Patches/0004-Travertine-1.16.3-Patch.patch
diff --git a/Waterfall b/Waterfall
index 8075dbe9..5aa8f709 160000
--- a/Waterfall
+++ b/Waterfall
@@ -1 +1 @@
-Subproject commit 8075dbe95dbc5da9dd9fecd61263a5ce85d3c4e3
+Subproject commit 5aa8f709bbae4356c02b75120477e4002d02b9e7
diff --git a/Waterfall-Proxy-Patches/0003-1.7.x-Protocol-Patch.patch b/Waterfall-Proxy-Patches/0003-1.7.x-Protocol-Patch.patch
index 7d50c191..4e98b8c1 100644
--- a/Waterfall-Proxy-Patches/0003-1.7.x-Protocol-Patch.patch
+++ b/Waterfall-Proxy-Patches/0003-1.7.x-Protocol-Patch.patch
@@ -1,4 +1,4 @@
-From d0c1b725cdfa4e07a4a8f9bf6bb810290f4e361e Mon Sep 17 00:00:00 2001
+From f7c69bedede5970d764bbd1e80f9849ffd63ff9e Mon Sep 17 00:00:00 2001
From: Troy Frew
Date: Tue, 15 Nov 2016 10:31:04 -0500
Subject: [PATCH] 1.7.x Protocol Patch
@@ -462,7 +462,7 @@ index d372933d..1feee418 100644
java.util.function.Supplier extends DefinedPacket> constructor = protocolData.packetConstructors[id]; // Waterfall - speed up packet construction
diff --git a/protocol/src/main/java/net/md_5/bungee/protocol/ProtocolConstants.java b/protocol/src/main/java/net/md_5/bungee/protocol/ProtocolConstants.java
-index aa1b770c..6f72983f 100644
+index f33bb5c4..659382c0 100644
--- a/protocol/src/main/java/net/md_5/bungee/protocol/ProtocolConstants.java
+++ b/protocol/src/main/java/net/md_5/bungee/protocol/ProtocolConstants.java
@@ -6,6 +6,8 @@ import java.util.List;
@@ -474,15 +474,15 @@ index aa1b770c..6f72983f 100644
public static final int MINECRAFT_1_8 = 47;
public static final int MINECRAFT_1_9 = 107;
public static final int MINECRAFT_1_9_1 = 108;
-@@ -32,6 +34,7 @@ public class ProtocolConstants
- public static final int MINECRAFT_1_16_1 = 736;
+@@ -33,6 +35,7 @@ public class ProtocolConstants
public static final int MINECRAFT_1_16_2 = 751;
+ public static final int MINECRAFT_1_16_3 = 753;
public static final List SUPPORTED_VERSIONS = Arrays.asList(
+ "1.7.x",
"1.8.x",
"1.9.x",
"1.10.x",
-@@ -43,6 +46,8 @@ public class ProtocolConstants
+@@ -44,6 +47,8 @@ public class ProtocolConstants
"1.16.x"
);
public static final List SUPPORTED_VERSION_IDS = Arrays.asList(
@@ -1512,7 +1512,7 @@ index b0125245..8c2a743a 100644
{
this.compressionThreshold = compressionThreshold;
diff --git a/proxy/src/main/java/net/md_5/bungee/connection/DownstreamBridge.java b/proxy/src/main/java/net/md_5/bungee/connection/DownstreamBridge.java
-index 44e6ed3f..585afa36 100644
+index 443d19bd..326de178 100644
--- a/proxy/src/main/java/net/md_5/bungee/connection/DownstreamBridge.java
+++ b/proxy/src/main/java/net/md_5/bungee/connection/DownstreamBridge.java
@@ -20,6 +20,7 @@ import io.netty.buffer.Unpooled;
@@ -1581,7 +1581,7 @@ index 44e6ed3f..585afa36 100644
con.unsafe().sendPacket( pluginMessage );
throw CancelSendSignal.INSTANCE;
diff --git a/proxy/src/main/java/net/md_5/bungee/connection/InitialHandler.java b/proxy/src/main/java/net/md_5/bungee/connection/InitialHandler.java
-index 4b40b465..13deb6c9 100644
+index 7e6027aa..fe6ff143 100644
--- a/proxy/src/main/java/net/md_5/bungee/connection/InitialHandler.java
+++ b/proxy/src/main/java/net/md_5/bungee/connection/InitialHandler.java
@@ -12,6 +12,13 @@ import java.util.List;
@@ -2038,5 +2038,5 @@ index daf12f74..e33861ab 100644
@Override
--
-2.27.0
+2.28.0
diff --git a/Waterfall-Proxy-Patches/0004-Travertine-1.16.3-Patch.patch b/Waterfall-Proxy-Patches/0004-Travertine-1.16.3-Patch.patch
deleted file mode 100644
index fee863ad..00000000
--- a/Waterfall-Proxy-Patches/0004-Travertine-1.16.3-Patch.patch
+++ /dev/null
@@ -1,31 +0,0 @@
-From e8c93c149c23d9d6d57acee204780c952a3394bf Mon Sep 17 00:00:00 2001
-From: "Five (Xer)"
-Date: Thu, 10 Sep 2020 17:59:48 +0200
-Subject: [PATCH] Travertine-1.16.3-Patch
-
-
-diff --git a/protocol/src/main/java/net/md_5/bungee/protocol/ProtocolConstants.java b/protocol/src/main/java/net/md_5/bungee/protocol/ProtocolConstants.java
-index 6f72983f..659382c0 100644
---- a/protocol/src/main/java/net/md_5/bungee/protocol/ProtocolConstants.java
-+++ b/protocol/src/main/java/net/md_5/bungee/protocol/ProtocolConstants.java
-@@ -33,6 +33,7 @@ public class ProtocolConstants
- public static final int MINECRAFT_1_16 = 735;
- public static final int MINECRAFT_1_16_1 = 736;
- public static final int MINECRAFT_1_16_2 = 751;
-+ public static final int MINECRAFT_1_16_3 = 753;
- public static final List SUPPORTED_VERSIONS = Arrays.asList(
- "1.7.x",
- "1.8.x",
-@@ -72,7 +73,8 @@ public class ProtocolConstants
- ProtocolConstants.MINECRAFT_1_15_2,
- ProtocolConstants.MINECRAFT_1_16,
- ProtocolConstants.MINECRAFT_1_16_1,
-- ProtocolConstants.MINECRAFT_1_16_2
-+ ProtocolConstants.MINECRAFT_1_16_2,
-+ ProtocolConstants.MINECRAFT_1_16_3
- );
-
- public static final boolean isBeforeOrEq(int before, int other)
---
-2.24.0
-
From 0883f3cee79b6da0d3f53231a58c51acdc56b379 Mon Sep 17 00:00:00 2001
From: Shane Freeder
Date: Tue, 15 Sep 2020 18:15:17 +0100
Subject: [PATCH 004/499] Updated Upstream (Waterfall)
Upstream has released updates that appears to apply and compile correctly.
This update has not been tested by PaperMC and as with ANY update, please do your own testing
Waterfall Changes:
dd1fbb9 Add the ability to generate decoder traces for debugging
d1d1b58 Updated Upstream (BungeeCord)
46fa4cf Rebuild patches
fae68b0 Allow to disable tablist rewrite
---
Waterfall | 2 +-
.../0003-1.7.x-Protocol-Patch.patch | 12 ++++++------
2 files changed, 7 insertions(+), 7 deletions(-)
diff --git a/Waterfall b/Waterfall
index 5aa8f709..dd1fbb94 160000
--- a/Waterfall
+++ b/Waterfall
@@ -1 +1 @@
-Subproject commit 5aa8f709bbae4356c02b75120477e4002d02b9e7
+Subproject commit dd1fbb948b867405b0273cc346959a793a5d9d48
diff --git a/Waterfall-Proxy-Patches/0003-1.7.x-Protocol-Patch.patch b/Waterfall-Proxy-Patches/0003-1.7.x-Protocol-Patch.patch
index 4e98b8c1..bff0e17e 100644
--- a/Waterfall-Proxy-Patches/0003-1.7.x-Protocol-Patch.patch
+++ b/Waterfall-Proxy-Patches/0003-1.7.x-Protocol-Patch.patch
@@ -1,4 +1,4 @@
-From f7c69bedede5970d764bbd1e80f9849ffd63ff9e Mon Sep 17 00:00:00 2001
+From 625904bd6432d8424530b17e58f498acd862b60d Mon Sep 17 00:00:00 2001
From: Troy Frew
Date: Tue, 15 Nov 2016 10:31:04 -0500
Subject: [PATCH] 1.7.x Protocol Patch
@@ -1512,7 +1512,7 @@ index b0125245..8c2a743a 100644
{
this.compressionThreshold = compressionThreshold;
diff --git a/proxy/src/main/java/net/md_5/bungee/connection/DownstreamBridge.java b/proxy/src/main/java/net/md_5/bungee/connection/DownstreamBridge.java
-index 443d19bd..326de178 100644
+index 9e180c30..d54d8539 100644
--- a/proxy/src/main/java/net/md_5/bungee/connection/DownstreamBridge.java
+++ b/proxy/src/main/java/net/md_5/bungee/connection/DownstreamBridge.java
@@ -20,6 +20,7 @@ import io.netty.buffer.Unpooled;
@@ -1523,7 +1523,7 @@ index 443d19bd..326de178 100644
import java.util.ArrayList;
import java.util.HashMap; // Waterfall
import java.util.List;
-@@ -173,7 +174,7 @@ public class DownstreamBridge extends PacketHandler
+@@ -179,7 +180,7 @@ public class DownstreamBridge extends PacketHandler
switch ( objective.getAction() )
{
case 0:
@@ -1532,7 +1532,7 @@ index 443d19bd..326de178 100644
break;
case 1:
serverScoreboard.removeObjective( objective.getName() );
-@@ -183,7 +184,7 @@ public class DownstreamBridge extends PacketHandler
+@@ -189,7 +190,7 @@ public class DownstreamBridge extends PacketHandler
if ( oldObjective != null )
{
oldObjective.setValue( objective.getValue() );
@@ -1541,7 +1541,7 @@ index 443d19bd..326de178 100644
}
break;
default:
-@@ -280,16 +281,28 @@ public class DownstreamBridge extends PacketHandler
+@@ -286,16 +287,28 @@ public class DownstreamBridge extends PacketHandler
if ( pluginMessage.getTag().equals( con.getPendingConnection().getVersion() >= ProtocolConstants.MINECRAFT_1_13 ? "minecraft:brand" : "MC|Brand" ) )
{
@@ -1669,7 +1669,7 @@ index 4d7b1b23..ad3bdee5 100644
con.getServer().disconnect( "Quitting" );
}
diff --git a/proxy/src/main/java/net/md_5/bungee/entitymap/EntityMap.java b/proxy/src/main/java/net/md_5/bungee/entitymap/EntityMap.java
-index 45f4449c..77274ec4 100644
+index a5acf512..67b68a3b 100644
--- a/proxy/src/main/java/net/md_5/bungee/entitymap/EntityMap.java
+++ b/proxy/src/main/java/net/md_5/bungee/entitymap/EntityMap.java
@@ -35,6 +35,10 @@ public abstract class EntityMap
From 2872444b12c487ead30658f7c595d229b0dc94f6 Mon Sep 17 00:00:00 2001
From: Shane Freeder
Date: Tue, 29 Sep 2020 00:30:12 +0100
Subject: [PATCH 005/499] Updated Upstream (Waterfall)
Upstream has released updates that appears to apply and compile correctly.
This update has not been tested by PaperMC and as with ANY update, please do your own testing
Waterfall Changes:
27e2885 Bump netty to 4.1.52.Final
9bbec04 Updated Upstream (BungeeCord)
899d687 [CI-SKIP] Add plugin developers section in README.md (#556)
---
Waterfall | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/Waterfall b/Waterfall
index dd1fbb94..27e2885a 160000
--- a/Waterfall
+++ b/Waterfall
@@ -1 +1 @@
-Subproject commit dd1fbb948b867405b0273cc346959a793a5d9d48
+Subproject commit 27e2885ab3759536fb5a16a3ff388511f3665ad8
From 06fe87ce3f85bcfadeaa80f1716a15dd12be51a8 Mon Sep 17 00:00:00 2001
From: Juan Cruz Linsalata
Date: Sun, 18 Oct 2020 16:26:58 -0300
Subject: [PATCH 006/499] Updated Source
---
Waterfall | 2 +-
.../0003-1.7.x-Protocol-Patch.patch | 14 +-
.../0004-FlameCord-General-Patch.patch | 2321 ++++
.../0004-FlameCord-Initial-Patch.patch | 11109 ----------------
...lameCord-Whitelist-servers-addresses.patch | 173 -
...0005-Made-ProxyPingEvent-cancellable.patch | 76 +
...Defaulted-timeout-from-30000-to-5000.patch | 30 -
7 files changed, 2405 insertions(+), 11320 deletions(-)
create mode 100644 Waterfall-Proxy-Patches/0004-FlameCord-General-Patch.patch
delete mode 100644 Waterfall-Proxy-Patches/0004-FlameCord-Initial-Patch.patch
delete mode 100644 Waterfall-Proxy-Patches/0005-FlameCord-Whitelist-servers-addresses.patch
create mode 100644 Waterfall-Proxy-Patches/0005-Made-ProxyPingEvent-cancellable.patch
delete mode 100644 Waterfall-Proxy-Patches/0006-FlameCord-Defaulted-timeout-from-30000-to-5000.patch
diff --git a/Waterfall b/Waterfall
index 61700eb8..27e2885a 160000
--- a/Waterfall
+++ b/Waterfall
@@ -1 +1 @@
-Subproject commit 61700eb820cb16034a0ed94d54182e37736294e9
+Subproject commit 27e2885ab3759536fb5a16a3ff388511f3665ad8
diff --git a/Waterfall-Proxy-Patches/0003-1.7.x-Protocol-Patch.patch b/Waterfall-Proxy-Patches/0003-1.7.x-Protocol-Patch.patch
index 90fcf0e2..156c680a 100644
--- a/Waterfall-Proxy-Patches/0003-1.7.x-Protocol-Patch.patch
+++ b/Waterfall-Proxy-Patches/0003-1.7.x-Protocol-Patch.patch
@@ -1,4 +1,4 @@
-From ece80e18ec59cfbc0b97676bf2a09b26a97375ff Mon Sep 17 00:00:00 2001
+From f3a05a0d743b35976ff51154c5b17003668c37c8 Mon Sep 17 00:00:00 2001
From: Troy Frew
Date: Tue, 15 Nov 2016 10:31:04 -0500
Subject: [PATCH] 1.7.x Protocol Patch
@@ -1512,7 +1512,7 @@ index b0125245..8c2a743a 100644
{
this.compressionThreshold = compressionThreshold;
diff --git a/proxy/src/main/java/net/md_5/bungee/connection/DownstreamBridge.java b/proxy/src/main/java/net/md_5/bungee/connection/DownstreamBridge.java
-index 443d19bd..326de178 100644
+index 9e180c30..d54d8539 100644
--- a/proxy/src/main/java/net/md_5/bungee/connection/DownstreamBridge.java
+++ b/proxy/src/main/java/net/md_5/bungee/connection/DownstreamBridge.java
@@ -20,6 +20,7 @@ import io.netty.buffer.Unpooled;
@@ -1523,7 +1523,7 @@ index 443d19bd..326de178 100644
import java.util.ArrayList;
import java.util.HashMap; // Waterfall
import java.util.List;
-@@ -173,7 +174,7 @@ public class DownstreamBridge extends PacketHandler
+@@ -179,7 +180,7 @@ public class DownstreamBridge extends PacketHandler
switch ( objective.getAction() )
{
case 0:
@@ -1532,7 +1532,7 @@ index 443d19bd..326de178 100644
break;
case 1:
serverScoreboard.removeObjective( objective.getName() );
-@@ -183,7 +184,7 @@ public class DownstreamBridge extends PacketHandler
+@@ -189,7 +190,7 @@ public class DownstreamBridge extends PacketHandler
if ( oldObjective != null )
{
oldObjective.setValue( objective.getValue() );
@@ -1541,7 +1541,7 @@ index 443d19bd..326de178 100644
}
break;
default:
-@@ -280,16 +281,28 @@ public class DownstreamBridge extends PacketHandler
+@@ -286,16 +287,28 @@ public class DownstreamBridge extends PacketHandler
if ( pluginMessage.getTag().equals( con.getPendingConnection().getVersion() >= ProtocolConstants.MINECRAFT_1_13 ? "minecraft:brand" : "MC|Brand" ) )
{
@@ -1581,7 +1581,7 @@ index 443d19bd..326de178 100644
con.unsafe().sendPacket( pluginMessage );
throw CancelSendSignal.INSTANCE;
diff --git a/proxy/src/main/java/net/md_5/bungee/connection/InitialHandler.java b/proxy/src/main/java/net/md_5/bungee/connection/InitialHandler.java
-index 4b40b465..13deb6c9 100644
+index 7e6027aa..fe6ff143 100644
--- a/proxy/src/main/java/net/md_5/bungee/connection/InitialHandler.java
+++ b/proxy/src/main/java/net/md_5/bungee/connection/InitialHandler.java
@@ -12,6 +12,13 @@ import java.util.List;
@@ -1669,7 +1669,7 @@ index 4d7b1b23..ad3bdee5 100644
con.getServer().disconnect( "Quitting" );
}
diff --git a/proxy/src/main/java/net/md_5/bungee/entitymap/EntityMap.java b/proxy/src/main/java/net/md_5/bungee/entitymap/EntityMap.java
-index 45f4449c..77274ec4 100644
+index a5acf512..67b68a3b 100644
--- a/proxy/src/main/java/net/md_5/bungee/entitymap/EntityMap.java
+++ b/proxy/src/main/java/net/md_5/bungee/entitymap/EntityMap.java
@@ -35,6 +35,10 @@ public abstract class EntityMap
diff --git a/Waterfall-Proxy-Patches/0004-FlameCord-General-Patch.patch b/Waterfall-Proxy-Patches/0004-FlameCord-General-Patch.patch
new file mode 100644
index 00000000..671d79bd
--- /dev/null
+++ b/Waterfall-Proxy-Patches/0004-FlameCord-General-Patch.patch
@@ -0,0 +1,2321 @@
+From b5fbd45e9ba865cb9af6f9aa4f75afb140db7647 Mon Sep 17 00:00:00 2001
+From: Juan Cruz Linsalata
+Date: Mon, 12 Oct 2020 15:40:53 -0300
+Subject: [PATCH] FlameCord General Patch
+
+
+diff --git a/api/.factorypath b/api/.factorypath
+new file mode 100644
+index 00000000..29bce69c
+--- /dev/null
++++ b/api/.factorypath
+@@ -0,0 +1,17 @@
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
+diff --git a/api/src/main/java/net/md_5/bungee/api/event/AsyncEvent.java b/api/src/main/java/net/md_5/bungee/api/event/AsyncEvent.java
+index cf85ca06..8a945a99 100644
+--- a/api/src/main/java/net/md_5/bungee/api/event/AsyncEvent.java
++++ b/api/src/main/java/net/md_5/bungee/api/event/AsyncEvent.java
+@@ -25,7 +25,8 @@ import net.md_5.bungee.api.plugin.Plugin;
+ @EqualsAndHashCode(callSuper = true)
+ public class AsyncEvent extends Event
+ {
+-
++ // FlameCord - Make a getter for the callback
++ @Getter
+ private final Callback done;
+ private final Map intents = new ConcurrentHashMap<>();
+ private final AtomicBoolean fired = new AtomicBoolean();
+diff --git a/api/src/main/java/net/md_5/bungee/api/event/PlayerHandshakeEvent.java b/api/src/main/java/net/md_5/bungee/api/event/PlayerHandshakeEvent.java
+index 2f7b38d9..e29b0ed3 100644
+--- a/api/src/main/java/net/md_5/bungee/api/event/PlayerHandshakeEvent.java
++++ b/api/src/main/java/net/md_5/bungee/api/event/PlayerHandshakeEvent.java
+@@ -2,8 +2,11 @@ package net.md_5.bungee.api.event;
+
+ import lombok.Data;
+ import lombok.EqualsAndHashCode;
++import lombok.Getter;
++import lombok.Setter;
+ import lombok.ToString;
+ import net.md_5.bungee.api.connection.PendingConnection;
++import net.md_5.bungee.api.plugin.Cancellable;
+ import net.md_5.bungee.api.plugin.Event;
+ import net.md_5.bungee.protocol.packet.Handshake;
+
+@@ -14,8 +17,11 @@ import net.md_5.bungee.protocol.packet.Handshake;
+ @Data
+ @ToString(callSuper = false)
+ @EqualsAndHashCode(callSuper = false)
+-public class PlayerHandshakeEvent extends Event
+-{
++// FlameCord - Implement cancellable
++public class PlayerHandshakeEvent extends Event implements Cancellable {
++ @Getter
++ @Setter
++ private boolean cancelled = false;
+
+ /**
+ * Connection attempting to login.
+diff --git a/bootstrap/.factorypath b/bootstrap/.factorypath
+new file mode 100644
+index 00000000..b9f2c65d
+--- /dev/null
++++ b/bootstrap/.factorypath
+@@ -0,0 +1,37 @@
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
+diff --git a/chat/.factorypath b/chat/.factorypath
+new file mode 100644
+index 00000000..ed4e646c
+--- /dev/null
++++ b/chat/.factorypath
+@@ -0,0 +1,6 @@
++
++
++
++
++
++
+diff --git a/config/.factorypath b/config/.factorypath
+new file mode 100644
+index 00000000..6e60b565
+--- /dev/null
++++ b/config/.factorypath
+@@ -0,0 +1,7 @@
++
++
++
++
++
++
++
+diff --git a/event/.factorypath b/event/.factorypath
+new file mode 100644
+index 00000000..f398f41e
+--- /dev/null
++++ b/event/.factorypath
+@@ -0,0 +1,5 @@
++
++
++
++
++
+diff --git a/flamecord/.factorypath b/flamecord/.factorypath
+new file mode 100644
+index 00000000..ed4e646c
+--- /dev/null
++++ b/flamecord/.factorypath
+@@ -0,0 +1,6 @@
++
++
++
++
++
++
+diff --git a/flamecord/pom.xml b/flamecord/pom.xml
+new file mode 100644
+index 00000000..dd511dac
+--- /dev/null
++++ b/flamecord/pom.xml
+@@ -0,0 +1,44 @@
++
++ 4.0.0
++
++
++ io.github.waterfallmc
++ travertine-parent
++ 1.16-R0.4-SNAPSHOT
++ ../pom.xml
++
++
++ dev._2lstudios
++ travertine-flamecord
++ 1.16-R0.4-SNAPSHOT
++ jar
++
++ Travertine-FlameCord
++ FlameCord adds security essentials and new configuration options
++
++
++
++ io.github.waterfallmc
++ travertine-config
++ ${project.version}
++ compile
++
++
++ io.github.waterfallmc
++ travertine-chat
++ ${project.version}
++ compile
++
++
++
++
++ ${project.name}
++
++
++ true
++ ${basedir}/src/main/resources
++
++
++
++
+diff --git a/flamecord/src/main/java/dev/_2lstudios/flamecord/FlameCord.java b/flamecord/src/main/java/dev/_2lstudios/flamecord/FlameCord.java
+new file mode 100644
+index 00000000..fd889644
+--- /dev/null
++++ b/flamecord/src/main/java/dev/_2lstudios/flamecord/FlameCord.java
+@@ -0,0 +1,68 @@
++package dev._2lstudios.flamecord;
++
++import java.util.Collection;
++import java.util.logging.Logger;
++
++import dev._2lstudios.flamecord.configuration.FlameCordConfiguration;
++import dev._2lstudios.flamecord.configuration.MessagesConfiguration;
++import dev._2lstudios.flamecord.configuration.ModulesConfiguration;
++import dev._2lstudios.flamecord.firewall.FirewallManager;
++import lombok.Getter;
++import net.md_5.bungee.config.ConfigurationProvider;
++import net.md_5.bungee.config.YamlConfiguration;
++
++public class FlameCord {
++ @Getter
++ private static FlameCord instance;
++ @Getter
++ private final FirewallManager firewallManager;
++ @Getter
++ private final FlameCordConfiguration flameCordConfiguration;
++ @Getter
++ private final ModulesConfiguration modulesConfiguration;
++ @Getter
++ private final MessagesConfiguration messagesConfiguration;
++ @Getter
++ private final Thread thread;
++ private boolean running = true;
++
++ public static void renew(final Logger logger, final Collection whitelistedAddresses) {
++ if (FlameCord.instance != null) {
++ FlameCord.instance.running = false;
++ }
++
++ final FlameCord instance = new FlameCord(logger, whitelistedAddresses);
++
++ FlameCord.instance = instance;
++ }
++
++ private FlameCord(final Logger logger, final Collection whitelistedAddresses) {
++ final ConfigurationProvider configurationProvider = ConfigurationProvider.getProvider(YamlConfiguration.class);
++
++ this.flameCordConfiguration = new FlameCordConfiguration(configurationProvider);
++ this.firewallManager = new FirewallManager(logger, whitelistedAddresses,
++ flameCordConfiguration.getFirewallSeconds());
++ this.modulesConfiguration = new ModulesConfiguration(configurationProvider);
++ this.messagesConfiguration = new MessagesConfiguration(logger, configurationProvider);
++ this.thread = new Thread() {
++ @Override
++ public void run() {
++ while (running) {
++ try {
++ sleep(1000L);
++
++ if (!running) {
++ return;
++ }
++
++ firewallManager.tick();
++ } catch (final Exception e) {
++ // Ignored
++ }
++ }
++ }
++ };
++
++ this.thread.start();
++ }
++}
+\ No newline at end of file
+diff --git a/flamecord/src/main/java/dev/_2lstudios/flamecord/configuration/FlameCordConfiguration.java b/flamecord/src/main/java/dev/_2lstudios/flamecord/configuration/FlameCordConfiguration.java
+new file mode 100644
+index 00000000..b7268e1d
+--- /dev/null
++++ b/flamecord/src/main/java/dev/_2lstudios/flamecord/configuration/FlameCordConfiguration.java
+@@ -0,0 +1,81 @@
++package dev._2lstudios.flamecord.configuration;
++
++import java.io.File;
++import java.io.IOException;
++import java.util.ArrayList;
++import java.util.Arrays;
++import java.util.Collection;
++import java.util.HashSet;
++
++import lombok.Getter;
++import net.md_5.bungee.config.Configuration;
++import net.md_5.bungee.config.ConfigurationProvider;
++
++public class FlameCordConfiguration {
++ @Getter
++ private boolean loggerInitialhandler = false, loggerExceptions = false, loggerDump = false, firewallNotify = true,
++ firewallEnabled = true;
++ @Getter
++ private int firewallSeconds = 60;
++ @Getter
++ private Collection firewallNames = new HashSet<>(Arrays.asList(new String[] { "mcspam" }));
++
++ public FlameCordConfiguration(final ConfigurationProvider configurationProvider) {
++ try {
++ final String fileName = "./flamecord.yml";
++ final File configurationFile = new File(fileName);
++ final Configuration configuration;
++ final boolean configurationExists = configurationFile.exists();
++
++ if (!configurationExists) {
++ configuration = new Configuration();
++ } else {
++ configuration = configurationProvider.load(configurationFile);
++ }
++
++ this.loggerInitialhandler = setIfUnexistant("logger.initialhandler", this.loggerInitialhandler,
++ configuration);
++ this.loggerExceptions = setIfUnexistant("logger.exceptions", this.loggerExceptions, configuration);
++ this.loggerDump = setIfUnexistant("logger.dump", this.loggerDump, configuration);
++ this.firewallEnabled = setIfUnexistant("firewall.enabled", this.firewallEnabled, configuration);
++ this.firewallNotify = setIfUnexistant("firewall.notify", this.firewallNotify, configuration);
++ this.firewallSeconds = setIfUnexistant("firewall.seconds", this.firewallSeconds, configuration);
++ this.firewallNames = setIfUnexistant("firewall.names", this.firewallNames, configuration);
++
++ if (!configurationExists) {
++ configurationProvider.save(configuration, configurationFile);
++ }
++ } catch (final IOException e) {
++ e.printStackTrace();
++ }
++ }
++
++ private int setIfUnexistant(final String arg1, final int arg2, final Configuration configuration) {
++ return (int) setIfUnexistant(arg1, (Object) arg2, configuration);
++ }
++
++ private boolean setIfUnexistant(final String arg1, final boolean arg2, final Configuration configuration) {
++ return (boolean) setIfUnexistant(arg1, (Object) arg2, configuration);
++ }
++
++ private Object setIfUnexistant(final String arg1, final Object arg2, final Configuration configuration) {
++ if (!configuration.contains(arg1)) {
++ configuration.set(arg1, arg2);
++
++ return arg2;
++ } else {
++ return configuration.get(arg1);
++ }
++ }
++
++ private Collection setIfUnexistant(final String arg1, final Collection arg2,
++ final Configuration configuration) {
++ if (!configuration.contains(arg1)) {
++ configuration.set(arg1, new ArrayList<>(arg2));
++
++ return arg2;
++ } else {
++ return new HashSet<>(configuration.getStringList(arg1));
++ }
++ }
++}
+diff --git a/flamecord/src/main/java/dev/_2lstudios/flamecord/configuration/MessagesConfiguration.java b/flamecord/src/main/java/dev/_2lstudios/flamecord/configuration/MessagesConfiguration.java
+new file mode 100644
+index 00000000..c88077ad
+--- /dev/null
++++ b/flamecord/src/main/java/dev/_2lstudios/flamecord/configuration/MessagesConfiguration.java
+@@ -0,0 +1,129 @@
++package dev._2lstudios.flamecord.configuration;
++
++import java.io.File;
++import java.io.IOException;
++import java.text.MessageFormat;
++import java.util.HashMap;
++import java.util.Map;
++import java.util.logging.Logger;
++
++import net.md_5.bungee.api.ChatColor;
++import net.md_5.bungee.config.Configuration;
++import net.md_5.bungee.config.ConfigurationProvider;
++
++public class MessagesConfiguration {
++ private final Logger logger;
++ private final Map messages = new HashMap<>();
++
++ public MessagesConfiguration(final Logger logger, final ConfigurationProvider configurationProvider) {
++ this.logger = logger;
++
++ try {
++ final String fileName = "./messages.yml";
++ final File configurationFile = new File(fileName);
++ final Configuration configuration;
++ final boolean configurationExists = configurationFile.exists();
++
++ if (!configurationExists) {
++ configuration = new Configuration();
++ } else {
++ configuration = configurationProvider.load(configurationFile);
++ }
++
++ // BungeeCord
++ setIfUnexistant("alert", "&8[&4Alert&8]&r ", configuration);
++ setIfUnexistant("already_connected", "&cYou are already connected to this server!", configuration);
++ setIfUnexistant("already_connected_proxy", "&cYou are already connected to this proxy!", configuration);
++ setIfUnexistant("already_connecting", "&cAlready connecting to this server!", configuration);
++ setIfUnexistant("command_list", "&a[{0}] &e({1}): &r{2}", configuration);
++ setIfUnexistant("connect_kick", "&cKicked whilst connecting to {0}: {1}", configuration);
++ setIfUnexistant("current_server", "&6You are currently connected to {0}.", configuration);
++ setIfUnexistant("fallback_kick",
++ "&cCould not connect to a default or fallback server, please try again later: {0}", configuration);
++ setIfUnexistant("fallback_lobby",
++ "&cCould not connect to target server, you have been moved to a fallback server.", configuration);
++ setIfUnexistant("lost_connection", "[Proxy] Lost connection to server.", configuration);
++ setIfUnexistant("mojang_fail", "Error occurred while contacting login servers, are they down?",
++ configuration);
++ setIfUnexistant("no_permission", "&cYou do not have permission to execute this command!", configuration);
++ setIfUnexistant("no_server", "&cThe specified server does not exist.", configuration);
++ setIfUnexistant("no_server_permission", "&cYou don't have permission to access this server.",
++ configuration);
++ setIfUnexistant("outdated_client", "Outdated client! Please use {0}", configuration);
++ setIfUnexistant("outdated_server", "Outdated server! I'm still on {0}", configuration);
++ setIfUnexistant("proxy_full", "Server is full!", configuration);
++ setIfUnexistant("restart", "[Proxy] Proxy restarting.", configuration);
++ setIfUnexistant("server_kick", "[Kicked] ", configuration);
++ setIfUnexistant("server_list", "&6You may connect to the following servers at this time: ", configuration);
++ setIfUnexistant("server_went_down",
++ "&cThe server you were previously on went down, you have been connected to a fallback server",
++ configuration);
++ setIfUnexistant("total_players", "Total players online: {0}", configuration);
++ setIfUnexistant("name_too_long", "Cannot have username longer than 16 characters", configuration);
++ setIfUnexistant("name_invalid", "Username contains invalid characters.", configuration);
++ setIfUnexistant("ping_cannot_connect", "&c[Bungee] Can't connect to server.", configuration);
++ setIfUnexistant("offline_mode_player", "Not authenticated with Minecraft.net", configuration);
++ setIfUnexistant("message_needed", "&cYou must supply a message.", configuration);
++ setIfUnexistant("error_occurred_player",
++ "&cAn error occurred while parsing your message. (Hover for details)", configuration);
++ setIfUnexistant("error_occurred_console", "&cAn error occurred while parsing your message: {0}",
++ configuration);
++ setIfUnexistant("click_to_connect", "Click to connect to the server", configuration);
++ setIfUnexistant("username_needed", "&cPlease follow this command by a user name.", configuration);
++ setIfUnexistant("user_not_online", "&cThat user is not online.", configuration);
++ setIfUnexistant("user_online_at", "&a{0} &ris online at {1}", configuration);
++ setIfUnexistant("send_cmd_usage",
++ "&cNot enough arguments, usage: /send ", configuration);
++ setIfUnexistant("player_only", "&cOnly in game players can use this command", configuration);
++ setIfUnexistant("successfully_summoned", "&aSuccessfully summoned player(s)", configuration);
++ setIfUnexistant("you_got_summoned", "&6Summoned to {0} by {1}", configuration);
++ setIfUnexistant("command_perms_groups", "&6You have the following groups: {0}", configuration);
++ setIfUnexistant("command_perms_permission", "&9- {0}", configuration);
++ setIfUnexistant("command_ip", "&9IP of {0} is {1}", configuration);
++
++ // FlameCord
++ setIfUnexistant("firewall_added", "&e{0}&c had been firewalled from the proxy!", configuration);
++ setIfUnexistant("firewall_blocked", "&e{0}&c is firewalled from the proxy, request blocked!",
++ configuration);
++ setIfUnexistant("firewall_info",
++ "&aThere are&b {0} &aaddresses firewalled!\n&aThe firewall will clear in &b{1} &aseconds!",
++ configuration);
++ setIfUnexistant("firewall_cleared", "&b{0}&a addresses had been automatically removed from the firewall!",
++ configuration);
++ setIfUnexistant("flamecord_reload", "&aAll files had been successfully reloaded!", configuration);
++ setIfUnexistant("flamecord_help",
++ "&aFlameCord&b {0}&a by&b LinsaFTW&a &&b Sammwy&r\n&e /flamecord reload&7 >&b Reloads FlameCord files!\n&e /flamecord firewall&7 >&b Shows information about the Firewall!\n&e /flamecord help&7 >&b Shows this message!",
++ configuration);
++ setIfUnexistant("flamecord_nopermission", "&cYou don't have permission to do this!", configuration);
++
++ if (!configurationExists) {
++ configurationProvider.save(configuration, configurationFile);
++ }
++
++ for (final String key : configuration.getKeys()) {
++ final Object value = configuration.get(key);
++
++ if (value instanceof String) {
++ this.messages.put(key, ChatColor.translateAlternateColorCodes('&', (String) value));
++ }
++ }
++ } catch (final IOException e) {
++ e.printStackTrace();
++ }
++ }
++
++ public String getTranslation(final String name, final Object... args) {
++ if (!messages.containsKey(name)) {
++ logger.warning("[FlameCord] Tried to get translation '" + name
++ + "' from messages.yml file but wasn't found. Please try resetting this file or report to a developer.");
++ }
++
++ return MessageFormat.format(messages.getOrDefault(name, ""), args);
++ }
++
++ private void setIfUnexistant(final String arg1, final Object arg2, final Configuration configuration) {
++ if (!configuration.contains(arg1)) {
++ configuration.set(arg1, arg2);
++ }
++ }
++}
+\ No newline at end of file
+diff --git a/flamecord/src/main/java/dev/_2lstudios/flamecord/configuration/ModulesConfiguration.java b/flamecord/src/main/java/dev/_2lstudios/flamecord/configuration/ModulesConfiguration.java
+new file mode 100644
+index 00000000..e82c4844
+--- /dev/null
++++ b/flamecord/src/main/java/dev/_2lstudios/flamecord/configuration/ModulesConfiguration.java
+@@ -0,0 +1,94 @@
++package dev._2lstudios.flamecord.configuration;
++
++import java.io.File;
++import java.io.IOException;
++
++import net.md_5.bungee.config.Configuration;
++import net.md_5.bungee.config.ConfigurationProvider;
++
++public class ModulesConfiguration {
++ // Reconnect Module
++ public boolean reconnectEnabled = false;
++
++ // Alert Module
++ public boolean alertEnabled = true;
++
++ // Find Module
++ public boolean findEnabled = true;
++
++ // IP Module
++ public boolean ipEnabled = true;
++
++ // List Module
++ public boolean listEnabled = true;
++
++ // Perms Module
++ public boolean permsEnabled = true;
++
++ // Reload Module
++ public boolean reloadEnabled = true;
++
++ // Send Module
++ public boolean sendEnabled = true;
++
++ // Server
++ public boolean serverEnabled = true;
++
++ public ModulesConfiguration(final ConfigurationProvider configurationProvider) {
++ try {
++ final String fileName = "./modules.yml";
++ final File configurationFile = new File(fileName);
++ final Configuration configuration;
++ final boolean configurationExists = configurationFile.exists();
++
++ if (!configurationExists) {
++ configuration = new Configuration();
++ } else {
++ configuration = configurationProvider.load(configurationFile);
++ }
++
++ this.alertEnabled = setIfUnexistant("alert.enabled", this.alertEnabled, configuration);
++
++ this.findEnabled = setIfUnexistant("find.enabled", this.findEnabled, configuration);
++
++ this.ipEnabled = setIfUnexistant("ip.enabled", this.ipEnabled, configuration);
++
++ this.listEnabled = setIfUnexistant("list.enabled", this.listEnabled, configuration);
++
++ this.permsEnabled = setIfUnexistant("perms.enabled", this.permsEnabled, configuration);
++
++ this.reloadEnabled = setIfUnexistant("reload.enabled", this.reloadEnabled, configuration);
++
++ this.sendEnabled = setIfUnexistant("send.enabled", this.sendEnabled, configuration);
++
++ this.serverEnabled = setIfUnexistant("server.enabled", this.serverEnabled, configuration);
++
++ this.reconnectEnabled = setIfUnexistant("reconnect.enabled", this.reconnectEnabled,
++ configuration);
++
++ if (!configurationExists) {
++ configurationProvider.save(configuration, configurationFile);
++ }
++ } catch (final IOException e) {
++ e.printStackTrace();
++ }
++ }
++
++ private String setIfUnexistant(final String arg1, final String arg2, final Configuration configuration) {
++ return (String) setIfUnexistant(arg1, (Object) arg2, configuration);
++ }
++
++ private boolean setIfUnexistant(final String arg1, final boolean arg2, final Configuration configuration) {
++ return (boolean) setIfUnexistant(arg1, (Object) arg2, configuration);
++ }
++
++ private Object setIfUnexistant(final String arg1, final Object arg2, final Configuration configuration) {
++ if (!configuration.contains(arg1)) {
++ configuration.set(arg1, arg2);
++
++ return arg2;
++ } else {
++ return configuration.get(arg1);
++ }
++ }
++}
+diff --git a/flamecord/src/main/java/dev/_2lstudios/flamecord/firewall/FirewallException.java b/flamecord/src/main/java/dev/_2lstudios/flamecord/firewall/FirewallException.java
+new file mode 100644
+index 00000000..aca06844
+--- /dev/null
++++ b/flamecord/src/main/java/dev/_2lstudios/flamecord/firewall/FirewallException.java
+@@ -0,0 +1,19 @@
++package dev._2lstudios.flamecord.firewall;
++
++import java.net.SocketAddress;
++
++public class FirewallException extends Exception {
++ private static final long serialVersionUID = 1L;
++
++ public FirewallException(final SocketAddress address) {
++ super("The address " + address + " is blocked from the server!");
++ }
++
++ public FirewallException(final String string) {
++ super(string);
++ }
++
++ public FirewallException(final String string, final Throwable throwable) {
++ super(string, throwable);
++ }
++}
+\ No newline at end of file
+diff --git a/flamecord/src/main/java/dev/_2lstudios/flamecord/firewall/FirewallManager.java b/flamecord/src/main/java/dev/_2lstudios/flamecord/firewall/FirewallManager.java
+new file mode 100644
+index 00000000..8a474758
+--- /dev/null
++++ b/flamecord/src/main/java/dev/_2lstudios/flamecord/firewall/FirewallManager.java
+@@ -0,0 +1,116 @@
++package dev._2lstudios.flamecord.firewall;
++
++import java.net.InetSocketAddress;
++import java.net.SocketAddress;
++import java.util.Collection;
++import java.util.HashSet;
++import java.util.logging.Logger;
++
++import dev._2lstudios.flamecord.FlameCord;
++import dev._2lstudios.flamecord.configuration.FlameCordConfiguration;
++import lombok.Getter;
++
++public class FirewallManager {
++ private final Logger logger;
++ private final Collection whitelistedAddresses;
++ private final Collection firewalled;
++ private final int defaultSeconds;
++ @Getter
++ private int seconds;
++
++ public FirewallManager(final Logger logger, final Collection whitelistedAddresses,
++ final int defaultSeconds) {
++ this.logger = logger;
++ this.whitelistedAddresses = whitelistedAddresses;
++ this.firewalled = new HashSet<>();
++ this.defaultSeconds = defaultSeconds;
++ this.seconds = defaultSeconds;
++ }
++
++ public boolean isWhitelisted(final SocketAddress address) {
++ final String addressString = address.toString();
++
++ for (final String whitelistedAddressString : whitelistedAddresses) {
++ if (addressString.endsWith(whitelistedAddressString)) {
++ return true;
++ }
++ }
++
++ return false;
++ }
++
++ public void addFirewalled(final SocketAddress address) {
++ if (FlameCord.getInstance().getFlameCordConfiguration().isFirewallEnabled() && !isWhitelisted(address)) {
++ final InetSocketAddress iNetSocketAddress = (InetSocketAddress) address;
++ final String hostString = iNetSocketAddress.getHostString();
++
++ if (!this.firewalled.contains(hostString)) {
++ this.firewalled.add(hostString);
++ logAdded(address);
++ }
++ }
++ }
++
++ public void logAdded(final SocketAddress address) {
++ final FlameCord flameCord = FlameCord.getInstance();
++ final FlameCordConfiguration flameCordConfiguration = flameCord.getFlameCordConfiguration();
++
++ if (flameCordConfiguration.isFirewallNotify()) {
++ final InetSocketAddress iNetSocketAddress = (InetSocketAddress) address;
++ final String hostString = iNetSocketAddress.getHostString();
++
++ this.logger.info(flameCord.getMessagesConfiguration().getTranslation("firewall_added", hostString));
++ }
++ }
++
++ public void logBlocked(final SocketAddress address) {
++ final FlameCord flameCord = FlameCord.getInstance();
++ final FlameCordConfiguration flameCordConfiguration = flameCord.getFlameCordConfiguration();
++
++ if (flameCordConfiguration.isFirewallNotify()) {
++ final InetSocketAddress iNetSocketAddress = (InetSocketAddress) address;
++ final String hostString = iNetSocketAddress.getHostString();
++
++ this.logger.info(flameCord.getMessagesConfiguration().getTranslation("firewall_blocked", hostString));
++ }
++ }
++
++ public Collection getFirewalled() {
++ return this.firewalled;
++ }
++
++ public boolean isFirewalled(final SocketAddress address) {
++ final InetSocketAddress iNetSocketAddress = (InetSocketAddress) address;
++
++ return this.firewalled.contains(iNetSocketAddress.getHostString());
++ }
++
++ public boolean isFirewalled(final String name) {
++ final String nameLowerCase = name.toLowerCase();
++
++ for (final String string : FlameCord.getInstance().getFlameCordConfiguration().getFirewallNames()) {
++ if (nameLowerCase.contains(string)) {
++ return true;
++ }
++ }
++
++ return false;
++ }
++
++ public void tick() {
++ if (--seconds <= 0) {
++ final FlameCord flameCord = FlameCord.getInstance();
++ final int size = this.firewalled.size();
++
++ if (size > 0) {
++ if (flameCord.getFlameCordConfiguration().isFirewallNotify()) {
++ this.logger.info(flameCord.getMessagesConfiguration().getTranslation("firewall_cleared", size));
++ }
++
++ this.firewalled.clear();
++ }
++
++ this.seconds = defaultSeconds;
++ }
++ }
++}
+\ No newline at end of file
+diff --git a/log/.factorypath b/log/.factorypath
+new file mode 100644
+index 00000000..542d5259
+--- /dev/null
++++ b/log/.factorypath
+@@ -0,0 +1,7 @@
++
++
++
++
++
++
++
+diff --git a/log4j/.factorypath b/log4j/.factorypath
+new file mode 100644
+index 00000000..f08118bd
+--- /dev/null
++++ b/log4j/.factorypath
+@@ -0,0 +1,18 @@
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
+diff --git a/module/cmd-alert/.factorypath b/module/cmd-alert/.factorypath
+new file mode 100644
+index 00000000..29bce69c
+--- /dev/null
++++ b/module/cmd-alert/.factorypath
+@@ -0,0 +1,17 @@
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
+diff --git a/module/cmd-find/.factorypath b/module/cmd-find/.factorypath
+new file mode 100644
+index 00000000..29bce69c
+--- /dev/null
++++ b/module/cmd-find/.factorypath
+@@ -0,0 +1,17 @@
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
+diff --git a/module/cmd-list/.factorypath b/module/cmd-list/.factorypath
+new file mode 100644
+index 00000000..29bce69c
+--- /dev/null
++++ b/module/cmd-list/.factorypath
+@@ -0,0 +1,17 @@
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
+diff --git a/module/cmd-send/.factorypath b/module/cmd-send/.factorypath
+new file mode 100644
+index 00000000..29bce69c
+--- /dev/null
++++ b/module/cmd-send/.factorypath
+@@ -0,0 +1,17 @@
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
+diff --git a/module/cmd-server/.factorypath b/module/cmd-server/.factorypath
+new file mode 100644
+index 00000000..29bce69c
+--- /dev/null
++++ b/module/cmd-server/.factorypath
+@@ -0,0 +1,17 @@
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
+diff --git a/module/reconnect-yaml/.factorypath b/module/reconnect-yaml/.factorypath
+new file mode 100644
+index 00000000..29bce69c
+--- /dev/null
++++ b/module/reconnect-yaml/.factorypath
+@@ -0,0 +1,17 @@
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
+diff --git a/native/.factorypath b/native/.factorypath
+new file mode 100644
+index 00000000..3ae914e6
+--- /dev/null
++++ b/native/.factorypath
+@@ -0,0 +1,9 @@
++
++
++
++
++
++
++
++
++
+diff --git a/pom.xml b/pom.xml
+index 61920717..2126cda1 100644
+--- a/pom.xml
++++ b/pom.xml
+@@ -62,6 +62,9 @@
+ proxy
+ query
+ native
++
++ flamecord
++
+
+
+
+diff --git a/protocol/.factorypath b/protocol/.factorypath
+new file mode 100644
+index 00000000..192c13a0
+--- /dev/null
++++ b/protocol/.factorypath
+@@ -0,0 +1,14 @@
++
++
++
++
++
++
++
++
++
++
++
++
++
++
+diff --git a/protocol/pom.xml b/protocol/pom.xml
+index ba3ffe3d..9228f72a 100644
+--- a/protocol/pom.xml
++++ b/protocol/pom.xml
+@@ -64,5 +64,14 @@
+ 1.3.0
+ compile
+
++
++
++
++ dev._2lstudios
++ travertine-flamecord
++ ${project.version}
++ compile
++
++
+
+
+diff --git a/protocol/src/main/java/net/md_5/bungee/protocol/MinecraftDecoder.java b/protocol/src/main/java/net/md_5/bungee/protocol/MinecraftDecoder.java
+index ec932e92..0d9ed57d 100644
+--- a/protocol/src/main/java/net/md_5/bungee/protocol/MinecraftDecoder.java
++++ b/protocol/src/main/java/net/md_5/bungee/protocol/MinecraftDecoder.java
+@@ -1,5 +1,6 @@
+ package net.md_5.bungee.protocol;
+
++import dev._2lstudios.flamecord.FlameCord;
+ import io.netty.buffer.ByteBuf;
+ import io.netty.buffer.ByteBufUtil;
+ import io.netty.channel.ChannelHandlerContext;
+@@ -39,6 +40,19 @@ public class MinecraftDecoder extends MessageToMessageDecoder
+ }
+
+ Protocol.DirectionData prot = ( server ) ? protocol.TO_SERVER : protocol.TO_CLIENT;
++
++ // FlameCord - Check size before decoding
++ if (prot == protocol.TO_SERVER) {
++ final int readableBytes = in.readableBytes();
++ final int capacity = in.capacity();
++
++ if (readableBytes > 2097152) {
++ throw new DecoderException("Error decoding packet with too many readableBytes: " + readableBytes);
++ } else if (capacity > 2097152) {
++ throw new DecoderException("Error decoding packet with too big capacity: " + capacity);
++ }
++ }
++
+ ByteBuf slice = in.copy(); // Can't slice this one due to EntityMap :(
+
+ Object packetTypeInfo = null;
+@@ -79,7 +93,14 @@ public class MinecraftDecoder extends MessageToMessageDecoder
+ } else {
+ packetTypeStr = "unknown";
+ }
+- throw new FastDecoderException("Error decoding packet " + packetTypeStr + " with contents:\n" + ByteBufUtil.prettyHexDump(slice), e); // Waterfall
++
++ // FlameCord - Toggle Dumping packet info
++ // FlameCord - Change from FastDecoderException to DecoderException
++ if (FlameCord.getInstance().getFlameCordConfiguration().isLoggerDump()) {
++ throw new DecoderException( "Error decoding packet " + packetTypeStr + " with contents:\n" + ByteBufUtil.prettyHexDump(slice), e ); // Waterfall
++ } else {
++ throw new DecoderException( "Error decoding packet " + packetTypeStr, e );
++ }
+ } finally
+ {
+ if ( slice != null )
+diff --git a/proxy/.factorypath b/proxy/.factorypath
+new file mode 100644
+index 00000000..b9f2c65d
+--- /dev/null
++++ b/proxy/.factorypath
+@@ -0,0 +1,37 @@
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
+diff --git a/proxy/pom.xml b/proxy/pom.xml
+index 4bda0d62..0018d6f8 100644
+--- a/proxy/pom.xml
++++ b/proxy/pom.xml
+@@ -113,6 +113,51 @@
+ runtime
+
+
++
++
++
++ dev._2lstudios
++ travertine-flamecord
++ ${project.version}
++ compile
++
++
++ io.github.waterfallmc
++ travertine-module-cmd-alert
++ ${project.version}
++ compile
++
++
++ io.github.waterfallmc
++ travertine-module-cmd-find
++ ${project.version}
++ compile
++
++
++ io.github.waterfallmc
++ travertine-module-cmd-list
++ ${project.version}
++ compile
++
++
++ io.github.waterfallmc
++ travertine-module-cmd-send
++ ${project.version}
++ compile
++
++
++ io.github.waterfallmc
++ travertine-module-cmd-server
++ ${project.version}
++ compile
++
++
++ io.github.waterfallmc
++ travertine-module-reconnect-yaml
++ ${project.version}
++ compile
++
++
+
+
+
+diff --git a/proxy/src/main/java/dev/_2lstudios/flamecord/commands/FlameCordCommand.java b/proxy/src/main/java/dev/_2lstudios/flamecord/commands/FlameCordCommand.java
+new file mode 100644
+index 00000000..fa0b59c2
+--- /dev/null
++++ b/proxy/src/main/java/dev/_2lstudios/flamecord/commands/FlameCordCommand.java
+@@ -0,0 +1,71 @@
++package dev._2lstudios.flamecord.commands;
++
++import java.util.Collection;
++import java.util.HashSet;
++
++import dev._2lstudios.flamecord.FlameCord;
++import dev._2lstudios.flamecord.configuration.MessagesConfiguration;
++import dev._2lstudios.flamecord.firewall.FirewallManager;
++import net.md_5.bungee.BungeeCord;
++import net.md_5.bungee.api.CommandSender;
++import net.md_5.bungee.api.chat.TextComponent;
++import net.md_5.bungee.api.config.ServerInfo;
++import net.md_5.bungee.api.plugin.Command;
++
++public class FlameCordCommand extends Command {
++private final BungeeCord bungeeCord;
++
++ public FlameCordCommand(final BungeeCord bungeeCord) {
++ super("flamecord");
++
++ this.bungeeCord = bungeeCord;
++ }
++
++ @Override
++ public void execute(final CommandSender sender, final String[] args) {
++ final FlameCord flameCord = FlameCord.getInstance();
++ final MessagesConfiguration messagesConfiguration = flameCord.getMessagesConfiguration();
++
++ if (sender.hasPermission("flamecord.usage")) {
++ if (args.length > 0) {
++ final String arg0 = args[0];
++
++ switch (arg0) {
++ case "firewall": {
++ final FirewallManager firewallManager = flameCord.getFirewallManager();
++ final int amount = firewallManager.getFirewalled().size(),
++ seconds = firewallManager.getSeconds();
++
++ sender.sendMessage(TextComponent.fromLegacyText(
++ messagesConfiguration.getTranslation("firewall_info", amount, seconds)));
++ break;
++ }
++ case "reload": {
++ // FlameCord - Collect ips from servers
++ final Collection whitelistedAddresses = new HashSet<>();
++
++ for (final ServerInfo serverInfo : bungeeCord.getServers().values()) {
++ whitelistedAddresses.add(serverInfo.getSocketAddress().toString());
++ }
++
++ FlameCord.renew(bungeeCord.getLogger(), whitelistedAddresses);
++ sender.sendMessage(TextComponent
++ .fromLegacyText(messagesConfiguration.getTranslation("flamecord_reload")));
++ break;
++ }
++ default: {
++ sender.sendMessage(TextComponent.fromLegacyText(
++ messagesConfiguration.getTranslation("flamecord_help", bungeeCord.getVersion())));
++ break;
++ }
++ }
++ } else {
++ sender.sendMessage(TextComponent
++ .fromLegacyText(messagesConfiguration.getTranslation("flamecord_help", bungeeCord.getVersion())));
++ }
++ } else {
++ sender.sendMessage(TextComponent
++ .fromLegacyText(messagesConfiguration.getTranslation("flamecord_nopermission")));
++ }
++ }
++}
+diff --git a/proxy/src/main/java/io/github/waterfallmc/waterfall/conf/WaterfallConfiguration.java b/proxy/src/main/java/io/github/waterfallmc/waterfall/conf/WaterfallConfiguration.java
+index 527f310e..a4ef6d3b 100644
+--- a/proxy/src/main/java/io/github/waterfallmc/waterfall/conf/WaterfallConfiguration.java
++++ b/proxy/src/main/java/io/github/waterfallmc/waterfall/conf/WaterfallConfiguration.java
+@@ -51,7 +51,8 @@ public class WaterfallConfiguration extends Configuration {
+ YamlConfig config = new YamlConfig(new File("waterfall.yml"));
+ config.load(false); // Load, but no permissions
+ logInitialHandlerConnections = config.getBoolean( "log_initial_handler_connections", logInitialHandlerConnections );
+- gameVersion = config.getString("game_version", "").isEmpty() ? Joiner.on(", ").join(ProtocolConstants.SUPPORTED_VERSIONS) : config.getString("game_version", "");
++ // FlameCord - Make the version look better
++ gameVersion = config.getString("game_version", "").isEmpty() ? ProtocolConstants.SUPPORTED_VERSIONS.get(0) + "-" + ProtocolConstants.SUPPORTED_VERSIONS.get(ProtocolConstants.SUPPORTED_VERSIONS.size() - 1) : config.getString("game_version", "");
+ useNettyDnsResolver = config.getBoolean("use_netty_dns_resolver", useNettyDnsResolver);
+ // Throttling options
+ tabThrottle = config.getInt("throttling.tab_complete", tabThrottle);
+diff --git a/proxy/src/main/java/net/md_5/bungee/BungeeCord.java b/proxy/src/main/java/net/md_5/bungee/BungeeCord.java
+index a17ed68e..e051b9c7 100644
+--- a/proxy/src/main/java/net/md_5/bungee/BungeeCord.java
++++ b/proxy/src/main/java/net/md_5/bungee/BungeeCord.java
+@@ -9,6 +9,10 @@ import com.google.common.collect.Sets;
+ import com.google.common.util.concurrent.ThreadFactoryBuilder;
+ import com.google.gson.Gson;
+ import com.google.gson.GsonBuilder;
++
++import dev._2lstudios.flamecord.FlameCord;
++import dev._2lstudios.flamecord.commands.FlameCordCommand;
++import dev._2lstudios.flamecord.configuration.ModulesConfiguration;
+ import edu.umd.cs.findbugs.annotations.SuppressFBWarnings;
+ import io.github.waterfallmc.waterfall.conf.WaterfallConfiguration;
+ import io.github.waterfallmc.waterfall.event.ProxyExceptionEvent;
+@@ -86,6 +90,12 @@ import net.md_5.bungee.conf.Configuration;
+ import net.md_5.bungee.conf.YamlConfig;
+ import net.md_5.bungee.forge.ForgeConstants;
+ import net.md_5.bungee.module.ModuleManager;
++import net.md_5.bungee.module.cmd.alert.CommandAlert;
++import net.md_5.bungee.module.cmd.find.CommandFind;
++import net.md_5.bungee.module.cmd.list.CommandList;
++import net.md_5.bungee.module.cmd.send.CommandSend;
++import net.md_5.bungee.module.cmd.server.CommandServer;
++import net.md_5.bungee.module.reconnect.yaml.YamlReconnectHandler;
+ import net.md_5.bungee.netty.PipelineUtils;
+ import net.md_5.bungee.protocol.DefinedPacket;
+ import net.md_5.bungee.protocol.ProtocolConstants;
+@@ -232,11 +242,12 @@ public class BungeeCord extends ProxyServer
+ // Waterfall end
+
+ pluginManager = new PluginManager( this );
+- getPluginManager().registerCommand( null, new CommandReload() );
+- getPluginManager().registerCommand( null, new CommandEnd() );
+- getPluginManager().registerCommand( null, new CommandIP() );
+- getPluginManager().registerCommand( null, new CommandBungee() );
+- getPluginManager().registerCommand( null, new CommandPerms() );
++ // FlameCord - We register commands in our new method
++ //getPluginManager().registerCommand( null, new CommandReload() );
++ //getPluginManager().registerCommand( null, new CommandEnd() );
++ //getPluginManager().registerCommand( null, new CommandIP() );
++ //getPluginManager().registerCommand( null, new CommandBungee() );
++ //getPluginManager().registerCommand( null, new CommandPerms() );
+
+ if ( !Boolean.getBoolean( "net.md_5.bungee.native.disable" ) )
+ {
+@@ -285,6 +296,16 @@ public class BungeeCord extends ProxyServer
+ pluginManager.loadPlugins();
+ config.load();
+
++ // FlameCord - Renew and register modules
++ final Collection whitelistedAddresses = new HashSet<>();
++
++ for (final ServerInfo serverInfo : getServers().values()) {
++ whitelistedAddresses.add(serverInfo.getSocketAddress().toString());
++ }
++
++ FlameCord.renew(logger, whitelistedAddresses);
++ registerModules();
++
+ if ( config.isForgeSupport() )
+ {
+ registerChannel( ForgeConstants.FML_TAG );
+@@ -546,13 +567,13 @@ public class BungeeCord extends ProxyServer
+ @Override
+ public String getName()
+ {
+- return "Travertine";
++ return "FlameCord";
+ }
+
+ @Override
+ public String getVersion()
+ {
+- return ( BungeeCord.class.getPackage().getImplementationVersion() == null ) ? "unknown" : BungeeCord.class.getPackage().getImplementationVersion();
++ return "0.4.3";
+ }
+
+ public void reloadMessages()
+@@ -815,4 +836,56 @@ public class BungeeCord extends ProxyServer
+ {
+ return new BungeeTitle();
+ }
++
++ // FlameCord - Method to simplify module registering
++ public void registerModules() {
++ final ModulesConfiguration modulesConfiguration = FlameCord.getInstance().getModulesConfiguration();
++
++ // Bungeecord Commands
++ pluginManager.registerCommand(null, new CommandEnd());
++ pluginManager.registerCommand(null, new CommandBungee());
++
++ if (modulesConfiguration.reloadEnabled) {
++ pluginManager.registerCommand(null, new CommandReload());
++ }
++ if (modulesConfiguration.ipEnabled) {
++ pluginManager.registerCommand(null, new CommandIP());
++ }
++ if (modulesConfiguration.permsEnabled) {
++ pluginManager.registerCommand(null, new CommandPerms());
++ }
++
++ // Modules Commands
++ if (modulesConfiguration.alertEnabled) {
++ pluginManager.registerCommand(null, new CommandAlert());
++ }
++ if (modulesConfiguration.findEnabled) {
++ pluginManager.registerCommand(null, new CommandFind());
++ }
++ if (modulesConfiguration.listEnabled) {
++ pluginManager.registerCommand(null, new CommandList());
++ }
++ if (modulesConfiguration.sendEnabled) {
++ pluginManager.registerCommand(null, new CommandSend());
++ }
++ if (modulesConfiguration.serverEnabled) {
++ pluginManager.registerCommand(null, new CommandServer());
++ }
++
++ try {
++ if (modulesConfiguration.reconnectEnabled) {
++ for (ListenerInfo info : getConfig().getListeners()) {
++ if (!info.isForceDefault() && getReconnectHandler() == null) {
++ setReconnectHandler(new YamlReconnectHandler());
++ break;
++ }
++ }
++ }
++ } catch (final Exception exception) {
++ logger.warning("Reconnect module is not able to work on FlameCord!");
++ }
++
++ // Flamecord - Commands (Had to make it like this because of maven limitations)
++ pluginManager.registerCommand(null, new FlameCordCommand(this));
++ }
+ }
+diff --git a/proxy/src/main/java/net/md_5/bungee/BungeeCordLauncher.java b/proxy/src/main/java/net/md_5/bungee/BungeeCordLauncher.java
+index ad9a6d0c..ad8f8733 100644
+--- a/proxy/src/main/java/net/md_5/bungee/BungeeCordLauncher.java
++++ b/proxy/src/main/java/net/md_5/bungee/BungeeCordLauncher.java
+@@ -40,25 +40,12 @@ public class BungeeCordLauncher
+ return;
+ }
+
+- if ( BungeeCord.class.getPackage().getSpecificationVersion() != null && System.getProperty( "IReallyKnowWhatIAmDoingISwear" ) == null )
+- {
+- Date buildDate = new SimpleDateFormat( "yyyyMMdd" ).parse( BungeeCord.class.getPackage().getSpecificationVersion() );
+-
+- Calendar deadline = Calendar.getInstance();
+- deadline.add( Calendar.WEEK_OF_YEAR, -8 );
+- if ( buildDate.before( deadline.getTime() ) )
+- {
+- System.err.println( "*** Hey! This build is potentially outdated :( ***" );
+- System.err.println( "*** Please check for a new build from https://papermc.io/ci/job/Travertine/ ***" );
+- System.err.println( "*** Should this build be outdated, you will get NO support for it. ***" );
+- System.err.println( "*** Server will start in 10 seconds ***" );
+- Thread.sleep( TimeUnit.SECONDS.toMillis( 10 ) );
+- }
+- }
++ // FlameCord - Disable update checker
+
+ BungeeCord bungee = new BungeeCord();
+ ProxyServer.setInstance( bungee );
+- bungee.getLogger().info( "Enabled Travertine version " + bungee.getVersion() );
++ // FlameCord - Use bungee name
++ bungee.getLogger().info( "Enabled " + bungee.getName() + " version " + bungee.getVersion() );
+ bungee.start();
+
+ if ( !options.has( "noconsole" ) )
+diff --git a/proxy/src/main/java/net/md_5/bungee/ServerConnector.java b/proxy/src/main/java/net/md_5/bungee/ServerConnector.java
+index c12085e1..3cfef373 100644
+--- a/proxy/src/main/java/net/md_5/bungee/ServerConnector.java
++++ b/proxy/src/main/java/net/md_5/bungee/ServerConnector.java
+@@ -1,6 +1,8 @@
+ package net.md_5.bungee;
+
+ import com.google.common.base.Preconditions;
++
++import dev._2lstudios.flamecord.FlameCord;
+ import io.netty.buffer.ByteBuf;
+ import io.netty.buffer.ByteBufAllocator;
+ import java.net.InetSocketAddress;
+@@ -34,6 +36,7 @@ import net.md_5.bungee.netty.ChannelWrapper;
+ import net.md_5.bungee.netty.HandlerBoss;
+ import net.md_5.bungee.netty.PacketHandler;
+ import net.md_5.bungee.netty.PipelineUtils;
++import net.md_5.bungee.protocol.BadPacketException;
+ import net.md_5.bungee.protocol.DefinedPacket;
+ import net.md_5.bungee.protocol.MinecraftDecoder;
+ import net.md_5.bungee.protocol.PacketWrapper;
+@@ -125,7 +128,8 @@ public class ServerConnector extends PacketHandler
+ newp[newp.length - 2] = new LoginResult.Property( ForgeConstants.FML_LOGIN_PROFILE, "true", null );
+
+ // If we do not perform the replacement, then the IP Forwarding code in Spigot et. al. will try to split on this prematurely.
+- newp[newp.length - 1] = new LoginResult.Property( ForgeConstants.EXTRA_DATA, user.getExtraDataInHandshake().replaceAll( "\0", "\1"), "" );
++ // FlameCord - Change replaceAll() to replace()
++ newp[newp.length - 1] = new LoginResult.Property( ForgeConstants.EXTRA_DATA, user.getExtraDataInHandshake().replace( "\0", "\1"), "" );
+
+ // All done.
+ properties = newp;
+@@ -160,7 +164,13 @@ public class ServerConnector extends PacketHandler
+ {
+ if ( packet.packet == null )
+ {
+- throw new QuietException( "Unexpected packet received during server login process!\n" + BufUtil.dump( packet.buf, 16 ) );
++ // FlameCord - Toggle Dumping packet info
++ // FlameCord - Change from QuietException to BadPacketException
++ if (FlameCord.getInstance().getFlameCordConfiguration().isLoggerDump()) {
++ throw new BadPacketException( "Unexpected packet received during server connector process!\n" + BufUtil.dump(packet.buf, 16) );
++ } else {
++ throw new BadPacketException( "Unexpected packet received during server connector process!" );
++ }
+ }
+ }
+
+@@ -266,7 +276,8 @@ public class ServerConnector extends PacketHandler
+ user.getSentBossBars().clear();
+
+ user.unsafe().sendPacket( new Respawn( login.getDimension(), login.getWorldName(), login.getSeed(), login.getDifficulty(), login.getGameMode(), login.getPreviousGameMode(), login.getLevelType(), login.isDebug(), login.isFlat(), false ) );
+- user.getServer().disconnect( "Quitting" );
++ // FlameCord - Remove "Quitting" reason
++ user.getServer().disconnect();
+ } else
+ {
+ // Travertine start
+@@ -361,13 +372,15 @@ public class ServerConnector extends PacketHandler
+ user.setDimension( login.getDimension() );
+
+ // Remove from old servers
+- user.getServer().disconnect( "Quitting" );
++ // FlameCord - Remove "Quitting" reason
++ user.getServer().disconnect();
+ }
+
+ // TODO: Fix this?
+ if ( !user.isActive() )
+ {
+- server.disconnect( "Quitting" );
++ // FlameCord - Remove "Quitting" reason
++ server.disconnect();
+ // Silly server admins see stack trace and die
+ bungee.getLogger().warning( "No client connected for pending server!" );
+ return;
+diff --git a/proxy/src/main/java/net/md_5/bungee/UserConnection.java b/proxy/src/main/java/net/md_5/bungee/UserConnection.java
+index 8c2a743a..26c0e560 100644
+--- a/proxy/src/main/java/net/md_5/bungee/UserConnection.java
++++ b/proxy/src/main/java/net/md_5/bungee/UserConnection.java
+@@ -35,6 +35,7 @@ import net.md_5.bungee.api.SkinConfiguration;
+ import net.md_5.bungee.api.Title;
+ import net.md_5.bungee.api.chat.BaseComponent;
+ import net.md_5.bungee.api.chat.TextComponent;
++import net.md_5.bungee.api.config.ListenerInfo;
+ import net.md_5.bungee.api.config.ServerInfo;
+ import net.md_5.bungee.api.connection.ProxiedPlayer;
+ import net.md_5.bungee.api.event.PermissionCheckEvent;
+@@ -65,6 +66,7 @@ import net.md_5.bungee.tab.ServerUnique;
+ import net.md_5.bungee.tab.TabList;
+ import net.md_5.bungee.util.CaseInsensitiveSet;
+ import net.md_5.bungee.util.ChatComponentTransformer;
++import net.md_5.bungee.util.QuietException;
+
+ @RequiredArgsConstructor
+ public final class UserConnection implements ProxiedPlayer
+@@ -307,7 +309,8 @@ public final class UserConnection implements ProxiedPlayer
+
+ if ( getServer() == null && !ch.isClosing() )
+ {
+- throw new IllegalStateException( "Cancelled ServerConnectEvent with no server or disconnect." );
++ // FlameCord - Change IllegalStateException to QuietException and explain that is a plugin
++ throw new QuietException("A plugin cancelled ServerConnectEvent with no server or disconnect.");
+ }
+ return;
+ }
+@@ -386,9 +389,11 @@ public final class UserConnection implements ProxiedPlayer
+ .option( ChannelOption.CONNECT_TIMEOUT_MILLIS, request.getConnectTimeout() )
+ .remoteAddress( target.getAddress() );
+ // Windows is bugged, multi homed users will just have to live with random connecting IPs
+- if ( getPendingConnection().getListener().isSetLocalAddress() && !PlatformDependent.isWindows() && getPendingConnection().getListener().getSocketAddress() instanceof InetSocketAddress )
++ // FlameCord - Use listenerInfo
++ final ListenerInfo listenerInfo = getPendingConnection().getListener();
++ if ( listenerInfo.isSetLocalAddress() && !PlatformDependent.isWindows() && listenerInfo.getSocketAddress() instanceof InetSocketAddress )
+ {
+- b.localAddress( getPendingConnection().getListener().getHost().getHostString(), 0 );
++ b.localAddress( listenerInfo.getHost().getHostString(), 0 );
+ }
+ b.connect().addListener( listener );
+ }
+@@ -425,7 +430,8 @@ public final class UserConnection implements ProxiedPlayer
+ if ( server != null )
+ {
+ server.setObsolete( true );
+- server.disconnect( "Quitting" );
++ // FlameCord - Remove "Quitting" reason
++ server.disconnect();
+ }
+ }
+ }
+diff --git a/proxy/src/main/java/net/md_5/bungee/command/CommandBungee.java b/proxy/src/main/java/net/md_5/bungee/command/CommandBungee.java
+index 4e2c6129..aeda7963 100644
+--- a/proxy/src/main/java/net/md_5/bungee/command/CommandBungee.java
++++ b/proxy/src/main/java/net/md_5/bungee/command/CommandBungee.java
+@@ -16,6 +16,7 @@ public class CommandBungee extends Command
+ @Override
+ public void execute(CommandSender sender, String[] args)
+ {
+- sender.sendMessage( ChatColor.BLUE + "This server is running Travertine version " + ProxyServer.getInstance().getVersion() + " by md_5" );
++ // FlameCord - Use custom version message
++ sender.sendMessage( ChatColor.translateAlternateColorCodes( '&', "&eThis server is running &c" + ProxyServer.getInstance().getName() + "&e version &a" + ProxyServer.getInstance().getVersion() + "&e by &bLinsaFTW & Sammwy&e." ) );
+ }
+ }
+diff --git a/proxy/src/main/java/net/md_5/bungee/conf/Configuration.java b/proxy/src/main/java/net/md_5/bungee/conf/Configuration.java
+index 85d2197a..1294495d 100644
+--- a/proxy/src/main/java/net/md_5/bungee/conf/Configuration.java
++++ b/proxy/src/main/java/net/md_5/bungee/conf/Configuration.java
+@@ -35,7 +35,8 @@ public abstract class Configuration implements ProxyConfig
+ /**
+ * Time before users are disconnected due to no network activity.
+ */
+- private int timeout = 30000;
++ // FlameCord - Default timeout to 10000
++ private int timeout = 10000;
+ /**
+ * UUID used for metrics.
+ */
+diff --git a/proxy/src/main/java/net/md_5/bungee/conf/YamlConfig.java b/proxy/src/main/java/net/md_5/bungee/conf/YamlConfig.java
+index d4fad294..7994c1c1 100644
+--- a/proxy/src/main/java/net/md_5/bungee/conf/YamlConfig.java
++++ b/proxy/src/main/java/net/md_5/bungee/conf/YamlConfig.java
+@@ -22,6 +22,7 @@ import java.util.Locale;
+ import java.util.Map;
+ import java.util.logging.Level;
+ import lombok.RequiredArgsConstructor;
++import net.md_5.bungee.BungeeCord;
+ import net.md_5.bungee.Util;
+ import net.md_5.bungee.api.ChatColor;
+ import net.md_5.bungee.api.ProxyServer;
+@@ -227,7 +228,8 @@ public class YamlConfig implements ConfigurationAdapter
+ Map val = entry.getValue();
+ String name = entry.getKey();
+ String addr = get( "address", "localhost:25565", val );
+- String motd = ChatColor.translateAlternateColorCodes( '&', get( "motd", "&1Just another Travertine - Forced Host", val ) );
++ // FlameCord - Use Bungee name instead
++ String motd = ChatColor.translateAlternateColorCodes( '&', get( "motd", "&1Just another " + BungeeCord.getInstance().getName() + " - Forced Host", val ) );
+ boolean restricted = get( "restricted", false, val );
+ SocketAddress address = Util.getAddr( addr );
+ ServerInfo info = ProxyServer.getInstance().constructServerInfo( name, address, motd, restricted );
+@@ -253,7 +255,8 @@ public class YamlConfig implements ConfigurationAdapter
+
+ for ( Map val : base )
+ {
+- String motd = get( "motd", "&1Another Bungee server", val );
++ // FlameCord - Use Bungee name instead
++ String motd = get( "motd", "&1Another " + BungeeCord.getInstance().getName() + " server", val );
+ motd = ChatColor.translateAlternateColorCodes( '&', motd );
+
+ int maxPlayers = get( "max_players", 1, val );
+diff --git a/proxy/src/main/java/net/md_5/bungee/connection/DownstreamBridge.java b/proxy/src/main/java/net/md_5/bungee/connection/DownstreamBridge.java
+index d54d8539..474551d3 100644
+--- a/proxy/src/main/java/net/md_5/bungee/connection/DownstreamBridge.java
++++ b/proxy/src/main/java/net/md_5/bungee/connection/DownstreamBridge.java
+@@ -285,6 +285,7 @@ public class DownstreamBridge extends PacketHandler
+ throw CancelSendSignal.INSTANCE;
+ }
+
++ // FlameCord - Use elseIfs
+ if ( pluginMessage.getTag().equals( con.getPendingConnection().getVersion() >= ProtocolConstants.MINECRAFT_1_13 ? "minecraft:brand" : "MC|Brand" ) )
+ {
+ // Travertine start
+@@ -313,8 +314,7 @@ public class DownstreamBridge extends PacketHandler
+ con.unsafe().sendPacket( pluginMessage );
+ throw CancelSendSignal.INSTANCE;
+ }
+-
+- if ( pluginMessage.getTag().equals( "BungeeCord" ) )
++ else if ( pluginMessage.getTag().equals( "BungeeCord" ) )
+ {
+ DataInput in = pluginMessage.getStream();
+ ByteArrayDataOutput out = ByteStreams.newDataOutput();
+@@ -343,7 +343,7 @@ public class DownstreamBridge extends PacketHandler
+ // Null out stream, important as we don't want to send to ourselves
+ out = null;
+ }
+- if ( subChannel.equals( "Forward" ) )
++ else if ( subChannel.equals( "Forward" ) )
+ {
+ // Read data from server
+ String target = in.readUTF();
+@@ -388,7 +388,7 @@ public class DownstreamBridge extends PacketHandler
+ }
+ }
+ }
+- if ( subChannel.equals( "Connect" ) )
++ else if ( subChannel.equals( "Connect" ) )
+ {
+ ServerInfo server = bungee.getServerInfo( in.readUTF() );
+ if ( server != null )
+@@ -396,7 +396,7 @@ public class DownstreamBridge extends PacketHandler
+ con.connect( server, ServerConnectEvent.Reason.PLUGIN_MESSAGE );
+ }
+ }
+- if ( subChannel.equals( "ConnectOther" ) )
++ else if ( subChannel.equals( "ConnectOther" ) )
+ {
+ ProxiedPlayer player = bungee.getPlayer( in.readUTF() );
+ if ( player != null )
+@@ -408,7 +408,7 @@ public class DownstreamBridge extends PacketHandler
+ }
+ }
+ }
+- if ( subChannel.equals( "IP" ) )
++ else if ( subChannel.equals( "IP" ) )
+ {
+ out.writeUTF( "IP" );
+ if ( con.getSocketAddress() instanceof InetSocketAddress )
+@@ -421,7 +421,7 @@ public class DownstreamBridge extends PacketHandler
+ out.writeInt( 0 );
+ }
+ }
+- if ( subChannel.equals( "IPOther" ) )
++ else if ( subChannel.equals( "IPOther" ) )
+ {
+ ProxiedPlayer player = bungee.getPlayer( in.readUTF() );
+ if ( player != null )
+@@ -440,7 +440,7 @@ public class DownstreamBridge extends PacketHandler
+ }
+ }
+ }
+- if ( subChannel.equals( "PlayerCount" ) )
++ else if ( subChannel.equals( "PlayerCount" ) )
+ {
+ String target = in.readUTF();
+ out.writeUTF( "PlayerCount" );
+@@ -458,7 +458,7 @@ public class DownstreamBridge extends PacketHandler
+ }
+ }
+ }
+- if ( subChannel.equals( "PlayerList" ) )
++ else if ( subChannel.equals( "PlayerList" ) )
+ {
+ String target = in.readUTF();
+ out.writeUTF( "PlayerList" );
+@@ -476,12 +476,12 @@ public class DownstreamBridge extends PacketHandler
+ }
+ }
+ }
+- if ( subChannel.equals( "GetServers" ) )
++ else if ( subChannel.equals( "GetServers" ) )
+ {
+ out.writeUTF( "GetServers" );
+ out.writeUTF( Util.csv( bungee.getServers().keySet() ) );
+ }
+- if ( subChannel.equals( "Message" ) )
++ else if ( subChannel.equals( "Message" ) )
+ {
+ String target = in.readUTF();
+ String message = in.readUTF();
+@@ -500,7 +500,7 @@ public class DownstreamBridge extends PacketHandler
+ }
+ }
+ }
+- if ( subChannel.equals( "MessageRaw" ) )
++ else if ( subChannel.equals( "MessageRaw" ) )
+ {
+ String target = in.readUTF();
+ BaseComponent[] message = ComponentSerializer.parse( in.readUTF() );
+@@ -519,17 +519,17 @@ public class DownstreamBridge extends PacketHandler
+ }
+ }
+ }
+- if ( subChannel.equals( "GetServer" ) )
++ else if ( subChannel.equals( "GetServer" ) )
+ {
+ out.writeUTF( "GetServer" );
+ out.writeUTF( server.getInfo().getName() );
+ }
+- if ( subChannel.equals( "UUID" ) )
++ else if ( subChannel.equals( "UUID" ) )
+ {
+ out.writeUTF( "UUID" );
+ out.writeUTF( con.getUUID() );
+ }
+- if ( subChannel.equals( "UUIDOther" ) )
++ else if ( subChannel.equals( "UUIDOther" ) )
+ {
+ ProxiedPlayer player = bungee.getPlayer( in.readUTF() );
+ if ( player != null )
+@@ -539,18 +539,21 @@ public class DownstreamBridge extends PacketHandler
+ out.writeUTF( player.getUUID() );
+ }
+ }
+- if ( subChannel.equals( "ServerIP" ) )
++ else if ( subChannel.equals( "ServerIP" ) )
+ {
+ ServerInfo info = bungee.getServerInfo( in.readUTF() );
+- if ( info != null && !info.getAddress().isUnresolved() )
++ // FlameCord use address
++ InetSocketAddress address = info.getAddress();
++ if ( info != null && !address.isUnresolved() )
+ {
+ out.writeUTF( "ServerIP" );
+ out.writeUTF( info.getName() );
+- out.writeUTF( info.getAddress().getAddress().getHostAddress() );
+- out.writeShort( info.getAddress().getPort() );
++ // FlameCord - Use getHostString
++ out.writeUTF( address.getHostString() );
++ out.writeShort( address.getPort() );
+ }
+ }
+- if ( subChannel.equals( "KickPlayer" ) )
++ else if ( subChannel.equals( "KickPlayer" ) )
+ {
+ ProxiedPlayer player = bungee.getPlayer( in.readUTF() );
+ if ( player != null )
+diff --git a/proxy/src/main/java/net/md_5/bungee/connection/InitialHandler.java b/proxy/src/main/java/net/md_5/bungee/connection/InitialHandler.java
+index fe6ff143..138dffa0 100644
+--- a/proxy/src/main/java/net/md_5/bungee/connection/InitialHandler.java
++++ b/proxy/src/main/java/net/md_5/bungee/connection/InitialHandler.java
+@@ -19,6 +19,8 @@ import com.google.gson.Gson;
+
+ import com.google.gson.JsonElement;
+ import com.google.gson.JsonObject;
++
++import dev._2lstudios.flamecord.FlameCord;
+ import lombok.Getter;
+ import lombok.RequiredArgsConstructor;
+ import net.md_5.bungee.BungeeCord;
+@@ -52,6 +54,7 @@ import net.md_5.bungee.netty.PacketHandler;
+ import net.md_5.bungee.netty.PipelineUtils;
+ import net.md_5.bungee.netty.cipher.CipherDecoder;
+ import net.md_5.bungee.netty.cipher.CipherEncoder;
++import net.md_5.bungee.protocol.BadPacketException;
+ import net.md_5.bungee.protocol.DefinedPacket;
+ import net.md_5.bungee.protocol.PacketWrapper;
+ import net.md_5.bungee.protocol.Protocol;
+@@ -155,7 +158,13 @@ public class InitialHandler extends PacketHandler implements PendingConnection
+ {
+ if ( packet.packet == null )
+ {
+- throw new QuietException( "Unexpected packet received during login process! " + BufUtil.dump( packet.buf, 16 ) );
++ // FlameCord - Toggle Dumping packet info
++ // FlameCord - Change from QuietException to BadPacketException
++ if (FlameCord.getInstance().getFlameCordConfiguration().isLoggerDump()) {
++ throw new BadPacketException( "Unexpected packet received during server login process!\n" + BufUtil.dump(packet.buf, 16) );
++ } else {
++ throw new BadPacketException( "Unexpected packet received during server login process!" );
++ }
+ }
+ }
+
+@@ -197,6 +206,13 @@ public class InitialHandler extends PacketHandler implements PendingConnection
+ }
+
+ ServerPing legacy = result.getResponse();
++
++ // FlameCord - Close and return if legacy == null
++ if (legacy == null) {
++ ch.close();
++ return;
++ }
++
+ String kickMessage;
+
+ if ( v1_5 )
+@@ -267,6 +283,16 @@ public class InitialHandler extends PacketHandler implements PendingConnection
+ {
+ bungee.getConnectionThrottle().unthrottle( getSocketAddress() );
+ }
++
++ // FlameCord - Close if response is null
++ // FlameCord - Return if connection is closed
++ if (pingResult.getResponse() == null) {
++ ch.close();
++ return;
++ } else if (ch.isClosed()) {
++ return;
++ }
++
+ // Travertine start
+ if ( ProtocolConstants.isBeforeOrEq( handshake.getProtocolVersion() , ProtocolConstants.MINECRAFT_1_8 ) )
+ {
+@@ -307,11 +333,11 @@ public class InitialHandler extends PacketHandler implements PendingConnection
+ @Override
+ public void handle(PingPacket ping) throws Exception
+ {
+- if (!ACCEPT_INVALID_PACKETS) {
+- Preconditions.checkState(thisState == State.PING, "Not expecting PING");
+- }
++ // FlameCord - Never accept invalid packets
++ Preconditions.checkState(thisState == State.PING, "Not expecting PING");
+ unsafe.sendPacket( ping );
+- disconnect( "" );
++ // FlameCord - Close instead of disconnect
++ ch.close();
+ }
+
+ @Override
+@@ -341,13 +367,18 @@ public class InitialHandler extends PacketHandler implements PendingConnection
+
+ this.virtualHost = InetSocketAddress.createUnresolved( handshake.getHost(), handshake.getPort() );
+
+- bungee.getPluginManager().callEvent( new PlayerHandshakeEvent( InitialHandler.this, handshake ) );
++ // FlameCord - Make PlayerHandshakeEvent cancellable
++ if (bungee.getPluginManager().callEvent(new PlayerHandshakeEvent(InitialHandler.this, handshake)).isCancelled()) {
++ ch.close();
++ return;
++ }
+
+ switch ( handshake.getRequestedProtocol() )
+ {
+ case 1:
+ // Ping
+- if ( bungee.getConfig().isLogPings() )
++ // FlameCord - Toggle for initialhandler logger
++ if ( bungee.getConfig().isLogPings() && FlameCord.getInstance().getFlameCordConfiguration().isLoggerInitialhandler() )
+ {
+ bungee.getLogger().log( Level.INFO, "{0} has pinged", this );
+ }
+@@ -356,7 +387,8 @@ public class InitialHandler extends PacketHandler implements PendingConnection
+ break;
+ case 2:
+ // Login
+- if (BungeeCord.getInstance().getConfig().isLogInitialHandlerConnections() ) // Waterfall
++ // FlameCord - Toggle for initialhandler logger
++ if (BungeeCord.getInstance().getConfig().isLogInitialHandlerConnections() && FlameCord.getInstance().getFlameCordConfiguration().isLoggerInitialhandler() ) // Waterfall
+ {
+ bungee.getLogger().log( Level.INFO, "{0} has connected", this );
+ }
+@@ -386,13 +418,16 @@ public class InitialHandler extends PacketHandler implements PendingConnection
+ Preconditions.checkState( thisState == State.USERNAME, "Not expecting USERNAME" );
+ this.loginRequest = loginRequest;
+
+- if ( getName().contains( "." ) )
++ // FlameCord - Use name
++ final String name = getName();
++
++ if ( name.contains( "." ) )
+ {
+ disconnect( bungee.getTranslation( "name_invalid" ) );
+ return;
+ }
+
+- if ( getName().length() > 16 )
++ if ( name.length() > 16 )
+ {
+ disconnect( bungee.getTranslation( "name_too_long" ) );
+ return;
+@@ -431,11 +466,12 @@ public class InitialHandler extends PacketHandler implements PendingConnection
+ if ( onlineMode )
+ {
+ unsafe().sendPacket( request = EncryptionUtil.encryptRequest() );
++ // FlameCord - Change state to encrypt only if onlineMode is true
++ thisState = State.ENCRYPT;
+ } else
+ {
+ finish();
+ }
+- thisState = State.ENCRYPT;
+ }
+ };
+
+@@ -447,6 +483,8 @@ public class InitialHandler extends PacketHandler implements PendingConnection
+ public void handle(final EncryptionResponse encryptResponse) throws Exception
+ {
+ Preconditions.checkState( thisState == State.ENCRYPT, "Not expecting ENCRYPT" );
++ // FlameCord - Finish here to avoid multiple incoming packets
++ thisState = State.FINISHED;
+
+ SecretKey sharedKey = EncryptionUtil.getSecret( encryptResponse, request );
+ BungeeCipher decrypt = EncryptionUtil.getCipher( false, sharedKey );
+@@ -481,7 +519,10 @@ public class InitialHandler extends PacketHandler implements PendingConnection
+ {
+ loginProfile = obj;
+ name = obj.getName();
+- uniqueId = Util.getUUID( obj.getId() );
++ // FlameCord - Don't declare uuid unless it's null
++ if (uniqueId == null) {
++ uniqueId = Util.getUUID(obj.getId());
++ }
+ finish();
+ return;
+ }
+@@ -499,6 +540,9 @@ public class InitialHandler extends PacketHandler implements PendingConnection
+
+ private void finish()
+ {
++ // FlameCord - Finish here to avoid multiple incoming packets
++ thisState = State.FINISHED;
++
+ if ( isOnlineMode() )
+ {
+ // Check for multiple connections
+@@ -580,8 +624,6 @@ public class InitialHandler extends PacketHandler implements PendingConnection
+ }
+
+ userCon.connect( server, null, true, ServerConnectEvent.Reason.JOIN_PROXY );
+-
+- thisState = State.FINISHED;
+ }
+ }
+ } );
+@@ -615,7 +657,8 @@ public class InitialHandler extends PacketHandler implements PendingConnection
+ {
+ if ( canSendKickMessage() )
+ {
+- ch.delayedClose( new Kick( ComponentSerializer.toString( reason ) ) );
++ // FlameCord - Changed delayedClose to close
++ ch.close( new Kick( ComponentSerializer.toString( reason ) ) );
+ } else
+ {
+ ch.close();
+@@ -672,7 +715,7 @@ public class InitialHandler extends PacketHandler implements PendingConnection
+ public void setUniqueId(UUID uuid)
+ {
+ Preconditions.checkState( thisState == State.USERNAME, "Can only set uuid while state is username" );
+- Preconditions.checkState( !onlineMode, "Can only set uuid when online mode is false" );
++ // FlameCord - Allow custom uuids even if onlineMode is true
+ this.uniqueId = uuid;
+ }
+
+diff --git a/proxy/src/main/java/net/md_5/bungee/connection/PingHandler.java b/proxy/src/main/java/net/md_5/bungee/connection/PingHandler.java
+index 6cd71071..09909bd9 100644
+--- a/proxy/src/main/java/net/md_5/bungee/connection/PingHandler.java
++++ b/proxy/src/main/java/net/md_5/bungee/connection/PingHandler.java
+@@ -1,6 +1,8 @@
+ package net.md_5.bungee.connection;
+
+ import com.google.gson.Gson;
++
++import dev._2lstudios.flamecord.FlameCord;
+ import edu.umd.cs.findbugs.annotations.SuppressFBWarnings;
+ import lombok.RequiredArgsConstructor;
+ import net.md_5.bungee.BungeeCord;
+@@ -12,6 +14,7 @@ import net.md_5.bungee.api.config.ServerInfo;
+ import net.md_5.bungee.netty.ChannelWrapper;
+ import net.md_5.bungee.netty.PacketHandler;
+ import net.md_5.bungee.netty.PipelineUtils;
++import net.md_5.bungee.protocol.BadPacketException;
+ import net.md_5.bungee.protocol.MinecraftDecoder;
+ import net.md_5.bungee.protocol.MinecraftEncoder;
+ import net.md_5.bungee.protocol.PacketWrapper;
+@@ -58,7 +61,13 @@ public class PingHandler extends PacketHandler
+ {
+ if ( packet.packet == null )
+ {
+- throw new QuietException( "Unexpected packet received during ping process! " + BufUtil.dump( packet.buf, 16 ) );
++ // FlameCord - Toggle dumping packet info
++ // FlameCord - Change from QuietException to BadPacketException
++ if (FlameCord.getInstance().getFlameCordConfiguration().isLoggerDump()) {
++ throw new BadPacketException( "Unexpected packet received during ping process! " + BufUtil.dump( packet.buf, 16 ) );
++ } else {
++ throw new BadPacketException( "Unexpected packet received during ping process!" );
++ }
+ }
+ }
+
+diff --git a/proxy/src/main/java/net/md_5/bungee/connection/UpstreamBridge.java b/proxy/src/main/java/net/md_5/bungee/connection/UpstreamBridge.java
+index ad3bdee5..c05714ba 100644
+--- a/proxy/src/main/java/net/md_5/bungee/connection/UpstreamBridge.java
++++ b/proxy/src/main/java/net/md_5/bungee/connection/UpstreamBridge.java
+@@ -92,6 +92,7 @@ public class UpstreamBridge extends PacketHandler
+ }
+ // Travertine end
+ }
++ // FlameCord - Remove "Quitting" reason
+ con.getServer().disconnect( "Quitting" );
+ }
+ }
+diff --git a/proxy/src/main/java/net/md_5/bungee/netty/ChannelWrapper.java b/proxy/src/main/java/net/md_5/bungee/netty/ChannelWrapper.java
+index 6dc5633f..606866a5 100644
+--- a/proxy/src/main/java/net/md_5/bungee/netty/ChannelWrapper.java
++++ b/proxy/src/main/java/net/md_5/bungee/netty/ChannelWrapper.java
+@@ -5,6 +5,8 @@ import io.netty.channel.Channel;
+ import io.netty.channel.ChannelFutureListener;
+ import io.netty.channel.ChannelHandler;
+ import io.netty.channel.ChannelHandlerContext;
++import io.netty.channel.ChannelPipeline;
++
+ import java.net.SocketAddress;
+ import java.util.concurrent.TimeUnit;
+ import lombok.Getter;
+@@ -37,14 +39,18 @@ public class ChannelWrapper
+
+ public void setProtocol(Protocol protocol)
+ {
+- ch.pipeline().get( MinecraftDecoder.class ).setProtocol( protocol );
+- ch.pipeline().get( MinecraftEncoder.class ).setProtocol( protocol );
++ // FlameCord - Use pipeline to reduce redundancy
++ final ChannelPipeline pipeline = ch.pipeline();
++ pipeline.get( MinecraftDecoder.class ).setProtocol( protocol );
++ pipeline.get( MinecraftEncoder.class ).setProtocol( protocol );
+ }
+
+ public void setVersion(int protocol)
+ {
+- ch.pipeline().get( MinecraftDecoder.class ).setProtocolVersion( protocol );
+- ch.pipeline().get( MinecraftEncoder.class ).setProtocolVersion( protocol );
++ // FlameCord - Use pipeline to reduce redundancy
++ final ChannelPipeline pipeline = ch.pipeline();
++ pipeline.get( MinecraftDecoder.class ).setProtocolVersion( protocol );
++ pipeline.get( MinecraftEncoder.class ).setProtocolVersion( protocol );
+ }
+
+ public void write(Object packet)
+@@ -80,40 +86,27 @@ public class ChannelWrapper
+
+ if ( packet != null && ch.isActive() )
+ {
+- ch.writeAndFlush( packet ).addListeners( ChannelFutureListener.FIRE_EXCEPTION_ON_FAILURE, ChannelFutureListener.CLOSE );
++ // FlameCord - Remove the firing of exceptions on failure
++ ch.writeAndFlush( packet ).addListeners( ChannelFutureListener.CLOSE );
+ } else
+ {
+- ch.flush();
++ // FlameCord - Don't flush just close
+ ch.close();
+ }
+ }
+ }
+
++ // FlameCord - Deprecate and "disable" delayedClose because it doesn't have a reason to exist
++ @Deprecated
+ public void delayedClose(final Kick kick)
+ {
+- if ( !closing )
+- {
+- closing = true;
+-
+- // Minecraft client can take some time to switch protocols.
+- // Sending the wrong disconnect packet whilst a protocol switch is in progress will crash it.
+- // Delay 250ms to ensure that the protocol switch (if any) has definitely taken place.
+- ch.eventLoop().schedule( new Runnable()
+- {
+-
+- @Override
+- public void run()
+- {
+- close( kick );
+- }
+- }, 250, TimeUnit.MILLISECONDS );
+- }
++ close(kick);
+ }
+
+ public void addBefore(String baseName, String name, ChannelHandler handler)
+ {
+ Preconditions.checkState( ch.eventLoop().inEventLoop(), "cannot add handler outside of event loop" );
+- ch.pipeline().flush();
++ // FlameCord - Don't flush if not necessary
+ ch.pipeline().addBefore( baseName, name, handler );
+ }
+
+@@ -124,25 +117,27 @@ public class ChannelWrapper
+
+ public void setCompressionThreshold(int compressionThreshold)
+ {
+- if ( ch.pipeline().get( PacketCompressor.class ) == null && compressionThreshold != -1 )
++ // FlameCord - Use pipeline to reduce redundancy
++ final ChannelPipeline pipeline = ch.pipeline();
++ if ( pipeline.get( PacketCompressor.class ) == null && compressionThreshold != -1 )
+ {
+ addBefore( PipelineUtils.PACKET_ENCODER, "compress", new PacketCompressor() );
+ }
+ if ( compressionThreshold != -1 )
+ {
+- ch.pipeline().get( PacketCompressor.class ).setThreshold( compressionThreshold );
++ pipeline.get( PacketCompressor.class ).setThreshold( compressionThreshold );
+ } else
+ {
+- ch.pipeline().remove( "compress" );
++ pipeline.remove( "compress" );
+ }
+
+- if ( ch.pipeline().get( PacketDecompressor.class ) == null && compressionThreshold != -1 )
++ if ( pipeline.get( PacketDecompressor.class ) == null && compressionThreshold != -1 )
+ {
+ addBefore( PipelineUtils.PACKET_DECODER, "decompress", new PacketDecompressor(compressionThreshold) );
+ }
+ if ( compressionThreshold == -1 )
+ {
+- ch.pipeline().remove( "decompress" );
++ pipeline.remove( "decompress" );
+ }
+ }
+ }
+diff --git a/proxy/src/main/java/net/md_5/bungee/netty/HandlerBoss.java b/proxy/src/main/java/net/md_5/bungee/netty/HandlerBoss.java
+index 989bfd87..46e338ca 100644
+--- a/proxy/src/main/java/net/md_5/bungee/netty/HandlerBoss.java
++++ b/proxy/src/main/java/net/md_5/bungee/netty/HandlerBoss.java
+@@ -1,6 +1,9 @@
+ package net.md_5.bungee.netty;
+
+ import com.google.common.base.Preconditions;
++
++import dev._2lstudios.flamecord.FlameCord;
++import dev._2lstudios.flamecord.firewall.FirewallException;
+ import io.netty.channel.ChannelHandlerContext;
+ import io.netty.channel.ChannelInboundHandlerAdapter;
+ import io.netty.handler.codec.CorruptedFrameException;
+@@ -9,6 +12,7 @@ import io.netty.handler.codec.haproxy.HAProxyMessage;
+ import io.netty.handler.timeout.ReadTimeoutException;
+ import java.io.IOException;
+ import java.net.InetSocketAddress;
++import java.net.SocketAddress;
+ import java.util.logging.Level;
+ import net.md_5.bungee.api.ProxyServer;
+ import net.md_5.bungee.connection.CancelSendSignal;
+@@ -39,12 +43,20 @@ public class HandlerBoss extends ChannelInboundHandlerAdapter
+ @Override
+ public void channelActive(ChannelHandlerContext ctx) throws Exception
+ {
++ // FlameCord - Firewall system
++ final SocketAddress remoteAddress = ctx.channel().remoteAddress();
++
++ if (remoteAddress != null && FlameCord.getInstance().getFirewallManager().isFirewalled(remoteAddress)) {
++ throw new FirewallException(remoteAddress);
++ }
++
+ if ( handler != null )
+ {
+ channel = new ChannelWrapper( ctx );
+ handler.connected( channel );
+
+- if ( !( handler instanceof InitialHandler || handler instanceof PingHandler ) )
++ // FlameCord - Added isLoggerInitialhandler boolean
++ if ( !( handler instanceof InitialHandler || handler instanceof PingHandler ) && FlameCord.getInstance().getFlameCordConfiguration().isLoggerInitialhandler() )
+ {
+ ProxyServer.getInstance().getLogger().log( Level.INFO, "{0} has connected", handler );
+ }
+@@ -56,10 +68,12 @@ public class HandlerBoss extends ChannelInboundHandlerAdapter
+ {
+ if ( handler != null )
+ {
+- channel.markClosed();
++ // FlameCord - close instead of markClosed
++ channel.close();
+ handler.disconnected( channel );
+
+- if ( !( handler instanceof InitialHandler || handler instanceof PingHandler ) )
++ // FlameCord - Added isLoggerInitialhandler boolean
++ if ( !( handler instanceof InitialHandler || handler instanceof PingHandler ) && FlameCord.getInstance().getFlameCordConfiguration().isLoggerInitialhandler() )
+ {
+ ProxyServer.getInstance().getLogger().log( Level.INFO, "{0} has disconnected", handler );
+ }
+@@ -78,6 +92,11 @@ public class HandlerBoss extends ChannelInboundHandlerAdapter
+ @Override
+ public void channelRead(ChannelHandlerContext ctx, Object msg) throws Exception
+ {
++ // FlameCord - Return if channel isn't active
++ if (!ctx.channel().isActive()) {
++ return;
++ }
++
+ if ( msg instanceof HAProxyMessage )
+ {
+ HAProxyMessage proxy = (HAProxyMessage) msg;
+@@ -124,7 +143,24 @@ public class HandlerBoss extends ChannelInboundHandlerAdapter
+ {
+ if ( ctx.channel().isActive() )
+ {
+- boolean logExceptions = !( handler instanceof PingHandler );
++ // FlameCord - Use flamecord
++ final FlameCord flameCord = FlameCord.getInstance();
++ // FlameCord - log exceptions based on FlameCord configuration and FirewallException
++ boolean logExceptions = flameCord.getFlameCordConfiguration().isLoggerExceptions() && !(cause instanceof FirewallException);
++
++ // FlameCord - Firewall system
++ if (cause instanceof DecoderException || cause instanceof IllegalStateException || cause instanceof BadPacketException) {
++ final SocketAddress remoteAddress = ctx.channel().remoteAddress();
++
++ if (remoteAddress != null) {
++ flameCord.getFirewallManager().addFirewalled(remoteAddress);
++ }
++ }
++
++ // FlameCord - Handle firewall exceptions
++ if (cause instanceof FirewallException) {
++ flameCord.getFirewallManager().logBlocked(ctx.channel().remoteAddress());
++ }
+
+ if ( logExceptions )
+ {
+@@ -180,8 +216,9 @@ public class HandlerBoss extends ChannelInboundHandlerAdapter
+ ProxyServer.getInstance().getLogger().log( Level.SEVERE, handler + " - exception processing exception", ex );
+ }
+ }
+-
+- ctx.close();
+ }
++
++ // FlameCord - Close even if the channel isn't active
++ ctx.close();
+ }
+ }
+diff --git a/proxy/src/main/java/net/md_5/bungee/netty/PipelineUtils.java b/proxy/src/main/java/net/md_5/bungee/netty/PipelineUtils.java
+index 9a39f69e..008b03cb 100644
+--- a/proxy/src/main/java/net/md_5/bungee/netty/PipelineUtils.java
++++ b/proxy/src/main/java/net/md_5/bungee/netty/PipelineUtils.java
+@@ -1,10 +1,14 @@
+ package net.md_5.bungee.netty;
+
+ import com.google.common.base.Preconditions;
++
++import dev._2lstudios.flamecord.FlameCord;
++import dev._2lstudios.flamecord.firewall.FirewallException;
+ import io.github.waterfallmc.waterfall.event.ConnectionInitEvent;
+ import io.netty.buffer.PooledByteBufAllocator;
+ import io.netty.channel.Channel;
+ import io.netty.channel.ChannelException;
++import io.netty.channel.ChannelHandlerContext;
+ import io.netty.channel.ChannelInitializer;
+ import io.netty.channel.ChannelOption;
+ import io.netty.channel.EventLoopGroup;
+@@ -60,6 +64,11 @@ public class PipelineUtils
+ {
+ SocketAddress remoteAddress = ( ch.remoteAddress() == null ) ? ch.parent().localAddress() : ch.remoteAddress();
+
++ // FlameCord - Firewall system
++ if (remoteAddress != null && FlameCord.getInstance().getFirewallManager().isFirewalled(remoteAddress)) {
++ throw new FirewallException(remoteAddress);
++ }
++
+ if ( BungeeCord.getInstance().getConnectionThrottle() != null && BungeeCord.getInstance().getConnectionThrottle().throttle( remoteAddress ) )
+ {
+ ch.close();
+@@ -102,6 +111,16 @@ public class PipelineUtils
+
+ BungeeCord.getInstance().getPluginManager().callEvent(connectionInitEvent);
+ }
++
++ // FlameCord - Close on exception caught
++ @Override
++ public void exceptionCaught(final ChannelHandlerContext ctx, final Throwable cause) throws Exception {
++ if (FlameCord.getInstance().getFlameCordConfiguration().isLoggerExceptions()) {
++ cause.printStackTrace();
++ }
++
++ ctx.close();
++ }
+ };
+ public static final Base BASE = new Base();
+ private static final KickStringWriter legacyKicker = new KickStringWriter();
+diff --git a/query/.factorypath b/query/.factorypath
+new file mode 100644
+index 00000000..7bec3430
+--- /dev/null
++++ b/query/.factorypath
+@@ -0,0 +1,17 @@
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
++
+diff --git a/query/src/main/java/net/md_5/bungee/query/QueryHandler.java b/query/src/main/java/net/md_5/bungee/query/QueryHandler.java
+index 0c1ecfb8..b3bdfd05 100644
+--- a/query/src/main/java/net/md_5/bungee/query/QueryHandler.java
++++ b/query/src/main/java/net/md_5/bungee/query/QueryHandler.java
+@@ -71,6 +71,8 @@ public class QueryHandler extends SimpleChannelInboundHandler
+ if ( in.readUnsignedByte() != 0xFE || in.readUnsignedByte() != 0xFD )
+ {
+ bungee.getLogger().log( Level.WARNING, "Query - Incorrect magic!: {0}", msg.sender() );
++ // FlameCord - Close on incorrect magic
++ ctx.close();
+ return;
+ }
+
+--
+2.27.0.windows.1
+
diff --git a/Waterfall-Proxy-Patches/0004-FlameCord-Initial-Patch.patch b/Waterfall-Proxy-Patches/0004-FlameCord-Initial-Patch.patch
deleted file mode 100644
index 4e51eaf2..00000000
--- a/Waterfall-Proxy-Patches/0004-FlameCord-Initial-Patch.patch
+++ /dev/null
@@ -1,11109 +0,0 @@
-From dbd1f205759879cade80260550eab994705145c3 Mon Sep 17 00:00:00 2001
-From: Juan Cruz Linsalata
-Date: Sat, 15 Aug 2020 15:19:22 -0300
-Subject: [PATCH] FlameCord Initial Patch
-
-
-diff --git a/api/.factorypath b/api/.factorypath
-new file mode 100644
-index 00000000..7a4b5ae4
---- /dev/null
-+++ b/api/.factorypath
-@@ -0,0 +1,17 @@
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-diff --git a/api/pom.xml b/api/pom.xml
-index d3016c10..365457d6 100644
---- a/api/pom.xml
-+++ b/api/pom.xml
-@@ -1,6 +1,5 @@
--
--
-+
- 4.0.0
-
-
-diff --git a/api/src/main/java/net/md_5/bungee/api/event/AsyncEvent.java b/api/src/main/java/net/md_5/bungee/api/event/AsyncEvent.java
-index cf85ca06..da5082ed 100644
---- a/api/src/main/java/net/md_5/bungee/api/event/AsyncEvent.java
-+++ b/api/src/main/java/net/md_5/bungee/api/event/AsyncEvent.java
-@@ -1,10 +1,12 @@
- package net.md_5.bungee.api.event;
-
--import com.google.common.base.Preconditions;
- import java.util.Map;
- import java.util.concurrent.ConcurrentHashMap;
- import java.util.concurrent.atomic.AtomicBoolean;
- import java.util.concurrent.atomic.AtomicInteger;
-+
-+import com.google.common.base.Preconditions;
-+
- import lombok.AccessLevel;
- import lombok.Data;
- import lombok.EqualsAndHashCode;
-@@ -23,8 +25,7 @@ import net.md_5.bungee.api.plugin.Plugin;
- @Getter(AccessLevel.NONE)
- @ToString(callSuper = true)
- @EqualsAndHashCode(callSuper = true)
--public class AsyncEvent extends Event
--{
-+public class AsyncEvent extends Event {
-
- private final Callback done;
- private final Map intents = new ConcurrentHashMap<>();
-@@ -33,61 +34,59 @@ public class AsyncEvent extends Event
-
- @Override
- @SuppressWarnings("unchecked")
-- public void postCall()
-- {
-- if ( latch.get() == 0 )
-- {
-- done.done( (T) this, null );
-+ public void postCall() {
-+ if (latch.get() == 0) {
-+ done.done((T) this, null);
- }
-- fired.set( true );
-+ fired.set(true);
- }
-
- /**
- * Register an intent that this plugin will continue to perform work on a
- * background task, and wishes to let the event proceed once the registered
- * background task has completed. Multiple intents can be registered by a
-- * plugin, but the plugin must complete the same amount of intents for the
-- * event to proceed.
-+ * plugin, but the plugin must complete the same amount of intents for the event
-+ * to proceed.
- *
- * @param plugin the plugin registering this intent
- */
-- public void registerIntent(Plugin plugin)
-- {
-- Preconditions.checkState( !fired.get(), "Event %s has already been fired", this );
-+ public void registerIntent(Plugin plugin) {
-+ Preconditions.checkState(!fired.get(), "Event %s has already been fired", this);
-
-- AtomicInteger intentCount = intents.get( plugin );
-- if ( intentCount == null )
-- {
-- intents.put( plugin, new AtomicInteger( 1 ) );
-- } else
-- {
-+ AtomicInteger intentCount = intents.get(plugin);
-+ if (intentCount == null) {
-+ intents.put(plugin, new AtomicInteger(1));
-+ } else {
- intentCount.incrementAndGet();
- }
- latch.incrementAndGet();
- }
-
- /**
-- * Notifies this event that this plugin has completed an intent and wishes
-- * to let the event proceed once all intents have been completed.
-+ * Notifies this event that this plugin has completed an intent and wishes to
-+ * let the event proceed once all intents have been completed.
- *
- * @param plugin a plugin which has an intent registered for this event
- */
- @SuppressWarnings("unchecked")
-- public void completeIntent(Plugin plugin)
-- {
-- AtomicInteger intentCount = intents.get( plugin );
-- Preconditions.checkState( intentCount != null && intentCount.get() > 0, "Plugin %s has not registered intents for event %s", plugin, this );
-+ public void completeIntent(Plugin plugin) {
-+ AtomicInteger intentCount = intents.get(plugin);
-+ Preconditions.checkState(intentCount != null && intentCount.get() > 0,
-+ "Plugin %s has not registered intents for event %s", plugin, this);
-
- intentCount.decrementAndGet();
-- if ( fired.get() )
-- {
-- if ( latch.decrementAndGet() == 0 )
-- {
-- done.done( (T) this, null );
-+ if (fired.get()) {
-+ if (latch.decrementAndGet() == 0) {
-+ done.done((T) this, null);
- }
-- } else
-- {
-+ } else {
- latch.decrementAndGet();
- }
- }
-+
-+ // FlameCord start - Added getDone() by request
-+ public Callback getDone() {
-+ return this.done;
-+ }
-+ // FlameCord end - Added getDone() by request
- }
-diff --git a/bootstrap/.factorypath b/bootstrap/.factorypath
-new file mode 100644
-index 00000000..c6fe9856
---- /dev/null
-+++ b/bootstrap/.factorypath
-@@ -0,0 +1,37 @@
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-diff --git a/bootstrap/pom.xml b/bootstrap/pom.xml
-index 078c5b1a..ec4202db 100644
---- a/bootstrap/pom.xml
-+++ b/bootstrap/pom.xml
-@@ -1,6 +1,5 @@
--
--
-+
- 4.0.0
-
-
-diff --git a/chat/.factorypath b/chat/.factorypath
-new file mode 100644
-index 00000000..ed4e646c
---- /dev/null
-+++ b/chat/.factorypath
-@@ -0,0 +1,6 @@
-+
-+
-+
-+
-+
-+
-diff --git a/chat/pom.xml b/chat/pom.xml
-index 29094871..863832b5 100644
---- a/chat/pom.xml
-+++ b/chat/pom.xml
-@@ -1,6 +1,5 @@
--
--
-+
- 4.0.0
-
-
-diff --git a/config/.factorypath b/config/.factorypath
-new file mode 100644
-index 00000000..6e60b565
---- /dev/null
-+++ b/config/.factorypath
-@@ -0,0 +1,7 @@
-+
-+
-+
-+
-+
-+
-+
-diff --git a/config/pom.xml b/config/pom.xml
-index 18f0a14e..f6d6d160 100644
---- a/config/pom.xml
-+++ b/config/pom.xml
-@@ -1,6 +1,5 @@
--
--
-+
- 4.0.0
-
-
-diff --git a/event/.factorypath b/event/.factorypath
-new file mode 100644
-index 00000000..f398f41e
---- /dev/null
-+++ b/event/.factorypath
-@@ -0,0 +1,5 @@
-+
-+
-+
-+
-+
-diff --git a/event/pom.xml b/event/pom.xml
-index 592bef24..91e739bc 100644
---- a/event/pom.xml
-+++ b/event/pom.xml
-@@ -1,6 +1,5 @@
--
--
-+
- 4.0.0
-
-
-diff --git a/flamecord/.factorypath b/flamecord/.factorypath
-new file mode 100644
-index 00000000..f398f41e
---- /dev/null
-+++ b/flamecord/.factorypath
-@@ -0,0 +1,5 @@
-+
-+
-+
-+
-+
-diff --git a/flamecord/pom.xml b/flamecord/pom.xml
-new file mode 100644
-index 00000000..939f1c2d
---- /dev/null
-+++ b/flamecord/pom.xml
-@@ -0,0 +1,44 @@
-+
-+ 4.0.0
-+
-+
-+ io.github.waterfallmc
-+ travertine-parent
-+ 1.16-R0.4-SNAPSHOT
-+ ../pom.xml
-+
-+
-+ dev._2lstudios.flamecord
-+ travertine-flamecord
-+ 1.16-R0.4-SNAPSHOT
-+ jar
-+
-+ Travertine-FlameCord
-+ FlameCord contains security essentials and new configuration options
-+
-+
-+
-+ io.github.waterfallmc
-+ travertine-config
-+ ${project.version}
-+ compile
-+
-+
-+ io.github.waterfallmc
-+ travertine-chat
-+ ${project.version}
-+ compile
-+
-+
-+
-+
-+ ${project.name}
-+
-+
-+ true
-+ ${basedir}/src/main/resources
-+
-+
-+
-+
-diff --git a/flamecord/src/main/java/dev/_2lstudios/flamecord/FlameCord.java b/flamecord/src/main/java/dev/_2lstudios/flamecord/FlameCord.java
-new file mode 100644
-index 00000000..3a7f56ee
---- /dev/null
-+++ b/flamecord/src/main/java/dev/_2lstudios/flamecord/FlameCord.java
-@@ -0,0 +1,57 @@
-+package dev._2lstudios.flamecord;
-+
-+import java.util.logging.Logger;
-+
-+import dev._2lstudios.flamecord.configuration.FlameCordConfiguration;
-+import dev._2lstudios.flamecord.configuration.MessagesConfiguration;
-+import dev._2lstudios.flamecord.configuration.ModulesConfiguration;
-+import dev._2lstudios.flamecord.firewall.FirewallManager;
-+import lombok.Getter;
-+import net.md_5.bungee.config.ConfigurationProvider;
-+import net.md_5.bungee.config.YamlConfiguration;
-+
-+public class FlameCord {
-+ @Getter
-+ private static FlameCord instance;
-+ @Getter
-+ private final FirewallManager firewallManager;
-+ @Getter
-+ private final FlameCordConfiguration flameCordConfiguration;
-+ @Getter
-+ private final ModulesConfiguration modulesConfiguration;
-+ @Getter
-+ private final MessagesConfiguration messagesConfiguration;
-+ private final Thread thread;
-+
-+ public static void renew(final Logger logger) {
-+ if (FlameCord.instance != null) {
-+ FlameCord.instance.thread.interrupt();
-+ }
-+
-+ FlameCord.instance = new FlameCord(logger);
-+ }
-+
-+ private FlameCord(final Logger logger) {
-+ final ConfigurationProvider configurationProvider = YamlConfiguration.getProvider(YamlConfiguration.class);
-+
-+ this.flameCordConfiguration = new FlameCordConfiguration(configurationProvider);
-+ this.firewallManager = new FirewallManager(logger, flameCordConfiguration.getFirewallSeconds());
-+ this.modulesConfiguration = new ModulesConfiguration(configurationProvider);
-+ this.messagesConfiguration = new MessagesConfiguration(logger, configurationProvider);
-+ this.thread = new Thread() {
-+ @Override
-+ public void run() {
-+ try {
-+ for (;;) {
-+ firewallManager.tick();
-+
-+ sleep(1000L);
-+ }
-+ } catch (final Exception e) {
-+ }
-+ }
-+ };
-+
-+ this.thread.start();
-+ }
-+}
-\ No newline at end of file
-diff --git a/flamecord/src/main/java/dev/_2lstudios/flamecord/configuration/FlameCordConfiguration.java b/flamecord/src/main/java/dev/_2lstudios/flamecord/configuration/FlameCordConfiguration.java
-new file mode 100644
-index 00000000..b7268e1d
---- /dev/null
-+++ b/flamecord/src/main/java/dev/_2lstudios/flamecord/configuration/FlameCordConfiguration.java
-@@ -0,0 +1,81 @@
-+package dev._2lstudios.flamecord.configuration;
-+
-+import java.io.File;
-+import java.io.IOException;
-+import java.util.ArrayList;
-+import java.util.Arrays;
-+import java.util.Collection;
-+import java.util.HashSet;
-+
-+import lombok.Getter;
-+import net.md_5.bungee.config.Configuration;
-+import net.md_5.bungee.config.ConfigurationProvider;
-+
-+public class FlameCordConfiguration {
-+ @Getter
-+ private boolean loggerInitialhandler = false, loggerExceptions = false, loggerDump = false, firewallNotify = true,
-+ firewallEnabled = true;
-+ @Getter
-+ private int firewallSeconds = 60;
-+ @Getter
-+ private Collection firewallNames = new HashSet<>(Arrays.asList(new String[] { "mcspam" }));
-+
-+ public FlameCordConfiguration(final ConfigurationProvider configurationProvider) {
-+ try {
-+ final String fileName = "./flamecord.yml";
-+ final File configurationFile = new File(fileName);
-+ final Configuration configuration;
-+ final boolean configurationExists = configurationFile.exists();
-+
-+ if (!configurationExists) {
-+ configuration = new Configuration();
-+ } else {
-+ configuration = configurationProvider.load(configurationFile);
-+ }
-+
-+ this.loggerInitialhandler = setIfUnexistant("logger.initialhandler", this.loggerInitialhandler,
-+ configuration);
-+ this.loggerExceptions = setIfUnexistant("logger.exceptions", this.loggerExceptions, configuration);
-+ this.loggerDump = setIfUnexistant("logger.dump", this.loggerDump, configuration);
-+ this.firewallEnabled = setIfUnexistant("firewall.enabled", this.firewallEnabled, configuration);
-+ this.firewallNotify = setIfUnexistant("firewall.notify", this.firewallNotify, configuration);
-+ this.firewallSeconds = setIfUnexistant("firewall.seconds", this.firewallSeconds, configuration);
-+ this.firewallNames = setIfUnexistant("firewall.names", this.firewallNames, configuration);
-+
-+ if (!configurationExists) {
-+ configurationProvider.save(configuration, configurationFile);
-+ }
-+ } catch (final IOException e) {
-+ e.printStackTrace();
-+ }
-+ }
-+
-+ private int setIfUnexistant(final String arg1, final int arg2, final Configuration configuration) {
-+ return (int) setIfUnexistant(arg1, (Object) arg2, configuration);
-+ }
-+
-+ private boolean setIfUnexistant(final String arg1, final boolean arg2, final Configuration configuration) {
-+ return (boolean) setIfUnexistant(arg1, (Object) arg2, configuration);
-+ }
-+
-+ private Object setIfUnexistant(final String arg1, final Object arg2, final Configuration configuration) {
-+ if (!configuration.contains(arg1)) {
-+ configuration.set(arg1, arg2);
-+
-+ return arg2;
-+ } else {
-+ return configuration.get(arg1);
-+ }
-+ }
-+
-+ private Collection setIfUnexistant(final String arg1, final Collection arg2,
-+ final Configuration configuration) {
-+ if (!configuration.contains(arg1)) {
-+ configuration.set(arg1, new ArrayList<>(arg2));
-+
-+ return arg2;
-+ } else {
-+ return new HashSet<>(configuration.getStringList(arg1));
-+ }
-+ }
-+}
-diff --git a/flamecord/src/main/java/dev/_2lstudios/flamecord/configuration/MessagesConfiguration.java b/flamecord/src/main/java/dev/_2lstudios/flamecord/configuration/MessagesConfiguration.java
-new file mode 100644
-index 00000000..c88077ad
---- /dev/null
-+++ b/flamecord/src/main/java/dev/_2lstudios/flamecord/configuration/MessagesConfiguration.java
-@@ -0,0 +1,129 @@
-+package dev._2lstudios.flamecord.configuration;
-+
-+import java.io.File;
-+import java.io.IOException;
-+import java.text.MessageFormat;
-+import java.util.HashMap;
-+import java.util.Map;
-+import java.util.logging.Logger;
-+
-+import net.md_5.bungee.api.ChatColor;
-+import net.md_5.bungee.config.Configuration;
-+import net.md_5.bungee.config.ConfigurationProvider;
-+
-+public class MessagesConfiguration {
-+ private final Logger logger;
-+ private final Map messages = new HashMap<>();
-+
-+ public MessagesConfiguration(final Logger logger, final ConfigurationProvider configurationProvider) {
-+ this.logger = logger;
-+
-+ try {
-+ final String fileName = "./messages.yml";
-+ final File configurationFile = new File(fileName);
-+ final Configuration configuration;
-+ final boolean configurationExists = configurationFile.exists();
-+
-+ if (!configurationExists) {
-+ configuration = new Configuration();
-+ } else {
-+ configuration = configurationProvider.load(configurationFile);
-+ }
-+
-+ // BungeeCord
-+ setIfUnexistant("alert", "&8[&4Alert&8]&r ", configuration);
-+ setIfUnexistant("already_connected", "&cYou are already connected to this server!", configuration);
-+ setIfUnexistant("already_connected_proxy", "&cYou are already connected to this proxy!", configuration);
-+ setIfUnexistant("already_connecting", "&cAlready connecting to this server!", configuration);
-+ setIfUnexistant("command_list", "&a[{0}] &e({1}): &r{2}", configuration);
-+ setIfUnexistant("connect_kick", "&cKicked whilst connecting to {0}: {1}", configuration);
-+ setIfUnexistant("current_server", "&6You are currently connected to {0}.", configuration);
-+ setIfUnexistant("fallback_kick",
-+ "&cCould not connect to a default or fallback server, please try again later: {0}", configuration);
-+ setIfUnexistant("fallback_lobby",
-+ "&cCould not connect to target server, you have been moved to a fallback server.", configuration);
-+ setIfUnexistant("lost_connection", "[Proxy] Lost connection to server.", configuration);
-+ setIfUnexistant("mojang_fail", "Error occurred while contacting login servers, are they down?",
-+ configuration);
-+ setIfUnexistant("no_permission", "&cYou do not have permission to execute this command!", configuration);
-+ setIfUnexistant("no_server", "&cThe specified server does not exist.", configuration);
-+ setIfUnexistant("no_server_permission", "&cYou don't have permission to access this server.",
-+ configuration);
-+ setIfUnexistant("outdated_client", "Outdated client! Please use {0}", configuration);
-+ setIfUnexistant("outdated_server", "Outdated server! I'm still on {0}", configuration);
-+ setIfUnexistant("proxy_full", "Server is full!", configuration);
-+ setIfUnexistant("restart", "[Proxy] Proxy restarting.", configuration);
-+ setIfUnexistant("server_kick", "[Kicked] ", configuration);
-+ setIfUnexistant("server_list", "&6You may connect to the following servers at this time: ", configuration);
-+ setIfUnexistant("server_went_down",
-+ "&cThe server you were previously on went down, you have been connected to a fallback server",
-+ configuration);
-+ setIfUnexistant("total_players", "Total players online: {0}", configuration);
-+ setIfUnexistant("name_too_long", "Cannot have username longer than 16 characters", configuration);
-+ setIfUnexistant("name_invalid", "Username contains invalid characters.", configuration);
-+ setIfUnexistant("ping_cannot_connect", "&c[Bungee] Can't connect to server.", configuration);
-+ setIfUnexistant("offline_mode_player", "Not authenticated with Minecraft.net", configuration);
-+ setIfUnexistant("message_needed", "&cYou must supply a message.", configuration);
-+ setIfUnexistant("error_occurred_player",
-+ "&cAn error occurred while parsing your message. (Hover for details)", configuration);
-+ setIfUnexistant("error_occurred_console", "&cAn error occurred while parsing your message: {0}",
-+ configuration);
-+ setIfUnexistant("click_to_connect", "Click to connect to the server", configuration);
-+ setIfUnexistant("username_needed", "&cPlease follow this command by a user name.", configuration);
-+ setIfUnexistant("user_not_online", "&cThat user is not online.", configuration);
-+ setIfUnexistant("user_online_at", "&a{0} &ris online at {1}", configuration);
-+ setIfUnexistant("send_cmd_usage",
-+ "&cNot enough arguments, usage: /send ", configuration);
-+ setIfUnexistant("player_only", "&cOnly in game players can use this command", configuration);
-+ setIfUnexistant("successfully_summoned", "&aSuccessfully summoned player(s)", configuration);
-+ setIfUnexistant("you_got_summoned", "&6Summoned to {0} by {1}", configuration);
-+ setIfUnexistant("command_perms_groups", "&6You have the following groups: {0}", configuration);
-+ setIfUnexistant("command_perms_permission", "&9- {0}", configuration);
-+ setIfUnexistant("command_ip", "&9IP of {0} is {1}", configuration);
-+
-+ // FlameCord
-+ setIfUnexistant("firewall_added", "&e{0}&c had been firewalled from the proxy!", configuration);
-+ setIfUnexistant("firewall_blocked", "&e{0}&c is firewalled from the proxy, request blocked!",
-+ configuration);
-+ setIfUnexistant("firewall_info",
-+ "&aThere are&b {0} &aaddresses firewalled!\n&aThe firewall will clear in &b{1} &aseconds!",
-+ configuration);
-+ setIfUnexistant("firewall_cleared", "&b{0}&a addresses had been automatically removed from the firewall!",
-+ configuration);
-+ setIfUnexistant("flamecord_reload", "&aAll files had been successfully reloaded!", configuration);
-+ setIfUnexistant("flamecord_help",
-+ "&aFlameCord&b {0}&a by&b LinsaFTW&a &&b Sammwy&r\n&e /flamecord reload&7 >&b Reloads FlameCord files!\n&e /flamecord firewall&7 >&b Shows information about the Firewall!\n&e /flamecord help&7 >&b Shows this message!",
-+ configuration);
-+ setIfUnexistant("flamecord_nopermission", "&cYou don't have permission to do this!", configuration);
-+
-+ if (!configurationExists) {
-+ configurationProvider.save(configuration, configurationFile);
-+ }
-+
-+ for (final String key : configuration.getKeys()) {
-+ final Object value = configuration.get(key);
-+
-+ if (value instanceof String) {
-+ this.messages.put(key, ChatColor.translateAlternateColorCodes('&', (String) value));
-+ }
-+ }
-+ } catch (final IOException e) {
-+ e.printStackTrace();
-+ }
-+ }
-+
-+ public String getTranslation(final String name, final Object... args) {
-+ if (!messages.containsKey(name)) {
-+ logger.warning("[FlameCord] Tried to get translation '" + name
-+ + "' from messages.yml file but wasn't found. Please try resetting this file or report to a developer.");
-+ }
-+
-+ return MessageFormat.format(messages.getOrDefault(name, ""), args);
-+ }
-+
-+ private void setIfUnexistant(final String arg1, final Object arg2, final Configuration configuration) {
-+ if (!configuration.contains(arg1)) {
-+ configuration.set(arg1, arg2);
-+ }
-+ }
-+}
-\ No newline at end of file
-diff --git a/flamecord/src/main/java/dev/_2lstudios/flamecord/configuration/ModulesConfiguration.java b/flamecord/src/main/java/dev/_2lstudios/flamecord/configuration/ModulesConfiguration.java
-new file mode 100644
-index 00000000..e82c4844
---- /dev/null
-+++ b/flamecord/src/main/java/dev/_2lstudios/flamecord/configuration/ModulesConfiguration.java
-@@ -0,0 +1,94 @@
-+package dev._2lstudios.flamecord.configuration;
-+
-+import java.io.File;
-+import java.io.IOException;
-+
-+import net.md_5.bungee.config.Configuration;
-+import net.md_5.bungee.config.ConfigurationProvider;
-+
-+public class ModulesConfiguration {
-+ // Reconnect Module
-+ public boolean reconnectEnabled = false;
-+
-+ // Alert Module
-+ public boolean alertEnabled = true;
-+
-+ // Find Module
-+ public boolean findEnabled = true;
-+
-+ // IP Module
-+ public boolean ipEnabled = true;
-+
-+ // List Module
-+ public boolean listEnabled = true;
-+
-+ // Perms Module
-+ public boolean permsEnabled = true;
-+
-+ // Reload Module
-+ public boolean reloadEnabled = true;
-+
-+ // Send Module
-+ public boolean sendEnabled = true;
-+
-+ // Server
-+ public boolean serverEnabled = true;
-+
-+ public ModulesConfiguration(final ConfigurationProvider configurationProvider) {
-+ try {
-+ final String fileName = "./modules.yml";
-+ final File configurationFile = new File(fileName);
-+ final Configuration configuration;
-+ final boolean configurationExists = configurationFile.exists();
-+
-+ if (!configurationExists) {
-+ configuration = new Configuration();
-+ } else {
-+ configuration = configurationProvider.load(configurationFile);
-+ }
-+
-+ this.alertEnabled = setIfUnexistant("alert.enabled", this.alertEnabled, configuration);
-+
-+ this.findEnabled = setIfUnexistant("find.enabled", this.findEnabled, configuration);
-+
-+ this.ipEnabled = setIfUnexistant("ip.enabled", this.ipEnabled, configuration);
-+
-+ this.listEnabled = setIfUnexistant("list.enabled", this.listEnabled, configuration);
-+
-+ this.permsEnabled = setIfUnexistant("perms.enabled", this.permsEnabled, configuration);
-+
-+ this.reloadEnabled = setIfUnexistant("reload.enabled", this.reloadEnabled, configuration);
-+
-+ this.sendEnabled = setIfUnexistant("send.enabled", this.sendEnabled, configuration);
-+
-+ this.serverEnabled = setIfUnexistant("server.enabled", this.serverEnabled, configuration);
-+
-+ this.reconnectEnabled = setIfUnexistant("reconnect.enabled", this.reconnectEnabled,
-+ configuration);
-+
-+ if (!configurationExists) {
-+ configurationProvider.save(configuration, configurationFile);
-+ }
-+ } catch (final IOException e) {
-+ e.printStackTrace();
-+ }
-+ }
-+
-+ private String setIfUnexistant(final String arg1, final String arg2, final Configuration configuration) {
-+ return (String) setIfUnexistant(arg1, (Object) arg2, configuration);
-+ }
-+
-+ private boolean setIfUnexistant(final String arg1, final boolean arg2, final Configuration configuration) {
-+ return (boolean) setIfUnexistant(arg1, (Object) arg2, configuration);
-+ }
-+
-+ private Object setIfUnexistant(final String arg1, final Object arg2, final Configuration configuration) {
-+ if (!configuration.contains(arg1)) {
-+ configuration.set(arg1, arg2);
-+
-+ return arg2;
-+ } else {
-+ return configuration.get(arg1);
-+ }
-+ }
-+}
-diff --git a/flamecord/src/main/java/dev/_2lstudios/flamecord/firewall/FirewallException.java b/flamecord/src/main/java/dev/_2lstudios/flamecord/firewall/FirewallException.java
-new file mode 100644
-index 00000000..aca06844
---- /dev/null
-+++ b/flamecord/src/main/java/dev/_2lstudios/flamecord/firewall/FirewallException.java
-@@ -0,0 +1,19 @@
-+package dev._2lstudios.flamecord.firewall;
-+
-+import java.net.SocketAddress;
-+
-+public class FirewallException extends Exception {
-+ private static final long serialVersionUID = 1L;
-+
-+ public FirewallException(final SocketAddress address) {
-+ super("The address " + address + " is blocked from the server!");
-+ }
-+
-+ public FirewallException(final String string) {
-+ super(string);
-+ }
-+
-+ public FirewallException(final String string, final Throwable throwable) {
-+ super(string, throwable);
-+ }
-+}
-\ No newline at end of file
-diff --git a/flamecord/src/main/java/dev/_2lstudios/flamecord/firewall/FirewallManager.java b/flamecord/src/main/java/dev/_2lstudios/flamecord/firewall/FirewallManager.java
-new file mode 100644
-index 00000000..a90c8426
---- /dev/null
-+++ b/flamecord/src/main/java/dev/_2lstudios/flamecord/firewall/FirewallManager.java
-@@ -0,0 +1,101 @@
-+package dev._2lstudios.flamecord.firewall;
-+
-+import java.net.InetSocketAddress;
-+import java.net.SocketAddress;
-+import java.util.Collection;
-+import java.util.HashSet;
-+import java.util.logging.Logger;
-+
-+import dev._2lstudios.flamecord.FlameCord;
-+import dev._2lstudios.flamecord.configuration.FlameCordConfiguration;
-+import lombok.Getter;
-+
-+public class FirewallManager {
-+ private final Logger logger;
-+ private final Collection firewalled;
-+ private final int defaultSeconds;
-+ @Getter
-+ private int seconds;
-+
-+ public FirewallManager(final Logger logger, final int defaultSeconds) {
-+ this.logger = logger;
-+ this.firewalled = new HashSet<>();
-+ this.defaultSeconds = defaultSeconds;
-+ this.seconds = defaultSeconds;
-+ }
-+
-+ public void addFirewalled(final SocketAddress address) {
-+ if (FlameCord.getInstance().getFlameCordConfiguration().isFirewallEnabled()) {
-+ final InetSocketAddress iNetSocketAddress = (InetSocketAddress) address;
-+ final String hostString = iNetSocketAddress.getHostString();
-+
-+ if (!this.firewalled.contains(hostString)) {
-+ this.firewalled.add(hostString);
-+ logAdded(address);
-+ }
-+ }
-+ }
-+
-+ public void logAdded(final SocketAddress address) {
-+ final FlameCord flameCord = FlameCord.getInstance();
-+ final FlameCordConfiguration flameCordConfiguration = flameCord.getFlameCordConfiguration();
-+
-+ if (flameCordConfiguration.isFirewallNotify()) {
-+ final InetSocketAddress iNetSocketAddress = (InetSocketAddress) address;
-+ final String hostString = iNetSocketAddress.getHostString();
-+
-+ this.logger.info(flameCord.getMessagesConfiguration().getTranslation("firewall_added", hostString));
-+ }
-+ }
-+
-+ public void logBlocked(final SocketAddress address) {
-+ final FlameCord flameCord = FlameCord.getInstance();
-+ final FlameCordConfiguration flameCordConfiguration = flameCord.getFlameCordConfiguration();
-+
-+ if (flameCordConfiguration.isFirewallNotify()) {
-+ final InetSocketAddress iNetSocketAddress = (InetSocketAddress) address;
-+ final String hostString = iNetSocketAddress.getHostString();
-+
-+ this.logger.info(flameCord.getMessagesConfiguration().getTranslation("firewall_blocked", hostString));
-+ }
-+ }
-+
-+ public Collection getFirewalled() {
-+ return this.firewalled;
-+ }
-+
-+ public boolean isFirewalled(final SocketAddress address) {
-+ final InetSocketAddress iNetSocketAddress = (InetSocketAddress) address;
-+
-+ return this.firewalled.contains(iNetSocketAddress.getHostString());
-+ }
-+
-+ public boolean isFirewalled(final String name) {
-+ final String nameLowerCase = name.toLowerCase();
-+
-+ for (final String string : FlameCord.getInstance().getFlameCordConfiguration().getFirewallNames()) {
-+ if (nameLowerCase.contains(string)) {
-+ return true;
-+ }
-+ }
-+
-+ return false;
-+ }
-+
-+ public void tick() {
-+ if (--seconds <= 0) {
-+ final FlameCord flameCord = FlameCord.getInstance();
-+ final int size = this.firewalled.size();
-+
-+ if (size > 0) {
-+ if (flameCord.getFlameCordConfiguration().isFirewallNotify()) {
-+ this.logger.info(flameCord.getMessagesConfiguration().getTranslation("firewall_cleared", size));
-+ }
-+
-+ this.firewalled.clear();
-+ }
-+
-+ this.seconds = defaultSeconds;
-+ }
-+ }
-+}
-\ No newline at end of file
-diff --git a/log/.factorypath b/log/.factorypath
-new file mode 100644
-index 00000000..542d5259
---- /dev/null
-+++ b/log/.factorypath
-@@ -0,0 +1,7 @@
-+
-+
-+
-+
-+
-+
-+
-diff --git a/log/pom.xml b/log/pom.xml
-index 3ef8acf2..e0177785 100644
---- a/log/pom.xml
-+++ b/log/pom.xml
-@@ -1,6 +1,5 @@
--
--
-+
- 4.0.0
-
-
-diff --git a/log4j/.factorypath b/log4j/.factorypath
-new file mode 100644
-index 00000000..f08118bd
---- /dev/null
-+++ b/log4j/.factorypath
-@@ -0,0 +1,18 @@
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-diff --git a/log4j/pom.xml b/log4j/pom.xml
-index ca18158f..bf76e567 100644
---- a/log4j/pom.xml
-+++ b/log4j/pom.xml
-@@ -1,5 +1,5 @@
--
-+
- 4.0.0
-
-
-diff --git a/log4j/src/main/java/io/github/waterfallmc/waterfall/log4j/Log4JLogHandler.java b/log4j/src/main/java/io/github/waterfallmc/waterfall/log4j/Log4JLogHandler.java
-index 63f66d3c..721cbb5e 100644
---- a/log4j/src/main/java/io/github/waterfallmc/waterfall/log4j/Log4JLogHandler.java
-+++ b/log4j/src/main/java/io/github/waterfallmc/waterfall/log4j/Log4JLogHandler.java
-@@ -16,9 +16,11 @@ import java.util.logging.LogRecord;
- /**
- * A {@link Handler} that forwards all log messages to the Log4J logger.
- *
-- *
We don't use Log4J's custom JUL LogManager currently, because it breaks
-+ *
-+ * We don't use Log4J's custom JUL LogManager currently, because it breaks
- * adding custom handlers to JUL loggers. Some plugins may depend on that
-- * functionality...
-+ * functionality...
-+ *
- */
- class Log4JLogHandler extends Handler {
-
-diff --git a/log4j/src/main/resources/log4j2-bungee.xml b/log4j/src/main/resources/log4j2-bungee.xml
-index 6e9c09c5..42059c2a 100644
---- a/log4j/src/main/resources/log4j2-bungee.xml
-+++ b/log4j/src/main/resources/log4j2-bungee.xml
-@@ -1,20 +1,21 @@
-
-
-+
-
-
-
-
--
-+
-
--
-+
-
-
-
-
-
--
-+
-
--
-+
-
-
-
-diff --git a/log4j/src/main/resources/log4j2.xml b/log4j/src/main/resources/log4j2.xml
-index 3b3525f0..89352ebe 100644
---- a/log4j/src/main/resources/log4j2.xml
-+++ b/log4j/src/main/resources/log4j2.xml
-@@ -3,9 +3,9 @@
-
-
-
--
-+
-
--
-+
-
-
-
-diff --git a/module/cmd-alert/.factorypath b/module/cmd-alert/.factorypath
-new file mode 100644
-index 00000000..7a4b5ae4
---- /dev/null
-+++ b/module/cmd-alert/.factorypath
-@@ -0,0 +1,17 @@
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-diff --git a/module/cmd-alert/pom.xml b/module/cmd-alert/pom.xml
-index 83bc7a7d..f45742c6 100644
---- a/module/cmd-alert/pom.xml
-+++ b/module/cmd-alert/pom.xml
-@@ -1,6 +1,5 @@
--
--
-+
- 4.0.0
-
-
-diff --git a/module/cmd-find/.factorypath b/module/cmd-find/.factorypath
-new file mode 100644
-index 00000000..7a4b5ae4
---- /dev/null
-+++ b/module/cmd-find/.factorypath
-@@ -0,0 +1,17 @@
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-diff --git a/module/cmd-find/pom.xml b/module/cmd-find/pom.xml
-index 42fb0a11..b717fb3b 100644
---- a/module/cmd-find/pom.xml
-+++ b/module/cmd-find/pom.xml
-@@ -1,6 +1,5 @@
--
--
-+
- 4.0.0
-
-
-diff --git a/module/cmd-list/.factorypath b/module/cmd-list/.factorypath
-new file mode 100644
-index 00000000..7a4b5ae4
---- /dev/null
-+++ b/module/cmd-list/.factorypath
-@@ -0,0 +1,17 @@
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-diff --git a/module/cmd-list/pom.xml b/module/cmd-list/pom.xml
-index cc2e55f9..9f3cf2f1 100644
---- a/module/cmd-list/pom.xml
-+++ b/module/cmd-list/pom.xml
-@@ -1,6 +1,5 @@
--
--
-+
- 4.0.0
-
-
-diff --git a/module/cmd-send/.factorypath b/module/cmd-send/.factorypath
-new file mode 100644
-index 00000000..7a4b5ae4
---- /dev/null
-+++ b/module/cmd-send/.factorypath
-@@ -0,0 +1,17 @@
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-diff --git a/module/cmd-send/pom.xml b/module/cmd-send/pom.xml
-index af82bb2c..7b5dae7a 100644
---- a/module/cmd-send/pom.xml
-+++ b/module/cmd-send/pom.xml
-@@ -1,6 +1,5 @@
--
--
-+
- 4.0.0
-
-
-diff --git a/module/cmd-server/.factorypath b/module/cmd-server/.factorypath
-new file mode 100644
-index 00000000..7a4b5ae4
---- /dev/null
-+++ b/module/cmd-server/.factorypath
-@@ -0,0 +1,17 @@
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-diff --git a/module/cmd-server/pom.xml b/module/cmd-server/pom.xml
-index 8d96679e..474e7eb4 100644
---- a/module/cmd-server/pom.xml
-+++ b/module/cmd-server/pom.xml
-@@ -1,6 +1,5 @@
--
--
-+
- 4.0.0
-
-
-diff --git a/module/pom.xml b/module/pom.xml
-index ca1f7487..51b58ada 100644
---- a/module/pom.xml
-+++ b/module/pom.xml
-@@ -1,6 +1,5 @@
--
--
-+
- 4.0.0
-
-
-diff --git a/module/reconnect-yaml/.factorypath b/module/reconnect-yaml/.factorypath
-new file mode 100644
-index 00000000..7a4b5ae4
---- /dev/null
-+++ b/module/reconnect-yaml/.factorypath
-@@ -0,0 +1,17 @@
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-diff --git a/module/reconnect-yaml/pom.xml b/module/reconnect-yaml/pom.xml
-index e6ee3cd8..23e319da 100644
---- a/module/reconnect-yaml/pom.xml
-+++ b/module/reconnect-yaml/pom.xml
-@@ -1,6 +1,5 @@
--
--
-+
- 4.0.0
-
-
-diff --git a/native/.factorypath b/native/.factorypath
-new file mode 100644
-index 00000000..0b31e14c
---- /dev/null
-+++ b/native/.factorypath
-@@ -0,0 +1,9 @@
-+
-+
-+
-+
-+
-+
-+
-+
-+
-diff --git a/native/pom.xml b/native/pom.xml
-index 28d1a02c..3aa9efa9 100644
---- a/native/pom.xml
-+++ b/native/pom.xml
-@@ -1,6 +1,5 @@
--
--
-+
- 4.0.0
-
-
-diff --git a/pom.xml b/pom.xml
-index 94e4aca2..7f0152ab 100644
---- a/pom.xml
-+++ b/pom.xml
-@@ -1,6 +1,5 @@
--
--
-+
- 4.0.0
-
-
-@@ -47,6 +46,14 @@
-
- fuzzybot
-
-+
-+
-+ LinsaFTW
-+
-+
-+ Sammwy
-+
-+
-
-
-
-@@ -62,6 +69,8 @@
- proxy
- query
- native
-+
-+ flamecord
-
-
-
-@@ -91,7 +100,7 @@
-
-
- unknown
-- 4.1.49.Final
-+ 4.1.51.Final
- 1.8
- 1.8
- UTF-8
-diff --git a/protocol/.factorypath b/protocol/.factorypath
-new file mode 100644
-index 00000000..739c34b9
---- /dev/null
-+++ b/protocol/.factorypath
-@@ -0,0 +1,14 @@
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-+
-diff --git a/protocol/pom.xml b/protocol/pom.xml
-index ba3ffe3d..bdb8b8c8 100644
---- a/protocol/pom.xml
-+++ b/protocol/pom.xml
-@@ -1,6 +1,5 @@
--
--
-+
- 4.0.0
-
-
-@@ -46,6 +45,14 @@
- ${project.version}
- compile
-
-+
-+
-+ dev._2lstudios.flamecord
-+ travertine-flamecord
-+ ${project.version}
-+ compile
-+
-+
-
- io.netty
- netty-codec
-diff --git a/protocol/src/main/java/net/md_5/bungee/protocol/DefinedPacket.java b/protocol/src/main/java/net/md_5/bungee/protocol/DefinedPacket.java
-index 6ba7ae70..e7a5682b 100644
---- a/protocol/src/main/java/net/md_5/bungee/protocol/DefinedPacket.java
-+++ b/protocol/src/main/java/net/md_5/bungee/protocol/DefinedPacket.java
-@@ -11,151 +11,140 @@ import java.io.IOException;
- import java.util.ArrayList;
- import java.util.List;
- import java.util.UUID;
-+
-+import com.google.common.base.Charsets;
-+
-+import io.netty.buffer.ByteBuf;
- import lombok.RequiredArgsConstructor;
- import se.llbit.nbt.NamedTag;
- import se.llbit.nbt.Tag;
-
- @RequiredArgsConstructor
--public abstract class DefinedPacket
--{
-+public abstract class DefinedPacket {
-
- private static final boolean PROCESS_TRACES = Boolean.getBoolean("waterfall.bad-packet-traces");
-- private static final BadPacketException OVERSIZED_VAR_INT_EXCEPTION = new BadPacketException( "VarInt too big" );
-- private static final BadPacketException NO_MORE_BYTES_EXCEPTION = new BadPacketException("No more bytes reading varint");
-- public static void writeString(String s, ByteBuf buf)
-- {
-- if ( s.length() > Short.MAX_VALUE )
-- {
-- throw new OverflowPacketException( String.format( "Cannot send string longer than Short.MAX_VALUE (got %s characters)", s.length() ) );
-+ private static final BadPacketException OVERSIZED_VAR_INT_EXCEPTION = new BadPacketException("VarInt too big");
-+ private static final BadPacketException NO_MORE_BYTES_EXCEPTION = new BadPacketException(
-+ "No more bytes reading varint");
-+
-+ public static void writeString(String s, ByteBuf buf) {
-+ if (s.length() > Short.MAX_VALUE) {
-+ throw new OverflowPacketException(
-+ String.format("Cannot send string longer than Short.MAX_VALUE (got %s characters)", s.length()));
- }
-
-- byte[] b = s.getBytes( Charsets.UTF_8 );
-- writeVarInt( b.length, buf );
-- buf.writeBytes( b );
-+ byte[] b = s.getBytes(Charsets.UTF_8);
-+ writeVarInt(b.length, buf);
-+ buf.writeBytes(b);
- }
-
-- public static String readString(ByteBuf buf)
-- {
-- int len = readVarInt( buf );
-- if ( len > Short.MAX_VALUE )
-- {
-- throw new OverflowPacketException( String.format( "Cannot receive string longer than Short.MAX_VALUE (got %s characters)", len ) );
-+ public static String readString(ByteBuf buf) {
-+ int len = readVarInt(buf);
-+ if (len > Short.MAX_VALUE) {
-+ throw new OverflowPacketException(
-+ String.format("Cannot receive string longer than Short.MAX_VALUE (got %s characters)", len));
- }
-
-- byte[] b = new byte[ len ];
-- buf.readBytes( b );
-+ byte[] b = new byte[len];
-+ buf.readBytes(b);
-
-- return new String( b, Charsets.UTF_8 );
-+ return new String(b, Charsets.UTF_8);
- }
-
- // Waterfall start
-- public static void writeString(String s, final int maxLength, ByteBuf buf)
-- {
-- if ( s.length() > maxLength )
-- {
-- throw new OverflowPacketException( String.format( "Cannot send string longer than %s (got %s characters)", maxLength, s.length() ) );
-+ public static void writeString(String s, final int maxLength, ByteBuf buf) {
-+ if (s.length() > maxLength) {
-+ throw new OverflowPacketException(
-+ String.format("Cannot send string longer than %s (got %s characters)", maxLength, s.length()));
- }
-
-- byte[] b = s.getBytes( Charsets.UTF_8 );
-- writeVarInt( b.length, buf );
-- buf.writeBytes( b );
-+ byte[] b = s.getBytes(Charsets.UTF_8);
-+ writeVarInt(b.length, buf);
-+ buf.writeBytes(b);
- }
-
-- public static String readString(ByteBuf buf, final int maxLength)
-- {
-- int len = readVarInt( buf );
-- if ( len > maxLength )
-- {
-- throw new OverflowPacketException( String.format( "Cannot receive string longer than %s (got %s characters)", maxLength, len ) );
-+ public static String readString(ByteBuf buf, final int maxLength) {
-+ int len = readVarInt(buf);
-+ if (len > maxLength) {
-+ throw new OverflowPacketException(
-+ String.format("Cannot receive string longer than %s (got %s characters)", maxLength, len));
- }
-
-- byte[] b = new byte[ len ];
-- buf.readBytes( b );
-+ byte[] b = new byte[len];
-+ buf.readBytes(b);
-
-- return new String( b, Charsets.UTF_8 );
-+ return new String(b, Charsets.UTF_8);
- }
- // Waterfall end
-
-- public static void writeArray(byte[] b, ByteBuf buf)
-- {
-- if ( b.length > Short.MAX_VALUE )
-- {
-- throw new OverflowPacketException( String.format( "Cannot send byte array longer than Short.MAX_VALUE (got %s bytes)", b.length ) );
-+ public static void writeArray(byte[] b, ByteBuf buf) {
-+ if (b.length > Short.MAX_VALUE) {
-+ throw new OverflowPacketException(
-+ String.format("Cannot send byte array longer than Short.MAX_VALUE (got %s bytes)", b.length));
- }
-- writeVarInt( b.length, buf );
-- buf.writeBytes( b );
-+ writeVarInt(b.length, buf);
-+ buf.writeBytes(b);
- }
-
-- public static byte[] toArray(ByteBuf buf)
-- {
-- byte[] ret = new byte[ buf.readableBytes() ];
-- buf.readBytes( ret );
-+ public static byte[] toArray(ByteBuf buf) {
-+ byte[] ret = new byte[buf.readableBytes()];
-+ buf.readBytes(ret);
-
- return ret;
- }
-
-- public static byte[] readArray(ByteBuf buf)
-- {
-- return readArray( buf, buf.readableBytes() );
-+ public static byte[] readArray(ByteBuf buf) {
-+ return readArray(buf, buf.readableBytes());
- }
-
-- public static byte[] readArray(ByteBuf buf, int limit)
-- {
-- int len = readVarInt( buf );
-- if ( len > limit )
-- {
-- throw new OverflowPacketException( String.format( "Cannot receive byte array longer than %s (got %s bytes)", limit, len ) );
-+ public static byte[] readArray(ByteBuf buf, int limit) {
-+ int len = readVarInt(buf);
-+ if (len > limit) {
-+ throw new OverflowPacketException(
-+ String.format("Cannot receive byte array longer than %s (got %s bytes)", limit, len));
- }
-- byte[] ret = new byte[ len ];
-- buf.readBytes( ret );
-+ byte[] ret = new byte[len];
-+ buf.readBytes(ret);
- return ret;
- }
-
-- public static int[] readVarIntArray(ByteBuf buf)
-- {
-- int len = readVarInt( buf );
-- int[] ret = new int[ len ];
-+ public static int[] readVarIntArray(ByteBuf buf) {
-+ int len = readVarInt(buf);
-+ int[] ret = new int[len];
-
-- for ( int i = 0; i < len; i++ )
-- {
-- ret[i] = readVarInt( buf );
-+ for (int i = 0; i < len; i++) {
-+ ret[i] = readVarInt(buf);
- }
-
- return ret;
- }
-
-- public static void writeStringArray(List s, ByteBuf buf)
-- {
-- writeVarInt( s.size(), buf );
-- for ( String str : s )
-- {
-- writeString( str, buf );
-+ public static void writeStringArray(List s, ByteBuf buf) {
-+ writeVarInt(s.size(), buf);
-+ for (String str : s) {
-+ writeString(str, buf);
- }
- }
-
-- public static List readStringArray(ByteBuf buf)
-- {
-- int len = readVarInt( buf );
-- List ret = new ArrayList<>( len );
-- for ( int i = 0; i < len; i++ )
-- {
-- ret.add( readString( buf ) );
-+ public static List readStringArray(ByteBuf buf) {
-+ int len = readVarInt(buf);
-+ List ret = new ArrayList<>(len);
-+ for (int i = 0; i < len; i++) {
-+ ret.add(readString(buf));
- }
- return ret;
- }
-
-- public static int readVarInt(ByteBuf input)
-- {
-- return readVarInt( input, 5 );
-+ public static int readVarInt(ByteBuf input) {
-+ return readVarInt(input, 5);
- }
-
-- public static int readVarInt(ByteBuf input, int maxBytes)
-- {
-+ public static int readVarInt(ByteBuf input, int maxBytes) {
- int out = 0;
- int bytes = 0;
- byte in;
-- while ( true )
-- {
-+
-+ while (true) {
- // Waterfall start
- if (input.readableBytes() == 0) {
- throw PROCESS_TRACES ? new BadPacketException("No more bytes reading varint") : NO_MORE_BYTES_EXCEPTION;
-@@ -163,15 +152,13 @@ public abstract class DefinedPacket
- // Waterfall end
- in = input.readByte();
-
-- out |= ( in & 0x7F ) << ( bytes++ * 7 );
-+ out |= (in & 0x7F) << (bytes++ * 7);
-
-- if ( bytes > maxBytes )
-- {
-- throw PROCESS_TRACES ? new BadPacketException( "VarInt too big" ) : OVERSIZED_VAR_INT_EXCEPTION;
-+ if (bytes > maxBytes) {
-+ throw PROCESS_TRACES ? new BadPacketException("VarInt too big") : OVERSIZED_VAR_INT_EXCEPTION;
- }
-
-- if ( ( in & 0x80 ) != 0x80 )
-- {
-+ if ((in & 0x80) != 0x80) {
- break;
- }
- }
-@@ -179,112 +166,91 @@ public abstract class DefinedPacket
- return out;
- }
-
-- public static void writeVarInt(int value, ByteBuf output)
-- {
-+ public static void writeVarInt(int value, ByteBuf output) {
- int part;
-- while ( true )
-- {
-+ while (true) {
- part = value & 0x7F;
-
- value >>>= 7;
-- if ( value != 0 )
-- {
-+ if (value != 0) {
- part |= 0x80;
- }
-
-- output.writeByte( part );
-+ output.writeByte(part);
-
-- if ( value == 0 )
-- {
-+ if (value == 0) {
- break;
- }
- }
- }
-
-- public static int readVarShort(ByteBuf buf)
-- {
-+ public static int readVarShort(ByteBuf buf) {
- int low = buf.readUnsignedShort();
- int high = 0;
-- if ( ( low & 0x8000 ) != 0 )
-- {
-+ if ((low & 0x8000) != 0) {
- low = low & 0x7FFF;
- high = buf.readUnsignedByte();
- }
-- return ( ( high & 0xFF ) << 15 ) | low;
-+ return ((high & 0xFF) << 15) | low;
- }
-
-- public static void writeVarShort(ByteBuf buf, int toWrite)
-- {
-+ public static void writeVarShort(ByteBuf buf, int toWrite) {
- int low = toWrite & 0x7FFF;
-- int high = ( toWrite & 0x7F8000 ) >> 15;
-- if ( high != 0 )
-- {
-+ int high = (toWrite & 0x7F8000) >> 15;
-+ if (high != 0) {
- low = low | 0x8000;
- }
-- buf.writeShort( low );
-- if ( high != 0 )
-- {
-- buf.writeByte( high );
-+ buf.writeShort(low);
-+ if (high != 0) {
-+ buf.writeByte(high);
- }
- }
-
-- public static void writeUUID(UUID value, ByteBuf output)
-- {
-- output.writeLong( value.getMostSignificantBits() );
-- output.writeLong( value.getLeastSignificantBits() );
-+ public static void writeUUID(UUID value, ByteBuf output) {
-+ output.writeLong(value.getMostSignificantBits());
-+ output.writeLong(value.getLeastSignificantBits());
- }
-
-- public static UUID readUUID(ByteBuf input)
-- {
-- return new UUID( input.readLong(), input.readLong() );
-+ public static UUID readUUID(ByteBuf input) {
-+ return new UUID(input.readLong(), input.readLong());
- }
-
-- public static Tag readTag(ByteBuf input)
-- {
-- Tag tag = NamedTag.read( new DataInputStream( new ByteBufInputStream( input ) ) );
-- Preconditions.checkArgument( !tag.isError(), "Error reading tag: %s", tag.error() );
-+ public static Tag readTag(ByteBuf input) {
-+ Tag tag = NamedTag.read(new DataInputStream(new ByteBufInputStream(input)));
-+ Preconditions.checkArgument(!tag.isError(), "Error reading tag: %s", tag.error());
- return tag;
- }
-
-- public static void writeTag(Tag tag, ByteBuf output)
-- {
-- try
-- {
-- tag.write( new DataOutputStream( new ByteBufOutputStream( output ) ) );
-- } catch ( IOException ex )
-- {
-- throw new RuntimeException( "Exception writing tag", ex );
-+ public static void writeTag(Tag tag, ByteBuf output) {
-+ try {
-+ tag.write(new DataOutputStream(new ByteBufOutputStream(output)));
-+ } catch (IOException ex) {
-+ throw new RuntimeException("Exception writing tag", ex);
- }
- }
-
-- public void read(ByteBuf buf)
-- {
-- throw new UnsupportedOperationException( "Packet must implement read method" );
-+ public void read(ByteBuf buf) {
-+ throw new UnsupportedOperationException("Packet must implement read method");
- }
-
-- public void read(ByteBuf buf, ProtocolConstants.Direction direction, int protocolVersion)
-- {
-- read( buf );
-+ public void read(ByteBuf buf, ProtocolConstants.Direction direction, int protocolVersion) {
-+ read(buf);
- }
-
-- public void read0(ByteBuf buf, ProtocolConstants.Direction direction, int protocolVersion)
-- {
-- read( buf, direction, protocolVersion );
-+ public void read0(ByteBuf buf, ProtocolConstants.Direction direction, int protocolVersion) {
-+ read(buf, direction, protocolVersion);
- }
-
-- public void write(ByteBuf buf)
-- {
-- throw new UnsupportedOperationException( "Packet must implement write method" );
-+ public void write(ByteBuf buf) {
-+ throw new UnsupportedOperationException("Packet must implement write method");
- }
-
-- public void write(ByteBuf buf, ProtocolConstants.Direction direction, int protocolVersion)
-- {
-- write( buf );
-+ public void write(ByteBuf buf, ProtocolConstants.Direction direction, int protocolVersion) {
-+ write(buf);
- }
-
-- public void write0(ByteBuf buf, ProtocolConstants.Direction direction, int protocolVersion)
-- {
-- write( buf, direction, protocolVersion );
-+ public void write0(ByteBuf buf, ProtocolConstants.Direction direction, int protocolVersion) {
-+ write(buf, direction, protocolVersion);
- }
-
- public abstract void handle(AbstractPacketHandler handler) throws Exception;
-diff --git a/protocol/src/main/java/net/md_5/bungee/protocol/LegacyDecoder.java b/protocol/src/main/java/net/md_5/bungee/protocol/LegacyDecoder.java
-index 5518bf26..b70f236b 100644
---- a/protocol/src/main/java/net/md_5/bungee/protocol/LegacyDecoder.java
-+++ b/protocol/src/main/java/net/md_5/bungee/protocol/LegacyDecoder.java
-@@ -1,46 +1,42 @@
- package net.md_5.bungee.protocol;
-
-+import java.util.List;
-+
- import io.netty.buffer.ByteBuf;
- import io.netty.buffer.Unpooled;
- import io.netty.channel.ChannelHandlerContext;
- import io.netty.handler.codec.ByteToMessageDecoder;
--import java.util.List;
- import net.md_5.bungee.protocol.packet.LegacyHandshake;
- import net.md_5.bungee.protocol.packet.LegacyPing;
-
--public class LegacyDecoder extends ByteToMessageDecoder
--{
-+public class LegacyDecoder extends ByteToMessageDecoder {
-
- @Override
-- protected void decode(ChannelHandlerContext ctx, ByteBuf in, List
-+
-+
-+ dev._2lstudios.flamecord
-+ travertine-flamecord
-+ ${project.version}
-+ compile
-+
-+
-+ io.github.waterfallmc
-+ travertine-module-cmd-alert
-+ ${project.version}
-+ compile
-+
-+
-+ io.github.waterfallmc
-+ travertine-module-cmd-find
-+ ${project.version}
-+ compile
-+
-+
-+ io.github.waterfallmc
-+ travertine-module-cmd-list
-+ ${project.version}
-+ compile
-+
-+
-+ io.github.waterfallmc
-+ travertine-module-cmd-send
-+ ${project.version}
-+ compile
-+
-+
-+ io.github.waterfallmc
-+ travertine-module-cmd-server
-+ ${project.version}
-+ compile
-+
-+
-+ io.github.waterfallmc
-+ travertine-module-reconnect-yaml
-+ ${project.version}
-+ compile
-+
-+
-
- net.sf.jopt-simple
- jopt-simple
-diff --git a/proxy/src/main/java/io/github/waterfallmc/waterfall/conf/WaterfallConfiguration.java b/proxy/src/main/java/io/github/waterfallmc/waterfall/conf/WaterfallConfiguration.java
-index e860214f..9f008a31 100644
---- a/proxy/src/main/java/io/github/waterfallmc/waterfall/conf/WaterfallConfiguration.java
-+++ b/proxy/src/main/java/io/github/waterfallmc/waterfall/conf/WaterfallConfiguration.java
-@@ -1,12 +1,11 @@
- package io.github.waterfallmc.waterfall.conf;
-
--import com.google.common.base.Joiner;
-+import java.io.File;
-+
- import net.md_5.bungee.conf.Configuration;
- import net.md_5.bungee.conf.YamlConfig;
- import net.md_5.bungee.protocol.ProtocolConstants;
-
--import java.io.File;
--
- public class WaterfallConfiguration extends Configuration {
-
- /**
-@@ -50,7 +49,9 @@ public class WaterfallConfiguration extends Configuration {
- YamlConfig config = new YamlConfig(new File("waterfall.yml"));
- config.load(false); // Load, but no permissions
- logInitialHandlerConnections = config.getBoolean( "log_initial_handler_connections", logInitialHandlerConnections );
-- gameVersion = config.getString("game_version", "").isEmpty() ? Joiner.on(", ").join(ProtocolConstants.SUPPORTED_VERSIONS) : config.getString("game_version", "");
-+ // FlameCord - Make the version look better
-+ //gameVersion = config.getString("game_version", "").isEmpty() ? Joiner.on(", ").join(ProtocolConstants.SUPPORTED_VERSIONS) : config.getString("game_version", "");
-+ gameVersion = config.getString("game_version", "").isEmpty() ? ProtocolConstants.SUPPORTED_VERSIONS.get(0) + "-" + ProtocolConstants.SUPPORTED_VERSIONS.get(ProtocolConstants.SUPPORTED_VERSIONS.size() - 1) : config.getString("game_version", "");
- useNettyDnsResolver = config.getBoolean("use_netty_dns_resolver", useNettyDnsResolver);
- // Throttling options
- tabThrottle = config.getInt("throttling.tab_complete", tabThrottle);
-diff --git a/proxy/src/main/java/net/md_5/bungee/BungeeCord.java b/proxy/src/main/java/net/md_5/bungee/BungeeCord.java
-index a17ed68e..4351b1f4 100644
---- a/proxy/src/main/java/net/md_5/bungee/BungeeCord.java
-+++ b/proxy/src/main/java/net/md_5/bungee/BungeeCord.java
-@@ -1,33 +1,10 @@
- package net.md_5.bungee;
-
--import com.google.common.base.Charsets;
--import com.google.common.base.Preconditions;
--import com.google.common.base.Predicate;
--import com.google.common.collect.Iterables;
--import com.google.common.collect.Lists;
--import com.google.common.collect.Sets;
--import com.google.common.util.concurrent.ThreadFactoryBuilder;
--import com.google.gson.Gson;
--import com.google.gson.GsonBuilder;
--import edu.umd.cs.findbugs.annotations.SuppressFBWarnings;
--import io.github.waterfallmc.waterfall.conf.WaterfallConfiguration;
--import io.github.waterfallmc.waterfall.event.ProxyExceptionEvent;
--import io.github.waterfallmc.waterfall.exception.ProxyPluginEnableDisableException;
--import io.netty.bootstrap.ServerBootstrap;
--import io.netty.channel.Channel;
--import io.netty.channel.ChannelException;
--import io.netty.channel.ChannelFuture;
--import io.netty.channel.ChannelFutureListener;
--import io.netty.channel.ChannelOption;
--import io.netty.channel.EventLoopGroup;
--import io.netty.util.ResourceLeakDetector;
- import java.io.File;
- import java.io.FileReader;
- import java.io.IOException;
--import java.io.PrintStream;
- import java.net.InetSocketAddress;
- import java.net.SocketAddress;
--import java.text.MessageFormat;
- import java.util.ArrayList;
- import java.util.Collection;
- import java.util.Collections;
-@@ -48,6 +25,33 @@ import java.util.concurrent.locks.ReentrantReadWriteLock;
- import java.util.logging.Handler;
- import java.util.logging.Level;
- import java.util.logging.Logger;
-+
-+import com.google.common.base.Charsets;
-+import com.google.common.base.Preconditions;
-+import com.google.common.base.Predicate;
-+import com.google.common.collect.Iterables;
-+import com.google.common.collect.Lists;
-+import com.google.common.collect.Sets;
-+import com.google.common.util.concurrent.ThreadFactoryBuilder;
-+import com.google.gson.Gson;
-+import com.google.gson.GsonBuilder;
-+
-+import dev._2lstudios.flamecord.FlameCord;
-+import dev._2lstudios.flamecord.configuration.MessagesConfiguration;
-+import dev._2lstudios.flamecord.configuration.ModulesConfiguration;
-+import dev._2lstudios.flamecord.firewall.FirewallManager;
-+import edu.umd.cs.findbugs.annotations.SuppressFBWarnings;
-+import io.github.waterfallmc.waterfall.conf.WaterfallConfiguration;
-+import io.github.waterfallmc.waterfall.event.ProxyExceptionEvent;
-+import io.github.waterfallmc.waterfall.exception.ProxyPluginEnableDisableException;
-+import io.netty.bootstrap.ServerBootstrap;
-+import io.netty.channel.Channel;
-+import io.netty.channel.ChannelException;
-+import io.netty.channel.ChannelFuture;
-+import io.netty.channel.ChannelFutureListener;
-+import io.netty.channel.ChannelOption;
-+import io.netty.channel.EventLoopGroup;
-+import io.netty.util.ResourceLeakDetector;
- import lombok.Getter;
- import lombok.Setter;
- import lombok.Synchronized;
-@@ -67,6 +71,7 @@ import net.md_5.bungee.api.config.ConfigurationAdapter;
- import net.md_5.bungee.api.config.ListenerInfo;
- import net.md_5.bungee.api.config.ServerInfo;
- import net.md_5.bungee.api.connection.ProxiedPlayer;
-+import net.md_5.bungee.api.plugin.Command;
- import net.md_5.bungee.api.plugin.Plugin;
- import net.md_5.bungee.api.plugin.PluginManager;
- import net.md_5.bungee.chat.ComponentSerializer;
-@@ -86,6 +91,12 @@ import net.md_5.bungee.conf.Configuration;
- import net.md_5.bungee.conf.YamlConfig;
- import net.md_5.bungee.forge.ForgeConstants;
- import net.md_5.bungee.module.ModuleManager;
-+import net.md_5.bungee.module.cmd.alert.CommandAlert;
-+import net.md_5.bungee.module.cmd.find.CommandFind;
-+import net.md_5.bungee.module.cmd.list.CommandList;
-+import net.md_5.bungee.module.cmd.send.CommandSend;
-+import net.md_5.bungee.module.cmd.server.CommandServer;
-+import net.md_5.bungee.module.reconnect.yaml.YamlReconnectHandler;
- import net.md_5.bungee.netty.PipelineUtils;
- import net.md_5.bungee.protocol.DefinedPacket;
- import net.md_5.bungee.protocol.ProtocolConstants;
-@@ -97,8 +108,7 @@ import net.md_5.bungee.util.CaseInsensitiveMap;
- /**
- * Main BungeeCord proxy class.
- */
--public class BungeeCord extends ProxyServer
--{
-+public class BungeeCord extends ProxyServer {
-
- /**
- * Current operation state.
-@@ -118,8 +128,9 @@ public class BungeeCord extends ProxyServer
- /**
- * locations.yml save thread.
- */
-- private final Timer saveThread = new Timer( "Reconnect Saver" );
-- // private final Timer metricsThread = new Timer( "Metrics Thread" ); // Waterfall: Disable Metrics
-+ private final Timer saveThread = new Timer("Reconnect Saver");
-+ // private final Timer metricsThread = new Timer( "Metrics Thread" ); //
-+ // Waterfall: Disable Metrics
- /**
- * Server socket listener.
- */
-@@ -133,8 +144,8 @@ public class BungeeCord extends ProxyServer
- private final Map connectionsByUUID = new HashMap<>();
- private final ReadWriteLock connectionLock = new ReentrantReadWriteLock();
- /**
-- * Lock to protect the shutdown process from being triggered simultaneously
-- * from multiple sources.
-+ * Lock to protect the shutdown process from being triggered simultaneously from
-+ * multiple sources.
- */
- private final ReentrantLock shutdownLock = new ReentrantLock();
- /**
-@@ -150,33 +161,31 @@ public class BungeeCord extends ProxyServer
- private ConfigurationAdapter configurationAdapter = new YamlConfig();
- private final Collection pluginChannels = new HashSet<>();
- @Getter
-- private final File pluginsFolder = new File( "plugins" );
-+ private final File pluginsFolder = new File("plugins");
- @Getter
- private final BungeeScheduler scheduler = new BungeeScheduler();
- // Waterfall start - Remove ConsoleReader for JLine 3 update
- /*
-- @Getter
-- private final ConsoleReader consoleReader;
-- */
-+ * @Getter private final ConsoleReader consoleReader;
-+ */
- // Waterfall end
- @Getter
- private final Logger logger;
-- public final Gson gson = new GsonBuilder()
-- .registerTypeAdapter( BaseComponent.class, new ComponentSerializer() )
-- .registerTypeAdapter( TextComponent.class, new TextComponentSerializer() )
-- .registerTypeAdapter( TranslatableComponent.class, new TranslatableComponentSerializer() )
-- .registerTypeAdapter( KeybindComponent.class, new KeybindComponentSerializer() )
-- .registerTypeAdapter( ScoreComponent.class, new ScoreComponentSerializer() )
-- .registerTypeAdapter( SelectorComponent.class, new SelectorComponentSerializer() )
-- .registerTypeAdapter( ServerPing.PlayerInfo.class, new PlayerInfoSerializer() )
-- .registerTypeAdapter( Favicon.class, Favicon.getFaviconTypeAdapter() ).create();
-+ public final Gson gson = new GsonBuilder().registerTypeAdapter(BaseComponent.class, new ComponentSerializer())
-+ .registerTypeAdapter(TextComponent.class, new TextComponentSerializer())
-+ .registerTypeAdapter(TranslatableComponent.class, new TranslatableComponentSerializer())
-+ .registerTypeAdapter(KeybindComponent.class, new KeybindComponentSerializer())
-+ .registerTypeAdapter(ScoreComponent.class, new ScoreComponentSerializer())
-+ .registerTypeAdapter(SelectorComponent.class, new SelectorComponentSerializer())
-+ .registerTypeAdapter(ServerPing.PlayerInfo.class, new PlayerInfoSerializer())
-+ .registerTypeAdapter(Favicon.class, Favicon.getFaviconTypeAdapter()).create();
- // Travertine start
-- public final Gson gsonLegacy = new GsonBuilder()
-- .registerTypeAdapter( BaseComponent.class, new ComponentSerializer() )
-- .registerTypeAdapter( TextComponent.class, new TextComponentSerializer() )
-- .registerTypeAdapter( TranslatableComponent.class, new TranslatableComponentSerializer() )
-- .registerTypeAdapter( ServerPing.PlayerInfo.class, new PlayerInfoSerializer( ProtocolConstants.MINECRAFT_1_7_2 ) )
-- .registerTypeAdapter( Favicon.class, Favicon.getFaviconTypeAdapter() ).create();
-+ public final Gson gsonLegacy = new GsonBuilder().registerTypeAdapter(BaseComponent.class, new ComponentSerializer())
-+ .registerTypeAdapter(TextComponent.class, new TextComponentSerializer())
-+ .registerTypeAdapter(TranslatableComponent.class, new TranslatableComponentSerializer())
-+ .registerTypeAdapter(ServerPing.PlayerInfo.class,
-+ new PlayerInfoSerializer(ProtocolConstants.MINECRAFT_1_7_2))
-+ .registerTypeAdapter(Favicon.class, Favicon.getFaviconTypeAdapter()).create();
- // Travertine end
- @Getter
- private ConnectionThrottle connectionThrottle;
-@@ -184,241 +193,227 @@ public class BungeeCord extends ProxyServer
-
- {
- // TODO: Proper fallback when we interface the manager
-- registerChannel( "BungeeCord" );
-+ registerChannel("BungeeCord");
- }
-
-- public static BungeeCord getInstance()
-- {
-+ public static BungeeCord getInstance() {
- return (BungeeCord) ProxyServer.getInstance();
- }
-
- @SuppressFBWarnings("DM_DEFAULT_ENCODING")
-- public BungeeCord() throws IOException
-- {
-- // Java uses ! to indicate a resource inside of a jar/zip/other container. Running Bungee from within a directory that has a ! will cause this to muck up.
-- Preconditions.checkState( new File( "." ).getAbsolutePath().indexOf( '!' ) == -1, "Cannot use Travertine in directory with ! in path." );
--
-- try
-- {
-- baseBundle = ResourceBundle.getBundle( "messages" );
-- } catch ( MissingResourceException ex )
-- {
-- baseBundle = ResourceBundle.getBundle( "messages", Locale.ENGLISH );
-+ public BungeeCord() throws IOException {
-+ // Java uses ! to indicate a resource inside of a jar/zip/other container.
-+ // Running Bungee from within a directory that has a ! will cause this to muck
-+ // up.
-+ Preconditions.checkState(new File(".").getAbsolutePath().indexOf('!') == -1,
-+ "Cannot use Travertine in directory with ! in path.");
-+
-+ try {
-+ baseBundle = ResourceBundle.getBundle("messages");
-+ } catch (MissingResourceException ex) {
-+ baseBundle = ResourceBundle.getBundle("messages", Locale.ENGLISH);
- }
- reloadMessages();
-
-- // This is a workaround for quite possibly the weirdest bug I have ever encountered in my life!
-- // When jansi attempts to extract its natives, by default it tries to extract a specific version,
-- // using the loading class's implementation version. Normally this works completely fine,
-- // however when on Windows certain characters such as - and : can trigger special behaviour.
-- // Furthermore this behaviour only occurs in specific combinations due to the parsing done by jansi.
-- // For example test-test works fine, but test-test-test does not! In order to avoid this all together but
-- // still keep our versions the same as they were, we set the override property to the essentially garbage version
-- // BungeeCord. This version is only used when extracting the libraries to their temp folder.
-- System.setProperty( "library.jansi.version", "BungeeCord" );
-+ // This is a workaround for quite possibly the weirdest bug I have ever
-+ // encountered in my life!
-+ // When jansi attempts to extract its natives, by default it tries to extract a
-+ // specific version,
-+ // using the loading class's implementation version. Normally this works
-+ // completely fine,
-+ // however when on Windows certain characters such as - and : can trigger
-+ // special behaviour.
-+ // Furthermore this behaviour only occurs in specific combinations due to the
-+ // parsing done by jansi.
-+ // For example test-test works fine, but test-test-test does not! In order to
-+ // avoid this all together but
-+ // still keep our versions the same as they were, we set the override property
-+ // to the essentially garbage version
-+ // BungeeCord. This version is only used when extracting the libraries to their
-+ // temp folder.
-+ System.setProperty("library.jansi.version", "BungeeCord");
-
- // Waterfall start - Use TerminalConsoleAppender and Log4J
- /*
-- AnsiConsole.systemInstall();
-- consoleReader = new ConsoleReader();
-- consoleReader.setExpandEvents( false );
-- consoleReader.addCompleter( new ConsoleCommandCompleter( this ) );
--
-- logger = new BungeeLogger( "BungeeCord", "proxy.log", consoleReader );
-- System.setErr( new PrintStream( new LoggingOutputStream( logger, Level.SEVERE ), true ) );
-- System.setOut( new PrintStream( new LoggingOutputStream( logger, Level.INFO ), true ) );
-- */
-+ * AnsiConsole.systemInstall(); consoleReader = new ConsoleReader();
-+ * consoleReader.setExpandEvents( false ); consoleReader.addCompleter( new
-+ * ConsoleCommandCompleter( this ) );
-+ *
-+ * logger = new BungeeLogger( "BungeeCord", "proxy.log", consoleReader );
-+ * System.setErr( new PrintStream( new LoggingOutputStream( logger, Level.SEVERE
-+ * ), true ) ); System.setOut( new PrintStream( new LoggingOutputStream( logger,
-+ * Level.INFO ), true ) );
-+ */
- logger = io.github.waterfallmc.waterfall.log4j.WaterfallLogger.create();
- // Waterfall end
-
-- pluginManager = new PluginManager( this );
-- getPluginManager().registerCommand( null, new CommandReload() );
-- getPluginManager().registerCommand( null, new CommandEnd() );
-- getPluginManager().registerCommand( null, new CommandIP() );
-- getPluginManager().registerCommand( null, new CommandBungee() );
-- getPluginManager().registerCommand( null, new CommandPerms() );
--
-- if ( !Boolean.getBoolean( "net.md_5.bungee.native.disable" ) )
-- {
-- if ( EncryptionUtil.nativeFactory.load() )
-- {
-- logger.info( "Using mbed TLS based native cipher." );
-- } else
-- {
-- logger.info( "Using standard Java JCE cipher." );
-+ pluginManager = new PluginManager(this);
-+ // FlameCord - Use own module system
-+ // getPluginManager().registerCommand( null, new CommandReload() );
-+ // getPluginManager().registerCommand( null, new CommandEnd() );
-+ // getPluginManager().registerCommand( null, new CommandIP() );
-+ // getPluginManager().registerCommand( null, new CommandBungee() );
-+ // getPluginManager().registerCommand( null, new CommandPerms() );
-+
-+ if (!Boolean.getBoolean("net.md_5.bungee.native.disable")) {
-+ if (EncryptionUtil.nativeFactory.load()) {
-+ logger.info("Using mbed TLS based native cipher.");
-+ } else {
-+ logger.info("Using standard Java JCE cipher.");
- }
-- if ( CompressFactory.zlib.load() )
-- {
-- logger.info( "Using zlib based native compressor." );
-- } else
-- {
-- logger.info( "Using standard Java compressor." );
-+ if (CompressFactory.zlib.load()) {
-+ logger.info("Using zlib based native compressor.");
-+ } else {
-+ logger.info("Using standard Java compressor.");
- }
- }
- }
-
- /**
-- * Start this proxy instance by loading the configuration, plugins and
-- * starting the connect thread.
-+ * Start this proxy instance by loading the configuration, plugins and starting
-+ * the connect thread.
- *
- * @throws Exception any critical errors encountered
- */
- @SuppressFBWarnings("RV_RETURN_VALUE_IGNORED_BAD_PRACTICE")
-- public void start() throws Exception
-- {
-- System.setProperty( "io.netty.selectorAutoRebuildThreshold", "0" ); // Seems to cause Bungee to stop accepting connections
-- if ( System.getProperty( "io.netty.leakDetectionLevel" ) == null )
-- {
-- ResourceLeakDetector.setLevel( ResourceLeakDetector.Level.DISABLED ); // Eats performance
-+ public void start() throws Exception {
-+ System.setProperty("io.netty.selectorAutoRebuildThreshold", "0"); // Seems to cause Bungee to stop accepting
-+ // connections
-+ if (System.getProperty("io.netty.leakDetectionLevel") == null) {
-+ ResourceLeakDetector.setLevel(ResourceLeakDetector.Level.DISABLED); // Eats performance
- }
-
-- bossEventLoopGroup = PipelineUtils.newEventLoopGroup( 0, new ThreadFactoryBuilder().setNameFormat( "Netty Boss IO Thread #%1$d" ).build() );
-- workerEventLoopGroup = PipelineUtils.newEventLoopGroup( 0, new ThreadFactoryBuilder().setNameFormat( "Netty Worker IO Thread #%1$d" ).build() );
-+ bossEventLoopGroup = PipelineUtils.newEventLoopGroup(0,
-+ new ThreadFactoryBuilder().setNameFormat("Netty Boss IO Thread #%1$d").build());
-+ workerEventLoopGroup = PipelineUtils.newEventLoopGroup(0,
-+ new ThreadFactoryBuilder().setNameFormat("Netty Worker IO Thread #%1$d").build());
-
-- File moduleDirectory = new File( "modules" );
-- moduleManager.load( this, moduleDirectory );
-- pluginManager.detectPlugins( moduleDirectory );
-+ // FlameCord - Use own module system and reload FlameCord
-+ /*
-+ * File moduleDirectory = new File( "modules" ); moduleManager.load( this,
-+ * moduleDirectory ); pluginManager.detectPlugins( moduleDirectory );
-+ */
-+ FlameCord.renew(logger);
-+ registerModules();
-
- pluginsFolder.mkdir();
-- pluginManager.detectPlugins( pluginsFolder );
-+ pluginManager.detectPlugins(pluginsFolder);
-
- pluginManager.loadPlugins();
- config.load();
-
-- if ( config.isForgeSupport() )
-- {
-- registerChannel( ForgeConstants.FML_TAG );
-- registerChannel( ForgeConstants.FML_HANDSHAKE_TAG );
-- registerChannel( ForgeConstants.FORGE_REGISTER );
-+ if (config.isForgeSupport()) {
-+ registerChannel(ForgeConstants.FML_TAG);
-+ registerChannel(ForgeConstants.FML_HANDSHAKE_TAG);
-+ registerChannel(ForgeConstants.FORGE_REGISTER);
- }
-
- isRunning = true;
-
- pluginManager.enablePlugins();
-
-- if ( config.getThrottle() > 0 )
-- {
-- connectionThrottle = new ConnectionThrottle( config.getThrottle(), config.getThrottleLimit() );
-+ if (config.getThrottle() > 0) {
-+ connectionThrottle = new ConnectionThrottle(config.getThrottle(), config.getThrottleLimit());
- }
- startListeners();
-
-- saveThread.scheduleAtFixedRate( new TimerTask()
-- {
-+ saveThread.scheduleAtFixedRate(new TimerTask() {
- @Override
-- public void run()
-- {
-- if ( getReconnectHandler() != null )
-- {
-+ public void run() {
-+ if (getReconnectHandler() != null) {
- getReconnectHandler().save();
- }
- }
-- }, 0, TimeUnit.MINUTES.toMillis( 5 ) );
-- //metricsThread.scheduleAtFixedRate( new Metrics(), 0, TimeUnit.MINUTES.toMillis( Metrics.PING_INTERVAL ) ); // Waterfall: Disable Metrics
-+ }, 0, TimeUnit.MINUTES.toMillis(5));
-+ // metricsThread.scheduleAtFixedRate( new Metrics(), 0,
-+ // TimeUnit.MINUTES.toMillis( Metrics.PING_INTERVAL ) ); // Waterfall: Disable
-+ // Metrics
-
-- Runtime.getRuntime().addShutdownHook( new Thread()
-- {
-+ Runtime.getRuntime().addShutdownHook(new Thread() {
- @Override
-- public void run()
-- {
-- independentThreadStop( getTranslation( "restart" ), false );
-+ public void run() {
-+ independentThreadStop(getTranslation("restart"), false);
- }
-- } );
-+ });
- }
-
-- public void startListeners()
-- {
-- for ( final ListenerInfo info : config.getListeners() )
-- {
-- if ( info.isProxyProtocol() )
-- {
-- getLogger().log( Level.WARNING, "Using PROXY protocol for listener {0}, please ensure this listener is adequately firewalled.", info.getSocketAddress() );
--
-- if ( connectionThrottle != null )
-- {
-+ public void startListeners() {
-+ for (final ListenerInfo info : config.getListeners()) {
-+ if (info.isProxyProtocol()) {
-+ logger.log(Level.WARNING,
-+ "Using PROXY protocol for listener {0}, please ensure this listener is adequately firewalled.",
-+ info.getSocketAddress());
-+
-+ if (connectionThrottle != null) {
- connectionThrottle = null;
-- getLogger().log( Level.WARNING, "Since PROXY protocol is in use, internal connection throttle has been disabled." );
-+ logger.log(Level.WARNING,
-+ "Since PROXY protocol is in use, internal connection throttle has been disabled.");
- }
- }
-
-- ChannelFutureListener listener = new ChannelFutureListener()
-- {
-+ ChannelFutureListener listener = new ChannelFutureListener() {
- @Override
-- public void operationComplete(ChannelFuture future) throws Exception
-- {
-- if ( future.isSuccess() )
-- {
-- listeners.add( future.channel() );
-- getLogger().log( Level.INFO, "Listening on {0}", info.getSocketAddress() );
-- } else
-- {
-- getLogger().log( Level.WARNING, "Could not bind to host " + info.getSocketAddress(), future.cause() );
-+ public void operationComplete(ChannelFuture future) throws Exception {
-+ if (future.isSuccess()) {
-+ listeners.add(future.channel());
-+ logger.log(Level.INFO, "Listening on {0}", info.getSocketAddress());
-+ } else {
-+ logger.log(Level.WARNING, "Could not bind to host " + info.getSocketAddress(), future.cause());
- }
- }
- };
-- new ServerBootstrap()
-- .channel( PipelineUtils.getServerChannel( info.getSocketAddress() ) )
-- .option( ChannelOption.SO_REUSEADDR, true ) // TODO: Move this elsewhere!
-- .childAttr( PipelineUtils.LISTENER, info )
-- .childHandler( PipelineUtils.SERVER_CHILD )
-- .group( bossEventLoopGroup, workerEventLoopGroup )
-- .localAddress( info.getSocketAddress() )
-- .bind().addListener( listener );
--
-- if ( info.isQueryEnabled() )
-- {
-- Preconditions.checkArgument( info.getSocketAddress() instanceof InetSocketAddress, "Can only create query listener on UDP address" );
--
-- ChannelFutureListener bindListener = new ChannelFutureListener()
-- {
-+ new ServerBootstrap().channel(PipelineUtils.getServerChannel(info.getSocketAddress()))
-+ .option(ChannelOption.SO_REUSEADDR, true) // TODO: Move this elsewhere!
-+ .childAttr(PipelineUtils.LISTENER, info).childHandler(PipelineUtils.SERVER_CHILD)
-+ .group(bossEventLoopGroup, workerEventLoopGroup).localAddress(info.getSocketAddress()).bind()
-+ .addListener(listener);
-+
-+ if (info.isQueryEnabled()) {
-+ Preconditions.checkArgument(info.getSocketAddress() instanceof InetSocketAddress,
-+ "Can only create query listener on UDP address");
-+
-+ ChannelFutureListener bindListener = new ChannelFutureListener() {
- @Override
-- public void operationComplete(ChannelFuture future) throws Exception
-- {
-- if ( future.isSuccess() )
-- {
-- listeners.add( future.channel() );
-- getLogger().log( Level.INFO, "Started query on {0}", future.channel().localAddress() );
-- } else
-- {
-- getLogger().log( Level.WARNING, "Could not bind to host " + info.getSocketAddress(), future.cause() );
-+ public void operationComplete(ChannelFuture future) throws Exception {
-+ if (future.isSuccess()) {
-+ listeners.add(future.channel());
-+ logger.log(Level.INFO, "Started query on {0}", future.channel().localAddress());
-+ } else {
-+ logger.log(Level.WARNING, "Could not bind to host " + info.getSocketAddress(),
-+ future.cause());
- }
- }
- };
-- new RemoteQuery( this, info ).start( PipelineUtils.getDatagramChannel(), new InetSocketAddress( info.getHost().getAddress(), info.getQueryPort() ), workerEventLoopGroup, bindListener );
-+ new RemoteQuery(this, info).start(PipelineUtils.getDatagramChannel(),
-+ new InetSocketAddress(info.getHost().getAddress(), info.getQueryPort()), workerEventLoopGroup,
-+ bindListener);
- }
- }
- }
-
-- public void stopListeners()
-- {
-- for ( Channel listener : listeners )
-- {
-- getLogger().log( Level.INFO, "Closing listener {0}", listener );
-- try
-- {
-+ public void stopListeners() {
-+ for (Channel listener : listeners) {
-+ logger.log(Level.INFO, "Closing listener {0}", listener);
-+ try {
- listener.close().syncUninterruptibly();
-- } catch ( ChannelException ex )
-- {
-- getLogger().severe( "Could not close listen thread" );
-+ } catch (ChannelException ex) {
-+ logger.severe("Could not close listen thread");
- }
- }
- listeners.clear();
- }
-
- @Override
-- public void stop()
-- {
-- stop( getTranslation( "restart" ) );
-+ public void stop() {
-+ stop(getTranslation("restart"));
- }
-
- @Override
-- public void stop(final String reason)
-- {
-- new Thread( "Shutdown Thread" )
-- {
-+ public void stop(final String reason) {
-+ new Thread("Shutdown Thread") {
- @Override
-- public void run()
-- {
-- independentThreadStop( reason, true );
-+ public void run() {
-+ independentThreadStop(reason, true);
- }
- }.start();
- }
-@@ -426,15 +421,14 @@ public class BungeeCord extends ProxyServer
- // This must be run on a separate thread to avoid deadlock!
- @SuppressFBWarnings("DM_EXIT")
- @SuppressWarnings("TooBroadCatch")
-- private void independentThreadStop(final String reason, boolean callSystemExit)
-- {
-+ private void independentThreadStop(final String reason, boolean callSystemExit) {
- // Acquire the shutdown lock
-- // This needs to actually block here, otherwise running 'end' and then ctrl+c will cause the thread to terminate prematurely
-+ // This needs to actually block here, otherwise running 'end' and then ctrl+c
-+ // will cause the thread to terminate prematurely
- shutdownLock.lock();
-
- // Acquired the shutdown lock
-- if ( !isRunning )
-- {
-+ if (!isRunning) {
- // Server is already shutting down - nothing to do
- shutdownLock.unlock();
- return;
-@@ -442,84 +436,75 @@ public class BungeeCord extends ProxyServer
- isRunning = false;
-
- stopListeners();
-- getLogger().info( "Closing pending connections" );
-+ getLogger().info("Closing pending connections");
-
- connectionLock.readLock().lock();
-- try
-- {
-- getLogger().log( Level.INFO, "Disconnecting {0} connections", connections.size() );
-- for ( UserConnection user : connections.values() )
-- {
-- user.disconnect( reason );
-+ try {
-+ getLogger().log(Level.INFO, "Disconnecting {0} connections", connections.size());
-+ for (UserConnection user : connections.values()) {
-+ user.disconnect(reason);
- }
-- } finally
-- {
-+ } finally {
- connectionLock.readLock().unlock();
- }
-
-- try
-- {
-- Thread.sleep( 500 );
-- } catch ( InterruptedException ex )
-- {
-+ try {
-+ Thread.sleep(500);
-+ } catch (InterruptedException ex) {
- }
-
-- if ( reconnectHandler != null )
-- {
-- getLogger().info( "Saving reconnect locations" );
-+ if (reconnectHandler != null) {
-+ getLogger().info("Saving reconnect locations");
- reconnectHandler.save();
- reconnectHandler.close();
- }
- saveThread.cancel();
-- //metricsThread.cancel(); // Waterfall: Disable Metrics
-+ // metricsThread.cancel(); // Waterfall: Disable Metrics
-
-- getLogger().info( "Disabling plugins" );
-- for ( Plugin plugin : Lists.reverse( new ArrayList<>( pluginManager.getPlugins() ) ) )
-- {
-- try
-- {
-+ getLogger().info("Disabling plugins");
-+ for (Plugin plugin : Lists.reverse(new ArrayList<>(pluginManager.getPlugins()))) {
-+ try {
- plugin.onDisable();
-- for ( Handler handler : plugin.getLogger().getHandlers() )
-- {
-+ for (Handler handler : plugin.getLogger().getHandlers()) {
- handler.close();
- }
-- } catch ( Throwable t )
-- {
-+ } catch (Throwable t) {
- // Waterfall start - throw exception event
- String msg = "Exception disabling plugin " + plugin.getDescription().getName();
-- getLogger().log( Level.SEVERE, msg, t );
-- pluginManager.callEvent( new ProxyExceptionEvent( new ProxyPluginEnableDisableException( msg, t, plugin) ) );
-+ getLogger().log(Level.SEVERE, msg, t);
-+ pluginManager.callEvent(new ProxyExceptionEvent(new ProxyPluginEnableDisableException(msg, t, plugin)));
- // Waterfall end
- }
-- getScheduler().cancel( plugin );
-+ getScheduler().cancel(plugin);
- plugin.getExecutorService().shutdownNow();
- }
-
-- getLogger().info( "Closing IO threads" );
-- bossEventLoopGroup.shutdownGracefully();
-- workerEventLoopGroup.shutdownGracefully();
-- while (true) {
-- try {
-- bossEventLoopGroup.awaitTermination(Long.MAX_VALUE, TimeUnit.NANOSECONDS);
-- workerEventLoopGroup.awaitTermination(Long.MAX_VALUE, TimeUnit.NANOSECONDS);
-- break;
-- } catch (InterruptedException ignored) {}
-+ logger.info("Closing IO threads");
-+ bossEventLoopGroup.shutdownGracefully();
-+ workerEventLoopGroup.shutdownGracefully();
-+ while (true) {
-+ try {
-+ bossEventLoopGroup.awaitTermination(Long.MAX_VALUE, TimeUnit.NANOSECONDS);
-+ workerEventLoopGroup.awaitTermination(Long.MAX_VALUE, TimeUnit.NANOSECONDS);
-+ break;
-+ } catch (InterruptedException ignored) {
-+ }
- }
-
-- getLogger().info( "Thank you and goodbye" );
-+ getLogger().info("Thank you and goodbye");
- // Need to close loggers after last message!
-- for ( Handler handler : getLogger().getHandlers() )
-- {
-+ for (Handler handler : getLogger().getHandlers()) {
- handler.close();
- }
-
-- // Unlock the thread before optionally calling system exit, which might invoke this function again.
-- // If that happens, the system will obtain the lock, and then see that isRunning == false and return without doing anything.
-+ // Unlock the thread before optionally calling system exit, which might invoke
-+ // this function again.
-+ // If that happens, the system will obtain the lock, and then see that isRunning
-+ // == false and return without doing anything.
- shutdownLock.unlock();
-
-- if ( callSystemExit )
-- {
-- System.exit( 0 );
-+ if (callSystemExit) {
-+ System.exit(0);
- }
- }
-
-@@ -528,291 +513,336 @@ public class BungeeCord extends ProxyServer
- *
- * @param packet the packet to send
- */
-- public void broadcast(DefinedPacket packet)
-- {
-+ public void broadcast(DefinedPacket packet) {
- connectionLock.readLock().lock();
-- try
-- {
-- for ( UserConnection con : connections.values() )
-- {
-- con.unsafe().sendPacket( packet );
-+ try {
-+ for (UserConnection con : connections.values()) {
-+ con.unsafe().sendPacket(packet);
- }
-- } finally
-- {
-+ } finally {
- connectionLock.readLock().unlock();
- }
- }
-
- @Override
-- public String getName()
-- {
-- return "Travertine";
-+ public String getName() {
-+ // FlameCord - Use our own version name
-+ return "FlameCord";
- }
-
- @Override
-- public String getVersion()
-- {
-- return ( BungeeCord.class.getPackage().getImplementationVersion() == null ) ? "unknown" : BungeeCord.class.getPackage().getImplementationVersion();
-- }
--
-- public void reloadMessages()
-- {
-- File file = new File( "messages.properties" );
-- if ( file.isFile() )
-- {
-- try ( FileReader rd = new FileReader( file ) )
-- {
-- customBundle = new PropertyResourceBundle( rd );
-- } catch ( IOException ex )
-- {
-- getLogger().log( Level.SEVERE, "Could not load custom messages.properties", ex );
-+ public String getVersion() {
-+ // FlameCord - Use our own version string
-+ return "0.4.2";
-+ }
-+
-+ public void reloadMessages() {
-+ File file = new File("messages.properties");
-+ if (file.isFile()) {
-+ try (FileReader rd = new FileReader(file)) {
-+ customBundle = new PropertyResourceBundle(rd);
-+ } catch (IOException ex) {
-+ getLogger().log(Level.SEVERE, "Could not load custom messages.properties", ex);
- }
- }
- }
-
- @Override
-- public String getTranslation(String name, Object... args)
-- {
-- String translation = "";
-- try
-- {
-- final String string = customBundle != null && customBundle.containsKey( name ) ? customBundle.getString( name ) : baseBundle.getString( name );
--
-- translation = ( args.length == 0 ) ? string : MessageFormat.format( string, args );
-- } catch ( MissingResourceException ex )
-- {
-- }
-- return translation;
-+ public String getTranslation(String name, Object... args) {
-+ // FlameCord - Use our own translation system
-+ /*
-+ * String translation = ""; try { final
-+ * String string = customBundle != null && customBundle.containsKey(name) ?
-+ * customBundle.getString(name) : baseBundle.getString(name);
-+ *
-+ * translation = (args.length == 0) ? string : MessageFormat.format(string,
-+ * args); } catch (MissingResourceException ex) { } return translation;
-+ */
-+ return FlameCord.getInstance().getMessagesConfiguration().getTranslation(name, args);
- }
-
- @Override
- @SuppressWarnings("unchecked")
-- public Collection getPlayers()
-- {
-+ public Collection getPlayers() {
- connectionLock.readLock().lock();
-- try
-- {
-- return Collections.unmodifiableCollection( new HashSet( connections.values() ) );
-- } finally
-- {
-+ try {
-+ return Collections.unmodifiableCollection(new HashSet(connections.values()));
-+ } finally {
- connectionLock.readLock().unlock();
- }
- }
-
- @Override
-- public int getOnlineCount()
-- {
-+ public int getOnlineCount() {
- return connections.size();
- }
-
- @Override
-- public ProxiedPlayer getPlayer(String name)
-- {
-+ public ProxiedPlayer getPlayer(String name) {
- connectionLock.readLock().lock();
-- try
-- {
-- return connections.get( name );
-- } finally
-- {
-+ try {
-+ return connections.get(name);
-+ } finally {
- connectionLock.readLock().unlock();
- }
- }
-
-- public UserConnection getPlayerByOfflineUUID(UUID name)
-- {
-+ public UserConnection getPlayerByOfflineUUID(UUID name) {
- connectionLock.readLock().lock();
-- try
-- {
-- return connectionsByOfflineUUID.get( name );
-- } finally
-- {
-+ try {
-+ return connectionsByOfflineUUID.get(name);
-+ } finally {
- connectionLock.readLock().unlock();
- }
- }
-
- @Override
-- public ProxiedPlayer getPlayer(UUID uuid)
-- {
-+ public ProxiedPlayer getPlayer(UUID uuid) {
- connectionLock.readLock().lock();
-- try
-- {
-- return connectionsByUUID.get( uuid );
-- } finally
-- {
-+ try {
-+ return connectionsByUUID.get(uuid);
-+ } finally {
- connectionLock.readLock().unlock();
- }
- }
-
- @Override
-- public Map getServers()
-- {
-+ public Map getServers() {
- return config.getServers();
- }
-
- // Waterfall start
- @Override
-- public Map getServersCopy()
-- {
-+ public Map getServersCopy() {
- return config.getServersCopy();
- }
- // Waterfall end
-
- @Override
-- public ServerInfo getServerInfo(String name)
-- {
-- return config.getServerInfo( name ); // Waterfall
-+ public ServerInfo getServerInfo(String name) {
-+ return config.getServerInfo(name); // Waterfall
- }
-
- @Override
- @Synchronized("pluginChannels")
-- public void registerChannel(String channel)
-- {
-- pluginChannels.add( channel );
-+ public void registerChannel(String channel) {
-+ pluginChannels.add(channel);
- }
-
- @Override
- @Synchronized("pluginChannels")
-- public void unregisterChannel(String channel)
-- {
-- pluginChannels.remove( channel );
-+ public void unregisterChannel(String channel) {
-+ pluginChannels.remove(channel);
- }
-
- @Override
- @Synchronized("pluginChannels")
-- public Collection getChannels()
-- {
-- return Collections.unmodifiableCollection( pluginChannels );
-+ public Collection getChannels() {
-+ return Collections.unmodifiableCollection(pluginChannels);
- }
-
-- public PluginMessage registerChannels(int protocolVersion)
-- {
-- if ( protocolVersion >= ProtocolConstants.MINECRAFT_1_13 )
-- {
-- return new PluginMessage( "minecraft:register", Util.format( Iterables.transform( pluginChannels, PluginMessage.MODERNISE ), "\00" ).getBytes( Charsets.UTF_8 ), false );
-+ public PluginMessage registerChannels(int protocolVersion) {
-+ if (protocolVersion >= ProtocolConstants.MINECRAFT_1_13) {
-+ return new PluginMessage("minecraft:register",
-+ Util.format(Iterables.transform(pluginChannels, PluginMessage.MODERNISE), "\00")
-+ .getBytes(Charsets.UTF_8),
-+ false);
- }
-
-- return new PluginMessage( "REGISTER", Util.format( pluginChannels, "\00" ).getBytes( Charsets.UTF_8 ), false );
-+ return new PluginMessage("REGISTER", Util.format(pluginChannels, "\00").getBytes(Charsets.UTF_8), false);
- }
-
- @Override
-- public int getProtocolVersion()
-- {
-- return ProtocolConstants.SUPPORTED_VERSION_IDS.get( ProtocolConstants.SUPPORTED_VERSION_IDS.size() - 1 );
-+ public int getProtocolVersion() {
-+ return ProtocolConstants.SUPPORTED_VERSION_IDS.get(ProtocolConstants.SUPPORTED_VERSION_IDS.size() - 1);
- }
-
- @Override
-- public String getGameVersion()
-- {
-+ public String getGameVersion() {
- return getConfig().getGameVersion(); // Waterfall
- }
-
- @Override
-- public ServerInfo constructServerInfo(String name, InetSocketAddress address, String motd, boolean restricted)
-- {
-- return constructServerInfo( name, (SocketAddress) address, motd, restricted );
-+ public ServerInfo constructServerInfo(String name, InetSocketAddress address, String motd, boolean restricted) {
-+ return constructServerInfo(name, (SocketAddress) address, motd, restricted);
- }
-
- @Override
-- public ServerInfo constructServerInfo(String name, SocketAddress address, String motd, boolean restricted)
-- {
-- return new BungeeServerInfo( name, address, motd, restricted );
-+ public ServerInfo constructServerInfo(String name, SocketAddress address, String motd, boolean restricted) {
-+ return new BungeeServerInfo(name, address, motd, restricted);
- }
-
- @Override
-- public CommandSender getConsole()
-- {
-+ public CommandSender getConsole() {
- return ConsoleCommandSender.getInstance();
- }
-
- @Override
-- public void broadcast(String message)
-- {
-- broadcast( TextComponent.fromLegacyText( message ) );
-+ public void broadcast(String message) {
-+ broadcast(TextComponent.fromLegacyText(message));
- }
-
- @Override
-- public void broadcast(BaseComponent... message)
-- {
-- getConsole().sendMessage( BaseComponent.toLegacyText( message ) );
-- for ( ProxiedPlayer player : getPlayers() )
-- {
-- player.sendMessage( message );
-+ public void broadcast(BaseComponent... message) {
-+ getConsole().sendMessage(BaseComponent.toLegacyText(message));
-+ for (ProxiedPlayer player : getPlayers()) {
-+ player.sendMessage(message);
- }
- }
-
- @Override
-- public void broadcast(BaseComponent message)
-- {
-- getConsole().sendMessage( message.toLegacyText() );
-- for ( ProxiedPlayer player : getPlayers() )
-- {
-- player.sendMessage( message );
-+ public void broadcast(BaseComponent message) {
-+ getConsole().sendMessage(message.toLegacyText());
-+ for (ProxiedPlayer player : getPlayers()) {
-+ player.sendMessage(message);
- }
- }
-
-- public void addConnection(UserConnection con)
-- {
-+ public void addConnection(UserConnection con) {
- connectionLock.writeLock().lock();
-- try
-- {
-- connections.put( con.getName(), con );
-- connectionsByUUID.put( con.getUniqueId(), con );
-- connectionsByOfflineUUID.put( con.getPendingConnection().getOfflineId(), con );
-- } finally
-- {
-+ try {
-+ connections.put(con.getName(), con);
-+ connectionsByUUID.put(con.getUniqueId(), con);
-+ connectionsByOfflineUUID.put(con.getPendingConnection().getOfflineId(), con);
-+ } finally {
- connectionLock.writeLock().unlock();
- }
- }
-
-- public void removeConnection(UserConnection con)
-- {
-+ public void removeConnection(UserConnection con) {
- connectionLock.writeLock().lock();
-- try
-- {
-+ try {
- // TODO See #1218
-- if ( connections.get( con.getName() ) == con )
-- {
-- connections.remove( con.getName() );
-- connectionsByUUID.remove( con.getUniqueId() );
-- connectionsByOfflineUUID.remove( con.getPendingConnection().getOfflineId() );
-+ if (connections.get(con.getName()) == con) {
-+ connections.remove(con.getName());
-+ connectionsByUUID.remove(con.getUniqueId());
-+ connectionsByOfflineUUID.remove(con.getPendingConnection().getOfflineId());
- }
-- } finally
-- {
-+ } finally {
- connectionLock.writeLock().unlock();
- }
- }
-
- @Override
-- public Collection getDisabledCommands()
-- {
-+ public Collection getDisabledCommands() {
- return config.getDisabledCommands();
- }
-
- @Override
-- public Collection matchPlayer(final String partialName)
-- {
-- Preconditions.checkNotNull( partialName, "partialName" );
-+ public Collection matchPlayer(final String partialName) {
-+ Preconditions.checkNotNull(partialName, "partialName");
-
-- ProxiedPlayer exactMatch = getPlayer( partialName );
-- if ( exactMatch != null )
-- {
-- return Collections.singleton( exactMatch );
-+ ProxiedPlayer exactMatch = getPlayer(partialName);
-+ if (exactMatch != null) {
-+ return Collections.singleton(exactMatch);
- }
-
-- return Sets.newHashSet( Iterables.filter( getPlayers(), new Predicate()
-- {
-+ return Sets.newHashSet(Iterables.filter(getPlayers(), new Predicate() {
-
- @Override
-- public boolean apply(ProxiedPlayer input)
-- {
-- return ( input == null ) ? false : input.getName().toLowerCase( Locale.ROOT ).startsWith( partialName.toLowerCase( Locale.ROOT ) );
-+ public boolean apply(ProxiedPlayer input) {
-+ return (input == null) ? false
-+ : input.getName().toLowerCase(Locale.ROOT).startsWith(partialName.toLowerCase(Locale.ROOT));
- }
-- } ) );
-+ }));
- }
-
- @Override
-- public Title createTitle()
-- {
-+ public Title createTitle() {
- return new BungeeTitle();
- }
-+
-+ // FlameCord - Method to simplify module registering
-+ public void registerModules() {
-+ final PluginManager pluginManager = getPluginManager();
-+ final ModulesConfiguration modulesConfiguration = FlameCord.getInstance().getModulesConfiguration();
-+
-+ // Bungeecord Commands
-+ pluginManager.registerCommand(null, new CommandEnd());
-+ pluginManager.registerCommand(null, new CommandBungee());
-+
-+ if (modulesConfiguration.reloadEnabled) {
-+ pluginManager.registerCommand(null, new CommandReload());
-+ }
-+ if (modulesConfiguration.ipEnabled) {
-+ pluginManager.registerCommand(null, new CommandIP());
-+ }
-+ if (modulesConfiguration.permsEnabled) {
-+ pluginManager.registerCommand(null, new CommandPerms());
-+ }
-+
-+ // Modules Commands
-+ if (modulesConfiguration.alertEnabled) {
-+ pluginManager.registerCommand(null, new CommandAlert());
-+ }
-+ if (modulesConfiguration.findEnabled) {
-+ pluginManager.registerCommand(null, new CommandFind());
-+ }
-+ if (modulesConfiguration.listEnabled) {
-+ pluginManager.registerCommand(null, new CommandList());
-+ }
-+ if (modulesConfiguration.sendEnabled) {
-+ pluginManager.registerCommand(null, new CommandSend());
-+ }
-+ if (modulesConfiguration.serverEnabled) {
-+ pluginManager.registerCommand(null, new CommandServer());
-+ }
-+
-+ try {
-+ if (modulesConfiguration.reconnectEnabled) {
-+ for (ListenerInfo info : getConfig().getListeners()) {
-+ if (!info.isForceDefault() && getReconnectHandler() == null) {
-+ setReconnectHandler(new YamlReconnectHandler());
-+ break;
-+ }
-+ }
-+ }
-+ } catch (final Exception exception) {
-+ logger.warning("Reconnect module is not able to work on FlameCord!");
-+ }
-+
-+ // Flamecord - Commands (Had to make it like this because of netty limitations)
-+ pluginManager.registerCommand(null, new Command("flamecord") {
-+ @Override
-+ public void execute(final CommandSender sender, final String[] args) {
-+ final FlameCord flameCord = FlameCord.getInstance();
-+ final MessagesConfiguration messagesConfiguration = flameCord.getMessagesConfiguration();
-+
-+ if (sender.hasPermission("flamecord.usage")) {
-+ if (args.length > 0) {
-+ final String arg0 = args[0];
-+
-+ switch (arg0) {
-+ case "firewall": {
-+ final FirewallManager firewallManager = flameCord.getFirewallManager();
-+ final int amount = firewallManager.getFirewalled().size(),
-+ seconds = firewallManager.getSeconds();
-+
-+ sender.sendMessage(TextComponent.fromLegacyText(
-+ messagesConfiguration.getTranslation("firewall_info", amount, seconds)));
-+ break;
-+ }
-+ case "reload": {
-+ FlameCord.renew(logger);
-+ sender.sendMessage(TextComponent
-+ .fromLegacyText(messagesConfiguration.getTranslation("flamecord_reload")));
-+ break;
-+ }
-+ default: {
-+ sender.sendMessage(TextComponent.fromLegacyText(
-+ messagesConfiguration.getTranslation("flamecord_help", getVersion())));
-+ break;
-+ }
-+ }
-+ } else {
-+ sender.sendMessage(TextComponent
-+ .fromLegacyText(messagesConfiguration.getTranslation("flamecord_help", getVersion())));
-+ }
-+ } else {
-+ sender.sendMessage(TextComponent
-+ .fromLegacyText(messagesConfiguration.getTranslation("flamecord_nopermission")));
-+ }
-+ }
-+ });
-+ }
- }
-diff --git a/proxy/src/main/java/net/md_5/bungee/BungeeCordLauncher.java b/proxy/src/main/java/net/md_5/bungee/BungeeCordLauncher.java
-index ad9a6d0c..a2b585b3 100644
---- a/proxy/src/main/java/net/md_5/bungee/BungeeCordLauncher.java
-+++ b/proxy/src/main/java/net/md_5/bungee/BungeeCordLauncher.java
-@@ -1,80 +1,70 @@
- package net.md_5.bungee;
-
- import java.security.Security;
--import java.text.SimpleDateFormat;
- import java.util.Arrays;
--import java.util.Calendar;
--import java.util.Date;
--import java.util.concurrent.TimeUnit;
-+
- import joptsimple.OptionParser;
- import joptsimple.OptionSet;
--import net.md_5.bungee.api.ChatColor;
- import net.md_5.bungee.api.ProxyServer;
--import net.md_5.bungee.api.chat.ComponentBuilder;
--import net.md_5.bungee.command.ConsoleCommandSender;
-
--public class BungeeCordLauncher
--{
-+public class BungeeCordLauncher {
-
-- public static void main(String[] args) throws Exception
-- {
-- Security.setProperty( "networkaddress.cache.ttl", "30" );
-- Security.setProperty( "networkaddress.cache.negative.ttl", "10" );
-+ public static void main(String[] args) throws Exception {
-+ Security.setProperty("networkaddress.cache.ttl", "30");
-+ Security.setProperty("networkaddress.cache.negative.ttl", "10");
-
- OptionParser parser = new OptionParser();
- parser.allowsUnrecognizedOptions();
-- parser.acceptsAll( Arrays.asList( "help" ), "Show the help" );
-- parser.acceptsAll( Arrays.asList( "v", "version" ), "Print version and exit" );
-- parser.acceptsAll( Arrays.asList( "noconsole" ), "Disable console input" );
-+ parser.acceptsAll(Arrays.asList("help"), "Show the help");
-+ parser.acceptsAll(Arrays.asList("v", "version"), "Print version and exit");
-+ parser.acceptsAll(Arrays.asList("noconsole"), "Disable console input");
-
-- OptionSet options = parser.parse( args );
-+ OptionSet options = parser.parse(args);
-
-- if ( options.has( "help" ) )
-- {
-- parser.printHelpOn( System.out );
-+ if (options.has("help")) {
-+ parser.printHelpOn(System.out);
- return;
- }
-- if ( options.has( "version" ) )
-- {
-- System.out.println( BungeeCord.class.getPackage().getImplementationVersion() );
-+ if (options.has("version")) {
-+ System.out.println(BungeeCord.class.getPackage().getImplementationVersion());
- return;
- }
-
-- if ( BungeeCord.class.getPackage().getSpecificationVersion() != null && System.getProperty( "IReallyKnowWhatIAmDoingISwear" ) == null )
-- {
-- Date buildDate = new SimpleDateFormat( "yyyyMMdd" ).parse( BungeeCord.class.getPackage().getSpecificationVersion() );
--
-- Calendar deadline = Calendar.getInstance();
-- deadline.add( Calendar.WEEK_OF_YEAR, -8 );
-- if ( buildDate.before( deadline.getTime() ) )
-- {
-- System.err.println( "*** Hey! This build is potentially outdated :( ***" );
-- System.err.println( "*** Please check for a new build from https://papermc.io/ci/job/Travertine/ ***" );
-- System.err.println( "*** Should this build be outdated, you will get NO support for it. ***" );
-- System.err.println( "*** Server will start in 10 seconds ***" );
-- Thread.sleep( TimeUnit.SECONDS.toMillis( 10 ) );
-- }
-- }
-+ // FlameCord start - Disable update checker
-+ /*
-+ * if ( BungeeCord.class.getPackage().getSpecificationVersion() != null &&
-+ * System.getProperty( "IReallyKnowWhatIAmDoingISwear" ) == null ) { Date
-+ * buildDate = new SimpleDateFormat( "yyyyMMdd" ).parse(
-+ * BungeeCord.class.getPackage().getSpecificationVersion() );
-+ *
-+ * Calendar deadline = Calendar.getInstance(); deadline.add(
-+ * Calendar.WEEK_OF_YEAR, -8 ); if ( buildDate.before( deadline.getTime() ) ) {
-+ * System.err.println( "*** Hey! This build is potentially outdated :( ***" );
-+ * System.err.println(
-+ * "*** Please check for a new build from https://papermc.io/ci/job/Travertine/ ***"
-+ * ); System.err.println(
-+ * "*** Should this build be outdated, you will get NO support for it. ***" );
-+ * System.err.println( "*** Server will start in 10 seconds ***" );
-+ * Thread.sleep( TimeUnit.SECONDS.toMillis( 10 ) ); } }
-+ */
-
- BungeeCord bungee = new BungeeCord();
-- ProxyServer.setInstance( bungee );
-- bungee.getLogger().info( "Enabled Travertine version " + bungee.getVersion() );
-+ ProxyServer.setInstance(bungee);
-+ // FlameCord start - Renamed enabled message
-+ bungee.getLogger().info("Enabled FlameCord version " + bungee.getVersion());
- bungee.start();
-
-- if ( !options.has( "noconsole" ) )
-- {
-+ if (!options.has("noconsole")) {
- // Waterfall start - Use TerminalConsoleAppender
- new io.github.waterfallmc.waterfall.console.WaterfallConsole().start();
- /*
-- String line;
-- while ( bungee.isRunning && ( line = bungee.getConsoleReader().readLine( ">" ) ) != null )
-- {
-- if ( !bungee.getPluginManager().dispatchCommand( ConsoleCommandSender.getInstance(), line ) )
-- {
-- bungee.getConsole().sendMessage( new ComponentBuilder( "Command not found" ).color( ChatColor.RED ).create() );
-- }
-- }
-- */
-+ * String line; while ( bungee.isRunning && ( line =
-+ * bungee.getConsoleReader().readLine( ">" ) ) != null ) { if (
-+ * !bungee.getPluginManager().dispatchCommand(
-+ * ConsoleCommandSender.getInstance(), line ) ) {
-+ * bungee.getConsole().sendMessage( new ComponentBuilder( "Command not found"
-+ * ).color( ChatColor.RED ).create() ); } }
-+ */
- // Waterfall end
- }
- }
-diff --git a/proxy/src/main/java/net/md_5/bungee/BungeeServerInfo.java b/proxy/src/main/java/net/md_5/bungee/BungeeServerInfo.java
-index 7b002089..145bf328 100644
---- a/proxy/src/main/java/net/md_5/bungee/BungeeServerInfo.java
-+++ b/proxy/src/main/java/net/md_5/bungee/BungeeServerInfo.java
-@@ -1,10 +1,5 @@
- package net.md_5.bungee;
-
--import com.google.common.base.Preconditions;
--import io.netty.bootstrap.Bootstrap;
--import io.netty.channel.ChannelFuture;
--import io.netty.channel.ChannelFutureListener;
--import io.netty.channel.ChannelOption;
- import java.net.InetSocketAddress;
- import java.net.SocketAddress;
- import java.util.ArrayList;
-@@ -14,6 +9,13 @@ import java.util.HashSet;
- import java.util.LinkedList;
- import java.util.Objects;
- import java.util.Queue;
-+
-+import com.google.common.base.Preconditions;
-+
-+import io.netty.bootstrap.Bootstrap;
-+import io.netty.channel.ChannelFuture;
-+import io.netty.channel.ChannelFutureListener;
-+import io.netty.channel.ChannelOption;
- import lombok.Getter;
- import lombok.RequiredArgsConstructor;
- import lombok.Synchronized;
-diff --git a/proxy/src/main/java/net/md_5/bungee/PlayerInfoSerializer.java b/proxy/src/main/java/net/md_5/bungee/PlayerInfoSerializer.java
-index 299a216c..0ce9b03b 100644
---- a/proxy/src/main/java/net/md_5/bungee/PlayerInfoSerializer.java
-+++ b/proxy/src/main/java/net/md_5/bungee/PlayerInfoSerializer.java
-@@ -12,51 +12,45 @@ import java.util.UUID;
- import net.md_5.bungee.api.ServerPing;
- import net.md_5.bungee.protocol.ProtocolConstants;
-
--public class PlayerInfoSerializer implements JsonSerializer, JsonDeserializer
--{
-+public class PlayerInfoSerializer
-+ implements JsonSerializer, JsonDeserializer {
-
- // Travertine start
- private final int protocol;
-
-- public PlayerInfoSerializer()
-- {
-+ public PlayerInfoSerializer() {
- this.protocol = ProtocolConstants.MINECRAFT_1_7_6;
- }
-
-- public PlayerInfoSerializer(int protocol)
-- {
-+ public PlayerInfoSerializer(int protocol) {
- this.protocol = protocol;
- }
- // Travertine end
-
- @Override
-- public ServerPing.PlayerInfo deserialize(JsonElement json, Type typeOfT, JsonDeserializationContext context) throws JsonParseException
-- {
-+ public ServerPing.PlayerInfo deserialize(JsonElement json, Type typeOfT, JsonDeserializationContext context)
-+ throws JsonParseException {
- JsonObject js = json.getAsJsonObject();
-- ServerPing.PlayerInfo info = new ServerPing.PlayerInfo( js.get( "name" ).getAsString(), (UUID) null );
-- String id = js.get( "id" ).getAsString();
-- if ( ProtocolConstants.isBeforeOrEq( protocol, ProtocolConstants.MINECRAFT_1_7_2 ) || !id.contains( "-" ) ) // Travertine
-+ ServerPing.PlayerInfo info = new ServerPing.PlayerInfo(js.get("name").getAsString(), (UUID) null);
-+ String id = js.get("id").getAsString();
-+ if (ProtocolConstants.isBeforeOrEq(protocol, ProtocolConstants.MINECRAFT_1_7_2) || !id.contains("-")) // Travertine
- {
-- info.setId( id );
-- } else
-- {
-- info.setUniqueId( UUID.fromString( id ) );
-+ info.setId(id);
-+ } else {
-+ info.setUniqueId(UUID.fromString(id));
- }
- return info;
- }
-
- @Override
-- public JsonElement serialize(ServerPing.PlayerInfo src, Type typeOfSrc, JsonSerializationContext context)
-- {
-+ public JsonElement serialize(ServerPing.PlayerInfo src, Type typeOfSrc, JsonSerializationContext context) {
- JsonObject out = new JsonObject();
-- out.addProperty( "name", src.getName() );
-+ out.addProperty("name", src.getName());
- // Travertine start
-- if ( ProtocolConstants.isBeforeOrEq( protocol, ProtocolConstants.MINECRAFT_1_7_2 ) )
-- {
-- out.addProperty( "id", src.getId() );
-- } else
-- {
-- out.addProperty( "id", src.getUniqueId().toString() );
-+ if (ProtocolConstants.isBeforeOrEq(protocol, ProtocolConstants.MINECRAFT_1_7_2)) {
-+ out.addProperty("id", src.getId());
-+ } else {
-+ out.addProperty("id", src.getUniqueId().toString());
- }
- // Travertine end
- return out;
-diff --git a/proxy/src/main/java/net/md_5/bungee/ServerConnector.java b/proxy/src/main/java/net/md_5/bungee/ServerConnector.java
-index c12085e1..a80d56cf 100644
---- a/proxy/src/main/java/net/md_5/bungee/ServerConnector.java
-+++ b/proxy/src/main/java/net/md_5/bungee/ServerConnector.java
-@@ -1,15 +1,18 @@
- package net.md_5.bungee;
-
--import com.google.common.base.Preconditions;
--import io.netty.buffer.ByteBuf;
--import io.netty.buffer.ByteBufAllocator;
- import java.net.InetSocketAddress;
--import java.util.Locale;
--import java.util.Arrays; // Waterfall
- import java.nio.charset.StandardCharsets; // Travertine
-+import java.util.Arrays; // Waterfall
-+import java.util.Locale;
- import java.util.Queue;
- import java.util.Set;
- import java.util.UUID;
-+
-+import com.google.common.base.Preconditions;
-+
-+import dev._2lstudios.flamecord.FlameCord;
-+import io.netty.buffer.ByteBuf;
-+import io.netty.buffer.ByteBufAllocator;
- import lombok.Getter;
- import lombok.RequiredArgsConstructor;
- import net.md_5.bungee.api.ChatColor;
-@@ -34,6 +37,7 @@ import net.md_5.bungee.netty.ChannelWrapper;
- import net.md_5.bungee.netty.HandlerBoss;
- import net.md_5.bungee.netty.PacketHandler;
- import net.md_5.bungee.netty.PipelineUtils;
-+import net.md_5.bungee.protocol.BadPacketException;
- import net.md_5.bungee.protocol.DefinedPacket;
- import net.md_5.bungee.protocol.MinecraftDecoder;
- import net.md_5.bungee.protocol.PacketWrapper;
-@@ -57,8 +61,7 @@ import net.md_5.bungee.util.BufUtil;
- import net.md_5.bungee.util.QuietException;
-
- @RequiredArgsConstructor
--public class ServerConnector extends PacketHandler
--{
-+public class ServerConnector extends PacketHandler {
-
- private final ProxyServer bungee;
- private ChannelWrapper ch;
-@@ -69,63 +72,58 @@ public class ServerConnector extends PacketHandler
- private ForgeServerHandler handshakeHandler;
- private boolean obsolete;
-
-- private enum State
-- {
-+ private enum State {
-
- LOGIN_SUCCESS, ENCRYPT_RESPONSE, LOGIN, FINISHED;
- }
-
- @Override
-- public void exception(Throwable t) throws Exception
-- {
-- if ( obsolete )
-- {
-+ public void exception(Throwable t) throws Exception {
-+ if (obsolete) {
- return;
- }
-
-- String message = "Exception Connecting:" + Util.exception( t );
-- if ( user.getServer() == null )
-- {
-- user.disconnect( message );
-- } else
-- {
-- user.sendMessage( ChatColor.RED + message );
-+ String message = "Exception Connecting:" + Util.exception(t);
-+ if (user.getServer() == null) {
-+ user.disconnect(message);
-+ } else {
-+ user.sendMessage(ChatColor.RED + message);
- }
- }
-
- @Override
-- public void connected(ChannelWrapper channel) throws Exception
-- {
-+ public void connected(ChannelWrapper channel) throws Exception {
- this.ch = channel;
-
-- this.handshakeHandler = new ForgeServerHandler( user, ch, target );
-+ this.handshakeHandler = new ForgeServerHandler(user, ch, target);
- Handshake originalHandshake = user.getPendingConnection().getHandshake();
-- Handshake copiedHandshake = new Handshake( originalHandshake.getProtocolVersion(), originalHandshake.getHost(), originalHandshake.getPort(), 2 );
-+ Handshake copiedHandshake = new Handshake(originalHandshake.getProtocolVersion(), originalHandshake.getHost(),
-+ originalHandshake.getPort(), 2);
-
-- if ( BungeeCord.getInstance().config.isIpForward() && user.getSocketAddress() instanceof InetSocketAddress )
-- {
-- String newHost = copiedHandshake.getHost() + "\00" + user.getAddress().getHostString() + "\00" + user.getUUID();
-+ if (BungeeCord.getInstance().config.isIpForward() && user.getSocketAddress() instanceof InetSocketAddress) {
-+ String newHost = copiedHandshake.getHost() + "\00" + user.getAddress().getHostString() + "\00"
-+ + user.getUUID();
-
- LoginResult profile = user.getPendingConnection().getLoginProfile();
-
- // Handle properties.
- LoginResult.Property[] properties = new LoginResult.Property[0];
-
-- if ( profile != null && profile.getProperties() != null && profile.getProperties().length > 0 )
-- {
-+ if (profile != null && profile.getProperties() != null && profile.getProperties().length > 0) {
- properties = profile.getProperties();
- }
-
-- if ( user.getForgeClientHandler().isFmlTokenInHandshake() )
-- {
-+ if (user.getForgeClientHandler().isFmlTokenInHandshake()) {
- // Get the current properties and copy them into a slightly bigger array.
-- LoginResult.Property[] newp = Arrays.copyOf( properties, properties.length + 2 );
-+ LoginResult.Property[] newp = Arrays.copyOf(properties, properties.length + 2);
-
- // Add a new profile property that specifies that this user is a Forge user.
-- newp[newp.length - 2] = new LoginResult.Property( ForgeConstants.FML_LOGIN_PROFILE, "true", null );
-+ newp[newp.length - 2] = new LoginResult.Property(ForgeConstants.FML_LOGIN_PROFILE, "true", null);
-
-- // If we do not perform the replacement, then the IP Forwarding code in Spigot et. al. will try to split on this prematurely.
-- newp[newp.length - 1] = new LoginResult.Property( ForgeConstants.EXTRA_DATA, user.getExtraDataInHandshake().replaceAll( "\0", "\1"), "" );
-+ // If we do not perform the replacement, then the IP Forwarding code in Spigot
-+ // et. al. will try to split on this prematurely.
-+ newp[newp.length - 1] = new LoginResult.Property(ForgeConstants.EXTRA_DATA,
-+ user.getExtraDataInHandshake().replaceAll("\0", "\1"), "");
-
- // All done.
- properties = newp;
-@@ -136,57 +134,60 @@ public class ServerConnector extends PacketHandler
- newHost += "\00" + BungeeCord.getInstance().gson.toJson(properties);
- }
-
-- copiedHandshake.setHost( newHost );
-- } else if ( !user.getExtraDataInHandshake().isEmpty() )
-- {
-+ copiedHandshake.setHost(newHost);
-+ } else if (!user.getExtraDataInHandshake().isEmpty()) {
- // Restore the extra data
-- copiedHandshake.setHost( copiedHandshake.getHost() + user.getExtraDataInHandshake() );
-+ copiedHandshake.setHost(copiedHandshake.getHost() + user.getExtraDataInHandshake());
- }
-
-- channel.write( copiedHandshake );
-+ channel.write(copiedHandshake);
-
-- channel.setProtocol( Protocol.LOGIN );
-- channel.write( new LoginRequest( user.getName() ) );
-+ channel.setProtocol(Protocol.LOGIN);
-+ channel.write(new LoginRequest(user.getName()));
- }
-
- @Override
-- public void disconnected(ChannelWrapper channel) throws Exception
-- {
-- user.getPendingConnects().remove( target );
-+ public void disconnected(ChannelWrapper channel) throws Exception {
-+ user.getPendingConnects().remove(target);
- }
-
- @Override
-- public void handle(PacketWrapper packet) throws Exception
-- {
-- if ( packet.packet == null )
-- {
-- throw new QuietException( "Unexpected packet received during server login process!\n" + BufUtil.dump( packet.buf, 16 ) );
-+ public void handle(final PacketWrapper packet) throws Exception {
-+ if (packet.packet == null) {
-+ // FlameCord - Toggle Dumping packet info
-+ if (FlameCord.getInstance().getFlameCordConfiguration().isLoggerDump()) {
-+ // FlameCord - Change from QuietException to BadPacketException
-+ throw new BadPacketException(
-+ "Unexpected packet received during server connector process!\n" + BufUtil.dump(packet.buf, 16));
-+ } else {
-+ // FlameCord - Change from QuietException to BadPacketException
-+ throw new BadPacketException("Unexpected packet received during connector process!");
-+ }
- }
- }
-
- @Override
-- public void handle(LoginSuccess loginSuccess) throws Exception
-- {
-- Preconditions.checkState( thisState == State.LOGIN_SUCCESS, "Not expecting LOGIN_SUCCESS" );
-- ch.setProtocol( Protocol.GAME );
-+ public void handle(LoginSuccess loginSuccess) throws Exception {
-+ Preconditions.checkState(thisState == State.LOGIN_SUCCESS, "Not expecting LOGIN_SUCCESS");
-+ ch.setProtocol(Protocol.GAME);
- thisState = State.LOGIN;
-
- // Only reset the Forge client when:
- // 1) The user is switching servers (so has a current server)
- // 2) The handshake is complete
- // 3) The user is currently on a modded server (if we are on a vanilla server,
-- // we may be heading for another vanilla server, so we don't need to reset.)
-+ // we may be heading for another vanilla server, so we don't need to reset.)
- //
- // user.getServer() gets the user's CURRENT server, not the one we are trying
- // to connect to.
- //
- // We will reset the connection later if the current server is vanilla, and
-- // we need to switch to a modded connection. However, we always need to reset the
-+ // we need to switch to a modded connection. However, we always need to reset
-+ // the
- // connection when we have a modded server regardless of where we go - doing it
- // here makes sense.
-- if ( user.getServer() != null && user.getForgeClientHandler().isHandshakeComplete()
-- && user.getServer().isForgeServer() )
-- {
-+ if (user.getServer() != null && user.getForgeClientHandler().isHandshakeComplete()
-+ && user.getServer().isForgeServer()) {
- user.getForgeClientHandler().resetHandshake();
- }
-
-@@ -194,197 +195,217 @@ public class ServerConnector extends PacketHandler
- }
-
- @Override
-- public void handle(SetCompression setCompression) throws Exception
-- {
-- ch.setCompressionThreshold( setCompression.getThreshold() );
-+ public void handle(SetCompression setCompression) throws Exception {
-+ ch.setCompressionThreshold(setCompression.getThreshold());
- }
-
- @Override
-- public void handle(Login login) throws Exception
-- {
-- Preconditions.checkState( thisState == State.LOGIN, "Not expecting LOGIN" );
-+ public void handle(Login login) throws Exception {
-+ Preconditions.checkState(thisState == State.LOGIN, "Not expecting LOGIN");
-
-- ServerConnection server = new ServerConnection( ch, target );
-- ServerConnectedEvent event = new ServerConnectedEvent( user, server );
-+ ServerConnection server = new ServerConnection(ch, target);
-+ ServerConnectedEvent event = new ServerConnectedEvent(user, server);
-
- if (server.isForgeServer() && user.isForgeUser()) {
-- ((MinecraftDecoder) server.getCh().getHandle().pipeline().get(PipelineUtils.PACKET_DECODER)).setSupportsForge(true);
-- ((MinecraftDecoder) user.getCh().getHandle().pipeline().get(PipelineUtils.PACKET_DECODER)).setSupportsForge(true);
-+ ((MinecraftDecoder) server.getCh().getHandle().pipeline().get(PipelineUtils.PACKET_DECODER))
-+ .setSupportsForge(true);
-+ ((MinecraftDecoder) user.getCh().getHandle().pipeline().get(PipelineUtils.PACKET_DECODER))
-+ .setSupportsForge(true);
- }
-
-- bungee.getPluginManager().callEvent( event );
-+ bungee.getPluginManager().callEvent(event);
-
-- ch.write( BungeeCord.getInstance().registerChannels( user.getPendingConnection().getVersion() ) );
-+ ch.write(BungeeCord.getInstance().registerChannels(user.getPendingConnection().getVersion()));
- Queue packetQueue = target.getPacketQueue();
-- synchronized ( packetQueue )
-- {
-- while ( !packetQueue.isEmpty() )
-- {
-- ch.write( packetQueue.poll() );
-- }
-+ // FlameCord - Remove the usage of synchronized
-+ // synchronized (packetQueue) {
-+ while (!packetQueue.isEmpty()) {
-+ ch.write(packetQueue.poll());
- }
-+ // }
-
-- for ( PluginMessage message : user.getPendingConnection().getRelayMessages() )
-- {
-- ch.write( message );
-+ for (PluginMessage message : user.getPendingConnection().getRelayMessages()) {
-+ ch.write(message);
- }
-
-- if (!user.isDisableEntityMetadataRewrite() && user.getSettings() != null )
-- {
-- ch.write( user.getSettings() );
-+ if (!user.isDisableEntityMetadataRewrite() && user.getSettings() != null) {
-+ ch.write(user.getSettings());
- }
-
-- if ( user.getForgeClientHandler().getClientModList() == null && !user.getForgeClientHandler().isHandshakeComplete() ) // Vanilla
-+ if (user.getForgeClientHandler().getClientModList() == null
-+ && !user.getForgeClientHandler().isHandshakeComplete()) // Vanilla
- {
- user.getForgeClientHandler().setHandshakeComplete();
- }
-
-- if ( user.getServer() == null || !( login.getDimension() instanceof Integer ) )
-- {
-+ if (user.getServer() == null || !(login.getDimension() instanceof Integer)) {
- // Once again, first connection
-- user.setClientEntityId( login.getEntityId() );
-- user.setServerEntityId( login.getEntityId() );
-+ user.setClientEntityId(login.getEntityId());
-+ user.setServerEntityId(login.getEntityId());
-
- // Set tab list size, TODO: what shall we do about packet mutability
-- Login modLogin = new Login( login.getEntityId(), login.isHardcore(), login.getGameMode(), login.getPreviousGameMode(), login.getWorldNames(), login.getDimensions(), login.getDimension(), login.getWorldName(), login.getSeed(), login.getDifficulty(),
-- (byte) user.getPendingConnection().getListener().getTabListSize(), login.getLevelType(), login.getViewDistance(), login.isReducedDebugInfo(), login.isNormalRespawn(), login.isDebug(), login.isFlat() );
-+ Login modLogin = new Login(login.getEntityId(), login.isHardcore(), login.getGameMode(),
-+ login.getPreviousGameMode(), login.getWorldNames(), login.getDimensions(), login.getDimension(),
-+ login.getWorldName(), login.getSeed(), login.getDifficulty(),
-+ (byte) user.getPendingConnection().getListener().getTabListSize(), login.getLevelType(),
-+ login.getViewDistance(), login.isReducedDebugInfo(), login.isNormalRespawn(), login.isDebug(),
-+ login.isFlat());
-
-- user.unsafe().sendPacket( modLogin );
-+ user.unsafe().sendPacket(modLogin);
-
-- if ( user.getServer() != null )
-- {
-- user.getServer().setObsolete( true );
-+ if (user.getServer() != null) {
-+ user.getServer().setObsolete(true);
- user.getTabListHandler().onServerChange();
-
- user.getServerSentScoreboard().clear();
-
-- for ( UUID bossbar : user.getSentBossBars() )
-- {
-+ for (UUID bossbar : user.getSentBossBars()) {
- // Send remove bossbar packet
-- user.unsafe().sendPacket( new net.md_5.bungee.protocol.packet.BossBar( bossbar, 1 ) );
-+ user.unsafe().sendPacket(new net.md_5.bungee.protocol.packet.BossBar(bossbar, 1));
- }
- user.getSentBossBars().clear();
-
-- user.unsafe().sendPacket( new Respawn( login.getDimension(), login.getWorldName(), login.getSeed(), login.getDifficulty(), login.getGameMode(), login.getPreviousGameMode(), login.getLevelType(), login.isDebug(), login.isFlat(), false ) );
-- user.getServer().disconnect( "Quitting" );
-- } else
-- {
-+ user.unsafe()
-+ .sendPacket(new Respawn(login.getDimension(), login.getWorldName(), login.getSeed(),
-+ login.getDifficulty(), login.getGameMode(), login.getPreviousGameMode(),
-+ login.getLevelType(), login.isDebug(), login.isFlat(), false));
-+ user.getServer().disconnect("Quitting");
-+ } else {
- // Travertine start
- String brandString = bungee.getName() + " (" + bungee.getVersion() + ")";
-
-- if ( ProtocolConstants.isBeforeOrEq( user.getPendingConnection().getVersion(), ProtocolConstants.MINECRAFT_1_7_6 ) )
-- {
-- user.unsafe().sendPacket( new PluginMessage( "MC|Brand", brandString.getBytes( StandardCharsets.UTF_8 ), handshakeHandler.isServerForge() ) );
-- } else
-- {
-+ if (ProtocolConstants.isBeforeOrEq(user.getPendingConnection().getVersion(),
-+ ProtocolConstants.MINECRAFT_1_7_6)) {
-+ user.unsafe().sendPacket(new PluginMessage("MC|Brand", brandString.getBytes(StandardCharsets.UTF_8),
-+ handshakeHandler.isServerForge()));
-+ } else {
- ByteBuf brand = ByteBufAllocator.DEFAULT.heapBuffer();
- DefinedPacket.writeString(brandString, brand);
-- user.unsafe().sendPacket( new PluginMessage( user.getPendingConnection().getVersion() >= ProtocolConstants.MINECRAFT_1_13 ? "minecraft:brand" : "MC|Brand", brand, handshakeHandler.isServerForge() ) );
-+ user.unsafe()
-+ .sendPacket(new PluginMessage(
-+ user.getPendingConnection().getVersion() >= ProtocolConstants.MINECRAFT_1_13
-+ ? "minecraft:brand"
-+ : "MC|Brand",
-+ brand, handshakeHandler.isServerForge()));
- brand.release();
- }
- // Travertine end
- }
-
-- user.setDimension( login.getDimension() );
-- } else
-- {
-- user.getServer().setObsolete( true );
-+ user.setDimension(login.getDimension());
-+ } else {
-+ user.getServer().setObsolete(true);
- user.getTabListHandler().onServerChange();
-
- Scoreboard serverScoreboard = user.getServerSentScoreboard();
-- if ( !user.isDisableEntityMetadataRewrite() ) { // Waterfall
-- for ( Objective objective : serverScoreboard.getObjectives() )
-- {
-- user.unsafe().sendPacket( new ScoreboardObjective( objective.getName(), objective.getValue(), objective.getType() == null ? null : ScoreboardObjective.HealthDisplay.fromString(objective.getType()), (byte) 1 ) ); // Travertine - 1.7
-- }
-- for ( Score score : serverScoreboard.getScores() )
-- {
-- user.unsafe().sendPacket( new ScoreboardScore( score.getItemName(), (byte) 1, score.getScoreName(), score.getValue() ) );
-- }
-- for ( Team team : serverScoreboard.getTeams() )
-- {
-- user.unsafe().sendPacket( new net.md_5.bungee.protocol.packet.Team( team.getName() ) );
-- }
-+ if (!user.isDisableEntityMetadataRewrite()) { // Waterfall
-+ for (Objective objective : serverScoreboard.getObjectives()) {
-+ user.unsafe()
-+ .sendPacket(new ScoreboardObjective(objective.getName(), objective.getValue(),
-+ objective.getType() == null ? null
-+ : ScoreboardObjective.HealthDisplay.fromString(objective.getType()),
-+ (byte) 1)); // Travertine - 1.7
-+ }
-+ for (Score score : serverScoreboard.getScores()) {
-+ user.unsafe().sendPacket(
-+ new ScoreboardScore(score.getItemName(), (byte) 1, score.getScoreName(), score.getValue()));
-+ }
-+ for (Team team : serverScoreboard.getTeams()) {
-+ user.unsafe().sendPacket(new net.md_5.bungee.protocol.packet.Team(team.getName()));
-+ }
- } // Waterfall
- serverScoreboard.clear();
-
-- for ( UUID bossbar : user.getSentBossBars() )
-- {
-+ for (UUID bossbar : user.getSentBossBars()) {
- // Send remove bossbar packet
-- user.unsafe().sendPacket( new net.md_5.bungee.protocol.packet.BossBar( bossbar, 1 ) );
-+ user.unsafe().sendPacket(new net.md_5.bungee.protocol.packet.BossBar(bossbar, 1));
- }
- user.getSentBossBars().clear();
-
- // Update debug info from login packet
-- user.unsafe().sendPacket( new EntityStatus( user.getClientEntityId(), login.isReducedDebugInfo() ? EntityStatus.DEBUG_INFO_REDUCED : EntityStatus.DEBUG_INFO_NORMAL ) );
-+ user.unsafe().sendPacket(new EntityStatus(user.getClientEntityId(),
-+ login.isReducedDebugInfo() ? EntityStatus.DEBUG_INFO_REDUCED : EntityStatus.DEBUG_INFO_NORMAL));
- // And immediate respawn
-- if ( user.getPendingConnection().getVersion() >= ProtocolConstants.MINECRAFT_1_15 )
-- {
-- user.unsafe().sendPacket( new GameState( GameState.IMMEDIATE_RESPAWN, login.isNormalRespawn() ? 0 : 1 ) );
-+ if (user.getPendingConnection().getVersion() >= ProtocolConstants.MINECRAFT_1_15) {
-+ user.unsafe().sendPacket(new GameState(GameState.IMMEDIATE_RESPAWN, login.isNormalRespawn() ? 0 : 1));
- }
-
-- user.setDimensionChange( true );
-- if ( !user.isDisableEntityMetadataRewrite() && login.getDimension() == user.getDimension() ) // Waterfall - defer
-+ user.setDimensionChange(true);
-+ if (!user.isDisableEntityMetadataRewrite() && login.getDimension() == user.getDimension()) // Waterfall -
-+ // defer
- {
-- user.unsafe().sendPacket( new Respawn( (Integer) login.getDimension() >= 0 ? -1 : 0, login.getWorldName(), login.getSeed(), login.getDifficulty(), login.getGameMode(), login.getPreviousGameMode(), login.getLevelType(), login.isDebug(), login.isFlat(), false ) );
-+ user.unsafe().sendPacket(new Respawn((Integer) login.getDimension() >= 0 ? -1 : 0, login.getWorldName(),
-+ login.getSeed(), login.getDifficulty(), login.getGameMode(), login.getPreviousGameMode(),
-+ login.getLevelType(), login.isDebug(), login.isFlat(), false));
- }
-
-- user.setServerEntityId( login.getEntityId() );
-+ user.setServerEntityId(login.getEntityId());
-
- // Waterfall start
-- if ( user.isDisableEntityMetadataRewrite() ) {
-+ if (user.isDisableEntityMetadataRewrite()) {
- // Ensure that we maintain consistency
-- user.setClientEntityId( login.getEntityId() );
-+ user.setClientEntityId(login.getEntityId());
-
- // Only send if we are not in the same dimension
-- if ( login.getDimension() != user.getDimension() ) // Waterfall - defer
-+ if (login.getDimension() != user.getDimension()) // Waterfall - defer
- {
-- user.unsafe().sendPacket( new Respawn( (Integer) user.getDimension() >= 0 ? -1 : 0, login.getWorldName(), login.getSeed(), login.getDifficulty(), login.getGameMode(), login.getPreviousGameMode(), login.getLevelType(), login.isDebug(), login.isFlat(), false ) );
-+ user.unsafe().sendPacket(new Respawn((Integer) user.getDimension() >= 0 ? -1 : 0,
-+ login.getWorldName(), login.getSeed(), login.getDifficulty(), login.getGameMode(),
-+ login.getPreviousGameMode(), login.getLevelType(), login.isDebug(), login.isFlat(), false));
- }
-
-- Login modLogin = new Login( login.getEntityId(), login.isHardcore(), login.getGameMode(), login.getPreviousGameMode(), login.getWorldNames(), login.getDimensions(), login.getDimension(), login.getWorldName(), login.getSeed(), login.getDifficulty(),
-- (byte) user.getPendingConnection().getListener().getTabListSize(), login.getLevelType(), login.getViewDistance(), login.isReducedDebugInfo(), login.isNormalRespawn(), login.isDebug(), login.isFlat() );
-+ Login modLogin = new Login(login.getEntityId(), login.isHardcore(), login.getGameMode(),
-+ login.getPreviousGameMode(), login.getWorldNames(), login.getDimensions(), login.getDimension(),
-+ login.getWorldName(), login.getSeed(), login.getDifficulty(),
-+ (byte) user.getPendingConnection().getListener().getTabListSize(), login.getLevelType(),
-+ login.getViewDistance(), login.isReducedDebugInfo(), login.isNormalRespawn(), login.isDebug(),
-+ login.isFlat());
- user.unsafe().sendPacket(modLogin);
-
- // Only send if we're in the same dimension
-- if ( login.getDimension() == user.getDimension() ) // Waterfall - defer
-+ if (login.getDimension() == user.getDimension()) // Waterfall - defer
- {
-- user.unsafe().sendPacket( new Respawn( (Integer) login.getDimension() >= 0 ? -1 : 0, login.getWorldName(), login.getSeed(), login.getDifficulty(), login.getGameMode(), login.getPreviousGameMode(), login.getLevelType(), login.isDebug(), login.isFlat(), false ) );
-+ user.unsafe().sendPacket(new Respawn((Integer) login.getDimension() >= 0 ? -1 : 0,
-+ login.getWorldName(), login.getSeed(), login.getDifficulty(), login.getGameMode(),
-+ login.getPreviousGameMode(), login.getLevelType(), login.isDebug(), login.isFlat(), false));
- }
- }
- // Waterfall end
-- user.unsafe().sendPacket( new Respawn( login.getDimension(), login.getWorldName(), login.getSeed(), login.getDifficulty(), login.getGameMode(), login.getPreviousGameMode(), login.getLevelType(), login.isDebug(), login.isFlat(), false ) );
-- if ( user.getPendingConnection().getVersion() >= ProtocolConstants.MINECRAFT_1_14 )
-- {
-- user.unsafe().sendPacket( new ViewDistance( login.getViewDistance() ) );
-+ user.unsafe()
-+ .sendPacket(new Respawn(login.getDimension(), login.getWorldName(), login.getSeed(),
-+ login.getDifficulty(), login.getGameMode(), login.getPreviousGameMode(),
-+ login.getLevelType(), login.isDebug(), login.isFlat(), false));
-+ if (user.getPendingConnection().getVersion() >= ProtocolConstants.MINECRAFT_1_14) {
-+ user.unsafe().sendPacket(new ViewDistance(login.getViewDistance()));
- }
-- user.setDimension( login.getDimension() );
-+ user.setDimension(login.getDimension());
-
- // Remove from old servers
-- user.getServer().disconnect( "Quitting" );
-+ // FlameCord - Remove "Quitting" reason
-+ user.getServer().disconnect();
- }
-
- // TODO: Fix this?
-- if ( !user.isActive() )
-- {
-- server.disconnect( "Quitting" );
-+ if (!user.isActive()) {
-+ // FlameCord - Remove "Quitting" reason
-+ server.disconnect();
- // Silly server admins see stack trace and die
-- bungee.getLogger().warning( "No client connected for pending server!" );
-+ bungee.getLogger().warning("No client connected for pending server!");
- return;
- }
-
- // Add to new server
- // TODO: Move this to the connected() method of DownstreamBridge
-- target.addPlayer( user );
-- user.getPendingConnects().remove( target );
-- user.setServerJoinQueue( null );
-- user.setDimensionChange( false );
-+ target.addPlayer(user);
-+ user.getPendingConnects().remove(target);
-+ user.setServerJoinQueue(null);
-+ user.setDimensionChange(false);
-
-- ServerInfo from = ( user.getServer() == null ) ? null : user.getServer().getInfo();
-- user.setServer( server );
-- ch.getHandle().pipeline().get( HandlerBoss.class ).setHandler( new DownstreamBridge( bungee, user, server ) );
-+ ServerInfo from = (user.getServer() == null) ? null : user.getServer().getInfo();
-+ user.setServer(server);
-+ ch.getHandle().pipeline().get(HandlerBoss.class).setHandler(new DownstreamBridge(bungee, user, server));
-
-- bungee.getPluginManager().callEvent( new ServerSwitchEvent( user, from ) );
-+ bungee.getPluginManager().callEvent(new ServerSwitchEvent(user, from));
-
- thisState = State.FINISHED;
-
-@@ -392,59 +413,49 @@ public class ServerConnector extends PacketHandler
- }
-
- @Override
-- public void handle(EncryptionRequest encryptionRequest) throws Exception
-- {
-- throw new QuietException( "Server is online mode!" );
-+ public void handle(EncryptionRequest encryptionRequest) throws Exception {
-+ throw new QuietException("Server is online mode!");
- }
-
- @Override
-- public void handle(Kick kick) throws Exception
-- {
-- ServerInfo def = user.updateAndGetNextServer( target );
-- ServerKickEvent event = new ServerKickEvent( user, target, ComponentSerializer.parse( kick.getMessage() ), def, ServerKickEvent.State.CONNECTING, ServerKickEvent.Cause.SERVER ); // Waterfall
-- if ( event.getKickReason().toLowerCase( Locale.ROOT ).contains( "outdated" ) && def != null )
-- {
-+ public void handle(Kick kick) throws Exception {
-+ ServerInfo def = user.updateAndGetNextServer(target);
-+ ServerKickEvent event = new ServerKickEvent(user, target, ComponentSerializer.parse(kick.getMessage()), def,
-+ ServerKickEvent.State.CONNECTING, ServerKickEvent.Cause.SERVER); // Waterfall
-+ if (event.getKickReason().toLowerCase(Locale.ROOT).contains("outdated") && def != null) {
- // Pre cancel the event if we are going to try another server
-- event.setCancelled( true );
-+ event.setCancelled(true);
- }
-- bungee.getPluginManager().callEvent( event );
-- if ( event.isCancelled() && event.getCancelServer() != null )
-- {
-+ bungee.getPluginManager().callEvent(event);
-+ if (event.isCancelled() && event.getCancelServer() != null) {
- obsolete = true;
-- user.connect( event.getCancelServer(), ServerConnectEvent.Reason.KICK_REDIRECT );
-+ user.connect(event.getCancelServer(), ServerConnectEvent.Reason.KICK_REDIRECT);
- throw CancelSendSignal.INSTANCE;
- }
-
-- String message = bungee.getTranslation( "connect_kick", target.getName(), event.getKickReason() );
-- if ( user.isDimensionChange() )
-- {
-- user.disconnect( message );
-- } else
-- {
-- user.sendMessage( message );
-+ String message = bungee.getTranslation("connect_kick", target.getName(), event.getKickReason());
-+ if (user.isDimensionChange()) {
-+ user.disconnect(message);
-+ } else {
-+ user.sendMessage(message);
- }
-
- throw CancelSendSignal.INSTANCE;
- }
-
- @Override
-- public void handle(PluginMessage pluginMessage) throws Exception
-- {
-- if ( BungeeCord.getInstance().config.isForgeSupport() )
-- {
-- if ( pluginMessage.getTag().equals( ForgeConstants.FML_REGISTER ) )
-- {
-- Set channels = ForgeUtils.readRegisteredChannels( pluginMessage );
-+ public void handle(PluginMessage pluginMessage) throws Exception {
-+ if (BungeeCord.getInstance().config.isForgeSupport()) {
-+ if (pluginMessage.getTag().equals(ForgeConstants.FML_REGISTER)) {
-+ Set channels = ForgeUtils.readRegisteredChannels(pluginMessage);
- boolean isForgeServer = false;
-- for ( String channel : channels )
-- {
-- if ( channel.equals( ForgeConstants.FML_HANDSHAKE_TAG ) )
-- {
-+ for (String channel : channels) {
-+ if (channel.equals(ForgeConstants.FML_HANDSHAKE_TAG)) {
- // If we have a completed handshake and we have been asked to register a FML|HS
-- // packet, let's send the reset packet now. Then, we can continue the message sending.
-+ // packet, let's send the reset packet now. Then, we can continue the message
-+ // sending.
- // The handshake will not be complete if we reset this earlier.
-- if ( user.getServer() != null && user.getForgeClientHandler().isHandshakeComplete() )
-- {
-+ if (user.getServer() != null && user.getForgeClientHandler().isHandshakeComplete()) {
- user.getForgeClientHandler().resetHandshake();
- }
-
-@@ -453,21 +464,19 @@ public class ServerConnector extends PacketHandler
- }
- }
-
-- if ( isForgeServer && !this.handshakeHandler.isServerForge() )
-- {
-+ if (isForgeServer && !this.handshakeHandler.isServerForge()) {
- // We now set the server-side handshake handler for the client to this.
- handshakeHandler.setServerAsForgeServer();
-- user.setForgeServerHandler( handshakeHandler );
-+ user.setForgeServerHandler(handshakeHandler);
- }
- }
-
-- if ( pluginMessage.getTag().equals( ForgeConstants.FML_HANDSHAKE_TAG ) || pluginMessage.getTag().equals( ForgeConstants.FORGE_REGISTER ) )
-- {
-- this.handshakeHandler.handle( pluginMessage );
-+ if (pluginMessage.getTag().equals(ForgeConstants.FML_HANDSHAKE_TAG)
-+ || pluginMessage.getTag().equals(ForgeConstants.FORGE_REGISTER)) {
-+ this.handshakeHandler.handle(pluginMessage);
-
- // Travertine start
-- if ( user.getForgeClientHandler().checkUserOutdated() )
-- {
-+ if (user.getForgeClientHandler().checkUserOutdated()) {
- ch.close();
- user.getPendingConnects().remove(target);
- }
-@@ -478,14 +487,14 @@ public class ServerConnector extends PacketHandler
- }
- }
-
-- // We have to forward these to the user, especially with Forge as stuff might break
-+ // We have to forward these to the user, especially with Forge as stuff might
-+ // break
- // This includes any REGISTER messages we intercepted earlier.
-- user.unsafe().sendPacket( pluginMessage );
-+ user.unsafe().sendPacket(pluginMessage);
- }
-
- @Override
-- public String toString()
-- {
-+ public String toString() {
- return "[" + user.getName() + "|" + user.getAddress() + "] <-> ServerConnector [" + target.getName() + "]";
- }
- }
-diff --git a/proxy/src/main/java/net/md_5/bungee/UserConnection.java b/proxy/src/main/java/net/md_5/bungee/UserConnection.java
-index 8c2a743a..f0015076 100644
---- a/proxy/src/main/java/net/md_5/bungee/UserConnection.java
-+++ b/proxy/src/main/java/net/md_5/bungee/UserConnection.java
-@@ -1,16 +1,5 @@
- package net.md_5.bungee;
-
--import com.google.common.base.Preconditions;
--import com.google.common.collect.HashMultimap;
--import com.google.common.collect.ImmutableMap;
--import com.google.common.collect.Multimap;
--import io.netty.bootstrap.Bootstrap;
--import io.netty.channel.Channel;
--import io.netty.channel.ChannelFuture;
--import io.netty.channel.ChannelFutureListener;
--import io.netty.channel.ChannelInitializer;
--import io.netty.channel.ChannelOption;
--import io.netty.util.internal.PlatformDependent;
- import java.net.InetSocketAddress;
- import java.net.SocketAddress;
- import java.util.Collection;
-@@ -23,6 +12,19 @@ import java.util.Objects;
- import java.util.Queue;
- import java.util.UUID;
- import java.util.logging.Level;
-+
-+import com.google.common.base.Preconditions;
-+import com.google.common.collect.HashMultimap;
-+import com.google.common.collect.ImmutableMap;
-+import com.google.common.collect.Multimap;
-+
-+import io.netty.bootstrap.Bootstrap;
-+import io.netty.channel.Channel;
-+import io.netty.channel.ChannelFuture;
-+import io.netty.channel.ChannelFutureListener;
-+import io.netty.channel.ChannelInitializer;
-+import io.netty.channel.ChannelOption;
-+import io.netty.util.internal.PlatformDependent;
- import lombok.Getter;
- import lombok.NonNull;
- import lombok.RequiredArgsConstructor;
-@@ -35,6 +37,7 @@ import net.md_5.bungee.api.SkinConfiguration;
- import net.md_5.bungee.api.Title;
- import net.md_5.bungee.api.chat.BaseComponent;
- import net.md_5.bungee.api.chat.TextComponent;
-+import net.md_5.bungee.api.config.ListenerInfo;
- import net.md_5.bungee.api.config.ServerInfo;
- import net.md_5.bungee.api.connection.ProxiedPlayer;
- import net.md_5.bungee.api.event.PermissionCheckEvent;
-@@ -65,12 +68,12 @@ import net.md_5.bungee.tab.ServerUnique;
- import net.md_5.bungee.tab.TabList;
- import net.md_5.bungee.util.CaseInsensitiveSet;
- import net.md_5.bungee.util.ChatComponentTransformer;
-+import net.md_5.bungee.util.QuietException;
-
- @RequiredArgsConstructor
--public final class UserConnection implements ProxiedPlayer
--{
-+public final class UserConnection implements ProxiedPlayer {
-
-- /*========================================================================*/
-+ /* ======================================================================== */
- @NonNull
- private final ProxyServer bungee;
- @NonNull
-@@ -81,7 +84,7 @@ public final class UserConnection implements ProxiedPlayer
- private final String name;
- @Getter
- private final InitialHandler pendingConnection;
-- /*========================================================================*/
-+ /* ======================================================================== */
- @Getter
- @Setter
- private ServerConnection server;
-@@ -93,7 +96,7 @@ public final class UserConnection implements ProxiedPlayer
- private boolean dimensionChange = true;
- @Getter
- private final Collection pendingConnects = new HashSet<>();
-- /*========================================================================*/
-+ /* ======================================================================== */
- @Getter
- @Setter
- private int ping = 100;
-@@ -110,10 +113,10 @@ public final class UserConnection implements ProxiedPlayer
- // Used for trying multiple servers in order
- @Setter
- private Queue serverJoinQueue;
-- /*========================================================================*/
-+ /* ======================================================================== */
- private final Collection groups = new CaseInsensitiveSet();
- private final Collection permissions = new CaseInsensitiveSet();
-- /*========================================================================*/
-+ /* ======================================================================== */
- @Getter
- @Setter
- private int clientEntityId;
-@@ -130,122 +133,104 @@ public final class UserConnection implements ProxiedPlayer
- @Getter
- private final Multimap potions = HashMultimap.create();
- // Waterfall end
-- /*========================================================================*/
-+ /* ======================================================================== */
- @Getter
- private String displayName;
- @Getter
- private EntityMap entityRewrite;
- private Locale locale;
-- /*========================================================================*/
-+ /* ======================================================================== */
- @Getter
- @Setter
- private ForgeClientHandler forgeClientHandler;
- @Getter
- @Setter
- private ForgeServerHandler forgeServerHandler;
-- /*========================================================================*/
-- private final Unsafe unsafe = new Unsafe()
-- {
-+ /* ======================================================================== */
-+ private final Unsafe unsafe = new Unsafe() {
- @Override
-- public void sendPacket(DefinedPacket packet)
-- {
-- ch.write( packet );
-+ public void sendPacket(DefinedPacket packet) {
-+ ch.write(packet);
- }
- };
-
-- public void init()
-- {
-- this.entityRewrite = EntityMap.getEntityMap( getPendingConnection().getVersion() );
-+ public void init() {
-+ this.entityRewrite = EntityMap.getEntityMap(getPendingConnection().getVersion());
-
- this.displayName = name;
-
-- tabListHandler = new ServerUnique( this );
-+ tabListHandler = new ServerUnique(this);
-
-- Collection g = bungee.getConfigurationAdapter().getGroups( name );
-- g.addAll( bungee.getConfigurationAdapter().getGroups( getUniqueId().toString() ) );
-- for ( String s : g )
-- {
-- addGroups( s );
-+ Collection g = bungee.getConfigurationAdapter().getGroups(name);
-+ g.addAll(bungee.getConfigurationAdapter().getGroups(getUniqueId().toString()));
-+ for (String s : g) {
-+ addGroups(s);
- }
-
-- forgeClientHandler = new ForgeClientHandler( this );
-+ forgeClientHandler = new ForgeClientHandler(this);
-
- // No-config FML handshake marker.
- // Set whether the connection has a 1.8 FML marker in the handshake.
-- if (this.getPendingConnection().getExtraDataInHandshake().contains( ForgeConstants.FML_HANDSHAKE_TOKEN ))
-- {
-- forgeClientHandler.setFmlTokenInHandshake( true );
-+ if (this.getPendingConnection().getExtraDataInHandshake().contains(ForgeConstants.FML_HANDSHAKE_TOKEN)) {
-+ forgeClientHandler.setFmlTokenInHandshake(true);
- }
- }
-
-- public void sendPacket(PacketWrapper packet)
-- {
-- ch.write( packet );
-+ public void sendPacket(PacketWrapper packet) {
-+ ch.write(packet);
- }
-
- @Deprecated
-- public boolean isActive()
-- {
-+ public boolean isActive() {
- return !ch.isClosed();
- }
-
- @Override
-- public void setDisplayName(String name)
-- {
-- Preconditions.checkNotNull( name, "displayName" );
-- Preconditions.checkArgument( name.length() <= 16, "Display name cannot be longer than 16 characters" ); // Travertine
-+ public void setDisplayName(String name) {
-+ Preconditions.checkNotNull(name, "displayName");
-+ Preconditions.checkArgument(name.length() <= 16, "Display name cannot be longer than 16 characters"); // Travertine
- displayName = name;
- }
-
- @Override
-- public void connect(ServerInfo target)
-- {
-- connect( target, null, ServerConnectEvent.Reason.PLUGIN );
-+ public void connect(ServerInfo target) {
-+ connect(target, null, ServerConnectEvent.Reason.PLUGIN);
- }
-
- @Override
-- public void connect(ServerInfo target, ServerConnectEvent.Reason reason)
-- {
-- connect( target, null, false, reason );
-+ public void connect(ServerInfo target, ServerConnectEvent.Reason reason) {
-+ connect(target, null, false, reason);
- }
-
- @Override
-- public void connect(ServerInfo target, Callback callback)
-- {
-- connect( target, callback, false, ServerConnectEvent.Reason.PLUGIN );
-+ public void connect(ServerInfo target, Callback callback) {
-+ connect(target, callback, false, ServerConnectEvent.Reason.PLUGIN);
- }
-
- @Override
-- public void connect(ServerInfo target, Callback callback, ServerConnectEvent.Reason reason)
-- {
-- connect( target, callback, false, reason );
-+ public void connect(ServerInfo target, Callback callback, ServerConnectEvent.Reason reason) {
-+ connect(target, callback, false, reason);
- }
-
- @Deprecated
-- public void connectNow(ServerInfo target)
-- {
-- connectNow( target, ServerConnectEvent.Reason.UNKNOWN );
-+ public void connectNow(ServerInfo target) {
-+ connectNow(target, ServerConnectEvent.Reason.UNKNOWN);
- }
-
-- public void connectNow(ServerInfo target, ServerConnectEvent.Reason reason)
-- {
-+ public void connectNow(ServerInfo target, ServerConnectEvent.Reason reason) {
- dimensionChange = true;
-- connect( target, reason );
-+ connect(target, reason);
- }
-
-- public ServerInfo updateAndGetNextServer(ServerInfo currentTarget)
-- {
-- if ( serverJoinQueue == null )
-- {
-- serverJoinQueue = new LinkedList<>( getPendingConnection().getListener().getServerPriority() );
-+ public ServerInfo updateAndGetNextServer(ServerInfo currentTarget) {
-+ if (serverJoinQueue == null) {
-+ serverJoinQueue = new LinkedList<>(getPendingConnection().getListener().getServerPriority());
- }
-
- ServerInfo next = null;
-- while ( !serverJoinQueue.isEmpty() )
-- {
-- ServerInfo candidate = ProxyServer.getInstance().getServerInfo( serverJoinQueue.remove() );
-- if ( !Objects.equals( currentTarget, candidate ) )
-- {
-+ while (!serverJoinQueue.isEmpty()) {
-+ ServerInfo candidate = ProxyServer.getInstance().getServerInfo(serverJoinQueue.remove());
-+ if (!Objects.equals(currentTarget, candidate)) {
- next = candidate;
- break;
- }
-@@ -254,389 +239,346 @@ public final class UserConnection implements ProxiedPlayer
- return next;
- }
-
-- public void connect(ServerInfo info, final Callback callback, final boolean retry)
-- {
-- connect( info, callback, retry, ServerConnectEvent.Reason.PLUGIN );
-+ public void connect(ServerInfo info, final Callback callback, final boolean retry) {
-+ connect(info, callback, retry, ServerConnectEvent.Reason.PLUGIN);
- }
-
-- public void connect(ServerInfo info, final Callback callback, final boolean retry, ServerConnectEvent.Reason reason)
-- {
-+ public void connect(ServerInfo info, final Callback callback, final boolean retry,
-+ ServerConnectEvent.Reason reason) {
- // Waterfall start
- connect(info, callback, retry, reason, bungee.getConfig().getServerConnectTimeout());
- }
-+
- public void connect(ServerInfo info, final Callback callback, final boolean retry, int timeout) {
- connect(info, callback, retry, ServerConnectEvent.Reason.PLUGIN, timeout);
- }
-
-- public void connect(ServerInfo info, final Callback callback, final boolean retry, ServerConnectEvent.Reason reason, final int timeout)
-- {
-+ public void connect(ServerInfo info, final Callback callback, final boolean retry,
-+ ServerConnectEvent.Reason reason, final int timeout) {
- // Waterfall end
-- Preconditions.checkNotNull( info, "info" );
-+ Preconditions.checkNotNull(info, "info");
-
-- ServerConnectRequest.Builder builder = ServerConnectRequest.builder().retry( retry ).reason( reason ).target( info );
-+ ServerConnectRequest.Builder builder = ServerConnectRequest.builder().retry(retry).reason(reason).target(info);
- builder.connectTimeout(timeout); // Waterfall
-- if ( callback != null )
-- {
-- // Convert the Callback to be compatible with Callback from ServerConnectRequest.
-- builder.callback( new Callback()
-- {
-+ if (callback != null) {
-+ // Convert the Callback to be compatible with Callback from
-+ // ServerConnectRequest.
-+ builder.callback(new Callback() {
- @Override
-- public void done(ServerConnectRequest.Result result, Throwable error)
-- {
-- callback.done( ( result == ServerConnectRequest.Result.SUCCESS ) ? Boolean.TRUE : Boolean.FALSE, error );
-+ public void done(ServerConnectRequest.Result result, Throwable error) {
-+ callback.done((result == ServerConnectRequest.Result.SUCCESS) ? Boolean.TRUE : Boolean.FALSE,
-+ error);
- }
-- } );
-+ });
- }
-
-- connect( builder.build() );
-+ connect(builder.build());
- }
-
- @Override
-- public void connect(final ServerConnectRequest request)
-- {
-- Preconditions.checkNotNull( request, "request" );
-+ public void connect(final ServerConnectRequest request) {
-+ Preconditions.checkNotNull(request, "request");
-
- final Callback callback = request.getCallback();
-- ServerConnectEvent event = new ServerConnectEvent( this, request.getTarget(), request.getReason(), request );
-- if ( bungee.getPluginManager().callEvent( event ).isCancelled() )
-- {
-- if ( callback != null )
-- {
-- callback.done( ServerConnectRequest.Result.EVENT_CANCEL, null );
-+ ServerConnectEvent event = new ServerConnectEvent(this, request.getTarget(), request.getReason(), request);
-+ if (bungee.getPluginManager().callEvent(event).isCancelled()) {
-+ if (callback != null) {
-+ callback.done(ServerConnectRequest.Result.EVENT_CANCEL, null);
- }
-
-- if ( getServer() == null && !ch.isClosing() )
-- {
-- throw new IllegalStateException( "Cancelled ServerConnectEvent with no server or disconnect." );
-+ if (getServer() == null && !ch.isClosing()) {
-+ // FlameCord - Change IllegalStateException to QuietException
-+ // throw new IllegalStateException("Cancelled ServerConnectEvent with no server
-+ // or disconnect.");
-+ throw new QuietException("A plugin cancelled ServerConnectEvent with no server or disconnect.");
- }
- return;
- }
-
- final BungeeServerInfo target = (BungeeServerInfo) event.getTarget(); // Update in case the event changed target
-
-- if ( getServer() != null && Objects.equals( getServer().getInfo(), target ) )
-- {
-- if ( callback != null )
-- {
-- callback.done( ServerConnectRequest.Result.ALREADY_CONNECTED, null );
-+ if (getServer() != null && Objects.equals(getServer().getInfo(), target)) {
-+ if (callback != null) {
-+ callback.done(ServerConnectRequest.Result.ALREADY_CONNECTED, null);
- }
-
-- sendMessage( bungee.getTranslation( "already_connected" ) );
-+ sendMessage(bungee.getTranslation("already_connected"));
- return;
- }
-- if ( pendingConnects.contains( target ) )
-- {
-- if ( callback != null )
-- {
-- callback.done( ServerConnectRequest.Result.ALREADY_CONNECTING, null );
-+ if (pendingConnects.contains(target)) {
-+ if (callback != null) {
-+ callback.done(ServerConnectRequest.Result.ALREADY_CONNECTING, null);
- }
-
-- sendMessage( bungee.getTranslation( "already_connecting" ) );
-+ sendMessage(bungee.getTranslation("already_connecting"));
- return;
- }
-
-- pendingConnects.add( target );
-+ pendingConnects.add(target);
-
-- ChannelInitializer initializer = new ChannelInitializer()
-- {
-+ ChannelInitializer initializer = new ChannelInitializer() {
- @Override
-- protected void initChannel(Channel ch) throws Exception
-- {
-- PipelineUtils.BASE.initChannel( ch );
-- ch.pipeline().addAfter( PipelineUtils.FRAME_DECODER, PipelineUtils.PACKET_DECODER, new MinecraftDecoder( Protocol.HANDSHAKE, false, getPendingConnection().getVersion() ) );
-- ch.pipeline().addAfter( PipelineUtils.FRAME_PREPENDER, PipelineUtils.PACKET_ENCODER, new MinecraftEncoder( Protocol.HANDSHAKE, false, getPendingConnection().getVersion() ) );
-- ch.pipeline().get( HandlerBoss.class ).setHandler( new ServerConnector( bungee, UserConnection.this, target ) );
-+ protected void initChannel(Channel ch) throws Exception {
-+ PipelineUtils.BASE.initChannel(ch);
-+ ch.pipeline().addAfter(PipelineUtils.FRAME_DECODER, PipelineUtils.PACKET_DECODER,
-+ new MinecraftDecoder(Protocol.HANDSHAKE, false, getPendingConnection().getVersion()));
-+ ch.pipeline().addAfter(PipelineUtils.FRAME_PREPENDER, PipelineUtils.PACKET_ENCODER,
-+ new MinecraftEncoder(Protocol.HANDSHAKE, false, getPendingConnection().getVersion()));
-+ ch.pipeline().get(HandlerBoss.class)
-+ .setHandler(new ServerConnector(bungee, UserConnection.this, target));
- }
- };
-- ChannelFutureListener listener = new ChannelFutureListener()
-- {
-+ ChannelFutureListener listener = new ChannelFutureListener() {
- @Override
- @SuppressWarnings("ThrowableResultIgnored")
-- public void operationComplete(ChannelFuture future) throws Exception
-- {
-- if ( callback != null )
-- {
-- callback.done( ( future.isSuccess() ) ? ServerConnectRequest.Result.SUCCESS : ServerConnectRequest.Result.FAIL, future.cause() );
-+ public void operationComplete(ChannelFuture future) throws Exception {
-+ if (callback != null) {
-+ callback.done((future.isSuccess()) ? ServerConnectRequest.Result.SUCCESS
-+ : ServerConnectRequest.Result.FAIL, future.cause());
- }
-
-- if ( !future.isSuccess() )
-- {
-+ if (!future.isSuccess()) {
- future.channel().close();
-- pendingConnects.remove( target );
--
-- ServerInfo def = updateAndGetNextServer( target );
-- if ( request.isRetry() && def != null && ( getServer() == null || def != getServer().getInfo() ) )
-- {
-- sendMessage( bungee.getTranslation( "fallback_lobby" ) );
-- connect( def, null, true, ServerConnectEvent.Reason.LOBBY_FALLBACK, request.getConnectTimeout() ); // Waterfall
-- } else if ( dimensionChange )
-- {
-- disconnect( bungee.getTranslation( "fallback_kick", future.cause().getClass().getName() ) );
-- } else
-- {
-- sendMessage( bungee.getTranslation( "fallback_kick", future.cause().getClass().getName() ) );
-+ pendingConnects.remove(target);
-+
-+ ServerInfo def = updateAndGetNextServer(target);
-+ if (request.isRetry() && def != null && (getServer() == null || def != getServer().getInfo())) {
-+ sendMessage(bungee.getTranslation("fallback_lobby"));
-+ connect(def, null, true, ServerConnectEvent.Reason.LOBBY_FALLBACK, request.getConnectTimeout()); // Waterfall
-+ } else if (dimensionChange) {
-+ disconnect(bungee.getTranslation("fallback_kick", future.cause().getClass().getName()));
-+ } else {
-+ sendMessage(bungee.getTranslation("fallback_kick", future.cause().getClass().getName()));
- }
- }
- }
- };
-- Bootstrap b = new Bootstrap()
-- .channel( PipelineUtils.getChannel( target.getAddress() ) )
-- .group( ch.getHandle().eventLoop() )
-- .handler( initializer )
-- .option( ChannelOption.CONNECT_TIMEOUT_MILLIS, request.getConnectTimeout() )
-- .remoteAddress( target.getAddress() );
-- // Windows is bugged, multi homed users will just have to live with random connecting IPs
-- if ( getPendingConnection().getListener().isSetLocalAddress() && !PlatformDependent.isWindows() && getPendingConnection().getListener().getSocketAddress() instanceof InetSocketAddress )
-- {
-- b.localAddress( getPendingConnection().getListener().getHost().getHostString(), 0 );
-+ Bootstrap b = new Bootstrap().channel(PipelineUtils.getChannel(target.getAddress()))
-+ .group(ch.getHandle().eventLoop()).handler(initializer)
-+ .option(ChannelOption.CONNECT_TIMEOUT_MILLIS, request.getConnectTimeout())
-+ .remoteAddress(target.getAddress());
-+ // Windows is bugged, multi homed users will just have to live with random
-+ // connecting IPs
-+ // FlameCord - Use listenerInfo
-+ final ListenerInfo listenerInfo = getPendingConnection().getListener();
-+
-+ if (listenerInfo.isSetLocalAddress() && !PlatformDependent.isWindows()
-+ && listenerInfo.getSocketAddress() instanceof InetSocketAddress) {
-+ b.localAddress(listenerInfo.getHost().getHostString(), 0);
- }
-- b.connect().addListener( listener );
-+ b.connect().addListener(listener);
- }
-
- @Override
-- public void disconnect(String reason)
-- {
-- disconnect0( TextComponent.fromLegacyText( reason ) );
-+ public void disconnect(String reason) {
-+ disconnect0(TextComponent.fromLegacyText(reason));
- }
-
- @Override
-- public void disconnect(BaseComponent... reason)
-- {
-- disconnect0( reason );
-+ public void disconnect(BaseComponent... reason) {
-+ disconnect0(reason);
- }
-
- @Override
-- public void disconnect(BaseComponent reason)
-- {
-- disconnect0( reason );
-+ public void disconnect(BaseComponent reason) {
-+ disconnect0(reason);
- }
-
-- public void disconnect0(final BaseComponent... reason)
-- {
-- if ( !ch.isClosing() )
-- {
-- bungee.getLogger().log( Level.INFO, "[{0}] disconnected with: {1}", new Object[]
-- {
-- getName(), BaseComponent.toLegacyText( reason )
-- } );
-+ public void disconnect0(final BaseComponent... reason) {
-+ if (!ch.isClosing()) {
-+ bungee.getLogger().log(Level.INFO, "[{0}] disconnected with: {1}",
-+ new Object[] { getName(), BaseComponent.toLegacyText(reason) });
-
-- ch.close( new Kick( ComponentSerializer.toString( reason ) ) );
-+ ch.close(new Kick(ComponentSerializer.toString(reason)));
-
-- if ( server != null )
-- {
-- server.setObsolete( true );
-- server.disconnect( "Quitting" );
-+ if (server != null) {
-+ server.setObsolete(true);
-+ // FlameCord - Remove "Quitting" reason
-+ server.disconnect();
- }
- }
- }
-
- @Override
-- public void chat(String message)
-- {
-- Preconditions.checkState( server != null, "Not connected to server" );
-- server.getCh().write( new Chat( message ) );
-+ public void chat(String message) {
-+ Preconditions.checkState(server != null, "Not connected to server");
-+ server.getCh().write(new Chat(message));
- }
-
- @Override
-- public void sendMessage(String message)
-- {
-- sendMessage( TextComponent.fromLegacyText( message ) );
-+ public void sendMessage(String message) {
-+ sendMessage(TextComponent.fromLegacyText(message));
- }
-
- @Override
-- public void sendMessages(String... messages)
-- {
-- for ( String message : messages )
-- {
-- sendMessage( message );
-+ public void sendMessages(String... messages) {
-+ for (String message : messages) {
-+ sendMessage(message);
- }
- }
-
- @Override
-- public void sendMessage(BaseComponent... message)
-- {
-- sendMessage( ChatMessageType.SYSTEM, message );
-+ public void sendMessage(BaseComponent... message) {
-+ sendMessage(ChatMessageType.SYSTEM, message);
- }
-
- @Override
-- public void sendMessage(BaseComponent message)
-- {
-- sendMessage( ChatMessageType.SYSTEM, message );
-+ public void sendMessage(BaseComponent message) {
-+ sendMessage(ChatMessageType.SYSTEM, message);
- }
-
-- private void sendMessage(ChatMessageType position, String message)
-- {
-- unsafe().sendPacket( new Chat( message, (byte) position.ordinal() ) );
-+ private void sendMessage(ChatMessageType position, String message) {
-+ unsafe().sendPacket(new Chat(message, (byte) position.ordinal()));
- }
-
- @Override
-- public void sendMessage(ChatMessageType position, BaseComponent... message)
-- {
-+ public void sendMessage(ChatMessageType position, BaseComponent... message) {
- // transform score components
-- message = ChatComponentTransformer.getInstance().transform( this, true, message );
-+ message = ChatComponentTransformer.getInstance().transform(this, true, message);
-
-- // Action bar doesn't display the new JSON formattings, legacy works - send it using this for now
-- if ( position == ChatMessageType.ACTION_BAR && getPendingConnection().getVersion() >= ProtocolConstants.MINECRAFT_1_8 ) // Travertine
-+ // Action bar doesn't display the new JSON formattings, legacy works - send it
-+ // using this for now
-+ if (position == ChatMessageType.ACTION_BAR
-+ && getPendingConnection().getVersion() >= ProtocolConstants.MINECRAFT_1_8) // Travertine
- {
-- // Versions older than 1.11 cannot send the Action bar with the new JSON formattings
-- // Fix by converting to a legacy message, see https://bugs.mojang.com/browse/MC-119145
-- if ( getPendingConnection().getVersion() <= ProtocolConstants.MINECRAFT_1_10 )
-- {
-- sendMessage( position, ComponentSerializer.toString( new TextComponent( BaseComponent.toLegacyText( message ) ) ) );
-- } else
-- {
-+ // Versions older than 1.11 cannot send the Action bar with the new JSON
-+ // formattings
-+ // Fix by converting to a legacy message, see
-+ // https://bugs.mojang.com/browse/MC-119145
-+ if (getPendingConnection().getVersion() <= ProtocolConstants.MINECRAFT_1_10) {
-+ sendMessage(position,
-+ ComponentSerializer.toString(new TextComponent(BaseComponent.toLegacyText(message))));
-+ } else {
- net.md_5.bungee.protocol.packet.Title title = new net.md_5.bungee.protocol.packet.Title();
-- title.setAction( net.md_5.bungee.protocol.packet.Title.Action.ACTIONBAR );
-- title.setText( ComponentSerializer.toString( message ) );
-- unsafe.sendPacket( title );
-+ title.setAction(net.md_5.bungee.protocol.packet.Title.Action.ACTIONBAR);
-+ title.setText(ComponentSerializer.toString(message));
-+ unsafe.sendPacket(title);
- }
-- } else
-- {
-- sendMessage( position, ComponentSerializer.toString( message ) );
-+ } else {
-+ sendMessage(position, ComponentSerializer.toString(message));
- }
- }
-
- @Override
-- public void sendMessage(ChatMessageType position, BaseComponent message)
-- {
-- message = ChatComponentTransformer.getInstance().transform( this, true, message )[0];
-+ public void sendMessage(ChatMessageType position, BaseComponent message) {
-+ message = ChatComponentTransformer.getInstance().transform(this, true, message)[0];
-
-- // Action bar doesn't display the new JSON formattings, legacy works - send it using this for now
-- if ( position == ChatMessageType.ACTION_BAR && getPendingConnection().getVersion() >= ProtocolConstants.MINECRAFT_1_8 ) // Travertine
-+ // Action bar doesn't display the new JSON formattings, legacy works - send it
-+ // using this for now
-+ if (position == ChatMessageType.ACTION_BAR
-+ && getPendingConnection().getVersion() >= ProtocolConstants.MINECRAFT_1_8) // Travertine
- {
-- sendMessage( position, ComponentSerializer.toString( new TextComponent( BaseComponent.toLegacyText( message ) ) ) );
-- } else
-- {
-- sendMessage( position, ComponentSerializer.toString( message ) );
-+ sendMessage(position, ComponentSerializer.toString(new TextComponent(BaseComponent.toLegacyText(message))));
-+ } else {
-+ sendMessage(position, ComponentSerializer.toString(message));
- }
- }
-
- @Override
-- public void sendData(String channel, byte[] data)
-- {
-- unsafe().sendPacket( new PluginMessage( channel, data, forgeClientHandler.isForgeUser() ) );
-+ public void sendData(String channel, byte[] data) {
-+ unsafe().sendPacket(new PluginMessage(channel, data, forgeClientHandler.isForgeUser()));
- }
-
- @Override
-- public InetSocketAddress getAddress()
-- {
-+ public InetSocketAddress getAddress() {
- return (InetSocketAddress) getSocketAddress();
- }
-
- @Override
-- public SocketAddress getSocketAddress()
-- {
-+ public SocketAddress getSocketAddress() {
- return ch.getRemoteAddress();
- }
-
- @Override
-- public Collection getGroups()
-- {
-- return Collections.unmodifiableCollection( groups );
-+ public Collection getGroups() {
-+ return Collections.unmodifiableCollection(groups);
- }
-
- @Override
-- public void addGroups(String... groups)
-- {
-- for ( String group : groups )
-- {
-- this.groups.add( group );
-- for ( String permission : bungee.getConfigurationAdapter().getPermissions( group ) )
-- {
-- setPermission( permission, true );
-+ public void addGroups(String... groups) {
-+ for (String group : groups) {
-+ this.groups.add(group);
-+ for (String permission : bungee.getConfigurationAdapter().getPermissions(group)) {
-+ setPermission(permission, true);
- }
- }
- }
-
- @Override
-- public void removeGroups(String... groups)
-- {
-- for ( String group : groups )
-- {
-- this.groups.remove( group );
-- for ( String permission : bungee.getConfigurationAdapter().getPermissions( group ) )
-- {
-- setPermission( permission, false );
-+ public void removeGroups(String... groups) {
-+ for (String group : groups) {
-+ this.groups.remove(group);
-+ for (String permission : bungee.getConfigurationAdapter().getPermissions(group)) {
-+ setPermission(permission, false);
- }
- }
- }
-
- @Override
-- public boolean hasPermission(String permission)
-- {
-- return bungee.getPluginManager().callEvent( new PermissionCheckEvent( this, permission, permissions.contains( permission ) ) ).hasPermission();
-+ public boolean hasPermission(String permission) {
-+ return bungee.getPluginManager()
-+ .callEvent(new PermissionCheckEvent(this, permission, permissions.contains(permission)))
-+ .hasPermission();
- }
-
- @Override
-- public void setPermission(String permission, boolean value)
-- {
-- if ( value )
-- {
-- permissions.add( permission );
-- } else
-- {
-- permissions.remove( permission );
-+ public void setPermission(String permission, boolean value) {
-+ if (value) {
-+ permissions.add(permission);
-+ } else {
-+ permissions.remove(permission);
- }
- }
-
- @Override
-- public Collection getPermissions()
-- {
-- return Collections.unmodifiableCollection( permissions );
-+ public Collection getPermissions() {
-+ return Collections.unmodifiableCollection(permissions);
- }
-
- @Override
-- public String toString()
-- {
-+ public String toString() {
- return name;
- }
-
- @Override
-- public Unsafe unsafe()
-- {
-+ public Unsafe unsafe() {
- return unsafe;
- }
-
- @Override
-- public String getUUID()
-- {
-+ public String getUUID() {
- return getPendingConnection().getUUID();
- }
-
- @Override
-- public UUID getUniqueId()
-- {
-+ public UUID getUniqueId() {
- return getPendingConnection().getUniqueId();
- }
-
-- public void setSettings(ClientSettings settings)
-- {
-+ public void setSettings(ClientSettings settings) {
- this.settings = settings;
- this.locale = null;
- }
-
- @Override
-- public Locale getLocale()
-- {
-- return ( locale == null && settings != null ) ? locale = Locale.forLanguageTag( settings.getLocale().replace( '_', '-' ) ) : locale;
-+ public Locale getLocale() {
-+ return (locale == null && settings != null)
-+ ? locale = Locale.forLanguageTag(settings.getLocale().replace('_', '-'))
-+ : locale;
- }
-
- @Override
-- public byte getViewDistance()
-- {
-- return ( settings != null ) ? settings.getViewDistance() : 10;
-+ public byte getViewDistance() {
-+ return (settings != null) ? settings.getViewDistance() : 10;
- }
-
- @Override
-- public ProxiedPlayer.ChatMode getChatMode()
-- {
-- if ( settings == null )
-- {
-+ public ProxiedPlayer.ChatMode getChatMode() {
-+ if (settings == null) {
- return ProxiedPlayer.ChatMode.SHOWN;
- }
-
-- switch ( settings.getChatFlags() )
-- {
-+ switch (settings.getChatFlags()) {
- default:
- case 0:
- return ProxiedPlayer.ChatMode.SHOWN;
-@@ -648,106 +590,93 @@ public final class UserConnection implements ProxiedPlayer
- }
-
- @Override
-- public boolean hasChatColors()
-- {
-+ public boolean hasChatColors() {
- return settings == null || settings.isChatColours();
- }
-
- @Override
-- public SkinConfiguration getSkinParts()
-- {
-- return ( settings != null ) ? new PlayerSkinConfiguration( settings.getSkinParts() ) : PlayerSkinConfiguration.SKIN_SHOW_ALL;
-+ public SkinConfiguration getSkinParts() {
-+ return (settings != null) ? new PlayerSkinConfiguration(settings.getSkinParts())
-+ : PlayerSkinConfiguration.SKIN_SHOW_ALL;
- }
-
- @Override
-- public ProxiedPlayer.MainHand getMainHand()
-- {
-- return ( settings == null || settings.getMainHand() == 1 ) ? ProxiedPlayer.MainHand.RIGHT : ProxiedPlayer.MainHand.LEFT;
-+ public ProxiedPlayer.MainHand getMainHand() {
-+ return (settings == null || settings.getMainHand() == 1) ? ProxiedPlayer.MainHand.RIGHT
-+ : ProxiedPlayer.MainHand.LEFT;
- }
-
- @Override
-- public boolean isForgeUser()
-- {
-+ public boolean isForgeUser() {
- return forgeClientHandler.isForgeUser();
- }
-
- @Override
-- public Map getModList()
-- {
-- if ( forgeClientHandler.getClientModList() == null )
-- {
-+ public Map getModList() {
-+ if (forgeClientHandler.getClientModList() == null) {
- // Return an empty map, rather than a null, if the client hasn't got any mods,
- // or is yet to complete a handshake.
- return ImmutableMap.of();
- }
-
-- return ImmutableMap.copyOf( forgeClientHandler.getClientModList() );
-+ return ImmutableMap.copyOf(forgeClientHandler.getClientModList());
- }
-
- @Override
-- public void setTabHeader(BaseComponent header, BaseComponent footer)
-- {
-- if ( ProtocolConstants.isBeforeOrEq( pendingConnection.getVersion(), ProtocolConstants.MINECRAFT_1_7_6 ) ) return; // Travertine
-- header = ChatComponentTransformer.getInstance().transform( this, true, header )[0];
-- footer = ChatComponentTransformer.getInstance().transform( this, true, footer )[0];
-+ public void setTabHeader(BaseComponent header, BaseComponent footer) {
-+ if (ProtocolConstants.isBeforeOrEq(pendingConnection.getVersion(), ProtocolConstants.MINECRAFT_1_7_6))
-+ return; // Travertine
-+ header = ChatComponentTransformer.getInstance().transform(this, true, header)[0];
-+ footer = ChatComponentTransformer.getInstance().transform(this, true, footer)[0];
-
-- unsafe().sendPacket( new PlayerListHeaderFooter(
-- ComponentSerializer.toString( header ),
-- ComponentSerializer.toString( footer )
-- ) );
-+ unsafe().sendPacket(
-+ new PlayerListHeaderFooter(ComponentSerializer.toString(header), ComponentSerializer.toString(footer)));
- }
-
- @Override
-- public void setTabHeader(BaseComponent[] header, BaseComponent[] footer)
-- {
-- if ( ProtocolConstants.isBeforeOrEq( pendingConnection.getVersion(), ProtocolConstants.MINECRAFT_1_7_6 ) ) return; // Travertine
-- header = ChatComponentTransformer.getInstance().transform( this, true, header );
-- footer = ChatComponentTransformer.getInstance().transform( this, true, footer );
-+ public void setTabHeader(BaseComponent[] header, BaseComponent[] footer) {
-+ if (ProtocolConstants.isBeforeOrEq(pendingConnection.getVersion(), ProtocolConstants.MINECRAFT_1_7_6))
-+ return; // Travertine
-+ header = ChatComponentTransformer.getInstance().transform(this, true, header);
-+ footer = ChatComponentTransformer.getInstance().transform(this, true, footer);
-
-- unsafe().sendPacket( new PlayerListHeaderFooter(
-- ComponentSerializer.toString( header ),
-- ComponentSerializer.toString( footer )
-- ) );
-+ unsafe().sendPacket(
-+ new PlayerListHeaderFooter(ComponentSerializer.toString(header), ComponentSerializer.toString(footer)));
- }
-
- @Override
-- public void resetTabHeader()
-- {
-- // Mojang did not add a way to remove the header / footer completely, we can only set it to empty
-- setTabHeader( (BaseComponent) null, null );
-+ public void resetTabHeader() {
-+ // Mojang did not add a way to remove the header / footer completely, we can
-+ // only set it to empty
-+ setTabHeader((BaseComponent) null, null);
- }
-
- @Override
-- public void sendTitle(Title title)
-- {
-- title.send( this );
-+ public void sendTitle(Title title) {
-+ title.send(this);
- }
-
-- public String getExtraDataInHandshake()
-- {
-+ public String getExtraDataInHandshake() {
- return this.getPendingConnection().getExtraDataInHandshake();
- }
-
-- public void setCompressionThreshold(int compressionThreshold)
-- {
-- if ( ProtocolConstants.isBeforeOrEq( pendingConnection.getVersion(), ProtocolConstants.MINECRAFT_1_7_6 ) ) return; // Travertine
-- if ( !ch.isClosing() && this.compressionThreshold == -1 && compressionThreshold >= 0 )
-- {
-+ public void setCompressionThreshold(int compressionThreshold) {
-+ if (ProtocolConstants.isBeforeOrEq(pendingConnection.getVersion(), ProtocolConstants.MINECRAFT_1_7_6))
-+ return; // Travertine
-+ if (!ch.isClosing() && this.compressionThreshold == -1 && compressionThreshold >= 0) {
- this.compressionThreshold = compressionThreshold;
-- unsafe.sendPacket( new SetCompression( compressionThreshold ) );
-- ch.setCompressionThreshold( compressionThreshold );
-+ unsafe.sendPacket(new SetCompression(compressionThreshold));
-+ ch.setCompressionThreshold(compressionThreshold);
- }
- }
-
- @Override
-- public boolean isConnected()
-- {
-+ public boolean isConnected() {
- return !ch.isClosed();
- }
-
- @Override
-- public Scoreboard getScoreboard()
-- {
-+ public Scoreboard getScoreboard() {
- return serverSentScoreboard;
- }
-
-diff --git a/proxy/src/main/java/net/md_5/bungee/command/CommandBungee.java b/proxy/src/main/java/net/md_5/bungee/command/CommandBungee.java
-index 4e2c6129..9a8a70dd 100644
---- a/proxy/src/main/java/net/md_5/bungee/command/CommandBungee.java
-+++ b/proxy/src/main/java/net/md_5/bungee/command/CommandBungee.java
-@@ -3,19 +3,22 @@ package net.md_5.bungee.command;
- import net.md_5.bungee.api.ChatColor;
- import net.md_5.bungee.api.CommandSender;
- import net.md_5.bungee.api.ProxyServer;
-+import net.md_5.bungee.api.chat.TextComponent;
- import net.md_5.bungee.api.plugin.Command;
-
--public class CommandBungee extends Command
--{
-+public class CommandBungee extends Command {
-
-- public CommandBungee()
-- {
-- super( "bungee" );
-+ public CommandBungee() {
-+ super("bungee");
- }
-
- @Override
-- public void execute(CommandSender sender, String[] args)
-- {
-- sender.sendMessage( ChatColor.BLUE + "This server is running Travertine version " + ProxyServer.getInstance().getVersion() + " by md_5" );
-+ public void execute(CommandSender sender, String[] args) {
-+ final ProxyServer proxyServer = ProxyServer.getInstance();
-+ final String name = proxyServer.getName(), version = proxyServer.getVersion();
-+
-+ sender.sendMessage(TextComponent.fromLegacyText(ChatColor.translateAlternateColorCodes('&', "&cRunning &f"
-+ + name + "&c version &e" + version
-+ + "&c by 2LS &b(@Sammwy_ and @LinsaFTW)\n&9Forked from Travertine by PaperMC and contributors.")));
- }
- }
-diff --git a/proxy/src/main/java/net/md_5/bungee/conf/YamlConfig.java b/proxy/src/main/java/net/md_5/bungee/conf/YamlConfig.java
-index d4fad294..5454efad 100644
---- a/proxy/src/main/java/net/md_5/bungee/conf/YamlConfig.java
-+++ b/proxy/src/main/java/net/md_5/bungee/conf/YamlConfig.java
-@@ -1,7 +1,5 @@
- package net.md_5.bungee.conf;
-
--import com.google.common.base.Charsets;
--import edu.umd.cs.findbugs.annotations.SuppressFBWarnings;
- import java.io.File;
- import java.io.FileInputStream;
- import java.io.FileOutputStream;
-@@ -21,7 +19,16 @@ import java.util.List;
- import java.util.Locale;
- import java.util.Map;
- import java.util.logging.Level;
-+
-+import com.google.common.base.Charsets;
-+
-+import org.yaml.snakeyaml.DumperOptions;
-+import org.yaml.snakeyaml.Yaml;
-+import org.yaml.snakeyaml.error.YAMLException;
-+
-+import edu.umd.cs.findbugs.annotations.SuppressFBWarnings;
- import lombok.RequiredArgsConstructor;
-+import net.md_5.bungee.BungeeCord;
- import net.md_5.bungee.Util;
- import net.md_5.bungee.api.ChatColor;
- import net.md_5.bungee.api.ProxyServer;
-@@ -29,22 +36,18 @@ import net.md_5.bungee.api.config.ConfigurationAdapter;
- import net.md_5.bungee.api.config.ListenerInfo;
- import net.md_5.bungee.api.config.ServerInfo;
- import net.md_5.bungee.util.CaseInsensitiveMap;
--import org.yaml.snakeyaml.DumperOptions;
--import org.yaml.snakeyaml.Yaml;
--import org.yaml.snakeyaml.error.YAMLException;
-
--public class YamlConfig implements ConfigurationAdapter
--{
-+public class YamlConfig implements ConfigurationAdapter {
-
- /**
- * The default tab list options available for picking.
- */
- @RequiredArgsConstructor
-- private enum DefaultTabList
-- {
-+ private enum DefaultTabList {
-
- GLOBAL(), GLOBAL_PING(), SERVER();
- }
-+
- private final Yaml yaml;
- private Map config;
- private final File file;
-@@ -53,185 +56,155 @@ public class YamlConfig implements ConfigurationAdapter
- this(new File("config.yml"));
- }
-
-- public YamlConfig(File file)
-- {
-+ public YamlConfig(File file) {
- this.file = file;
- DumperOptions options = new DumperOptions();
-- options.setDefaultFlowStyle( DumperOptions.FlowStyle.BLOCK );
-- yaml = new Yaml( options );
-+ options.setDefaultFlowStyle(DumperOptions.FlowStyle.BLOCK);
-+ yaml = new Yaml(options);
- }
-
- @Override
-- public void load()
-- {
-+ public void load() {
- load(true);
- }
-
-- public void load(boolean doPermissions)
-- {
-- try
-- {
-+ public void load(boolean doPermissions) {
-+ try {
- file.createNewFile();
-
-- try ( InputStream is = new FileInputStream( file ) )
-- {
-- try
-- {
-- config = (Map) yaml.load( is );
-- } catch ( YAMLException ex )
-- {
-- throw new RuntimeException( "Invalid configuration encountered - this is a configuration error and NOT a bug! Please attempt to fix the error or see https://www.spigotmc.org/ for help.", ex );
-+ try (InputStream is = new FileInputStream(file)) {
-+ try {
-+ config = (Map) yaml.load(is);
-+ } catch (YAMLException ex) {
-+ throw new RuntimeException(
-+ "Invalid configuration encountered - this is a configuration error and NOT a bug! Please attempt to fix the error or see https://www.spigotmc.org/ for help.",
-+ ex);
- }
- }
-
-- if ( config == null )
-- {
-+ if (config == null) {
- config = new CaseInsensitiveMap<>();
-- } else
-- {
-- config = new CaseInsensitiveMap<>( config );
-+ } else {
-+ config = new CaseInsensitiveMap<>(config);
- }
-- } catch ( IOException ex )
-- {
-- throw new RuntimeException( "Could not load configuration!", ex );
-+ } catch (IOException ex) {
-+ throw new RuntimeException("Could not load configuration!", ex);
- }
-
-- if(!doPermissions) return; // Waterfall
-- Map permissions = get( "permissions", null );
-- if ( permissions == null )
-- {
-- set( "permissions.default", Arrays.asList( new String[]
-- {
-- "bungeecord.command.server", "bungeecord.command.list"
-- } ) );
-- set( "permissions.admin", Arrays.asList( new String[]
-- {
-- "bungeecord.command.alert", "bungeecord.command.end", "bungeecord.command.ip", "bungeecord.command.reload"
-- } ) );
-+ if (!doPermissions)
-+ return; // Waterfall
-+ Map permissions = get("permissions", null);
-+ if (permissions == null) {
-+ set("permissions.default",
-+ Arrays.asList(new String[] { "bungeecord.command.server", "bungeecord.command.list" }));
-+ set("permissions.admin", Arrays.asList(new String[] { "bungeecord.command.alert", "bungeecord.command.end",
-+ "bungeecord.command.ip", "bungeecord.command.reload" }));
- }
-
-- Map groups = get( "groups", null );
-- if ( groups == null )
-- {
-- set( "groups.md_5", Collections.singletonList( "admin" ) );
-+ Map groups = get("groups", null);
-+ if (groups == null) {
-+ set("groups.md_5", Collections.singletonList("admin"));
- }
- }
-
-- private T get(String path, T def)
-- {
-- return get( path, def, config );
-+ private T get(String path, T def) {
-+ return get(path, def, config);
- }
-
- @SuppressWarnings("unchecked")
-- private T get(String path, T def, Map submap)
-- {
-- int index = path.indexOf( '.' );
-- if ( index == -1 )
-- {
-- Object val = submap.get( path );
-- if ( val == null && def != null )
-- {
-+ private T get(String path, T def, Map submap) {
-+ int index = path.indexOf('.');
-+ if (index == -1) {
-+ Object val = submap.get(path);
-+ if (val == null && def != null) {
- val = def;
-- submap.put( path, def );
-+ submap.put(path, def);
- save();
- }
- return (T) val;
-- } else
-- {
-- String first = path.substring( 0, index );
-- String second = path.substring( index + 1, path.length() );
-- Map sub = (Map) submap.get( first );
-- if ( sub == null )
-- {
-+ } else {
-+ String first = path.substring(0, index);
-+ String second = path.substring(index + 1, path.length());
-+ Map sub = (Map) submap.get(first);
-+ if (sub == null) {
- sub = new LinkedHashMap();
-- submap.put( first, sub );
-+ submap.put(first, sub);
- }
-- return get( second, def, sub );
-+ return get(second, def, sub);
- }
- }
-
-- private void set(String path, Object val)
-- {
-- set( path, val, config );
-+ private void set(String path, Object val) {
-+ set(path, val, config);
- }
-
- @SuppressWarnings("unchecked")
-- private void set(String path, Object val, Map submap)
-- {
-- int index = path.indexOf( '.' );
-- if ( index == -1 )
-- {
-- if ( val == null )
-- {
-- submap.remove( path );
-- } else
-- {
-- submap.put( path, val );
-+ private void set(String path, Object val, Map submap) {
-+ int index = path.indexOf('.');
-+ if (index == -1) {
-+ if (val == null) {
-+ submap.remove(path);
-+ } else {
-+ submap.put(path, val);
- }
- save();
-- } else
-- {
-- String first = path.substring( 0, index );
-- String second = path.substring( index + 1, path.length() );
-- Map sub = (Map) submap.get( first );
-- if ( sub == null )
-- {
-+ } else {
-+ String first = path.substring(0, index);
-+ String second = path.substring(index + 1, path.length());
-+ Map sub = (Map) submap.get(first);
-+ if (sub == null) {
- sub = new LinkedHashMap();
-- submap.put( first, sub );
-+ submap.put(first, sub);
- }
-- set( second, val, sub );
-+ set(second, val, sub);
- }
- }
-
-- private void save()
-- {
-- try
-- {
-- try ( Writer wr = new OutputStreamWriter( new FileOutputStream( file ), Charsets.UTF_8 ) )
-- {
-- yaml.dump( config, wr );
-+ private void save() {
-+ try {
-+ try (Writer wr = new OutputStreamWriter(new FileOutputStream(file), Charsets.UTF_8)) {
-+ yaml.dump(config, wr);
- }
-- } catch ( IOException ex )
-- {
-- ProxyServer.getInstance().getLogger().log( Level.WARNING, "Could not save config", ex );
-+ } catch (IOException ex) {
-+ ProxyServer.getInstance().getLogger().log(Level.WARNING, "Could not save config", ex);
- }
- }
-
- @Override
-- public int getInt(String path, int def)
-- {
-- return get( path, def );
-+ public int getInt(String path, int def) {
-+ return get(path, def);
- }
-
- @Override
-- public String getString(String path, String def)
-- {
-- return get( path, def );
-+ public String getString(String path, String def) {
-+ return get(path, def);
- }
-
- @Override
-- public boolean getBoolean(String path, boolean def)
-- {
-- return get( path, def );
-+ public boolean getBoolean(String path, boolean def) {
-+ return get(path, def);
- }
-
- @Override
- @SuppressWarnings("unchecked")
-- public Map getServers()
-- {
-- Map> base = get( "servers", (Map) Collections.singletonMap( "lobby", new HashMap<>() ) );
-+ public Map getServers() {
-+ Map> base = get("servers",
-+ (Map) Collections.singletonMap("lobby", new HashMap<>()));
- Map ret = new HashMap<>();
-
-- for ( Map.Entry> entry : base.entrySet() )
-- {
-+ for (Map.Entry> entry : base.entrySet()) {
- Map val = entry.getValue();
- String name = entry.getKey();
-- String addr = get( "address", "localhost:25565", val );
-- String motd = ChatColor.translateAlternateColorCodes( '&', get( "motd", "&1Just another Travertine - Forced Host", val ) );
-- boolean restricted = get( "restricted", false, val );
-- SocketAddress address = Util.getAddr( addr );
-- ServerInfo info = ProxyServer.getInstance().constructServerInfo( name, address, motd, restricted );
-- ret.put( name, info );
-+ String addr = get("address", "localhost:25565", val);
-+ // FlameCord - Use getName() instead of Travertine
-+ // String motd = ChatColor.translateAlternateColorCodes( '&', get( "motd",
-+ // "&1Just another Travertine - Forced Host", val ) );
-+ String motd = ChatColor.translateAlternateColorCodes('&',
-+ get("motd", "&1Just another " + BungeeCord.getInstance().getName() + " - Forced Host", val));
-+ boolean restricted = get("restricted", false, val);
-+ SocketAddress address = Util.getAddr(addr);
-+ ServerInfo info = ProxyServer.getInstance().constructServerInfo(name, address, motd, restricted);
-+ ret.put(name, info);
- }
-
- return ret;
-@@ -240,67 +213,62 @@ public class YamlConfig implements ConfigurationAdapter
- @Override
- @SuppressWarnings("unchecked")
- @SuppressFBWarnings("RCN_REDUNDANT_NULLCHECK_OF_NONNULL_VALUE")
-- public Collection getListeners()
-- {
-- Collection