feat(jdk8): move files to new folder to avoid resources compiled.

This commit is contained in:
2025-09-07 15:25:52 +08:00
parent 3f0047bf6f
commit 8c35cfb1c0
17415 changed files with 217 additions and 213 deletions

View File

@@ -0,0 +1,579 @@
/*
* Copyright (c) 1997, 2013, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Oracle designates this
* particular file as subject to the "Classpath" exception as provided
* by Oracle in the LICENSE file that accompanied this code.
*
* This code 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
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*/
package java.rmi.activation;
import java.rmi.MarshalledObject;
import java.rmi.NoSuchObjectException;
import java.rmi.Remote;
import java.rmi.RemoteException;
import java.rmi.activation.UnknownGroupException;
import java.rmi.activation.UnknownObjectException;
import java.rmi.server.RMIClientSocketFactory;
import java.rmi.server.RMIServerSocketFactory;
import java.rmi.server.RemoteServer;
import sun.rmi.server.ActivatableServerRef;
/**
* The <code>Activatable</code> class provides support for remote
* objects that require persistent access over time and that
* can be activated by the system.
*
* <p>For the constructors and static <code>exportObject</code> methods,
* the stub for a remote object being exported is obtained as described in
* {@link java.rmi.server.UnicastRemoteObject}.
*
* <p>An attempt to serialize explicitly an instance of this class will
* fail.
*
* @author Ann Wollrath
* @since 1.2
* @serial exclude
*/
public abstract class Activatable extends RemoteServer {
private ActivationID id;
/** indicate compatibility with the Java 2 SDK v1.2 version of class */
private static final long serialVersionUID = -3120617863591563455L;
/**
* Constructs an activatable remote object by registering
* an activation descriptor (with the specified location, data, and
* restart mode) for this object, and exporting the object with the
* specified port.
*
* <p><strong>Note:</strong> Using the <code>Activatable</code>
* constructors that both register and export an activatable remote
* object is strongly discouraged because the actions of registering
* and exporting the remote object are <i>not</i> guaranteed to be
* atomic. Instead, an application should register an activation
* descriptor and export a remote object separately, so that exceptions
* can be handled properly.
*
* <p>This method invokes the {@link
* #exportObject(Remote,String,MarshalledObject,boolean,int)
* exportObject} method with this object, and the specified location,
* data, restart mode, and port. Subsequent calls to {@link #getID}
* will return the activation identifier returned from the call to
* <code>exportObject</code>.
*
* @param location the location for classes for this object
* @param data the object's initialization data
* @param port the port on which the object is exported (an anonymous
* port is used if port=0)
* @param restart if true, the object is restarted (reactivated) when
* either the activator is restarted or the object's activation group
* is restarted after an unexpected crash; if false, the object is only
* activated on demand. Specifying <code>restart</code> to be
* <code>true</code> does not force an initial immediate activation of
* a newly registered object; initial activation is lazy.
* @exception ActivationException if object registration fails.
* @exception RemoteException if either of the following fails:
* a) registering the object with the activation system or b) exporting
* the object to the RMI runtime.
* @exception UnsupportedOperationException if and only if activation is
* not supported by this implementation.
* @since 1.2
**/
protected Activatable(String location,
MarshalledObject<?> data,
boolean restart,
int port)
throws ActivationException, RemoteException
{
super();
id = exportObject(this, location, data, restart, port);
}
/**
* Constructs an activatable remote object by registering
* an activation descriptor (with the specified location, data, and
* restart mode) for this object, and exporting the object with the
* specified port, and specified client and server socket factories.
*
* <p><strong>Note:</strong> Using the <code>Activatable</code>
* constructors that both register and export an activatable remote
* object is strongly discouraged because the actions of registering
* and exporting the remote object are <i>not</i> guaranteed to be
* atomic. Instead, an application should register an activation
* descriptor and export a remote object separately, so that exceptions
* can be handled properly.
*
* <p>This method invokes the {@link
* #exportObject(Remote,String,MarshalledObject,boolean,int,RMIClientSocketFactory,RMIServerSocketFactory)
* exportObject} method with this object, and the specified location,
* data, restart mode, port, and client and server socket factories.
* Subsequent calls to {@link #getID} will return the activation
* identifier returned from the call to <code>exportObject</code>.
*
* @param location the location for classes for this object
* @param data the object's initialization data
* @param restart if true, the object is restarted (reactivated) when
* either the activator is restarted or the object's activation group
* is restarted after an unexpected crash; if false, the object is only
* activated on demand. Specifying <code>restart</code> to be
* <code>true</code> does not force an initial immediate activation of
* a newly registered object; initial activation is lazy.
* @param port the port on which the object is exported (an anonymous
* port is used if port=0)
* @param csf the client-side socket factory for making calls to the
* remote object
* @param ssf the server-side socket factory for receiving remote calls
* @exception ActivationException if object registration fails.
* @exception RemoteException if either of the following fails:
* a) registering the object with the activation system or b) exporting
* the object to the RMI runtime.
* @exception UnsupportedOperationException if and only if activation is
* not supported by this implementation.
* @since 1.2
**/
protected Activatable(String location,
MarshalledObject<?> data,
boolean restart,
int port,
RMIClientSocketFactory csf,
RMIServerSocketFactory ssf)
throws ActivationException, RemoteException
{
super();
id = exportObject(this, location, data, restart, port, csf, ssf);
}
/**
* Constructor used to activate/export the object on a specified
* port. An "activatable" remote object must have a constructor that
* takes two arguments: <ul>
* <li>the object's activation identifier (<code>ActivationID</code>), and
* <li>the object's initialization data (a <code>MarshalledObject</code>).
* </ul><p>
*
* A concrete subclass of this class must call this constructor when it is
* <i>activated</i> via the two parameter constructor described above. As
* a side-effect of construction, the remote object is "exported"
* to the RMI runtime (on the specified <code>port</code>) and is
* available to accept incoming calls from clients.
*
* @param id activation identifier for the object
* @param port the port number on which the object is exported
* @exception RemoteException if exporting the object to the RMI
* runtime fails
* @exception UnsupportedOperationException if and only if activation is
* not supported by this implementation
* @since 1.2
*/
protected Activatable(ActivationID id, int port)
throws RemoteException
{
super();
this.id = id;
exportObject(this, id, port);
}
/**
* Constructor used to activate/export the object on a specified
* port. An "activatable" remote object must have a constructor that
* takes two arguments: <ul>
* <li>the object's activation identifier (<code>ActivationID</code>), and
* <li>the object's initialization data (a <code>MarshalledObject</code>).
* </ul><p>
*
* A concrete subclass of this class must call this constructor when it is
* <i>activated</i> via the two parameter constructor described above. As
* a side-effect of construction, the remote object is "exported"
* to the RMI runtime (on the specified <code>port</code>) and is
* available to accept incoming calls from clients.
*
* @param id activation identifier for the object
* @param port the port number on which the object is exported
* @param csf the client-side socket factory for making calls to the
* remote object
* @param ssf the server-side socket factory for receiving remote calls
* @exception RemoteException if exporting the object to the RMI
* runtime fails
* @exception UnsupportedOperationException if and only if activation is
* not supported by this implementation
* @since 1.2
*/
protected Activatable(ActivationID id, int port,
RMIClientSocketFactory csf,
RMIServerSocketFactory ssf)
throws RemoteException
{
super();
this.id = id;
exportObject(this, id, port, csf, ssf);
}
/**
* Returns the object's activation identifier. The method is
* protected so that only subclasses can obtain an object's
* identifier.
* @return the object's activation identifier
* @since 1.2
*/
protected ActivationID getID() {
return id;
}
/**
* Register an object descriptor for an activatable remote
* object so that is can be activated on demand.
*
* @param desc the object's descriptor
* @return the stub for the activatable remote object
* @exception UnknownGroupException if group id in <code>desc</code>
* is not registered with the activation system
* @exception ActivationException if activation system is not running
* @exception RemoteException if remote call fails
* @exception UnsupportedOperationException if and only if activation is
* not supported by this implementation
* @since 1.2
*/
public static Remote register(ActivationDesc desc)
throws UnknownGroupException, ActivationException, RemoteException
{
// register object with activator.
ActivationID id =
ActivationGroup.getSystem().registerObject(desc);
return sun.rmi.server.ActivatableRef.getStub(desc, id);
}
/**
* Informs the system that the object with the corresponding activation
* <code>id</code> is currently inactive. If the object is currently
* active, the object is "unexported" from the RMI runtime (only if
* there are no pending or in-progress calls)
* so the that it can no longer receive incoming calls. This call
* informs this VM's ActivationGroup that the object is inactive,
* that, in turn, informs its ActivationMonitor. If this call
* completes successfully, a subsequent activate request to the activator
* will cause the object to reactivate. The operation may still
* succeed if the object is considered active but has already
* unexported itself.
*
* @param id the object's activation identifier
* @return true if the operation succeeds (the operation will
* succeed if the object in currently known to be active and is
* either already unexported or is currently exported and has no
* pending/executing calls); false is returned if the object has
* pending/executing calls in which case it cannot be deactivated
* @exception UnknownObjectException if object is not known (it may
* already be inactive)
* @exception ActivationException if group is not active
* @exception RemoteException if call informing monitor fails
* @exception UnsupportedOperationException if and only if activation is
* not supported by this implementation
* @since 1.2
*/
public static boolean inactive(ActivationID id)
throws UnknownObjectException, ActivationException, RemoteException
{
return ActivationGroup.currentGroup().inactiveObject(id);
}
/**
* Revokes previous registration for the activation descriptor
* associated with <code>id</code>. An object can no longer be
* activated via that <code>id</code>.
*
* @param id the object's activation identifier
* @exception UnknownObjectException if object (<code>id</code>) is unknown
* @exception ActivationException if activation system is not running
* @exception RemoteException if remote call to activation system fails
* @exception UnsupportedOperationException if and only if activation is
* not supported by this implementation
* @since 1.2
*/
public static void unregister(ActivationID id)
throws UnknownObjectException, ActivationException, RemoteException
{
ActivationGroup.getSystem().unregisterObject(id);
}
/**
* Registers an activation descriptor (with the specified location,
* data, and restart mode) for the specified object, and exports that
* object with the specified port.
*
* <p><strong>Note:</strong> Using this method (as well as the
* <code>Activatable</code> constructors that both register and export
* an activatable remote object) is strongly discouraged because the
* actions of registering and exporting the remote object are
* <i>not</i> guaranteed to be atomic. Instead, an application should
* register an activation descriptor and export a remote object
* separately, so that exceptions can be handled properly.
*
* <p>This method invokes the {@link
* #exportObject(Remote,String,MarshalledObject,boolean,int,RMIClientSocketFactory,RMIServerSocketFactory)
* exportObject} method with the specified object, location, data,
* restart mode, and port, and <code>null</code> for both client and
* server socket factories, and then returns the resulting activation
* identifier.
*
* @param obj the object being exported
* @param location the object's code location
* @param data the object's bootstrapping data
* @param restart if true, the object is restarted (reactivated) when
* either the activator is restarted or the object's activation group
* is restarted after an unexpected crash; if false, the object is only
* activated on demand. Specifying <code>restart</code> to be
* <code>true</code> does not force an initial immediate activation of
* a newly registered object; initial activation is lazy.
* @param port the port on which the object is exported (an anonymous
* port is used if port=0)
* @return the activation identifier obtained from registering the
* descriptor, <code>desc</code>, with the activation system
* the wrong group
* @exception ActivationException if activation group is not active
* @exception RemoteException if object registration or export fails
* @exception UnsupportedOperationException if and only if activation is
* not supported by this implementation
* @since 1.2
**/
public static ActivationID exportObject(Remote obj,
String location,
MarshalledObject<?> data,
boolean restart,
int port)
throws ActivationException, RemoteException
{
return exportObject(obj, location, data, restart, port, null, null);
}
/**
* Registers an activation descriptor (with the specified location,
* data, and restart mode) for the specified object, and exports that
* object with the specified port, and the specified client and server
* socket factories.
*
* <p><strong>Note:</strong> Using this method (as well as the
* <code>Activatable</code> constructors that both register and export
* an activatable remote object) is strongly discouraged because the
* actions of registering and exporting the remote object are
* <i>not</i> guaranteed to be atomic. Instead, an application should
* register an activation descriptor and export a remote object
* separately, so that exceptions can be handled properly.
*
* <p>This method first registers an activation descriptor for the
* specified object as follows. It obtains the activation system by
* invoking the method {@link ActivationGroup#getSystem
* ActivationGroup.getSystem}. This method then obtains an {@link
* ActivationID} for the object by invoking the activation system's
* {@link ActivationSystem#registerObject registerObject} method with
* an {@link ActivationDesc} constructed with the specified object's
* class name, and the specified location, data, and restart mode. If
* an exception occurs obtaining the activation system or registering
* the activation descriptor, that exception is thrown to the caller.
*
* <p>Next, this method exports the object by invoking the {@link
* #exportObject(Remote,ActivationID,int,RMIClientSocketFactory,RMIServerSocketFactory)
* exportObject} method with the specified remote object, the
* activation identifier obtained from registration, the specified
* port, and the specified client and server socket factories. If an
* exception occurs exporting the object, this method attempts to
* unregister the activation identifier (obtained from registration) by
* invoking the activation system's {@link
* ActivationSystem#unregisterObject unregisterObject} method with the
* activation identifier. If an exception occurs unregistering the
* identifier, that exception is ignored, and the original exception
* that occurred exporting the object is thrown to the caller.
*
* <p>Finally, this method invokes the {@link
* ActivationGroup#activeObject activeObject} method on the activation
* group in this VM with the activation identifier and the specified
* remote object, and returns the activation identifier to the caller.
*
* @param obj the object being exported
* @param location the object's code location
* @param data the object's bootstrapping data
* @param restart if true, the object is restarted (reactivated) when
* either the activator is restarted or the object's activation group
* is restarted after an unexpected crash; if false, the object is only
* activated on demand. Specifying <code>restart</code> to be
* <code>true</code> does not force an initial immediate activation of
* a newly registered object; initial activation is lazy.
* @param port the port on which the object is exported (an anonymous
* port is used if port=0)
* @param csf the client-side socket factory for making calls to the
* remote object
* @param ssf the server-side socket factory for receiving remote calls
* @return the activation identifier obtained from registering the
* descriptor with the activation system
* @exception ActivationException if activation group is not active
* @exception RemoteException if object registration or export fails
* @exception UnsupportedOperationException if and only if activation is
* not supported by this implementation
* @since 1.2
**/
public static ActivationID exportObject(Remote obj,
String location,
MarshalledObject<?> data,
boolean restart,
int port,
RMIClientSocketFactory csf,
RMIServerSocketFactory ssf)
throws ActivationException, RemoteException
{
ActivationDesc desc = new ActivationDesc(obj.getClass().getName(),
location, data, restart);
/*
* Register descriptor.
*/
ActivationSystem system = ActivationGroup.getSystem();
ActivationID id = system.registerObject(desc);
/*
* Export object.
*/
try {
exportObject(obj, id, port, csf, ssf);
} catch (RemoteException e) {
/*
* Attempt to unregister activation descriptor because export
* failed and register/export should be atomic (see 4323621).
*/
try {
system.unregisterObject(id);
} catch (Exception ex) {
}
/*
* Report original exception.
*/
throw e;
}
/*
* This call can't fail (it is a local call, and the only possible
* exception, thrown if the group is inactive, will not be thrown
* because the group is not inactive).
*/
ActivationGroup.currentGroup().activeObject(id, obj);
return id;
}
/**
* Export the activatable remote object to the RMI runtime to make
* the object available to receive incoming calls. The object is
* exported on an anonymous port, if <code>port</code> is zero. <p>
*
* During activation, this <code>exportObject</code> method should
* be invoked explicitly by an "activatable" object, that does not
* extend the <code>Activatable</code> class. There is no need for objects
* that do extend the <code>Activatable</code> class to invoke this
* method directly because the object is exported during construction.
*
* @return the stub for the activatable remote object
* @param obj the remote object implementation
* @param id the object's activation identifier
* @param port the port on which the object is exported (an anonymous
* port is used if port=0)
* @exception RemoteException if object export fails
* @exception UnsupportedOperationException if and only if activation is
* not supported by this implementation
* @since 1.2
*/
public static Remote exportObject(Remote obj,
ActivationID id,
int port)
throws RemoteException
{
return exportObject(obj, new ActivatableServerRef(id, port));
}
/**
* Export the activatable remote object to the RMI runtime to make
* the object available to receive incoming calls. The object is
* exported on an anonymous port, if <code>port</code> is zero. <p>
*
* During activation, this <code>exportObject</code> method should
* be invoked explicitly by an "activatable" object, that does not
* extend the <code>Activatable</code> class. There is no need for objects
* that do extend the <code>Activatable</code> class to invoke this
* method directly because the object is exported during construction.
*
* @return the stub for the activatable remote object
* @param obj the remote object implementation
* @param id the object's activation identifier
* @param port the port on which the object is exported (an anonymous
* port is used if port=0)
* @param csf the client-side socket factory for making calls to the
* remote object
* @param ssf the server-side socket factory for receiving remote calls
* @exception RemoteException if object export fails
* @exception UnsupportedOperationException if and only if activation is
* not supported by this implementation
* @since 1.2
*/
public static Remote exportObject(Remote obj,
ActivationID id,
int port,
RMIClientSocketFactory csf,
RMIServerSocketFactory ssf)
throws RemoteException
{
return exportObject(obj, new ActivatableServerRef(id, port, csf, ssf));
}
/**
* Remove the remote object, obj, from the RMI runtime. If
* successful, the object can no longer accept incoming RMI calls.
* If the force parameter is true, the object is forcibly unexported
* even if there are pending calls to the remote object or the
* remote object still has calls in progress. If the force
* parameter is false, the object is only unexported if there are
* no pending or in progress calls to the object.
*
* @param obj the remote object to be unexported
* @param force if true, unexports the object even if there are
* pending or in-progress calls; if false, only unexports the object
* if there are no pending or in-progress calls
* @return true if operation is successful, false otherwise
* @exception NoSuchObjectException if the remote object is not
* currently exported
* @exception UnsupportedOperationException if and only if activation is
* not supported by this implementation
* @since 1.2
*/
public static boolean unexportObject(Remote obj, boolean force)
throws NoSuchObjectException
{
return sun.rmi.transport.ObjectTable.unexportObject(obj, force);
}
/**
* Exports the specified object using the specified server ref.
*/
private static Remote exportObject(Remote obj, ActivatableServerRef sref)
throws RemoteException
{
// if obj extends Activatable, set its ref.
if (obj instanceof Activatable) {
((Activatable) obj).ref = sref;
}
return sref.exportObject(obj, null, false);
}
}

