diff --git a/core/src/main/java/hudson/Proc.java b/core/src/main/java/hudson/Proc.java index f3352a3478..e1400eda25 100644 --- a/core/src/main/java/hudson/Proc.java +++ b/core/src/main/java/hudson/Proc.java @@ -49,6 +49,11 @@ import java.util.logging.Logger; public abstract class Proc { private Proc() {} + /** + * Checks if the process is still alive. + */ + public abstract boolean isAlive() throws IOException, InterruptedException; + /** * Terminates the process. * @@ -176,6 +181,16 @@ public abstract class Proc { } } + @Override + public boolean isAlive() throws IOException, InterruptedException { + try { + proc.exitValue(); + return false; + } catch (IllegalThreadStateException e) { + return true; + } + } + @Override public void kill() throws InterruptedException, IOException { destroy(); @@ -254,6 +269,11 @@ public abstract class Proc { throw new IOException2("Failed to join the process",e); } } + + @Override + public boolean isAlive() throws IOException, InterruptedException { + return !process.isDone(); + } } private static final Logger LOGGER = Logger.getLogger(Proc.class.getName()); diff --git a/core/src/main/java/hudson/maven/MavenProcessFactory.java b/core/src/main/java/hudson/maven/MavenProcessFactory.java index f7024426a3..c86d018cd3 100644 --- a/core/src/main/java/hudson/maven/MavenProcessFactory.java +++ b/core/src/main/java/hudson/maven/MavenProcessFactory.java @@ -26,6 +26,7 @@ package hudson.maven; import hudson.FilePath; import hudson.Launcher; import hudson.Proc; +import hudson.AbortException; import static hudson.Util.fixNull; import hudson.maven.agent.Main; import hudson.model.BuildListener; @@ -60,6 +61,7 @@ import java.net.ServerSocket; import java.net.Socket; import java.net.URL; import java.net.URLConnection; +import java.net.SocketTimeoutException; import java.util.Arrays; import java.util.Map; import java.util.jar.JarFile; @@ -196,7 +198,19 @@ final class MavenProcessFactory implements ProcessCache.Factory { String[] cmds = cmdLine.toCommandArray(); final Proc proc = launcher.launch(cmds, envVars, out, workDir); - Connection con = acceptor.accept(); + Connection con; + try { + con = acceptor.accept(); + } catch (SocketTimeoutException e) { + // failed to connect. Is the process dead? + // if so, the error should have been provided by the launcher already. + // so abort gracefully without a stack trace. + if(!proc.isAlive()) { + listener.getLogger().println("Failed to launch Maven. Exit code = "+proc.join()); + throw new AbortException(); + } + throw e; + } return new Channel("Channel to Maven "+ Arrays.toString(cmds), Computer.threadPoolForRemoting, new BufferedInputStream(con.in), new BufferedOutputStream(con.out)) {