Skip to content

Commit

Permalink
fix: introduce SignalUtils and fix ctrl+c operation
Browse files Browse the repository at this point in the history
  • Loading branch information
smartcmd committed Sep 21, 2024
1 parent de4c15f commit 2c99347
Show file tree
Hide file tree
Showing 2 changed files with 77 additions and 5 deletions.
14 changes: 9 additions & 5 deletions server/src/main/java/org/allaymc/server/AllayServer.java
Original file line number Diff line number Diff line change
Expand Up @@ -49,6 +49,7 @@
import org.allaymc.server.scroreboard.storage.JsonScoreboardStorage;
import org.allaymc.server.terminal.AllayTerminalConsole;
import org.allaymc.server.utils.AllayComputeThread;
import org.allaymc.server.utils.SignalUtils;
import org.allaymc.server.world.AllayWorldPool;
import org.apache.logging.log4j.Level;
import org.apache.logging.log4j.LogManager;
Expand Down Expand Up @@ -84,6 +85,7 @@ public final class AllayServer implements Server {
@Getter
private final AllayWorldPool worldPool = new AllayWorldPool();
private final AtomicBoolean isRunning = new AtomicBoolean(true);
private boolean isFullyStopped = false;
private final Object2ObjectMap<UUID, PlayerListPacket.Entry> playerListEntryMap = new Object2ObjectOpenHashMap<>();
@Getter
private final PlayerStorage playerStorage = Server.SETTINGS.storageSettings().savePlayerData() ? new AllayNBTFilePlayerStorage(Path.of("players")) : AllayEmptyPlayerStorage.INSTANCE;
Expand Down Expand Up @@ -153,11 +155,11 @@ public void start(long initialTime) {
ctx.updateLoggers();
}

Runtime.getRuntime().addShutdownHook(new Thread("ShutDownHookThread") {
@Override
public void run() {
if (isRunning.get()) return;
shutdown();
SignalUtils.addTask(() -> {
if (!isRunning.get()) return;
shutdown();
while (!isFullyStopped) {
Thread.yield();
}
});

Expand Down Expand Up @@ -238,6 +240,8 @@ private void shutdownReally() {
// Shutdown thread pools
virtualThreadPool.shutdown();
computeThreadPool.shutdown();

isFullyStopped = true;
}

@Override
Expand Down
68 changes: 68 additions & 0 deletions server/src/main/java/org/allaymc/server/utils/SignalUtils.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,68 @@
package org.allaymc.server.utils;

import lombok.experimental.UtilityClass;
import lombok.extern.slf4j.Slf4j;
import sun.misc.Signal;

import java.util.Deque;
import java.util.concurrent.ConcurrentLinkedDeque;
import java.util.concurrent.atomic.AtomicBoolean;

/**
* @author daoge_cmd
*/
@Slf4j
@UtilityClass
public class SignalUtils {

private static final AtomicBoolean TRIGGERED = new AtomicBoolean(false);
private static final AtomicBoolean SIGNAL_REGISTERED = new AtomicBoolean(false);
private static final String[] SIGNAL_LISTEN_TO = {"TERM", "INT"};
private static final Deque<Runnable> TASKS = new ConcurrentLinkedDeque<>();

public static void addTask(Runnable runnable) {
registerSignalIfNeeded();
TASKS.addLast(runnable);
}

public static void addTaskToFirst(Runnable runnable) {
registerSignalIfNeeded();
TASKS.addFirst(runnable);
}

private static void registerSignalIfNeeded() {
if (!SIGNAL_REGISTERED.getAndSet(true)) {
registerTermSignalIfNeeded();
}
}

private static void registerTermSignalIfNeeded() {
for (var name : SIGNAL_LISTEN_TO) {
Signal.handle(new Signal(name), signal -> {
log.info("Signal {} received", name);

if (TRIGGERED.getAndSet(true)) {
return;
}

try {
doTasks();
System.exit(0);
} catch (Throwable t) {
log.error("Error while executing shutdown tasks", t);
System.exit(1);
}
});
}
}

private static void doTasks() {
for (Runnable runnable : TASKS) {
try {
runnable.run();
} catch (Throwable t) {
log.error("Error while executing shutdown task: {}", runnable, t);
}
}
}
}

0 comments on commit 2c99347

Please sign in to comment.