View File

@@ -0,0 +1,62 @@
/*
* Copyright (c) 1998, 1999, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Oracle designates this
* particular file as subject to the "Classpath" exception as provided
* by Oracle in the LICENSE file that accompanied this code.
*
* This code 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
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*/
package java.rmi.activation;
/**
* This exception is thrown by the RMI runtime when activation
* fails during a remote call to an activatable object.
*
* @author Ann Wollrath
* @since 1.2
*/
public class ActivateFailedException extends java.rmi.RemoteException {
/** indicate compatibility with the Java 2 SDK v1.2 version of class */
private static final long serialVersionUID = 4863550261346652506L;
/**
* Constructs an <code>ActivateFailedException</code> with the specified
* detail message.
*
* @param s the detail message
* @since 1.2
*/
public ActivateFailedException(String s) {
super(s);
}
/**
* Constructs an <code>ActivateFailedException</code> with the specified
* detail message and nested exception.
*
* @param s the detail message
* @param ex the nested exception
* @since 1.2
*/
public ActivateFailedException(String s, Exception ex) {
super(s, ex);
}
}

View File

@@ -0,0 +1,347 @@
/*
* Copyright (c) 1997, 2013, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Oracle designates this
* particular file as subject to the "Classpath" exception as provided
* by Oracle in the LICENSE file that accompanied this code.
*
* This code 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
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*/
package java.rmi.activation;
import java.io.Serializable;
import java.rmi.MarshalledObject;
/**
* An activation descriptor contains the information necessary to
* activate an object: <ul>
* <li> the object's group identifier,
* <li> the object's fully-qualified class name,
* <li> the object's code location (the location of the class), a codebase URL
* path,
* <li> the object's restart "mode", and,
* <li> a "marshalled" object that can contain object specific
* initialization data. </ul>
*
* <p>A descriptor registered with the activation system can be used to
* recreate/activate the object specified by the descriptor. The
* <code>MarshalledObject</code> in the object's descriptor is passed
* as the second argument to the remote object's constructor for
* object to use during reinitialization/activation.
*
* @author Ann Wollrath
* @since 1.2
* @see java.rmi.activation.Activatable
*/
public final class ActivationDesc implements Serializable {
/**
* @serial the group's identifier
*/
private ActivationGroupID groupID;
/**
* @serial the object's class name
*/
private String className;
/**
* @serial the object's code location
*/
private String location;
/**
* @serial the object's initialization data
*/
private MarshalledObject<?> data;
/**
* @serial indicates whether the object should be restarted
*/
private boolean restart;
/** indicate compatibility with the Java 2 SDK v1.2 version of class */
private static final long serialVersionUID = 7455834104417690957L;
/**
* Constructs an object descriptor for an object whose class name
* is <code>className</code>, that can be loaded from the
* code <code>location</code> and whose initialization
* information is <code>data</code>. If this form of the constructor
* is used, the <code>groupID</code> defaults to the current id for
* <code>ActivationGroup</code> for this VM. All objects with the
* same <code>ActivationGroupID</code> are activated in the same VM.
*
* <p>Note that objects specified by a descriptor created with this
* constructor will only be activated on demand (by default, the restart
* mode is <code>false</code>). If an activatable object requires restart
* services, use one of the <code>ActivationDesc</code> constructors that
* takes a boolean parameter, <code>restart</code>.
*
* <p> This constructor will throw <code>ActivationException</code> if
* there is no current activation group for this VM. To create an
* <code>ActivationGroup</code> use the
* <code>ActivationGroup.createGroup</code> method.
*
* @param className the object's fully package qualified class name
* @param location the object's code location (from where the class is
* loaded)
* @param data the object's initialization (activation) data contained
* in marshalled form.
* @exception ActivationException if the current group is nonexistent
* @exception UnsupportedOperationException if and only if activation is
* not supported by this implementation
* @since 1.2
*/
public ActivationDesc(String className,
String location,
MarshalledObject<?> data)
throws ActivationException
{
this(ActivationGroup.internalCurrentGroupID(),
className, location, data, false);
}
/**
* Constructs an object descriptor for an object whose class name
* is <code>className</code>, that can be loaded from the
* code <code>location</code> and whose initialization
* information is <code>data</code>. If this form of the constructor
* is used, the <code>groupID</code> defaults to the current id for
* <code>ActivationGroup</code> for this VM. All objects with the
* same <code>ActivationGroupID</code> are activated in the same VM.
*
* <p>This constructor will throw <code>ActivationException</code> if
* there is no current activation group for this VM. To create an
* <code>ActivationGroup</code> use the
* <code>ActivationGroup.createGroup</code> method.
*
* @param className the object's fully package qualified class name
* @param location the object's code location (from where the class is
* loaded)
* @param data the object's initialization (activation) data contained
* in marshalled form.
* @param restart if true, the object is restarted (reactivated) when
* either the activator is restarted or the object's activation group
* is restarted after an unexpected crash; if false, the object is only
* activated on demand. Specifying <code>restart</code> to be
* <code>true</code> does not force an initial immediate activation of
* a newly registered object; initial activation is lazy.
* @exception ActivationException if the current group is nonexistent
* @exception UnsupportedOperationException if and only if activation is
* not supported by this implementation
* @since 1.2
*/
public ActivationDesc(String className,
String location,
MarshalledObject<?> data,
boolean restart)
throws ActivationException
{
this(ActivationGroup.internalCurrentGroupID(),
className, location, data, restart);
}
/**
* Constructs an object descriptor for an object whose class name
* is <code>className</code> that can be loaded from the
* code <code>location</code> and whose initialization
* information is <code>data</code>. All objects with the same
* <code>groupID</code> are activated in the same Java VM.
*
* <p>Note that objects specified by a descriptor created with this
* constructor will only be activated on demand (by default, the restart
* mode is <code>false</code>). If an activatable object requires restart
* services, use one of the <code>ActivationDesc</code> constructors that
* takes a boolean parameter, <code>restart</code>.
*
* @param groupID the group's identifier (obtained from registering
* <code>ActivationSystem.registerGroup</code> method). The group
* indicates the VM in which the object should be activated.
* @param className the object's fully package-qualified class name
* @param location the object's code location (from where the class is
* loaded)
* @param data the object's initialization (activation) data contained
* in marshalled form.
* @exception IllegalArgumentException if <code>groupID</code> is null
* @exception UnsupportedOperationException if and only if activation is
* not supported by this implementation
* @since 1.2
*/
public ActivationDesc(ActivationGroupID groupID,
String className,
String location,
MarshalledObject<?> data)
{
this(groupID, className, location, data, false);
}
/**
* Constructs an object descriptor for an object whose class name
* is <code>className</code> that can be loaded from the
* code <code>location</code> and whose initialization
* information is <code>data</code>. All objects with the same
* <code>groupID</code> are activated in the same Java VM.
*
* @param groupID the group's identifier (obtained from registering
* <code>ActivationSystem.registerGroup</code> method). The group
* indicates the VM in which the object should be activated.
* @param className the object's fully package-qualified class name
* @param location the object's code location (from where the class is
* loaded)
* @param data the object's initialization (activation) data contained
* in marshalled form.
* @param restart if true, the object is restarted (reactivated) when
* either the activator is restarted or the object's activation group
* is restarted after an unexpected crash; if false, the object is only
* activated on demand. Specifying <code>restart</code> to be
* <code>true</code> does not force an initial immediate activation of
* a newly registered object; initial activation is lazy.
* @exception IllegalArgumentException if <code>groupID</code> is null
* @exception UnsupportedOperationException if and only if activation is
* not supported by this implementation
* @since 1.2
*/
public ActivationDesc(ActivationGroupID groupID,
String className,
String location,
MarshalledObject<?> data,
boolean restart)
{
if (groupID == null)
throw new IllegalArgumentException("groupID can't be null");
this.groupID = groupID;
this.className = className;
this.location = location;
this.data = data;
this.restart = restart;
}
/**
* Returns the group identifier for the object specified by this
* descriptor. A group provides a way to aggregate objects into a
* single Java virtual machine. RMI creates/activates objects with
* the same <code>groupID</code> in the same virtual machine.
*
* @return the group identifier
* @since 1.2
*/
public ActivationGroupID getGroupID() {
return groupID;
}
/**
* Returns the class name for the object specified by this
* descriptor.
* @return the class name
* @since 1.2
*/
public String getClassName() {
return className;
}
/**
* Returns the code location for the object specified by
* this descriptor.
* @return the code location
* @since 1.2
*/
public String getLocation() {
return location;
}
/**
* Returns a "marshalled object" containing intialization/activation
* data for the object specified by this descriptor.
* @return the object specific "initialization" data
* @since 1.2
*/
public MarshalledObject<?> getData() {
return data;
}
/**
* Returns the "restart" mode of the object associated with
* this activation descriptor.
*
* @return true if the activatable object associated with this
* activation descriptor is restarted via the activation
* daemon when either the daemon comes up or the object's group
* is restarted after an unexpected crash; otherwise it returns false,
* meaning that the object is only activated on demand via a
* method call. Note that if the restart mode is <code>true</code>, the
* activator does not force an initial immediate activation of
* a newly registered object; initial activation is lazy.
* @since 1.2
*/
public boolean getRestartMode() {
return restart;
}
/**
* Compares two activation descriptors for content equality.
*
* @param obj the Object to compare with
* @return true if these Objects are equal; false otherwise.
* @see java.util.Hashtable
* @since 1.2
*/
public boolean equals(Object obj) {
if (obj instanceof ActivationDesc) {
ActivationDesc desc = (ActivationDesc) obj;
return
((groupID == null ? desc.groupID == null :
groupID.equals(desc.groupID)) &&
(className == null ? desc.className == null :
className.equals(desc.className)) &&
(location == null ? desc.location == null:
location.equals(desc.location)) &&
(data == null ? desc.data == null :
data.equals(desc.data)) &&
(restart == desc.restart));
} else {
return false;
}
}
/**
* Return the same hashCode for similar <code>ActivationDesc</code>s.
* @return an integer
* @see java.util.Hashtable
*/
public int hashCode() {
return ((location == null
? 0
: location.hashCode() << 24) ^
(groupID == null
? 0
: groupID.hashCode() << 16) ^
(className == null
? 0
: className.hashCode() << 9) ^
(data == null
? 0
: data.hashCode() << 1) ^
(restart
? 1
: 0));
}
}

