src/solaris/classes/java/lang/UNIXProcess.java.linux
Print this page
@@ -61,15 +61,65 @@
private /* final */ OutputStream stdin;
private /* final */ InputStream stdout;
private /* final */ InputStream stderr;
+ private static enum LaunchMechanism {
+ FORK(1),
+ VFORK(3);
+
+ private int value;
+ LaunchMechanism(int x) {value = x;}
+ };
+
+ /* default is VFORK on Linux */
+ private static final LaunchMechanism launchMechanism;
+ private static byte[] helperpath;
+
+ private static byte[] toCString(String s) {
+ if (s == null)
+ return null;
+ byte[] bytes = s.getBytes();
+ byte[] result = new byte[bytes.length + 1];
+ System.arraycopy(bytes, 0,
+ result, 0,
+ bytes.length);
+ result[result.length-1] = (byte)0;
+ return result;
+ }
+
+ static {
+ launchMechanism = AccessController.doPrivileged(
+ new PrivilegedAction<LaunchMechanism>()
+ {
+ public LaunchMechanism run() {
+ String javahome = System.getProperty("java.home");
+ String osArch = System.getProperty("os.arch");
+
+ helperpath = toCString(javahome + "/lib/" + osArch + "/jspawnhelper");
+ String s = System.getProperty(
+ "jdk.lang.Process.launchMechanism", "vfork");
+
+ try {
+ return LaunchMechanism.valueOf(s.toUpperCase());
+ } catch (IllegalArgumentException e) {
+ throw new Error(s + " is not a supported " +
+ "process launch mechanism on this platform.");
+ }
+ }
+ });
+ }
+
/* this is for the reaping thread */
private native int waitForProcessExit(int pid);
/**
- * Create a process using fork(2) and exec(2).
+ * Create a process. Depending on the mode flag, this is done by
+ * one of the following mechanisms.
+ * - fork(2) and exec(2)
+ * - clone(2) and exec(2)
+ * - vfork(2) and exec(2)
*
* @param fds an array of three file descriptors.
* Indexes 0, 1, and 2 correspond to standard input,
* standard output and standard error, respectively. On
* input, a value of -1 means to create a pipe to connect
@@ -78,11 +128,12 @@
* pipe which has been created. An element of this array
* is -1 on input if and only if it is <em>not</em> -1 on
* output.
* @return the pid of the subprocess
*/
- private native int forkAndExec(byte[] prog,
+ private native int forkAndExec(int mode, byte[] helperpath,
+ byte[] prog,
byte[] argBlock, int argc,
byte[] envBlock, int envc,
byte[] dir,
int[] fds,
boolean redirectErrorStream)
@@ -130,11 +181,13 @@
final byte[] dir,
final int[] fds,
final boolean redirectErrorStream)
throws IOException {
- pid = forkAndExec(prog,
+ pid = forkAndExec(launchMechanism.value,
+ helperpath,
+ prog,
argBlock, argc,
envBlock, envc,
dir,
fds,
redirectErrorStream);
@@ -234,15 +287,14 @@
try { stdin.close(); } catch (IOException ignored) {}
try { stdout.close(); } catch (IOException ignored) {}
try { stderr.close(); } catch (IOException ignored) {}
}
- /* This routine initializes JNI field offsets for the class */
- private static native void initIDs();
+ private static native void init();
static {
- initIDs();
+ init();
}
/**
* A buffered input stream for a subprocess pipe file descriptor
* that allows the underlying file descriptor to be reclaimed when