Paper/CraftBukkit-Patches/0120-Remove-the-lastChunkAccessed-if-it-is-unloaded.patch

61 lines
3.2 KiB
Diff
Raw Normal View History

2014-03-27 04:34:47 +08:00
From b3502d90dfb5e97bde75acca10428ca5a0c225c8 Mon Sep 17 00:00:00 2001
From: Thinkofdeath <thethinkofdeath@gmail.com>
Date: Tue, 18 Mar 2014 09:49:30 +0000
Subject: [PATCH] Remove the lastChunkAccessed if it is unloaded.
This fixes an issue where a chunk would be unloaded but remain in lastChunkAccessed meaning calls on getChunkAt could return a chunk that is no longer loaded, this caused an issue where the chunk could be reloaded whilst in use reverting any block changes. This caused findEndPortal to return null even after createEndPortal which would crash the server trying to teleport to a null location.
diff --git a/src/main/java/net/minecraft/server/ChunkProviderServer.java b/src/main/java/net/minecraft/server/ChunkProviderServer.java
2014-03-23 08:06:43 +08:00
index 7f19bec..a9ef533 100644
--- a/src/main/java/net/minecraft/server/ChunkProviderServer.java
+++ b/src/main/java/net/minecraft/server/ChunkProviderServer.java
2014-03-23 08:06:43 +08:00
@@ -315,6 +315,13 @@ public class ChunkProviderServer implements IChunkProvider {
long chunkcoordinates = this.unloadQueue.popFirst();
Chunk chunk = this.chunks.get(chunkcoordinates);
if (chunk == null) continue;
+ // Spigot start - Remove the chunk from the cache if it is unloaded
+ Chunk result = world.lastChunkAccessed;
+ if ( result != null && result.locX == chunk.locX && result.locZ == chunk.locZ )
+ {
+ world.lastChunkAccessed = null;
+ }
+ // Spigot end
ChunkUnloadEvent event = new ChunkUnloadEvent(chunk.bukkitChunk);
server.getPluginManager().callEvent(event);
diff --git a/src/main/java/net/minecraft/server/World.java b/src/main/java/net/minecraft/server/World.java
2014-03-27 04:34:47 +08:00
index 2f9f300..7529e0c 100644
--- a/src/main/java/net/minecraft/server/World.java
+++ b/src/main/java/net/minecraft/server/World.java
2014-03-23 08:06:43 +08:00
@@ -153,7 +153,7 @@ public abstract class World implements IBlockAccess {
public boolean pvpMode;
public boolean keepSpawnInMemory = true;
public ChunkGenerator generator;
- Chunk lastChunkAccessed;
+ public Chunk lastChunkAccessed; // Spigot - Make public
int lastXAccessed = Integer.MIN_VALUE;
int lastZAccessed = Integer.MIN_VALUE;
final Object chunkLock = new Object();
diff --git a/src/main/java/org/bukkit/craftbukkit/CraftWorld.java b/src/main/java/org/bukkit/craftbukkit/CraftWorld.java
2014-03-27 04:34:47 +08:00
index 154b868..8592205 100644
--- a/src/main/java/org/bukkit/craftbukkit/CraftWorld.java
+++ b/src/main/java/org/bukkit/craftbukkit/CraftWorld.java
@@ -187,6 +187,14 @@ public class CraftWorld implements World {
world.chunkProviderServer.saveChunkNOP(chunk);
}
+ // Spigot start - Remove the chunk from the cache if it is unloaded
+ net.minecraft.server.Chunk result = world.lastChunkAccessed;
+ if ( result != null && result.locX == chunk.locX && result.locZ == chunk.locZ )
+ {
+ world.lastChunkAccessed = null;
+ }
+ // Spigot end
+
world.chunkProviderServer.unloadQueue.remove(x, z);
world.chunkProviderServer.chunks.remove(LongHash.toLong(x, z));
--
1.8.5.2.msysgit.0