View File

@@ -0,0 +1,118 @@
/*
* Copyright (c) 1997, 2003, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Oracle designates this
* particular file as subject to the "Classpath" exception as provided
* by Oracle in the LICENSE file that accompanied this code.
*
* This code 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
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*/
package java.rmi.activation;
/**
* General exception used by the activation interfaces.
*
* <p>As of release 1.4, this exception has been retrofitted to conform to
* the general purpose exception-chaining mechanism. The "detail exception"
* that may be provided at construction time and accessed via the public
* {@link #detail} field is now known as the <i>cause</i>, and may be
* accessed via the {@link Throwable#getCause()} method, as well as
* the aforementioned "legacy field."
*
* <p>Invoking the method {@link Throwable#initCause(Throwable)} on an
* instance of <code>ActivationException</code> always throws {@link
* IllegalStateException}.
*
* @author Ann Wollrath
* @since 1.2
*/
public class ActivationException extends Exception {
/**
* The cause of the activation exception.
*
* <p>This field predates the general-purpose exception chaining facility.
* The {@link Throwable#getCause()} method is now the preferred means of
* obtaining this information.
*
* @serial
*/
public Throwable detail;
/** indicate compatibility with the Java 2 SDK v1.2 version of class */
private static final long serialVersionUID = -4320118837291406071L;
/**
* Constructs an <code>ActivationException</code>.
*/
public ActivationException() {
initCause(null); // Disallow subsequent initCause
}
/**
* Constructs an <code>ActivationException</code> with the specified
* detail message.
*
* @param s the detail message
*/
public ActivationException(String s) {
super(s);
initCause(null); // Disallow subsequent initCause
}
/**
* Constructs an <code>ActivationException</code> with the specified
* detail message and cause. This constructor sets the {@link #detail}
* field to the specified <code>Throwable</code>.
*
* @param s the detail message
* @param cause the cause
*/
public ActivationException(String s, Throwable cause) {
super(s);
initCause(null); // Disallow subsequent initCause
detail = cause;
}
/**
* Returns the detail message, including the message from the cause, if
* any, of this exception.
*
* @return the detail message
*/
public String getMessage() {
if (detail == null)
return super.getMessage();
else
return super.getMessage() +
"; nested exception is: \n\t" +
detail.toString();
}
/**
* Returns the cause of this exception. This method returns the value
* of the {@link #detail} field.
*
* @return the cause, which may be <tt>null</tt>.
* @since 1.4
*/
public Throwable getCause() {
return detail;
}
}

View File

