9
0
mirror of https://github.com/Winds-Studio/Leaf.git synced 2025-12-19 15:09:25 +00:00

Fix PWT deadlock with WorldGuard dragon egg teleportation (#506)

Fixes https://github.com/Winds-Studio/Leaf/issues/502
This commit is contained in:
MrlingXD
2025-10-13 11:38:44 +08:00
committed by GitHub
parent 92dbf8e033
commit 667f15c124
2 changed files with 53 additions and 38 deletions

View File

@@ -423,7 +423,7 @@ index eaaa66c4d86d4ebda0acf8f1dbe8ecb55aa28285..3a6c894178829cec8daa08ea9f0294f7
continue;
}
diff --git a/net/minecraft/server/level/ServerLevel.java b/net/minecraft/server/level/ServerLevel.java
index 30bb5b9d021d01dea272313763b0748856ce28a6..bfb4ea9d597b5f480ca0b7c095edf5090b84211c 100644
index 06294e4036991a803deefc20e35160c5ff76a81b..8f93d8887d1e0ee8d27d0ead8e733cf7fa5d719d 100644
--- a/net/minecraft/server/level/ServerLevel.java
+++ b/net/minecraft/server/level/ServerLevel.java
@@ -180,7 +180,7 @@ public class ServerLevel extends Level implements ServerEntityGetter, WorldGenLe
@@ -523,7 +523,7 @@ index 30bb5b9d021d01dea272313763b0748856ce28a6..bfb4ea9d597b5f480ca0b7c095edf509
+ }
+
+ // Executes the actual read operation based on the request type
+ private Object executeReadRequest(org.dreeam.leaf.async.world.WorldReadRequest request) {
+ public Object executeReadRequest(org.dreeam.leaf.async.world.WorldReadRequest request) {
+ Object[] params = request.params();
+ BlockPos pos; // Declare pos outside the switch
+
@@ -858,7 +858,7 @@ index f9e7532f86122a379692561a639a209a126e8bba..fab317d6c9a1c914f19bae11846cb576
if (isLocatorBarEnabledFor(player)) {
if (!connection.isBroken()) {
diff --git a/net/minecraft/world/entity/Entity.java b/net/minecraft/world/entity/Entity.java
index 67556752551e1d30519e2533543de9b04342420b..45bc4aa35fda48c816e08ec8bacfb11a5c792b27 100644
index c18f6f3f8307ae1d221a38cd1dc2191cdc4e767a..1bb78f90f9bfc58f39f21605d1e4e45680fdd41b 100644
--- a/net/minecraft/world/entity/Entity.java
+++ b/net/minecraft/world/entity/Entity.java
@@ -3476,15 +3476,40 @@ public abstract class Entity implements SyncedDataHolder, Nameable, EntityAccess

View File

@@ -5,6 +5,8 @@ Subject: [PATCH] SparklyPaper: Parallel world ticking
Original project: https://github.com/SparklyPower/SparklyPaper
Co-authored-by: MrlingXD <90316914+wling-art@users.noreply.github.com>
diff --git a/src/main/java/ca/spottedleaf/moonrise/common/util/TickThread.java b/src/main/java/ca/spottedleaf/moonrise/common/util/TickThread.java
index 69cdd304d255d52c9b7dc9b6a33ffdb630b79abe..09dfab1ace05ee62df5cf6e292f8be0146e85a36 100644
--- a/src/main/java/ca/spottedleaf/moonrise/common/util/TickThread.java
@@ -337,10 +339,10 @@ index 61121d2efd0df2fcafdc4c272e1cd1b986f42e24..ee5f342995a335593932a497c2bafd36
}
// Paper end
diff --git a/src/main/java/org/bukkit/craftbukkit/block/CraftBlock.java b/src/main/java/org/bukkit/craftbukkit/block/CraftBlock.java
index dd122bbbe2c33183017dbde6997d3f1cd08479b5..d164d50bcee7281283c6d9a7b85ee2596d89bcd1 100644
index dd122bbbe2c33183017dbde6997d3f1cd08479b5..d447b4180f8db81dd28a34cd60cec2ad36c6b641 100644
--- a/src/main/java/org/bukkit/craftbukkit/block/CraftBlock.java
+++ b/src/main/java/org/bukkit/craftbukkit/block/CraftBlock.java
@@ -74,12 +74,97 @@ public class CraftBlock implements Block {
@@ -74,12 +74,109 @@ public class CraftBlock implements Block {
return new CraftBlock(world, position);
}
@@ -367,6 +369,18 @@ index dd122bbbe2c33183017dbde6997d3f1cd08479b5..d164d50bcee7281283c6d9a7b85ee259
+ return defaultValue;
+ }
+
+ // Leaf start - SparklyPaper - parallel world ticking - Deadlock prevention
+ if (Thread.currentThread() instanceof ca.spottedleaf.moonrise.common.util.TickThread.ServerLevelTickThread) {
+ try {
+ org.dreeam.leaf.async.world.WorldReadRequest request = new org.dreeam.leaf.async.world.WorldReadRequest(type, params, null);
+ Object result = level.executeReadRequest(request);
+ return (T) result;
+ } catch (Exception e) {
+ return defaultValue;
+ }
+ }
+ // Leaf end - SparklyPaper - parallel world ticking - Deadlock prevention
+
+ java.util.concurrent.CompletableFuture<Object> future = new java.util.concurrent.CompletableFuture<>();
+
+ // Leaf start - SparklyPaper - parallel world ticking - Shutdown handling for async reads
@@ -440,7 +454,7 @@ index dd122bbbe2c33183017dbde6997d3f1cd08479b5..d164d50bcee7281283c6d9a7b85ee259
}
public BlockPos getPosition() {
@@ -142,10 +227,12 @@ public class CraftBlock implements Block {
@@ -142,10 +239,12 @@ public class CraftBlock implements Block {
return this.getWorld().getChunkAt(this);
}
@@ -453,7 +467,7 @@ index dd122bbbe2c33183017dbde6997d3f1cd08479b5..d164d50bcee7281283c6d9a7b85ee259
public void setData(final byte data, boolean applyPhysics) {
if (applyPhysics) {
this.setData(data, net.minecraft.world.level.block.Block.UPDATE_ALL);
@@ -155,12 +242,18 @@ public class CraftBlock implements Block {
@@ -155,12 +254,18 @@ public class CraftBlock implements Block {
}
private void setData(final byte data, int flags) {
@@ -473,7 +487,7 @@ index dd122bbbe2c33183017dbde6997d3f1cd08479b5..d164d50bcee7281283c6d9a7b85ee259
return CraftMagicNumbers.toLegacyData(state);
}
@@ -177,6 +270,7 @@ public class CraftBlock implements Block {
@@ -177,6 +282,7 @@ public class CraftBlock implements Block {
@Override
public void setType(Material type, boolean applyPhysics) {
Preconditions.checkArgument(type != null, "Material cannot be null");
@@ -481,7 +495,7 @@ index dd122bbbe2c33183017dbde6997d3f1cd08479b5..d164d50bcee7281283c6d9a7b85ee259
this.setBlockData(type.createBlockData(), applyPhysics);
}
@@ -196,6 +290,11 @@ public class CraftBlock implements Block {
@@ -196,6 +302,11 @@ public class CraftBlock implements Block {
}
public static boolean setBlockState(LevelAccessor world, BlockPos pos, net.minecraft.world.level.block.state.BlockState oldState, net.minecraft.world.level.block.state.BlockState newState, boolean applyPhysics) {
@@ -493,7 +507,7 @@ index dd122bbbe2c33183017dbde6997d3f1cd08479b5..d164d50bcee7281283c6d9a7b85ee259
// SPIGOT-611: need to do this to prevent glitchiness. Easier to handle this here (like /setblock) than to fix weirdness in block entity cleanup
if (oldState.hasBlockEntity() && newState.getBlock() != oldState.getBlock()) { // SPIGOT-3725 remove old block entity if block changes
// SPIGOT-4612: faster - just clear tile
@@ -227,22 +326,62 @@ public class CraftBlock implements Block {
@@ -227,22 +338,62 @@ public class CraftBlock implements Block {
@Override
public Material getType() {
@@ -560,7 +574,7 @@ index dd122bbbe2c33183017dbde6997d3f1cd08479b5..d164d50bcee7281283c6d9a7b85ee259
}
public Block getFace(final BlockFace face) {
@@ -287,47 +426,32 @@ public class CraftBlock implements Block {
@@ -287,47 +438,32 @@ public class CraftBlock implements Block {
}
public static BlockFace notchToBlockFace(Direction notch) {
@@ -631,7 +645,7 @@ index dd122bbbe2c33183017dbde6997d3f1cd08479b5..d164d50bcee7281283c6d9a7b85ee259
}
@Override
@@ -344,18 +468,65 @@ public class CraftBlock implements Block {
@@ -344,18 +480,65 @@ public class CraftBlock implements Block {
@Override
public Biome getBiome() {
@@ -699,7 +713,7 @@ index dd122bbbe2c33183017dbde6997d3f1cd08479b5..d164d50bcee7281283c6d9a7b85ee259
this.getWorld().setBiome(this.getX(), this.getY(), this.getZ(), bio);
}
@@ -371,12 +542,50 @@ public class CraftBlock implements Block {
@@ -371,12 +554,50 @@ public class CraftBlock implements Block {
@Override
public boolean isBlockPowered() {
@@ -752,7 +766,7 @@ index dd122bbbe2c33183017dbde6997d3f1cd08479b5..d164d50bcee7281283c6d9a7b85ee259
}
@Override
@@ -398,44 +607,103 @@ public class CraftBlock implements Block {
@@ -398,45 +619,104 @@ public class CraftBlock implements Block {
@Override
public boolean isBlockFacePowered(BlockFace face) {
@@ -835,7 +849,8 @@ index dd122bbbe2c33183017dbde6997d3f1cd08479b5..d164d50bcee7281283c6d9a7b85ee259
+ if (needsBuffering(level, handlingMode)) {
+ // Buffered path
+ return executeBufferedRead(level, org.dreeam.leaf.async.world.ReadOperationType.BLOCK_GET_BLOCK_POWER, new Object[]{this.position, face}, 0, "getBlockPower");
+ } else {
} else {
- return Math.max(state.getValue(RedStoneWireBlock.POWER), power);
+ // Strict/Disabled/Non-ServerLevel path
+ checkStrictMode(level, handlingMode, "getBlockPower");
+ try {
@@ -863,24 +878,24 @@ index dd122bbbe2c33183017dbde6997d3f1cd08479b5..d164d50bcee7281283c6d9a7b85ee259
+ org.bukkit.Bukkit.getLogger().log(java.util.logging.Level.SEVERE, "PWT: Direct access failed for getBlockPower" + (level == null ? " (Not a ServerLevel)" : ""), e);
+ return 0;
+ }
+ }
+ }
+
}
}
+ // Static helper, safe
+ public static int getPower(int currentMax, net.minecraft.world.level.block.state.BlockState neighborState) {
+ if (!neighborState.is(Blocks.REDSTONE_WIRE)) {
+ return currentMax;
} else {
- return Math.max(state.getValue(RedStoneWireBlock.POWER), power);
+ } else {
+ int neighborPower = neighborState.getValue(RedStoneWireBlock.POWER);
+ return Math.max(neighborPower, currentMax);
}
}
+ }
+ }
+ // Leaf end - SparklyPaper - parallel world ticking
+
@Override
public int getBlockPower() {
@@ -478,23 +746,35 @@ public class CraftBlock implements Block {
return this.getBlockPower(BlockFace.SELF);
@@ -478,23 +758,35 @@ public class CraftBlock implements Block {
@Override
public PistonMoveReaction getPistonMoveReaction() {
@@ -919,7 +934,7 @@ index dd122bbbe2c33183017dbde6997d3f1cd08479b5..d164d50bcee7281283c6d9a7b85ee259
}
@Override
@@ -506,84 +786,147 @@ public class CraftBlock implements Block {
@@ -506,84 +798,147 @@ public class CraftBlock implements Block {
public boolean breakNaturally(ItemStack item, boolean triggerEffect, boolean dropExperience, boolean forceEffect) {
// Paper end
// Order matters here, need to drop before setting to air so skulls can get their data
@@ -978,7 +993,7 @@ index dd122bbbe2c33183017dbde6997d3f1cd08479b5..d164d50bcee7281283c6d9a7b85ee259
+ // Log if we couldn't drop XP because it wasn't a ServerLevel
+ if (dropExperience && !state.isAir()) { // Only warn if XP was requested and block wasn't air
+ org.bukkit.Bukkit.getLogger().log(java.util.logging.Level.WARNING, "PWT: Cannot drop experience for breakNaturally: Not a ServerLevel.");
}
+ }
+ // Still trigger effects if requested and possible with LevelAccessor
+ if (triggerEffect && !state.isAir()) {
+ int eventId = (state.getBlock() instanceof net.minecraft.world.level.block.BaseFireBlock)
@@ -987,9 +1002,11 @@ index dd122bbbe2c33183017dbde6997d3f1cd08479b5..d164d50bcee7281283c6d9a7b85ee259
+ int eventData = (eventId == net.minecraft.world.level.block.LevelEvent.PARTICLES_DESTROY_BLOCK)
+ ? net.minecraft.world.level.block.Block.getId(state) : 0;
+ this.world.levelEvent(eventId, this.position, eventData);
+ }
+ }
+
}
}
- // SPIGOT-6778: Directly call setBlock instead of setBlockState, so that the block entity is not removed and custom remove logic is run.
- // Paper start - improve breakNaturally
+ // Trigger effect using LevelAccessor (safe)
+ if ((droppedItems && triggerEffect) || (forceEffect && block != Blocks.AIR)) {
+ int eventId = (state.getBlock() instanceof net.minecraft.world.level.block.BaseFireBlock)
@@ -998,10 +1015,8 @@ index dd122bbbe2c33183017dbde6997d3f1cd08479b5..d164d50bcee7281283c6d9a7b85ee259
+ int eventData = (eventId == net.minecraft.world.level.block.LevelEvent.PARTICLES_DESTROY_BLOCK)
+ ? net.minecraft.world.level.block.Block.getId(state) : 0;
+ this.world.levelEvent(eventId, this.position, eventData);
}
- // SPIGOT-6778: Directly call setBlock instead of setBlockState, so that the block entity is not removed and custom remove logic is run.
- // Paper start - improve breakNaturally
+ }
+
+ // Remove the block using LevelAccessor (safe)
boolean destroyed = this.world.removeBlock(this.position, false);
if (destroyed) {
@@ -1104,7 +1119,7 @@ index dd122bbbe2c33183017dbde6997d3f1cd08479b5..d164d50bcee7281283c6d9a7b85ee259
}
@Override
@@ -598,20 +941,45 @@ public class CraftBlock implements Block {
@@ -598,20 +953,45 @@ public class CraftBlock implements Block {
@Override
public Collection<ItemStack> getDrops(ItemStack item, Entity entity) {
@@ -1157,7 +1172,7 @@ index dd122bbbe2c33183017dbde6997d3f1cd08479b5..d164d50bcee7281283c6d9a7b85ee259
net.minecraft.world.level.block.state.BlockState state = this.getNMS();
net.minecraft.world.item.ItemStack nms = CraftItemStack.asNMSCopy(item);
return CraftBlockData.isPreferredTool(state, nms);
@@ -620,9 +988,23 @@ public class CraftBlock implements Block {
@@ -620,9 +1000,23 @@ public class CraftBlock implements Block {
@Override
public float getBreakSpeed(Player player) {
Preconditions.checkArgument(player != null, "player cannot be null");
@@ -1182,7 +1197,7 @@ index dd122bbbe2c33183017dbde6997d3f1cd08479b5..d164d50bcee7281283c6d9a7b85ee259
@Override
public void setMetadata(String metadataKey, MetadataValue newMetadataValue) {
this.getCraftWorld().getBlockMetadata().setMetadata(this, metadataKey, newMetadataValue);
@@ -645,57 +1027,148 @@ public class CraftBlock implements Block {
@@ -645,57 +1039,148 @@ public class CraftBlock implements Block {
@Override
public boolean isPassable() {
@@ -1354,7 +1369,7 @@ index dd122bbbe2c33183017dbde6997d3f1cd08479b5..d164d50bcee7281283c6d9a7b85ee259
}
@Override
@@ -711,7 +1184,10 @@ public class CraftBlock implements Block {
@@ -711,7 +1196,10 @@ public class CraftBlock implements Block {
// Paper start
@Override
public com.destroystokyo.paper.block.BlockSoundGroup getSoundGroup() {
@@ -1366,7 +1381,7 @@ index dd122bbbe2c33183017dbde6997d3f1cd08479b5..d164d50bcee7281283c6d9a7b85ee259
}
@Override
@@ -724,26 +1200,76 @@ public class CraftBlock implements Block {
@@ -724,26 +1212,76 @@ public class CraftBlock implements Block {
return this.getNMS().getBlock().getDescriptionId();
}