mirror of
https://github.com/VolmitSoftware/Iris.git
synced 2026-04-22 16:09:16 +00:00
implement Headless for 1.20.4
This commit is contained in:
@@ -150,10 +150,12 @@ public class CommandDeveloper implements DecreeExecutor {
|
||||
@Decree(description = "Test")
|
||||
public void packBenchmark(
|
||||
@Param(description = "The pack to bench", aliases = {"pack"})
|
||||
IrisDimension dimension
|
||||
IrisDimension dimension,
|
||||
@Param(description = "Headless", defaultValue = "false")
|
||||
boolean headless
|
||||
) {
|
||||
Iris.info("test");
|
||||
IrisPackBenchmarking benchmark = new IrisPackBenchmarking(dimension, 1);
|
||||
IrisPackBenchmarking benchmark = new IrisPackBenchmarking(dimension, 1, headless);
|
||||
|
||||
}
|
||||
|
||||
|
||||
22
core/src/main/java/com/volmit/iris/core/nms/IHeadless.java
Normal file
22
core/src/main/java/com/volmit/iris/core/nms/IHeadless.java
Normal file
@@ -0,0 +1,22 @@
|
||||
package com.volmit.iris.core.nms;
|
||||
|
||||
import com.volmit.iris.core.pregenerator.PregenListener;
|
||||
import com.volmit.iris.util.documentation.ChunkCoordinates;
|
||||
import com.volmit.iris.util.documentation.RegionCoordinates;
|
||||
import com.volmit.iris.util.parallel.MultiBurst;
|
||||
|
||||
import java.io.Closeable;
|
||||
|
||||
public interface IHeadless extends Closeable {
|
||||
|
||||
void saveAll();
|
||||
|
||||
@RegionCoordinates
|
||||
boolean exists(int x, int z);
|
||||
|
||||
@RegionCoordinates
|
||||
void generateRegion(MultiBurst burst, int x, int z, PregenListener listener);
|
||||
|
||||
@ChunkCoordinates
|
||||
void generateChunk(int x, int z);
|
||||
}
|
||||
@@ -22,6 +22,7 @@ import com.volmit.iris.engine.framework.Engine;
|
||||
import com.volmit.iris.engine.object.IrisDimension;
|
||||
import com.volmit.iris.util.collection.KList;
|
||||
import com.volmit.iris.util.collection.KMap;
|
||||
import com.volmit.iris.util.documentation.RegionCoordinates;
|
||||
import com.volmit.iris.util.mantle.Mantle;
|
||||
import com.volmit.iris.util.math.Vector3d;
|
||||
import com.volmit.iris.util.nbt.mca.palette.MCABiomeContainer;
|
||||
@@ -119,4 +120,8 @@ public interface INMSBinding {
|
||||
boolean registerDimension(String name, IrisDimension dimension);
|
||||
|
||||
void injectBukkit();
|
||||
|
||||
default IHeadless createHeadless(Engine engine) {
|
||||
throw new IllegalStateException("Headless mode not supported");
|
||||
}
|
||||
}
|
||||
|
||||
@@ -0,0 +1,96 @@
|
||||
package com.volmit.iris.core.pregenerator.methods;
|
||||
|
||||
import com.volmit.iris.Iris;
|
||||
import com.volmit.iris.core.nms.IHeadless;
|
||||
import com.volmit.iris.core.nms.INMS;
|
||||
import com.volmit.iris.core.pregenerator.PregenListener;
|
||||
import com.volmit.iris.core.pregenerator.PregeneratorMethod;
|
||||
import com.volmit.iris.engine.framework.Engine;
|
||||
import com.volmit.iris.util.collection.KList;
|
||||
import com.volmit.iris.util.mantle.Mantle;
|
||||
import com.volmit.iris.util.parallel.MultiBurst;
|
||||
|
||||
import java.io.IOException;
|
||||
import java.util.Objects;
|
||||
import java.util.concurrent.Future;
|
||||
|
||||
public class HeadlessPregenMethod implements PregeneratorMethod {
|
||||
private final Engine engine;
|
||||
private final IHeadless headless;
|
||||
private final MultiBurst burst;
|
||||
private final KList<Future<?>> futures;
|
||||
|
||||
public HeadlessPregenMethod(Engine engine) {
|
||||
this.engine = engine;
|
||||
this.headless = INMS.get().createHeadless(engine);
|
||||
this.burst = new MultiBurst("Iris Headless", Thread.MAX_PRIORITY);
|
||||
this.futures = new KList<>();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void init() {}
|
||||
|
||||
@Override
|
||||
public void close() {
|
||||
waitForChunksPartial(0);
|
||||
burst.close();
|
||||
headless.saveAll();
|
||||
try {
|
||||
headless.close();
|
||||
} catch (IOException e) {
|
||||
Iris.error("Failed to close headless");
|
||||
e.printStackTrace();
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void save() {
|
||||
headless.saveAll();
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean supportsRegions(int x, int z, PregenListener listener) {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getMethod(int x, int z) {
|
||||
return "Headless";
|
||||
}
|
||||
|
||||
@Override
|
||||
public void generateRegion(int x, int z, PregenListener listener) {}
|
||||
|
||||
@Override
|
||||
public void generateChunk(int x, int z, PregenListener listener) {
|
||||
futures.removeIf(Future::isDone);
|
||||
waitForChunksPartial(512);
|
||||
futures.add(burst.complete(() -> {
|
||||
listener.onChunkGenerating(x, z);
|
||||
headless.generateChunk(x, z);
|
||||
listener.onChunkGenerated(x, z);
|
||||
}));
|
||||
}
|
||||
|
||||
@Override
|
||||
public Mantle getMantle() {
|
||||
return engine.getMantle().getMantle();
|
||||
}
|
||||
|
||||
private void waitForChunksPartial(int maxWaiting) {
|
||||
futures.removeWhere(Objects::isNull);
|
||||
while (futures.size() > maxWaiting) {
|
||||
try {
|
||||
Future<?> i = futures.remove(0);
|
||||
|
||||
if (i == null) {
|
||||
continue;
|
||||
}
|
||||
|
||||
i.get();
|
||||
} catch (Throwable e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -2,9 +2,17 @@ package com.volmit.iris.core.tools;
|
||||
|
||||
|
||||
import com.volmit.iris.Iris;
|
||||
import com.volmit.iris.core.IrisSettings;
|
||||
import com.volmit.iris.core.loader.IrisData;
|
||||
import com.volmit.iris.core.pregenerator.PregenTask;
|
||||
import com.volmit.iris.core.pregenerator.methods.HeadlessPregenMethod;
|
||||
import com.volmit.iris.core.pregenerator.methods.HybridPregenMethod;
|
||||
import com.volmit.iris.core.service.StudioSVC;
|
||||
import com.volmit.iris.engine.IrisEngine;
|
||||
import com.volmit.iris.engine.framework.Engine;
|
||||
import com.volmit.iris.engine.framework.EngineTarget;
|
||||
import com.volmit.iris.engine.object.IrisDimension;
|
||||
import com.volmit.iris.engine.object.IrisWorld;
|
||||
import com.volmit.iris.util.collection.KList;
|
||||
import com.volmit.iris.util.collection.KMap;
|
||||
import com.volmit.iris.util.exceptions.IrisException;
|
||||
@@ -36,13 +44,16 @@ public class IrisPackBenchmarking {
|
||||
public static boolean benchmarkInProgress = false;
|
||||
private IrisDimension IrisDimension;
|
||||
private int radius;
|
||||
private final boolean headless;
|
||||
private boolean finished = false;
|
||||
private Engine engine;
|
||||
PrecisionStopwatch stopwatch;
|
||||
|
||||
public IrisPackBenchmarking(IrisDimension dimension, int r) {
|
||||
public IrisPackBenchmarking(IrisDimension dimension, int r, boolean headless) {
|
||||
instance = this;
|
||||
this.IrisDimension = dimension;
|
||||
this.radius = r;
|
||||
this.headless = headless;
|
||||
runBenchmark();
|
||||
}
|
||||
|
||||
@@ -52,12 +63,12 @@ public class IrisPackBenchmarking {
|
||||
service.submit(() -> {
|
||||
Iris.info("Setting up benchmark environment ");
|
||||
benchmarkInProgress = true;
|
||||
File file = new File("benchmark");
|
||||
File file = new File(Bukkit.getWorldContainer(), "benchmark");
|
||||
if (file.exists()) {
|
||||
deleteDirectory(file.toPath());
|
||||
}
|
||||
createBenchmark();
|
||||
while (!IrisToolbelt.isIrisWorld(Bukkit.getWorld("benchmark"))) {
|
||||
engine = createBenchmark();
|
||||
while (!headless && !IrisToolbelt.isIrisWorld(Bukkit.getWorld("benchmark"))) {
|
||||
J.sleep(1000);
|
||||
Iris.debug("Iris PackBenchmark: Waiting...");
|
||||
}
|
||||
@@ -75,7 +86,6 @@ public class IrisPackBenchmarking {
|
||||
public void finishedBenchmark(KList<Integer> cps) {
|
||||
try {
|
||||
String time = Form.duration(stopwatch.getMillis());
|
||||
Engine engine = IrisToolbelt.access(Bukkit.getWorld("benchmark")).getEngine();
|
||||
Iris.info("-----------------");
|
||||
Iris.info("Results:");
|
||||
Iris.info("- Total time: " + time);
|
||||
@@ -88,8 +98,8 @@ public class IrisPackBenchmarking {
|
||||
File profilers = new File("plugins" + File.separator + "Iris" + File.separator + "packbenchmarks");
|
||||
profilers.mkdir();
|
||||
|
||||
File results = new File("plugins " + File.separator + "Iris", IrisDimension.getName() + LocalDateTime.now(Clock.systemDefaultZone()) + ".txt");
|
||||
results.createNewFile();
|
||||
File results = new File("plugins" + File.separator + "Iris", IrisDimension.getName() + " " + LocalDateTime.now(Clock.systemDefaultZone()).toString().replace(':', '-') + ".txt");
|
||||
results.getParentFile().mkdirs();
|
||||
KMap<String, Double> metrics = engine.getMetrics().pull();
|
||||
try (FileWriter writer = new FileWriter(results)) {
|
||||
writer.write("-----------------\n");
|
||||
@@ -123,15 +133,32 @@ public class IrisPackBenchmarking {
|
||||
e.printStackTrace();
|
||||
}
|
||||
}
|
||||
private void createBenchmark(){
|
||||
private Engine createBenchmark(){
|
||||
try {
|
||||
IrisToolbelt.createWorld()
|
||||
if (headless) {
|
||||
IrisWorld world = IrisWorld.builder()
|
||||
.name("benchmark")
|
||||
.minHeight(IrisDimension.getMinHeight())
|
||||
.maxHeight(IrisDimension.getMaxHeight())
|
||||
.seed(1337)
|
||||
.worldFolder(new File(Bukkit.getWorldContainer(), "benchmark"))
|
||||
.environment(IrisDimension.getEnvironment())
|
||||
.build();
|
||||
Iris.service(StudioSVC.class).installIntoWorld(
|
||||
Iris.getSender(),
|
||||
IrisDimension.getLoadKey(),
|
||||
world.worldFolder());
|
||||
var data = IrisData.get(new File(world.worldFolder(), "iris/pack"));
|
||||
var dim = data.getDimensionLoader().load(IrisDimension.getLoadKey());
|
||||
return new IrisEngine(new EngineTarget(world, dim, data), false);
|
||||
}
|
||||
return IrisToolbelt.access(IrisToolbelt.createWorld()
|
||||
.dimension(IrisDimension.getName())
|
||||
.name("benchmark")
|
||||
.seed(1337)
|
||||
.studio(false)
|
||||
.benchmark(true)
|
||||
.create();
|
||||
.create()).getEngine();
|
||||
} catch (IrisException e) {
|
||||
throw new RuntimeException(e);
|
||||
}
|
||||
@@ -146,8 +173,8 @@ public class IrisPackBenchmarking {
|
||||
.center(new Position2(x, z))
|
||||
.width(5)
|
||||
.height(5)
|
||||
.build(), Bukkit.getWorld("benchmark")
|
||||
);
|
||||
.build(), headless ? new HeadlessPregenMethod(engine) : new HybridPregenMethod(engine.getWorld().realWorld(),
|
||||
IrisSettings.getThreadCount(IrisSettings.get().getConcurrency().getParallelism())), engine);
|
||||
}
|
||||
|
||||
private double calculateAverage(KList<Integer> list) {
|
||||
|
||||
@@ -286,6 +286,13 @@ public class IrisEngine implements Engine {
|
||||
return generated.get();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void addGenerated() {
|
||||
if (generated.incrementAndGet() == 661) {
|
||||
J.a(() -> getData().savePrefetch(this));
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public double getGeneratedPerSecond() {
|
||||
if (perSecondLatch.flip()) {
|
||||
@@ -468,11 +475,7 @@ public class IrisEngine implements Engine {
|
||||
|
||||
getMantle().getMantle().flag(x >> 4, z >> 4, MantleFlag.REAL, true);
|
||||
getMetrics().getTotal().put(p.getMilliseconds());
|
||||
generated.incrementAndGet();
|
||||
|
||||
if (generated.get() == 661) {
|
||||
J.a(() -> getData().savePrefetch(this));
|
||||
}
|
||||
addGenerated();
|
||||
} catch (Throwable e) {
|
||||
Iris.reportError(e);
|
||||
fail("Failed to generate " + x + ", " + z, e);
|
||||
|
||||
@@ -577,6 +577,8 @@ public interface Engine extends DataProvider, Fallible, LootProvider, BlockUpdat
|
||||
|
||||
int getGenerated();
|
||||
|
||||
void addGenerated();
|
||||
|
||||
default <T> IrisPosition lookForStreamResult(T find, ProceduralStream<T> stream, Function2<T, T, Boolean> matcher, long timeout) {
|
||||
AtomicInteger checked = new AtomicInteger();
|
||||
AtomicLong time = new AtomicLong(M.ms());
|
||||
|
||||
Reference in New Issue
Block a user