@@ -0,0 +1,538 @@
/*
* Copyright (c) 1997, 2013, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Oracle designates this
* particular file as subject to the "Classpath" exception as provided
* by Oracle in the LICENSE file that accompanied this code.
*
* This code 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
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*/
package java.rmi.activation;
import java.lang.reflect.Constructor;
import java.lang.reflect.InvocationTargetException;
import java.rmi.MarshalledObject;
import java.rmi.Naming;
import java.rmi.Remote;
import java.rmi.RemoteException;
import java.rmi.activation.UnknownGroupException;
import java.rmi.activation.UnknownObjectException;
import java.rmi.server.RMIClassLoader;
import java.rmi.server.UnicastRemoteObject;
import java.security.AccessController;
import sun.security.action.GetIntegerAction;
/**
* An <code>ActivationGroup</code> is responsible for creating new
* instances of "activatable" objects in its group, informing its
* <code>ActivationMonitor</code> when either: its object's become
* active or inactive, or the group as a whole becomes inactive. <p>
*
* An <code>ActivationGroup</code> is <i>initially</i> created in one
* of several ways: <ul>
* <li>as a side-effect of creating an <code>ActivationDesc</code>
* without an explicit <code>ActivationGroupID</code> for the
* first activatable object in the group, or
* <li>via the <code>ActivationGroup.createGroup</code> method
* <li>as a side-effect of activating the first object in a group
* whose <code>ActivationGroupDesc</code> was only registered.</ul><p>
*
* Only the activator can <i>recreate</i> an
* <code>ActivationGroup</code>. The activator spawns, as needed, a
* separate VM (as a child process, for example) for each registered
* activation group and directs activation requests to the appropriate
* group. It is implementation specific how VMs are spawned. An
* activation group is created via the
* <code>ActivationGroup.createGroup</code> static method. The
* <code>createGroup</code> method has two requirements on the group
* to be created: 1) the group must be a concrete subclass of
* <code>ActivationGroup</code>, and 2) the group must have a
* constructor that takes two arguments:
*
* <ul>
* <li> the group's <code>ActivationGroupID</code>, and
* <li> the group's initialization data (in a
* <code>java.rmi.MarshalledObject</code>)</ul><p>
*
* When created, the default implementation of
* <code>ActivationGroup</code> will override the system properties
* with the properties requested when its
* <code>ActivationGroupDesc</code> was created, and will set a
* {@link SecurityManager} as the default system
* security manager. If your application requires specific properties
* to be set when objects are activated in the group, the application
* should create a special <code>Properties</code> object containing
* these properties, then create an <code>ActivationGroupDesc</code>
* with the <code>Properties</code> object, and use
* <code>ActivationGroup.createGroup</code> before creating any
* <code>ActivationDesc</code>s (before the default
* <code>ActivationGroupDesc</code> is created). If your application
* requires the use of a security manager other than
* {@link SecurityManager}, in the
* ActivativationGroupDescriptor properties list you can set
* <code>java.security.manager</code> property to the name of the security
* manager you would like to install.
*
* @author Ann Wollrath
* @see ActivationInstantiator
* @see ActivationGroupDesc
* @see ActivationGroupID
* @since 1.2
*/
public abstract class ActivationGroup
extends UnicastRemoteObject
implements ActivationInstantiator
{
/**
* @serial the group's identifier
*/
private ActivationGroupID groupID;
/**
* @serial the group's monitor
*/
private ActivationMonitor monitor;
/**
* @serial the group's incarnation number
*/
private long incarnation;
/** the current activation group for this VM */
private static ActivationGroup currGroup;
/** the current group's identifier */
private static ActivationGroupID currGroupID;
/** the current group's activation system */
private static ActivationSystem currSystem;
/** used to control a group being created only once */
private static boolean canCreate = true;
/** indicate compatibility with the Java 2 SDK v1.2 version of class */
private static final long serialVersionUID = -7696947875314805420L;
/**
* Constructs an activation group with the given activation group
* identifier. The group is exported as a
* <code>java.rmi.server.UnicastRemoteObject</code>.
*
* @param groupID the group's identifier
* @throws RemoteException if this group could not be exported
* @throws UnsupportedOperationException if and only if activation is
* not supported by this implementation
* @since 1.2
*/
protected ActivationGroup(ActivationGroupID groupID)
throws RemoteException
{
// call super constructor to export the object
super();
this.groupID = groupID;
}
/**
* The group's <code>inactiveObject</code> method is called
* indirectly via a call to the <code>Activatable.inactive</code>
* method. A remote object implementation must call
* <code>Activatable</code>'s <code>inactive</code> method when
* that object deactivates (the object deems that it is no longer
* active). If the object does not call
* <code>Activatable.inactive</code> when it deactivates, the
* object will never be garbage collected since the group keeps
* strong references to the objects it creates.
*
* <p>The group's <code>inactiveObject</code> method unexports the
* remote object from the RMI runtime so that the object can no
* longer receive incoming RMI calls. An object will only be unexported
* if the object has no pending or executing calls.
* The subclass of <code>ActivationGroup</code> must override this
* method and unexport the object.
*
* <p>After removing the object from the RMI runtime, the group
* must inform its <code>ActivationMonitor</code> (via the monitor's
* <code>inactiveObject</code> method) that the remote object is
* not currently active so that the remote object will be
* re-activated by the activator upon a subsequent activation
* request.
*
* <p>This method simply informs the group's monitor that the object
* is inactive. It is up to the concrete subclass of ActivationGroup
* to fulfill the additional requirement of unexporting the object. <p>
*
* @param id the object's activation identifier
* @return true if the object was successfully deactivated; otherwise
* returns false.
* @exception UnknownObjectException if object is unknown (may already
* be inactive)
* @exception RemoteException if call informing monitor fails
* @exception ActivationException if group is inactive
* @since 1.2
*/
public boolean inactiveObject(ActivationID id)
throws ActivationException, UnknownObjectException, RemoteException
{
getMonitor().inactiveObject(id);
return true;
}
/**
* The group's <code>activeObject</code> method is called when an
* object is exported (either by <code>Activatable</code> object
* construction or an explicit call to
* <code>Activatable.exportObject</code>. The group must inform its
* <code>ActivationMonitor</code> that the object is active (via
* the monitor's <code>activeObject</code> method) if the group
* hasn't already done so.
*
* @param id the object's identifier
* @param obj the remote object implementation
* @exception UnknownObjectException if object is not registered
* @exception RemoteException if call informing monitor fails
* @exception ActivationException if group is inactive
* @since 1.2
*/
public abstract void activeObject(ActivationID id, Remote obj)
throws ActivationException, UnknownObjectException, RemoteException;
/**
* Create and set the activation group for the current VM. The
* activation group can only be set if it is not currently set.
* An activation group is set using the <code>createGroup</code>
* method when the <code>Activator</code> initiates the
* re-creation of an activation group in order to carry out
* incoming <code>activate</code> requests. A group must first be
* registered with the <code>ActivationSystem</code> before it can
* be created via this method.
*
* <p>The group class specified by the
* <code>ActivationGroupDesc</code> must be a concrete subclass of
* <code>ActivationGroup</code> and have a public constructor that
* takes two arguments: the <code>ActivationGroupID</code> for the
* group and the <code>MarshalledObject</code> containing the
* group's initialization data (obtained from the
* <code>ActivationGroupDesc</code>.
*
* <p>If the group class name specified in the
* <code>ActivationGroupDesc</code> is <code>null</code>, then
* this method will behave as if the group descriptor contained
* the name of the default activation group implementation class.
*
* <p>Note that if your application creates its own custom
* activation group, a security manager must be set for that
* group. Otherwise objects cannot be activated in the group.
* {@link SecurityManager} is set by default.
*
* <p>If a security manager is already set in the group VM, this
* method first calls the security manager's
* <code>checkSetFactory</code> method. This could result in a
* <code>SecurityException</code>. If your application needs to
* set a different security manager, you must ensure that the
* policy file specified by the group's
* <code>ActivationGroupDesc</code> grants the group the necessary
* permissions to set a new security manager. (Note: This will be
* necessary if your group downloads and sets a security manager).
*
* <p>After the group is created, the
* <code>ActivationSystem</code> is informed that the group is
* active by calling the <code>activeGroup</code> method which
* returns the <code>ActivationMonitor</code> for the group. The
* application need not call <code>activeGroup</code>
* independently since it is taken care of by this method.
*
* <p>Once a group is created, subsequent calls to the
* <code>currentGroupID</code> method will return the identifier
* for this group until the group becomes inactive.
*
* @param id the activation group's identifier
* @param desc the activation group's descriptor
* @param incarnation the group's incarnation number (zero on group's
* initial creation)
* @return the activation group for the VM
* @exception ActivationException if group already exists or if error
* occurs during group creation
* @exception SecurityException if permission to create group is denied.
* (Note: The default implementation of the security manager
* <code>checkSetFactory</code>
* method requires the RuntimePermission "setFactory")
* @exception UnsupportedOperationException if and only if activation is
* not supported by this implementation
* @see SecurityManager#checkSetFactory
* @since 1.2
*/
public static synchronized
ActivationGroup createGroup(ActivationGroupID id,
final ActivationGroupDesc desc,
long incarnation)
throws ActivationException
{
SecurityManager security = System.getSecurityManager();
if (security != null)
security.checkSetFactory();
if (currGroup != null)
throw new ActivationException("group already exists");
if (canCreate == false)
throw new ActivationException("group deactivated and " +
"cannot be recreated");
try {
// load group's class
String groupClassName = desc.getClassName();
Class<? extends ActivationGroup> cl;
Class<? extends ActivationGroup> defaultGroupClass =
sun.rmi.server.ActivationGroupImpl.class;
if (groupClassName == null || // see 4252236
groupClassName.equals(defaultGroupClass.getName()))
{
cl = defaultGroupClass;
} else {
Class<?> cl0;
try {
cl0 = RMIClassLoader.loadClass(desc.getLocation(),
groupClassName);
} catch (Exception ex) {
throw new ActivationException(
"Could not load group implementation class", ex);
}
if (ActivationGroup.class.isAssignableFrom(cl0)) {
cl = cl0.asSubclass(ActivationGroup.class);
} else {
throw new ActivationException("group not correct class: " +
cl0.getName());
}
}
// create group
Constructor<? extends ActivationGroup> constructor =
cl.getConstructor(ActivationGroupID.class,
MarshalledObject.class);
ActivationGroup newGroup =
constructor.newInstance(id, desc.getData());
currSystem = id.getSystem();
newGroup.incarnation = incarnation;
newGroup.monitor =
currSystem.activeGroup(id, newGroup, incarnation);
currGroup = newGroup;
currGroupID = id;
canCreate = false;
} catch (InvocationTargetException e) {
e.getTargetException().printStackTrace();
throw new ActivationException("exception in group constructor",
e.getTargetException());
} catch (ActivationException e) {
throw e;
} catch (Exception e) {
throw new ActivationException("exception creating group", e);
}
return currGroup;
}
/**
* Returns the current activation group's identifier. Returns null
* if no group is currently active for this VM.
* @exception UnsupportedOperationException if and only if activation is
* not supported by this implementation
* @return the activation group's identifier
* @since 1.2
*/
public static synchronized ActivationGroupID currentGroupID() {
return currGroupID;
}
/**
* Returns the activation group identifier for the VM. If an
* activation group does not exist for this VM, a default
* activation group is created. A group can be created only once,
* so if a group has already become active and deactivated.
*
* @return the activation group identifier
* @exception ActivationException if error occurs during group
* creation, if security manager is not set, or if the group
* has already been created and deactivated.
*/
static synchronized ActivationGroupID internalCurrentGroupID()
throws ActivationException
{
if (currGroupID == null)
throw new ActivationException("nonexistent group");
return currGroupID;
}
/**
* Set the activation system for the VM. The activation system can
* only be set it if no group is currently active. If the activation
* system is not set via this call, then the <code>getSystem</code>
* method attempts to obtain a reference to the
* <code>ActivationSystem</code> by looking up the name
* "java.rmi.activation.ActivationSystem" in the Activator's
* registry. By default, the port number used to look up the
* activation system is defined by
* <code>ActivationSystem.SYSTEM_PORT</code>. This port can be overridden
* by setting the property <code>java.rmi.activation.port</code>.
*
* <p>If there is a security manager, this method first
* calls the security manager's <code>checkSetFactory</code> method.
* This could result in a SecurityException.
*
* @param system remote reference to the <code>ActivationSystem</code>
* @exception ActivationException if activation system is already set
* @exception SecurityException if permission to set the activation system is denied.
* (Note: The default implementation of the security manager
* <code>checkSetFactory</code>
* method requires the RuntimePermission "setFactory")
* @exception UnsupportedOperationException if and only if activation is
* not supported by this implementation
* @see #getSystem
* @see SecurityManager#checkSetFactory
* @since 1.2
*/
public static synchronized void setSystem(ActivationSystem system)
throws ActivationException
{
SecurityManager security = System.getSecurityManager();
if (security != null)
security.checkSetFactory();
if (currSystem != null)
throw new ActivationException("activation system already set");
currSystem = system;
}
/**
* Returns the activation system for the VM. The activation system
* may be set by the <code>setSystem</code> method. If the
* activation system is not set via the <code>setSystem</code>
* method, then the <code>getSystem</code> method attempts to
* obtain a reference to the <code>ActivationSystem</code> by
* looking up the name "java.rmi.activation.ActivationSystem" in
* the Activator's registry. By default, the port number used to
* look up the activation system is defined by
* <code>ActivationSystem.SYSTEM_PORT</code>. This port can be
* overridden by setting the property
* <code>java.rmi.activation.port</code>.
*
* @return the activation system for the VM/group
* @exception ActivationException if activation system cannot be
* obtained or is not bound
* (means that it is not running)
* @exception UnsupportedOperationException if and only if activation is
* not supported by this implementation
* @see #setSystem
* @since 1.2
*/
public static synchronized ActivationSystem getSystem()
throws ActivationException
{
if (currSystem == null) {
try {
int port = AccessController.doPrivileged(
new GetIntegerAction("java.rmi.activation.port",
ActivationSystem.SYSTEM_PORT));
currSystem = (ActivationSystem)
Naming.lookup("//:" + port +
"/java.rmi.activation.ActivationSystem");
} catch (Exception e) {
throw new ActivationException(
"unable to obtain ActivationSystem", e);
}
}
return currSystem;
}
/**
* This protected method is necessary for subclasses to
* make the <code>activeObject</code> callback to the group's
* monitor. The call is simply forwarded to the group's
* <code>ActivationMonitor</code>.
*
* @param id the object's identifier
* @param mobj a marshalled object containing the remote object's stub
* @exception UnknownObjectException if object is not registered
* @exception RemoteException if call informing monitor fails
* @exception ActivationException if an activation error occurs
* @since 1.2
*/
protected void activeObject(ActivationID id,
MarshalledObject<? extends Remote> mobj)
throws ActivationException, UnknownObjectException, RemoteException
{
getMonitor().activeObject(id, mobj);
}
/**
* This protected method is necessary for subclasses to
* make the <code>inactiveGroup</code> callback to the group's
* monitor. The call is simply forwarded to the group's
* <code>ActivationMonitor</code>. Also, the current group
* for the VM is set to null.
*
* @exception UnknownGroupException if group is not registered
* @exception RemoteException if call informing monitor fails
* @since 1.2
*/
protected void inactiveGroup()
throws UnknownGroupException, RemoteException
{
try {
getMonitor().inactiveGroup(groupID, incarnation);
} finally {
destroyGroup();
}
}
/**
* Returns the monitor for the activation group.
*/
private ActivationMonitor getMonitor() throws RemoteException {
synchronized (ActivationGroup.class) {
if (monitor != null) {
return monitor;
}
}
throw new RemoteException("monitor not received");
}
/**
* Destroys the current group.
*/
private static synchronized void destroyGroup() {
currGroup = null;
currGroupID = null;
// NOTE: don't set currSystem to null since it may be needed
}
/**
* Returns the current group for the VM.
* @exception ActivationException if current group is null (not active)
*/
static synchronized ActivationGroup currentGroup()
throws ActivationException
{
if (currGroup == null) {
throw new ActivationException("group is not active");
}
return currGroup;
}
}

