aboutsummaryrefslogtreecommitdiffhomepage
path: root/patches/server/1024-Remove-wall-time-unused-skip-tick-protection.patch
diff options
context:
space:
mode:
Diffstat (limited to 'patches/server/1024-Remove-wall-time-unused-skip-tick-protection.patch')
-rw-r--r--patches/server/1024-Remove-wall-time-unused-skip-tick-protection.patch163
1 files changed, 163 insertions, 0 deletions
diff --git a/patches/server/1024-Remove-wall-time-unused-skip-tick-protection.patch b/patches/server/1024-Remove-wall-time-unused-skip-tick-protection.patch
new file mode 100644
index 0000000000..da0d05dd0d
--- /dev/null
+++ b/patches/server/1024-Remove-wall-time-unused-skip-tick-protection.patch
@@ -0,0 +1,163 @@
+From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
+From: Bjarne Koll <[email protected]>
+Date: Mon, 16 Sep 2024 23:07:29 +0200
+Subject: [PATCH] Remove wall-time / unused skip tick protection
+
+Spigot still maintains some partial implementation of "tick skipping", a
+practice in which the MinecraftServer.currentTick field is updated not
+by an increment of one per actual tick, but instead set to
+System.currentTimeMillis() / 50. This behaviour means that the tracked
+tick may "skip" a tick value in case a previous tick took more than the
+expected 50ms.
+
+To compensate for this in important paths, spigot/craftbukkit
+implements "wall-time". Instead of incrementing/decrementing ticks on
+block entities/entities by one for each call to their tick() method,
+they instead increment/decrement important values, like
+an ItemEntity's age or pickupDelay, by the difference of
+`currentTick - lastTick`, where `lastTick` is the value of
+`currentTick` during the last tick() call.
+
+These "fixes" however do not play nicely with minecraft's simulation
+distance as entities/block entities implementing the above behaviour
+would "catch up" their values when moving from a non-ticking chunk to a
+ticking one as their `lastTick` value remains stuck on the last tick in
+a ticking chunk and hence lead to a large "catch up" once ticked again.
+
+Paper completely removes the "tick skipping" behaviour (See patch
+"Further-improve-server-tick-loop"), making the above precautions
+completely unnecessary, which also rids paper of the previous described
+incompatibility with non-ticking chunks.
+
+diff --git a/src/main/java/net/minecraft/world/entity/item/ItemEntity.java b/src/main/java/net/minecraft/world/entity/item/ItemEntity.java
+index 246b5649883e4f305afa5a887b9df0f3735f7593..5d8885bca55503bf7e1a2a4e1bb9b3bd86d55391 100644
+--- a/src/main/java/net/minecraft/world/entity/item/ItemEntity.java
++++ b/src/main/java/net/minecraft/world/entity/item/ItemEntity.java
+@@ -60,7 +60,7 @@ public class ItemEntity extends Entity implements TraceableEntity {
+ @Nullable
+ public UUID target;
+ public final float bobOffs;
+- private int lastTick = MinecraftServer.currentTick - 1; // CraftBukkit
++ // private int lastTick = MinecraftServer.currentTick - 1; // CraftBukkit // Paper - remove anti tick skipping measures / wall time
+ public boolean canMobPickup = true; // Paper - Item#canEntityPickup
+ private int despawnRate = -1; // Paper - Alternative item-despawn-rate
+ public net.kyori.adventure.util.TriState frictionState = net.kyori.adventure.util.TriState.NOT_SET; // Paper - Friction API
+@@ -153,12 +153,11 @@ public class ItemEntity extends Entity implements TraceableEntity {
+ this.discard(EntityRemoveEvent.Cause.DESPAWN); // CraftBukkit - add Bukkit remove cause
+ } else {
+ super.tick();
+- // CraftBukkit start - Use wall time for pickup and despawn timers
+- int elapsedTicks = MinecraftServer.currentTick - this.lastTick;
+- if (this.pickupDelay != 32767) this.pickupDelay -= elapsedTicks;
+- if (this.age != -32768) this.age += elapsedTicks;
+- this.lastTick = MinecraftServer.currentTick;
+- // CraftBukkit end
++ // Paper start - remove anti tick skipping measures / wall time - revert to vanilla
++ if (this.pickupDelay > 0 && this.pickupDelay != 32767) {
++ --this.pickupDelay;
++ }
++ // Paper end - remove anti tick skipping measures / wall time - revert to vanilla
+
+ this.xo = this.getX();
+ this.yo = this.getY();
+@@ -212,7 +211,7 @@ public class ItemEntity extends Entity implements TraceableEntity {
+ this.mergeWithNeighbours();
+ }
+
+- /* CraftBukkit start - moved up
++ // Paper - remove anti tick skipping measures / wall time - revert to vanilla /* CraftBukkit start - moved up
+ if (this.age != -32768) {
+ ++this.age;
+ }
+@@ -243,12 +242,14 @@ public class ItemEntity extends Entity implements TraceableEntity {
+ // Spigot start - copied from above
+ @Override
+ public void inactiveTick() {
+- // CraftBukkit start - Use wall time for pickup and despawn timers
+- int elapsedTicks = MinecraftServer.currentTick - this.lastTick;
+- if (this.pickupDelay != 32767) this.pickupDelay -= elapsedTicks;
+- if (this.age != -32768) this.age += elapsedTicks;
+- this.lastTick = MinecraftServer.currentTick;
+- // CraftBukkit end
++ // Paper start - remove anti tick skipping measures / wall time - copied from above
++ if (this.pickupDelay > 0 && this.pickupDelay != 32767) {
++ --this.pickupDelay;
++ }
++ if (this.age != -32768) {
++ ++this.age;
++ }
++ // Paper end - remove anti tick skipping measures / wall time - copied from above
+
+ if (!this.level().isClientSide && this.age >= this.despawnRate) { // Spigot // Paper - Alternative item-despawn-rate
+ // CraftBukkit start - fire ItemDespawnEvent
+diff --git a/src/main/java/net/minecraft/world/entity/monster/Zombie.java b/src/main/java/net/minecraft/world/entity/monster/Zombie.java
+index 94b3ba2688676e92d9d093b63d92cab39d5d2f02..a12461907278cfbfa3b1c0aa74b9f07a31768b8a 100644
+--- a/src/main/java/net/minecraft/world/entity/monster/Zombie.java
++++ b/src/main/java/net/minecraft/world/entity/monster/Zombie.java
+@@ -98,7 +98,7 @@ public class Zombie extends Monster {
+ private boolean canBreakDoors;
+ private int inWaterTime;
+ public int conversionTime;
+- private int lastTick = MinecraftServer.currentTick; // CraftBukkit - add field
++ // private int lastTick = MinecraftServer.currentTick; // CraftBukkit - add field // Paper - remove anti tick skipping measures / wall time
+ private boolean shouldBurnInDay = true; // Paper - Add more Zombie API
+
+ public Zombie(EntityType<? extends Zombie> type, Level world) {
+@@ -217,10 +217,7 @@ public class Zombie extends Monster {
+ public void tick() {
+ if (!this.level().isClientSide && this.isAlive() && !this.isNoAi()) {
+ if (this.isUnderWaterConverting()) {
+- // CraftBukkit start - Use wall time instead of ticks for conversion
+- int elapsedTicks = MinecraftServer.currentTick - this.lastTick;
+- this.conversionTime -= elapsedTicks;
+- // CraftBukkit end
++ --this.conversionTime; // Paper - remove anti tick skipping measures / wall time
+ if (this.conversionTime < 0) {
+ this.doUnderWaterConversion();
+ }
+@@ -237,7 +234,7 @@ public class Zombie extends Monster {
+ }
+
+ super.tick();
+- this.lastTick = MinecraftServer.currentTick; // CraftBukkit
++ // this.lastTick = MinecraftServer.currentTick; // CraftBukkit // Paper - remove anti tick skipping measures / wall time
+ }
+
+ @Override
+@@ -278,7 +275,7 @@ public class Zombie extends Monster {
+ }
+ // Paper end - Add more Zombie API
+ public void startUnderWaterConversion(int ticksUntilWaterConversion) {
+- this.lastTick = MinecraftServer.currentTick; // CraftBukkit
++ // this.lastTick = MinecraftServer.currentTick; // CraftBukkit // Paper - remove anti tick skipping measures / wall time
+ this.conversionTime = ticksUntilWaterConversion;
+ this.getEntityData().set(Zombie.DATA_DROWNED_CONVERSION_ID, true);
+ }
+diff --git a/src/main/java/net/minecraft/world/level/block/entity/BrewingStandBlockEntity.java b/src/main/java/net/minecraft/world/level/block/entity/BrewingStandBlockEntity.java
+index 2bafacd7bc56186d9105d2031180f8c4a6940018..4ea29e8f2b39d7b44e0461d6a2cdd3fc257abd44 100644
+--- a/src/main/java/net/minecraft/world/level/block/entity/BrewingStandBlockEntity.java
++++ b/src/main/java/net/minecraft/world/level/block/entity/BrewingStandBlockEntity.java
+@@ -55,7 +55,7 @@ public class BrewingStandBlockEntity extends BaseContainerBlockEntity implements
+ public int fuel;
+ protected final ContainerData dataAccess;
+ // CraftBukkit start - add fields and methods
+- private int lastTick = MinecraftServer.currentTick;
++ // private int lastTick = MinecraftServer.currentTick; // Paper - remove anti tick skipping measures / wall time
+ public List<HumanEntity> transaction = new java.util.ArrayList<HumanEntity>();
+ private int maxStack = MAX_STACK;
+
+@@ -170,12 +170,10 @@ public class BrewingStandBlockEntity extends BaseContainerBlockEntity implements
+ boolean flag1 = blockEntity.brewTime > 0;
+ ItemStack itemstack1 = (ItemStack) blockEntity.items.get(3);
+
+- // CraftBukkit start - Use wall time instead of ticks for brewing
+- int elapsedTicks = MinecraftServer.currentTick - blockEntity.lastTick;
+- blockEntity.lastTick = MinecraftServer.currentTick;
++ // Paper - remove anti tick skipping measures / wall time
+
+ if (flag1) {
+- blockEntity.brewTime -= elapsedTicks;
++ --blockEntity.brewTime; // Paper - remove anti tick skipping measures / wall time - revert to vanilla
+ boolean flag2 = blockEntity.brewTime <= 0; // == -> <=
+ // CraftBukkit end
+