JDK-6474073 : (process) Runtime.exec() creates zombies (sol)
  • Type: Bug
  • Component: core-libs
  • Sub-Component: java.lang
  • Affected Version: 6
  • Priority: P3
  • Status: Closed
  • Resolution: Fixed
  • OS: linux,solaris_2.5.1
  • CPU: x86
  • Submitted: 2006-09-22
  • Updated: 2011-03-07
  • Resolved: 2011-03-07
The Version table provides details related to the release that this issue/RFE will be addressed.

Unresolved : Release in which this issue/RFE will be addressed.
Resolved: Release in which this issue/RFE has been resolved.
Fixed : Release in which this issue/RFE has been fixed. The release containing this fix may be available for download as an Early Access Release or a General Availability Release.

To download the current JDK release, click here.
JDK 6 JDK 7
6u2Fixed 7 b03Fixed
Related Reports
Duplicate :  
Duplicate :  
Relates :  
Relates :  
Relates :  
Relates :  
Description
FULL PRODUCT VERSION :
java version "1.6.0-beta2"
Java(TM) SE Runtime Environment (build 1.6.0-beta2-b86)
Java HotSpot(TM) 64-Bit Server VM (build 1.6.0-beta2-b86, mixed mode)

A DESCRIPTION OF THE PROBLEM :
My application uses Runtime.exec() to execute external commands (shell scripts, system binaries).

If the external command does not exist an IOException is thrown and a defunct process (zombie) is left behind.

This issue does not appear in java version 1.5.0

STEPS TO FOLLOW TO REPRODUCE THE PROBLEM :
call Runtime.exec() with a non-existing file. e.g. 'Runtime.exec("no-such-file")'

EXPECTED VERSUS ACTUAL BEHAVIOR :
EXPECTED -
Checking the running processes does not show any defunct (zombie) process
ACTUAL -
After Runtime.exec runs, a defunct process is left behind, which is only removed when the JVM itself exits.

REPRODUCIBILITY :
This bug can be reproduced always.

---------- BEGIN SOURCE ----------
import java.io.*;
public class Zombie{
    private static void check() {
        try {
            Process p = Runtime.getRuntime().exec("ps -ef");
            BufferedReader br = new BufferedReader(new InputStreamReader(p.getInputStream()));
            String line;
            while (true) {
                line = br.readLine();
                if (line == null)
                    break;
                if (line.indexOf("defunct") > 0) {
                    System.out.println(line);
                }
            }
        } catch (IOException e) { }
    }
        
    
    public static void main(String[] args) {
        System.out.println("check before");
        check();
        try {
            Runtime.getRuntime().exec("no-such-file");
        } catch (IOException e) { }
        System.out.println("check after");
        check();
    }
}
---------- END SOURCE ----------

Comments
EVALUATION Apparently, zombies only show up in the ps output on solaris. On linux, some mechanism causes zombies to be removed from the output of ps.
22-09-2006

EVALUATION An excellent find by the submitter. Introduced in b81 by the fixes for 4052517: (process) Runtime.exec won't execute programs belonging to other groups on Unix 4811767: (process) Runtime.exec should throw IOException when workdir does not exist (Unix) 5033302: (process) Can't execute Solaris NFS programs with uid>64k on Linux-amd64 The following looks like the fix: --- /tmp/geta13483 2006-09-22 04:00:00.418839800 -0700 +++ UNIXProcess_md.c 2006-09-22 03:55:15.499011000 -0700 @@ -571,14 +571,15 @@ _exit(-1); } /* parent process */ close(fail[1]); fail[1] = -1; /* See: WhyCantJohnnyExec */ if (read(fail[0], &errnum, sizeof(errnum)) != 0) { + waitpid(resultPid, NULL, 0); throwIOException(env, errnum, "Exec failed"); goto Catch; } (*env)->SetIntField(env, stdin_fd, IO_fd_fdID, in [1]); (*env)->SetIntField(env, stdout_fd, IO_fd_fdID, out[0]); (*env)->SetIntField(env, stderr_fd, IO_fd_fdID, err[0]);
22-09-2006