View File

@@ -0,0 +1,370 @@
/*
* Copyright (c) 1997, 2008, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Oracle designates this
* particular file as subject to the "Classpath" exception as provided
* by Oracle in the LICENSE file that accompanied this code.
*
* This code 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
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*/
package java.rmi.activation;
import java.io.IOException;
import java.io.ObjectInputStream;
import java.io.Serializable;
import java.rmi.MarshalledObject;
import java.util.Arrays;
import java.util.Properties;
/**
* An activation group descriptor contains the information necessary to
* create/recreate an activation group in which to activate objects.
* Such a descriptor contains: <ul>
* <li> the group's class name,
* <li> the group's code location (the location of the group's class), and
* <li> a "marshalled" object that can contain group specific
* initialization data. </ul> <p>
*
* The group's class must be a concrete subclass of
* <code>ActivationGroup</code>. A subclass of
* <code>ActivationGroup</code> is created/recreated via the
* <code>ActivationGroup.createGroup</code> static method that invokes
* a special constructor that takes two arguments: <ul>
*
* <li> the group's <code>ActivationGroupID</code>, and
* <li> the group's initialization data (in a
* <code>java.rmi.MarshalledObject</code>)</ul><p>
*
* @author Ann Wollrath
* @since 1.2
* @see ActivationGroup
* @see ActivationGroupID
*/
public final class ActivationGroupDesc implements Serializable {
/**
* @serial The group's fully package qualified class name.
*/
private String className;
/**
* @serial The location from where to load the group's class.
*/
private String location;
/**
* @serial The group's initialization data.
*/
private MarshalledObject<?> data;
/**
* @serial The controlling options for executing the VM in
* another process.
*/
private CommandEnvironment env;
/**
* @serial A properties map which will override those set
* by default in the subprocess environment.
*/
private Properties props;
/** indicate compatibility with the Java 2 SDK v1.2 version of class */
private static final long serialVersionUID = -4936225423168276595L;
/**
* Constructs a group descriptor that uses the system defaults for group
* implementation and code location. Properties specify Java
* environment overrides (which will override system properties in
* the group implementation's VM). The command
* environment can control the exact command/options used in
* starting the child VM, or can be <code>null</code> to accept
* rmid's default.
*
* <p>This constructor will create an <code>ActivationGroupDesc</code>
* with a <code>null</code> group class name, which indicates the system's
* default <code>ActivationGroup</code> implementation.
*
* @param overrides the set of properties to set when the group is
* recreated.
* @param cmd the controlling options for executing the VM in
* another process (or <code>null</code>).
* @since 1.2
*/
public ActivationGroupDesc(Properties overrides,
CommandEnvironment cmd)
{
this(null, null, null, overrides, cmd);
}
/**
* Specifies an alternate group implementation and execution
* environment to be used for the group.
*
* @param className the group's package qualified class name or
* <code>null</code>. A <code>null</code> group class name indicates
* the system's default <code>ActivationGroup</code> implementation.
* @param location the location from where to load the group's
* class
* @param data the group's initialization data contained in
* marshalled form (could contain properties, for example)
* @param overrides a properties map which will override those set
* by default in the subprocess environment (will be translated
* into <code>-D</code> options), or <code>null</code>.
* @param cmd the controlling options for executing the VM in
* another process (or <code>null</code>).
* @since 1.2
*/
public ActivationGroupDesc(String className,
String location,
MarshalledObject<?> data,
Properties overrides,
CommandEnvironment cmd)
{
this.props = overrides;
this.env = cmd;
this.data = data;
this.location = location;
this.className = className;
}
/**
* Returns the group's class name (possibly <code>null</code>). A
* <code>null</code> group class name indicates the system's default
* <code>ActivationGroup</code> implementation.
* @return the group's class name
* @since 1.2
*/
public String getClassName() {
return className;
}
/**
* Returns the group's code location.
* @return the group's code location
* @since 1.2
*/
public String getLocation() {
return location;
}
/**
* Returns the group's initialization data.
* @return the group's initialization data
* @since 1.2
*/
public MarshalledObject<?> getData() {
return data;
}
/**
* Returns the group's property-override list.
* @return the property-override list, or <code>null</code>
* @since 1.2
*/
public Properties getPropertyOverrides() {
return (props != null) ? (Properties) props.clone() : null;
}
/**
* Returns the group's command-environment control object.
* @return the command-environment object, or <code>null</code>
* @since 1.2
*/
public CommandEnvironment getCommandEnvironment() {
return this.env;
}
/**
* Startup options for ActivationGroup implementations.
*
* This class allows overriding default system properties and
* specifying implementation-defined options for ActivationGroups.
* @since 1.2
*/
public static class CommandEnvironment implements Serializable {
private static final long serialVersionUID = 6165754737887770191L;
/**
* @serial
*/
private String command;
/**
* @serial
*/
private String[] options;
/**
* Create a CommandEnvironment with all the necessary
* information.
*
* @param cmdpath the name of the java executable, including
* the full path, or <code>null</code>, meaning "use rmid's default".
* The named program <em>must</em> be able to accept multiple
* <code>-Dpropname=value</code> options (as documented for the
* "java" tool)
*
* @param argv extra options which will be used in creating the
* ActivationGroup. Null has the same effect as an empty
* list.
* @since 1.2
*/
public CommandEnvironment(String cmdpath,
String[] argv)
{
this.command = cmdpath; // might be null
// Hold a safe copy of argv in this.options
if (argv == null) {
this.options = new String[0];
} else {
this.options = new String[argv.length];
System.arraycopy(argv, 0, this.options, 0, argv.length);
}
}
/**
* Fetch the configured path-qualified java command name.
*
* @return the configured name, or <code>null</code> if configured to
* accept the default
* @since 1.2
*/
public String getCommandPath() {
return (this.command);
}
/**
* Fetch the configured java command options.
*
* @return An array of the command options which will be passed
* to the new child command by rmid.
* Note that rmid may add other options before or after these
* options, or both.
* Never returns <code>null</code>.
* @since 1.2
*/
public String[] getCommandOptions() {
return options.clone();
}
/**
* Compares two command environments for content equality.
*
* @param obj the Object to compare with
* @return true if these Objects are equal; false otherwise.
* @see java.util.Hashtable
* @since 1.2
*/
public boolean equals(Object obj) {
if (obj instanceof CommandEnvironment) {
CommandEnvironment env = (CommandEnvironment) obj;
return
((command == null ? env.command == null :
command.equals(env.command)) &&
Arrays.equals(options, env.options));
} else {
return false;
}
}
/**
* Return identical values for similar
* <code>CommandEnvironment</code>s.
* @return an integer
* @see java.util.Hashtable
*/
public int hashCode()
{
// hash command and ignore possibly expensive options
return (command == null ? 0 : command.hashCode());
}
/**
* <code>readObject</code> for custom serialization.
*
* <p>This method reads this object's serialized form for this
* class as follows:
*
* <p>This method first invokes <code>defaultReadObject</code> on
* the specified object input stream, and if <code>options</code>
* is <code>null</code>, then <code>options</code> is set to a
* zero-length array of <code>String</code>.
*/
private void readObject(ObjectInputStream in)
throws IOException, ClassNotFoundException
{
in.defaultReadObject();
if (options == null) {
options = new String[0];
}
}
}
/**
* Compares two activation group descriptors for content equality.
*
* @param obj the Object to compare with
* @return true if these Objects are equal; false otherwise.
* @see java.util.Hashtable
* @since 1.2
*/
public boolean equals(Object obj) {
if (obj instanceof ActivationGroupDesc) {
ActivationGroupDesc desc = (ActivationGroupDesc) obj;
return
((className == null ? desc.className == null :
className.equals(desc.className)) &&
(location == null ? desc.location == null :
location.equals(desc.location)) &&
(data == null ? desc.data == null : data.equals(desc.data)) &&
(env == null ? desc.env == null : env.equals(desc.env)) &&
(props == null ? desc.props == null :
props.equals(desc.props)));
} else {
return false;
}
}
/**
* Produce identical numbers for similar <code>ActivationGroupDesc</code>s.
* @return an integer
* @see java.util.Hashtable
*/
public int hashCode() {
// hash location, className, data, and env
// but omit props (may be expensive)
return ((location == null
? 0
: location.hashCode() << 24) ^
(env == null
? 0
: env.hashCode() << 16) ^
(className == null
? 0
: className.hashCode() << 8) ^
(data == null
? 0
: data.hashCode()));
}
}

