2017-08-12 06:59:44 +08:00
From f2bcb786e5eed44c74b3ebc8573f5735e589cd6d Mon Sep 17 00:00:00 2001
2017-08-10 07:11:57 +08:00
From: mezz <tehgeek@gmail.com>
Date: Wed, 9 Aug 2017 17:51:22 -0500
Subject: [PATCH] Fix MC-117075: TE Unload Lag Spike
diff --git a/src/main/java/net/minecraft/server/Chunk.java b/src/main/java/net/minecraft/server/Chunk.java
index ed595955..228792fa 100644
--- a/src/main/java/net/minecraft/server/Chunk.java
+++ b/src/main/java/net/minecraft/server/Chunk.java
@@ -823,6 +823,9 @@ public class Chunk {
public void removeEntities() {
this.j = false;
+ // Paper start - Fix MC-117075: TE Unload Lag Spike
+ this.world.markTileEntitiesForRemoval(this);
+ /*
Iterator iterator = this.tileEntities.values().iterator();
while (iterator.hasNext()) {
@@ -842,6 +845,8 @@ public class Chunk {
this.world.b(tileentity);
}
+ */
+ // Paper end
List[] aentityslice = this.entitySlices; // Spigot
int i = aentityslice.length;
diff --git a/src/main/java/net/minecraft/server/ChunkCoordIntPair.java b/src/main/java/net/minecraft/server/ChunkCoordIntPair.java
index 23944088..e8d1a1c6 100644
--- a/src/main/java/net/minecraft/server/ChunkCoordIntPair.java
+++ b/src/main/java/net/minecraft/server/ChunkCoordIntPair.java
@@ -15,6 +15,7 @@ public class ChunkCoordIntPair {
this.z = blockposition.getZ() >> 4;
}
+ public static long asLong(int x, int z) { return a(x, z); } // Paper - OBFHELPER
public static long a(int i, int j) {
return (long) i & 4294967295L | ((long) j & 4294967295L) << 32;
}
diff --git a/src/main/java/net/minecraft/server/World.java b/src/main/java/net/minecraft/server/World.java
2017-08-12 06:59:44 +08:00
index 12938b9f..e4fd7fa7 100644
2017-08-10 07:11:57 +08:00
--- a/src/main/java/net/minecraft/server/World.java
+++ b/src/main/java/net/minecraft/server/World.java
@@ -147,6 +147,7 @@ public abstract class World implements IBlockAccess {
private org.spigotmc.TickLimiter tileLimiter;
private int tileTickPosition;
public final Map<Explosion.CacheKey, Float> explosionDensityCache = new HashMap<>(); // Paper - Optimize explosions
+ private it.unimi.dsi.fastutil.longs.LongCollection tileEntitiesChunkToBeRemoved = new it.unimi.dsi.fastutil.longs.LongOpenHashSet(); // Paper - Fix MC-117075: TE Unload Lag Spike
public CraftWorld getWorld() {
return this.world;
@@ -1581,6 +1582,7 @@ public abstract class World implements IBlockAccess {
this.tileEntityListUnload.clear();
}
// CraftBukkit end
+ this.removeTileEntitiesForRemovedChunks(); // Paper - Fix MC-117075: TE Unload Lag Spike
// Spigot start
// Iterator iterator = this.tileEntityListTick.iterator();
2017-08-12 06:59:44 +08:00
@@ -3261,4 +3263,40 @@ public abstract class World implements IBlockAccess {
2017-08-10 07:11:57 +08:00
public BlockPosition a(String s, BlockPosition blockposition, boolean flag) {
return null;
}
+
+ // Paper start - Fix MC-117075: TE Unload Lag Spike
+ public void markTileEntitiesForRemoval(Chunk chunk) {
+ if (!chunk.getTileEntities().isEmpty()) {
+ long pos = net.minecraft.server.ChunkCoordIntPair.asLong(chunk.locX, chunk.locZ);
+ this.tileEntitiesChunkToBeRemoved.add(pos);
+ }
+ }
+
+ private void removeTileEntitiesForRemovedChunks() {
+ if (!this.tileEntitiesChunkToBeRemoved.isEmpty()) {
2017-08-12 06:59:44 +08:00
+ java.util.function.Predicate<TileEntity> isInChunkOrNull = (tileEntity) -> {
+ if (tileEntity == null) {
+ return true;
+ }
+
2017-08-10 07:11:57 +08:00
+ BlockPosition tilePos = tileEntity.getPosition();
+ long tileChunkPos = net.minecraft.server.ChunkCoordIntPair.asLong(tilePos.getX() >> 4, tilePos.getZ() >> 4);
+ final boolean willRemove = this.tileEntitiesChunkToBeRemoved.contains(tileChunkPos);
+ // Brought over from Chunk#removeEntities
+ if (willRemove && tileEntity instanceof IInventory) {
+ for (org.bukkit.entity.HumanEntity human : Lists.newArrayList(((IInventory) tileEntity).getViewers())) {
+ if (human instanceof org.bukkit.craftbukkit.entity.CraftHumanEntity) {
+ ((org.bukkit.craftbukkit.entity.CraftHumanEntity) human).getHandle().closeInventory();
+ }
+ }
+ }
+
+ return willRemove;
+ };
+
2017-08-12 06:59:44 +08:00
+ this.tileEntityListTick.removeIf(isInChunkOrNull);
2017-08-10 07:11:57 +08:00
+ this.tileEntitiesChunkToBeRemoved.clear();
+ }
+ }
+ // Paper end
}
--
2017-08-12 06:59:44 +08:00
2.14.1
2017-08-10 07:11:57 +08:00