Files
AkarinMC/patches/server/0013-Optimizations-for-network.patch
ㄗㄠˋ ㄑㄧˊ 6f26a671b5 Updated Upstream (Paper)
Upstream has released updates that appears to apply and compile correctly

Paper Changes:
26fb7cc35 Fix Chunk Post Processing deadlock risk
ffecc4e26 Revert "Optimize entity list iteration requiring entities be in"
0a4286cc4 Prevent Fire from loading chunks
07915ea18 Add Player Client Options API (#2883)
bc48a3172 Optimize entity list iteration requiring entities be in  loaded chunks
88092fef1 Optimize ChunkProviderServer's chunk level checking helper methods
01e8ce8d2 Forced Watchdog Crash support and Improve Async Shutdown
fdb8fe780 Be less strict with vanilla teleport command limits
0f06d3806 Restrict vanilla teleport command to within worldborder
24d93aafa Fix Optional null issue - Fixes #3155
eb71c5fa3 Fix incorect timing of mspt
1ca804342 Optimise entity hard collision checking
b67a42376 Don't run entity collision code if not needed
bd9aa547d Optimise ArraySetSorted#removeIf
2020-04-18 18:05:03 +08:00

462 lines
27 KiB
Diff

From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?=E3=84=97=E3=84=A0=CB=8B=20=E3=84=91=E3=84=A7=CB=8A?=
<tsao-chi@the-lingo.org>
Date: Sun, 5 Apr 2020 14:59:10 +0800
Subject: [PATCH] Optimizations for network
diff --git a/src/main/java/com/destroystokyo/paper/network/StandardPaperServerListPingEventImpl.java b/src/main/java/com/destroystokyo/paper/network/StandardPaperServerListPingEventImpl.java
index a85466bc7e0a8aa54b9eff14077fe6c992ae2902..324af1a12a5780170f8cd6e060ff2f2f9d152c3d 100644
--- a/src/main/java/com/destroystokyo/paper/network/StandardPaperServerListPingEventImpl.java
+++ b/src/main/java/com/destroystokyo/paper/network/StandardPaperServerListPingEventImpl.java
@@ -106,7 +106,7 @@ public final class StandardPaperServerListPingEventImpl extends PaperServerListP
}
// Send response
- networkManager.sendPacket(new PacketStatusOutServerInfo(ping));
+ networkManager.sendPacketAsync(new PacketStatusOutServerInfo(ping)); // Akarin - Async Sending packets
}
}
diff --git a/src/main/java/net/minecraft/server/HandshakeListener.java b/src/main/java/net/minecraft/server/HandshakeListener.java
index 0532f975b7af5b3f2916c26141221cd3701765d0..e7be1074b1b8fde3590b1323508965961824e671 100644
--- a/src/main/java/net/minecraft/server/HandshakeListener.java
+++ b/src/main/java/net/minecraft/server/HandshakeListener.java
@@ -39,7 +39,7 @@ public class HandshakeListener implements PacketHandshakingInListener {
if (throttleTracker.containsKey(address) && !"127.0.0.1".equals(address.getHostAddress()) && currentTime - throttleTracker.get(address) < connectionThrottle) {
throttleTracker.put(address, currentTime);
chatmessage = new ChatMessage(com.destroystokyo.paper.PaperConfig.connectionThrottleKickMessage); // Paper - Configurable connection throttle kick message
- this.b.sendPacket(new PacketLoginOutDisconnect(chatmessage));
+ this.b.sendPacketAsync(new PacketLoginOutDisconnect(chatmessage)); // Akarin - Async Sending packets
this.b.close(chatmessage);
return;
}
@@ -66,11 +66,11 @@ public class HandshakeListener implements PacketHandshakingInListener {
if (packethandshakinginsetprotocol.c() > SharedConstants.getGameVersion().getProtocolVersion()) {
chatmessage = new ChatMessage( java.text.MessageFormat.format( org.spigotmc.SpigotConfig.outdatedServerMessage.replaceAll("'", "''"), SharedConstants.getGameVersion().getName() ) ); // Spigot
- this.b.sendPacket(new PacketLoginOutDisconnect(chatmessage));
+ this.b.sendPacketAsync(new PacketLoginOutDisconnect(chatmessage));
this.b.close(chatmessage);
} else if (packethandshakinginsetprotocol.c() < SharedConstants.getGameVersion().getProtocolVersion()) {
chatmessage = new ChatMessage( java.text.MessageFormat.format( org.spigotmc.SpigotConfig.outdatedClientMessage.replaceAll("'", "''"), SharedConstants.getGameVersion().getName() ) ); // Spigot
- this.b.sendPacket(new PacketLoginOutDisconnect(chatmessage));
+ this.b.sendPacketAsync(new PacketLoginOutDisconnect(chatmessage));
this.b.close(chatmessage);
} else {
this.b.setPacketListener(new LoginListener(this.a, this.b));
diff --git a/src/main/java/net/minecraft/server/LoginListener.java b/src/main/java/net/minecraft/server/LoginListener.java
index f1222fcb2bd52b8781d0f92c94e1472fa7b1e493..522cfed4cb09bc9ecc48b6313da47f9af7a5e1d8 100644
--- a/src/main/java/net/minecraft/server/LoginListener.java
+++ b/src/main/java/net/minecraft/server/LoginListener.java
@@ -111,6 +111,19 @@ public class LoginListener implements PacketLoginInListener {
}
+ // Akarin Start - Async Sending packets
+ public void disconnectAsync(IChatBaseComponent ichatbasecomponent) {
+ try {
+ LoginListener.LOGGER.info("Disconnecting {}: {}", this.d(), ichatbasecomponent.getString());
+ this.networkManager.sendPacketAsync(new PacketLoginOutDisconnect(ichatbasecomponent));
+ this.networkManager.close(ichatbasecomponent);
+ } catch (Exception exception) {
+ LoginListener.LOGGER.error("Error whilst disconnecting player", exception);
+ }
+
+ }
+ // Akarin End - Async Sending packets
+
// Paper start - Cache authenticator threads
private static final AtomicInteger threadId = new AtomicInteger(0);
private static final java.util.concurrent.ExecutorService authenticatorPool = java.util.concurrent.Executors.newCachedThreadPool(
@@ -192,7 +205,7 @@ public class LoginListener implements PacketLoginInListener {
this.i = packetlogininstart.b();
if (this.server.getOnlineMode() && !this.networkManager.isLocal()) {
this.g = LoginListener.EnumProtocolState.KEY;
- this.networkManager.sendPacket(new PacketLoginOutEncryptionBegin("", this.server.getKeyPair().getPublic(), this.e));
+ this.networkManager.sendPacketAsync(new PacketLoginOutEncryptionBegin("", this.server.getKeyPair().getPublic(), this.e)); // Akarin - Async Sending packets
} else {
// Paper start - Velocity support
if (com.destroystokyo.paper.PaperConfig.velocitySupport) {
@@ -254,7 +267,7 @@ public class LoginListener implements PacketLoginInListener {
LoginListener.this.i = LoginListener.this.a(gameprofile);
LoginListener.this.g = LoginListener.EnumProtocolState.READY_TO_ACCEPT;
} else {
- LoginListener.this.disconnect(new ChatMessage("multiplayer.disconnect.unverified_username", new Object[0]));
+ LoginListener.this.disconnectAsync(new ChatMessage("multiplayer.disconnect.unverified_username", new Object[0])); // Akarin - Async Sending packets
LoginListener.LOGGER.error("Username '{}' tried to join with an invalid session", gameprofile.getName());
}
} catch (AuthenticationUnavailableException authenticationunavailableexception) {
@@ -267,7 +280,7 @@ public class LoginListener implements PacketLoginInListener {
if (com.destroystokyo.paper.PaperConfig.authenticationServersDownKickMessage != null) {
LoginListener.this.disconnect(new ChatComponentText(com.destroystokyo.paper.PaperConfig.authenticationServersDownKickMessage));
} else // Paper end
- LoginListener.this.disconnect(new ChatMessage("multiplayer.disconnect.authservers_down", new Object[0]));
+ LoginListener.this.disconnectAsync(new ChatMessage("multiplayer.disconnect.authservers_down", new Object[0])); // Akarin - Async Sending packets
LoginListener.LOGGER.error("Couldn't verify username because servers are unavailable");
}
// CraftBukkit start - catch all exceptions
@@ -376,7 +389,7 @@ public class LoginListener implements PacketLoginInListener {
return;
}
// Paper end
- this.disconnect(new ChatMessage("multiplayer.disconnect.unexpected_query_response", new Object[0]));
+ this.disconnectAsync(new ChatMessage("multiplayer.disconnect.unexpected_query_response", new Object[0])); // Akarin - Async Sending packets
}
protected GameProfile a(GameProfile gameprofile) {
diff --git a/src/main/java/net/minecraft/server/NetworkManager.java b/src/main/java/net/minecraft/server/NetworkManager.java
index 96a785af27e1924b0cc1959254d4ae3cdd0385a1..fd1d5fe3bf40950d5dbdd9fa79cf5828c7b42d57 100644
--- a/src/main/java/net/minecraft/server/NetworkManager.java
+++ b/src/main/java/net/minecraft/server/NetworkManager.java
@@ -43,6 +43,7 @@ public class NetworkManager extends SimpleChannelInboundHandler<Packet<?>> {
});
private final EnumProtocolDirection h;
private final Queue<NetworkManager.QueuedPacket> packetQueue = Queues.newConcurrentLinkedQueue(); private final Queue<NetworkManager.QueuedPacket> getPacketQueue() { return this.packetQueue; } // Paper - OBFHELPER
+ private EnumProtocol protocol; // Akarin - avoid map lookup
public Channel channel;
public SocketAddress socketAddress; public void setSpoofedRemoteAddress(SocketAddress address) { this.socketAddress = address; } // Paper - OBFHELPER
// Spigot Start
@@ -88,6 +89,7 @@ public class NetworkManager extends SimpleChannelInboundHandler<Packet<?>> {
public void setProtocol(EnumProtocol enumprotocol) {
this.channel.attr(NetworkManager.c).set(enumprotocol);
+ protocol = enumprotocol; // Akarin - avoid map lookup
this.channel.config().setAutoRead(true);
NetworkManager.LOGGER.debug("Enabled auto read");
}
@@ -175,8 +177,8 @@ public class NetworkManager extends SimpleChannelInboundHandler<Packet<?>> {
private void dispatchPacket(Packet<?> packet, @Nullable GenericFutureListener<? extends Future<? super Void>> genericFutureListener) { this.b(packet, genericFutureListener); } // Paper - OBFHELPER
private void b(Packet<?> packet, @Nullable GenericFutureListener<? extends Future<? super Void>> genericfuturelistener) {
- EnumProtocol enumprotocol = EnumProtocol.a(packet);
- EnumProtocol enumprotocol1 = (EnumProtocol) this.channel.attr(NetworkManager.c).get();
+ EnumProtocol enumprotocol = packet.protocol();//EnumProtocol.a(packet); // Akarin - avoid map lookup
+ EnumProtocol enumprotocol1 = protocol;//(EnumProtocol) this.channel.attr(NetworkManager.c).get(); // Akarin - avoid map lookup
++this.q;
if (enumprotocol1 != enumprotocol) {
@@ -184,7 +186,7 @@ public class NetworkManager extends SimpleChannelInboundHandler<Packet<?>> {
this.channel.config().setAutoRead(false);
}
- if (this.channel.eventLoop().inEventLoop()) {
+ if (false && this.channel.eventLoop().inEventLoop()) { // Akarin - Async Sending packets
if (enumprotocol != enumprotocol1) {
this.setProtocol(enumprotocol);
}
@@ -223,30 +225,92 @@ public class NetworkManager extends SimpleChannelInboundHandler<Packet<?>> {
}
- // Paper start - Async-Anti-Xray - Stop dispatching further packets and return false if the peeked packet is a chunk packet which is not ready
- private boolean sendPacketQueue() { return this.o(); } // OBFHELPER // void -> boolean
- private boolean o() { // void -> boolean
- if (this.channel != null && this.channel.isOpen()) {
- Queue queue = this.packetQueue;
-
- synchronized (this.packetQueue) {
- while (!this.packetQueue.isEmpty()) {
- NetworkManager.QueuedPacket networkmanager_queuedpacket = (NetworkManager.QueuedPacket) this.getPacketQueue().peek(); // poll -> peek
-
- if (networkmanager_queuedpacket != null) { // Fix NPE (Spigot bug caused by handleDisconnection())
- if (networkmanager_queuedpacket.getPacket() instanceof PacketPlayOutMapChunk && !((PacketPlayOutMapChunk) networkmanager_queuedpacket.getPacket()).isReady()) { // Check if the peeked packet is a chunk packet which is not ready
- return false; // Return false if the peeked packet is a chunk packet which is not ready
- } else {
- this.getPacketQueue().poll(); // poll here
- this.dispatchPacket(networkmanager_queuedpacket.getPacket(), networkmanager_queuedpacket.getGenericFutureListener()); // dispatch the packet
- }
- }
- }
+ // Akarin Start - Async Sending packets - multiple packets, copied from above
+ public void sendPacketAsync(Packet<?> packet) {
+ EnumProtocol enumprotocol = packet.protocol();
+ EnumProtocol enumprotocol1 = protocol;
- }
+ ++this.q;
+ if (enumprotocol1 != enumprotocol) {
+ NetworkManager.LOGGER.debug("Disabled auto read");
+ this.channel.config().setAutoRead(false);
+ this.setProtocol(enumprotocol);
}
- return true; // Return true if all packets were dispatched
+ ChannelFuture channelfuture = this.channel.writeAndFlush(packet);
+
+ channelfuture.addListener(ChannelFutureListener.FIRE_EXCEPTION_ON_FAILURE);
+
+ }
+
+ public void sendPackets(Packet<?> packet, Packet<?> other) {
+ EnumProtocol enumprotocol = packet.protocol();
+
+ ++this.q;
+ if (protocol != enumprotocol) {
+ NetworkManager.LOGGER.debug("Disabled auto read");
+ this.channel.config().setAutoRead(false);
+ }
+
+ this.channel.eventLoop().execute(() -> {
+ if (enumprotocol != protocol) {
+ this.setProtocol(enumprotocol);
+ }
+
+ this.channel.write(packet).addListener(ChannelFutureListener.FIRE_EXCEPTION_ON_FAILURE);
+ this.channel.write(other).addListener(ChannelFutureListener.FIRE_EXCEPTION_ON_FAILURE);
+ this.channel.flush();
+ });
+ }
+
+ public void sendPackets(Packet<?> packet, Packet<?> ...packets) {
+ EnumProtocol enumprotocol = packet.protocol();
+
+ ++this.q;
+ if (protocol != enumprotocol) {
+ NetworkManager.LOGGER.debug("Disabled auto read");
+ this.channel.config().setAutoRead(false);
+ }
+
+ this.channel.eventLoop().execute(() -> {
+ if (enumprotocol != protocol) {
+ this.setProtocol(enumprotocol);
+ }
+
+ this.channel.write(packet).addListener(ChannelFutureListener.FIRE_EXCEPTION_ON_FAILURE);
+ for (Packet<?> pkt : packets) {
+ this.channel.write(pkt).addListener(ChannelFutureListener.FIRE_EXCEPTION_ON_FAILURE);
+ }
+
+ this.channel.flush();
+ });
+ }
+ // Akarin End
+
+ // Paper start - Async-Anti-Xray - Stop dispatching further packets and return false if the peeked packet is a chunk packet which is not ready
+ private boolean sendPacketQueue() { return this.o(); } // OBFHELPER // void -> boolean
+ private boolean o() { // void -> boolean
+ if (this.channel != null && this.channel.isOpen()) {
+ Queue queue = this.packetQueue;
+
+ synchronized (this.packetQueue) {
+ while (!this.packetQueue.isEmpty()) {
+ NetworkManager.QueuedPacket networkmanager_queuedpacket = (NetworkManager.QueuedPacket) this.getPacketQueue().peek(); // poll -> peek
+
+ if (networkmanager_queuedpacket != null) { // Fix NPE (Spigot bug caused by handleDisconnection())
+ if (networkmanager_queuedpacket.getPacket() instanceof PacketPlayOutMapChunk && !((PacketPlayOutMapChunk) networkmanager_queuedpacket.getPacket()).isReady()) { // Check if the peeked packet is a chunk packet which is not ready
+ return false; // Return false if the peeked packet is a chunk packet which is not ready
+ } else {
+ this.getPacketQueue().poll(); // poll here
+ this.dispatchPacket(networkmanager_queuedpacket.getPacket(), networkmanager_queuedpacket.getGenericFutureListener()); // dispatch the packet
+ }
+ }
+ }
+
+ }
+ }
+
+ return true; // Return true if all packets were dispatched
}
// Paper end
@@ -260,9 +324,9 @@ public class NetworkManager extends SimpleChannelInboundHandler<Packet<?>> {
((PlayerConnection) this.packetListener).tick();
}
- if (this.channel != null) {
- if (enableExplicitFlush) this.channel.eventLoop().execute(() -> this.channel.flush()); // Paper - we don't need to explicit flush here, but allow opt in incase issues are found to a better version
- }
+ //if (this.channel != null) { // Akarin - already did
+ //if (enableExplicitFlush) this.channel.eventLoop().execute(() -> this.channel.flush()); // Paper - we don't need to explicit flush here, but allow opt in incase issues are found to a better version
+ //}
if (this.t++ % 20 == 0) {
this.s = this.s * 0.75F + (float) this.q * 0.25F;
diff --git a/src/main/java/net/minecraft/server/Packet.java b/src/main/java/net/minecraft/server/Packet.java
index 8d0965a0535b16f19eda21b97a44464b85b05460..7e27cd280fa889f6178d46aa9f9d3a613d9702e6 100644
--- a/src/main/java/net/minecraft/server/Packet.java
+++ b/src/main/java/net/minecraft/server/Packet.java
@@ -20,4 +20,10 @@ public interface Packet<T extends PacketListener> {
default boolean a() {
return false;
}
+
+ // Akarin start - add protocol
+ default EnumProtocol protocol() {
+ return EnumProtocol.PLAY;
+ }
+ // Akarin end
}
diff --git a/src/main/java/net/minecraft/server/PacketLoginOutCustomPayload.java b/src/main/java/net/minecraft/server/PacketLoginOutCustomPayload.java
index 7eb230f1b27eddf48f1b12fc78877a3678d802df..d01cac0bd40a11d82fa0d6874d87ad3f576a4e20 100644
--- a/src/main/java/net/minecraft/server/PacketLoginOutCustomPayload.java
+++ b/src/main/java/net/minecraft/server/PacketLoginOutCustomPayload.java
@@ -41,4 +41,11 @@ public class PacketLoginOutCustomPayload implements Packet<PacketLoginOutListene
public void a(PacketLoginOutListener packetloginoutlistener) {
packetloginoutlistener.a(this);
}
+
+ // Akarin start - add protocol
+ @Override
+ public EnumProtocol protocol() {
+ return EnumProtocol.LOGIN;
+ }
+ // Akarin end
}
diff --git a/src/main/java/net/minecraft/server/PacketLoginOutDisconnect.java b/src/main/java/net/minecraft/server/PacketLoginOutDisconnect.java
index e5094f55f1472c9b74f7f9394aec448237e87149..a5d9b6d94c386f05659f10d69cb84b150610138e 100644
--- a/src/main/java/net/minecraft/server/PacketLoginOutDisconnect.java
+++ b/src/main/java/net/minecraft/server/PacketLoginOutDisconnect.java
@@ -25,4 +25,11 @@ public class PacketLoginOutDisconnect implements Packet<PacketLoginOutListener>
public void a(PacketLoginOutListener packetloginoutlistener) {
packetloginoutlistener.a(this);
}
+
+ // Akarin start - add protocol
+ @Override
+ public EnumProtocol protocol() {
+ return EnumProtocol.LOGIN;
+ }
+ // Akarin end
}
diff --git a/src/main/java/net/minecraft/server/PacketLoginOutEncryptionBegin.java b/src/main/java/net/minecraft/server/PacketLoginOutEncryptionBegin.java
index b0d6342c319a48290fd8bf6aa07a16d108feae18..eeabb54c44d39197f34a7171884cc7e885bce453 100644
--- a/src/main/java/net/minecraft/server/PacketLoginOutEncryptionBegin.java
+++ b/src/main/java/net/minecraft/server/PacketLoginOutEncryptionBegin.java
@@ -34,4 +34,11 @@ public class PacketLoginOutEncryptionBegin implements Packet<PacketLoginOutListe
public void a(PacketLoginOutListener packetloginoutlistener) {
packetloginoutlistener.a(this);
}
+
+ // Akarin start - add protocol
+ @Override
+ public EnumProtocol protocol() {
+ return EnumProtocol.LOGIN;
+ }
+ // Akarin end
}
diff --git a/src/main/java/net/minecraft/server/PacketLoginOutSetCompression.java b/src/main/java/net/minecraft/server/PacketLoginOutSetCompression.java
index fa0653a7e4a21445fa5c2221a73e9ea419ae157c..d3b5f83d5659322360c89e379db9aef4c623159a 100644
--- a/src/main/java/net/minecraft/server/PacketLoginOutSetCompression.java
+++ b/src/main/java/net/minecraft/server/PacketLoginOutSetCompression.java
@@ -25,4 +25,11 @@ public class PacketLoginOutSetCompression implements Packet<PacketLoginOutListen
public void a(PacketLoginOutListener packetloginoutlistener) {
packetloginoutlistener.a(this);
}
+
+ // Akarin start - add protocol
+ @Override
+ public EnumProtocol protocol() {
+ return EnumProtocol.LOGIN;
+ }
+ // Akarin end
}
diff --git a/src/main/java/net/minecraft/server/PacketLoginOutSuccess.java b/src/main/java/net/minecraft/server/PacketLoginOutSuccess.java
index 54c29047180794a9802b4f1d79fbd35478870226..75d7bc19683a6c411af5f381a4809267a4cadaaa 100644
--- a/src/main/java/net/minecraft/server/PacketLoginOutSuccess.java
+++ b/src/main/java/net/minecraft/server/PacketLoginOutSuccess.java
@@ -34,4 +34,11 @@ public class PacketLoginOutSuccess implements Packet<PacketLoginOutListener> {
public void a(PacketLoginOutListener packetloginoutlistener) {
packetloginoutlistener.a(this);
}
+
+ // Akarin start - add protocol
+ @Override
+ public EnumProtocol protocol() {
+ return EnumProtocol.LOGIN;
+ }
+ // Akarin end
}
diff --git a/src/main/java/net/minecraft/server/PacketStatusListener.java b/src/main/java/net/minecraft/server/PacketStatusListener.java
index 4bb21c48bd50353370ec3c3546a00a5d20e4b9d8..06af567fc1fb3a2053eb4e8af6d93dbb2391616a 100644
--- a/src/main/java/net/minecraft/server/PacketStatusListener.java
+++ b/src/main/java/net/minecraft/server/PacketStatusListener.java
@@ -143,7 +143,7 @@ public class PacketStatusListener implements PacketStatusInListener {
@Override
public void a(PacketStatusInPing packetstatusinping) {
- this.networkManager.sendPacket(new PacketStatusOutPong(packetstatusinping.b()));
+ this.networkManager.sendPacketAsync(new PacketStatusOutPong(packetstatusinping.b())); // Akarin - Async Sending packets
this.networkManager.close(PacketStatusListener.a);
}
}
diff --git a/src/main/java/net/minecraft/server/PacketStatusOutPong.java b/src/main/java/net/minecraft/server/PacketStatusOutPong.java
index 94a0da87db34ee5131686e4fa813500794ffc30d..577c6ef9cfe26d38783cd38353720b0fe457d7f5 100644
--- a/src/main/java/net/minecraft/server/PacketStatusOutPong.java
+++ b/src/main/java/net/minecraft/server/PacketStatusOutPong.java
@@ -25,4 +25,11 @@ public class PacketStatusOutPong implements Packet<PacketStatusOutListener> {
public void a(PacketStatusOutListener packetstatusoutlistener) {
packetstatusoutlistener.a(this);
}
+
+ // Akarin start - add protocol
+ @Override
+ public EnumProtocol protocol() {
+ return EnumProtocol.STATUS;
+ }
+ // Akarin end
}
diff --git a/src/main/java/net/minecraft/server/PacketStatusOutServerInfo.java b/src/main/java/net/minecraft/server/PacketStatusOutServerInfo.java
index 50d5fb62efa7c89c7a73ccf072a0e7e433bcc650..4da7a2c1a4f84661e1018c7233b7a52449532d5b 100644
--- a/src/main/java/net/minecraft/server/PacketStatusOutServerInfo.java
+++ b/src/main/java/net/minecraft/server/PacketStatusOutServerInfo.java
@@ -28,4 +28,11 @@ public class PacketStatusOutServerInfo implements Packet<PacketStatusOutListener
public void a(PacketStatusOutListener packetstatusoutlistener) {
packetstatusoutlistener.a(this);
}
+
+ // Akarin start - add protocol
+ @Override
+ public EnumProtocol protocol() {
+ return EnumProtocol.STATUS;
+ }
+ // Akarin end
}
diff --git a/src/main/java/net/minecraft/server/PlayerConnection.java b/src/main/java/net/minecraft/server/PlayerConnection.java
index 6dfbbc67dd9cc60355dcf5ef751cd1a5b259be6b..b23612817b653b3f9a74b9c3bff70b8ce831b8f4 100644
--- a/src/main/java/net/minecraft/server/PlayerConnection.java
+++ b/src/main/java/net/minecraft/server/PlayerConnection.java
@@ -284,9 +284,9 @@ public class PlayerConnection implements PacketListenerPlayIn {
MinecraftServer minecraftserver = this.minecraftServer;
NetworkManager networkmanager = this.networkManager;
- this.networkManager.getClass();
+ //this.networkManager.getClass(); // Akarin - decompile fixes
// CraftBukkit - Don't wait
- minecraftserver.scheduleOnMain(networkmanager::handleDisconnection); // Paper
+ //minecraftserver.scheduleOnMain(networkmanager::handleDisconnection); // Paper // Akarin - Async Sending packets - already did
}
@Override
diff --git a/src/main/java/net/minecraft/server/PlayerList.java b/src/main/java/net/minecraft/server/PlayerList.java
index 0e1703c9dac8e122074ac6369a1a88240bbc3e70..9ca3fdc9cf5df3651d9b9267806c9f4b566515cb 100644
--- a/src/main/java/net/minecraft/server/PlayerList.java
+++ b/src/main/java/net/minecraft/server/PlayerList.java
@@ -159,6 +159,8 @@ public abstract class PlayerList {
// Spigot - view distance
playerconnection.sendPacket(new PacketPlayOutLogin(entityplayer.getId(), entityplayer.playerInteractManager.getGameMode(), WorldData.c(worlddata.getSeed()), worlddata.isHardcore(), worldserver.worldProvider.getDimensionManager().getType(), this.getMaxPlayers(), worlddata.getType(), worldserver.spigotConfig.viewDistance, flag1, !flag));
entityplayer.getBukkitEntity().sendSupportedChannels(); // CraftBukkit
+ // Akarin start - send multiple packets at once
+ /*
playerconnection.sendPacket(new PacketPlayOutCustomPayload(PacketPlayOutCustomPayload.a, (new PacketDataSerializer(Unpooled.buffer())).a(this.getServer().getServerModName())));
playerconnection.sendPacket(new PacketPlayOutServerDifficulty(worlddata.getDifficulty(), worlddata.isDifficultyLocked()));
playerconnection.sendPacket(new PacketPlayOutAbilities(entityplayer.abilities));
@@ -166,6 +168,17 @@ public abstract class PlayerList {
playerconnection.sendPacket(new PacketPlayOutRecipeUpdate(this.server.getCraftingManager().b()));
playerconnection.sendPacket(new PacketPlayOutTags(this.server.getTagRegistry()));
playerconnection.sendPacket(new PacketPlayOutEntityStatus(entityplayer, (byte) (worldserver.getGameRules().getBoolean(GameRules.REDUCED_DEBUG_INFO) ? 22 : 23))); // Paper - fix this rule not being initialized on the client
+ */
+ playerconnection.networkManager.sendPackets(
+ new PacketPlayOutCustomPayload(PacketPlayOutCustomPayload.a, (new PacketDataSerializer(Unpooled.buffer())).a(this.getServer().getServerModName())),
+ new PacketPlayOutServerDifficulty(worlddata.getDifficulty(), worlddata.isDifficultyLocked()),
+ new PacketPlayOutAbilities(entityplayer.abilities),
+ new PacketPlayOutHeldItemSlot(entityplayer.inventory.itemInHandIndex),
+ new PacketPlayOutRecipeUpdate(this.server.getCraftingManager().b()),
+ new PacketPlayOutTags(this.server.getTagRegistry()),
+ new PacketPlayOutEntityStatus(entityplayer, (byte) (worldserver.getGameRules().getBoolean(GameRules.REDUCED_DEBUG_INFO) ? 22 : 23))
+ );
+ // Akarin end
this.d(entityplayer);
entityplayer.getStatisticManager().c();
entityplayer.B().a(entityplayer);