View File

@@ -0,0 +1,117 @@
/*
* Copyright (c) 1997, 2013, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Oracle designates this
* particular file as subject to the "Classpath" exception as provided
* by Oracle in the LICENSE file that accompanied this code.
*
* This code 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
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*/
package java.rmi.activation;
import java.rmi.server.UID;
/**
* The identifier for a registered activation group serves several
* purposes: <ul>
* <li>identifies the group uniquely within the activation system, and
* <li>contains a reference to the group's activation system so that the
* group can contact its activation system when necessary.</ul><p>
*
* The <code>ActivationGroupID</code> is returned from the call to
* <code>ActivationSystem.registerGroup</code> and is used to identify
* the group within the activation system. This group id is passed
* as one of the arguments to the activation group's special constructor
* when an activation group is created/recreated.
*
* @author Ann Wollrath
* @see ActivationGroup
* @see ActivationGroupDesc
* @since 1.2
*/
public class ActivationGroupID implements java.io.Serializable {
/**
* @serial The group's activation system.
*/
private ActivationSystem system;
/**
* @serial The group's unique id.
*/
private UID uid = new UID();
/** indicate compatibility with the Java 2 SDK v1.2 version of class */
private static final long serialVersionUID = -1648432278909740833L;
/**
* Constructs a unique group id.
*
* @param system the group's activation system
* @throws UnsupportedOperationException if and only if activation is
* not supported by this implementation
* @since 1.2
*/
public ActivationGroupID(ActivationSystem system) {
this.system = system;
}
/**
* Returns the group's activation system.
* @return the group's activation system
* @since 1.2
*/
public ActivationSystem getSystem() {
return system;
}
/**
* Returns a hashcode for the group's identifier. Two group
* identifiers that refer to the same remote group will have the
* same hash code.
*
* @see java.util.Hashtable
* @since 1.2
*/
public int hashCode() {
return uid.hashCode();
}
/**
* Compares two group identifiers for content equality.
* Returns true if both of the following conditions are true:
* 1) the unique identifiers are equivalent (by content), and
* 2) the activation system specified in each
* refers to the same remote object.
*
* @param obj the Object to compare with
* @return true if these Objects are equal; false otherwise.
* @see java.util.Hashtable
* @since 1.2
*/
public boolean equals(Object obj) {
if (this == obj) {
return true;
} else if (obj instanceof ActivationGroupID) {
ActivationGroupID id = (ActivationGroupID)obj;
return (uid.equals(id.uid) && system.equals(id.system));
} else {
return false;
}
}
}

View File

@@ -0,0 +1,312 @@
/*
* Copyright (c) 1997, 2017, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Oracle designates this
* particular file as subject to the "Classpath" exception as provided
* by Oracle in the LICENSE file that accompanied this code.
*
* This code 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
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*/
package java.rmi.activation;
import java.io.IOException;
import java.io.InvalidObjectException;
import java.io.ObjectInputStream;
import java.io.ObjectOutputStream;
import java.io.Serializable;
import java.lang.reflect.InvocationHandler;
import java.lang.reflect.Proxy;
import java.rmi.MarshalledObject;
import java.rmi.Remote;
import java.rmi.RemoteException;
import java.rmi.UnmarshalException;
import java.rmi.server.RemoteObject;
import java.rmi.server.RemoteObjectInvocationHandler;
import java.rmi.server.RemoteRef;
import java.rmi.server.UID;
import java.security.AccessControlContext;
import java.security.AccessController;
import java.security.Permissions;
import java.security.PrivilegedActionException;
import java.security.PrivilegedExceptionAction;
import java.security.ProtectionDomain;
/**
* Activation makes use of special identifiers to denote remote
* objects that can be activated over time. An activation identifier
* (an instance of the class <code>ActivationID</code>) contains several
* pieces of information needed for activating an object:
* <ul>
* <li> a remote reference to the object's activator (a {@link
* java.rmi.server.RemoteRef RemoteRef}
* instance), and
* <li> a unique identifier (a {@link java.rmi.server.UID UID}
* instance) for the object. </ul> <p>
*
* An activation identifier for an object can be obtained by registering
* an object with the activation system. Registration is accomplished
* in a few ways: <ul>
* <li>via the <code>Activatable.register</code> method
* <li>via the first <code>Activatable</code> constructor (that takes
* three arguments and both registers and exports the object, and
* <li>via the first <code>Activatable.exportObject</code> method
* that takes the activation descriptor, object and port as arguments;
* this method both registers and exports the object. </ul>
*
* @author Ann Wollrath
* @see Activatable
* @since 1.2
*/
public class ActivationID implements Serializable {
/**
* the object's activator
*/
private transient Activator activator;
/**
* the object's unique id
*/
private transient UID uid = new UID();
/** indicate compatibility with the Java 2 SDK v1.2 version of class */
private static final long serialVersionUID = -4608673054848209235L;
/** an AccessControlContext with no permissions */
private static final AccessControlContext NOPERMS_ACC;
static {
Permissions perms = new Permissions();
ProtectionDomain[] pd = { new ProtectionDomain(null, perms) };
NOPERMS_ACC = new AccessControlContext(pd);
}
/**
* The constructor for <code>ActivationID</code> takes a single
* argument, activator, that specifies a remote reference to the
* activator responsible for activating the object associated with
* this identifier. An instance of <code>ActivationID</code> is globally
* unique.
*
* @param activator reference to the activator responsible for
* activating the object
* @throws UnsupportedOperationException if and only if activation is
* not supported by this implementation
* @since 1.2
*/
public ActivationID(Activator activator) {
this.activator = activator;
}
/**
* Activate the object for this id.
*
* @param force if true, forces the activator to contact the group
* when activating the object (instead of returning a cached reference);
* if false, returning a cached value is acceptable.
* @return the reference to the active remote object
* @exception ActivationException if activation fails
* @exception UnknownObjectException if the object is unknown
* @exception RemoteException if remote call fails
* @since 1.2
*/
public Remote activate(boolean force)
throws ActivationException, UnknownObjectException, RemoteException
{
try {
MarshalledObject<? extends Remote> mobj =
activator.activate(this, force);
return AccessController.doPrivileged(
new PrivilegedExceptionAction<Remote>() {
public Remote run() throws IOException, ClassNotFoundException {
return mobj.get();
}
}, NOPERMS_ACC);
} catch (PrivilegedActionException pae) {
Exception ex = pae.getException();
if (ex instanceof RemoteException) {
throw (RemoteException) ex;
} else {
throw new UnmarshalException("activation failed", ex);
}
}
}
/**
* Returns a hashcode for the activation id. Two identifiers that
* refer to the same remote object will have the same hash code.
*
* @see java.util.Hashtable
* @since 1.2
*/
public int hashCode() {
return uid.hashCode();
}
/**
* Compares two activation ids for content equality.
* Returns true if both of the following conditions are true:
* 1) the unique identifiers equivalent (by content), and
* 2) the activator specified in each identifier
* refers to the same remote object.
*
* @param obj the Object to compare with
* @return true if these Objects are equal; false otherwise.
* @see java.util.Hashtable
* @since 1.2
*/
public boolean equals(Object obj) {
if (obj instanceof ActivationID) {
ActivationID id = (ActivationID) obj;
return (uid.equals(id.uid) && activator.equals(id.activator));
} else {
return false;
}
}
/**
* <code>writeObject</code> for custom serialization.
*
* <p>This method writes this object's serialized form for
* this class as follows:
*
* <p>The <code>writeObject</code> method is invoked on
* <code>out</code> passing this object's unique identifier
* (a {@link java.rmi.server.UID UID} instance) as the argument.
*
* <p>Next, the {@link
* java.rmi.server.RemoteRef#getRefClass(java.io.ObjectOutput)
* getRefClass} method is invoked on the activator's
* <code>RemoteRef</code> instance to obtain its external ref
* type name. Next, the <code>writeUTF</code> method is
* invoked on <code>out</code> with the value returned by
* <code>getRefClass</code>, and then the
* <code>writeExternal</code> method is invoked on the
* <code>RemoteRef</code> instance passing <code>out</code>
* as the argument.
*
* @serialData The serialized data for this class comprises a
* <code>java.rmi.server.UID</code> (written with
* <code>ObjectOutput.writeObject</code>) followed by the
* external ref type name of the activator's
* <code>RemoteRef</code> instance (a string written with
* <code>ObjectOutput.writeUTF</code>), followed by the
* external form of the <code>RemoteRef</code> instance as
* written by its <code>writeExternal</code> method.
*
* <p>The external ref type name of the
* <code>RemoteRef</Code> instance is
* determined using the definitions of external ref type
* names specified in the {@link java.rmi.server.RemoteObject
* RemoteObject} <code>writeObject</code> method
* <b>serialData</b> specification. Similarly, the data
* written by the <code>writeExternal</code> method and read
* by the <code>readExternal</code> method of
* <code>RemoteRef</code> implementation classes
* corresponding to each of the defined external ref type
* names is specified in the {@link
* java.rmi.server.RemoteObject RemoteObject}
* <code>writeObject</code> method <b>serialData</b>
* specification.
**/
private void writeObject(ObjectOutputStream out)
throws IOException, ClassNotFoundException
{
out.writeObject(uid);
RemoteRef ref;
if (activator instanceof RemoteObject) {
ref = ((RemoteObject) activator).getRef();
} else if (Proxy.isProxyClass(activator.getClass())) {
InvocationHandler handler = Proxy.getInvocationHandler(activator);
if (!(handler instanceof RemoteObjectInvocationHandler)) {
throw new InvalidObjectException(
"unexpected invocation handler");
}
ref = ((RemoteObjectInvocationHandler) handler).getRef();
} else {
throw new InvalidObjectException("unexpected activator type");
}
out.writeUTF(ref.getRefClass(out));
ref.writeExternal(out);
}
/**
* <code>readObject</code> for custom serialization.
*
* <p>This method reads this object's serialized form for this
* class as follows:
*
* <p>The <code>readObject</code> method is invoked on
* <code>in</code> to read this object's unique identifier
* (a {@link java.rmi.server.UID UID} instance).
*
* <p>Next, the <code>readUTF</code> method is invoked on
* <code>in</code> to read the external ref type name of the
* <code>RemoteRef</code> instance for this object's
* activator. Next, the <code>RemoteRef</code>
* instance is created of an implementation-specific class
* corresponding to the external ref type name (returned by
* <code>readUTF</code>), and the <code>readExternal</code>
* method is invoked on that <code>RemoteRef</code> instance
* to read the external form corresponding to the external
* ref type name.
*
* <p>Note: If the external ref type name is
* <code>"UnicastRef"</code>, <code>"UnicastServerRef"</code>,
* <code>"UnicastRef2"</code>, <code>"UnicastServerRef2"</code>,
* or <code>"ActivatableRef"</code>, a corresponding
* implementation-specific class must be found, and its
* <code>readExternal</code> method must read the serial data
* for that external ref type name as specified to be written
* in the <b>serialData</b> documentation for this class.
* If the external ref type name is any other string (of non-zero
* length), a <code>ClassNotFoundException</code> will be thrown,
* unless the implementation provides an implementation-specific
* class corresponding to that external ref type name, in which
* case the <code>RemoteRef</code> will be an instance of
* that implementation-specific class.
*/
private void readObject(ObjectInputStream in)
throws IOException, ClassNotFoundException
{
uid = (UID)in.readObject();
try {
Class<? extends RemoteRef> refClass =
Class.forName(RemoteRef.packagePrefix + "." + in.readUTF())
.asSubclass(RemoteRef.class);
RemoteRef ref = refClass.newInstance();
ref.readExternal(in);
activator = (Activator)
Proxy.newProxyInstance(null,
new Class<?>[] { Activator.class },
new RemoteObjectInvocationHandler(ref));
} catch (InstantiationException e) {
throw (IOException)
new InvalidObjectException(
"Unable to create remote reference").initCause(e);
} catch (IllegalAccessException e) {
throw (IOException)
new InvalidObjectException(
"Unable to create remote reference").initCause(e);
}
}
}

