summaryrefslogtreecommitdiff
path: root/libjava/classpath/vm/reference/java/lang/VMProcess.java
diff options
context:
space:
mode:
authorAndrew Haley <aph@redhat.com>2016-09-30 16:24:48 +0000
committerAndrew Haley <aph@gcc.gnu.org>2016-09-30 16:24:48 +0000
commit07b78716af6a9d7c9fd1e94d9baf94a52c873947 (patch)
tree3f22b3241c513ad168c8353805614ae1249410f4 /libjava/classpath/vm/reference/java/lang/VMProcess.java
parenteae993948bae8b788c53772bcb9217c063716f93 (diff)
downloadgcc-07b78716af6a9d7c9fd1e94d9baf94a52c873947.tar.gz
Makefile.def: Remove libjava.
2016-09-30 Andrew Haley <aph@redhat.com> * Makefile.def: Remove libjava. * Makefile.tpl: Likewise. * Makefile.in: Regenerate. * configure.ac: Likewise. * configure: Likewise. * gcc/java: Remove. * libjava: Likewise. From-SVN: r240662
Diffstat (limited to 'libjava/classpath/vm/reference/java/lang/VMProcess.java')
-rw-r--r--libjava/classpath/vm/reference/java/lang/VMProcess.java402
1 files changed, 0 insertions, 402 deletions
diff --git a/libjava/classpath/vm/reference/java/lang/VMProcess.java b/libjava/classpath/vm/reference/java/lang/VMProcess.java
deleted file mode 100644
index c41d7cc0c08..00000000000
--- a/libjava/classpath/vm/reference/java/lang/VMProcess.java
+++ /dev/null
@@ -1,402 +0,0 @@
-/* java.lang.VMProcess -- VM implementation of java.lang.Process
- Copyright (C) 2004, 2005 Free Software Foundation, Inc.
-
-This file is part of GNU Classpath.
-
-GNU Classpath 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 2, or (at your option)
-any later version.
-
-GNU Classpath 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 GNU Classpath; see the file COPYING. If not, write to the
-Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
-02110-1301 USA.
-
-Linking this library statically or dynamically with other modules is
-making a combined work based on this library. Thus, the terms and
-conditions of the GNU General Public License cover the whole
-combination.
-
-As a special exception, the copyright holders of this library give you
-permission to link this library with independent modules to produce an
-executable, regardless of the license terms of these independent
-modules, and to copy and distribute the resulting executable under
-terms of your choice, provided that you also meet, for each linked
-independent module, the terms and conditions of the license of that
-module. An independent module is a module which is not derived from
-or based on this library. If you modify this library, you may extend
-this exception to your version of the library, but you are not
-obligated to do so. If you do not wish to do so, delete this
-exception statement from your version. */
-
-package java.lang;
-
-import java.io.File;
-import java.io.IOException;
-import java.io.InputStream;
-import java.io.OutputStream;
-import java.util.HashMap;
-import java.util.Iterator;
-import java.util.LinkedList;
-import java.util.List;
-import java.util.Map;
-
-/**
- * Represents one external process. Each instance of this class is in
- * one of three states: INITIAL, RUNNING, or TERMINATED. The instance
- * is {@link Object#notifyAll notifyAll()}'d each time the state changes.
- * The state of all instances is managed by a single dedicated thread
- * which does the actual fork()/exec() and wait() system calls. User
- * threads {@link Object#wait()} on the instance when creating the
- * process or waiting for it to terminate.
- *
- * <p>
- * See
- * <a href="http://gcc.gnu.org/bugzilla/show_bug.cgi?id=11801">GCC bug
- * #11801</a> for the motivation behind the design of this class.
- *
- * @author Archie Cobbs
- * @see Process
- * @see Runtime#exec(String)
- */
-final class VMProcess extends Process
-{
-
- // Possible states for a VMProcess
- private static final int INITIAL = 0;
- private static final int RUNNING = 1;
- private static final int TERMINATED = 2;
-
- // Dedicated thread that does all the fork()'ing and wait()'ing.
- static Thread processThread;
-
- // New processes waiting to be spawned by processThread.
- static final LinkedList workList = new LinkedList();
-
- // Return values set by nativeReap() when a child is reaped.
- // These are only accessed by processThread so no locking required.
- static long reapedPid;
- static int reapedExitValue;
-
- // Information about this process
- int state; // current state of process
- final String[] cmd; // copied from Runtime.exec()
- final String[] env; // copied from Runtime.exec()
- final File dir; // copied from Runtime.exec()
- Throwable exception; // if process failed to start
- long pid; // process id
- OutputStream stdin; // process input stream
- InputStream stdout; // process output stream
- InputStream stderr; // process error stream
- int exitValue; // process exit value
- boolean redirect; // redirect stderr -> stdout
-
- //
- // Dedicated thread that does all the fork()'ing and wait()'ing
- // for external processes. This is needed because some systems like
- // Linux use a process-per-thread model, which means the same thread
- // that did the fork()/exec() must also do the wait().
- //
- private static class ProcessThread extends Thread
- {
-
- // Max time (in ms) we'll delay before trying to reap another child.
- private static final int MAX_REAP_DELAY = 1000;
-
- // Processes created but not yet terminated; maps Long(pid) -> VMProcess
- // Only used in run() and spawn() method from this Thread, so no locking.
- private final HashMap activeMap = new HashMap();
-
- // We have an explicit constructor, because the default
- // constructor will be private, which means the compiler will have
- // to generate a second package-private constructor, which is
- // bogus.
- ProcessThread ()
- {
- }
-
- public void run()
- {
- final LinkedList workList = VMProcess.workList;
- while (true)
- {
-
- // Get the next process to spawn (if any) and spawn it. Spawn
- // at most one at a time before checking for reapable children.
- VMProcess process = null;
- synchronized (workList)
- {
- if (!workList.isEmpty())
- process = (VMProcess)workList.removeFirst();
- }
-
- if (process != null)
- spawn(process);
-
-
- // Check for termination of active child processes
- while (!activeMap.isEmpty() && VMProcess.nativeReap())
- {
- long pid = VMProcess.reapedPid;
- int exitValue = VMProcess.reapedExitValue;
- process = (VMProcess)activeMap.remove(new Long(pid));
- if (process != null)
- {
- synchronized (process)
- {
- process.exitValue = exitValue;
- process.state = TERMINATED;
- process.notify();
- }
- }
- else
- System.err.println("VMProcess WARNING reaped unknown process: "
- + pid);
- }
-
-
- // If there are more new processes to create, go do that now.
- // If there is nothing left to do, exit this thread. Otherwise,
- // sleep a little while, and then check again for reapable children.
- // We will get woken up immediately if there are new processes to
- // spawn, but not if there are new children to reap. So we only
- // sleep a short time, in effect polling while processes are active.
- synchronized (workList)
- {
- if (!workList.isEmpty())
- continue;
- if (activeMap.isEmpty())
- {
- processThread = null;
- break;
- }
-
- try
- {
- workList.wait(MAX_REAP_DELAY);
- }
- catch (InterruptedException e)
- {
- /* ignore */
- }
- }
- }
- }
-
- // Spawn a process
- private void spawn(VMProcess process)
- {
-
- // Spawn the process and put it in our active map indexed by pid.
- // If the spawn operation fails, store the exception with the process.
- // In either case, wake up thread that created the process.
- synchronized (process)
- {
- try
- {
- process.nativeSpawn(process.cmd, process.env, process.dir,
- process.redirect);
- process.state = RUNNING;
- activeMap.put(new Long(process.pid), process);
- }
- catch (ThreadDeath death)
- {
- throw death;
- }
- catch (Throwable t)
- {
- process.state = TERMINATED;
- process.exception = t;
- }
- process.notify();
- }
- }
- }
-
- // Constructor
- private VMProcess(String[] cmd, String[] env, File dir, boolean redirect)
- throws IOException
- {
-
- // Initialize this process
- this.state = INITIAL;
- this.cmd = cmd;
- this.env = env;
- this.dir = dir;
- this.redirect = redirect;
-
- // Add process to the new process work list and wakeup processThread
- synchronized (workList)
- {
- workList.add(this);
- if (processThread == null)
- {
- processThread = new ProcessThread();
- processThread.setDaemon(true);
- processThread.start();
- }
- else
- {
- workList.notify();
- }
- }
-
- // Wait for processThread to spawn this process and update its state
- synchronized (this)
- {
- while (state == INITIAL)
- {
- try
- {
- wait();
- }
- catch (InterruptedException e)
- {
- /* ignore */
- }
- }
- }
-
- // If spawning failed, rethrow the exception in this thread
- if (exception != null)
- {
- exception.fillInStackTrace();
- if (exception instanceof IOException)
- throw (IOException)exception;
-
- if (exception instanceof Error)
- throw (Error)exception;
-
- if (exception instanceof RuntimeException)
- throw (RuntimeException)exception;
-
- throw new RuntimeException(exception);
- }
- }
-
- // Invoked by native code (from nativeSpawn()) to record process info.
- private void setProcessInfo(OutputStream stdin,
- InputStream stdout, InputStream stderr, long pid)
- {
- this.stdin = stdin;
- this.stdout = stdout;
- if (stderr == null)
- this.stderr = new InputStream()
- {
- public int read() throws IOException
- {
- return -1;
- }
- };
- else
- this.stderr = stderr;
- this.pid = pid;
- }
-
- /**
- * Entry point from Runtime.exec().
- */
- static Process exec(String[] cmd, String[] env, File dir) throws IOException
- {
- return new VMProcess(cmd, env, dir, false);
- }
-
- static Process exec(List cmd, Map env,
- File dir, boolean redirect) throws IOException
- {
- String[] acmd = (String[]) cmd.toArray(new String[cmd.size()]);
- String[] aenv = new String[env.size()];
-
- int i = 0;
- Iterator iter = env.entrySet().iterator();
- while (iter.hasNext())
- {
- Map.Entry entry = (Map.Entry) iter.next();
- aenv[i++] = entry.getKey() + "=" + entry.getValue();
- }
-
- return new VMProcess(acmd, aenv, dir, redirect);
- }
-
- public OutputStream getOutputStream()
- {
- return stdin;
- }
-
- public InputStream getInputStream()
- {
- return stdout;
- }
-
- public InputStream getErrorStream()
- {
- return stderr;
- }
-
- public synchronized int waitFor() throws InterruptedException
- {
- while (state != TERMINATED)
- wait();
- return exitValue;
- }
-
- public synchronized int exitValue()
- {
- if (state != TERMINATED)
- throw new IllegalThreadStateException();
- return exitValue;
- }
-
- public synchronized void destroy()
- {
- if (state == TERMINATED)
- return;
-
- nativeKill(pid);
-
- while (state != TERMINATED)
- {
- try
- {
- wait();
- }
- catch (InterruptedException e)
- {
- /* ignore */
- }
- }
- }
-
- /**
- * Does the fork()/exec() thing to create the O/S process.
- * Must invoke setProcessInfo() before returning successfully.
- * This method is only invoked by processThread.
- *
- * @throws IOException if the O/S process could not be created.
- */
- native void nativeSpawn(String[] cmd, String[] env, File dir,
- boolean redirect)
- throws IOException;
-
- /**
- * Test for a reapable child process, and reap if so. Does not block.
- * If a child was reaped, this method must set reapedPid and
- * reapedExitValue appropriately before returning.
- * This method is only invoked by processThread.
- *
- * @return true if a child was reaped, otherwise false
- */
- // This is not private as it is called from an inner class.
- static native boolean nativeReap();
-
- /**
- * Kill a process. This sends it a fatal signal but does not reap it.
- */
- private static native void nativeKill(long pid);
-}