Paper/patches/server/0865-Fix-swamp-hut-cat-generation-deadlock.patch
Nassim Jahnke 385f313a8b
Updated Upstream (Bukkit/CraftBukkit/Spigot) (#8092)
Upstream has released updates that appear to apply and compile correctly.
This update has not been tested by PaperMC and as with ANY update, please do your own testing

Bukkit Changes:
d41796de SPIGOT-7071: Add Player#stopSound(SoundCategory category)
61dae5b2 SPIGOT-7011, SPIGOT-7065: Overhaul of structures

CraftBukkit Changes:
991aeda12 SPIGOT-1729, SPIGOT-7090: Keep precision in teleportation between worlds
5c9a5f628 SPIGOT-7071: Add Player#stopSound(SoundCategory category)
68f888ded SPIGOT-7011, SPIGOT-7065: Overhaul of structures
0231a3746 Remove outdated build delay.

Spigot Changes:
475f6008 Rebuild patches
8ce1761f Rebuild patches
2022-07-04 16:38:06 +02:00

63 lines
3.6 KiB
Diff

From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
From: Spottedleaf <Spottedleaf@users.noreply.github.com>
Date: Sat, 12 Mar 2022 06:31:13 -0800
Subject: [PATCH] Fix swamp hut cat generation deadlock
The worldgen thread will attempt to get structure references
via the world's getChunkAt method, which is fine if the gen is
not cancelled - but if the chunk was unloaded, the call will block
indefinitely. Instead of using the world state, we use the already
supplied ServerLevelAccessor which will always have the chunk available.
diff --git a/src/main/java/net/minecraft/world/entity/animal/Cat.java b/src/main/java/net/minecraft/world/entity/animal/Cat.java
index 5ad968a2f1add27da0d6a858e683d5d771128092..e44352857272a2a4027c67bd25a28a9498b7bb49 100644
--- a/src/main/java/net/minecraft/world/entity/animal/Cat.java
+++ b/src/main/java/net/minecraft/world/entity/animal/Cat.java
@@ -361,7 +361,7 @@ public class Cat extends TamableAnimal {
});
ServerLevel worldserver = world.getLevel();
- if (worldserver.structureManager().getStructureWithPieceAt(this.blockPosition(), StructureTags.CATS_SPAWN_AS_BLACK).isValid()) {
+ if (worldserver.structureManager().getStructureWithPieceAt(this.blockPosition(), StructureTags.CATS_SPAWN_AS_BLACK, world).isValid()) { // Paper - fix deadlock
this.setCatVariant(CatVariant.ALL_BLACK);
this.setPersistenceRequired();
}
diff --git a/src/main/java/net/minecraft/world/level/StructureManager.java b/src/main/java/net/minecraft/world/level/StructureManager.java
index 21afcbc71fdb10994f2f3451f5b06e4bb75c60c7..bca1e39da66a889caf92c28b6348623a440e1c7f 100644
--- a/src/main/java/net/minecraft/world/level/StructureManager.java
+++ b/src/main/java/net/minecraft/world/level/StructureManager.java
@@ -43,7 +43,12 @@ public class StructureManager {
}
public List<StructureStart> startsForStructure(ChunkPos chunkPos, Predicate<Structure> predicate) {
- Map<Structure, LongSet> map = this.level.getChunk(chunkPos.x, chunkPos.z, ChunkStatus.STRUCTURE_REFERENCES).getAllReferences();
+ // Paper start
+ return this.startsForStructure(chunkPos, predicate, null);
+ }
+ public List<StructureStart> startsForStructure(ChunkPos chunkPos, Predicate<Structure> predicate, @Nullable ServerLevelAccessor levelAccessor) {
+ // Paper end
+ Map<Structure, LongSet> map = (levelAccessor == null ? this.level : levelAccessor).getChunk(chunkPos.x, chunkPos.z, ChunkStatus.STRUCTURE_REFERENCES).getAllReferences();
ImmutableList.Builder<StructureStart> builder = ImmutableList.builder();
for(Map.Entry<Structure, LongSet> entry : map.entrySet()) {
@@ -107,13 +112,18 @@ public class StructureManager {
}
public StructureStart getStructureWithPieceAt(BlockPos pos, TagKey<Structure> structureTag) {
+ // Paper start
+ return this.getStructureWithPieceAt(pos, structureTag, null);
+ }
+ public StructureStart getStructureWithPieceAt(BlockPos pos, TagKey<Structure> structureTag, @Nullable ServerLevelAccessor levelAccessor) {
+ // Paper end
Registry<Structure> registry = this.registryAccess().registryOrThrow(Registry.STRUCTURE_REGISTRY);
for(StructureStart structureStart : this.startsForStructure(new ChunkPos(pos), (structure) -> {
return registry.getHolder(registry.getId(structure)).map((holder) -> {
return holder.is(structureTag);
}).orElse(false);
- })) {
+ }, levelAccessor)) { // Paper
if (this.structureHasPieceAt(pos, structureStart)) {
return structureStart;
}