View File

@@ -0,0 +1,76 @@
/*
* Copyright (c) 1997, 2005, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Oracle designates this
* particular file as subject to the "Classpath" exception as provided
* by Oracle in the LICENSE file that accompanied this code.
*
* This code 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
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*/
package java.rmi.activation;
import java.rmi.MarshalledObject;
import java.rmi.Remote;
import java.rmi.RemoteException;
/**
* An <code>ActivationInstantiator</code> is responsible for creating
* instances of "activatable" objects. A concrete subclass of
* <code>ActivationGroup</code> implements the <code>newInstance</code>
* method to handle creating objects within the group.
*
* @author Ann Wollrath
* @see ActivationGroup
* @since 1.2
*/
public interface ActivationInstantiator extends Remote {
/**
* The activator calls an instantiator's <code>newInstance</code>
* method in order to recreate in that group an object with the
* activation identifier, <code>id</code>, and descriptor,
* <code>desc</code>. The instantiator is responsible for: <ul>
*
* <li> determining the class for the object using the descriptor's
* <code>getClassName</code> method,
*
* <li> loading the class from the code location obtained from the
* descriptor (using the <code>getLocation</code> method),
*
* <li> creating an instance of the class by invoking the special
* "activation" constructor of the object's class that takes two
* arguments: the object's <code>ActivationID</code>, and the
* <code>MarshalledObject</code> containing object specific
* initialization data, and
*
* <li> returning a MarshalledObject containing the stub for the
* remote object it created </ul>
*
* @param id the object's activation identifier
* @param desc the object's descriptor
* @return a marshalled object containing the serialized
* representation of remote object's stub
* @exception ActivationException if object activation fails
* @exception RemoteException if remote call fails
* @since 1.2
*/
public MarshalledObject<? extends Remote> newInstance(ActivationID id,
ActivationDesc desc)
throws ActivationException, RemoteException;
}

View File

@@ -0,0 +1,108 @@
/*
* Copyright (c) 1997, 2005, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Oracle designates this
* particular file as subject to the "Classpath" exception as provided
* by Oracle in the LICENSE file that accompanied this code.
*
* This code 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
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*/
package java.rmi.activation;
import java.rmi.MarshalledObject;
import java.rmi.Remote;
import java.rmi.RemoteException;
import java.rmi.activation.UnknownGroupException;
import java.rmi.activation.UnknownObjectException;
/**
* An <code>ActivationMonitor</code> is specific to an
* <code>ActivationGroup</code> and is obtained when a group is
* reported active via a call to
* <code>ActivationSystem.activeGroup</code> (this is done
* internally). An activation group is responsible for informing its
* <code>ActivationMonitor</code> when either: its objects become active or
* inactive, or the group as a whole becomes inactive.
*
* @author Ann Wollrath
* @see Activator
* @see ActivationSystem
* @see ActivationGroup
* @since 1.2
*/
public interface ActivationMonitor extends Remote {
/**
* An activation group calls its monitor's
* <code>inactiveObject</code> method when an object in its group
* becomes inactive (deactivates). An activation group discovers
* that an object (that it participated in activating) in its VM
* is no longer active, via calls to the activation group's
* <code>inactiveObject</code> method. <p>
*
* The <code>inactiveObject</code> call informs the
* <code>ActivationMonitor</code> that the remote object reference
* it holds for the object with the activation identifier,
* <code>id</code>, is no longer valid. The monitor considers the
* reference associated with <code>id</code> as a stale reference.
* Since the reference is considered stale, a subsequent
* <code>activate</code> call for the same activation identifier
* results in re-activating the remote object.<p>
*
* @param id the object's activation identifier
* @exception UnknownObjectException if object is unknown
* @exception RemoteException if remote call fails
* @since 1.2
*/
public void inactiveObject(ActivationID id)
throws UnknownObjectException, RemoteException;
/**
* Informs that an object is now active. An <code>ActivationGroup</code>
* informs its monitor if an object in its group becomes active by
* other means than being activated directly (i.e., the object
* is registered and "activated" itself).
*
* @param id the active object's id
* @param obj the marshalled form of the object's stub
* @exception UnknownObjectException if object is unknown
* @exception RemoteException if remote call fails
* @since 1.2
*/
public void activeObject(ActivationID id,
MarshalledObject<? extends Remote> obj)
throws UnknownObjectException, RemoteException;
/**
* Informs that the group is now inactive. The group will be
* recreated upon a subsequent request to activate an object
* within the group. A group becomes inactive when all objects
* in the group report that they are inactive.
*
* @param id the group's id
* @param incarnation the group's incarnation number
* @exception UnknownGroupException if group is unknown
* @exception RemoteException if remote call fails
* @since 1.2
*/
public void inactiveGroup(ActivationGroupID id,
long incarnation)
throws UnknownGroupException, RemoteException;
}

View File

