jaroslav@1258: /*
jaroslav@1258: * Copyright (c) 1994, 2011, Oracle and/or its affiliates. All rights reserved.
jaroslav@1258: * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
jaroslav@1258: *
jaroslav@1258: * This code is free software; you can redistribute it and/or modify it
jaroslav@1258: * under the terms of the GNU General Public License version 2 only, as
jaroslav@1258: * published by the Free Software Foundation. Oracle designates this
jaroslav@1258: * particular file as subject to the "Classpath" exception as provided
jaroslav@1258: * by Oracle in the LICENSE file that accompanied this code.
jaroslav@1258: *
jaroslav@1258: * This code is distributed in the hope that it will be useful, but WITHOUT
jaroslav@1258: * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
jaroslav@1258: * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
jaroslav@1258: * version 2 for more details (a copy is included in the LICENSE file that
jaroslav@1258: * accompanied this code).
jaroslav@1258: *
jaroslav@1258: * You should have received a copy of the GNU General Public License version
jaroslav@1258: * 2 along with this work; if not, write to the Free Software Foundation,
jaroslav@1258: * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
jaroslav@1258: *
jaroslav@1258: * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
jaroslav@1258: * or visit www.oracle.com if you need additional information or have any
jaroslav@1258: * questions.
jaroslav@1258: */
jaroslav@1258: package java.lang;
jaroslav@1258:
jaroslav@1258: import java.io.*;
jaroslav@1258: import java.util.Properties;
jaroslav@1258: import java.util.PropertyPermission;
jaroslav@1258: import java.util.StringTokenizer;
jaroslav@1258: import java.security.AccessController;
jaroslav@1258: import java.security.PrivilegedAction;
jaroslav@1258: import java.security.AllPermission;
jaroslav@1258: import java.nio.channels.Channel;
jaroslav@1258: import java.nio.channels.spi.SelectorProvider;
jaroslav@1258: import sun.nio.ch.Interruptible;
jaroslav@1258: import sun.reflect.Reflection;
jaroslav@1258: import sun.security.util.SecurityConstants;
jaroslav@1258: import sun.reflect.annotation.AnnotationType;
jaroslav@1258:
jaroslav@1258: /**
jaroslav@1258: * The System class contains several useful class fields
jaroslav@1258: * and methods. It cannot be instantiated.
jaroslav@1258: *
jaroslav@1258: *
Among the facilities provided by the System class
jaroslav@1258: * are standard input, standard output, and error output streams;
jaroslav@1258: * access to externally defined properties and environment
jaroslav@1258: * variables; a means of loading files and libraries; and a utility
jaroslav@1258: * method for quickly copying a portion of an array.
jaroslav@1258: *
jaroslav@1258: * @author unascribed
jaroslav@1258: * @since JDK1.0
jaroslav@1258: */
jaroslav@1258: public final class System {
jaroslav@1258:
jaroslav@1258: /* register the natives via the static initializer.
jaroslav@1258: *
jaroslav@1258: * VM will invoke the initializeSystemClass method to complete
jaroslav@1258: * the initialization for this class separated from clinit.
jaroslav@1258: * Note that to use properties set by the VM, see the constraints
jaroslav@1258: * described in the initializeSystemClass method.
jaroslav@1258: */
jaroslav@1258: private static native void registerNatives();
jaroslav@1258: static {
jaroslav@1258: registerNatives();
jaroslav@1258: }
jaroslav@1258:
jaroslav@1258: /** Don't let anyone instantiate this class */
jaroslav@1258: private System() {
jaroslav@1258: }
jaroslav@1258:
jaroslav@1258: /**
jaroslav@1258: * The "standard" input stream. This stream is already
jaroslav@1258: * open and ready to supply input data. Typically this stream
jaroslav@1258: * corresponds to keyboard input or another input source specified by
jaroslav@1258: * the host environment or user.
jaroslav@1258: */
jaroslav@1258: public final static InputStream in = null;
jaroslav@1258:
jaroslav@1258: /**
jaroslav@1258: * The "standard" output stream. This stream is already
jaroslav@1258: * open and ready to accept output data. Typically this stream
jaroslav@1258: * corresponds to display output or another output destination
jaroslav@1258: * specified by the host environment or user.
jaroslav@1258: *
jaroslav@1258: * For simple stand-alone Java applications, a typical way to write
jaroslav@1258: * a line of output data is:
jaroslav@1258: *
jaroslav@1258: * See the println methods in class PrintStream.
jaroslav@1258: *
jaroslav@1258: * @see java.io.PrintStream#println()
jaroslav@1258: * @see java.io.PrintStream#println(boolean)
jaroslav@1258: * @see java.io.PrintStream#println(char)
jaroslav@1258: * @see java.io.PrintStream#println(char[])
jaroslav@1258: * @see java.io.PrintStream#println(double)
jaroslav@1258: * @see java.io.PrintStream#println(float)
jaroslav@1258: * @see java.io.PrintStream#println(int)
jaroslav@1258: * @see java.io.PrintStream#println(long)
jaroslav@1258: * @see java.io.PrintStream#println(java.lang.Object)
jaroslav@1258: * @see java.io.PrintStream#println(java.lang.String)
jaroslav@1258: */
jaroslav@1258: public final static PrintStream out = null;
jaroslav@1258:
jaroslav@1258: /**
jaroslav@1258: * The "standard" error output stream. This stream is already
jaroslav@1258: * open and ready to accept output data.
jaroslav@1258: *
jaroslav@1258: * Typically this stream corresponds to display output or another
jaroslav@1258: * output destination specified by the host environment or user. By
jaroslav@1258: * convention, this output stream is used to display error messages
jaroslav@1258: * or other information that should come to the immediate attention
jaroslav@1258: * of a user even if the principal output stream, the value of the
jaroslav@1258: * variable out, has been redirected to a file or other
jaroslav@1258: * destination that is typically not continuously monitored.
jaroslav@1258: */
jaroslav@1258: public final static PrintStream err = null;
jaroslav@1258:
jaroslav@1258: /* The security manager for the system.
jaroslav@1258: */
jaroslav@1258: private static volatile SecurityManager security = null;
jaroslav@1258:
jaroslav@1258: /**
jaroslav@1258: * Reassigns the "standard" input stream.
jaroslav@1258: *
jaroslav@1258: *
First, if there is a security manager, its checkPermission
jaroslav@1258: * method is called with a RuntimePermission("setIO") permission
jaroslav@1258: * to see if it's ok to reassign the "standard" input stream.
jaroslav@1258: *
jaroslav@1258: *
jaroslav@1258: * @param in the new standard input stream.
jaroslav@1258: *
jaroslav@1258: * @throws SecurityException
jaroslav@1258: * if a security manager exists and its
jaroslav@1258: * checkPermission method doesn't allow
jaroslav@1258: * reassigning of the standard input stream.
jaroslav@1258: *
jaroslav@1258: * @see SecurityManager#checkPermission
jaroslav@1258: * @see java.lang.RuntimePermission
jaroslav@1258: *
jaroslav@1258: * @since JDK1.1
jaroslav@1258: */
jaroslav@1258: public static void setIn(InputStream in) {
jaroslav@1258: checkIO();
jaroslav@1258: setIn0(in);
jaroslav@1258: }
jaroslav@1258:
jaroslav@1258: /**
jaroslav@1258: * Reassigns the "standard" output stream.
jaroslav@1258: *
jaroslav@1258: *
First, if there is a security manager, its checkPermission
jaroslav@1258: * method is called with a RuntimePermission("setIO") permission
jaroslav@1258: * to see if it's ok to reassign the "standard" output stream.
jaroslav@1258: *
jaroslav@1258: * @param out the new standard output stream
jaroslav@1258: *
jaroslav@1258: * @throws SecurityException
jaroslav@1258: * if a security manager exists and its
jaroslav@1258: * checkPermission method doesn't allow
jaroslav@1258: * reassigning of the standard output stream.
jaroslav@1258: *
jaroslav@1258: * @see SecurityManager#checkPermission
jaroslav@1258: * @see java.lang.RuntimePermission
jaroslav@1258: *
jaroslav@1258: * @since JDK1.1
jaroslav@1258: */
jaroslav@1258: public static void setOut(PrintStream out) {
jaroslav@1258: checkIO();
jaroslav@1258: setOut0(out);
jaroslav@1258: }
jaroslav@1258:
jaroslav@1258: /**
jaroslav@1258: * Reassigns the "standard" error output stream.
jaroslav@1258: *
jaroslav@1258: *
First, if there is a security manager, its checkPermission
jaroslav@1258: * method is called with a RuntimePermission("setIO") permission
jaroslav@1258: * to see if it's ok to reassign the "standard" error output stream.
jaroslav@1258: *
jaroslav@1258: * @param err the new standard error output stream.
jaroslav@1258: *
jaroslav@1258: * @throws SecurityException
jaroslav@1258: * if a security manager exists and its
jaroslav@1258: * checkPermission method doesn't allow
jaroslav@1258: * reassigning of the standard error output stream.
jaroslav@1258: *
jaroslav@1258: * @see SecurityManager#checkPermission
jaroslav@1258: * @see java.lang.RuntimePermission
jaroslav@1258: *
jaroslav@1258: * @since JDK1.1
jaroslav@1258: */
jaroslav@1258: public static void setErr(PrintStream err) {
jaroslav@1258: checkIO();
jaroslav@1258: setErr0(err);
jaroslav@1258: }
jaroslav@1258:
jaroslav@1258: private static volatile Console cons = null;
jaroslav@1258: /**
jaroslav@1258: * Returns the unique {@link java.io.Console Console} object associated
jaroslav@1258: * with the current Java virtual machine, if any.
jaroslav@1258: *
jaroslav@1258: * @return The system console, if any, otherwise null.
jaroslav@1258: *
jaroslav@1258: * @since 1.6
jaroslav@1258: */
jaroslav@1258: public static Console console() {
jaroslav@1258: if (cons == null) {
jaroslav@1258: synchronized (System.class) {
jaroslav@1258: cons = sun.misc.SharedSecrets.getJavaIOAccess().console();
jaroslav@1258: }
jaroslav@1258: }
jaroslav@1258: return cons;
jaroslav@1258: }
jaroslav@1258:
jaroslav@1258: /**
jaroslav@1258: * Returns the channel inherited from the entity that created this
jaroslav@1258: * Java virtual machine.
jaroslav@1258: *
jaroslav@1258: *
This method returns the channel obtained by invoking the
jaroslav@1258: * {@link java.nio.channels.spi.SelectorProvider#inheritedChannel
jaroslav@1258: * inheritedChannel} method of the system-wide default
jaroslav@1258: * {@link java.nio.channels.spi.SelectorProvider} object.
jaroslav@1258: *
jaroslav@1258: *
In addition to the network-oriented channels described in
jaroslav@1258: * {@link java.nio.channels.spi.SelectorProvider#inheritedChannel
jaroslav@1258: * inheritedChannel}, this method may return other kinds of
jaroslav@1258: * channels in the future.
jaroslav@1258: *
jaroslav@1258: * @return The inherited channel, if any, otherwise null.
jaroslav@1258: *
jaroslav@1258: * @throws IOException
jaroslav@1258: * If an I/O error occurs
jaroslav@1258: *
jaroslav@1258: * @throws SecurityException
jaroslav@1258: * If a security manager is present and it does not
jaroslav@1258: * permit access to the channel.
jaroslav@1258: *
jaroslav@1258: * @since 1.5
jaroslav@1258: */
jaroslav@1258: public static Channel inheritedChannel() throws IOException {
jaroslav@1258: return SelectorProvider.provider().inheritedChannel();
jaroslav@1258: }
jaroslav@1258:
jaroslav@1258: private static void checkIO() {
jaroslav@1258: SecurityManager sm = getSecurityManager();
jaroslav@1258: if (sm != null) {
jaroslav@1258: sm.checkPermission(new RuntimePermission("setIO"));
jaroslav@1258: }
jaroslav@1258: }
jaroslav@1258:
jaroslav@1258: private static native void setIn0(InputStream in);
jaroslav@1258: private static native void setOut0(PrintStream out);
jaroslav@1258: private static native void setErr0(PrintStream err);
jaroslav@1258:
jaroslav@1258: /**
jaroslav@1258: * Sets the System security.
jaroslav@1258: *
jaroslav@1258: *
If there is a security manager already installed, this method first
jaroslav@1258: * calls the security manager's checkPermission method
jaroslav@1258: * with a RuntimePermission("setSecurityManager")
jaroslav@1258: * permission to ensure it's ok to replace the existing
jaroslav@1258: * security manager.
jaroslav@1258: * This may result in throwing a SecurityException.
jaroslav@1258: *
jaroslav@1258: *
Otherwise, the argument is established as the current
jaroslav@1258: * security manager. If the argument is null and no
jaroslav@1258: * security manager has been established, then no action is taken and
jaroslav@1258: * the method simply returns.
jaroslav@1258: *
jaroslav@1258: * @param s the security manager.
jaroslav@1258: * @exception SecurityException if the security manager has already
jaroslav@1258: * been set and its checkPermission method
jaroslav@1258: * doesn't allow it to be replaced.
jaroslav@1258: * @see #getSecurityManager
jaroslav@1258: * @see SecurityManager#checkPermission
jaroslav@1258: * @see java.lang.RuntimePermission
jaroslav@1258: */
jaroslav@1258: public static
jaroslav@1258: void setSecurityManager(final SecurityManager s) {
jaroslav@1258: try {
jaroslav@1258: s.checkPackageAccess("java.lang");
jaroslav@1258: } catch (Exception e) {
jaroslav@1258: // no-op
jaroslav@1258: }
jaroslav@1258: setSecurityManager0(s);
jaroslav@1258: }
jaroslav@1258:
jaroslav@1258: private static synchronized
jaroslav@1258: void setSecurityManager0(final SecurityManager s) {
jaroslav@1258: SecurityManager sm = getSecurityManager();
jaroslav@1258: if (sm != null) {
jaroslav@1258: // ask the currently installed security manager if we
jaroslav@1258: // can replace it.
jaroslav@1258: sm.checkPermission(new RuntimePermission
jaroslav@1258: ("setSecurityManager"));
jaroslav@1258: }
jaroslav@1258:
jaroslav@1258: if ((s != null) && (s.getClass().getClassLoader() != null)) {
jaroslav@1258: // New security manager class is not on bootstrap classpath.
jaroslav@1258: // Cause policy to get initialized before we install the new
jaroslav@1258: // security manager, in order to prevent infinite loops when
jaroslav@1258: // trying to initialize the policy (which usually involves
jaroslav@1258: // accessing some security and/or system properties, which in turn
jaroslav@1258: // calls the installed security manager's checkPermission method
jaroslav@1258: // which will loop infinitely if there is a non-system class
jaroslav@1258: // (in this case: the new security manager class) on the stack).
jaroslav@1258: AccessController.doPrivileged(new PrivilegedAction