use of org.spongepowered.asm.util.PrettyPrinter in project SpongeCommon by SpongePowered.
the class PhaseTracker method printEmptyStackOnCompletion.
private void printEmptyStackOnCompletion() {
if (this.hasPrintedEmptyOnce) {
// because of it.
return;
}
final PrettyPrinter printer = new PrettyPrinter(60).add("Unexpectedly Completing An Empty Stack").centre().hr().addWrapped(60, "Sponge's tracking system is very dependent on knowing when" + " a change to any world takes place, however, we have been told" + " to complete a \"phase\" without having entered any phases." + " This is an error usually on Sponge's part, so a report" + " is required on the issue tracker on GitHub.").hr().add("StackTrace:").add(new Exception()).add();
this.generateVersionInfo(printer);
printer.trace(System.err, SpongeImpl.getLogger(), Level.ERROR);
if (!SpongeImpl.getGlobalConfig().getConfig().getPhaseTracker().isVerbose()) {
this.hasPrintedEmptyOnce = true;
}
}
use of org.spongepowered.asm.util.PrettyPrinter in project SpongeCommon by SpongePowered.
the class PhaseTracker method printIncorrectPhaseCompletion.
private void printIncorrectPhaseCompletion(IPhaseState<?> prevState, IPhaseState<?> state) {
if (!SpongeImpl.getGlobalConfig().getConfig().getPhaseTracker().isVerbose() && !this.completedIncorrectStates.isEmpty()) {
for (Tuple<IPhaseState<?>, IPhaseState<?>> tuple : this.completedIncorrectStates) {
if ((tuple.getFirst().equals(prevState) && tuple.getSecond().equals(state))) {
// being completed incorrectly. only print it once.
return;
}
}
}
PrettyPrinter printer = new PrettyPrinter(60).add("Completing incorrect phase").centre().hr().addWrapped("Sponge's tracking system is very dependent on knowing when" + " a change to any world takes place, however, we are attempting" + " to complete a \"phase\" other than the one we most recently entered." + " This is an error usually on Sponge's part, so a report" + " is required on the issue tracker on GitHub.").hr().add("Expected to exit phase: %s", prevState).add("But instead found phase: %s", state).add("StackTrace:").add(new Exception());
printer.add(" Phases Remaining:");
this.stack.forEach(data -> PHASE_PRINTER.accept(printer, data));
printer.add();
this.generateVersionInfo(printer);
printer.trace(System.err, SpongeImpl.getLogger(), Level.ERROR);
if (!SpongeImpl.getGlobalConfig().getConfig().getPhaseTracker().isVerbose()) {
this.completedIncorrectStates.add(new Tuple<>(prevState, state));
}
}
use of org.spongepowered.asm.util.PrettyPrinter in project SpongeCommon by SpongePowered.
the class PhaseTracker method printExceptionSpawningEntity.
private void printExceptionSpawningEntity(PhaseContext<?> context, Throwable e) {
if (!SpongeImpl.getGlobalConfig().getConfig().getPhaseTracker().isVerbose() && !this.printedExceptionsForEntities.isEmpty()) {
if (this.printedExceptionsForEntities.contains(context.state)) {
return;
}
}
final PrettyPrinter printer = new PrettyPrinter(60).add("Exception attempting to capture or spawn an Entity!").centre().hr();
printer.addWrapped(60, "%s :", "PhaseContext");
CONTEXT_PRINTER.accept(printer, context);
printer.addWrapped(60, "%s :", "Phases remaining");
this.stack.forEach(data -> PHASE_PRINTER.accept(printer, data));
printer.add("Stacktrace:");
printer.add(e);
printer.trace(System.err, SpongeImpl.getLogger(), Level.ERROR);
if (!SpongeImpl.getGlobalConfig().getConfig().getPhaseTracker().isVerbose()) {
this.printedExceptionsForEntities.add(context.state);
}
}
use of org.spongepowered.asm.util.PrettyPrinter in project SpongeCommon by SpongePowered.
the class PhaseTracker method validateEntitySpawn.
/**
* Validates the {@link Entity} being spawned is being spawned on the main server
* thread, if it is available. If the entity is NOT being spawned on the main server thread,
* well..... a mod (or plugin) is attempting to spawn an entity to the world
* <b>off thread</b>. The problem with doing this is that the PhaseTracker is
* <b>not</b> thread safe, and capturing entities off thread is always bad.
*
* @param mixinWorldServer The server the entity is being spawned into
* @param entity The entity to spawn
* @return True if the entity spawn is on the main thread.
*/
public static boolean validateEntitySpawn(IMixinWorldServer mixinWorldServer, Entity entity) {
if (Sponge.isServerAvailable() && (Sponge.getServer().isMainThread() || SpongeImpl.getServer().isServerStopped())) {
return true;
}
// We will DEFINITELY be doing bad things otherwise. We need to artificially capture here.
if (!SpongeImpl.getGlobalConfig().getConfig().getPhaseTracker().captureEntitiesAsync()) {
// Print a pretty warning about not capturing an async spawned entity, but don't care about spawning.
if (!SpongeImpl.getGlobalConfig().getConfig().getPhaseTracker().isVerbose()) {
return false;
}
// If we have, we don't want to print any more times.
if (!SpongeImpl.getGlobalConfig().getConfig().getPhaseTracker().verboseErrors() && PhaseTracker.getInstance().hasPrintedAsyncEntities) {
return false;
}
// Otherwise, let's print out either the first time, or several more times.
new PrettyPrinter(60).add("Async Entity Spawn Warning").centre().hr().add("An entity was attempting to spawn off the \"main\" server thread").add().add("Details of the spawning are disabled according to the Sponge").add("configuration file. A stack trace of the attempted spawn should").add("provide information about how it was being spawned. Sponge is").add("currently configured to NOT attempt to capture this spawn and").add("spawn the entity at an appropriate time, while on the main server").add("thread.").add().add("Details of the spawn:").add("%s : %s", "Entity", entity).add("Stacktrace").add(new Exception("Async entity spawn attempt")).trace(SpongeImpl.getLogger(), Level.WARN);
PhaseTracker.getInstance().hasPrintedAsyncEntities = true;
return false;
}
ASYNC_CAPTURED_ENTITIES.add((net.minecraft.entity.Entity) entity);
// Print a pretty warning about not capturing an async spawned entity, but don't care about spawning.
if (!SpongeImpl.getGlobalConfig().getConfig().getPhaseTracker().isVerbose()) {
return false;
}
// If we have, we don't want to print any more times.
if (!SpongeImpl.getGlobalConfig().getConfig().getPhaseTracker().verboseErrors() && PhaseTracker.getInstance().hasPrintedAsyncEntities) {
return false;
}
// Otherwise, let's print out either the first time, or several more times.
new PrettyPrinter(60).add("Async Entity Spawn Warning").centre().hr().add("An entity was attempting to spawn off the \"main\" server thread").add().add("Delayed spawning is ENABLED for Sponge.").add("The entity is safely captured by Sponge while off the main").add("server thread, and therefore will be spawned the next tick.").add("Some cases where a mod is expecting the entity back while").add("async can cause issues with said mod.").add().add("Details of the spawn:").add("%s : %s", "Entity", entity).add("Stacktrace").add(new Exception("Async entity spawn attempt")).trace(SpongeImpl.getLogger(), Level.WARN);
PhaseTracker.getInstance().hasPrintedAsyncEntities = true;
return false;
}
use of org.spongepowered.asm.util.PrettyPrinter in project SpongeCommon by SpongePowered.
the class PhaseTracker method printRunnawayPhaseCompletion.
private void printRunnawayPhaseCompletion(IPhaseState<?> state) {
if (!SpongeImpl.getGlobalConfig().getConfig().getPhaseTracker().isVerbose() && !this.hasPrintedAboutRunnawayPhases) {
// Avoiding spam logs.
return;
}
final PrettyPrinter printer = new PrettyPrinter(60);
printer.add("Completing Phase").centre().hr();
printer.addWrapped(60, "Detecting a runaway phase! Potentially a problem " + "where something isn't completing a phase!!! Sponge will stop printing" + "after three more times to avoid generating extra logs");
printer.add();
printer.addWrapped(60, "%s : %s", "Completing phase", state);
printer.add(" Phases Remaining:");
this.stack.forEach(data -> PHASE_PRINTER.accept(printer, data));
printer.add();
printer.add("Stacktrace:");
printer.add(new Exception("Stack trace"));
printer.add();
this.generateVersionInfo(printer);
printer.trace(System.err, SpongeImpl.getLogger(), Level.ERROR);
if (!SpongeImpl.getGlobalConfig().getConfig().getPhaseTracker().isVerbose() && this.printRunawayCount++ > 3) {
this.hasPrintedAboutRunnawayPhases = true;
}
}
Aggregations