@@ -0,0 +1,229 @@
/*
* Copyright (c) 1997, 2003, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Oracle designates this
* particular file as subject to the "Classpath" exception as provided
* by Oracle in the LICENSE file that accompanied this code.
*
* This code 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
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*/
package java.rmi.activation;
import java.rmi.Remote;
import java.rmi.RemoteException;
import java.rmi.activation.UnknownGroupException;
import java.rmi.activation.UnknownObjectException;
/**
* The <code>ActivationSystem</code> provides a means for registering
* groups and "activatable" objects to be activated within those groups.
* The <code>ActivationSystem</code> works closely with the
* <code>Activator</code>, which activates objects registered via the
* <code>ActivationSystem</code>, and the <code>ActivationMonitor</code>,
* which obtains information about active and inactive objects,
* and inactive groups.
*
* @author Ann Wollrath
* @see Activator
* @see ActivationMonitor
* @since 1.2
*/
public interface ActivationSystem extends Remote {
/** The port to lookup the activation system. */
public static final int SYSTEM_PORT = 1098;
/**
* The <code>registerObject</code> method is used to register an
* activation descriptor, <code>desc</code>, and obtain an
* activation identifier for a activatable remote object. The
* <code>ActivationSystem</code> creates an
* <code>ActivationID</code> (a activation identifier) for the
* object specified by the descriptor, <code>desc</code>, and
* records, in stable storage, the activation descriptor and its
* associated identifier for later use. When the <code>Activator</code>
* receives an <code>activate</code> request for a specific identifier, it
* looks up the activation descriptor (registered previously) for
* the specified identifier and uses that information to activate
* the object. <p>
*
* @param desc the object's activation descriptor
* @return the activation id that can be used to activate the object
* @exception ActivationException if registration fails (e.g., database
* update failure, etc).
* @exception UnknownGroupException if group referred to in
* <code>desc</code> is not registered with this system
* @exception RemoteException if remote call fails
* @since 1.2
*/
public ActivationID registerObject(ActivationDesc desc)
throws ActivationException, UnknownGroupException, RemoteException;
/**
* Remove the activation id and associated descriptor previously
* registered with the <code>ActivationSystem</code>; the object
* can no longer be activated via the object's activation id.
*
* @param id the object's activation id (from previous registration)
* @exception ActivationException if unregister fails (e.g., database
* update failure, etc).
* @exception UnknownObjectException if object is unknown (not registered)
* @exception RemoteException if remote call fails
* @since 1.2
*/
public void unregisterObject(ActivationID id)
throws ActivationException, UnknownObjectException, RemoteException;
/**
* Register the activation group. An activation group must be
* registered with the <code>ActivationSystem</code> before objects
* can be registered within that group.
*
* @param desc the group's descriptor
* @return an identifier for the group
* @exception ActivationException if group registration fails
* @exception RemoteException if remote call fails
* @since 1.2
*/
public ActivationGroupID registerGroup(ActivationGroupDesc desc)
throws ActivationException, RemoteException;
/**
* Callback to inform activation system that group is now
* active. This call is made internally by the
* <code>ActivationGroup.createGroup</code> method to inform
* the <code>ActivationSystem</code> that the group is now
* active.
*
* @param id the activation group's identifier
* @param group the group's instantiator
* @param incarnation the group's incarnation number
* @return monitor for activation group
* @exception UnknownGroupException if group is not registered
* @exception ActivationException if a group for the specified
* <code>id</code> is already active and that group is not equal
* to the specified <code>group</code> or that group has a different
* <code>incarnation</code> than the specified <code>group</code>
* @exception RemoteException if remote call fails
* @since 1.2
*/
public ActivationMonitor activeGroup(ActivationGroupID id,
ActivationInstantiator group,
long incarnation)
throws UnknownGroupException, ActivationException, RemoteException;
/**
* Remove the activation group. An activation group makes this call back
* to inform the activator that the group should be removed (destroyed).
* If this call completes successfully, objects can no longer be
* registered or activated within the group. All information of the
* group and its associated objects is removed from the system.
*
* @param id the activation group's identifier
* @exception ActivationException if unregister fails (e.g., database
* update failure, etc).
* @exception UnknownGroupException if group is not registered
* @exception RemoteException if remote call fails
* @since 1.2
*/
public void unregisterGroup(ActivationGroupID id)
throws ActivationException, UnknownGroupException, RemoteException;
/**
* Shutdown the activation system. Destroys all groups spawned by
* the activation daemon and exits the activation daemon.
* @exception RemoteException if failed to contact/shutdown the activation
* daemon
* @since 1.2
*/
public void shutdown() throws RemoteException;
/**
* Set the activation descriptor, <code>desc</code> for the object with
* the activation identifier, <code>id</code>. The change will take
* effect upon subsequent activation of the object.
*
* @param id the activation identifier for the activatable object
* @param desc the activation descriptor for the activatable object
* @exception UnknownGroupException the group associated with
* <code>desc</code> is not a registered group
* @exception UnknownObjectException the activation <code>id</code>
* is not registered
* @exception ActivationException for general failure (e.g., unable
* to update log)
* @exception RemoteException if remote call fails
* @return the previous value of the activation descriptor
* @see #getActivationDesc
* @since 1.2
*/
public ActivationDesc setActivationDesc(ActivationID id,
ActivationDesc desc)
throws ActivationException, UnknownObjectException,
UnknownGroupException, RemoteException;
/**
* Set the activation group descriptor, <code>desc</code> for the object
* with the activation group identifier, <code>id</code>. The change will
* take effect upon subsequent activation of the group.
*
* @param id the activation group identifier for the activation group
* @param desc the activation group descriptor for the activation group
* @exception UnknownGroupException the group associated with
* <code>id</code> is not a registered group
* @exception ActivationException for general failure (e.g., unable
* to update log)
* @exception RemoteException if remote call fails
* @return the previous value of the activation group descriptor
* @see #getActivationGroupDesc
* @since 1.2
*/
public ActivationGroupDesc setActivationGroupDesc(ActivationGroupID id,
ActivationGroupDesc desc)
throws ActivationException, UnknownGroupException, RemoteException;
/**
* Returns the activation descriptor, for the object with the activation
* identifier, <code>id</code>.
*
* @param id the activation identifier for the activatable object
* @exception UnknownObjectException if <code>id</code> is not registered
* @exception ActivationException for general failure
* @exception RemoteException if remote call fails
* @return the activation descriptor
* @see #setActivationDesc
* @since 1.2
*/
public ActivationDesc getActivationDesc(ActivationID id)
throws ActivationException, UnknownObjectException, RemoteException;
/**
* Returns the activation group descriptor, for the group
* with the activation group identifier, <code>id</code>.
*
* @param id the activation group identifier for the group
* @exception UnknownGroupException if <code>id</code> is not registered
* @exception ActivationException for general failure
* @exception RemoteException if remote call fails
* @return the activation group descriptor
* @see #setActivationGroupDesc
* @since 1.2
*/
public ActivationGroupDesc getActivationGroupDesc(ActivationGroupID id)
throws ActivationException, UnknownGroupException, RemoteException;
}

View File

@@ -0,0 +1,114 @@
/*
* Copyright (c) 1997, 2005, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Oracle designates this
* particular file as subject to the "Classpath" exception as provided
* by Oracle in the LICENSE file that accompanied this code.
*
* This code 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
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*/
package java.rmi.activation;
import java.rmi.MarshalledObject;
import java.rmi.Remote;
import java.rmi.RemoteException;
import java.rmi.activation.UnknownObjectException;
/**
* The <code>Activator</code> facilitates remote object activation. A
* "faulting" remote reference calls the activator's
* <code>activate</code> method to obtain a "live" reference to a
* "activatable" remote object. Upon receiving a request for activation,
* the activator looks up the activation descriptor for the activation
* identifier, <code>id</code>, determines the group in which the
* object should be activated initiates object re-creation via the
* group's <code>ActivationInstantiator</code> (via a call to the
* <code>newInstance</code> method). The activator initiates the
* execution of activation groups as necessary. For example, if an
* activation group for a specific group identifier is not already
* executing, the activator initiates the execution of a VM for the
* group. <p>
*
* The <code>Activator</code> works closely with
* <code>ActivationSystem</code>, which provides a means for registering
* groups and objects within those groups, and <code>ActivationMonitor</code>,
* which recives information about active and inactive objects and inactive
* groups. <p>
*
* The activator is responsible for monitoring and detecting when
* activation groups fail so that it can remove stale remote references
* to groups and active object's within those groups.<p>
*
* @author Ann Wollrath
* @see ActivationInstantiator
* @see ActivationGroupDesc
* @see ActivationGroupID
* @since 1.2
*/
public interface Activator extends Remote {
/**
* Activate the object associated with the activation identifier,
* <code>id</code>. If the activator knows the object to be active
* already, and <code>force</code> is false , the stub with a
* "live" reference is returned immediately to the caller;
* otherwise, if the activator does not know that corresponding
* the remote object is active, the activator uses the activation
* descriptor information (previously registered) to determine the
* group (VM) in which the object should be activated. If an
* <code>ActivationInstantiator</code> corresponding to the
* object's group descriptor already exists, the activator invokes
* the activation group's <code>newInstance</code> method passing
* it the object's id and descriptor. <p>
*
* If the activation group for the object's group descriptor does
* not yet exist, the activator starts an
* <code>ActivationInstantiator</code> executing (by spawning a
* child process, for example). When the activator receives the
* activation group's call back (via the
* <code>ActivationSystem</code>'s <code>activeGroup</code>
* method) specifying the activation group's reference, the
* activator can then invoke that activation instantiator's
* <code>newInstance</code> method to forward each pending
* activation request to the activation group and return the
* result (a marshalled remote object reference, a stub) to the
* caller.<p>
*
* Note that the activator receives a "marshalled" object instead of a
* Remote object so that the activator does not need to load the
* code for that object, or participate in distributed garbage
* collection for that object. If the activator kept a strong
* reference to the remote object, the activator would then
* prevent the object from being garbage collected under the
* normal distributed garbage collection mechanism. <p>
*
* @param id the activation identifier for the object being activated
* @param force if true, the activator contacts the group to obtain
* the remote object's reference; if false, returning the cached value
* is allowed.
* @return the remote object (a stub) in a marshalled form
* @exception ActivationException if object activation fails
* @exception UnknownObjectException if object is unknown (not registered)
* @exception RemoteException if remote call fails
* @since 1.2
*/
public MarshalledObject<? extends Remote> activate(ActivationID id,
boolean force)
throws ActivationException, UnknownObjectException, RemoteException;
}

View File

@@ -0,0 +1,60 @@
/*
* Copyright (c) 1997, 1999, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Oracle designates this
* particular file as subject to the "Classpath" exception as provided
* by Oracle in the LICENSE file that accompanied this code.
*
* This code 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
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*/
package java.rmi.activation;
/**
* An <code>UnknownGroupException</code> is thrown by methods of classes and
* interfaces in the <code>java.rmi.activation</code> package when the
* <code>ActivationGroupID</code> parameter to the method is determined to be
* invalid, i.e., not known by the <code>ActivationSystem</code>. An
* <code>UnknownGroupException</code> is also thrown if the
* <code>ActivationGroupID</code> in an <code>ActivationDesc</code> refers to
* a group that is not registered with the <code>ActivationSystem</code>
*
* @author Ann Wollrath
* @since 1.2
* @see java.rmi.activation.Activatable
* @see java.rmi.activation.ActivationGroup
* @see java.rmi.activation.ActivationGroupID
* @see java.rmi.activation.ActivationMonitor
* @see java.rmi.activation.ActivationSystem
*/
public class UnknownGroupException extends ActivationException {
/** indicate compatibility with the Java 2 SDK v1.2 version of class */
private static final long serialVersionUID = 7056094974750002460L;
/**
* Constructs an <code>UnknownGroupException</code> with the specified
* detail message.
*
* @param s the detail message
* @since 1.2
*/
public UnknownGroupException(String s) {
super(s);
}
}

View File

@@ -0,0 +1,62 @@
/*
* Copyright (c) 1997, 1999, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Oracle designates this
* particular file as subject to the "Classpath" exception as provided
* by Oracle in the LICENSE file that accompanied this code.
*
* This code 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
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*/
package java.rmi.activation;
/**
* An <code>UnknownObjectException</code> is thrown by methods of classes and
* interfaces in the <code>java.rmi.activation</code> package when the
* <code>ActivationID</code> parameter to the method is determined to be
* invalid. An <code>ActivationID</code> is invalid if it is not currently
* known by the <code>ActivationSystem</code>. An <code>ActivationID</code>
* is obtained by the <code>ActivationSystem.registerObject</code> method.
* An <code>ActivationID</code> is also obtained during the
* <code>Activatable.register</code> call.
*
* @author Ann Wollrath
* @since 1.2
* @see java.rmi.activation.Activatable
* @see java.rmi.activation.ActivationGroup
* @see java.rmi.activation.ActivationID
* @see java.rmi.activation.ActivationMonitor
* @see java.rmi.activation.ActivationSystem
* @see java.rmi.activation.Activator
*/
public class UnknownObjectException extends ActivationException {
/** indicate compatibility with the Java 2 SDK v1.2 version of class */
private static final long serialVersionUID = 3425547551622251430L;
/**
* Constructs an <code>UnknownObjectException</code> with the specified
* detail message.
*
* @param s the detail message
* @since 1.2
*/
public UnknownObjectException(String s) {
super(s);
}
}