Optimise multiple block updates occurring in the same chunk

We can avoid multiple ticket additions for the same ChunkTasks
instance. This will help in situations where significant number of
block updates occur for the same chunk in the same tick, such as
water draining.
This commit is contained in:
Spottedleaf 2023-09-11 07:15:18 -07:00
parent c9cd94f3c6
commit fb06829845
2 changed files with 107 additions and 62 deletions

View File

@ -3035,10 +3035,10 @@ index 0000000000000000000000000000000000000000..ad1eeebe6de219143492b94da309cb54
+} +}
diff --git a/src/main/java/ca/spottedleaf/starlight/common/light/StarLightInterface.java b/src/main/java/ca/spottedleaf/starlight/common/light/StarLightInterface.java diff --git a/src/main/java/ca/spottedleaf/starlight/common/light/StarLightInterface.java b/src/main/java/ca/spottedleaf/starlight/common/light/StarLightInterface.java
new file mode 100644 new file mode 100644
index 0000000000000000000000000000000000000000..146c78a333e47cb4d8aa97700e19a12ca176ce76 index 0000000000000000000000000000000000000000..499c069d64692872924963d3a7ac39664b20468d
--- /dev/null --- /dev/null
+++ b/src/main/java/ca/spottedleaf/starlight/common/light/StarLightInterface.java +++ b/src/main/java/ca/spottedleaf/starlight/common/light/StarLightInterface.java
@@ -0,0 +1,673 @@ @@ -0,0 +1,674 @@
+package ca.spottedleaf.starlight.common.light; +package ca.spottedleaf.starlight.common.light;
+ +
+import ca.spottedleaf.starlight.common.util.CoordinateUtils; +import ca.spottedleaf.starlight.common.util.CoordinateUtils;
@ -3233,7 +3233,7 @@ index 0000000000000000000000000000000000000000..146c78a333e47cb4d8aa97700e19a12c
+ return this.hasBlockLight; + return this.hasBlockLight;
+ } + }
+ +
+ protected int getSkyLightValue(final BlockPos blockPos, final ChunkAccess chunk) { + public int getSkyLightValue(final BlockPos blockPos, final ChunkAccess chunk) {
+ if (!this.hasSkyLight) { + if (!this.hasSkyLight) {
+ return 0; + return 0;
+ } + }
@ -3303,7 +3303,7 @@ index 0000000000000000000000000000000000000000..146c78a333e47cb4d8aa97700e19a12c
+ return 15; + return 15;
+ } + }
+ +
+ protected int getBlockLightValue(final BlockPos blockPos, final ChunkAccess chunk) { + public int getBlockLightValue(final BlockPos blockPos, final ChunkAccess chunk) {
+ if (!this.hasBlockLight) { + if (!this.hasBlockLight) {
+ return 0; + return 0;
+ } + }
@ -3422,7 +3422,7 @@ index 0000000000000000000000000000000000000000..146c78a333e47cb4d8aa97700e19a12c
+ } + }
+ } + }
+ +
+ public CompletableFuture<Void> blockChange(final BlockPos pos) { + public LightQueue.ChunkTasks blockChange(final BlockPos pos) {
+ if (this.world == null || pos.getY() < WorldUtil.getMinBlockY(this.world) || pos.getY() > WorldUtil.getMaxBlockY(this.world)) { // empty world + if (this.world == null || pos.getY() < WorldUtil.getMinBlockY(this.world) || pos.getY() > WorldUtil.getMaxBlockY(this.world)) { // empty world
+ return null; + return null;
+ } + }
@ -3430,7 +3430,7 @@ index 0000000000000000000000000000000000000000..146c78a333e47cb4d8aa97700e19a12c
+ return this.lightQueue.queueBlockChange(pos); + return this.lightQueue.queueBlockChange(pos);
+ } + }
+ +
+ public CompletableFuture<Void> sectionChange(final SectionPos pos, final boolean newEmptyValue) { + public LightQueue.ChunkTasks sectionChange(final SectionPos pos, final boolean newEmptyValue) {
+ if (this.world == null) { // empty world + if (this.world == null) { // empty world
+ return null; + return null;
+ } + }
@ -3613,7 +3613,7 @@ index 0000000000000000000000000000000000000000..146c78a333e47cb4d8aa97700e19a12c
+ } + }
+ } + }
+ +
+ protected static final class LightQueue { + public static final class LightQueue {
+ +
+ protected final Long2ObjectLinkedOpenHashMap<ChunkTasks> chunkTasks = new Long2ObjectLinkedOpenHashMap<>(); + protected final Long2ObjectLinkedOpenHashMap<ChunkTasks> chunkTasks = new Long2ObjectLinkedOpenHashMap<>();
+ protected final StarLightInterface manager; + protected final StarLightInterface manager;
@ -3626,13 +3626,13 @@ index 0000000000000000000000000000000000000000..146c78a333e47cb4d8aa97700e19a12c
+ return this.chunkTasks.isEmpty(); + return this.chunkTasks.isEmpty();
+ } + }
+ +
+ public synchronized CompletableFuture<Void> queueBlockChange(final BlockPos pos) { + public synchronized LightQueue.ChunkTasks queueBlockChange(final BlockPos pos) {
+ final ChunkTasks tasks = this.chunkTasks.computeIfAbsent(CoordinateUtils.getChunkKey(pos), ChunkTasks::new); + final ChunkTasks tasks = this.chunkTasks.computeIfAbsent(CoordinateUtils.getChunkKey(pos), ChunkTasks::new);
+ tasks.changedPositions.add(pos.immutable()); + tasks.changedPositions.add(pos.immutable());
+ return tasks.onComplete; + return tasks;
+ } + }
+ +
+ public synchronized CompletableFuture<Void> queueSectionChange(final SectionPos pos, final boolean newEmptyValue) { + public synchronized LightQueue.ChunkTasks queueSectionChange(final SectionPos pos, final boolean newEmptyValue) {
+ final ChunkTasks tasks = this.chunkTasks.computeIfAbsent(CoordinateUtils.getChunkKey(pos), ChunkTasks::new); + final ChunkTasks tasks = this.chunkTasks.computeIfAbsent(CoordinateUtils.getChunkKey(pos), ChunkTasks::new);
+ +
+ if (tasks.changedSectionSet == null) { + if (tasks.changedSectionSet == null) {
@ -3640,20 +3640,20 @@ index 0000000000000000000000000000000000000000..146c78a333e47cb4d8aa97700e19a12c
+ } + }
+ tasks.changedSectionSet[pos.getY() - this.manager.minSection] = Boolean.valueOf(newEmptyValue); + tasks.changedSectionSet[pos.getY() - this.manager.minSection] = Boolean.valueOf(newEmptyValue);
+ +
+ return tasks.onComplete; + return tasks;
+ } + }
+ +
+ public synchronized CompletableFuture<Void> queueChunkLighting(final ChunkPos pos, final Runnable lightTask) { + public synchronized LightQueue.ChunkTasks queueChunkLighting(final ChunkPos pos, final Runnable lightTask) {
+ final ChunkTasks tasks = this.chunkTasks.computeIfAbsent(CoordinateUtils.getChunkKey(pos), ChunkTasks::new); + final ChunkTasks tasks = this.chunkTasks.computeIfAbsent(CoordinateUtils.getChunkKey(pos), ChunkTasks::new);
+ if (tasks.lightTasks == null) { + if (tasks.lightTasks == null) {
+ tasks.lightTasks = new ArrayList<>(); + tasks.lightTasks = new ArrayList<>();
+ } + }
+ tasks.lightTasks.add(lightTask); + tasks.lightTasks.add(lightTask);
+ +
+ return tasks.onComplete; + return tasks;
+ } + }
+ +
+ public synchronized CompletableFuture<Void> queueChunkSkylightEdgeCheck(final SectionPos pos, final ShortCollection sections) { + public synchronized LightQueue.ChunkTasks queueChunkSkylightEdgeCheck(final SectionPos pos, final ShortCollection sections) {
+ final ChunkTasks tasks = this.chunkTasks.computeIfAbsent(CoordinateUtils.getChunkKey(pos), ChunkTasks::new); + final ChunkTasks tasks = this.chunkTasks.computeIfAbsent(CoordinateUtils.getChunkKey(pos), ChunkTasks::new);
+ +
+ ShortOpenHashSet queuedEdges = tasks.queuedEdgeChecksSky; + ShortOpenHashSet queuedEdges = tasks.queuedEdgeChecksSky;
@ -3662,10 +3662,10 @@ index 0000000000000000000000000000000000000000..146c78a333e47cb4d8aa97700e19a12c
+ } + }
+ queuedEdges.addAll(sections); + queuedEdges.addAll(sections);
+ +
+ return tasks.onComplete; + return tasks;
+ } + }
+ +
+ public synchronized CompletableFuture<Void> queueChunkBlocklightEdgeCheck(final SectionPos pos, final ShortCollection sections) { + public synchronized LightQueue.ChunkTasks queueChunkBlocklightEdgeCheck(final SectionPos pos, final ShortCollection sections) {
+ final ChunkTasks tasks = this.chunkTasks.computeIfAbsent(CoordinateUtils.getChunkKey(pos), ChunkTasks::new); + final ChunkTasks tasks = this.chunkTasks.computeIfAbsent(CoordinateUtils.getChunkKey(pos), ChunkTasks::new);
+ +
+ ShortOpenHashSet queuedEdges = tasks.queuedEdgeChecksBlock; + ShortOpenHashSet queuedEdges = tasks.queuedEdgeChecksBlock;
@ -3674,7 +3674,7 @@ index 0000000000000000000000000000000000000000..146c78a333e47cb4d8aa97700e19a12c
+ } + }
+ queuedEdges.addAll(sections); + queuedEdges.addAll(sections);
+ +
+ return tasks.onComplete; + return tasks;
+ } + }
+ +
+ public void removeChunk(final ChunkPos pos) { + public void removeChunk(final ChunkPos pos) {
@ -3694,7 +3694,7 @@ index 0000000000000000000000000000000000000000..146c78a333e47cb4d8aa97700e19a12c
+ return this.chunkTasks.removeFirst(); + return this.chunkTasks.removeFirst();
+ } + }
+ +
+ protected static final class ChunkTasks { + public static final class ChunkTasks {
+ +
+ public final Set<BlockPos> changedPositions = new ObjectOpenHashSet<>(); + public final Set<BlockPos> changedPositions = new ObjectOpenHashSet<>();
+ public Boolean[] changedSectionSet; + public Boolean[] changedSectionSet;
@ -3702,6 +3702,7 @@ index 0000000000000000000000000000000000000000..146c78a333e47cb4d8aa97700e19a12c
+ public ShortOpenHashSet queuedEdgeChecksBlock; + public ShortOpenHashSet queuedEdgeChecksBlock;
+ public List<Runnable> lightTasks; + public List<Runnable> lightTasks;
+ +
+ public boolean isTicketAdded = false;
+ public final CompletableFuture<Void> onComplete = new CompletableFuture<>(); + public final CompletableFuture<Void> onComplete = new CompletableFuture<>();
+ +
+ public final long chunkCoordinate; + public final long chunkCoordinate;
@ -4518,7 +4519,7 @@ index d8b83c8c89143d78620f812c491a1950e3218eb1..f3c9a3dbb6f0e6f825b7477c89ed72ed
while (objectiterator.hasNext()) { while (objectiterator.hasNext()) {
diff --git a/src/main/java/net/minecraft/server/level/ThreadedLevelLightEngine.java b/src/main/java/net/minecraft/server/level/ThreadedLevelLightEngine.java diff --git a/src/main/java/net/minecraft/server/level/ThreadedLevelLightEngine.java b/src/main/java/net/minecraft/server/level/ThreadedLevelLightEngine.java
index 65d72701b13c25dd701533833055e77c2aff9db8..481272124b7589cff0aa05b6df5b7e6f1d539414 100644 index 65d72701b13c25dd701533833055e77c2aff9db8..6716d9acc8b31f3fc3642b47fa52ce32c5195a3e 100644
--- a/src/main/java/net/minecraft/server/level/ThreadedLevelLightEngine.java --- a/src/main/java/net/minecraft/server/level/ThreadedLevelLightEngine.java
+++ b/src/main/java/net/minecraft/server/level/ThreadedLevelLightEngine.java +++ b/src/main/java/net/minecraft/server/level/ThreadedLevelLightEngine.java
@@ -23,6 +23,17 @@ import net.minecraft.world.level.chunk.LightChunkGetter; @@ -23,6 +23,17 @@ import net.minecraft.world.level.chunk.LightChunkGetter;
@ -4539,7 +4540,7 @@ index 65d72701b13c25dd701533833055e77c2aff9db8..481272124b7589cff0aa05b6df5b7e6f
public class ThreadedLevelLightEngine extends LevelLightEngine implements AutoCloseable { public class ThreadedLevelLightEngine extends LevelLightEngine implements AutoCloseable {
public static final int DEFAULT_BATCH_SIZE = 1000; public static final int DEFAULT_BATCH_SIZE = 1000;
private static final Logger LOGGER = LogUtils.getLogger(); private static final Logger LOGGER = LogUtils.getLogger();
@@ -33,12 +44,153 @@ public class ThreadedLevelLightEngine extends LevelLightEngine implements AutoCl @@ -33,13 +44,161 @@ public class ThreadedLevelLightEngine extends LevelLightEngine implements AutoCl
private final int taskPerBatch = 1000; private final int taskPerBatch = 1000;
private final AtomicBoolean scheduled = new AtomicBoolean(); private final AtomicBoolean scheduled = new AtomicBoolean();
@ -4614,7 +4615,8 @@ index 65d72701b13c25dd701533833055e77c2aff9db8..481272124b7589cff0aa05b6df5b7e6f
+ +
+ private final Long2IntOpenHashMap chunksBeingWorkedOn = new Long2IntOpenHashMap(); + private final Long2IntOpenHashMap chunksBeingWorkedOn = new Long2IntOpenHashMap();
+ +
+ private void queueTaskForSection(final int chunkX, final int chunkY, final int chunkZ, final Supplier<CompletableFuture<Void>> runnable) { + private void queueTaskForSection(final int chunkX, final int chunkY, final int chunkZ,
+ final Supplier<ca.spottedleaf.starlight.common.light.StarLightInterface.LightQueue.ChunkTasks> runnable) {
+ final ServerLevel world = (ServerLevel)this.theLightEngine.getWorld(); + final ServerLevel world = (ServerLevel)this.theLightEngine.getWorld();
+ +
+ final ChunkAccess center = this.theLightEngine.getAnyChunkNow(chunkX, chunkZ); + final ChunkAccess center = this.theLightEngine.getAnyChunkNow(chunkX, chunkZ);
@ -4641,20 +4643,26 @@ index 65d72701b13c25dd701533833055e77c2aff9db8..481272124b7589cff0aa05b6df5b7e6f
+ +
+ final long key = CoordinateUtils.getChunkKey(chunkX, chunkZ); + final long key = CoordinateUtils.getChunkKey(chunkX, chunkZ);
+ +
+ final CompletableFuture<Void> updateFuture = runnable.get(); + final ca.spottedleaf.starlight.common.light.StarLightInterface.LightQueue.ChunkTasks updateFuture = runnable.get();
+ +
+ if (updateFuture == null) { + if (updateFuture == null) {
+ // not scheduled + // not scheduled
+ return; + return;
+ } + }
+ +
+ if (updateFuture.isTicketAdded) {
+ // ticket already added
+ return;
+ }
+ updateFuture.isTicketAdded = true;
+
+ final int references = this.chunksBeingWorkedOn.addTo(key, 1); + final int references = this.chunksBeingWorkedOn.addTo(key, 1);
+ if (references == 0) { + if (references == 0) {
+ final ChunkPos pos = new ChunkPos(chunkX, chunkZ); + final ChunkPos pos = new ChunkPos(chunkX, chunkZ);
+ world.getChunkSource().addRegionTicket(ca.spottedleaf.starlight.common.light.StarLightInterface.CHUNK_WORK_TICKET, pos, 0, pos); + world.getChunkSource().addRegionTicket(ca.spottedleaf.starlight.common.light.StarLightInterface.CHUNK_WORK_TICKET, pos, 0, pos);
+ } + }
+ +
+ updateFuture.thenAcceptAsync((final Void ignore) -> { + updateFuture.onComplete.thenAcceptAsync((final Void ignore) -> {
+ final int newReferences = this.chunksBeingWorkedOn.get(key); + final int newReferences = this.chunksBeingWorkedOn.get(key);
+ if (newReferences == 1) { + if (newReferences == 1) {
+ this.chunksBeingWorkedOn.remove(key); + this.chunksBeingWorkedOn.remove(key);
@ -4668,8 +4676,8 @@ index 65d72701b13c25dd701533833055e77c2aff9db8..481272124b7589cff0aa05b6df5b7e6f
+ LOGGER.error("Failed to remove ticket level for post chunk task " + new ChunkPos(chunkX, chunkZ), thr); + LOGGER.error("Failed to remove ticket level for post chunk task " + new ChunkPos(chunkX, chunkZ), thr);
+ } + }
+ }); + });
+ } }
+
+ @Override + @Override
+ public boolean hasLightWork() { + public boolean hasLightWork() {
+ // route to new light engine + // route to new light engine
@ -4689,12 +4697,13 @@ index 65d72701b13c25dd701533833055e77c2aff9db8..481272124b7589cff0aa05b6df5b7e6f
+ if (sky == 15) return 15; + if (sky == 15) return 15;
+ final int block = this.theLightEngine.getBlockReader().getLightValue(pos); + final int block = this.theLightEngine.getBlockReader().getLightValue(pos);
+ return Math.max(sky, block); + return Math.max(sky, block);
} + }
+ // Paper end - replace light engine imp + // Paper end - replace light engine imp
+
@Override @Override
public void close() { public void close() {
@@ -51,15 +203,16 @@ public class ThreadedLevelLightEngine extends LevelLightEngine implements AutoCl }
@@ -51,15 +210,16 @@ public class ThreadedLevelLightEngine extends LevelLightEngine implements AutoCl
@Override @Override
public void checkBlock(BlockPos pos) { public void checkBlock(BlockPos pos) {
@ -4717,7 +4726,7 @@ index 65d72701b13c25dd701533833055e77c2aff9db8..481272124b7589cff0aa05b6df5b7e6f
this.addTask(pos.x, pos.z, () -> { this.addTask(pos.x, pos.z, () -> {
return 0; return 0;
}, ThreadedLevelLightEngine.TaskType.PRE_UPDATE, Util.name(() -> { }, ThreadedLevelLightEngine.TaskType.PRE_UPDATE, Util.name(() -> {
@@ -82,17 +235,16 @@ public class ThreadedLevelLightEngine extends LevelLightEngine implements AutoCl @@ -82,17 +242,16 @@ public class ThreadedLevelLightEngine extends LevelLightEngine implements AutoCl
@Override @Override
public void updateSectionStatus(SectionPos pos, boolean notReady) { public void updateSectionStatus(SectionPos pos, boolean notReady) {
@ -4741,7 +4750,7 @@ index 65d72701b13c25dd701533833055e77c2aff9db8..481272124b7589cff0aa05b6df5b7e6f
this.addTask(chunkPos.x, chunkPos.z, ThreadedLevelLightEngine.TaskType.PRE_UPDATE, Util.name(() -> { this.addTask(chunkPos.x, chunkPos.z, ThreadedLevelLightEngine.TaskType.PRE_UPDATE, Util.name(() -> {
super.propagateLightSources(chunkPos); super.propagateLightSources(chunkPos);
}, () -> { }, () -> {
@@ -102,6 +254,7 @@ public class ThreadedLevelLightEngine extends LevelLightEngine implements AutoCl @@ -102,6 +261,7 @@ public class ThreadedLevelLightEngine extends LevelLightEngine implements AutoCl
@Override @Override
public void setLightEnabled(ChunkPos pos, boolean retainData) { public void setLightEnabled(ChunkPos pos, boolean retainData) {
@ -4749,7 +4758,7 @@ index 65d72701b13c25dd701533833055e77c2aff9db8..481272124b7589cff0aa05b6df5b7e6f
this.addTask(pos.x, pos.z, ThreadedLevelLightEngine.TaskType.PRE_UPDATE, Util.name(() -> { this.addTask(pos.x, pos.z, ThreadedLevelLightEngine.TaskType.PRE_UPDATE, Util.name(() -> {
super.setLightEnabled(pos, retainData); super.setLightEnabled(pos, retainData);
}, () -> { }, () -> {
@@ -111,6 +264,7 @@ public class ThreadedLevelLightEngine extends LevelLightEngine implements AutoCl @@ -111,6 +271,7 @@ public class ThreadedLevelLightEngine extends LevelLightEngine implements AutoCl
@Override @Override
public void queueSectionData(LightLayer lightType, SectionPos pos, @Nullable DataLayer nibbles) { public void queueSectionData(LightLayer lightType, SectionPos pos, @Nullable DataLayer nibbles) {
@ -4757,7 +4766,7 @@ index 65d72701b13c25dd701533833055e77c2aff9db8..481272124b7589cff0aa05b6df5b7e6f
this.addTask(pos.x(), pos.z(), () -> { this.addTask(pos.x(), pos.z(), () -> {
return 0; return 0;
}, ThreadedLevelLightEngine.TaskType.PRE_UPDATE, Util.name(() -> { }, ThreadedLevelLightEngine.TaskType.PRE_UPDATE, Util.name(() -> {
@@ -136,6 +290,7 @@ public class ThreadedLevelLightEngine extends LevelLightEngine implements AutoCl @@ -136,6 +297,7 @@ public class ThreadedLevelLightEngine extends LevelLightEngine implements AutoCl
@Override @Override
public void retainData(ChunkPos pos, boolean retainData) { public void retainData(ChunkPos pos, boolean retainData) {
@ -4765,7 +4774,7 @@ index 65d72701b13c25dd701533833055e77c2aff9db8..481272124b7589cff0aa05b6df5b7e6f
this.addTask(pos.x, pos.z, () -> { this.addTask(pos.x, pos.z, () -> {
return 0; return 0;
}, ThreadedLevelLightEngine.TaskType.PRE_UPDATE, Util.name(() -> { }, ThreadedLevelLightEngine.TaskType.PRE_UPDATE, Util.name(() -> {
@@ -146,6 +301,7 @@ public class ThreadedLevelLightEngine extends LevelLightEngine implements AutoCl @@ -146,6 +308,7 @@ public class ThreadedLevelLightEngine extends LevelLightEngine implements AutoCl
} }
public CompletableFuture<ChunkAccess> initializeLight(ChunkAccess chunk, boolean bl) { public CompletableFuture<ChunkAccess> initializeLight(ChunkAccess chunk, boolean bl) {
@ -4773,7 +4782,7 @@ index 65d72701b13c25dd701533833055e77c2aff9db8..481272124b7589cff0aa05b6df5b7e6f
ChunkPos chunkPos = chunk.getPos(); ChunkPos chunkPos = chunk.getPos();
this.addTask(chunkPos.x, chunkPos.z, ThreadedLevelLightEngine.TaskType.PRE_UPDATE, Util.name(() -> { this.addTask(chunkPos.x, chunkPos.z, ThreadedLevelLightEngine.TaskType.PRE_UPDATE, Util.name(() -> {
LevelChunkSection[] levelChunkSections = chunk.getSections(); LevelChunkSection[] levelChunkSections = chunk.getSections();
@@ -171,6 +327,37 @@ public class ThreadedLevelLightEngine extends LevelLightEngine implements AutoCl @@ -171,6 +334,37 @@ public class ThreadedLevelLightEngine extends LevelLightEngine implements AutoCl
} }
public CompletableFuture<ChunkAccess> lightChunk(ChunkAccess chunk, boolean excludeBlocks) { public CompletableFuture<ChunkAccess> lightChunk(ChunkAccess chunk, boolean excludeBlocks) {
@ -4811,7 +4820,7 @@ index 65d72701b13c25dd701533833055e77c2aff9db8..481272124b7589cff0aa05b6df5b7e6f
ChunkPos chunkPos = chunk.getPos(); ChunkPos chunkPos = chunk.getPos();
chunk.setLightCorrect(false); chunk.setLightCorrect(false);
this.addTask(chunkPos.x, chunkPos.z, ThreadedLevelLightEngine.TaskType.PRE_UPDATE, Util.name(() -> { this.addTask(chunkPos.x, chunkPos.z, ThreadedLevelLightEngine.TaskType.PRE_UPDATE, Util.name(() -> {
@@ -191,7 +378,7 @@ public class ThreadedLevelLightEngine extends LevelLightEngine implements AutoCl @@ -191,7 +385,7 @@ public class ThreadedLevelLightEngine extends LevelLightEngine implements AutoCl
} }
public void tryScheduleUpdate() { public void tryScheduleUpdate() {
@ -4820,7 +4829,7 @@ index 65d72701b13c25dd701533833055e77c2aff9db8..481272124b7589cff0aa05b6df5b7e6f
this.taskMailbox.tell(() -> { this.taskMailbox.tell(() -> {
this.runUpdate(); this.runUpdate();
this.scheduled.set(false); this.scheduled.set(false);
@@ -213,7 +400,7 @@ public class ThreadedLevelLightEngine extends LevelLightEngine implements AutoCl @@ -213,7 +407,7 @@ public class ThreadedLevelLightEngine extends LevelLightEngine implements AutoCl
} }
objectListIterator.back(j); objectListIterator.back(j);

View File

@ -780,7 +780,7 @@ index 0000000000000000000000000000000000000000..64b5803d002b2968841a5ddee987f98b
+ } + }
+} +}
diff --git a/src/main/java/ca/spottedleaf/starlight/common/light/StarLightInterface.java b/src/main/java/ca/spottedleaf/starlight/common/light/StarLightInterface.java diff --git a/src/main/java/ca/spottedleaf/starlight/common/light/StarLightInterface.java b/src/main/java/ca/spottedleaf/starlight/common/light/StarLightInterface.java
index 146c78a333e47cb4d8aa97700e19a12ca176ce76..691239e65b0870ceb0d071b57793cff9b2593f62 100644 index 499c069d64692872924963d3a7ac39664b20468d..ef8ea36b2acefb935afda01396d2699e2921f396 100644
--- a/src/main/java/ca/spottedleaf/starlight/common/light/StarLightInterface.java --- a/src/main/java/ca/spottedleaf/starlight/common/light/StarLightInterface.java
+++ b/src/main/java/ca/spottedleaf/starlight/common/light/StarLightInterface.java +++ b/src/main/java/ca/spottedleaf/starlight/common/light/StarLightInterface.java
@@ -41,14 +41,14 @@ public final class StarLightInterface { @@ -41,14 +41,14 @@ public final class StarLightInterface {
@ -845,6 +845,24 @@ index 146c78a333e47cb4d8aa97700e19a12ca176ce76..691239e65b0870ceb0d071b57793cff9
if (this.cachedBlockPropagators == null) { if (this.cachedBlockPropagators == null) {
return; return;
} }
@@ -381,7 +382,7 @@ public final class StarLightInterface {
}
}
- public LightQueue.ChunkTasks blockChange(final BlockPos pos) {
+ public io.papermc.paper.chunk.system.light.LightQueue.ChunkTasks blockChange(final BlockPos pos) { // Paper - rewrite chunk system
if (this.world == null || pos.getY() < WorldUtil.getMinBlockY(this.world) || pos.getY() > WorldUtil.getMaxBlockY(this.world)) { // empty world
return null;
}
@@ -389,7 +390,7 @@ public final class StarLightInterface {
return this.lightQueue.queueBlockChange(pos);
}
- public LightQueue.ChunkTasks sectionChange(final SectionPos pos, final boolean newEmptyValue) {
+ public io.papermc.paper.chunk.system.light.LightQueue.ChunkTasks sectionChange(final SectionPos pos, final boolean newEmptyValue) { // Paper - rewrite chunk system
if (this.world == null) { // empty world
return null;
}
@@ -519,57 +520,15 @@ public final class StarLightInterface { @@ -519,57 +520,15 @@ public final class StarLightInterface {
} }
@ -905,7 +923,7 @@ index 146c78a333e47cb4d8aa97700e19a12ca176ce76..691239e65b0870ceb0d071b57793cff9
+ throw new UnsupportedOperationException("No longer implemented, task draining is now performed by the light thread"); // Paper - replace light queue + throw new UnsupportedOperationException("No longer implemented, task draining is now performed by the light thread"); // Paper - replace light queue
} }
protected static final class LightQueue { public static final class LightQueue {
diff --git a/src/main/java/co/aikar/timings/TimingsExport.java b/src/main/java/co/aikar/timings/TimingsExport.java diff --git a/src/main/java/co/aikar/timings/TimingsExport.java b/src/main/java/co/aikar/timings/TimingsExport.java
index 38f01952153348d937e326da0ec102cd9b0f80af..1080e1f67afe5574baca0df50cdb1d029a7a586a 100644 index 38f01952153348d937e326da0ec102cd9b0f80af..1080e1f67afe5574baca0df50cdb1d029a7a586a 100644
--- a/src/main/java/co/aikar/timings/TimingsExport.java --- a/src/main/java/co/aikar/timings/TimingsExport.java
@ -5951,7 +5969,7 @@ index 0000000000000000000000000000000000000000..8a11e10b01fa012b2f98b1c193c53251
+} +}
diff --git a/src/main/java/io/papermc/paper/chunk/system/light/LightQueue.java b/src/main/java/io/papermc/paper/chunk/system/light/LightQueue.java diff --git a/src/main/java/io/papermc/paper/chunk/system/light/LightQueue.java b/src/main/java/io/papermc/paper/chunk/system/light/LightQueue.java
new file mode 100644 new file mode 100644
index 0000000000000000000000000000000000000000..36e93fefdfbebddce4c153974c7cd81af3cb92e9 index 0000000000000000000000000000000000000000..de28d6ee71990da74d9deb360fac8bde5adbc918
--- /dev/null --- /dev/null
+++ b/src/main/java/io/papermc/paper/chunk/system/light/LightQueue.java +++ b/src/main/java/io/papermc/paper/chunk/system/light/LightQueue.java
@@ -0,0 +1,283 @@ @@ -0,0 +1,283 @@
@ -6036,7 +6054,7 @@ index 0000000000000000000000000000000000000000..36e93fefdfbebddce4c153974c7cd81a
+ } + }
+ } + }
+ +
+ public CompletableFuture<Void> queueBlockChange(final BlockPos pos) { + public ChunkTasks queueBlockChange(final BlockPos pos) {
+ final ChunkTasks tasks; + final ChunkTasks tasks;
+ synchronized (this) { + synchronized (this) {
+ tasks = this.chunkTasks.computeIfAbsent(CoordinateUtils.getChunkKey(pos), (final long keyInMap) -> { + tasks = this.chunkTasks.computeIfAbsent(CoordinateUtils.getChunkKey(pos), (final long keyInMap) -> {
@ -6047,10 +6065,10 @@ index 0000000000000000000000000000000000000000..36e93fefdfbebddce4c153974c7cd81a
+ +
+ tasks.schedule(); + tasks.schedule();
+ +
+ return tasks.onComplete; + return tasks;
+ } + }
+ +
+ public CompletableFuture<Void> queueSectionChange(final SectionPos pos, final boolean newEmptyValue) { + public ChunkTasks queueSectionChange(final SectionPos pos, final boolean newEmptyValue) {
+ final ChunkTasks tasks; + final ChunkTasks tasks;
+ synchronized (this) { + synchronized (this) {
+ tasks = this.chunkTasks.computeIfAbsent(CoordinateUtils.getChunkKey(pos), (final long keyInMap) -> { + tasks = this.chunkTasks.computeIfAbsent(CoordinateUtils.getChunkKey(pos), (final long keyInMap) -> {
@ -6065,10 +6083,10 @@ index 0000000000000000000000000000000000000000..36e93fefdfbebddce4c153974c7cd81a
+ +
+ tasks.schedule(); + tasks.schedule();
+ +
+ return tasks.onComplete; + return tasks;
+ } + }
+ +
+ public CompletableFuture<Void> queueChunkLightTask(final ChunkPos pos, final BooleanSupplier lightTask, final PrioritisedExecutor.Priority priority) { + public ChunkTasks queueChunkLightTask(final ChunkPos pos, final BooleanSupplier lightTask, final PrioritisedExecutor.Priority priority) {
+ final ChunkTasks tasks; + final ChunkTasks tasks;
+ synchronized (this) { + synchronized (this) {
+ tasks = this.chunkTasks.computeIfAbsent(CoordinateUtils.getChunkKey(pos), (final long keyInMap) -> { + tasks = this.chunkTasks.computeIfAbsent(CoordinateUtils.getChunkKey(pos), (final long keyInMap) -> {
@ -6082,10 +6100,10 @@ index 0000000000000000000000000000000000000000..36e93fefdfbebddce4c153974c7cd81a
+ +
+ tasks.schedule(); + tasks.schedule();
+ +
+ return tasks.onComplete; + return tasks;
+ } + }
+ +
+ public CompletableFuture<Void> queueChunkSkylightEdgeCheck(final SectionPos pos, final ShortCollection sections) { + public ChunkTasks queueChunkSkylightEdgeCheck(final SectionPos pos, final ShortCollection sections) {
+ final ChunkTasks tasks; + final ChunkTasks tasks;
+ synchronized (this) { + synchronized (this) {
+ tasks = this.chunkTasks.computeIfAbsent(CoordinateUtils.getChunkKey(pos), (final long keyInMap) -> { + tasks = this.chunkTasks.computeIfAbsent(CoordinateUtils.getChunkKey(pos), (final long keyInMap) -> {
@ -6101,10 +6119,10 @@ index 0000000000000000000000000000000000000000..36e93fefdfbebddce4c153974c7cd81a
+ +
+ tasks.schedule(); + tasks.schedule();
+ +
+ return tasks.onComplete; + return tasks;
+ } + }
+ +
+ public CompletableFuture<Void> queueChunkBlocklightEdgeCheck(final SectionPos pos, final ShortCollection sections) { + public ChunkTasks queueChunkBlocklightEdgeCheck(final SectionPos pos, final ShortCollection sections) {
+ final ChunkTasks tasks; + final ChunkTasks tasks;
+ +
+ synchronized (this) { + synchronized (this) {
@ -6121,7 +6139,7 @@ index 0000000000000000000000000000000000000000..36e93fefdfbebddce4c153974c7cd81a
+ +
+ tasks.schedule(); + tasks.schedule();
+ +
+ return tasks.onComplete; + return tasks;
+ } + }
+ +
+ public void removeChunk(final ChunkPos pos) { + public void removeChunk(final ChunkPos pos) {
@ -6134,20 +6152,20 @@ index 0000000000000000000000000000000000000000..36e93fefdfbebddce4c153974c7cd81a
+ } + }
+ } + }
+ +
+ protected static final class ChunkTasks implements Runnable { + public static final class ChunkTasks implements Runnable {
+
+ final Set<BlockPos> changedPositions = new HashSet<>();
+ Boolean[] changedSectionSet;
+ ShortOpenHashSet queuedEdgeChecksSky;
+ ShortOpenHashSet queuedEdgeChecksBlock;
+ List<BooleanSupplier> lightTasks;
+
+ final CompletableFuture<Void> onComplete = new CompletableFuture<>();
+ +
+ public final CompletableFuture<Void> onComplete = new CompletableFuture<>();
+ public boolean isTicketAdded;
+ public final long chunkCoordinate; + public final long chunkCoordinate;
+
+ private final StarLightInterface lightEngine; + private final StarLightInterface lightEngine;
+ private final LightQueue queue; + private final LightQueue queue;
+ private final PrioritisedExecutor.PrioritisedTask task; + private final PrioritisedExecutor.PrioritisedTask task;
+ private final Set<BlockPos> changedPositions = new HashSet<>();
+ private Boolean[] changedSectionSet;
+ private ShortOpenHashSet queuedEdgeChecksSky;
+ private ShortOpenHashSet queuedEdgeChecksBlock;
+ private List<BooleanSupplier> lightTasks;
+ +
+ public ChunkTasks(final long chunkCoordinate, final StarLightInterface lightEngine, final LightQueue queue) { + public ChunkTasks(final long chunkCoordinate, final StarLightInterface lightEngine, final LightQueue queue) {
+ this(chunkCoordinate, lightEngine, queue, PrioritisedExecutor.Priority.NORMAL); + this(chunkCoordinate, lightEngine, queue, PrioritisedExecutor.Priority.NORMAL);
@ -16980,7 +16998,7 @@ index 73c3070b2e300e0ab29ac1db1631023cef7970f8..f46ae930c6d1609dbefb56e67853f6e8
public boolean isDebugging() { public boolean isDebugging() {
diff --git a/src/main/java/net/minecraft/server/dedicated/DedicatedServer.java b/src/main/java/net/minecraft/server/dedicated/DedicatedServer.java diff --git a/src/main/java/net/minecraft/server/dedicated/DedicatedServer.java b/src/main/java/net/minecraft/server/dedicated/DedicatedServer.java
index 32d5d085721a6b9c539b261a2249f6206d0f8a87..ff279901038dfbed6a0b51cc5355ccd17efc6883 100644 index 14101c77fd9814a5d1e8e1bf0d8584f42086b051..fea6b32015f9e2654c40ad90301d7aaeb0dabf72 100644
--- a/src/main/java/net/minecraft/server/dedicated/DedicatedServer.java --- a/src/main/java/net/minecraft/server/dedicated/DedicatedServer.java
+++ b/src/main/java/net/minecraft/server/dedicated/DedicatedServer.java +++ b/src/main/java/net/minecraft/server/dedicated/DedicatedServer.java
@@ -399,7 +399,34 @@ public class DedicatedServer extends MinecraftServer implements ServerInterface @@ -399,7 +399,34 @@ public class DedicatedServer extends MinecraftServer implements ServerInterface
@ -20235,7 +20253,7 @@ index a0856fc649c50309258f015e623502dd46aeeab4..5a18f4649b64d47f429eb6c1dbb6238a
super(world, world.getSharedSpawnPos(), world.getSharedSpawnAngle(), profile); super(world, world.getSharedSpawnPos(), world.getSharedSpawnAngle(), profile);
this.chatVisibility = ChatVisiblity.FULL; this.chatVisibility = ChatVisiblity.FULL;
diff --git a/src/main/java/net/minecraft/server/level/ThreadedLevelLightEngine.java b/src/main/java/net/minecraft/server/level/ThreadedLevelLightEngine.java diff --git a/src/main/java/net/minecraft/server/level/ThreadedLevelLightEngine.java b/src/main/java/net/minecraft/server/level/ThreadedLevelLightEngine.java
index 481272124b7589cff0aa05b6df5b7e6f1d539414..b4be02ec4bb77059f79d3e4d6a6f1ee4843a01f9 100644 index 6716d9acc8b31f3fc3642b47fa52ce32c5195a3e..76bd323f25d7c2f4e12dd13baa53995fa4f8b27a 100644
--- a/src/main/java/net/minecraft/server/level/ThreadedLevelLightEngine.java --- a/src/main/java/net/minecraft/server/level/ThreadedLevelLightEngine.java
+++ b/src/main/java/net/minecraft/server/level/ThreadedLevelLightEngine.java +++ b/src/main/java/net/minecraft/server/level/ThreadedLevelLightEngine.java
@@ -37,15 +37,12 @@ import net.minecraft.world.level.chunk.ChunkStatus; @@ -37,15 +37,12 @@ import net.minecraft.world.level.chunk.ChunkStatus;
@ -20276,7 +20294,25 @@ index 481272124b7589cff0aa05b6df5b7e6f1d539414..b4be02ec4bb77059f79d3e4d6a6f1ee4
this.theLightEngine.relightChunks(chunks, (ChunkPos chunkPos) -> { this.theLightEngine.relightChunks(chunks, (ChunkPos chunkPos) -> {
chunkLightCallback.accept(chunkPos); chunkLightCallback.accept(chunkPos);
((java.util.concurrent.Executor)((ServerLevel)this.theLightEngine.getWorld()).getChunkSource().mainThreadProcessor).execute(() -> { ((java.util.concurrent.Executor)((ServerLevel)this.theLightEngine.getWorld()).getChunkSource().mainThreadProcessor).execute(() -> {
@@ -275,17 +271,11 @@ public class ThreadedLevelLightEngine extends LevelLightEngine implements AutoCl @@ -115,7 +111,7 @@ public class ThreadedLevelLightEngine extends LevelLightEngine implements AutoCl
private final Long2IntOpenHashMap chunksBeingWorkedOn = new Long2IntOpenHashMap();
private void queueTaskForSection(final int chunkX, final int chunkY, final int chunkZ,
- final Supplier<ca.spottedleaf.starlight.common.light.StarLightInterface.LightQueue.ChunkTasks> runnable) {
+ final Supplier<io.papermc.paper.chunk.system.light.LightQueue.ChunkTasks> runnable) { // Paper - rewrite chunk system
final ServerLevel world = (ServerLevel)this.theLightEngine.getWorld();
final ChunkAccess center = this.theLightEngine.getAnyChunkNow(chunkX, chunkZ);
@@ -142,7 +138,7 @@ public class ThreadedLevelLightEngine extends LevelLightEngine implements AutoCl
final long key = CoordinateUtils.getChunkKey(chunkX, chunkZ);
- final ca.spottedleaf.starlight.common.light.StarLightInterface.LightQueue.ChunkTasks updateFuture = runnable.get();
+ final io.papermc.paper.chunk.system.light.LightQueue.ChunkTasks updateFuture = runnable.get(); // Paper - rewrite chunk system
if (updateFuture == null) {
// not scheduled
@@ -282,17 +278,11 @@ public class ThreadedLevelLightEngine extends LevelLightEngine implements AutoCl
} }
private void addTask(int x, int z, ThreadedLevelLightEngine.TaskType stage, Runnable task) { private void addTask(int x, int z, ThreadedLevelLightEngine.TaskType stage, Runnable task) {
@ -20296,7 +20332,7 @@ index 481272124b7589cff0aa05b6df5b7e6f1d539414..b4be02ec4bb77059f79d3e4d6a6f1ee4
} }
@Override @Override
@@ -327,90 +317,15 @@ public class ThreadedLevelLightEngine extends LevelLightEngine implements AutoCl @@ -334,90 +324,15 @@ public class ThreadedLevelLightEngine extends LevelLightEngine implements AutoCl
} }
public CompletableFuture<ChunkAccess> lightChunk(ChunkAccess chunk, boolean excludeBlocks) { public CompletableFuture<ChunkAccess> lightChunk(ChunkAccess chunk, boolean excludeBlocks) {