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

Readd PWT

This commit is contained in:
Dreeam
2025-06-06 00:26:36 +08:00
parent 982d0044d6
commit 72a8fb8d95
61 changed files with 437 additions and 752 deletions

View File

@@ -6,10 +6,10 @@ Subject: [PATCH] SparklyPaper: Track each world MSPT
Original project: https://github.com/SparklyPower/SparklyPaper
diff --git a/net/minecraft/server/MinecraftServer.java b/net/minecraft/server/MinecraftServer.java
index 7f791ff5bdf6c29c78f863d21af16270a74d8e7e..1431a0fac3c8a846535c1bd2f60a1279d08f14ea 100644
index c9b8bc9592d5fce77750de89fa886db383d92a89..1dc599e28682b59c8389ff2ada100b405bf97240 100644
--- a/net/minecraft/server/MinecraftServer.java
+++ b/net/minecraft/server/MinecraftServer.java
@@ -1699,7 +1699,16 @@ public abstract class MinecraftServer extends ReentrantBlockableEventLoop<TickTa
@@ -1687,7 +1687,16 @@ public abstract class MinecraftServer extends ReentrantBlockableEventLoop<TickTa
// Leaf start - SparklyPaper - parallel world ticking mod (move level ticking logic out for branch convergence)
private void tickLevel(ServerLevel serverLevel, BooleanSupplier hasTimeLeft) {
try {
@@ -27,10 +27,10 @@ index 7f791ff5bdf6c29c78f863d21af16270a74d8e7e..1431a0fac3c8a846535c1bd2f60a1279
CrashReport crashReport = CrashReport.forThrowable(levelTickingException, "Exception ticking world");
serverLevel.fillReportDetails(crashReport);
diff --git a/net/minecraft/server/level/ServerLevel.java b/net/minecraft/server/level/ServerLevel.java
index d6524d5c442555eaeb4d90f6a101262ee669f0d9..5c1f99a8fd9920b30e6a80769bc306591510012a 100644
index 85bfc91ff163a2a564b7b610e27ff90e053787d0..f4b9d0bcf305d99d39e530c3369faaec60bbc5a8 100644
--- a/net/minecraft/server/level/ServerLevel.java
+++ b/net/minecraft/server/level/ServerLevel.java
@@ -574,6 +574,12 @@ public class ServerLevel extends Level implements ServerEntityGetter, WorldGenLe
@@ -567,6 +567,12 @@ public class ServerLevel extends Level implements ServerEntityGetter, WorldGenLe
}
// Paper end - chunk tick iteration

View File

@@ -230,10 +230,10 @@ index fb5077450aa9f7b7a03dd20c27a68dfdaab5ef06..f37fd3b9ab725e5b8eb7fccf9b35bbc0
player.getInventory().removeItem(ammo);
}
diff --git a/net/minecraft/world/level/Level.java b/net/minecraft/world/level/Level.java
index 22da84734462d09a55bc599db4374e1e4f4d6bd2..2f679f03360a2847ba3d98a6698b7c0210a0b67e 100644
index c8219508cf94da71143b8672661592c66b341782..6278fe737a555f47625098828a03952cf9b859a7 100644
--- a/net/minecraft/world/level/Level.java
+++ b/net/minecraft/world/level/Level.java
@@ -170,6 +170,7 @@ public abstract class Level implements LevelAccessor, UUIDLookup<Entity>, AutoCl
@@ -171,6 +171,7 @@ public abstract class Level implements LevelAccessor, UUIDLookup<Entity>, AutoCl
public final Map<ServerExplosion.CacheKey, Float> explosionDensityCache = new java.util.HashMap<>(); // Paper - Optimize explosions
public java.util.ArrayDeque<net.minecraft.world.level.block.RedstoneTorchBlock.Toggle> redstoneUpdateInfos; // Paper - Faster redstone torch rapid clock removal; Move from Map in BlockRedstoneTorch to here
public final net.minecraft.world.level.levelgen.BitRandomSource simpleRandom = org.dreeam.leaf.config.modules.opt.FastRNG.enabled ? new org.dreeam.leaf.util.math.random.FasterRandomSource(net.minecraft.world.level.levelgen.RandomSupport.generateUniqueSeed()) : new ca.spottedleaf.moonrise.common.util.SimpleThreadUnsafeRandom(net.minecraft.world.level.levelgen.RandomSupport.generateUniqueSeed()); // Gale - Pufferfish - move random tick random // Leaf - Faster random generator

View File

@@ -9,10 +9,10 @@ Leaf: ~48ms (-36%)
This should help drastically on the farms that use actively changing fluids.
diff --git a/net/minecraft/server/level/ServerLevel.java b/net/minecraft/server/level/ServerLevel.java
index 2ecb73fc7b6754ade93bf16b48c623e6b3a955a9..4ecca1bf5ece7788f3de41d5ec58565b8a768251 100644
index f4b9d0bcf305d99d39e530c3369faaec60bbc5a8..a311f81b7f34f2c988ebcd792ca87dfd7b175f96 100644
--- a/net/minecraft/server/level/ServerLevel.java
+++ b/net/minecraft/server/level/ServerLevel.java
@@ -1302,6 +1302,10 @@ public class ServerLevel extends Level implements ServerEntityGetter, WorldGenLe
@@ -1441,6 +1441,10 @@ public class ServerLevel extends Level implements ServerEntityGetter, WorldGenLe
this.emptyTime = 0;
}

View File

@@ -10,10 +10,10 @@ Leaf (After): ~628ms (-96%)
This should help for massive hopper chains or hopper matrix.
diff --git a/net/minecraft/world/level/chunk/LevelChunk.java b/net/minecraft/world/level/chunk/LevelChunk.java
index 5325989f46bd288c5a6f1362ec17d3354d55abfd..5ca0aa1fdaae3ba03a464e2c5bc061adc076b649 100644
index 8d8d909c4b9496ae6f44ba34203ee40433d37f8c..e82e55ec400c5e338502ed7ce433372a88d4acff 100644
--- a/net/minecraft/world/level/chunk/LevelChunk.java
+++ b/net/minecraft/world/level/chunk/LevelChunk.java
@@ -1014,15 +1014,29 @@ public class LevelChunk extends ChunkAccess implements ca.spottedleaf.moonrise.p
@@ -1016,15 +1016,29 @@ public class LevelChunk extends ChunkAccess implements ca.spottedleaf.moonrise.p
static class RebindableTickingBlockEntityWrapper implements TickingBlockEntity {
private TickingBlockEntity ticker;
private BlockPos cachedPos; // Leaf - Cache tile entity position
@@ -43,7 +43,7 @@ index 5325989f46bd288c5a6f1362ec17d3354d55abfd..5ca0aa1fdaae3ba03a464e2c5bc061ad
}
@Override
@@ -1032,6 +1046,11 @@ public class LevelChunk extends ChunkAccess implements ca.spottedleaf.moonrise.p
@@ -1034,6 +1048,11 @@ public class LevelChunk extends ChunkAccess implements ca.spottedleaf.moonrise.p
@Override
public boolean isRemoved() {

View File

@@ -25,10 +25,10 @@ index 3a596650feb96123c5684bb5065e20c5b005c0b9..f7a05fd098ef7b303254cd410414d50d
}
diff --git a/net/minecraft/world/level/Level.java b/net/minecraft/world/level/Level.java
index 2f679f03360a2847ba3d98a6698b7c0210a0b67e..309dbb3b7a485ef5e13f893e53bbdbec1401422e 100644
index 6278fe737a555f47625098828a03952cf9b859a7..4158bbe0740fe2971a9e857cb4cad08ee465576a 100644
--- a/net/minecraft/world/level/Level.java
+++ b/net/minecraft/world/level/Level.java
@@ -1174,6 +1174,12 @@ public abstract class Level implements LevelAccessor, UUIDLookup<Entity>, AutoCl
@@ -1177,6 +1177,12 @@ public abstract class Level implements LevelAccessor, UUIDLookup<Entity>, AutoCl
snapshot.setFlags(flags); // Paper - always set the flag of the most recent call to mitigate issues with multiple update at the same pos with different flags
}
BlockState blockState = chunkAt.setBlockState(pos, state, flags);

View File

