mirror of
https://github.com/jenkinsci/jenkins.git
synced 2026-11-10 02:26:18 +00:00
[JENKINS-23271] - Process statuses of Remote process join() operations directly inside methods (#2653)
* [JENKINS-23271] - Process statuses of Remote process join() operations directly inside methods * [JENKINS-23271] - Also prevent the issue when the kill() command is the last call in the usage sequence
This commit is contained in:
1 parent
9fe07a7596
commit
29893354a5
2 files changed
+68
-15
No files matched your search
@@ -49,6 +49,8 @@ import java.util.concurrent.Future;
|
||||
import java.util.concurrent.TimeUnit;
|
||||
import java.util.logging.Level;
|
||||
import java.util.logging.Logger;
|
||||
import org.kohsuke.accmod.Restricted;
|
||||
import org.kohsuke.accmod.restrictions.NoExternalUse;
|
||||
|
||||
/**
|
||||
* External process wrapper.
|
||||
@@ -431,7 +433,7 @@ public abstract class Proc {
|
||||
* @deprecated as of 1.399. Replaced by {@link Launcher.RemoteLauncher.ProcImpl}
|
||||
*/
|
||||
@Deprecated
|
||||
public static final class RemoteProc extends Proc {
|
||||
public static final class RemoteProc extends Proc implements ProcWithJenkins23271Patch {
|
||||
private final Future<Integer> process;
|
||||
|
||||
public RemoteProc(Future<Integer> process) {
|
||||
@@ -440,7 +442,14 @@ public abstract class Proc {
|
||||
|
||||
@Override
|
||||
public void kill() throws IOException, InterruptedException {
|
||||
process.cancel(true);
|
||||
try {
|
||||
process.cancel(true);
|
||||
} finally {
|
||||
if (this.isAlive()) { // Should never happen but this forces Proc to not be removed and early GC by escape analysis
|
||||
// TODO: Report exceptions if they happen?
|
||||
LOGGER.log(Level.WARNING, "Process {0} has not really finished after the kill() method execution", this);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
@@ -448,8 +457,8 @@ public abstract class Proc {
|
||||
try {
|
||||
return process.get();
|
||||
} catch (InterruptedException e) {
|
||||
// aborting. kill the process
|
||||
process.cancel(true);
|
||||
LOGGER.log(Level.FINE, String.format("Join operation has been interrupted for the process %s. Killing the process", this), e);
|
||||
kill();
|
||||
throw e;
|
||||
} catch (ExecutionException e) {
|
||||
if(e.getCause() instanceof IOException)
|
||||
@@ -457,6 +466,10 @@ public abstract class Proc {
|
||||
throw new IOException("Failed to join the process",e);
|
||||
} catch (CancellationException x) {
|
||||
return -1;
|
||||
} finally {
|
||||
if (this.isAlive()) { // Should never happen but this forces Proc to not be removed and early GC by escape analysis
|
||||
LOGGER.log(Level.WARNING, "Process {0} has not really finished after the join() method completion", this);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -486,4 +499,15 @@ public abstract class Proc {
|
||||
* Debug switch to have the thread display the process it's waiting for.
|
||||
*/
|
||||
public static boolean SHOW_PID = false;
|
||||
|
||||
/**
|
||||
* An instance of {@link Proc}, which has an internal workaround for JENKINS-23271.
|
||||
* It presumes that the instance of the object is guaranteed to be used after the {@link Proc#join()} call.
|
||||
* See <a href="https://issues.jenkins-ci.org/browse/JENKINS-23271">JENKINS-23271></a>
|
||||
* @author Oleg Nenashev
|
||||
*/
|
||||
@Restricted(NoExternalUse.class)
|
||||
public interface ProcWithJenkins23271Patch {
|
||||
// Empty marker interface
|
||||
}
|
||||
}
|
||||
Reference in new issue
Block a user