1
0
mirror of https://github.com/Minestom/Minestom.git synced 2025-04-06 04:07:45 +02:00
Minestom/src/main/java/net/minestom/server/thread/BatchThread.java
2021-04-14 22:48:13 +02:00

107 lines
3.0 KiB
Java

package net.minestom.server.thread;
import net.minestom.server.MinecraftServer;
import net.minestom.server.lock.Acquisition;
import net.minestom.server.utils.validate.Check;
import org.jetbrains.annotations.NotNull;
import java.util.ArrayDeque;
import java.util.Queue;
import java.util.concurrent.CountDownLatch;
public class BatchThread extends Thread {
private final BatchRunnable runnable;
private final BatchQueue queue;
public BatchThread(@NotNull BatchRunnable runnable, int number) {
super(runnable, MinecraftServer.THREAD_NAME_TICK + "-" + number);
this.runnable = runnable;
this.queue = new BatchQueue();
this.runnable.setLinkedThread(this);
}
@NotNull
public BatchRunnable getMainRunnable() {
return runnable;
}
@NotNull
public BatchQueue getQueue() {
return queue;
}
public void shutdown() {
this.runnable.stop = true;
}
public static class BatchRunnable implements Runnable {
private volatile boolean stop;
private BatchThread batchThread;
private volatile boolean inTick;
private volatile CountDownLatch countDownLatch;
private final Queue<Runnable> queue = new ArrayDeque<>();
private final Object tickLock = new Object();
@Override
public void run() {
Check.notNull(batchThread, "The linked BatchThread cannot be null!");
while (!stop) {
// The latch is necessary to control the tick rates
if (countDownLatch == null)
continue;
synchronized (tickLock) {
this.inTick = true;
// Execute all pending runnable
Runnable runnable;
while ((runnable = queue.poll()) != null) {
runnable.run();
}
// Execute waiting acquisition
{
Acquisition.processThreadTick(batchThread.getQueue());
}
this.countDownLatch.countDown();
this.countDownLatch = null;
this.inTick = false;
// Wait for the next notify (game tick)
try {
this.tickLock.wait();
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
}
public synchronized void startTick(@NotNull CountDownLatch countDownLatch, Runnable runnable) {
synchronized (tickLock) {
this.queue.add(runnable);
this.countDownLatch = countDownLatch;
this.tickLock.notifyAll();
}
}
public boolean isInTick() {
return inTick;
}
private void setLinkedThread(BatchThread batchThread) {
this.batchThread = batchThread;
}
}
}