Launching messages
This commit is contained in:
@@ -19,9 +19,6 @@ package org.jackhuang.hmcl.launch;
|
||||
|
||||
import org.jackhuang.hmcl.auth.AuthInfo;
|
||||
import org.jackhuang.hmcl.game.*;
|
||||
import org.jackhuang.hmcl.task.SimpleTaskResult;
|
||||
import org.jackhuang.hmcl.task.Task;
|
||||
import org.jackhuang.hmcl.task.TaskResult;
|
||||
import org.jackhuang.hmcl.util.*;
|
||||
|
||||
import java.io.*;
|
||||
@@ -220,14 +217,18 @@ public class DefaultLauncher extends Launcher {
|
||||
protected void appendJvmArgs(List<String> result) {
|
||||
}
|
||||
|
||||
public void decompressNatives(File destination) throws IOException {
|
||||
for (Library library : version.getLibraries())
|
||||
if (library.isNative())
|
||||
CompressingUtils.unzip(repository.getLibraryFile(version, library),
|
||||
destination,
|
||||
"",
|
||||
library.getExtract()::shouldExtract,
|
||||
false);
|
||||
public void decompressNatives(File destination) throws NotDecompressingNativesException {
|
||||
try {
|
||||
for (Library library : version.getLibraries())
|
||||
if (library.isNative())
|
||||
CompressingUtils.unzip(repository.getLibraryFile(version, library),
|
||||
destination,
|
||||
"",
|
||||
library.getExtract()::shouldExtract,
|
||||
false);
|
||||
} catch (IOException e) {
|
||||
throw new NotDecompressingNativesException(e);
|
||||
}
|
||||
}
|
||||
|
||||
protected Map<String, String> getConfigurations() {
|
||||
@@ -249,19 +250,26 @@ public class DefaultLauncher extends Launcher {
|
||||
@Override
|
||||
public ManagedProcess launch() throws IOException, InterruptedException {
|
||||
File nativeFolder = Files.createTempDirectory("minecraft").toFile();
|
||||
List<String> rawCommandLine = generateCommandLine(nativeFolder);
|
||||
|
||||
// To guarantee that when failed to generate code, we will not call precalled command
|
||||
ProcessBuilder builder = new ProcessBuilder(rawCommandLine);
|
||||
// To guarantee that when failed to generate launch command line, we will not call pre-launch command
|
||||
List<String> rawCommandLine = generateCommandLine(nativeFolder);
|
||||
|
||||
decompressNatives(nativeFolder);
|
||||
|
||||
if (StringUtils.isNotBlank(options.getPrecalledCommand()))
|
||||
Runtime.getRuntime().exec(options.getPrecalledCommand()).waitFor();
|
||||
|
||||
builder.directory(repository.getRunDirectory(version.getId()))
|
||||
.environment().put("APPDATA", options.getGameDir().getAbsoluteFile().getParent());
|
||||
ManagedProcess p = new ManagedProcess(builder.start(), rawCommandLine);
|
||||
Process process;
|
||||
try {
|
||||
ProcessBuilder builder = new ProcessBuilder(rawCommandLine);
|
||||
builder.directory(repository.getRunDirectory(version.getId()))
|
||||
.environment().put("APPDATA", options.getGameDir().getAbsoluteFile().getParent());
|
||||
process = builder.start();
|
||||
} catch (IOException e) {
|
||||
throw new ProcessCreationException(e);
|
||||
}
|
||||
|
||||
ManagedProcess p = new ManagedProcess(process, rawCommandLine);
|
||||
if (listener == null)
|
||||
startMonitors(p);
|
||||
else
|
||||
@@ -269,10 +277,6 @@ public class DefaultLauncher extends Launcher {
|
||||
return p;
|
||||
}
|
||||
|
||||
public final TaskResult<ManagedProcess> launchAsync() {
|
||||
return new SimpleTaskResult<>(LAUNCH_ASYNC_ID, this::launch);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void makeLaunchScript(File scriptFile) throws IOException {
|
||||
boolean isWindows = OperatingSystem.WINDOWS == OperatingSystem.CURRENT_OS;
|
||||
@@ -303,11 +307,7 @@ public class DefaultLauncher extends Launcher {
|
||||
writer.write(StringUtils.makeCommand(generateCommandLine(nativeFolder)));
|
||||
}
|
||||
if (!scriptFile.setExecutable(true))
|
||||
throw new IOException("Cannot make script file '" + scriptFile + "' executable.");
|
||||
}
|
||||
|
||||
public final Task makeLaunchScriptAsync(File file) {
|
||||
return Task.of(() -> makeLaunchScript(file));
|
||||
throw new PermissionException();
|
||||
}
|
||||
|
||||
private void startMonitors(ManagedProcess managedProcess) {
|
||||
@@ -362,7 +362,4 @@ public class DefaultLauncher extends Launcher {
|
||||
managedProcess.addRelatedThread(stderr);
|
||||
managedProcess.addRelatedThread(Lang.thread(new ExitWaiter(managedProcess, Arrays.asList(stdout, stderr), (exitCode, exitType) -> processListener.onExit(exitCode, exitType)), "exit-waiter", isDaemon));
|
||||
}
|
||||
|
||||
public static final String LAUNCH_ASYNC_ID = "process";
|
||||
public static final String LAUNCH_SCRIPT_ASYNC_ID = "script";
|
||||
}
|
||||
|
||||
@@ -65,16 +65,15 @@ final class ExitWaiter implements Runnable {
|
||||
ProcessListener.ExitType exitType;
|
||||
|
||||
// LaunchWrapper will catch the exception logged and will exit normally.
|
||||
if (exitCode != 0 || StringUtils.containsOne(errorLines, "Unable to launch")) {
|
||||
EventBus.EVENT_BUS.fireEvent(new ProcessExitedAbnormallyEvent(this, process));
|
||||
exitType = ProcessListener.ExitType.APPLICATION_ERROR;
|
||||
} else if (exitCode != 0 && StringUtils.containsOne(errorLines,
|
||||
if (exitCode != 0 && StringUtils.containsOne(errorLines,
|
||||
"Could not create the Java Virtual Machine.",
|
||||
"Error occurred during initialization of VM",
|
||||
"A fatal exception has occurred. Program will exit.",
|
||||
"Unable to launch")) {
|
||||
"A fatal exception has occurred. Program will exit.")) {
|
||||
EventBus.EVENT_BUS.fireEvent(new JVMLaunchFailedEvent(this, process));
|
||||
exitType = ProcessListener.ExitType.JVM_ERROR;
|
||||
} else if (exitCode != 0 || StringUtils.containsOne(errorLines, "Unable to launch")) {
|
||||
EventBus.EVENT_BUS.fireEvent(new ProcessExitedAbnormallyEvent(this, process));
|
||||
exitType = ProcessListener.ExitType.APPLICATION_ERROR;
|
||||
} else
|
||||
exitType = ProcessListener.ExitType.NORMAL;
|
||||
|
||||
@@ -82,7 +81,7 @@ final class ExitWaiter implements Runnable {
|
||||
|
||||
watcher.accept(exitCode, exitType);
|
||||
} catch (InterruptedException e) {
|
||||
watcher.accept(1, ProcessListener.ExitType.NORMAL);
|
||||
watcher.accept(1, ProcessListener.ExitType.INTERRUPTED);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -0,0 +1,37 @@
|
||||
/*
|
||||
* Hello Minecraft! Launcher.
|
||||
* Copyright (C) 2017 huangyuhui <huanghongxun2008@126.com>
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program. If not, see {http://www.gnu.org/licenses/}.
|
||||
*/
|
||||
package org.jackhuang.hmcl.launch;
|
||||
|
||||
import java.io.IOException;
|
||||
|
||||
public class NotDecompressingNativesException extends IOException {
|
||||
public NotDecompressingNativesException() {
|
||||
}
|
||||
|
||||
public NotDecompressingNativesException(String message) {
|
||||
super(message);
|
||||
}
|
||||
|
||||
public NotDecompressingNativesException(String message, Throwable cause) {
|
||||
super(message, cause);
|
||||
}
|
||||
|
||||
public NotDecompressingNativesException(Throwable cause) {
|
||||
super(cause);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,40 @@
|
||||
/*
|
||||
* Hello Minecraft! Launcher.
|
||||
* Copyright (C) 2017 huangyuhui <huanghongxun2008@126.com>
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program. If not, see {http://www.gnu.org/licenses/}.
|
||||
*/
|
||||
package org.jackhuang.hmcl.launch;
|
||||
|
||||
import java.io.IOException;
|
||||
|
||||
/**
|
||||
* Threw if unable to make file executable.
|
||||
*/
|
||||
public class PermissionException extends IOException {
|
||||
public PermissionException() {
|
||||
}
|
||||
|
||||
public PermissionException(String message) {
|
||||
super(message);
|
||||
}
|
||||
|
||||
public PermissionException(String message, Throwable cause) {
|
||||
super(message, cause);
|
||||
}
|
||||
|
||||
public PermissionException(Throwable cause) {
|
||||
super(cause);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,37 @@
|
||||
/*
|
||||
* Hello Minecraft! Launcher.
|
||||
* Copyright (C) 2017 huangyuhui <huanghongxun2008@126.com>
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program. If not, see {http://www.gnu.org/licenses/}.
|
||||
*/
|
||||
package org.jackhuang.hmcl.launch;
|
||||
|
||||
import java.io.IOException;
|
||||
|
||||
public class ProcessCreationException extends IOException {
|
||||
public ProcessCreationException() {
|
||||
}
|
||||
|
||||
public ProcessCreationException(String message) {
|
||||
super(message);
|
||||
}
|
||||
|
||||
public ProcessCreationException(String message, Throwable cause) {
|
||||
super(message, cause);
|
||||
}
|
||||
|
||||
public ProcessCreationException(Throwable cause) {
|
||||
super(cause);
|
||||
}
|
||||
}
|
||||
@@ -52,6 +52,7 @@ public interface ProcessListener {
|
||||
enum ExitType {
|
||||
JVM_ERROR,
|
||||
APPLICATION_ERROR,
|
||||
NORMAL
|
||||
NORMAL,
|
||||
INTERRUPTED
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user