@@ -5,10 +5,10 @@ Subject: [PATCH] Micro optimizations for random tick
diff --git a/net/minecraft/server/level/ServerLevel.java b/net/minecraft/server/level/ServerLevel.java
index 4ecca1bf5ece7788f3de41d5ec58565b8a768251..05173104db4c04823658930aa92645f6c2400109 100644
index a311f81b7f34f2c988ebcd792ca87dfd7b175f96..4948557d2faef1dff664cd18df7af4564a0431ff 100644
--- a/net/minecraft/server/level/ServerLevel.java
+++ b/net/minecraft/server/level/ServerLevel.java
@@ -905,7 +905,7 @@ public class ServerLevel extends Level implements ServerEntityGetter, WorldGenLe
@@ -1044,7 +1044,7 @@ public class ServerLevel extends Level implements ServerEntityGetter, WorldGenLe
// Paper start - optimise random ticking
private void optimiseRandomTick(final LevelChunk chunk, final int tickSpeed) {
final LevelChunkSection[] sections = chunk.getSections();
@@ -17,7 +17,7 @@ index 4ecca1bf5ece7788f3de41d5ec58565b8a768251..05173104db4c04823658930aa92645f6
final net.minecraft.world.level.levelgen.BitRandomSource simpleRandom = this.simpleRandom; // Leaf - Faster random generator - upcasting
final boolean doubleTickFluids = !ca.spottedleaf.moonrise.common.PlatformHooks.get().configFixMC224294();
@@ -914,41 +914,41 @@ public class ServerLevel extends Level implements ServerEntityGetter, WorldGenLe
@@ -1053,41 +1053,41 @@ public class ServerLevel extends Level implements ServerEntityGetter, WorldGenLe
final int offsetZ = cpos.z << 4;
for (int sectionIndex = 0, sectionsLen = sections.length; sectionIndex < sectionsLen; sectionIndex++) {

View File

@@ -11,10 +11,10 @@ As part of: Airplane (https://github.com/TECHNOVE/Airplane)
Licensed under: GPL-3.0 (https://www.gnu.org/licenses/gpl-3.0.html)
diff --git a/net/minecraft/world/entity/Entity.java b/net/minecraft/world/entity/Entity.java
index 309a31215cb63452215fd880590cffd569aee208..1db32873588673900a8afa9767c3af12c7b6742a 100644
index b89923a0b30a294c393716b666ff3377f0a835dc..cfd01993160bcc4a8a5b80c82df7c0c82b70f229 100644
--- a/net/minecraft/world/entity/Entity.java
+++ b/net/minecraft/world/entity/Entity.java
@@ -4579,10 +4579,7 @@ public abstract class Entity implements SyncedDataHolder, Nameable, EntityAccess
@@ -4606,10 +4606,7 @@ public abstract class Entity implements SyncedDataHolder, Nameable, EntityAccess
// Paper start - optimise collisions
public boolean updateFluidHeightAndDoFluidPushing(final TagKey<Fluid> fluid, final double flowScale) {
@@ -26,7 +26,7 @@ index 309a31215cb63452215fd880590cffd569aee208..1db32873588673900a8afa9767c3af12
final AABB boundingBox = this.getBoundingBox().deflate(1.0E-3);
final Level world = this.level;
@@ -4618,7 +4615,11 @@ public abstract class Entity implements SyncedDataHolder, Nameable, EntityAccess
@@ -4645,7 +4642,11 @@ public abstract class Entity implements SyncedDataHolder, Nameable, EntityAccess
for (int currChunkZ = minChunkZ; currChunkZ <= maxChunkZ; ++currChunkZ) {
for (int currChunkX = minChunkX; currChunkX <= maxChunkX; ++currChunkX) {

View File

@@ -106,18 +106,18 @@ index 7b686d834e4eb36be5758b0e0a846a70d1e2294b..956d48fb7146b9eb2a5b5b4e23a83f60
final EntityCollectionBySection byType = this.entitiesByType.get(entity.getType());
byType.removeEntity(entity, sectionIndex);
diff --git a/net/minecraft/server/MinecraftServer.java b/net/minecraft/server/MinecraftServer.java
index bbd2b327c658b56a1fcf30c8b77cab987d688fcc..f8dba8be5774035744233c251c61abf572dd7d49 100644
index 1dc599e28682b59c8389ff2ada100b405bf97240..c2c904565df5fb320b98307a4d451066286ad726 100644
--- a/net/minecraft/server/MinecraftServer.java
+++ b/net/minecraft/server/MinecraftServer.java
@@ -290,6 +290,7 @@ public abstract class MinecraftServer extends ReentrantBlockableEventLoop<TickTa
public boolean lagging = false; // Purpur - Lagging threshold
@@ -291,6 +291,7 @@ public abstract class MinecraftServer extends ReentrantBlockableEventLoop<TickTa
protected boolean upnp = false; // Purpur - UPnP Port Forwarding
public final Set<net.minecraft.world.entity.Entity> entitiesWithScheduledTasks = java.util.concurrent.ConcurrentHashMap.newKeySet(); // SparklyPaper - skip EntityScheduler's executeTick checks if there isn't any tasks to be run (concurrent because plugins may schedule tasks async)
public java.util.concurrent.Semaphore serverLevelTickingSemaphore = null; // SparklyPaper - parallel world ticking
+ @Nullable public org.dreeam.leaf.async.ai.AsyncGoalThread asyncGoalThread; // Leaf - Async target finding
public static <S extends MinecraftServer> S spin(Function<Thread, S> threadFunction) {
AtomicReference<S> atomicReference = new AtomicReference<>();
@@ -1073,6 +1074,14 @@ public abstract class MinecraftServer extends ReentrantBlockableEventLoop<TickTa
@@ -1092,6 +1093,14 @@ public abstract class MinecraftServer extends ReentrantBlockableEventLoop<TickTa
org.dreeam.leaf.async.AsyncPlayerDataSaving.IO_POOL.awaitTermination(30, java.util.concurrent.TimeUnit.SECONDS);
} catch (java.lang.InterruptedException ignored) {}
// Leaf end - Async playerdata saving
@@ -133,23 +133,22 @@ index bbd2b327c658b56a1fcf30c8b77cab987d688fcc..f8dba8be5774035744233c251c61abf5
public String getLocalIp() {
diff --git a/net/minecraft/server/dedicated/DedicatedServer.java b/net/minecraft/server/dedicated/DedicatedServer.java
index 54910c2e1d6e6bb556e536fda060bd09402e04e8..747eb54f84650a9a507398e3d5352e001b042490 100644
index 72e871b8c7fee9b5cbd567e03baee80ee4b9c82e..41bdd0a3bb9c18f4eae3e2ca78c2946979da4f0b 100644
--- a/net/minecraft/server/dedicated/DedicatedServer.java
+++ b/net/minecraft/server/dedicated/DedicatedServer.java
@@ -198,6 +198,11 @@ public class DedicatedServer extends MinecraftServer implements ServerInterface
@@ -204,6 +204,10 @@ public class DedicatedServer extends MinecraftServer implements ServerInterface
DedicatedServer.LOGGER.info("Using " + serverLevelTickingSemaphore.availablePermits() + " permits for parallel world ticking"); // SparklyPaper - parallel world ticking
}
org.purpurmc.purpur.PurpurConfig.registerCommands();
// Purpur end - Purpur config files
// Leaf end - SparklyPaper - parallel world ticking mod (make configurable)
+ // Leaf start - Async target finding
+ if (org.dreeam.leaf.config.modules.async.AsyncTargetFinding.enabled) {
+ asyncGoalThread = new org.dreeam.leaf.async.ai.AsyncGoalThread(this);
+ }
+ // Leaf end - Async target finding
com.destroystokyo.paper.VersionHistoryManager.INSTANCE.getClass(); // Paper - load version history now
// Gale start - Pufferfish - SIMD support
diff --git a/net/minecraft/server/level/ServerLevel.java b/net/minecraft/server/level/ServerLevel.java
index 05173104db4c04823658930aa92645f6c2400109..e0fdf7205ff1dfab2c5cccd3d18c2b22deda686a 100644
index 4948557d2faef1dff664cd18df7af4564a0431ff..c0044f4013520fd617ec365012b10862571744f3 100644
--- a/net/minecraft/server/level/ServerLevel.java
+++ b/net/minecraft/server/level/ServerLevel.java
@@ -173,7 +173,16 @@ public class ServerLevel extends Level implements ServerEntityGetter, WorldGenLe
@@ -170,7 +169,7 @@ index 05173104db4c04823658930aa92645f6c2400109..e0fdf7205ff1dfab2c5cccd3d18c2b22
public final ServerChunkCache chunkSource;
private final MinecraftServer server;
public final net.minecraft.world.level.storage.PrimaryLevelData serverLevelData; // CraftBukkit - type
@@ -213,6 +222,7 @@ public class ServerLevel extends Level implements ServerEntityGetter, WorldGenLe
@@ -216,6 +225,7 @@ public class ServerLevel extends Level implements ServerEntityGetter, WorldGenLe
private final alternate.current.wire.WireHandler wireHandler = new alternate.current.wire.WireHandler(this); // Paper - optimize redstone (Alternate Current)
public boolean hasRidableMoveEvent = false; // Purpur - Ridables
final List<ServerPlayer> realPlayers; // Leaves - skip
@@ -178,7 +177,7 @@ index 05173104db4c04823658930aa92645f6c2400109..e0fdf7205ff1dfab2c5cccd3d18c2b22
@Override
public @Nullable LevelChunk getChunkIfLoaded(int x, int z) {
@@ -331,6 +341,12 @@ public class ServerLevel extends Level implements ServerEntityGetter, WorldGenLe
@@ -334,6 +344,12 @@ public class ServerLevel extends Level implements ServerEntityGetter, WorldGenLe
((ca.spottedleaf.moonrise.patches.chunk_system.server.ChunkSystemMinecraftServer)this.server).moonrise$executeMidTickTasks();
}
@@ -191,10 +190,10 @@ index 05173104db4c04823658930aa92645f6c2400109..e0fdf7205ff1dfab2c5cccd3d18c2b22
@Override
public final ChunkAccess moonrise$syncLoadNonFull(final int chunkX, final int chunkZ, final net.minecraft.world.level.chunk.status.ChunkStatus status) {
return this.moonrise$getChunkTaskScheduler().syncLoadNonFull(chunkX, chunkZ, status);
@@ -693,6 +709,13 @@ public class ServerLevel extends Level implements ServerEntityGetter, WorldGenLe
this.getCraftServer().addWorld(this.getWorld()); // CraftBukkit
@@ -703,6 +719,13 @@ public class ServerLevel extends Level implements ServerEntityGetter, WorldGenLe
this.preciseTime = this.serverLevelData.getDayTime(); // Purpur - Configurable daylight cycle
this.realPlayers = Lists.newArrayList(); // Leaves - skip
this.tickExecutor = java.util.concurrent.Executors.newSingleThreadExecutor(new org.dreeam.leaf.async.world.SparklyPaperServerLevelTickExecutorThreadFactory(getWorld().getName())); // SparklyPaper - parallel world ticking
+ // Leaf start - Async target finding
+ if (org.dreeam.leaf.config.modules.async.AsyncTargetFinding.enabled) {
+ this.asyncGoalExecutor = new org.dreeam.leaf.async.ai.AsyncGoalExecutor(server.asyncGoalThread, this);
@@ -204,8 +203,8 @@ index 05173104db4c04823658930aa92645f6c2400109..e0fdf7205ff1dfab2c5cccd3d18c2b22
+ // Leaf end - Async target finding
}
// Paper start
@@ -837,12 +860,14 @@ public class ServerLevel extends Level implements ServerEntityGetter, WorldGenLe
// Leaf start - SparklyPaper - parallel world ticking - Shutdown handling for async reads
@@ -976,12 +999,14 @@ public class ServerLevel extends Level implements ServerEntityGetter, WorldGenLe
}
this.moonrise$midTickTasks(); // Paper - rewrite chunk system
// Gale end - Airplane - remove lambda from ticking guard - copied from guardEntityTick
@@ -220,16 +219,16 @@ index 05173104db4c04823658930aa92645f6c2400109..e0fdf7205ff1dfab2c5cccd3d18c2b22
}
// Paper - rewrite chunk system
}
@@ -1318,6 +1343,7 @@ public class ServerLevel extends Level implements ServerEntityGetter, WorldGenLe
}
@@ -1460,6 +1485,7 @@ public class ServerLevel extends Level implements ServerEntityGetter, WorldGenLe
// Leaf end - SparklyPaper - parallel world ticking (only run mid-tick at the end of each tick / fixes concurrency bugs related to executeMidTickTasks)
// Paper end - rewrite chunk system
+ this.leafMidTickTasks(); // Leaf - Async target finding
}
private void tickBlock(BlockPos pos, Block block) {
@@ -1331,6 +1357,7 @@ public class ServerLevel extends Level implements ServerEntityGetter, WorldGenLe
}
@@ -1476,6 +1502,7 @@ public class ServerLevel extends Level implements ServerEntityGetter, WorldGenLe
// Leaf end - SparklyPaper - parallel world ticking (only run mid-tick at the end of each tick / fixes concurrency bugs related to executeMidTickTasks)
// Paper end - rewrite chunk system
+ this.leafMidTickTasks(); // Leaf - Async target finding
@@ -2047,25 +2046,27 @@ index e1717b5c854aa81fdd7b7e715d7c3498d9f86072..3627e7479b4deea28e268245410ec4cd
static class StriderPathNavigation extends GroundPathNavigation {
diff --git a/net/minecraft/world/level/Level.java b/net/minecraft/world/level/Level.java
index 309dbb3b7a485ef5e13f893e53bbdbec1401422e..1ef49db44e8dcfd944b600ef64dbcaee36546688 100644
index 4158bbe0740fe2971a9e857cb4cad08ee465576a..e380cc68d0d88d983a1b7b1d9ef4ec8ef307761a 100644
--- a/net/minecraft/world/level/Level.java
+++ b/net/minecraft/world/level/Level.java
@@ -1525,6 +1525,7 @@ public abstract class Level implements LevelAccessor, UUIDLookup<Entity>, AutoCl
((ca.spottedleaf.moonrise.patches.chunk_system.level.ChunkSystemLevel)(Level)(Object)this).moonrise$midTickTasks();
@@ -1531,6 +1531,7 @@ public abstract class Level implements LevelAccessor, UUIDLookup<Entity>, AutoCl
}
// Leaf end - SparklyPaper - parallel world ticking (only run mid-tick at the end of each tick / fixes concurrency bugs related to executeMidTickTasks) - do not bother with condition work / make configurable
// Paper end - rewrite chunk system
+ ((ServerLevel) this).leafMidTickTasks(); // Leaf - Async target finding
}
}
this.blockEntityTickers.removeMarkedEntries(); // SparklyPaper - optimize block entity removals
@@ -1788,7 +1789,11 @@ public abstract class Level implements LevelAccessor, UUIDLookup<Entity>, AutoCl
@@ -1799,9 +1800,11 @@ public abstract class Level implements LevelAccessor, UUIDLookup<Entity>, AutoCl
@Override
public List<Entity> getEntities(@Nullable Entity entity, AABB boundingBox, Predicate<? super Entity> predicate) {
- if (org.dreeam.leaf.config.modules.async.SparklyPaperParallelWorldTicking.enabled) // Leaf start - SparklyPaper - parallel world ticking mod (make configurable)
- ca.spottedleaf.moonrise.common.util.TickThread.ensureTickThread((ServerLevel)this, boundingBox, "Cannot getEntities asynchronously"); // SparklyPaper - parallel world ticking (additional concurrency issues logs)
- List<Entity> list = Lists.newArrayList();
+ // Leaf start - Async target finding
+ // if (org.dreeam.leaf.config.modules.async.SparklyPaperParallelWorldTicking.enabled) // Leaf start - SparklyPaper - parallel world ticking mod (make configurable)
+ // ca.spottedleaf.moonrise.common.util.TickThread.ensureTickThread((ServerLevel)this, boundingBox, "Cannot getEntities asynchronously"); // SparklyPaper - parallel world ticking (additional concurrency issues logs)
+ //if (org.dreeam.leaf.config.modules.async.SparklyPaperParallelWorldTicking.enabled) // Leaf start - SparklyPaper - parallel world ticking mod (make configurable)
+ // ca.spottedleaf.moonrise.common.util.TickThread.ensureTickThread((ServerLevel)this, boundingBox, "Cannot getEntities asynchronously"); // SparklyPaper - parallel world ticking (additional concurrency issues logs)
+ //List<Entity> list = Lists.newArrayList(); // Leaf - Async target finding - unused
+ // Leaf end - Async target finding

View File

@@ -27,10 +27,10 @@ index 3a78e7512772fd3f7cf8f221e3a72474def14bea..ba52af914e9e231caa0ac50562e9a692
public static final int GENERATED_TICKET_LEVEL = ChunkHolderManager.FULL_LOADED_TICKET_LEVEL;
public static final int LOADED_TICKET_LEVEL = ChunkTaskScheduler.getTicketLevel(ChunkStatus.EMPTY);
diff --git a/net/minecraft/server/players/PlayerList.java b/net/minecraft/server/players/PlayerList.java
index 8b1652805a2ac9ebae9c99dd77e81c7a484a7abb..608d4612ed15ec04492b0137ec61e157161d792f 100644
index e4bccc642abe15b0ec4b1cf2634801065a27e11a..6a9aa085956ddd27e8910dd524ecb79caf9ae0ba 100644
--- a/net/minecraft/server/players/PlayerList.java
+++ b/net/minecraft/server/players/PlayerList.java
@@ -432,6 +432,13 @@ public abstract class PlayerList {
@@ -434,6 +434,13 @@ public abstract class PlayerList {
// this.broadcastAll(ClientboundPlayerInfoUpdatePacket.createPlayerInitializing(List.of(player))); // CraftBukkit - replaced with loop below
// Paper start - Fire PlayerJoinEvent when Player is actually ready; correctly register player BEFORE PlayerJoinEvent, so the entity is valid and doesn't require tick delay hacks
player.supressTrackerForLogin = true;

View File

@@ -6,7 +6,7 @@ Subject: [PATCH] Sakura: Optimise check inside blocks and traverse blocks
Dreeam TODO: refactor checkinsideblcoks
diff --git a/net/minecraft/world/entity/Entity.java b/net/minecraft/world/entity/Entity.java
index 1db32873588673900a8afa9767c3af12c7b6742a..5d1027cb511be78b1e29d0e3bdc49cc9d6add346 100644
index cfd01993160bcc4a8a5b80c82df7c0c82b70f229..f866fd8a7c37b94d24d6d1e41ed0a6106a82a4ac 100644
--- a/net/minecraft/world/entity/Entity.java
+++ b/net/minecraft/world/entity/Entity.java
@@ -1697,6 +1697,7 @@ public abstract class Entity implements SyncedDataHolder, Nameable, EntityAccess

View File

@@ -22,10 +22,10 @@ index 56fd1ed7ccaf96e7eedea60fbdbf7f934939d563..d2f522ea6d0a209496848af073c9af1c
}
diff --git a/net/minecraft/server/MinecraftServer.java b/net/minecraft/server/MinecraftServer.java
index f8dba8be5774035744233c251c61abf572dd7d49..2ca484a6c3e75fd392ca953737bb548ab10f2121 100644
index c2c904565df5fb320b98307a4d451066286ad726..84b90f496e5ab59d43503301fe935627af123e3f 100644
--- a/net/minecraft/server/MinecraftServer.java
+++ b/net/minecraft/server/MinecraftServer.java
@@ -1771,6 +1771,7 @@ public abstract class MinecraftServer extends ReentrantBlockableEventLoop<TickTa
@@ -1833,6 +1833,7 @@ public abstract class MinecraftServer extends ReentrantBlockableEventLoop<TickTa
}
org.leavesmc.leaves.protocol.core.LeavesProtocolManager.handleTick(tickCount); // Leaves - protocol
@@ -46,10 +46,10 @@ index 16b2ca8c96e9561aa57e0903d1e98e6441044b6d..939400c18eb4e87e0bf1b131e1601f4d
private Stream<Entity> mountedOrDismounted(List<Entity> entities) {
diff --git a/net/minecraft/server/level/ServerPlayer.java b/net/minecraft/server/level/ServerPlayer.java
index ccd442b24693bc9269cc8ab3e44887d0ad3eadbd..aee177756afebd3f39917ae8a08bbbd0e2efe4df 100644
index ac7ac519ecc58a31c4b9efc24f054ec014851fb4..59a61ac969e79966484a839b7d9ca0ac50e80994 100644
--- a/net/minecraft/server/level/ServerPlayer.java
+++ b/net/minecraft/server/level/ServerPlayer.java
@@ -803,6 +803,7 @@ public class ServerPlayer extends Player implements ca.spottedleaf.moonrise.patc
@@ -805,6 +805,7 @@ public class ServerPlayer extends Player implements ca.spottedleaf.moonrise.patc
}
}
// Purpur end - Ridables
@@ -71,10 +71,10 @@ index 18f0d486c478087f404d8bb6cd840079e2c8d239..1a6f1c5f4cf13ee50bc8445845cbb973
final byte[] data = discardedPayload.data();
try {
diff --git a/net/minecraft/server/players/PlayerList.java b/net/minecraft/server/players/PlayerList.java
index 608d4612ed15ec04492b0137ec61e157161d792f..7802f33f4259e9df0b2e682dd2e6bb8f6f74f25b 100644
index 6a9aa085956ddd27e8910dd524ecb79caf9ae0ba..e0f6b82d9836cb73f6fe631071bb1a0c5ec77eab 100644
--- a/net/minecraft/server/players/PlayerList.java
+++ b/net/minecraft/server/players/PlayerList.java
@@ -684,6 +684,7 @@ public abstract class PlayerList {
@@ -686,6 +686,7 @@ public abstract class PlayerList {
}
public @Nullable net.kyori.adventure.text.Component remove(ServerPlayer player, net.kyori.adventure.text.Component leaveMessage) {
org.leavesmc.leaves.protocol.core.LeavesProtocolManager.handlePlayerLeave(player); // Leaves - protocol

View File

@@ -5,7 +5,7 @@ Subject: [PATCH] Optimise BlockEntities tickersInLevel
diff --git a/net/minecraft/world/level/chunk/LevelChunk.java b/net/minecraft/world/level/chunk/LevelChunk.java
index 5ca0aa1fdaae3ba03a464e2c5bc061adc076b649..3e00ef33413764df933c85bb836d2cd327248edd 100644
index e82e55ec400c5e338502ed7ce433372a88d4acff..155e9b807a61ab1212ee25cc79a386821596dedc 100644
--- a/net/minecraft/world/level/chunk/LevelChunk.java
+++ b/net/minecraft/world/level/chunk/LevelChunk.java
@@ -73,7 +73,7 @@ public class LevelChunk extends ChunkAccess implements ca.spottedleaf.moonrise.p

View File

@@ -5,10 +5,10 @@ Subject: [PATCH] Only tick items at hand
diff --git a/net/minecraft/server/level/ServerPlayer.java b/net/minecraft/server/level/ServerPlayer.java
index aee177756afebd3f39917ae8a08bbbd0e2efe4df..b4e5405a3b48cc18d2dac264c5bb7ff666ad2e22 100644
index 59a61ac969e79966484a839b7d9ca0ac50e80994..82ac99c3c5b374482f3ff18f5d20bf888091e539 100644
--- a/net/minecraft/server/level/ServerPlayer.java
+++ b/net/minecraft/server/level/ServerPlayer.java
@@ -832,12 +832,19 @@ public class ServerPlayer extends Player implements ca.spottedleaf.moonrise.patc
@@ -834,12 +834,19 @@ public class ServerPlayer extends Player implements ca.spottedleaf.moonrise.patc
super.tick();
}

View File

@@ -5,7 +5,7 @@ Subject: [PATCH] Optimise player movement checks
diff --git a/net/minecraft/world/entity/Entity.java b/net/minecraft/world/entity/Entity.java
index 5d1027cb511be78b1e29d0e3bdc49cc9d6add346..1b4aae603e965ae15d9b7e204a2ac5d31d045db0 100644
index f866fd8a7c37b94d24d6d1e41ed0a6106a82a4ac..d09a32288398d3ffa0fa6e9c6fd06f953b33688f 100644
--- a/net/minecraft/world/entity/Entity.java
+++ b/net/minecraft/world/entity/Entity.java
@@ -1190,7 +1190,7 @@ public abstract class Entity implements SyncedDataHolder, Nameable, EntityAccess

View File

@@ -5,10 +5,10 @@ Subject: [PATCH] Add configurable death item drop knockback settings
diff --git a/net/minecraft/server/level/ServerPlayer.java b/net/minecraft/server/level/ServerPlayer.java
index b4e5405a3b48cc18d2dac264c5bb7ff666ad2e22..2a4fb4de12409166e9463eacafb13e37760a3a1b 100644
index 82ac99c3c5b374482f3ff18f5d20bf888091e539..c9fbbbef8d006a90023c70419b5be7220602ee3b 100644
--- a/net/minecraft/server/level/ServerPlayer.java
+++ b/net/minecraft/server/level/ServerPlayer.java
@@ -1051,7 +1051,7 @@ public class ServerPlayer extends Player implements ca.spottedleaf.moonrise.patc
@@ -1053,7 +1053,7 @@ public class ServerPlayer extends Player implements ca.spottedleaf.moonrise.patc
if (!keepInventory) {
for (ItemStack item : this.getInventory().getContents()) {
if (!item.isEmpty() && !EnchantmentHelper.has(item, net.minecraft.world.item.enchantment.EnchantmentEffectComponents.PREVENT_EQUIPMENT_DROP)) {

View File

@@ -5,10 +5,10 @@ Subject: [PATCH] Optimize getScaledTrackingDistance
diff --git a/net/minecraft/server/dedicated/DedicatedServer.java b/net/minecraft/server/dedicated/DedicatedServer.java
index 747eb54f84650a9a507398e3d5352e001b042490..595284787053a5fb7385e8493953c73a19fe7aee 100644
index 41bdd0a3bb9c18f4eae3e2ca78c2946979da4f0b..8192031ab3d947bb67eb00eec0a95ea99dce47ad 100644
--- a/net/minecraft/server/dedicated/DedicatedServer.java
+++ b/net/minecraft/server/dedicated/DedicatedServer.java
@@ -780,7 +780,13 @@ public class DedicatedServer extends MinecraftServer implements ServerInterface
@@ -785,7 +785,13 @@ public class DedicatedServer extends MinecraftServer implements ServerInterface
@Override
public int getScaledTrackingDistance(int trackingDistance) {

View File

@@ -5,7 +5,7 @@ Subject: [PATCH] Optimize isEyeInFluid
diff --git a/net/minecraft/world/entity/Entity.java b/net/minecraft/world/entity/Entity.java
index 1b4aae603e965ae15d9b7e204a2ac5d31d045db0..ffb23578d5d7a2a821427dae9bab343ec3c45036 100644
index d09a32288398d3ffa0fa6e9c6fd06f953b33688f..c377aef03861f2d860a7c6273f634248a6963f01 100644
--- a/net/minecraft/world/entity/Entity.java
+++ b/net/minecraft/world/entity/Entity.java
@@ -269,6 +269,9 @@ public abstract class Entity implements SyncedDataHolder, Nameable, EntityAccess

View File

@@ -77,7 +77,7 @@ index 4535858701b2bb232b9d2feb2af6551526232ddc..e65c62dbe4c1560ae153e4c4344e9194
- // Paper end - detailed watchdog information
}
diff --git a/net/minecraft/server/level/ServerChunkCache.java b/net/minecraft/server/level/ServerChunkCache.java
index 0f9d18dd29e210ad656da211a3cb1cb25cd4efb1..d1c36cd17c83e7e0167046093c4a2b8427c8bae0 100644
index b3acfc7e00797ea16cc2c1793452f3ed97b9c61a..17c1b05f520145b84e90fc359dca4523191f08cd 100644
--- a/net/minecraft/server/level/ServerChunkCache.java
+++ b/net/minecraft/server/level/ServerChunkCache.java
@@ -622,8 +622,10 @@ public class ServerChunkCache extends ChunkSource implements ca.spottedleaf.moon
@@ -94,10 +94,10 @@ index 0f9d18dd29e210ad656da211a3cb1cb25cd4efb1..d1c36cd17c83e7e0167046093c4a2b84
for (LevelChunk levelChunk : list) {
diff --git a/net/minecraft/server/level/ServerLevel.java b/net/minecraft/server/level/ServerLevel.java
index e0fdf7205ff1dfab2c5cccd3d18c2b22deda686a..9df599e94e17da12a880df2f40a2117c5ec2a569 100644
index c0044f4013520fd617ec365012b10862571744f3..14d23006d3ec15bb3ec6f976bff6c0975662c69d 100644
--- a/net/minecraft/server/level/ServerLevel.java
+++ b/net/minecraft/server/level/ServerLevel.java
@@ -1373,13 +1373,7 @@ public class ServerLevel extends Level implements ServerEntityGetter, WorldGenLe
@@ -1518,13 +1518,7 @@ public class ServerLevel extends Level implements ServerEntityGetter, WorldGenLe
// Paper end - log detailed entity tick information
public void tickNonPassenger(Entity entity) {
@@ -111,7 +111,7 @@ index e0fdf7205ff1dfab2c5cccd3d18c2b22deda686a..9df599e94e17da12a880df2f40a2117c
entity.setOldPosAndRot();
entity.tickCount++;
entity.totalEntityAge++; // Paper - age-like counter for all entities
@@ -1392,13 +1386,6 @@ public class ServerLevel extends Level implements ServerEntityGetter, WorldGenLe
@@ -1537,13 +1531,6 @@ public class ServerLevel extends Level implements ServerEntityGetter, WorldGenLe
for (Entity entity1 : entity.getPassengers()) {
this.tickPassenger(entity, entity1, isActive); // Paper - EAR 2
}
@@ -126,7 +126,7 @@ index e0fdf7205ff1dfab2c5cccd3d18c2b22deda686a..9df599e94e17da12a880df2f40a2117c
private void tickPassenger(Entity ridingEntity, Entity passengerEntity, final boolean isActive) { // Paper - EAR 2
diff --git a/net/minecraft/world/entity/Entity.java b/net/minecraft/world/entity/Entity.java
index ffb23578d5d7a2a821427dae9bab343ec3c45036..95a15fa08a5bd2bb799a125e03844259038ef290 100644
index c377aef03861f2d860a7c6273f634248a6963f01..192d65bdc9fc9ae96d460e9b0832c20a209d2b0d 100644
--- a/net/minecraft/world/entity/Entity.java
+++ b/net/minecraft/world/entity/Entity.java
@@ -1140,16 +1140,6 @@ public abstract class Entity implements SyncedDataHolder, Nameable, EntityAccess
@@ -177,7 +177,7 @@ index ffb23578d5d7a2a821427dae9bab343ec3c45036..95a15fa08a5bd2bb799a125e03844259
}
private void applyMovementEmissionAndPlaySound(Entity.MovementEmission movementEmission, Vec3 movement, BlockPos pos, BlockState state) {
@@ -4831,9 +4805,7 @@ public abstract class Entity implements SyncedDataHolder, Nameable, EntityAccess
@@ -4858,9 +4832,7 @@ public abstract class Entity implements SyncedDataHolder, Nameable, EntityAccess
}
public void setDeltaMovement(Vec3 deltaMovement) {
@@ -187,7 +187,7 @@ index ffb23578d5d7a2a821427dae9bab343ec3c45036..95a15fa08a5bd2bb799a125e03844259
}
public void addDeltaMovement(Vec3 addend) {
@@ -4941,9 +4913,7 @@ public abstract class Entity implements SyncedDataHolder, Nameable, EntityAccess
@@ -4968,9 +4940,7 @@ public abstract class Entity implements SyncedDataHolder, Nameable, EntityAccess
}
// Paper end - Fix MC-4
if (this.position.x != x || this.position.y != y || this.position.z != z) {

View File

@@ -5,10 +5,10 @@ Subject: [PATCH] Cache block path type
diff --git a/net/minecraft/server/dedicated/DedicatedServer.java b/net/minecraft/server/dedicated/DedicatedServer.java
index 595284787053a5fb7385e8493953c73a19fe7aee..6dec45b376288638433f0d50e474f9713266d99c 100644
index 8192031ab3d947bb67eb00eec0a95ea99dce47ad..6400f2b68a818e771b3b27724dede7f15562b2c0 100644
--- a/net/minecraft/server/dedicated/DedicatedServer.java
+++ b/net/minecraft/server/dedicated/DedicatedServer.java
@@ -360,6 +360,7 @@ public class DedicatedServer extends MinecraftServer implements ServerInterface
@@ -365,6 +365,7 @@ public class DedicatedServer extends MinecraftServer implements ServerInterface
}
if (org.dreeam.leaf.config.modules.async.AsyncMobSpawning.enabled) mobSpawnExecutor.start(); // Pufferfish

View File

@@ -42,7 +42,7 @@ index 2d24d03bbdb5ee0d862cbfff2219f58afffafe12..11f4f2f3bc4c9f9f6a1f83b90f3de34c
protected boolean addEntity(final Entity entity, final boolean fromDisk, final boolean event) {
diff --git a/net/minecraft/world/entity/Entity.java b/net/minecraft/world/entity/Entity.java
index 95a15fa08a5bd2bb799a125e03844259038ef290..905ffdc8d9188c40dc86216c651e22dcbd14dc95 100644
index 192d65bdc9fc9ae96d460e9b0832c20a209d2b0d..7961d8ff4fc13ca5274f6667181da5ce557ddc0f 100644
--- a/net/minecraft/world/entity/Entity.java
+++ b/net/minecraft/world/entity/Entity.java
@@ -370,6 +370,7 @@ public abstract class Entity implements SyncedDataHolder, Nameable, EntityAccess

View File

@@ -32327,10 +32327,10 @@ index 175647d57e59e838ea7b4680fbf22c161100c513..a7b772cfc89161414469cd7da374d6c7
return structureTemplate.save(new CompoundTag());
}
diff --git a/net/minecraft/server/MinecraftServer.java b/net/minecraft/server/MinecraftServer.java
index 2ca484a6c3e75fd392ca953737bb548ab10f2121..1540b1a571c8f44c4163f4720a9279f87a8032c9 100644
index 84b90f496e5ab59d43503301fe935627af123e3f..54e31a239d6563abe56435ee8de03e55548ead29 100644
--- a/net/minecraft/server/MinecraftServer.java
+++ b/net/minecraft/server/MinecraftServer.java
@@ -293,6 +293,7 @@ public abstract class MinecraftServer extends ReentrantBlockableEventLoop<TickTa
@@ -294,6 +294,7 @@ public abstract class MinecraftServer extends ReentrantBlockableEventLoop<TickTa
@Nullable public org.dreeam.leaf.async.ai.AsyncGoalThread asyncGoalThread; // Leaf - Async target finding
public static <S extends MinecraftServer> S spin(Function<Thread, S> threadFunction) {

View File

@@ -6,7 +6,7 @@ Subject: [PATCH] SparklyPaper: Parallel world ticking
Original project: https://github.com/SparklyPower/SparklyPaper
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 a4aa2615823d77920ff55b8aa0bcc27a54b8c3e1..2fb65ce228da94eb7d9364ee0f94582300178f1d 100644
index a4aa2615823d77920ff55b8aa0bcc27a54b8c3e1..e1bf7dfdb3be8f92ef2cb86d7f15a613b4ccadff 100644
--- a/src/main/java/ca/spottedleaf/moonrise/common/util/TickThread.java
+++ b/src/main/java/ca/spottedleaf/moonrise/common/util/TickThread.java
@@ -14,6 +14,7 @@ import java.util.concurrent.atomic.AtomicInteger;
@@ -17,75 +17,88 @@ index a4aa2615823d77920ff55b8aa0bcc27a54b8c3e1..2fb65ce228da94eb7d9364ee0f945823
private static String getThreadContext() {
return "thread=" + Thread.currentThread().getName();
@@ -26,14 +27,14 @@ public class TickThread extends Thread {
@@ -26,6 +27,7 @@ public class TickThread extends Thread {
public static void ensureTickThread(final String reason) {
if (!isTickThread()) {
LOGGER.error("Thread failed main thread check: " + reason + ", context=" + getThreadContext(), new Throwable());
- throw new IllegalStateException(reason);
+ if (HARD_THROW) throw new IllegalStateException(reason); // SparklyPaper - parallel world ticking
+ if (HARD_THROW) // SparklyPaper - parallel world ticking
throw new IllegalStateException(reason);
}
}
@@ -33,8 +35,9 @@ public class TickThread extends Thread {
public static void ensureTickThread(final Level world, final BlockPos pos, final String reason) {
if (!isTickThreadFor(world, pos)) {
final String ex = "Thread failed main thread check: " +
- reason + ", context=" + getThreadContext() + ", world=" + WorldUtil.getWorldName(world) + ", block_pos=" + pos;
+ reason + ", context=" + getThreadContext() + ", world=" + WorldUtil.getWorldName(world) + ", block_pos=" + pos + " - " + getTickThreadInformation(world.getServer()); // SparklyPaper - parallel world ticking
LOGGER.error(ex, new Throwable());
+ if (HARD_THROW) // SparklyPaper - parallel world ticking
throw new IllegalStateException(ex);
}
@@ -42,7 +43,7 @@ public class TickThread extends Thread {
}
@@ -42,8 +45,9 @@ public class TickThread extends Thread {
public static void ensureTickThread(final Level world, final BlockPos pos, final int blockRadius, final String reason) {
if (!isTickThreadFor(world, pos, blockRadius)) {
final String ex = "Thread failed main thread check: " +
- reason + ", context=" + getThreadContext() + ", world=" + WorldUtil.getWorldName(world) + ", block_pos=" + pos + ", block_radius=" + blockRadius;
+ reason + ", context=" + getThreadContext() + ", world=" + WorldUtil.getWorldName(world) + ", block_pos=" + pos + ", block_radius=" + blockRadius + " - " + getTickThreadInformation(world.getServer()); // SparklyPaper - parallel world ticking
LOGGER.error(ex, new Throwable());
+ if (HARD_THROW) // SparklyPaper - parallel world ticking
throw new IllegalStateException(ex);
}
@@ -51,7 +52,7 @@ public class TickThread extends Thread {
}
@@ -51,8 +55,9 @@ public class TickThread extends Thread {
public static void ensureTickThread(final Level world, final ChunkPos pos, final String reason) {
if (!isTickThreadFor(world, pos)) {
final String ex = "Thread failed main thread check: " +
- reason + ", context=" + getThreadContext() + ", world=" + WorldUtil.getWorldName(world) + ", chunk_pos=" + pos;
+ reason + ", context=" + getThreadContext() + ", world=" + WorldUtil.getWorldName(world) + ", chunk_pos=" + pos + " - " + getTickThreadInformation(world.getServer()); // SparklyPaper - parallel world ticking
LOGGER.error(ex, new Throwable());
+ if (HARD_THROW) // SparklyPaper - parallel world ticking
throw new IllegalStateException(ex);
}
@@ -60,7 +61,7 @@ public class TickThread extends Thread {
}
@@ -60,8 +65,9 @@ public class TickThread extends Thread {
public static void ensureTickThread(final Level world, final int chunkX, final int chunkZ, final String reason) {
if (!isTickThreadFor(world, chunkX, chunkZ)) {
final String ex = "Thread failed main thread check: " +
- reason + ", context=" + getThreadContext() + ", world=" + WorldUtil.getWorldName(world) + ", chunk_pos=" + new ChunkPos(chunkX, chunkZ);
+ reason + ", context=" + getThreadContext() + ", world=" + WorldUtil.getWorldName(world) + ", chunk_pos=" + new ChunkPos(chunkX, chunkZ) + " - " + getTickThreadInformation(world.getServer()); // SparklyPaper - parallel world ticking
LOGGER.error(ex, new Throwable());
+ if (HARD_THROW) // SparklyPaper - parallel world ticking
throw new IllegalStateException(ex);
}
@@ -69,7 +70,7 @@ public class TickThread extends Thread {
}
@@ -69,8 +75,9 @@ public class TickThread extends Thread {
public static void ensureTickThread(final Entity entity, final String reason) {
if (!isTickThreadFor(entity)) {
final String ex = "Thread failed main thread check: " +
- reason + ", context=" + getThreadContext() + ", entity=" + EntityUtil.dumpEntity(entity);
+ reason + ", context=" + getThreadContext() + ", entity=" + EntityUtil.dumpEntity(entity) + " - " + getTickThreadInformation(entity.getServer()); // SparklyPaper - parallel world ticking
LOGGER.error(ex, new Throwable());
+ if (HARD_THROW) // SparklyPaper - parallel world ticking
throw new IllegalStateException(ex);
}
@@ -78,7 +79,7 @@ public class TickThread extends Thread {
}
@@ -78,8 +85,9 @@ public class TickThread extends Thread {
public static void ensureTickThread(final Level world, final AABB aabb, final String reason) {
if (!isTickThreadFor(world, aabb)) {
final String ex = "Thread failed main thread check: " +
- reason + ", context=" + getThreadContext() + ", world=" + WorldUtil.getWorldName(world) + ", aabb=" + aabb;
+ reason + ", context=" + getThreadContext() + ", world=" + WorldUtil.getWorldName(world) + ", aabb=" + aabb + " - " + getTickThreadInformation(world.getServer()); // SparklyPaper - parallel world ticking
LOGGER.error(ex, new Throwable());
+ if (HARD_THROW) // SparklyPaper - parallel world ticking
throw new IllegalStateException(ex);
}
@@ -87,12 +88,70 @@ public class TickThread extends Thread {
}
@@ -87,12 +95,71 @@ public class TickThread extends Thread {
public static void ensureTickThread(final Level world, final double blockX, final double blockZ, final String reason) {
if (!isTickThreadFor(world, blockX, blockZ)) {
final String ex = "Thread failed main thread check: " +
- reason + ", context=" + getThreadContext() + ", world=" + WorldUtil.getWorldName(world) + ", block_pos=" + new Vec3(blockX, 0.0, blockZ);
+ reason + ", context=" + getThreadContext() + ", world=" + WorldUtil.getWorldName(world) + ", block_pos=" + new Vec3(blockX, 0.0, blockZ) + " - " + getTickThreadInformation(world.getServer()); // SparklyPaper - parallel world ticking
LOGGER.error(ex, new Throwable());
+ if (HARD_THROW) // SparklyPaper - parallel world ticking
throw new IllegalStateException(ex);
}
}
@@ -151,7 +164,7 @@ index a4aa2615823d77920ff55b8aa0bcc27a54b8c3e1..2fb65ce228da94eb7d9364ee0f945823
public final int id; /* We don't override getId as the spec requires that it be unique (with respect to all other threads) */
private static final AtomicInteger ID_GENERATOR = new AtomicInteger();
@@ -133,46 +192,74 @@ public class TickThread extends Thread {
@@ -133,46 +200,74 @@ public class TickThread extends Thread {
}
public static boolean isTickThreadFor(final Level world, final BlockPos pos) {
@@ -255,10 +268,10 @@ index 548fcd9646dee0c40b6ba9b3dafb9ca157dfe324..d7af94890bfccd6ff665d920cecfa1e5
} else if (!event.isAsynchronous() && !this.server.isPrimaryThread() && !this.server.isStopping()) {
// Leaf start - Multithreaded tracker
diff --git a/src/main/java/org/bukkit/craftbukkit/CraftWorld.java b/src/main/java/org/bukkit/craftbukkit/CraftWorld.java
index af33cab59932f4ec135caf94dc5828930833daf6..caa92e48d031cb54950e6613a82f407d7ed2455a 100644
index 0d2cfaef1413a343bc03829730453b03f903d5ce..bf87e5dcda7deb8f9c36a3f6b64285a97e48477f 100644
--- a/src/main/java/org/bukkit/craftbukkit/CraftWorld.java
+++ b/src/main/java/org/bukkit/craftbukkit/CraftWorld.java
@@ -455,7 +455,12 @@ public class CraftWorld extends CraftRegionAccessor implements World {
@@ -456,7 +456,12 @@ public class CraftWorld extends CraftRegionAccessor implements World {
}
private boolean unloadChunk0(int x, int z, boolean save) {
@@ -272,7 +285,7 @@ index af33cab59932f4ec135caf94dc5828930833daf6..caa92e48d031cb54950e6613a82f407d
if (!this.isChunkLoaded(x, z)) {
return true;
}
@@ -472,6 +477,8 @@ public class CraftWorld extends CraftRegionAccessor implements World {
@@ -473,6 +478,8 @@ public class CraftWorld extends CraftRegionAccessor implements World {
@Override
public boolean refreshChunk(int x, int z) {
@@ -281,7 +294,7 @@ index af33cab59932f4ec135caf94dc5828930833daf6..caa92e48d031cb54950e6613a82f407d
ChunkHolder playerChunk = this.world.getChunkSource().chunkMap.getVisibleChunkIfPresent(ChunkPos.asLong(x, z));
if (playerChunk == null) return false;
@@ -522,7 +529,12 @@ public class CraftWorld extends CraftRegionAccessor implements World {
@@ -523,7 +530,12 @@ public class CraftWorld extends CraftRegionAccessor implements World {
@Override
public boolean loadChunk(int x, int z, boolean generate) {
@@ -295,7 +308,7 @@ index af33cab59932f4ec135caf94dc5828930833daf6..caa92e48d031cb54950e6613a82f407d
warnUnsafeChunk("loading a faraway chunk", x, z); // Paper
ChunkAccess chunk = this.world.getChunkSource().getChunk(x, z, generate || isChunkGenerated(x, z) ? ChunkStatus.FULL : ChunkStatus.EMPTY, true); // Paper
@@ -750,6 +762,8 @@ public class CraftWorld extends CraftRegionAccessor implements World {
@@ -751,6 +763,8 @@ public class CraftWorld extends CraftRegionAccessor implements World {
@Override
public boolean generateTree(Location loc, TreeType type, BlockChangeDelegate delegate) {
@@ -304,7 +317,7 @@ index af33cab59932f4ec135caf94dc5828930833daf6..caa92e48d031cb54950e6613a82f407d
this.world.captureTreeGeneration = true;
this.world.captureBlockStates = true;
boolean grownTree = this.generateTree(loc, type);
@@ -865,6 +879,8 @@ public class CraftWorld extends CraftRegionAccessor implements World {
@@ -866,6 +880,8 @@ public class CraftWorld extends CraftRegionAccessor implements World {
}
public boolean createExplosion(double x, double y, double z, float power, boolean setFire, boolean breakBlocks, Entity source, Consumer<net.minecraft.world.level.ServerExplosion> configurator) {
// Paper end - expand explosion API
@@ -313,7 +326,7 @@ index af33cab59932f4ec135caf94dc5828930833daf6..caa92e48d031cb54950e6613a82f407d
net.minecraft.world.level.Level.ExplosionInteraction explosionType;
if (!breakBlocks) {
explosionType = net.minecraft.world.level.Level.ExplosionInteraction.NONE; // Don't break blocks
@@ -986,6 +1002,8 @@ public class CraftWorld extends CraftRegionAccessor implements World {
@@ -987,6 +1003,8 @@ public class CraftWorld extends CraftRegionAccessor implements World {
@Override
public void setBiome(int x, int y, int z, Holder<net.minecraft.world.level.biome.Biome> bb) {
BlockPos pos = new BlockPos(x, 0, z);
@@ -322,7 +335,7 @@ index af33cab59932f4ec135caf94dc5828930833daf6..caa92e48d031cb54950e6613a82f407d
if (this.world.hasChunkAt(pos)) {
net.minecraft.world.level.chunk.LevelChunk chunk = this.world.getChunkAt(pos);
@@ -2328,6 +2346,8 @@ public class CraftWorld extends CraftRegionAccessor implements World {
@@ -2334,6 +2352,8 @@ public class CraftWorld extends CraftRegionAccessor implements World {
@Override
public void sendGameEvent(Entity sourceEntity, org.bukkit.GameEvent gameEvent, Vector position) {
@@ -332,10 +345,10 @@ index af33cab59932f4ec135caf94dc5828930833daf6..caa92e48d031cb54950e6613a82f407d
}
// 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 811823a1a7e24a19a7e37eb4c08efdfa19e839ed..ac45c5cbe547705e3e341011740cf911c39f80c0 100644
index b00a82816784ea2f6422ca98c1f11597105cc177..04c8902bcf8d19e59c57ac013a33b0a2fb1190da 100644
--- a/src/main/java/org/bukkit/craftbukkit/block/CraftBlock.java
+++ b/src/main/java/org/bukkit/craftbukkit/block/CraftBlock.java
@@ -74,13 +74,98 @@ public class CraftBlock implements Block {
@@ -74,12 +74,97 @@ public class CraftBlock implements Block {
return new CraftBlock(world, position);
}
@@ -383,7 +396,7 @@ index 811823a1a7e24a19a7e37eb4c08efdfa19e839ed..ac45c5cbe547705e3e341011740cf911
+ } catch (java.util.concurrent.CompletionException e) {
+ // Leaf start - SparklyPaper - parallel world ticking - Shutdown handling for async reads
+ if (e.getCause() instanceof IllegalStateException && e.getCause().getMessage() != null && e.getCause().getMessage().contains("shutting down")) {
+ org.bukkit.Bukkit.getLogger().log(java.util.logging.Level.WARNING, "PWT: Async block read for " + methodName + " cancelled due to world shutdown: " + e.getCause().getMessage());
+ org.bukkit.Bukkit.getLogger().log(java.util.logging.Level.WARNING, "PWT: Async block read for " + methodName + " cancelled due to world shutdown: " + e.getCause().getMessage());
+ } else {
+ org.bukkit.Bukkit.getLogger().log(java.util.logging.Level.SEVERE, "PWT: Async block read failed for " + methodName + " on tick thread.", e.getCause() != null ? e.getCause() : e);
+ }
@@ -418,7 +431,6 @@ index 811823a1a7e24a19a7e37eb4c08efdfa19e839ed..ac45c5cbe547705e3e341011740cf911
+ // Leaf end - SparklyPaper - parallel world ticking
}
// Paper start
public net.minecraft.world.level.material.FluidState getNMSFluid() {
- return this.world.getFluidState(this.position);
+ // Leaf start - SparklyPaper - parallel world ticking
@@ -434,42 +446,42 @@ index 811823a1a7e24a19a7e37eb4c08efdfa19e839ed..ac45c5cbe547705e3e341011740cf911
+ }
+ // Leaf end - SparklyPaper - parallel world ticking
}
// Paper end
@@ -144,10 +229,12 @@ public class CraftBlock implements Block {
public BlockPos getPosition() {
@@ -142,10 +227,12 @@ public class CraftBlock implements Block {
return this.getWorld().getChunkAt(this);
}
+ @Deprecated // Leaf - SparklyPaper - parallel world ticking - Magic value
public void setData(final byte data) {
this.setData(data, 3);
this.setData(data, net.minecraft.world.level.block.Block.UPDATE_ALL);
}
+ @Deprecated // Leaf - SparklyPaper - parallel world ticking - Magic value
public void setData(final byte data, boolean applyPhysics) {
if (applyPhysics) {
this.setData(data, 3);
@@ -157,12 +244,18 @@ public class CraftBlock implements Block {
this.setData(data, net.minecraft.world.level.block.Block.UPDATE_ALL);
@@ -155,12 +242,18 @@ public class CraftBlock implements Block {
}
private void setData(final byte data, int flag) {
private void setData(final byte data, int flags) {
+ // SparklyPaper start - parallel world ticking
+ if (org.dreeam.leaf.config.modules.async.SparklyPaperParallelWorldTicking.enabled && world instanceof ServerLevel serverWorld) { // Leaf - SparklyPaper - parallel world ticking mod (make configurable)
+ ca.spottedleaf.moonrise.common.util.TickThread.ensureTickThread(serverWorld, position, "Cannot modify world asynchronously");
+ }
+ // SparklyPaper end - parallel world ticking
this.world.setBlock(this.position, CraftMagicNumbers.getBlock(this.getType(), data), flag);
this.world.setBlock(this.position, CraftMagicNumbers.getBlock(this.getType(), data), flags);
}
@Override
+ @Deprecated // Leaf - SparklyPaper - parallel world ticking - Magic value
public byte getData() {
- net.minecraft.world.level.block.state.BlockState blockData = this.world.getBlockState(this.position);
+ net.minecraft.world.level.block.state.BlockState blockData = this.getNMS(); // Leaf - SparklyPaper - parallel world ticking
return CraftMagicNumbers.toLegacyData(blockData);
- net.minecraft.world.level.block.state.BlockState state = this.world.getBlockState(this.position);
+ net.minecraft.world.level.block.state.BlockState state = this.getNMS(); // Leaf - SparklyPaper - parallel world ticking
return CraftMagicNumbers.toLegacyData(state);
}
@@ -179,6 +272,7 @@ public class CraftBlock implements Block {
@@ -177,6 +270,7 @@ public class CraftBlock implements Block {
@Override
public void setType(Material type, boolean applyPhysics) {
Preconditions.checkArgument(type != null, "Material cannot be null");
@@ -477,20 +489,19 @@ index 811823a1a7e24a19a7e37eb4c08efdfa19e839ed..ac45c5cbe547705e3e341011740cf911
this.setBlockData(type.createBlockData(), applyPhysics);
}
@@ -198,6 +292,12 @@ public class CraftBlock implements Block {
@@ -196,6 +290,11 @@ public class CraftBlock implements Block {
}
public static boolean setTypeAndData(LevelAccessor world, BlockPos position, net.minecraft.world.level.block.state.BlockState old, net.minecraft.world.level.block.state.BlockState blockData, boolean applyPhysics) {
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) {
+ // SparklyPaper start - parallel world ticking
+ if (org.dreeam.leaf.config.modules.async.SparklyPaperParallelWorldTicking.enabled && world instanceof ServerLevel serverWorld) { // Leaf - SparklyPaper - parallel world ticking mod (make configurable)
+ ca.spottedleaf.moonrise.common.util.TickThread.ensureTickThread(serverWorld, position, "Cannot modify world asynchronously");
+ ca.spottedleaf.moonrise.common.util.TickThread.ensureTickThread(serverWorld, pos, "Cannot modify world asynchronously");
+ }
+ // SparklyPaper end - parallel world ticking
+
// SPIGOT-611: need to do this to prevent glitchiness. Easier to handle this here (like /setblock) than to fix weirdness in tile entity cleanup
if (old.hasBlockEntity() && blockData.getBlock() != old.getBlock()) { // SPIGOT-3725 remove old tile entity if block changes
// 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
@@ -226,22 +326,62 @@ public class CraftBlock implements Block {
@@ -227,22 +326,62 @@ public class CraftBlock implements Block {
@Override
public Material getType() {
@@ -557,12 +568,7 @@ index 811823a1a7e24a19a7e37eb4c08efdfa19e839ed..ac45c5cbe547705e3e341011740cf911
}
public Block getFace(final BlockFace face) {
@@ -282,51 +422,37 @@ public class CraftBlock implements Block {
@Override
public String toString() {
- return "CraftBlock{pos=" + this.position + ",type=" + this.getType() + ",data=" + this.getNMS() + ",fluid=" + this.world.getFluidState(this.position) + '}';
+ return "CraftBlock{pos=" + this.position + ",type=" + this.getType() + ",data=" + this.getNMS() + ",fluid=" + this.getNMSFluid() + '}'; // Leaf - SparklyPaper - parallel world ticking
@@ -287,47 +426,32 @@ public class CraftBlock implements Block {
}
public static BlockFace notchToBlockFace(Direction notch) {
@@ -594,7 +600,6 @@ index 811823a1a7e24a19a7e37eb4c08efdfa19e839ed..ac45c5cbe547705e3e341011740cf911
+ case SOUTH -> BlockFace.SOUTH;
+ case WEST -> BlockFace.WEST;
+ case EAST -> BlockFace.EAST;
+ default -> BlockFace.SELF;
+ };
+ // Leaf end - SparklyPaper - parallel world ticking - formatting
}
@@ -634,7 +639,7 @@ index 811823a1a7e24a19a7e37eb4c08efdfa19e839ed..ac45c5cbe547705e3e341011740cf911
}
@Override
@@ -343,18 +469,65 @@ public class CraftBlock implements Block {
@@ -344,18 +468,65 @@ public class CraftBlock implements Block {
@Override
public Biome getBiome() {
@@ -702,7 +707,7 @@ index 811823a1a7e24a19a7e37eb4c08efdfa19e839ed..ac45c5cbe547705e3e341011740cf911
this.getWorld().setBiome(this.getX(), this.getY(), this.getZ(), bio);
}
@@ -370,12 +543,50 @@ public class CraftBlock implements Block {
@@ -371,12 +542,50 @@ public class CraftBlock implements Block {
@Override
public boolean isBlockPowered() {
@@ -755,7 +760,7 @@ index 811823a1a7e24a19a7e37eb4c08efdfa19e839ed..ac45c5cbe547705e3e341011740cf911
}
@Override
@@ -397,46 +608,102 @@ public class CraftBlock implements Block {
@@ -398,44 +607,103 @@ public class CraftBlock implements Block {
@Override
public boolean isBlockFacePowered(BlockFace face) {
@@ -781,10 +786,6 @@ index 811823a1a7e24a19a7e37eb4c08efdfa19e839ed..ac45c5cbe547705e3e341011740cf911
@Override
public boolean isBlockFaceIndirectlyPowered(BlockFace face) {
- int power = this.world.getMinecraftWorld().getSignal(this.position, CraftBlock.blockFaceToNotch(face));
-
- Block relative = this.getRelative(face);
- if (relative.getType() == Material.REDSTONE_WIRE) {
- return Math.max(power, relative.getData()) > 0;
+ // Leaf start - SparklyPaper - parallel world ticking
+ ServerLevel level = getServerLevel();
+ String handlingMode = org.dreeam.leaf.config.modules.async.SparklyPaperParallelWorldTicking.asyncUnsafeReadHandling;
@@ -805,9 +806,13 @@ index 811823a1a7e24a19a7e37eb4c08efdfa19e839ed..ac45c5cbe547705e3e341011740cf911
+ return false;
+ } catch (Exception e) {
+ org.bukkit.Bukkit.getLogger().log(java.util.logging.Level.SEVERE, "PWT: Direct access failed for isBlockFaceIndirectlyPowered" + (level == null ? " (Not a ServerLevel)" : ""), e);
- Block relative = this.getRelative(face);
- if (relative.getType() == Material.REDSTONE_WIRE) {
- return Math.max(power, relative.getData()) > 0; // todo remove legacy usage
+ return false;
}
-
- return power > 0;
+ // Leaf end - SparklyPaper - parallel world ticking
}
@@ -829,24 +834,22 @@ index 811823a1a7e24a19a7e37eb4c08efdfa19e839ed..ac45c5cbe547705e3e341011740cf911
- return power > 0 ? power : (face == BlockFace.SELF ? this.isBlockIndirectlyPowered() : this.isBlockFaceIndirectlyPowered(face)) ? 15 : 0;
- }
-
- private static int getPower(int i, net.minecraft.world.level.block.state.BlockState iblockdata) {
- if (!iblockdata.is(Blocks.REDSTONE_WIRE)) {
- return i;
- private static int getPower(int power, net.minecraft.world.level.block.state.BlockState state) {
- if (!state.is(Blocks.REDSTONE_WIRE)) {
- return power;
+ ServerLevel level = getServerLevel();
+ String handlingMode = org.dreeam.leaf.config.modules.async.SparklyPaperParallelWorldTicking.asyncUnsafeReadHandling;
+
+ 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 {
- int j = iblockdata.getValue(RedStoneWireBlock.POWER);
+ } else {
+ // Strict/Disabled/Non-ServerLevel path
+ checkStrictMode(level, handlingMode, "getBlockPower");
+ try {
+ // Requires Level for hasSignal and getBlockState
+ if (this.world instanceof net.minecraft.world.level.Level nmsLevel) {
+ int power = 0;
+ int x = this.getX(); int y = this.getY(); int z = this.getZ();
+ BlockPos currentPos = this.position; // Use immutable position
+
+ // Check neighbors using relative positions
@@ -870,13 +873,13 @@ index 811823a1a7e24a19a7e37eb4c08efdfa19e839ed..ac45c5cbe547705e3e341011740cf911
+ }
+ }
+ }
- return j > i ? j : i;
+
+ // 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 {
} else {
- return Math.max(state.getValue(RedStoneWireBlock.POWER), power);
+ int neighborPower = neighborState.getValue(RedStoneWireBlock.POWER);
+ return Math.max(neighborPower, currentMax);
}
@@ -885,7 +888,7 @@ index 811823a1a7e24a19a7e37eb4c08efdfa19e839ed..ac45c5cbe547705e3e341011740cf911
@Override
public int getBlockPower() {
@@ -479,105 +746,179 @@ public class CraftBlock implements Block {
@@ -478,106 +746,180 @@ public class CraftBlock implements Block {
@Override
public PistonMoveReaction getPistonMoveReaction() {
@@ -939,20 +942,21 @@ index 811823a1a7e24a19a7e37eb4c08efdfa19e839ed..ac45c5cbe547705e3e341011740cf911
+ }
+
+ // Get NMS state safely
net.minecraft.world.level.block.state.BlockState iblockdata = this.getNMS();
net.minecraft.world.level.block.Block block = iblockdata.getBlock();
+
net.minecraft.world.level.block.state.BlockState state = this.getNMS();
net.minecraft.world.level.block.Block block = state.getBlock();
net.minecraft.world.item.ItemStack nmsItem = CraftItemStack.asNMSCopy(item);
- boolean result = false;
-
- // Modelled off EntityHuman#hasBlock
- if (block != Blocks.AIR && (item == null || !iblockdata.requiresCorrectToolForDrops() || nmsItem.isCorrectToolForDrops(iblockdata))) {
- net.minecraft.world.level.block.Block.dropResources(iblockdata, this.world.getMinecraftWorld(), this.position, this.world.getBlockEntity(this.position), null, nmsItem, false); // Paper - Properly handle xp dropping
- // Paper start - improve Block#breanNaturally
- // Modelled off Player#hasCorrectToolForDrops
- if (block != Blocks.AIR && (item == null || !state.requiresCorrectToolForDrops() || nmsItem.isCorrectToolForDrops(state))) {
- net.minecraft.world.level.block.Block.dropResources(state, this.world.getMinecraftWorld(), this.position, this.world.getBlockEntity(this.position), null, nmsItem, false); // Paper - Properly handle xp dropping
- // Paper start - improve Block#breakNaturally
- if (triggerEffect) {
- if (iblockdata.getBlock() instanceof net.minecraft.world.level.block.BaseFireBlock) {
- if (state.getBlock() instanceof net.minecraft.world.level.block.BaseFireBlock) {
- this.world.levelEvent(net.minecraft.world.level.block.LevelEvent.SOUND_EXTINGUISH_FIRE, this.position, 0);
- } else {
- this.world.levelEvent(net.minecraft.world.level.block.LevelEvent.PARTICLES_DESTROY_BLOCK, this.position, net.minecraft.world.level.block.Block.getId(iblockdata));
- this.world.levelEvent(net.minecraft.world.level.block.LevelEvent.PARTICLES_DESTROY_BLOCK, this.position, net.minecraft.world.level.block.Block.getId(state));
+ boolean droppedItems = false;
+
+ // Experience dropping requires ServerLevel
@@ -960,73 +964,71 @@ index 811823a1a7e24a19a7e37eb4c08efdfa19e839ed..ac45c5cbe547705e3e341011740cf911
+
+ if (serverLevelForDrops != null) { // Only attempt drops/XP if we have a ServerLevel
+ // Check if block should drop items
+ if (!iblockdata.isAir() && (item == null || !iblockdata.requiresCorrectToolForDrops() || nmsItem.isCorrectToolForDrops(iblockdata))) {
+ if (!state.isAir() && (item == null || !state.requiresCorrectToolForDrops() || nmsItem.isCorrectToolForDrops(state))) {
+ // Drop items using ServerLevel
+ net.minecraft.world.level.block.Block.dropResources(iblockdata, serverLevelForDrops, this.position, this.world.getBlockEntity(this.position), null, nmsItem, false);
+ net.minecraft.world.level.block.Block.dropResources(state, serverLevelForDrops, this.position, this.world.getBlockEntity(this.position), null, nmsItem, false);
+
+ // Trigger effect using LevelAccessor (safe)
+ if (triggerEffect) {
+ int eventId = (iblockdata.getBlock() instanceof net.minecraft.world.level.block.BaseFireBlock)
+ int eventId = (state.getBlock() instanceof net.minecraft.world.level.block.BaseFireBlock)
+ ? net.minecraft.world.level.block.LevelEvent.SOUND_EXTINGUISH_FIRE
+ : net.minecraft.world.level.block.LevelEvent.PARTICLES_DESTROY_BLOCK;
+ int eventData = (eventId == net.minecraft.world.level.block.LevelEvent.PARTICLES_DESTROY_BLOCK)
+ ? net.minecraft.world.level.block.Block.getId(iblockdata) : 0;
+ ? net.minecraft.world.level.block.Block.getId(state) : 0;
+ this.world.levelEvent(eventId, this.position, eventData);
}
+ }
+ // Drop experience using ServerLevel
+ if (dropExperience) {
+ int xp = block.getExpDrop(iblockdata, serverLevelForDrops, this.position, nmsItem, true);
+ int xp = block.getExpDrop(state, serverLevelForDrops, this.position, nmsItem, true);
+ if (xp > 0) { // Only pop if there's XP to drop
+ block.popExperience(serverLevelForDrops, this.position, xp);
+ }
+ }
}
+ droppedItems = true;
+ }
+ } else {
+ // Log if we couldn't drop XP because it wasn't a ServerLevel
+ if (dropExperience && !iblockdata.isAir()) { // Only warn if XP was requested and block wasn't air
+ 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 && !iblockdata.isAir()) {
+ int eventId = (iblockdata.getBlock() instanceof net.minecraft.world.level.block.BaseFireBlock)
+ if (triggerEffect && !state.isAir()) {
+ int eventId = (state.getBlock() instanceof net.minecraft.world.level.block.BaseFireBlock)
+ ? net.minecraft.world.level.block.LevelEvent.SOUND_EXTINGUISH_FIRE
+ : net.minecraft.world.level.block.LevelEvent.PARTICLES_DESTROY_BLOCK;
+ int eventData = (eventId == net.minecraft.world.level.block.LevelEvent.PARTICLES_DESTROY_BLOCK)
+ ? net.minecraft.world.level.block.Block.getId(iblockdata) : 0;
+ ? net.minecraft.world.level.block.Block.getId(state) : 0;
+ this.world.levelEvent(eventId, this.position, eventData);
}
- if (dropExperience) block.popExperience(this.world.getMinecraftWorld(), this.position, block.getExpDrop(iblockdata, this.world.getMinecraftWorld(), this.position, nmsItem, true));
- if (dropExperience) block.popExperience(this.world.getMinecraftWorld(), this.position, block.getExpDrop(state, this.world.getMinecraftWorld(), this.position, nmsItem, true));
- // Paper end
- result = true;
}
- // SPIGOT-6778: Directly call setBlock instead of setTypeAndData, so that the tile entiy is not removed and custom remove logic is run.
- // 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) {
+ // Call destroy hook using LevelAccessor (safe)
block.destroy(this.world, this.position, iblockdata);
block.destroy(this.world, this.position, state);
}
- if (result) {
- // special cases
+
+ // Special case handling - requires Level, check again
+ if (droppedItems && this.world instanceof net.minecraft.world.level.Level nmsLevelForSpecialCases) {
if (block instanceof net.minecraft.world.level.block.IceBlock iceBlock) {
- iceBlock.afterDestroy(this.world.getMinecraftWorld(), this.position, nmsItem);
+ iceBlock.afterDestroy(nmsLevelForSpecialCases, this.position, nmsItem);
} else if (block instanceof net.minecraft.world.level.block.TurtleEggBlock turtleEggBlock) {
- turtleEggBlock.decreaseEggs(this.world.getMinecraftWorld(), this.position, iblockdata);
+ turtleEggBlock.decreaseEggs(nmsLevelForSpecialCases, this.position, iblockdata);
- turtleEggBlock.decreaseEggs(this.world.getMinecraftWorld(), this.position, state);
+ turtleEggBlock.decreaseEggs(nmsLevelForSpecialCases, this.position, state);
}
+ } else if (droppedItems) { // Log if special cases couldn't run
+ org.bukkit.Bukkit.getLogger().log(java.util.logging.Level.WARNING, "PWT: Cannot perform post-break special actions: Not a Level.");
}
- return destroyed && result;
- // Paper end
+
+ // Return true if the block was successfully destroyed AND items were dropped (or would have dropped if tool was right)
+ return destroyed && droppedItems;
+ // Leaf end - SparklyPaper - parallel world ticking - Write operation check
@@ -1056,20 +1058,20 @@ index 811823a1a7e24a19a7e37eb4c08efdfa19e839ed..ac45c5cbe547705e3e341011740cf911
- UseOnContext context = new UseOnContext(world, null, InteractionHand.MAIN_HAND, Items.BONE_MEAL.getDefaultInstance(), new BlockHitResult(Vec3.ZERO, direction, this.getPosition(), false));
+ UseOnContext context = new UseOnContext(level, null, InteractionHand.MAIN_HAND, Items.BONE_MEAL.getDefaultInstance(), new BlockHitResult(Vec3.ZERO, direction, this.getPosition(), false));
- // SPIGOT-6895: Call StructureGrowEvent and BlockFertilizeEvent
// SPIGOT-6895: Call StructureGrowEvent and BlockFertilizeEvent
- world.captureTreeGeneration = true;
+ level.captureTreeGeneration = true;
InteractionResult result = BoneMealItem.applyBonemeal(context);
- world.captureTreeGeneration = false;
-
- if (world.capturedBlockStates.size() > 0) {
- if (!world.capturedBlockStates.isEmpty()) {
- TreeType treeType = SaplingBlock.treeType;
- SaplingBlock.treeType = null;
- List<BlockState> blocks = new ArrayList<>(world.capturedBlockStates.values());
- List<BlockState> states = new ArrayList<>(world.capturedBlockStates.values());
- world.capturedBlockStates.clear();
+ level.captureTreeGeneration = false;
+
+ if (level.capturedBlockStates.size() > 0) {
+ if (level.capturedBlockStates.isEmpty()) {
+ TreeType treeType = SaplingBlock.getTreeTypeRT(); // Use thread-local getter
+ SaplingBlock.setTreeTypeRT(null); // Use thread-local setter
+ // Need Bukkit BlockState list for events
@@ -1078,24 +1080,25 @@ index 811823a1a7e24a19a7e37eb4c08efdfa19e839ed..ac45c5cbe547705e3e341011740cf911
StructureGrowEvent structureEvent = null;
if (treeType != null) {
- structureEvent = new StructureGrowEvent(this.getLocation(), treeType, true, null, blocks);
- structureEvent = new StructureGrowEvent(this.getLocation(), treeType, true, null, states);
+ structureEvent = new StructureGrowEvent(this.getLocation(), treeType, true, null, bukkitStates);
Bukkit.getPluginManager().callEvent(structureEvent);
}
- event = new BlockFertilizeEvent(CraftBlock.at(world, this.getPosition()), null, blocks);
- event = new BlockFertilizeEvent(CraftBlock.at(world, this.getPosition()), null, states);
+ event = new BlockFertilizeEvent(this, null, bukkitStates); // Use 'this' as the CraftBlock
event.setCancelled(structureEvent != null && structureEvent.isCancelled());
Bukkit.getPluginManager().callEvent(event);
if (!event.isCancelled()) {
- for (BlockState blockstate : blocks) {
- blockstate.update(true);
- world.checkCapturedTreeStateForObserverNotify(this.position, (org.bukkit.craftbukkit.block.CraftBlockState) blockstate); // Paper - notify observers even if grow failed
+ for (org.bukkit.block.BlockState blockstate : bukkitStates) {
+ blockstate.update(true); // This performs the actual block changes
- for (BlockState state : states) {
+ for (BlockState state : bukkitStates) {
CraftBlockState craftBlockState = (CraftBlockState) state;
- craftBlockState.place(craftBlockState.getFlags());
- world.checkCapturedTreeStateForObserverNotify(this.position, craftBlockState); // Paper - notify observers even if grow failed
+ craftBlockState.place(craftBlockState.getFlags()); // This performs the actual block changes
+ // Notify observers using the captured state info
+ level.checkCapturedTreeStateForObserverNotify(this.position, (org.bukkit.craftbukkit.block.CraftBlockState) blockstate);
+ level.checkCapturedTreeStateForObserverNotify(this.position, craftBlockState);
}
}
}
@@ -1106,11 +1109,11 @@ index 811823a1a7e24a19a7e37eb4c08efdfa19e839ed..ac45c5cbe547705e3e341011740cf911
}
@Override
@@ -592,31 +933,70 @@ public class CraftBlock implements Block {
@@ -592,31 +934,70 @@ public class CraftBlock implements Block {
@Override
public Collection<ItemStack> getDrops(ItemStack item, Entity entity) {
- net.minecraft.world.level.block.state.BlockState iblockdata = this.getNMS();
- net.minecraft.world.level.block.state.BlockState state = this.getNMS();
- net.minecraft.world.item.ItemStack nms = CraftItemStack.asNMSCopy(item);
+ // Leaf start - SparklyPaper - parallel world ticking - Write operation check
+ // Requires ServerLevel for Block.getDrops call
@@ -1120,9 +1123,9 @@ index 811823a1a7e24a19a7e37eb4c08efdfa19e839ed..ac45c5cbe547705e3e341011740cf911
+ return Collections.emptyList();
+ }
- // Modelled off EntityHuman#hasBlock
- if (item == null || CraftBlockData.isPreferredTool(iblockdata, nms)) {
- return net.minecraft.world.level.block.Block.getDrops(iblockdata, (ServerLevel) this.world.getMinecraftWorld(), this.position, this.world.getBlockEntity(this.position), entity == null ? null : ((CraftEntity) entity).getHandle(), nms)
- // Modelled off Player#hasCorrectToolForDrops
- if (item == null || CraftBlockData.isPreferredTool(state, nms)) {
- return net.minecraft.world.level.block.Block.getDrops(state, this.world.getMinecraftWorld(), this.position, this.world.getBlockEntity(this.position), entity == null ? null : ((CraftEntity) entity).getHandle(), nms)
- .stream().map(CraftItemStack::asBukkitCopy).collect(Collectors.toList());
- } else {
+ // Strict check if applicable
@@ -1130,15 +1133,15 @@ index 811823a1a7e24a19a7e37eb4c08efdfa19e839ed..ac45c5cbe547705e3e341011740cf911
+ checkStrictMode(level, handlingMode, "getDrops");
+
+ try {
+ net.minecraft.world.level.block.state.BlockState iblockdata = this.getNMS(); // Use safe getNMS
+ net.minecraft.world.level.block.state.BlockState state = this.getNMS(); // Use safe getNMS
+ net.minecraft.world.item.ItemStack nmsItem = CraftItemStack.asNMSCopy(item);
+ net.minecraft.world.entity.Entity nmsEntity = (entity == null) ? null : ((CraftEntity) entity).getHandle();
+
+ // Check tool requirement
+ if (item == null || !iblockdata.requiresCorrectToolForDrops() || nmsItem.isCorrectToolForDrops(iblockdata)) {
+ if (item == null || !state.requiresCorrectToolForDrops() || nmsItem.isCorrectToolForDrops(state)) {
+ // Call NMS getDrops using the verified ServerLevel
+ List<net.minecraft.world.item.ItemStack> nmsDrops = net.minecraft.world.level.block.Block.getDrops(
+ iblockdata, level, this.position, this.world.getBlockEntity(this.position), nmsEntity, nmsItem
+ state, level, this.position, this.world.getBlockEntity(this.position), nmsEntity, nmsItem
+ );
+ // Convert to Bukkit ItemStacks
+ return nmsDrops.stream().map(CraftItemStack::asBukkitCopy).collect(Collectors.toList());
@@ -1156,11 +1159,11 @@ index 811823a1a7e24a19a7e37eb4c08efdfa19e839ed..ac45c5cbe547705e3e341011740cf911
@Override
public boolean isPreferredTool(ItemStack item) {
+ // Leaf - SparklyPaper - parallel world ticking - Uses safe getNMS()
net.minecraft.world.level.block.state.BlockState iblockdata = this.getNMS();
net.minecraft.world.level.block.state.BlockState state = this.getNMS();
- net.minecraft.world.item.ItemStack nms = CraftItemStack.asNMSCopy(item);
- return CraftBlockData.isPreferredTool(iblockdata, nms);
- return CraftBlockData.isPreferredTool(state, nms);
+ net.minecraft.world.item.ItemStack nmsItem = CraftItemStack.asNMSCopy(item);
+ return iblockdata.requiresCorrectToolForDrops() && nmsItem.isCorrectToolForDrops(iblockdata); // Leaf - SparklyPaper - parallel world ticking - Delegate to helper which checks tool tags
+ return state.requiresCorrectToolForDrops() && nmsItem.isCorrectToolForDrops(state); // Leaf - SparklyPaper - parallel world ticking - Delegate to helper which checks tool tags
}
@Override
@@ -1187,7 +1190,7 @@ index 811823a1a7e24a19a7e37eb4c08efdfa19e839ed..ac45c5cbe547705e3e341011740cf911
@Override
public void setMetadata(String metadataKey, MetadataValue newMetadataValue) {
this.getCraftWorld().getBlockMetadata().setMetadata(this, metadataKey, newMetadataValue);
@@ -639,57 +1019,147 @@ public class CraftBlock implements Block {
@@ -639,57 +1020,148 @@ public class CraftBlock implements Block {
@Override
public boolean isPassable() {
@@ -1229,7 +1232,7 @@ index 811823a1a7e24a19a7e37eb4c08efdfa19e839ed..ac45c5cbe547705e3e341011740cf911
- }
-
- Vector dir = direction.clone().normalize().multiply(maxDistance);
- Vec3 startPos = CraftLocation.toVec3D(start);
- Vec3 startPos = CraftLocation.toVec3(start);
- Vec3 endPos = startPos.add(dir.getX(), dir.getY(), dir.getZ());
+ if (maxDistance < 0.0D) return null; // Max distance must be non-negative
+
@@ -1244,27 +1247,27 @@ index 811823a1a7e24a19a7e37eb4c08efdfa19e839ed..ac45c5cbe547705e3e341011740cf911
+ null, "rayTrace"
+ );
+ // Convert NMS result (can be null) to Bukkit result
+ return CraftRayTraceResult.fromNMS(this.getWorld(), nmsHitResult);
+ return CraftRayTraceResult.convertFromInternal(this.world, nmsHitResult);
+ } else {
+ // Strict/Disabled/Non-ServerLevel path
+ checkStrictMode(level, handlingMode, "rayTrace");
+ try {
+ // Calculate start and end points for the ray trace
+ Vec3 startPos = CraftLocation.toVec3D(start);
+ Vec3 startPos = CraftLocation.toVec3(start);
+ Vector dirNormalized = direction.clone().normalize(); // Normalize once
+ Vec3 endPos = startPos.add(dirNormalized.getX() * maxDistance, dirNormalized.getY() * maxDistance, dirNormalized.getZ() * maxDistance);
+
+ // Perform the clip using LevelAccessor (safe)
+ // Pass the block's position as the context position for the clip function
+ HitResult nmsHitResult = this.world.clip(
+ new ClipContext(startPos, endPos, ClipContext.Block.OUTLINE, CraftFluidCollisionMode.toNMS(fluidCollisionMode), CollisionContext.empty()),
+ new ClipContext(startPos, endPos, ClipContext.Block.OUTLINE, CraftFluidCollisionMode.toFluid(fluidCollisionMode), CollisionContext.empty()),
+ this.position // Provide the block's position here
+ );
- HitResult nmsHitResult = this.world.clip(new ClipContext(startPos, endPos, ClipContext.Block.OUTLINE, CraftFluidCollisionMode.toNMS(fluidCollisionMode), CollisionContext.empty()), this.position);
- return CraftRayTraceResult.fromNMS(this.getWorld(), nmsHitResult);
- HitResult hitResult = this.world.clip(new ClipContext(startPos, endPos, ClipContext.Block.OUTLINE, CraftFluidCollisionMode.toFluid(fluidCollisionMode), CollisionContext.empty()), this.position);
- return CraftRayTraceResult.convertFromInternal(this.world, hitResult);
+ // Convert NMS result to Bukkit result
+ return CraftRayTraceResult.fromNMS(this.getWorld(), nmsHitResult);
+ return CraftRayTraceResult.convertFromInternal(this.world, nmsHitResult);
+ } catch (Exception e) {
+ org.bukkit.Bukkit.getLogger().log(java.util.logging.Level.SEVERE, "PWT: Direct access failed for rayTrace" + (level == null ? " (Not a ServerLevel)" : ""), e);
+ return null; // Return null on error
@@ -1303,7 +1306,7 @@ index 811823a1a7e24a19a7e37eb4c08efdfa19e839ed..ac45c5cbe547705e3e341011740cf911
+ // Default to a full 1x1x1 box on error
+ return new BoundingBox(getX(), getY(), getZ(), getX() + 1, getY() + 1, getZ() + 1);
}
-
- AABB aabb = shape.bounds();
- return new BoundingBox(this.getX() + aabb.minX, this.getY() + aabb.minY, this.getZ() + aabb.minZ, this.getX() + aabb.maxX, this.getY() + aabb.maxY, this.getZ() + aabb.maxZ);
+ // Leaf end - SparklyPaper - parallel world ticking
@@ -1359,7 +1362,7 @@ index 811823a1a7e24a19a7e37eb4c08efdfa19e839ed..ac45c5cbe547705e3e341011740cf911
}
@Override
@@ -700,7 +1170,10 @@ public class CraftBlock implements Block {
@@ -705,7 +1177,10 @@ public class CraftBlock implements Block {
// Paper start
@Override
public com.destroystokyo.paper.block.BlockSoundGroup getSoundGroup() {
@@ -1371,7 +1374,7 @@ index 811823a1a7e24a19a7e37eb4c08efdfa19e839ed..ac45c5cbe547705e3e341011740cf911
}
@Override
@@ -713,26 +1186,76 @@ public class CraftBlock implements Block {
@@ -718,26 +1193,76 @@ public class CraftBlock implements Block {
return this.getNMS().getBlock().getDescriptionId();
}
@@ -1453,7 +1456,7 @@ index 811823a1a7e24a19a7e37eb4c08efdfa19e839ed..ac45c5cbe547705e3e341011740cf911
// Paper end
}
diff --git a/src/main/java/org/bukkit/craftbukkit/block/CraftBlockEntityState.java b/src/main/java/org/bukkit/craftbukkit/block/CraftBlockEntityState.java
index 768d3f93da2522d467183654260a8bd8653588b1..5cef786fa2e5dfd3e7b79918bc73af02891b0bea 100644
index 3422970353dcd886934b9ee906467769d39abbde..13c91223bbb4841cab0e491037a36113a33faf15 100644
--- a/src/main/java/org/bukkit/craftbukkit/block/CraftBlockEntityState.java
+++ b/src/main/java/org/bukkit/craftbukkit/block/CraftBlockEntityState.java
@@ -26,6 +26,27 @@ public abstract class CraftBlockEntityState<T extends BlockEntity> extends Craft
@@ -1482,8 +1485,8 @@ index 768d3f93da2522d467183654260a8bd8653588b1..5cef786fa2e5dfd3e7b79918bc73af02
+ }
+ // Leaf end - SparklyPaper - parallel world ticking mod
public CraftBlockEntityState(World world, T tileEntity) {
super(world, tileEntity.getBlockPos(), tileEntity.getBlockState());
public CraftBlockEntityState(World world, T blockEntity) {
super(world, blockEntity.getBlockPos(), blockEntity.getBlockState());
@@ -34,8 +55,8 @@ public abstract class CraftBlockEntityState<T extends BlockEntity> extends Craft
try { // Paper - Show blockstate location if we failed to read it
@@ -1492,14 +1495,14 @@ index 768d3f93da2522d467183654260a8bd8653588b1..5cef786fa2e5dfd3e7b79918bc73af02
- if (DISABLE_SNAPSHOT) {
+ this.snapshotDisabled = getDisableSnapshotTL(); // SparklyPaper - parallel world ticking // Leaf - SparklyPaper - parallel world ticking mod (collapse original behavior)
+ if (this.snapshotDisabled) { // SparklyPaper - parallel world ticking // Leaf - SparklyPaper - parallel world ticking mod (collapse original behavior)
this.snapshot = this.tileEntity;
this.snapshot = this.blockEntity;
} else {
this.snapshot = this.createSnapshot(tileEntity);
this.snapshot = this.createSnapshot(blockEntity);
diff --git a/src/main/java/org/bukkit/craftbukkit/block/CraftBlockState.java b/src/main/java/org/bukkit/craftbukkit/block/CraftBlockState.java
index fa63a6cfcfcc4eee4503a82d85333c139c8c8b2b..d106f65e4b745242484a195958fc559268a7dee0 100644
index 196835bdf95ba0e149b2977e9ef41698971f501f..eb7e63d4549e672ff1206055d2d754395f189a4a 100644
--- a/src/main/java/org/bukkit/craftbukkit/block/CraftBlockState.java
+++ b/src/main/java/org/bukkit/craftbukkit/block/CraftBlockState.java
@@ -215,6 +215,12 @@ public class CraftBlockState implements BlockState {
@@ -218,6 +218,12 @@ public class CraftBlockState implements BlockState {
LevelAccessor access = this.getWorldHandle();
CraftBlock block = this.getBlock();
@@ -1512,7 +1515,7 @@ index fa63a6cfcfcc4eee4503a82d85333c139c8c8b2b..d106f65e4b745242484a195958fc5592
if (block.getType() != this.getType()) {
if (!force) {
return false;
@@ -350,6 +356,8 @@ public class CraftBlockState implements BlockState {
@@ -365,6 +371,8 @@ public class CraftBlockState implements BlockState {
@Override
public java.util.Collection<org.bukkit.inventory.ItemStack> getDrops(org.bukkit.inventory.ItemStack item, org.bukkit.entity.Entity entity) {
@@ -1522,37 +1525,35 @@ index fa63a6cfcfcc4eee4503a82d85333c139c8c8b2b..d106f65e4b745242484a195958fc5592
net.minecraft.world.item.ItemStack nms = org.bukkit.craftbukkit.inventory.CraftItemStack.asNMSCopy(item);
diff --git a/src/main/java/org/bukkit/craftbukkit/block/CraftBlockStates.java b/src/main/java/org/bukkit/craftbukkit/block/CraftBlockStates.java
index 55572e799b5c8a74a546ac8febc14f80d5731c52..08a06c23c831a4de45b3e537228b837911019da8 100644
index 321280d7c9c3c828cbf2eb19d2fd196a1f84d4c3..cd8f771e08cee5d00c53a8e70f0fe37cf393cd52 100644
--- a/src/main/java/org/bukkit/craftbukkit/block/CraftBlockStates.java
+++ b/src/main/java/org/bukkit/craftbukkit/block/CraftBlockStates.java
@@ -249,8 +249,8 @@ public final class CraftBlockStates {
net.minecraft.world.level.block.state.BlockState blockData = craftBlock.getNMS();
BlockEntity tileEntity = craftBlock.getHandle().getBlockEntity(blockPosition);
// Paper start - block state snapshots
@@ -195,14 +195,14 @@ public final class CraftBlockStates {
BlockPos pos = craftBlock.getPosition();
net.minecraft.world.level.block.state.BlockState state = craftBlock.getNMS();
BlockEntity blockEntity = craftBlock.getHandle().getBlockEntity(pos);
- boolean prev = CraftBlockEntityState.DISABLE_SNAPSHOT;
- CraftBlockEntityState.DISABLE_SNAPSHOT = !useSnapshot;
+ boolean prev = CraftBlockEntityState.getDisableSnapshotTL(); // SparklyPaper - parallel world ticking // Leaf - SparklyPaper - parallel world ticking mod (collapse original behavior)
+ CraftBlockEntityState.setDisableSnapshotTL(!useSnapshot); // SparklyPaper - parallel world ticking // Leaf - SparklyPaper - parallel world ticking mod (collapse original behavior)
try {
// Paper end
CraftBlockState blockState = CraftBlockStates.getBlockState(world, blockPosition, blockData, tileEntity);
@@ -258,7 +258,7 @@ public final class CraftBlockStates {
return blockState;
// Paper start
CraftBlockState blockState = CraftBlockStates.getBlockState(world, pos, state, blockEntity);
blockState.setWorldHandle(craftBlock.getHandle()); // Inject the block's generator access
return blockState;
} finally {
- CraftBlockEntityState.DISABLE_SNAPSHOT = prev;
+ CraftBlockEntityState.setDisableSnapshotTL(prev); // SparklyPaper - parallel world ticking // Leaf - SparklyPaper - parallel world ticking mod (collapse original behavior)
}
// Paper end
}
diff --git a/src/main/java/org/bukkit/craftbukkit/event/CraftEventFactory.java b/src/main/java/org/bukkit/craftbukkit/event/CraftEventFactory.java
index c2552c3706831f7012b5b449fa43c7d5990056a4..4e8a1d01a6c0afef92ae56cc4909af06d63e5268 100644
--- a/src/main/java/org/bukkit/craftbukkit/event/CraftEventFactory.java
+++ b/src/main/java/org/bukkit/craftbukkit/event/CraftEventFactory.java
@@ -961,6 +961,28 @@ public class CraftEventFactory {
}
public static BlockPos sourceBlockOverride = null; // SPIGOT-7068: Add source block override, not the most elegant way but better than passing down a BlockPosition up to five methods deep.
diff --git a/src/main/java/org/bukkit/craftbukkit/event/CraftEventFactory.java b/src/main/java/org/bukkit/craftbukkit/event/CraftEventFactory.java
index fec0f3b72c1808c5019e95760e3fef19c45e1be0..d0991574d3c8c826e31b4448bbe6a6c79c16c91d 100644
--- a/src/main/java/org/bukkit/craftbukkit/event/CraftEventFactory.java
+++ b/src/main/java/org/bukkit/craftbukkit/event/CraftEventFactory.java
@@ -818,6 +818,28 @@ public class CraftEventFactory {
}
public static BlockPos sourceBlockOverride = null; // SPIGOT-7068: Add source block override, not the most elegant way but better than passing down a BlockPos up to five methods deep.
+ public static final ThreadLocal<BlockPos> sourceBlockOverrideRT = new ThreadLocal<>(); // SparklyPaper - parallel world ticking (this is from Folia, fixes concurrency bugs with sculk catalysts)
+
+ // Leaf start - SparklyPaper - parallel world ticking mod
@@ -1576,29 +1577,20 @@ index c2552c3706831f7012b5b449fa43c7d5990056a4..4e8a1d01a6c0afef92ae56cc4909af06
+ }
+ // Leaf end - SparklyPaper - parallel world ticking mod
public static boolean handleBlockSpreadEvent(LevelAccessor world, BlockPos source, BlockPos target, net.minecraft.world.level.block.state.BlockState block, int flag) {
// Suppress during worldgen
@@ -972,7 +994,10 @@ public class CraftEventFactory {
CraftBlockState state = CraftBlockStates.getBlockState(world, target, flag);
state.setData(block);
public static boolean handleBlockSpreadEvent(LevelAccessor world, BlockPos source, BlockPos target, net.minecraft.world.level.block.state.BlockState state, int flags) {
return handleBlockSpreadEvent(world, source, target, state, flags, false);
@@ -833,7 +855,10 @@ public class CraftEventFactory {
CraftBlockState snapshot = CraftBlockStates.getBlockState(world, target);
snapshot.setData(state);
- BlockSpreadEvent event = new BlockSpreadEvent(state.getBlock(), CraftBlock.at(world, CraftEventFactory.sourceBlockOverride != null ? CraftEventFactory.sourceBlockOverride : source), state);
- BlockSpreadEvent event = new BlockSpreadEvent(snapshot.getBlock(), CraftBlock.at(world, CraftEventFactory.sourceBlockOverride != null ? CraftEventFactory.sourceBlockOverride : source), snapshot);
+ // Leaf start - SparklyPaper parallel world ticking mod (collapse original behavior)
+ final BlockPos sourceBlockOverrideRTSnap = getSourceBlockOverrideRT();
+ BlockSpreadEvent event = new BlockSpreadEvent(state.getBlock(), CraftBlock.at(world, sourceBlockOverrideRTSnap != null ? sourceBlockOverrideRTSnap : source), state); // SparklyPaper - parallel world ticking
+ BlockSpreadEvent event = new BlockSpreadEvent(snapshot.getBlock(), CraftBlock.at(world, sourceBlockOverrideRTSnap != null ? sourceBlockOverrideRTSnap : source), snapshot); // SparklyPaper - parallel world ticking
+ // Leaf end - SparklyPaper parallel world ticking mod (collapse original behavior)
Bukkit.getPluginManager().callEvent(event);
if (!event.isCancelled()) {
@@ -2265,7 +2290,7 @@ public class CraftEventFactory {
CraftItemStack craftItem = CraftItemStack.asCraftMirror(itemStack.copyWithCount(1));
org.bukkit.event.block.BlockDispenseEvent event = new org.bukkit.event.block.BlockDispenseEvent(bukkitBlock, craftItem.clone(), CraftVector.toBukkit(to));
- if (!net.minecraft.world.level.block.DispenserBlock.eventFired) {
+ if (!net.minecraft.world.level.block.DispenserBlock.getEventFiredTL()) { // SparklyPaper - parallel world ticking // Leaf - SparklyPaper - parallel world ticking mod (collapse original behavior)
if (!event.callEvent()) {
return itemStack;
}
if (event.callEvent()) {
boolean result = snapshot.place(flags);
return !checkSetResult || result;
diff --git a/src/main/java/org/bukkit/craftbukkit/scheduler/CraftAsyncTask.java b/src/main/java/org/bukkit/craftbukkit/scheduler/CraftAsyncTask.java
index e4e2e42d0ca25df7fe9f2dd4275610e45fcb2c84..e7c6b2ab5f2c68f3319ccd52785c8d3488a2eef7 100644
--- a/src/main/java/org/bukkit/craftbukkit/scheduler/CraftAsyncTask.java

View File

@@ -5,7 +5,7 @@ import it.unimi.dsi.fastutil.Pair;
import net.kyori.adventure.text.Component;
import net.kyori.adventure.text.format.NamedTextColor;
import net.minecraft.Util;
//import org.dreeam.leaf.command.subcommands.MSPTCommand;
import org.dreeam.leaf.command.subcommands.MSPTCommand;
import org.dreeam.leaf.command.subcommands.ReloadCommand;
import org.dreeam.leaf.command.subcommands.VersionCommand;
import org.jetbrains.annotations.NotNull;
@@ -38,13 +38,13 @@ public final class LeafCommand extends Command {
// subcommand label -> subcommand
private static final LeafSubcommand RELOAD_SUBCOMMAND = new ReloadCommand();
private static final LeafSubcommand VERSION_SUBCOMMAND = new VersionCommand();
//private static final LeafSubcommand MSPT_SUBCOMMAND = new MSPTCommand();
private static final LeafSubcommand MSPT_SUBCOMMAND = new MSPTCommand();
private static final Map<String, LeafSubcommand> SUBCOMMANDS = Util.make(() -> {
final Map<Set<String>, LeafSubcommand> commands = new HashMap<>();
commands.put(Set.of(ReloadCommand.LITERAL_ARGUMENT), RELOAD_SUBCOMMAND);
commands.put(Set.of(VersionCommand.LITERAL_ARGUMENT), VERSION_SUBCOMMAND);
//commands.put(Set.of(MSPTCommand.LITERAL_ARGUMENT), MSPT_SUBCOMMAND);
commands.put(Set.of(MSPTCommand.LITERAL_ARGUMENT), MSPT_SUBCOMMAND);
return commands.entrySet().stream()
.flatMap(entry -> entry.getKey().stream().map(s -> Map.entry(s, entry.getValue())))