From b27cddc14f014d5e500d9e610ff7ca54c1d07130 Mon Sep 17 00:00:00 2001 From: RaphiMC <50594595+RaphiMC@users.noreply.github.com> Date: Fri, 31 Mar 2023 19:04:44 +0200 Subject: [PATCH] Prevented concurrency issues --- .../task/TimeLockTask.java | 34 +++++--- .../task/AlphaInventoryUpdateTask.java | 86 ++++++++++--------- .../task/PlayerAirTimeUpdateTask.java | 45 +++++----- .../storage/BlockDigStorage.java | 5 +- .../task/BlockDigTickTask.java | 4 +- .../task/ClassicPingTask.java | 18 ++-- .../task/EntityTrackerTickTask.java | 4 +- 7 files changed, 109 insertions(+), 87 deletions(-) diff --git a/src/main/java/net/raphimc/vialegacy/protocols/alpha/protocola1_0_17_1_0_17_4toa1_0_16_2/task/TimeLockTask.java b/src/main/java/net/raphimc/vialegacy/protocols/alpha/protocola1_0_17_1_0_17_4toa1_0_16_2/task/TimeLockTask.java index ba041ab..b1cd7f2 100644 --- a/src/main/java/net/raphimc/vialegacy/protocols/alpha/protocola1_0_17_1_0_17_4toa1_0_16_2/task/TimeLockTask.java +++ b/src/main/java/net/raphimc/vialegacy/protocols/alpha/protocola1_0_17_1_0_17_4toa1_0_16_2/task/TimeLockTask.java @@ -21,6 +21,7 @@ import com.viaversion.viaversion.api.Via; import com.viaversion.viaversion.api.connection.UserConnection; import com.viaversion.viaversion.api.protocol.packet.PacketWrapper; import com.viaversion.viaversion.api.type.Type; +import net.raphimc.vialegacy.ViaLegacy; import net.raphimc.vialegacy.protocols.alpha.protocola1_0_17_1_0_17_4toa1_0_16_2.Protocola1_0_17_1_0_17_4toa1_0_16_2; import net.raphimc.vialegacy.protocols.alpha.protocola1_0_17_1_0_17_4toa1_0_16_2.storage.TimeLockStorage; import net.raphimc.vialegacy.protocols.alpha.protocola1_1_0_1_1_2_1toa1_0_17_1_0_17_4.ClientboundPacketsa1_0_17; @@ -28,6 +29,8 @@ import net.raphimc.vialegacy.protocols.release.protocol1_6_1to1_5_2.Protocol1_6_ import net.raphimc.vialegacy.protocols.release.protocol1_6_2to1_6_1.ClientboundPackets1_6_1; import net.raphimc.vialegacy.protocols.release.protocol1_7_2_5to1_6_4.storage.PlayerInfoStorage; +import java.util.logging.Level; + public class TimeLockTask implements Runnable { @Override @@ -36,22 +39,25 @@ public class TimeLockTask implements Runnable { final TimeLockStorage timeLockStorage = info.get(TimeLockStorage.class); final PlayerInfoStorage playerInfoStorage = info.get(PlayerInfoStorage.class); if (timeLockStorage != null && playerInfoStorage != null && playerInfoStorage.entityId != -1) { - try { - if (info.getProtocolInfo().getPipeline().contains(Protocol1_6_1to1_5_2.class)) { - if (timeLockStorage.getTime() == 0) { // 0 always does the daylight cycle - timeLockStorage.setTime(1); // Set it to 1 which is close enough + info.getChannel().eventLoop().submit(() -> { + try { + if (info.getProtocolInfo().getPipeline().contains(Protocol1_6_1to1_5_2.class)) { + if (timeLockStorage.getTime() == 0) { // 0 always does the daylight cycle + timeLockStorage.setTime(1); // Set it to 1 which is close enough + } + final PacketWrapper updateTime = PacketWrapper.create(ClientboundPackets1_6_1.TIME_UPDATE, info); + updateTime.write(Type.LONG, timeLockStorage.getTime()); // time + updateTime.write(Type.LONG, -(timeLockStorage.getTime() % 24000)); // time of day + updateTime.send(Protocol1_6_1to1_5_2.class); + } else { + final PacketWrapper updateTime = PacketWrapper.create(ClientboundPacketsa1_0_17.TIME_UPDATE, info); + updateTime.write(Type.LONG, timeLockStorage.getTime()); // time + updateTime.send(Protocola1_0_17_1_0_17_4toa1_0_16_2.class); } - final PacketWrapper updateTime = PacketWrapper.create(ClientboundPackets1_6_1.TIME_UPDATE, info); - updateTime.write(Type.LONG, timeLockStorage.getTime()); // time - updateTime.write(Type.LONG, -(timeLockStorage.getTime() % 24000)); // time of day - updateTime.send(Protocol1_6_1to1_5_2.class); - } else { - final PacketWrapper updateTime = PacketWrapper.create(ClientboundPacketsa1_0_17.TIME_UPDATE, info); - updateTime.write(Type.LONG, timeLockStorage.getTime()); // time - updateTime.send(Protocola1_0_17_1_0_17_4toa1_0_16_2.class); + } catch (Throwable e) { + ViaLegacy.getPlatform().getLogger().log(Level.WARNING, "Error sending time update", e); } - } catch (Throwable ignored) { - } + }); } } } diff --git a/src/main/java/net/raphimc/vialegacy/protocols/alpha/protocolb1_0_1_1_1toa1_2_3_5_1_2_6/task/AlphaInventoryUpdateTask.java b/src/main/java/net/raphimc/vialegacy/protocols/alpha/protocolb1_0_1_1_1toa1_2_3_5_1_2_6/task/AlphaInventoryUpdateTask.java index 620a0dd..f554e56 100644 --- a/src/main/java/net/raphimc/vialegacy/protocols/alpha/protocolb1_0_1_1_1toa1_2_3_5_1_2_6/task/AlphaInventoryUpdateTask.java +++ b/src/main/java/net/raphimc/vialegacy/protocols/alpha/protocolb1_0_1_1_1toa1_2_3_5_1_2_6/task/AlphaInventoryUpdateTask.java @@ -44,50 +44,52 @@ public class AlphaInventoryUpdateTask implements Runnable { final InventoryStorage inventoryStorage = info.get(InventoryStorage.class); if (inventoryStorage == null) continue; - try { - final Item[] mainInventory = fixItems(Via.getManager().getProviders().get(AlphaInventoryProvider.class).getMainInventoryItems(info)); - final Item[] craftingInventory = fixItems(Via.getManager().getProviders().get(AlphaInventoryProvider.class).getCraftingInventoryItems(info)); - final Item[] armorInventory = fixItems(Via.getManager().getProviders().get(AlphaInventoryProvider.class).getArmorInventoryItems(info)); - final Item handItem = fixItem(Via.getManager().getProviders().get(AlphaInventoryProvider.class).getHandItem(info)); + info.getChannel().eventLoop().submit(() -> { + try { + final Item[] mainInventory = fixItems(Via.getManager().getProviders().get(AlphaInventoryProvider.class).getMainInventoryItems(info)); + final Item[] craftingInventory = fixItems(Via.getManager().getProviders().get(AlphaInventoryProvider.class).getCraftingInventoryItems(info)); + final Item[] armorInventory = fixItems(Via.getManager().getProviders().get(AlphaInventoryProvider.class).getArmorInventoryItems(info)); + final Item handItem = fixItem(Via.getManager().getProviders().get(AlphaInventoryProvider.class).getHandItem(info)); - if (!Objects.equals(handItem, inventoryStorage.handItem)) { - final PacketWrapper heldItemChange = PacketWrapper.create(ServerboundPacketsb1_1.HELD_ITEM_CHANGE, info); - heldItemChange.write(Type.SHORT, inventoryStorage.selectedHotbarSlot); // slot - heldItemChange.sendToServer(Protocolb1_0_1_1_1toa1_2_3_5_1_2_6.class, false); + if (!Objects.equals(handItem, inventoryStorage.handItem)) { + final PacketWrapper heldItemChange = PacketWrapper.create(ServerboundPacketsb1_1.HELD_ITEM_CHANGE, info); + heldItemChange.write(Type.SHORT, inventoryStorage.selectedHotbarSlot); // slot + heldItemChange.sendToServer(Protocolb1_0_1_1_1toa1_2_3_5_1_2_6.class, false); + } + + final Item[] mergedMainInventory = copyItems(inventoryStorage.mainInventory); + final Item[] mergedCraftingInventory = copyItems(inventoryStorage.craftingInventory); + final Item[] mergedArmorInventory = copyItems(inventoryStorage.armorInventory); + System.arraycopy(mainInventory, 0, mergedMainInventory, 0, mainInventory.length); + System.arraycopy(craftingInventory, 0, mergedCraftingInventory, 0, craftingInventory.length); + System.arraycopy(armorInventory, 0, mergedArmorInventory, 0, armorInventory.length); + + boolean hasChanged = !Arrays.equals(mergedMainInventory, inventoryStorage.mainInventory) || !Arrays.equals(mergedCraftingInventory, inventoryStorage.craftingInventory) || !Arrays.equals(mergedArmorInventory, inventoryStorage.armorInventory); + if (!hasChanged) return; + + inventoryStorage.mainInventory = copyItems(mergedMainInventory); + inventoryStorage.craftingInventory = copyItems(mergedCraftingInventory); + inventoryStorage.armorInventory = copyItems(mergedArmorInventory); + + final PacketWrapper mainContent = PacketWrapper.create(ServerboundPacketsa1_2_6.PLAYER_INVENTORY, info); + mainContent.write(Type.INT, -1); // type + mainContent.write(Types1_4_2.NBTLESS_ITEM_ARRAY, mergedMainInventory); // items + + final PacketWrapper craftingContent = PacketWrapper.create(ServerboundPacketsa1_2_6.PLAYER_INVENTORY, info); + craftingContent.write(Type.INT, -2); // type + craftingContent.write(Types1_4_2.NBTLESS_ITEM_ARRAY, mergedCraftingInventory); // items + + final PacketWrapper armorContent = PacketWrapper.create(ServerboundPacketsa1_2_6.PLAYER_INVENTORY, info); + armorContent.write(Type.INT, -3); // type + armorContent.write(Types1_4_2.NBTLESS_ITEM_ARRAY, mergedArmorInventory); // items + + mainContent.sendToServer(Protocolb1_0_1_1_1toa1_2_3_5_1_2_6.class); + craftingContent.sendToServer(Protocolb1_0_1_1_1toa1_2_3_5_1_2_6.class); + armorContent.sendToServer(Protocolb1_0_1_1_1toa1_2_3_5_1_2_6.class); + } catch (Throwable e) { + ViaLegacy.getPlatform().getLogger().log(Level.WARNING, "Error sending inventory update packets", e); } - - final Item[] mergedMainInventory = copyItems(inventoryStorage.mainInventory); - final Item[] mergedCraftingInventory = copyItems(inventoryStorage.craftingInventory); - final Item[] mergedArmorInventory = copyItems(inventoryStorage.armorInventory); - System.arraycopy(mainInventory, 0, mergedMainInventory, 0, mainInventory.length); - System.arraycopy(craftingInventory, 0, mergedCraftingInventory, 0, craftingInventory.length); - System.arraycopy(armorInventory, 0, mergedArmorInventory, 0, armorInventory.length); - - boolean hasChanged = !Arrays.equals(mergedMainInventory, inventoryStorage.mainInventory) || !Arrays.equals(mergedCraftingInventory, inventoryStorage.craftingInventory) || !Arrays.equals(mergedArmorInventory, inventoryStorage.armorInventory); - if (!hasChanged) continue; - - inventoryStorage.mainInventory = copyItems(mergedMainInventory); - inventoryStorage.craftingInventory = copyItems(mergedCraftingInventory); - inventoryStorage.armorInventory = copyItems(mergedArmorInventory); - - final PacketWrapper mainContent = PacketWrapper.create(ServerboundPacketsa1_2_6.PLAYER_INVENTORY, info); - mainContent.write(Type.INT, -1); // type - mainContent.write(Types1_4_2.NBTLESS_ITEM_ARRAY, mergedMainInventory); // items - - final PacketWrapper craftingContent = PacketWrapper.create(ServerboundPacketsa1_2_6.PLAYER_INVENTORY, info); - craftingContent.write(Type.INT, -2); // type - craftingContent.write(Types1_4_2.NBTLESS_ITEM_ARRAY, mergedCraftingInventory); // items - - final PacketWrapper armorContent = PacketWrapper.create(ServerboundPacketsa1_2_6.PLAYER_INVENTORY, info); - armorContent.write(Type.INT, -3); // type - armorContent.write(Types1_4_2.NBTLESS_ITEM_ARRAY, mergedArmorInventory); // items - - mainContent.sendToServer(Protocolb1_0_1_1_1toa1_2_3_5_1_2_6.class); - craftingContent.sendToServer(Protocolb1_0_1_1_1toa1_2_3_5_1_2_6.class); - armorContent.sendToServer(Protocolb1_0_1_1_1toa1_2_3_5_1_2_6.class); - } catch (Throwable e) { - ViaLegacy.getPlatform().getLogger().log(Level.WARNING, "Error sending inventory update packets", e); - } + }); } } diff --git a/src/main/java/net/raphimc/vialegacy/protocols/beta/protocol1_0_0_1tob1_8_0_1/task/PlayerAirTimeUpdateTask.java b/src/main/java/net/raphimc/vialegacy/protocols/beta/protocol1_0_0_1tob1_8_0_1/task/PlayerAirTimeUpdateTask.java index eae822b..a18743e 100644 --- a/src/main/java/net/raphimc/vialegacy/protocols/beta/protocol1_0_0_1tob1_8_0_1/task/PlayerAirTimeUpdateTask.java +++ b/src/main/java/net/raphimc/vialegacy/protocols/beta/protocol1_0_0_1tob1_8_0_1/task/PlayerAirTimeUpdateTask.java @@ -23,6 +23,7 @@ import com.viaversion.viaversion.api.connection.UserConnection; import com.viaversion.viaversion.api.minecraft.metadata.Metadata; import com.viaversion.viaversion.api.protocol.packet.PacketWrapper; import com.viaversion.viaversion.api.type.Type; +import net.raphimc.vialegacy.ViaLegacy; import net.raphimc.vialegacy.api.data.BlockList1_6; import net.raphimc.vialegacy.api.model.IdAndData; import net.raphimc.vialegacy.protocols.beta.protocol1_0_0_1tob1_8_0_1.Protocol1_0_0_1tob1_8_0_1; @@ -33,6 +34,8 @@ import net.raphimc.vialegacy.protocols.release.protocol1_4_2to1_3_1_2.types.Type import net.raphimc.vialegacy.protocols.release.protocol1_7_2_5to1_6_4.storage.ChunkTracker; import net.raphimc.vialegacy.protocols.release.protocol1_7_2_5to1_6_4.storage.PlayerInfoStorage; +import java.util.logging.Level; + public class PlayerAirTimeUpdateTask implements Runnable { @Override @@ -42,30 +45,32 @@ public class PlayerAirTimeUpdateTask implements Runnable { if (playerAirTimeStorage != null) { final PlayerInfoStorage playerInfoStorage = info.get(PlayerInfoStorage.class); if (playerInfoStorage == null) continue; - final IdAndData headBlock = info.get(ChunkTracker.class).getBlockNotNull(floor(playerInfoStorage.posX), floor(playerInfoStorage.posY + 1.62F), floor(playerInfoStorage.posZ)); - if (headBlock.id == BlockList1_6.waterMoving.blockID || headBlock.id == BlockList1_6.waterStill.blockID) { - playerAirTimeStorage.sentPacket = false; - playerAirTimeStorage.air--; - if (playerAirTimeStorage.air < 0) playerAirTimeStorage.air = 0; - this.sendAirTime(playerInfoStorage, playerAirTimeStorage, info); - } else if (!playerAirTimeStorage.sentPacket) { - playerAirTimeStorage.sentPacket = true; - playerAirTimeStorage.air = playerAirTimeStorage.MAX_AIR; - this.sendAirTime(playerInfoStorage, playerAirTimeStorage, info); - } + info.getChannel().eventLoop().submit(() -> { + try { + final IdAndData headBlock = info.get(ChunkTracker.class).getBlockNotNull(floor(playerInfoStorage.posX), floor(playerInfoStorage.posY + 1.62F), floor(playerInfoStorage.posZ)); + if (headBlock.id == BlockList1_6.waterMoving.blockID || headBlock.id == BlockList1_6.waterStill.blockID) { + playerAirTimeStorage.sentPacket = false; + playerAirTimeStorage.air--; + if (playerAirTimeStorage.air < 0) playerAirTimeStorage.air = 0; + this.sendAirTime(playerInfoStorage, playerAirTimeStorage, info); + } else if (!playerAirTimeStorage.sentPacket) { + playerAirTimeStorage.sentPacket = true; + playerAirTimeStorage.air = playerAirTimeStorage.MAX_AIR; + this.sendAirTime(playerInfoStorage, playerAirTimeStorage, info); + } + } catch (Throwable e) { + ViaLegacy.getPlatform().getLogger().log(Level.WARNING, "Error updating air time", e); + } + }); } } } - private void sendAirTime(final PlayerInfoStorage playerInfoStorage, final PlayerAirTimeStorage playerAirTimeStorage, final UserConnection userConnection) { - try { - final PacketWrapper updateAirTime = PacketWrapper.create(ClientboundPackets1_0.ENTITY_METADATA, userConnection); - updateAirTime.write(Type.INT, playerInfoStorage.entityId); // entity id - updateAirTime.write(Types1_3_1.METADATA_LIST, Lists.newArrayList(new Metadata(1, MetaType1_3_1.Short, Integer.valueOf(playerAirTimeStorage.air).shortValue()))); // metadata - updateAirTime.send(Protocol1_0_0_1tob1_8_0_1.class); - } catch (Throwable e) { - e.printStackTrace(); - } + private void sendAirTime(final PlayerInfoStorage playerInfoStorage, final PlayerAirTimeStorage playerAirTimeStorage, final UserConnection userConnection) throws Exception { + final PacketWrapper updateAirTime = PacketWrapper.create(ClientboundPackets1_0.ENTITY_METADATA, userConnection); + updateAirTime.write(Type.INT, playerInfoStorage.entityId); // entity id + updateAirTime.write(Types1_3_1.METADATA_LIST, Lists.newArrayList(new Metadata(1, MetaType1_3_1.Short, Integer.valueOf(playerAirTimeStorage.air).shortValue()))); // metadata + updateAirTime.send(Protocol1_0_0_1tob1_8_0_1.class); } private static int floor(double f) { diff --git a/src/main/java/net/raphimc/vialegacy/protocols/beta/protocolb1_3_0_1tob1_2_0_2/storage/BlockDigStorage.java b/src/main/java/net/raphimc/vialegacy/protocols/beta/protocolb1_3_0_1tob1_2_0_2/storage/BlockDigStorage.java index 8c36f83..32430fc 100644 --- a/src/main/java/net/raphimc/vialegacy/protocols/beta/protocolb1_3_0_1tob1_2_0_2/storage/BlockDigStorage.java +++ b/src/main/java/net/raphimc/vialegacy/protocols/beta/protocolb1_3_0_1tob1_2_0_2/storage/BlockDigStorage.java @@ -20,8 +20,11 @@ package net.raphimc.vialegacy.protocols.beta.protocolb1_3_0_1tob1_2_0_2.storage; import com.viaversion.viaversion.api.connection.StoredObject; import com.viaversion.viaversion.api.connection.UserConnection; import com.viaversion.viaversion.api.minecraft.Position; +import net.raphimc.vialegacy.ViaLegacy; import net.raphimc.vialegacy.protocols.beta.protocolb1_3_0_1tob1_2_0_2.Protocolb1_3_0_1tob1_2_0_2; +import java.util.logging.Level; + public class BlockDigStorage extends StoredObject { public int tick = 1; @@ -44,7 +47,7 @@ public class BlockDigStorage extends StoredObject { } Protocolb1_3_0_1tob1_2_0_2.sendBlockDigPacket(this.getUser(), (byte) 1, position, facing); } catch (Throwable e) { - e.printStackTrace(); + ViaLegacy.getPlatform().getLogger().log(Level.WARNING, "Error while ticking BlockDigStorage", e); } } diff --git a/src/main/java/net/raphimc/vialegacy/protocols/beta/protocolb1_3_0_1tob1_2_0_2/task/BlockDigTickTask.java b/src/main/java/net/raphimc/vialegacy/protocols/beta/protocolb1_3_0_1tob1_2_0_2/task/BlockDigTickTask.java index c7b41e6..809a3f5 100644 --- a/src/main/java/net/raphimc/vialegacy/protocols/beta/protocolb1_3_0_1tob1_2_0_2/task/BlockDigTickTask.java +++ b/src/main/java/net/raphimc/vialegacy/protocols/beta/protocolb1_3_0_1tob1_2_0_2/task/BlockDigTickTask.java @@ -27,7 +27,9 @@ public class BlockDigTickTask implements Runnable { public void run() { for (UserConnection info : Via.getManager().getConnectionManager().getConnections()) { final BlockDigStorage blockDigStorage = info.get(BlockDigStorage.class); - if (blockDigStorage != null) blockDigStorage.tick(); + if (blockDigStorage != null) { + info.getChannel().eventLoop().submit(blockDigStorage::tick); + } } } diff --git a/src/main/java/net/raphimc/vialegacy/protocols/classic/protocolc0_28_30toc0_28_30cpe/task/ClassicPingTask.java b/src/main/java/net/raphimc/vialegacy/protocols/classic/protocolc0_28_30toc0_28_30cpe/task/ClassicPingTask.java index a819b35..5737f90 100644 --- a/src/main/java/net/raphimc/vialegacy/protocols/classic/protocolc0_28_30toc0_28_30cpe/task/ClassicPingTask.java +++ b/src/main/java/net/raphimc/vialegacy/protocols/classic/protocolc0_28_30toc0_28_30cpe/task/ClassicPingTask.java @@ -38,14 +38,16 @@ public class ClassicPingTask implements Runnable { final ExtensionProtocolMetadataStorage protocolMetadata = info.get(ExtensionProtocolMetadataStorage.class); if (protocolMetadata == null) continue; if (!protocolMetadata.hasServerExtension(ClassicProtocolExtension.TWO_WAY_PING, 1)) continue; - try { - final PacketWrapper pingRequest = PacketWrapper.create(ServerboundPacketsc0_30cpe.EXT_TWO_WAY_PING, info); - pingRequest.write(Type.BYTE, (byte) 0); // direction - pingRequest.write(Type.SHORT, (short) (ThreadLocalRandom.current().nextInt() % Short.MAX_VALUE)); // data - pingRequest.sendToServer(Protocolc0_30toc0_30cpe.class); - } catch (Throwable e) { - ViaLegacy.getPlatform().getLogger().log(Level.WARNING, "Error sending TwoWayPing extension ping packet", e); - } + info.getChannel().eventLoop().submit(() -> { + try { + final PacketWrapper pingRequest = PacketWrapper.create(ServerboundPacketsc0_30cpe.EXT_TWO_WAY_PING, info); + pingRequest.write(Type.BYTE, (byte) 0); // direction + pingRequest.write(Type.SHORT, (short) (ThreadLocalRandom.current().nextInt() % Short.MAX_VALUE)); // data + pingRequest.sendToServer(Protocolc0_30toc0_30cpe.class); + } catch (Throwable e) { + ViaLegacy.getPlatform().getLogger().log(Level.WARNING, "Error sending TwoWayPing extension ping packet", e); + } + }); } } diff --git a/src/main/java/net/raphimc/vialegacy/protocols/release/protocol1_3_1_2to1_2_4_5/task/EntityTrackerTickTask.java b/src/main/java/net/raphimc/vialegacy/protocols/release/protocol1_3_1_2to1_2_4_5/task/EntityTrackerTickTask.java index 5135ca7..cd85d65 100644 --- a/src/main/java/net/raphimc/vialegacy/protocols/release/protocol1_3_1_2to1_2_4_5/task/EntityTrackerTickTask.java +++ b/src/main/java/net/raphimc/vialegacy/protocols/release/protocol1_3_1_2to1_2_4_5/task/EntityTrackerTickTask.java @@ -27,7 +27,9 @@ public class EntityTrackerTickTask implements Runnable { public void run() { for (UserConnection info : Via.getManager().getConnectionManager().getConnections()) { final EntityTracker entityTracker = info.get(EntityTracker.class); - if (entityTracker != null) entityTracker.tick(); + if (entityTracker != null) { + info.getChannel().eventLoop().submit(entityTracker::tick); + } } }