aboutsummaryrefslogtreecommitdiffhomepage
path: root/patches
diff options
context:
space:
mode:
Diffstat (limited to 'patches')
-rw-r--r--patches/server/0007-MC-Utils.patch49
-rw-r--r--patches/server/0857-Replace-player-chunk-loader-system.patch34
-rw-r--r--patches/server/0863-Option-to-have-default-CustomSpawners-in-custom-worl.patch6
-rw-r--r--patches/server/0876-Don-t-allow-vehicle-movement-from-players-while-tele.patch4
-rw-r--r--patches/server/0886-Ensure-entity-passenger-world-matches-ridden-entity.patch23
-rw-r--r--patches/server/0887-Guard-against-invalid-entity-positions.patch45
6 files changed, 133 insertions, 28 deletions
diff --git a/patches/server/0007-MC-Utils.patch b/patches/server/0007-MC-Utils.patch
index f8b5ec815f..0928d4a02d 100644
--- a/patches/server/0007-MC-Utils.patch
+++ b/patches/server/0007-MC-Utils.patch
@@ -2890,23 +2890,25 @@ index 0000000000000000000000000000000000000000..a1bc1d1d0c86217ef18883d281195bc6
+}
diff --git a/src/main/java/io/papermc/paper/util/IntervalledCounter.java b/src/main/java/io/papermc/paper/util/IntervalledCounter.java
new file mode 100644
-index 0000000000000000000000000000000000000000..059e8c61108cb78a80895cae36f2f8ac644e704c
+index 0000000000000000000000000000000000000000..cea9c098ade00ee87b8efc8164ab72f5279758f0
--- /dev/null
+++ b/src/main/java/io/papermc/paper/util/IntervalledCounter.java
-@@ -0,0 +1,100 @@
+@@ -0,0 +1,115 @@
+package io.papermc.paper.util;
+
+public final class IntervalledCounter {
+
+ protected long[] times;
++ protected long[] counts;
+ protected final long interval;
+ protected long minTime;
-+ protected int sum;
++ protected long sum;
+ protected int head; // inclusive
+ protected int tail; // exclusive
+
+ public IntervalledCounter(final long interval) {
+ this.times = new long[8];
++ this.counts = new long[8];
+ this.interval = interval;
+ }
+
@@ -2915,7 +2917,7 @@ index 0000000000000000000000000000000000000000..059e8c61108cb78a80895cae36f2f8ac
+ }
+
+ public void updateCurrentTime(final long currentTime) {
-+ int sum = this.sum;
++ long sum = this.sum;
+ int head = this.head;
+ final int tail = this.tail;
+ final long minTime = currentTime - this.interval;
@@ -2924,8 +2926,15 @@ index 0000000000000000000000000000000000000000..059e8c61108cb78a80895cae36f2f8ac
+
+ // guard against overflow by using subtraction
+ while (head != tail && this.times[head] - minTime < 0) {
-+ head = (head + 1) % arrayLen;
-+ --sum;
++ sum -= this.counts[head];
++ // there are two ways we can do this:
++ // 1. free the count when adding
++ // 2. free it now
++ // option #2
++ this.counts[head] = 0;
++ if (++head >= arrayLen) {
++ head = 0;
++ }
+ }
+
+ this.sum = sum;
@@ -2934,6 +2943,10 @@ index 0000000000000000000000000000000000000000..059e8c61108cb78a80895cae36f2f8ac
+ }
+
+ public void addTime(final long currTime) {
++ this.addTime(currTime, 1L);
++ }
++
++ public void addTime(final long currTime, final long count) {
+ // guard against overflow by using subtraction
+ if (currTime - this.minTime < 0) {
+ return;
@@ -2945,28 +2958,29 @@ index 0000000000000000000000000000000000000000..059e8c61108cb78a80895cae36f2f8ac
+ }
+
+ this.times[this.tail] = currTime;
++ this.counts[this.tail] += count;
++ this.sum += count;
+ this.tail = nextTail;
+ }
+
+ public void updateAndAdd(final int count) {
+ final long currTime = System.nanoTime();
+ this.updateCurrentTime(currTime);
-+ for (int i = 0; i < count; ++i) {
-+ this.addTime(currTime);
-+ }
++ this.addTime(currTime, count);
+ }
+
+ public void updateAndAdd(final int count, final long currTime) {
+ this.updateCurrentTime(currTime);
-+ for (int i = 0; i < count; ++i) {
-+ this.addTime(currTime);
-+ }
++ this.addTime(currTime, count);
+ }
+
+ private void resize() {
+ final long[] oldElements = this.times;
++ final long[] oldCounts = this.counts;
+ final long[] newElements = new long[this.times.length * 2];
++ final long[] newCounts = new long[this.times.length * 2];
+ this.times = newElements;
++ this.counts = newCounts;
+
+ final int head = this.head;
+ final int tail = this.tail;
@@ -2976,9 +2990,13 @@ index 0000000000000000000000000000000000000000..059e8c61108cb78a80895cae36f2f8ac
+
+ if (tail >= head) {
+ System.arraycopy(oldElements, head, newElements, 0, size);
++ System.arraycopy(oldCounts, head, newCounts, 0, size);
+ } else {
+ System.arraycopy(oldElements, head, newElements, 0, oldElements.length - head);
+ System.arraycopy(oldElements, 0, newElements, oldElements.length - head, tail);
++
++ System.arraycopy(oldCounts, head, newCounts, 0, oldCounts.length - head);
++ System.arraycopy(oldCounts, 0, newCounts, oldCounts.length - head, tail);
+ }
+ }
+
@@ -2987,11 +3005,8 @@ index 0000000000000000000000000000000000000000..059e8c61108cb78a80895cae36f2f8ac
+ return this.size() / (this.interval * 1.0e-9);
+ }
+
-+ public int size() {
-+ final int head = this.head;
-+ final int tail = this.tail;
-+
-+ return tail >= head ? (tail - head) : (tail + (this.times.length - head));
++ public long size() {
++ return this.sum;
+ }
+}
diff --git a/src/main/java/io/papermc/paper/util/WorldUtil.java b/src/main/java/io/papermc/paper/util/WorldUtil.java
diff --git a/patches/server/0857-Replace-player-chunk-loader-system.patch b/patches/server/0857-Replace-player-chunk-loader-system.patch
index 46d7fd489f..9dac047cdd 100644
--- a/patches/server/0857-Replace-player-chunk-loader-system.patch
+++ b/patches/server/0857-Replace-player-chunk-loader-system.patch
@@ -84,10 +84,10 @@ index 309dbf5fce3ce940d5e1b57d267b9d6b2c5ff5b6..5ba64e1083b7cb1eec64d1925095c6ca
}));
diff --git a/src/main/java/com/destroystokyo/paper/PaperConfig.java b/src/main/java/com/destroystokyo/paper/PaperConfig.java
-index 2e68fe31fc788a3ff1fe4ac52140e5e518f660b1..9bff729df7156b071b08913549838024bb17c3c9 100644
+index 2e68fe31fc788a3ff1fe4ac52140e5e518f660b1..b7cb07e36c0056dea64dea220a465337f0d5c843 100644
--- a/src/main/java/com/destroystokyo/paper/PaperConfig.java
+++ b/src/main/java/com/destroystokyo/paper/PaperConfig.java
-@@ -652,4 +652,33 @@ public class PaperConfig {
+@@ -652,4 +652,35 @@ public class PaperConfig {
private static void timeCommandAffectsAllWorlds() {
timeCommandAffectsAllWorlds = getBoolean("settings.time-command-affects-all-worlds", timeCommandAffectsAllWorlds);
}
@@ -102,6 +102,7 @@ index 2e68fe31fc788a3ff1fe4ac52140e5e518f660b1..9bff729df7156b071b08913549838024
+ public static double globalMaxChunkLoadRate;
+ public static double playerMaxConcurrentChunkLoads;
+ public static double globalMaxConcurrentChunkLoads;
++ public static double playerMaxChunkLoadRate;
+
+ private static void newPlayerChunkManagement() {
+ playerMinChunkLoadRadius = getInt("settings.chunk-loading.min-load-radius", 2);
@@ -119,14 +120,15 @@ index 2e68fe31fc788a3ff1fe4ac52140e5e518f660b1..9bff729df7156b071b08913549838024
+ set("settings.chunk-loading.player-max-concurrent-loads", playerMaxConcurrentChunkLoads = 20.0);
+ }
+ globalMaxConcurrentChunkLoads = getDouble("settings.chunk-loading.global-max-concurrent-loads", 500.0);
++ playerMaxChunkLoadRate = getDouble("settings.chunk-loading.player-max-chunk-load-rate", -1.0);
+ }
}
diff --git a/src/main/java/io/papermc/paper/chunk/PlayerChunkLoader.java b/src/main/java/io/papermc/paper/chunk/PlayerChunkLoader.java
new file mode 100644
-index 0000000000000000000000000000000000000000..bdd4cc040111d18b82d3ebeb5dbe2537cf148090
+index 0000000000000000000000000000000000000000..0f62a766a3249d8651a11dce6e9051b162693716
--- /dev/null
+++ b/src/main/java/io/papermc/paper/chunk/PlayerChunkLoader.java
-@@ -0,0 +1,1108 @@
+@@ -0,0 +1,1128 @@
+package io.papermc.paper.chunk;
+
+import com.destroystokyo.paper.PaperConfig;
@@ -218,10 +220,16 @@ index 0000000000000000000000000000000000000000..bdd4cc040111d18b82d3ebeb5dbe2537
+
+ final int priorityCompare = Double.compare(holder1 == null ? Double.MAX_VALUE : holder1.priority, holder2 == null ? Double.MAX_VALUE : holder2.priority);
+
-+ if (priorityCompare != 0) {
++ final int lastLoadTimeCompare = Long.compare(p1.lastChunkLoad, p2.lastChunkLoad);
++
++ if ((holder1 == null || holder2 == null || lastLoadTimeCompare == 0 || holder1.priority < 0.0 || holder2.priority < 0.0) && priorityCompare != 0) {
+ return priorityCompare;
+ }
+
++ if (lastLoadTimeCompare != 0) {
++ return lastLoadTimeCompare;
++ }
++
+ final int idCompare = Integer.compare(p1.player.getId(), p2.player.getId());
+
+ if (idCompare != 0) {
@@ -744,6 +752,8 @@ index 0000000000000000000000000000000000000000..bdd4cc040111d18b82d3ebeb5dbe2537
+ for (;;) {
+ final PlayerLoaderData data = this.chunkLoadQueue.pollFirst();
+
++ data.lastChunkLoad = time;
++
+ final ChunkPriorityHolder queuedLoad = data.loadQueue.peekFirst();
+ if (queuedLoad == null) {
+ if (this.chunkLoadQueue.isEmpty()) {
@@ -756,6 +766,8 @@ index 0000000000000000000000000000000000000000..bdd4cc040111d18b82d3ebeb5dbe2537
+ updatedCounters = true;
+ TICKET_ADDITION_COUNTER_SHORT.updateCurrentTime(time);
+ TICKET_ADDITION_COUNTER_LONG.updateCurrentTime(time);
++ data.ticketAdditionCounterShort.updateCurrentTime(time);
++ data.ticketAdditionCounterLong.updateCurrentTime(time);
+ }
+
+ if (this.isChunkPlayerLoaded(queuedLoad.chunkX, queuedLoad.chunkZ)) {
@@ -791,7 +803,8 @@ index 0000000000000000000000000000000000000000..bdd4cc040111d18b82d3ebeb5dbe2537
+ // priority >= 0.0 implies rate limited chunks
+
+ final int currentChunkLoads = this.concurrentChunkLoads;
-+ if (currentChunkLoads >= maxLoads || (PaperConfig.globalMaxChunkLoadRate > 0 && (TICKET_ADDITION_COUNTER_SHORT.getRate() >= PaperConfig.globalMaxChunkLoadRate || TICKET_ADDITION_COUNTER_LONG.getRate() >= PaperConfig.globalMaxChunkLoadRate))) {
++ if (currentChunkLoads >= maxLoads || (PaperConfig.globalMaxChunkLoadRate > 0 && (TICKET_ADDITION_COUNTER_SHORT.getRate() >= PaperConfig.globalMaxChunkLoadRate || TICKET_ADDITION_COUNTER_LONG.getRate() >= PaperConfig.globalMaxChunkLoadRate))
++ || (PaperConfig.playerMaxChunkLoadRate > 0.0 && (data.ticketAdditionCounterShort.getRate() >= PaperConfig.playerMaxChunkLoadRate || data.ticketAdditionCounterLong.getRate() >= PaperConfig.playerMaxChunkLoadRate))) {
+ // don't poll, we didn't load it
+ this.chunkLoadQueue.add(data);
+ break;
@@ -821,6 +834,8 @@ index 0000000000000000000000000000000000000000..bdd4cc040111d18b82d3ebeb5dbe2537
+ ++this.concurrentChunkLoads;
+ TICKET_ADDITION_COUNTER_SHORT.addTime(time);
+ TICKET_ADDITION_COUNTER_LONG.addTime(time);
++ data.ticketAdditionCounterShort.addTime(time);
++ data.ticketAdditionCounterLong.addTime(time);
+ }
+ }
+ }
@@ -926,6 +941,13 @@ index 0000000000000000000000000000000000000000..bdd4cc040111d18b82d3ebeb5dbe2537
+
+ protected long nextChunkSendTarget;
+
++ // this interval prevents bursting a lot of chunk loads
++ protected final IntervalledCounter ticketAdditionCounterShort = new IntervalledCounter((long)(1.0e6 * 50.0)); // 50ms
++ // this ensures the rate is kept between ticks correctly
++ protected final IntervalledCounter ticketAdditionCounterLong = new IntervalledCounter((long)(1.0e6 * 1000.0)); // 1000ms
++
++ public long lastChunkLoad;
++
+ public PlayerLoaderData(final ServerPlayer player, final PlayerChunkLoader loader) {
+ this.player = player;
+ this.loader = loader;
diff --git a/patches/server/0863-Option-to-have-default-CustomSpawners-in-custom-worl.patch b/patches/server/0863-Option-to-have-default-CustomSpawners-in-custom-worl.patch
index e4ea20bd18..5711927a4b 100644
--- a/patches/server/0863-Option-to-have-default-CustomSpawners-in-custom-worl.patch
+++ b/patches/server/0863-Option-to-have-default-CustomSpawners-in-custom-worl.patch
@@ -10,12 +10,12 @@ just looking at the LevelStem key, look at the DimensionType key which
is one level below that. Defaults to off to keep vanilla behavior.
diff --git a/src/main/java/com/destroystokyo/paper/PaperConfig.java b/src/main/java/com/destroystokyo/paper/PaperConfig.java
-index 9bff729df7156b071b08913549838024bb17c3c9..88a4dda44e59fbe6215d7ac2e5af0c54527a2fc7 100644
+index b7cb07e36c0056dea64dea220a465337f0d5c843..c9c08e20f729b40b1d90f3ac144f5245f4f35230 100644
--- a/src/main/java/com/destroystokyo/paper/PaperConfig.java
+++ b/src/main/java/com/destroystokyo/paper/PaperConfig.java
-@@ -681,4 +681,9 @@ public class PaperConfig {
- }
+@@ -683,4 +683,9 @@ public class PaperConfig {
globalMaxConcurrentChunkLoads = getDouble("settings.chunk-loading.global-max-concurrent-loads", 500.0);
+ playerMaxChunkLoadRate = getDouble("settings.chunk-loading.player-max-chunk-load-rate", -1.0);
}
+
+ public static boolean useDimensionTypeForCustomSpawners;
diff --git a/patches/server/0876-Don-t-allow-vehicle-movement-from-players-while-tele.patch b/patches/server/0876-Don-t-allow-vehicle-movement-from-players-while-tele.patch
index bd0b399825..d7c1d836f5 100644
--- a/patches/server/0876-Don-t-allow-vehicle-movement-from-players-while-tele.patch
+++ b/patches/server/0876-Don-t-allow-vehicle-movement-from-players-while-tele.patch
@@ -7,7 +7,7 @@ Bring the vehicle move packet behavior in line with the
regular player move packet.
diff --git a/src/main/java/net/minecraft/server/network/ServerGamePacketListenerImpl.java b/src/main/java/net/minecraft/server/network/ServerGamePacketListenerImpl.java
-index 952debf2fb4abf675e226224909b14c866528e62..68e1ab0057452228817ecbc6556338a8906c2538 100644
+index 952debf2fb4abf675e226224909b14c866528e62..e4d54fdc28b6161e74626f25299b1081e6605e98 100644
--- a/src/main/java/net/minecraft/server/network/ServerGamePacketListenerImpl.java
+++ b/src/main/java/net/minecraft/server/network/ServerGamePacketListenerImpl.java
@@ -517,6 +517,12 @@ public class ServerGamePacketListenerImpl implements ServerPlayerConnection, Ser
@@ -15,7 +15,7 @@ index 952debf2fb4abf675e226224909b14c866528e62..68e1ab0057452228817ecbc6556338a8
Entity entity = this.player.getRootVehicle();
+ // Paper start
-+ if (this.awaitingPositionFromClient != null) {
++ if (this.awaitingPositionFromClient != null || this.player.isImmobile() || entity.isRemoved()) {
+ return;
+ }
+ // Paper end
diff --git a/patches/server/0886-Ensure-entity-passenger-world-matches-ridden-entity.patch b/patches/server/0886-Ensure-entity-passenger-world-matches-ridden-entity.patch
new file mode 100644
index 0000000000..7de0352dbb
--- /dev/null
+++ b/patches/server/0886-Ensure-entity-passenger-world-matches-ridden-entity.patch
@@ -0,0 +1,23 @@
+From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
+From: Spottedleaf <[email protected]>
+Date: Thu, 31 Mar 2022 05:11:37 -0700
+Subject: [PATCH] Ensure entity passenger world matches ridden entity
+
+Bad plugins doing this would cause some obvious problems...
+
+diff --git a/src/main/java/net/minecraft/world/entity/Entity.java b/src/main/java/net/minecraft/world/entity/Entity.java
+index 8b57a24d4e8469dfbfb4eb2d11ca616e1db98598..26911884384d5e8afd1b43360494b793374f505f 100644
+--- a/src/main/java/net/minecraft/world/entity/Entity.java
++++ b/src/main/java/net/minecraft/world/entity/Entity.java
+@@ -2590,6 +2590,11 @@ public abstract class Entity implements Nameable, EntityAccess, CommandSource {
+ }
+
+ protected boolean addPassenger(Entity entity) { // CraftBukkit
++ // Paper start
++ if (entity.level != this.level) {
++ throw new IllegalArgumentException("Entity passenger world must match");
++ }
++ // Paper end
+ if (entity == this) throw new IllegalArgumentException("Entities cannot become a passenger of themselves"); // Paper - issue 572
+ if (entity.getVehicle() != this) {
+ throw new IllegalStateException("Use x.startRiding(y), not y.addPassenger(x)");
diff --git a/patches/server/0887-Guard-against-invalid-entity-positions.patch b/patches/server/0887-Guard-against-invalid-entity-positions.patch
new file mode 100644
index 0000000000..a9bce43337
--- /dev/null
+++ b/patches/server/0887-Guard-against-invalid-entity-positions.patch
@@ -0,0 +1,45 @@
+From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
+From: Spottedleaf <[email protected]>
+Date: Thu, 31 Mar 2022 05:18:28 -0700
+Subject: [PATCH] Guard against invalid entity positions
+
+Anything not finite should be blocked and logged
+
+diff --git a/src/main/java/net/minecraft/world/entity/Entity.java b/src/main/java/net/minecraft/world/entity/Entity.java
+index 26911884384d5e8afd1b43360494b793374f505f..49cf3601df7b145d49b1fe9a71ba0bc60c5394b3 100644
+--- a/src/main/java/net/minecraft/world/entity/Entity.java
++++ b/src/main/java/net/minecraft/world/entity/Entity.java
+@@ -4090,11 +4090,33 @@ public abstract class Entity implements Nameable, EntityAccess, CommandSource {
+ return this.getZ((2.0D * this.random.nextDouble() - 1.0D) * widthScale);
+ }
+
++ // Paper start - block invalid positions
++ public static boolean checkPosition(Entity entity, double newX, double newY, double newZ) {
++ if (Double.isFinite(newX) && Double.isFinite(newY) && Double.isFinite(newZ)) {
++ return true;
++ }
++
++ String entityInfo = null;
++ try {
++ entityInfo = entity.toString();
++ } catch (Exception ex) {
++ entityInfo = "[Entity info unavailable] ";
++ }
++ LOGGER.error("New entity position is invalid! Tried to set invalid position (" + newX + "," + newY + "," + newZ + ") for entity " + entity.getClass().getName() + " located at " + entity.position + ", entity info: " + entityInfo, new Throwable());
++ return false;
++ }
++ // Paper end - block invalid positions
++
+ public final void setPosRaw(double x, double y, double z) {
+ // Paper start
+ this.setPosRaw(x, y, z, false);
+ }
+ public final void setPosRaw(double x, double y, double z, boolean forceBoundingBoxUpdate) {
++ // Paper start - block invalid positions
++ if (!checkPosition(this, x, y, z)) {
++ return;
++ }
++ // Paper end - block invalid positions
+ // Paper end
+ // Paper start - fix MC-4
+ if (this instanceof ItemEntity) {