| /* |
| * Copyright (c) 2002, 2015, 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 com.sun.corba.se.impl.orb; |
| |
| import java.applet.Applet; |
| |
| import java.io.IOException; |
| |
| import java.lang.reflect.Constructor; |
| import java.lang.reflect.Field; |
| import java.lang.reflect.Modifier; |
| import java.lang.reflect.InvocationTargetException; |
| |
| import java.util.Set; |
| import java.util.HashSet; |
| import java.util.ArrayList; |
| import java.util.Iterator; |
| import java.util.Properties; |
| import java.util.Vector; |
| import java.util.Hashtable; |
| import java.util.Map; |
| import java.util.HashMap; |
| import java.util.LinkedList; |
| import java.util.Collection; |
| import java.util.Collections; |
| import java.util.StringTokenizer; |
| import java.util.Enumeration; |
| import java.util.WeakHashMap; |
| |
| import java.net.InetAddress; |
| |
| import java.security.PrivilegedAction; |
| import java.security.AccessController; |
| |
| import javax.rmi.CORBA.Util; |
| import javax.rmi.CORBA.ValueHandler; |
| |
| import org.omg.CORBA.Context; |
| import org.omg.CORBA.ContextList; |
| import org.omg.CORBA.Environment; |
| import org.omg.CORBA.ExceptionList; |
| import org.omg.CORBA.ORBPackage.InvalidName; |
| import org.omg.CORBA.NVList; |
| import org.omg.CORBA.TCKind; |
| import org.omg.CORBA.NamedValue; |
| import org.omg.CORBA.Request; |
| import org.omg.CORBA.SystemException; |
| import org.omg.CORBA.CompletionStatus; |
| import org.omg.CORBA.TypeCode; |
| import org.omg.CORBA.Any; |
| import org.omg.CORBA.StructMember; |
| import org.omg.CORBA.UnionMember; |
| import org.omg.CORBA.ValueMember; |
| import org.omg.CORBA.BAD_PARAM; |
| import org.omg.CORBA.MARSHAL; |
| |
| import org.omg.CORBA.portable.ValueFactory; |
| |
| import org.omg.CORBA.ORBPackage.InvalidName; |
| |
| import com.sun.org.omg.SendingContext.CodeBase; |
| |
| import com.sun.corba.se.pept.broker.Broker; |
| import com.sun.corba.se.pept.protocol.ClientInvocationInfo; |
| import com.sun.corba.se.pept.transport.ContactInfo; |
| import com.sun.corba.se.pept.transport.ConnectionCache; |
| import com.sun.corba.se.pept.transport.TransportManager; |
| |
| import com.sun.corba.se.spi.ior.IOR; |
| import com.sun.corba.se.spi.ior.IdentifiableFactoryFinder; |
| import com.sun.corba.se.spi.ior.TaggedComponentFactoryFinder; |
| import com.sun.corba.se.spi.ior.IORFactories; |
| import com.sun.corba.se.spi.ior.ObjectKey; |
| import com.sun.corba.se.spi.ior.ObjectKeyFactory; |
| import com.sun.corba.se.spi.ior.iiop.IIOPFactories; |
| import com.sun.corba.se.spi.ior.iiop.GIOPVersion; |
| import com.sun.corba.se.spi.oa.OAInvocationInfo; |
| import com.sun.corba.se.spi.oa.ObjectAdapterFactory; |
| import com.sun.corba.se.spi.orb.DataCollector; |
| import com.sun.corba.se.spi.orb.Operation; |
| import com.sun.corba.se.spi.orb.ORBData; |
| import com.sun.corba.se.spi.orb.ORBConfigurator; |
| import com.sun.corba.se.spi.orb.ParserImplBase; |
| import com.sun.corba.se.spi.orb.PropertyParser; |
| import com.sun.corba.se.spi.orb.OperationFactory; |
| import com.sun.corba.se.spi.orb.ORBVersion; |
| import com.sun.corba.se.spi.orb.ORBVersionFactory; |
| import com.sun.corba.se.spi.orbutil.closure.ClosureFactory; |
| import com.sun.corba.se.spi.orbutil.threadpool.ThreadPoolManager; |
| import com.sun.corba.se.spi.protocol.ClientDelegateFactory; |
| import com.sun.corba.se.spi.protocol.RequestDispatcherRegistry; |
| import com.sun.corba.se.spi.protocol.CorbaServerRequestDispatcher; |
| import com.sun.corba.se.spi.protocol.RequestDispatcherDefault; |
| import com.sun.corba.se.spi.protocol.PIHandler; |
| import com.sun.corba.se.spi.protocol.CorbaMessageMediator; |
| import com.sun.corba.se.spi.protocol.ForwardException; |
| import com.sun.corba.se.spi.resolver.Resolver; |
| import com.sun.corba.se.spi.resolver.LocalResolver; |
| import com.sun.corba.se.spi.orb.StringPair; |
| import com.sun.corba.se.spi.orb.StringPair; |
| import com.sun.corba.se.spi.transport.CorbaContactInfoListFactory; |
| import com.sun.corba.se.spi.transport.CorbaTransportManager; |
| import com.sun.corba.se.spi.legacy.connection.LegacyServerSocketManager; |
| import com.sun.corba.se.spi.copyobject.CopierManager; |
| import com.sun.corba.se.spi.presentation.rmi.PresentationDefaults; |
| import com.sun.corba.se.spi.presentation.rmi.PresentationManager; |
| import com.sun.corba.se.spi.presentation.rmi.StubAdapter; |
| import com.sun.corba.se.spi.servicecontext.ServiceContextRegistry; |
| |
| import com.sun.corba.se.impl.corba.TypeCodeFactory; |
| import com.sun.corba.se.impl.corba.TypeCodeImpl; |
| import com.sun.corba.se.impl.corba.NVListImpl; |
| import com.sun.corba.se.impl.corba.ExceptionListImpl; |
| import com.sun.corba.se.impl.corba.ContextListImpl; |
| import com.sun.corba.se.impl.corba.NamedValueImpl; |
| import com.sun.corba.se.impl.corba.EnvironmentImpl; |
| import com.sun.corba.se.impl.corba.AsynchInvoke; |
| import com.sun.corba.se.impl.corba.AnyImpl; |
| import com.sun.corba.se.impl.corba.RequestImpl; |
| import com.sun.corba.se.impl.dynamicany.DynAnyFactoryImpl; |
| import com.sun.corba.se.impl.encoding.EncapsOutputStream; |
| import com.sun.corba.se.impl.encoding.CachedCodeBase; |
| import com.sun.corba.se.impl.interceptors.PIHandlerImpl; |
| import com.sun.corba.se.impl.interceptors.PINoOpHandlerImpl; |
| import com.sun.corba.se.impl.ior.TaggedComponentFactoryFinderImpl; |
| import com.sun.corba.se.impl.ior.TaggedProfileFactoryFinderImpl; |
| import com.sun.corba.se.impl.ior.TaggedProfileTemplateFactoryFinderImpl; |
| import com.sun.corba.se.impl.oa.toa.TOAFactory; |
| import com.sun.corba.se.impl.oa.poa.BadServerIdHandler; |
| import com.sun.corba.se.impl.oa.poa.DelegateImpl; |
| import com.sun.corba.se.impl.oa.poa.POAFactory; |
| import com.sun.corba.se.impl.orbutil.ORBConstants; |
| import com.sun.corba.se.impl.orbutil.ORBUtility; |
| import com.sun.corba.se.impl.orbutil.StackImpl; |
| import com.sun.corba.se.impl.orbutil.threadpool.ThreadPoolImpl; |
| import com.sun.corba.se.impl.orbutil.threadpool.ThreadPoolManagerImpl; |
| import com.sun.corba.se.impl.protocol.RequestDispatcherRegistryImpl; |
| import com.sun.corba.se.impl.protocol.CorbaInvocationInfo; |
| import com.sun.corba.se.impl.transport.CorbaTransportManagerImpl; |
| import com.sun.corba.se.impl.legacy.connection.LegacyServerSocketManagerImpl; |
| import com.sun.corba.se.impl.util.Utility; |
| import com.sun.corba.se.impl.logging.ORBUtilSystemException; |
| import com.sun.corba.se.impl.copyobject.CopierManagerImpl; |
| import com.sun.corba.se.impl.presentation.rmi.PresentationManagerImpl; |
| |
| /** |
| * The JavaIDL ORB implementation. |
| */ |
| public class ORBImpl extends com.sun.corba.se.spi.orb.ORB |
| { |
| protected TransportManager transportManager; |
| protected LegacyServerSocketManager legacyServerSocketManager; |
| |
| private ThreadLocal OAInvocationInfoStack ; |
| |
| private ThreadLocal clientInvocationInfoStack ; |
| |
| // pure java orb, caching the servant IOR per ORB |
| private static IOR codeBaseIOR ; |
| |
| // Vector holding deferred Requests |
| private Vector dynamicRequests ; |
| private SynchVariable svResponseReceived ; |
| |
| private java.lang.Object runObj = new java.lang.Object(); |
| private java.lang.Object shutdownObj = new java.lang.Object(); |
| private java.lang.Object waitForCompletionObj = new java.lang.Object(); |
| private static final byte STATUS_OPERATING = 1; |
| private static final byte STATUS_SHUTTING_DOWN = 2; |
| private static final byte STATUS_SHUTDOWN = 3; |
| private static final byte STATUS_DESTROYED = 4; |
| private byte status = STATUS_OPERATING; |
| |
| // XXX Should we move invocation tracking to the first level server dispatcher? |
| private java.lang.Object invocationObj = new java.lang.Object(); |
| private int numInvocations = 0; |
| |
| // thread local variable to store a boolean to detect deadlock in |
| // ORB.shutdown(true). |
| private ThreadLocal isProcessingInvocation = new ThreadLocal () { |
| protected java.lang.Object initialValue() { |
| return Boolean.FALSE; |
| } |
| }; |
| |
| // This map is caching TypeCodes created for a certain class (key) |
| // and is used in Util.writeAny() |
| private Map typeCodeForClassMap ; |
| |
| // Cache to hold ValueFactories (Helper classes) keyed on repository ids |
| private Hashtable valueFactoryCache = new Hashtable(); |
| |
| // thread local variable to store the current ORB version. |
| // default ORB version is the version of ORB with correct Rep-id |
| // changes |
| private ThreadLocal orbVersionThreadLocal ; |
| |
| private RequestDispatcherRegistry requestDispatcherRegistry ; |
| |
| private CopierManager copierManager ; |
| |
| private int transientServerId ; |
| |
| private ServiceContextRegistry serviceContextRegistry ; |
| |
| // Needed here to implement connect/disconnect |
| private TOAFactory toaFactory ; |
| |
| // Needed here for set_delegate |
| private POAFactory poaFactory ; |
| |
| // The interceptor handler, which provides portable interceptor services for |
| // subcontracts and object adapters. |
| private PIHandler pihandler ; |
| |
| private ORBData configData ; |
| |
| private BadServerIdHandler badServerIdHandler ; |
| |
| private ClientDelegateFactory clientDelegateFactory ; |
| |
| private CorbaContactInfoListFactory corbaContactInfoListFactory ; |
| |
| // All access to resolver, localResolver, and urlOperation must be protected using |
| // resolverLock. Do not hold the ORBImpl lock while accessing |
| // resolver, or deadlocks may occur. |
| // Note that we now have separate locks for each resolver type. This is due |
| // to bug 6980681 and 6238477, which was caused by a deadlock while resolving a |
| // corbaname: URL that contained a reference to the same ORB as the |
| // ORB making the call to string_to_object. This caused a deadlock between the |
| // client thread holding the single lock for access to the urlOperation, |
| // and the server thread handling the client is_a request waiting on the |
| // same lock to access the localResolver. |
| |
| |
| // Used for resolver_initial_references and list_initial_services |
| private Resolver resolver ; |
| |
| // Used for register_initial_references |
| private LocalResolver localResolver ; |
| |
| // Converts strings to object references for resolvers and string_to_object |
| private Operation urlOperation ; |
| private final Object urlOperationLock = new java.lang.Object() ; |
| |
| private CorbaServerRequestDispatcher insNamingDelegate ; |
| |
| // resolverLock must be used for all access to either resolver or |
| // localResolver, since it is possible for the resolver to indirectly |
| // refer to the localResolver. Also used to protect access to |
| // insNamingDelegate. |
| private final Object resolverLock = new Object() ; |
| |
| private TaggedComponentFactoryFinder taggedComponentFactoryFinder ; |
| |
| private IdentifiableFactoryFinder taggedProfileFactoryFinder ; |
| |
| private IdentifiableFactoryFinder taggedProfileTemplateFactoryFinder ; |
| |
| private ObjectKeyFactory objectKeyFactory ; |
| |
| private boolean orbOwnsThreadPoolManager = false ; |
| |
| private ThreadPoolManager threadpoolMgr; |
| |
| private void dprint( String msg ) |
| { |
| ORBUtility.dprint( this, msg ) ; |
| } |
| |
| //////////////////////////////////////////////////// |
| // |
| // NOTE: |
| // |
| // Methods that are synchronized MUST stay synchronized. |
| // |
| // Methods that are NOT synchronized must stay that way to avoid deadlock. |
| // |
| // |
| // REVISIT: |
| // |
| // checkShutDownState - lock on different object - and normalize usage. |
| // starting/FinishDispatch and Shutdown |
| // |
| |
| public ORBData getORBData() |
| { |
| return configData ; |
| } |
| |
| public PIHandler getPIHandler() |
| { |
| return pihandler ; |
| } |
| |
| /** |
| * Create a new ORB. Should be followed by the appropriate |
| * set_parameters() call. |
| */ |
| public ORBImpl() |
| { |
| // All initialization is done through set_parameters(). |
| } |
| |
| public ORBVersion getORBVersion() |
| { |
| synchronized (this) { |
| checkShutdownState(); |
| } |
| return (ORBVersion)(orbVersionThreadLocal.get()) ; |
| } |
| |
| public void setORBVersion(ORBVersion verObj) |
| { |
| synchronized (this) { |
| checkShutdownState(); |
| } |
| orbVersionThreadLocal.set(verObj); |
| } |
| |
| /**************************************************************************** |
| * The following methods are ORB initialization |
| ****************************************************************************/ |
| |
| // preInit initializes all non-pluggable ORB data that is independent |
| // of the property parsing. |
| private void preInit( String[] params, Properties props ) |
| { |
| // Before ORBConfiguration we need to set a PINoOpHandlerImpl, |
| // because PersisentServer Initialization inside configurator will |
| // invoke orb.resolve_initial_references( ) which will result in a |
| // check on piHandler to invoke Interceptors. We do not want any |
| // Interceptors to be invoked before the complete ORB initialization. |
| // piHandler will be replaced by a real PIHandler implementation at the |
| // end of this method. |
| pihandler = new PINoOpHandlerImpl( ); |
| |
| // This is the unique id of this server (JVM). Multiple incarnations |
| // of this server will get different ids. |
| // Compute transientServerId = milliseconds since Jan 1, 1970 |
| // Note: transientServerId will wrap in about 2^32 / 86400000 = 49.7 days. |
| // If two ORBS are started at the same time then there is a possibility |
| // of having the same transientServerId. This may result in collision |
| // and may be a problem in ior.isLocal() check to see if the object |
| // belongs to the current ORB. This problem is taken care of by checking |
| // to see if the IOR port matches ORB server port in legacyIsLocalServerPort() |
| // method. |
| // |
| // XXX need to move server ID to a string for CORBA 3.0. At that point, |
| // make this more unique (possibly use java.rmi.server.UID). |
| transientServerId = (int)System.currentTimeMillis(); |
| |
| orbVersionThreadLocal = new ThreadLocal () { |
| protected java.lang.Object initialValue() { |
| // set default to version of the ORB with correct Rep-ids |
| return ORBVersionFactory.getORBVersion() ; |
| } |
| }; |
| |
| |
| requestDispatcherRegistry = new RequestDispatcherRegistryImpl( |
| this, ORBConstants.DEFAULT_SCID); |
| copierManager = new CopierManagerImpl( this ) ; |
| |
| taggedComponentFactoryFinder = |
| new TaggedComponentFactoryFinderImpl(this) ; |
| taggedProfileFactoryFinder = |
| new TaggedProfileFactoryFinderImpl(this) ; |
| taggedProfileTemplateFactoryFinder = |
| new TaggedProfileTemplateFactoryFinderImpl(this) ; |
| |
| dynamicRequests = new Vector(); |
| svResponseReceived = new SynchVariable(); |
| |
| OAInvocationInfoStack = |
| new ThreadLocal () { |
| protected java.lang.Object initialValue() |
| { |
| return new StackImpl(); |
| } |
| }; |
| |
| clientInvocationInfoStack = |
| new ThreadLocal() { |
| protected java.lang.Object initialValue() { |
| return new StackImpl(); |
| } |
| }; |
| |
| serviceContextRegistry = new ServiceContextRegistry( this ) ; |
| } |
| |
| protected void setDebugFlags( String[] args ) |
| { |
| for (int ctr=0; ctr<args.length; ctr++ ) { |
| String token = args[ctr] ; |
| |
| // If there is a public boolean data member in this class |
| // named token + "DebugFlag", set it to true. |
| try { |
| Field fld = this.getClass().getField( token + "DebugFlag" ) ; |
| int mod = fld.getModifiers() ; |
| if (Modifier.isPublic( mod ) && !Modifier.isStatic( mod )) |
| if (fld.getType() == boolean.class) |
| fld.setBoolean( this, true ) ; |
| } catch (Exception exc) { |
| // ignore it XXX log this as info |
| } |
| } |
| } |
| |
| // Class that defines a parser that gets the name of the |
| // ORBConfigurator class. |
| private static class ConfigParser extends ParserImplBase { |
| // The default here is the ORBConfiguratorImpl that we define, |
| // but this can be replaced. |
| public Class configurator = ORBConfiguratorImpl.class ; |
| |
| public PropertyParser makeParser() |
| { |
| PropertyParser parser = new PropertyParser() ; |
| parser.add( ORBConstants.SUN_PREFIX + "ORBConfigurator", |
| OperationFactory.classAction(), "configurator" ) ; |
| return parser ; |
| } |
| } |
| |
| private void postInit( String[] params, DataCollector dataCollector ) |
| { |
| // First, create the standard ORB config data. |
| // This must be initialized before the ORBConfigurator |
| // is executed. |
| configData = new ORBDataParserImpl( this, dataCollector) ; |
| |
| // Set the debug flags early so they can be used by other |
| // parts of the initialization. |
| setDebugFlags( configData.getORBDebugFlags() ) ; |
| |
| // REVISIT: this should go away after more transport init cleanup |
| // and going to ORT based ORBD. |
| getTransportManager(); |
| getLegacyServerSocketManager(); |
| |
| // Create a parser to get the configured ORBConfigurator. |
| ConfigParser parser = new ConfigParser() ; |
| parser.init( dataCollector ) ; |
| |
| ORBConfigurator configurator = null ; |
| try { |
| configurator = |
| (ORBConfigurator)(parser.configurator.newInstance()) ; |
| } catch (Exception iexc) { |
| throw wrapper.badOrbConfigurator( iexc, parser.configurator.getName() ) ; |
| } |
| |
| // Finally, run the configurator. Note that the default implementation allows |
| // other configurators with their own parsers to run, |
| // using the same DataCollector. |
| try { |
| configurator.configure( dataCollector, this ) ; |
| } catch (Exception exc) { |
| throw wrapper.orbConfiguratorError( exc ) ; |
| } |
| |
| // Last of all, create the PIHandler and run the ORB initializers. |
| pihandler = new PIHandlerImpl( this, params) ; |
| pihandler.initialize() ; |
| |
| // Initialize the thread manager pool and byte buffer pool |
| // so they may be initialized & accessed without synchronization |
| getThreadPoolManager(); |
| |
| super.getByteBufferPool(); |
| } |
| |
| private synchronized POAFactory getPOAFactory() |
| { |
| if (poaFactory == null) { |
| poaFactory = (POAFactory)requestDispatcherRegistry.getObjectAdapterFactory( |
| ORBConstants.TRANSIENT_SCID ) ; |
| } |
| |
| return poaFactory ; |
| } |
| |
| private synchronized TOAFactory getTOAFactory() |
| { |
| if (toaFactory == null) { |
| toaFactory = (TOAFactory)requestDispatcherRegistry.getObjectAdapterFactory( |
| ORBConstants.TOA_SCID ) ; |
| } |
| |
| return toaFactory ; |
| } |
| |
| public void set_parameters( Properties props ) |
| { |
| synchronized (this) { |
| checkShutdownState(); |
| } |
| preInit( null, props ) ; |
| DataCollector dataCollector = |
| DataCollectorFactory.create( props, getLocalHostName() ) ; |
| postInit( null, dataCollector ) ; |
| } |
| |
| protected void set_parameters(Applet app, Properties props) |
| { |
| preInit( null, props ) ; |
| DataCollector dataCollector = |
| DataCollectorFactory.create( app, props, getLocalHostName() ) ; |
| postInit( null, dataCollector ) ; |
| } |
| |
| protected void set_parameters (String[] params, Properties props) |
| { |
| preInit( params, props ) ; |
| DataCollector dataCollector = |
| DataCollectorFactory.create( params, props, getLocalHostName() ) ; |
| postInit( params, dataCollector ) ; |
| } |
| |
| /**************************************************************************** |
| * The following methods are standard public CORBA ORB APIs |
| ****************************************************************************/ |
| |
| public synchronized org.omg.CORBA.portable.OutputStream create_output_stream() |
| { |
| checkShutdownState(); |
| return sun.corba.OutputStreamFactory.newEncapsOutputStream(this); |
| } |
| |
| /** |
| * Get a Current pseudo-object. |
| * The Current interface is used to manage thread-specific |
| * information for use by the transactions, security and other |
| * services. This method is deprecated, |
| * and replaced by ORB.resolve_initial_references("NameOfCurrentObject"); |
| * |
| * @return a Current pseudo-object. |
| * @deprecated |
| */ |
| public synchronized org.omg.CORBA.Current get_current() |
| { |
| checkShutdownState(); |
| |
| /* _REVISIT_ |
| The implementation of get_current is not clear. How would |
| ORB know whether the caller wants a Current for transactions |
| or security ?? Or is it assumed that there is just one |
| implementation for both ? If Current is thread-specific, |
| then it should not be instantiated; so where does the |
| ORB get a Current ? |
| |
| This should probably be deprecated. */ |
| |
| throw wrapper.genericNoImpl() ; |
| } |
| |
| /** |
| * Create an NVList |
| * |
| * @param count size of list to create |
| * @return NVList created |
| * |
| * @see NVList |
| */ |
| public synchronized NVList create_list(int count) |
| { |
| checkShutdownState(); |
| return new NVListImpl(this, count); |
| } |
| |
| /** |
| * Create an NVList corresponding to an OperationDef |
| * |
| * @param oper operation def to use to create list |
| * @return NVList created |
| * |
| * @see NVList |
| */ |
| public synchronized NVList create_operation_list(org.omg.CORBA.Object oper) |
| { |
| checkShutdownState(); |
| throw wrapper.genericNoImpl() ; |
| } |
| |
| /** |
| * Create a NamedValue |
| * |
| * @return NamedValue created |
| */ |
| public synchronized NamedValue create_named_value(String s, Any any, int flags) |
| { |
| checkShutdownState(); |
| return new NamedValueImpl(this, s, any, flags); |
| } |
| |
| /** |
| * Create an ExceptionList |
| * |
| * @return ExceptionList created |
| */ |
| public synchronized org.omg.CORBA.ExceptionList create_exception_list() |
| { |
| checkShutdownState(); |
| return new ExceptionListImpl(); |
| } |
| |
| /** |
| * Create a ContextList |
| * |
| * @return ContextList created |
| */ |
| public synchronized org.omg.CORBA.ContextList create_context_list() |
| { |
| checkShutdownState(); |
| return new ContextListImpl(this); |
| } |
| |
| /** |
| * Get the default Context object |
| * |
| * @return the default Context object |
| */ |
| public synchronized org.omg.CORBA.Context get_default_context() |
| { |
| checkShutdownState(); |
| throw wrapper.genericNoImpl() ; |
| } |
| |
| /** |
| * Create an Environment |
| * |
| * @return Environment created |
| */ |
| public synchronized org.omg.CORBA.Environment create_environment() |
| { |
| checkShutdownState(); |
| return new EnvironmentImpl(); |
| } |
| |
| public synchronized void send_multiple_requests_oneway(Request[] req) |
| { |
| checkShutdownState(); |
| |
| // Invoke the send_oneway on each new Request |
| for (int i = 0; i < req.length; i++) { |
| req[i].send_oneway(); |
| } |
| } |
| |
| /** |
| * Send multiple dynamic requests asynchronously. |
| * |
| * @param req an array of request objects. |
| */ |
| public synchronized void send_multiple_requests_deferred(Request[] req) |
| { |
| checkShutdownState(); |
| |
| // add the new Requests to pending dynamic Requests |
| for (int i = 0; i < req.length; i++) { |
| dynamicRequests.addElement(req[i]); |
| } |
| |
| // Invoke the send_deferred on each new Request |
| for (int i = 0; i < req.length; i++) { |
| AsynchInvoke invokeObject = new AsynchInvoke( this, |
| (com.sun.corba.se.impl.corba.RequestImpl)req[i], true); |
| new Thread(null, invokeObject, "ORB-Request-Thread", 0, false).start(); |
| } |
| } |
| |
| /** |
| * Find out if any of the deferred invocations have a response yet. |
| */ |
| public synchronized boolean poll_next_response() |
| { |
| checkShutdownState(); |
| |
| Request currRequest; |
| |
| // poll on each pending request |
| Enumeration ve = dynamicRequests.elements(); |
| while (ve.hasMoreElements() == true) { |
| currRequest = (Request)ve.nextElement(); |
| if (currRequest.poll_response() == true) { |
| return true; |
| } |
| } |
| return false; |
| } |
| |
| /** |
| * Get the next request that has gotten a response. |
| * |
| * @return the next request ready with a response. |
| */ |
| public org.omg.CORBA.Request get_next_response() |
| throws org.omg.CORBA.WrongTransaction |
| { |
| synchronized( this ) { |
| checkShutdownState(); |
| } |
| |
| while (true) { |
| // check if there already is a response |
| synchronized ( dynamicRequests ) { |
| Enumeration elems = dynamicRequests.elements(); |
| while ( elems.hasMoreElements() ) { |
| Request currRequest = (Request)elems.nextElement(); |
| if ( currRequest.poll_response() ) { |
| // get the response for this successfully polled Request |
| currRequest.get_response(); |
| dynamicRequests.removeElement(currRequest); |
| return currRequest; |
| } |
| } |
| } |
| |
| // wait for a response |
| synchronized(this.svResponseReceived) { |
| while (!this.svResponseReceived.value()) { |
| try { |
| this.svResponseReceived.wait(); |
| } catch(java.lang.InterruptedException ex) { |
| // NO-OP |
| } |
| } |
| // reinitialize the response flag |
| this.svResponseReceived.reset(); |
| } |
| } |
| } |
| |
| /** |
| * Notify response to ORB for get_next_response |
| */ |
| public void notifyORB() |
| { |
| synchronized (this) { |
| checkShutdownState(); |
| } |
| synchronized (this.svResponseReceived) { |
| this.svResponseReceived.set(); |
| this.svResponseReceived.notify(); |
| } |
| } |
| |
| /** |
| * Convert an object ref to a string. |
| * @param obj The object to stringify. |
| * @return A stringified object reference. |
| */ |
| public synchronized String object_to_string(org.omg.CORBA.Object obj) |
| { |
| checkShutdownState(); |
| |
| // Handle the null objref case |
| if (obj == null) { |
| IOR nullIOR = IORFactories.makeIOR( this ) ; |
| return nullIOR.stringify(); |
| } |
| |
| IOR ior = null ; |
| |
| try { |
| ior = ORBUtility.connectAndGetIOR( this, obj ) ; |
| } catch (BAD_PARAM bp) { |
| // Throw MARSHAL instead if this is a LOCAL_OBJECT_NOT_ALLOWED error. |
| if (bp.minor == ORBUtilSystemException.LOCAL_OBJECT_NOT_ALLOWED) { |
| throw omgWrapper.notAnObjectImpl( bp ) ; |
| } else |
| // Not a local object problem: just rethrow the exception. |
| // Do not wrap and log this, since it was already logged at its |
| // point of origin. |
| throw bp ; |
| } |
| |
| return ior.stringify() ; |
| } |
| |
| /** |
| * Convert a stringified object reference to the object it represents. |
| * @param str The stringified object reference. |
| * @return The unstringified object reference. |
| */ |
| public org.omg.CORBA.Object string_to_object(String str) |
| { |
| Operation op ; |
| |
| synchronized (this) { |
| checkShutdownState(); |
| op = urlOperation ; |
| } |
| |
| if (str == null) |
| throw wrapper.nullParam() ; |
| |
| synchronized (urlOperationLock) { |
| org.omg.CORBA.Object obj = (org.omg.CORBA.Object)op.operate( str ) ; |
| return obj ; |
| } |
| } |
| |
| // pure java orb support, moved this method from FVDCodeBaseImpl. |
| // Note that we connect this if we have not already done so. |
| public synchronized IOR getFVDCodeBaseIOR() |
| { |
| checkShutdownState(); |
| |
| if (codeBaseIOR != null) // i.e. We are already connected to it |
| return codeBaseIOR; |
| |
| // backward compatability 4365188 |
| CodeBase cb; |
| |
| ValueHandler vh = ORBUtility.createValueHandler(); |
| |
| cb = (CodeBase)vh.getRunTimeCodeBase(); |
| return ORBUtility.connectAndGetIOR( this, cb ) ; |
| } |
| |
| /** |
| * Get the TypeCode for a primitive type. |
| * |
| * @param tcKind the integer kind for the primitive type |
| * @return the requested TypeCode |
| */ |
| public synchronized TypeCode get_primitive_tc(TCKind tcKind) |
| { |
| checkShutdownState(); |
| return get_primitive_tc( tcKind.value() ) ; |
| } |
| |
| /** |
| * Create a TypeCode for a structure. |
| * |
| * @param id the logical id for the typecode. |
| * @param name the name for the typecode. |
| * @param members an array describing the members of the TypeCode. |
| * @return the requested TypeCode. |
| */ |
| public synchronized TypeCode create_struct_tc(String id, |
| String name, |
| StructMember[] members) |
| { |
| checkShutdownState(); |
| return new TypeCodeImpl(this, TCKind._tk_struct, id, name, members); |
| } |
| |
| /** |
| * Create a TypeCode for a union. |
| * |
| * @param id the logical id for the typecode. |
| * @param name the name for the typecode. |
| * @param discriminator_type |
| * the type of the union discriminator. |
| * @param members an array describing the members of the TypeCode. |
| * @return the requested TypeCode. |
| */ |
| public synchronized TypeCode create_union_tc(String id, |
| String name, |
| TypeCode discriminator_type, |
| UnionMember[] members) |
| { |
| checkShutdownState(); |
| return new TypeCodeImpl(this, |
| TCKind._tk_union, |
| id, |
| name, |
| discriminator_type, |
| members); |
| } |
| |
| /** |
| * Create a TypeCode for an enum. |
| * |
| * @param id the logical id for the typecode. |
| * @param name the name for the typecode. |
| * @param members an array describing the members of the TypeCode. |
| * @return the requested TypeCode. |
| */ |
| public synchronized TypeCode create_enum_tc(String id, |
| String name, |
| String[] members) |
| { |
| checkShutdownState(); |
| return new TypeCodeImpl(this, TCKind._tk_enum, id, name, members); |
| } |
| |
| /** |
| * Create a TypeCode for an alias. |
| * |
| * @param id the logical id for the typecode. |
| * @param name the name for the typecode. |
| * @param original_type |
| * the type this is an alias for. |
| * @return the requested TypeCode. |
| */ |
| public synchronized TypeCode create_alias_tc(String id, |
| String name, |
| TypeCode original_type) |
| { |
| checkShutdownState(); |
| return new TypeCodeImpl(this, TCKind._tk_alias, id, name, original_type); |
| } |
| |
| /** |
| * Create a TypeCode for an exception. |
| * |
| * @param id the logical id for the typecode. |
| * @param name the name for the typecode. |
| * @param members an array describing the members of the TypeCode. |
| * @return the requested TypeCode. |
| */ |
| public synchronized TypeCode create_exception_tc(String id, |
| String name, |
| StructMember[] members) |
| { |
| checkShutdownState(); |
| return new TypeCodeImpl(this, TCKind._tk_except, id, name, members); |
| } |
| |
| /** |
| * Create a TypeCode for an interface. |
| * |
| * @param id the logical id for the typecode. |
| * @param name the name for the typecode. |
| * @return the requested TypeCode. |
| */ |
| public synchronized TypeCode create_interface_tc(String id, |
| String name) |
| { |
| checkShutdownState(); |
| return new TypeCodeImpl(this, TCKind._tk_objref, id, name); |
| } |
| |
| /** |
| * Create a TypeCode for a string. |
| * |
| * @param bound the bound for the string. |
| * @return the requested TypeCode. |
| */ |
| public synchronized TypeCode create_string_tc(int bound) |
| { |
| checkShutdownState(); |
| return new TypeCodeImpl(this, TCKind._tk_string, bound); |
| } |
| |
| /** |
| * Create a TypeCode for a wide string. |
| * |
| * @param bound the bound for the string. |
| * @return the requested TypeCode. |
| */ |
| public synchronized TypeCode create_wstring_tc(int bound) |
| { |
| checkShutdownState(); |
| return new TypeCodeImpl(this, TCKind._tk_wstring, bound); |
| } |
| |
| /** |
| * Create a TypeCode for a sequence. |
| * |
| * @param bound the bound for the sequence. |
| * @param element_type |
| * the type of elements of the sequence. |
| * @return the requested TypeCode. |
| */ |
| public synchronized TypeCode create_sequence_tc(int bound, |
| TypeCode element_type) |
| { |
| checkShutdownState(); |
| return new TypeCodeImpl(this, TCKind._tk_sequence, bound, element_type); |
| } |
| |
| |
| /** |
| * Create a recursive TypeCode in a sequence. |
| * |
| * @param bound the bound for the sequence. |
| * @param offset the index to the enclosing TypeCode that is |
| * being referenced. |
| * @return the requested TypeCode. |
| */ |
| public synchronized TypeCode create_recursive_sequence_tc(int bound, |
| int offset) |
| { |
| checkShutdownState(); |
| return new TypeCodeImpl(this, TCKind._tk_sequence, bound, offset); |
| } |
| |
| |
| /** |
| * Create a TypeCode for an array. |
| * |
| * @param length the length of the array. |
| * @param element_type |
| * the type of elements of the array. |
| * @return the requested TypeCode. |
| */ |
| public synchronized TypeCode create_array_tc(int length, |
| TypeCode element_type) |
| { |
| checkShutdownState(); |
| return new TypeCodeImpl(this, TCKind._tk_array, length, element_type); |
| } |
| |
| |
| public synchronized org.omg.CORBA.TypeCode create_native_tc(String id, |
| String name) |
| { |
| checkShutdownState(); |
| return new TypeCodeImpl(this, TCKind._tk_native, id, name); |
| } |
| |
| public synchronized org.omg.CORBA.TypeCode create_abstract_interface_tc( |
| String id, |
| String name) |
| { |
| checkShutdownState(); |
| return new TypeCodeImpl(this, TCKind._tk_abstract_interface, id, name); |
| } |
| |
| public synchronized org.omg.CORBA.TypeCode create_fixed_tc(short digits, short scale) |
| { |
| checkShutdownState(); |
| return new TypeCodeImpl(this, TCKind._tk_fixed, digits, scale); |
| } |
| |
| public synchronized org.omg.CORBA.TypeCode create_value_tc(String id, |
| String name, |
| short type_modifier, |
| TypeCode concrete_base, |
| ValueMember[] members) |
| { |
| checkShutdownState(); |
| return new TypeCodeImpl(this, TCKind._tk_value, id, name, |
| type_modifier, concrete_base, members); |
| } |
| |
| public synchronized org.omg.CORBA.TypeCode create_recursive_tc(String id) { |
| checkShutdownState(); |
| return new TypeCodeImpl(this, id); |
| } |
| |
| public synchronized org.omg.CORBA.TypeCode create_value_box_tc(String id, |
| String name, |
| TypeCode boxed_type) |
| { |
| checkShutdownState(); |
| return new TypeCodeImpl(this, TCKind._tk_value_box, id, name, |
| boxed_type); |
| } |
| |
| /** |
| * Create a new Any |
| * |
| * @return the new Any created. |
| */ |
| public synchronized Any create_any() |
| { |
| checkShutdownState(); |
| return new AnyImpl(this); |
| } |
| |
| // TypeCodeFactory interface methods. |
| // Keeping track of type codes by repository id. |
| |
| // Keeping a cache of TypeCodes associated with the class |
| // they got created from in Util.writeAny(). |
| |
| public synchronized void setTypeCodeForClass(Class c, TypeCodeImpl tci) |
| { |
| checkShutdownState(); |
| |
| if (typeCodeForClassMap == null) |
| typeCodeForClassMap = Collections.synchronizedMap( |
| new WeakHashMap(64)); |
| // Store only one TypeCode per class. |
| if ( ! typeCodeForClassMap.containsKey(c)) |
| typeCodeForClassMap.put(c, tci); |
| } |
| |
| public synchronized TypeCodeImpl getTypeCodeForClass(Class c) |
| { |
| checkShutdownState(); |
| |
| if (typeCodeForClassMap == null) |
| return null; |
| return (TypeCodeImpl)typeCodeForClassMap.get(c); |
| } |
| |
| /**************************************************************************** |
| * The following methods deal with listing and resolving the initial |
| * (bootstrap) object references such as "NameService". |
| ****************************************************************************/ |
| |
| /** |
| * Get a list of the initially available CORBA services. |
| * This does not work unless an ORBInitialHost is specified during |
| * initialization (or unless there is an ORB running on the AppletHost) |
| * since the localhostname |
| * is inaccessible to applets. If a service properties URL was specified, |
| * then it is used, otherwise the bootstrapping protocol is used. |
| * @return A list of the initial services available. |
| */ |
| public String[] list_initial_services() |
| { |
| Resolver res ; |
| |
| synchronized( this ) { |
| checkShutdownState(); |
| res = resolver ; |
| } |
| |
| synchronized (resolverLock) { |
| java.util.Set keys = res.list() ; |
| return (String[])keys.toArray( new String[keys.size()] ) ; |
| } |
| } |
| |
| /** |
| * Resolve the stringified reference of one of the initially |
| * available CORBA services. |
| * @param identifier The stringified object reference of the |
| * desired service. |
| * @return An object reference for the desired service. |
| * @exception InvalidName The supplied identifier is not associated |
| * with a known service. |
| * @exception SystemException One of a fixed set of Corba system exceptions. |
| */ |
| public org.omg.CORBA.Object resolve_initial_references( |
| String identifier) throws InvalidName |
| { |
| Resolver res ; |
| |
| synchronized( this ) { |
| checkShutdownState(); |
| res = resolver ; |
| } |
| |
| synchronized (resolverLock) { |
| org.omg.CORBA.Object result = res.resolve( identifier ) ; |
| |
| if (result == null) |
| throw new InvalidName() ; |
| else |
| return result ; |
| } |
| } |
| |
| /** |
| * If this operation is called with an id, <code>"Y"</code>, and an |
| * object, <code>YY</code>, then a subsequent call to |
| * <code>ORB.resolve_initial_references( "Y" )</code> will |
| * return object <code>YY</code>. |
| * |
| * @param id The ID by which the initial reference will be known. |
| * @param obj The initial reference itself. |
| * @throws InvalidName if this operation is called with an empty string id |
| * or this operation is called with an id that is already registered, |
| * including the default names defined by OMG. |
| * @throws BAD_PARAM if the obj parameter is null. |
| */ |
| public void register_initial_reference( |
| String id, org.omg.CORBA.Object obj ) throws InvalidName |
| { |
| CorbaServerRequestDispatcher insnd ; |
| |
| synchronized (this) { |
| checkShutdownState(); |
| } |
| |
| if ((id == null) || (id.length() == 0)) |
| throw new InvalidName() ; |
| |
| synchronized (this) { |
| checkShutdownState(); |
| } |
| |
| synchronized (resolverLock) { |
| insnd = insNamingDelegate ; |
| |
| java.lang.Object obj2 = localResolver.resolve( id ) ; |
| if (obj2 != null) |
| throw new InvalidName(id + " already registered") ; |
| |
| localResolver.register( id, ClosureFactory.makeConstant( obj )) ; |
| } |
| |
| synchronized (this) { |
| if (StubAdapter.isStub(obj)) |
| // Make all remote object references available for INS. |
| requestDispatcherRegistry.registerServerRequestDispatcher( |
| insnd, id ) ; |
| } |
| } |
| |
| /**************************************************************************** |
| * The following methods (introduced in POA / CORBA2.1) deal with |
| * shutdown / single threading. |
| ****************************************************************************/ |
| |
| public void run() |
| { |
| synchronized (this) { |
| checkShutdownState(); |
| } |
| |
| synchronized (runObj) { |
| try { |
| runObj.wait(); |
| } catch ( InterruptedException ex ) {} |
| } |
| } |
| |
| public void shutdown(boolean wait_for_completion) { |
| boolean wait = false; |
| |
| synchronized (this) { |
| checkShutdownState(); |
| |
| // This is to avoid deadlock: don't allow a thread that is |
| // processing a request to call shutdown( true ), because |
| // the shutdown would block waiting for the request to complete, |
| // while the request would block waiting for shutdown to complete. |
| if (wait_for_completion && |
| isProcessingInvocation.get() == Boolean.TRUE) { |
| throw omgWrapper.shutdownWaitForCompletionDeadlock(); |
| } |
| |
| if (status == STATUS_SHUTTING_DOWN) { |
| if (wait_for_completion) { |
| wait = true; |
| } else { |
| return; |
| } |
| } |
| |
| status = STATUS_SHUTTING_DOWN; |
| } |
| |
| // Avoid more than one thread performing shutdown at a time. |
| synchronized (shutdownObj) { |
| // At this point, the ORB status is certainly STATUS_SHUTTING_DOWN. |
| // If wait is true, another thread already called shutdown( true ), |
| // and so we wait for completion |
| if (wait) { |
| while (true) { |
| synchronized (this) { |
| if (status == STATUS_SHUTDOWN) |
| break; |
| } |
| |
| try { |
| shutdownObj.wait(); |
| } catch (InterruptedException exc) { |
| // NOP: just loop and wait until state is changed |
| } |
| } |
| } else { |
| // perform the actual shutdown |
| shutdownServants(wait_for_completion); |
| |
| if (wait_for_completion) { |
| synchronized ( waitForCompletionObj ) { |
| while (numInvocations > 0) { |
| try { |
| waitForCompletionObj.wait(); |
| } catch (InterruptedException ex) {} |
| } |
| } |
| } |
| |
| synchronized (runObj) { |
| runObj.notifyAll(); |
| } |
| |
| status = STATUS_SHUTDOWN; |
| |
| shutdownObj.notifyAll(); |
| } |
| } |
| } |
| |
| // Cause all ObjectAdapaterFactories to clean up all of their internal state, which |
| // may include activated objects that have associated state and callbacks that must |
| // complete in order to shutdown. This will cause new request to be rejected. |
| protected void shutdownServants(boolean wait_for_completion) { |
| Set<ObjectAdapterFactory> oaset; |
| synchronized (this) { |
| oaset = new HashSet<>(requestDispatcherRegistry.getObjectAdapterFactories()); |
| } |
| |
| for (ObjectAdapterFactory oaf : oaset) |
| oaf.shutdown(wait_for_completion); |
| } |
| |
| // Note that the caller must hold the ORBImpl lock. |
| public void checkShutdownState() |
| { |
| if (status == STATUS_DESTROYED) { |
| throw wrapper.orbDestroyed() ; |
| } |
| |
| if (status == STATUS_SHUTDOWN) { |
| throw omgWrapper.badOperationAfterShutdown() ; |
| } |
| } |
| |
| public boolean isDuringDispatch() |
| { |
| synchronized (this) { |
| checkShutdownState(); |
| } |
| Boolean value = (Boolean)(isProcessingInvocation.get()) ; |
| return value.booleanValue() ; |
| } |
| |
| public void startingDispatch() |
| { |
| synchronized (this) { |
| checkShutdownState(); |
| } |
| synchronized (invocationObj) { |
| isProcessingInvocation.set(Boolean.TRUE); |
| numInvocations++; |
| } |
| } |
| |
| public void finishedDispatch() |
| { |
| synchronized (this) { |
| checkShutdownState(); |
| } |
| synchronized (invocationObj) { |
| numInvocations--; |
| isProcessingInvocation.set(false); |
| if (numInvocations == 0) { |
| synchronized (waitForCompletionObj) { |
| waitForCompletionObj.notifyAll(); |
| } |
| } else if (numInvocations < 0) { |
| throw wrapper.numInvocationsAlreadyZero( |
| CompletionStatus.COMPLETED_YES); |
| } |
| } |
| } |
| |
| /** |
| * formal/99-10-07 p 159: "If destroy is called on an ORB that has |
| * not been shut down, it will start the shutdown process and block until |
| * the ORB has shut down before it destroys the ORB." |
| */ |
| public void destroy() |
| { |
| boolean shutdownFirst = false; |
| |
| synchronized (this) { |
| shutdownFirst = (status == STATUS_OPERATING); |
| } |
| |
| if (shutdownFirst) { |
| shutdown(true); |
| } |
| |
| synchronized (this) { |
| if (status < STATUS_DESTROYED) { |
| getCorbaTransportManager().close(); |
| getPIHandler().destroyInterceptors(); |
| status = STATUS_DESTROYED; |
| } |
| } |
| synchronized (threadPoolManagerAccessLock) { |
| if (orbOwnsThreadPoolManager) { |
| try { |
| threadpoolMgr.close(); |
| threadpoolMgr = null; |
| } catch (IOException exc) { |
| wrapper.ioExceptionOnClose(exc); |
| } |
| } |
| } |
| |
| try { |
| monitoringManager.close(); |
| monitoringManager = null; |
| } catch (IOException exc) { |
| wrapper.ioExceptionOnClose(exc); |
| } |
| |
| CachedCodeBase.cleanCache(this); |
| try { |
| pihandler.close(); |
| } catch (IOException exc) { |
| wrapper.ioExceptionOnClose(exc); |
| } |
| |
| super.destroy(); |
| |
| badServerIdHandlerAccessLock = null; |
| clientDelegateFactoryAccessorLock = null; |
| corbaContactInfoListFactoryAccessLock = null; |
| |
| objectKeyFactoryAccessLock = null; |
| legacyServerSocketManagerAccessLock = null; |
| threadPoolManagerAccessLock = null; |
| transportManager = null; |
| legacyServerSocketManager = null; |
| OAInvocationInfoStack = null; |
| clientInvocationInfoStack = null; |
| codeBaseIOR = null; |
| dynamicRequests = null; |
| svResponseReceived = null; |
| runObj = null; |
| shutdownObj = null; |
| waitForCompletionObj = null; |
| invocationObj = null; |
| isProcessingInvocation = null; |
| typeCodeForClassMap = null; |
| valueFactoryCache = null; |
| orbVersionThreadLocal = null; |
| requestDispatcherRegistry = null; |
| copierManager = null; |
| toaFactory = null; |
| poaFactory = null; |
| pihandler = null; |
| configData = null; |
| badServerIdHandler = null; |
| clientDelegateFactory = null; |
| corbaContactInfoListFactory = null; |
| resolver = null; |
| localResolver = null; |
| insNamingDelegate = null; |
| urlOperation = null; |
| taggedComponentFactoryFinder = null; |
| taggedProfileFactoryFinder = null; |
| taggedProfileTemplateFactoryFinder = null; |
| objectKeyFactory = null; |
| } |
| |
| /** |
| * Registers a value factory for a particular repository ID. |
| * |
| * @param repositoryID the repository ID. |
| * @param factory the factory. |
| * @return the previously registered factory for the given repository ID, |
| * or null if no such factory was previously registered. |
| * @exception org.omg.CORBA.BAD_PARAM if the registration fails. |
| **/ |
| public synchronized ValueFactory register_value_factory(String repositoryID, |
| ValueFactory factory) |
| { |
| checkShutdownState(); |
| |
| if ((repositoryID == null) || (factory == null)) |
| throw omgWrapper.unableRegisterValueFactory() ; |
| |
| return (ValueFactory)valueFactoryCache.put(repositoryID, factory); |
| } |
| |
| /** |
| * Unregisters a value factory for a particular repository ID. |
| * |
| * @param repositoryID the repository ID. |
| **/ |
| public synchronized void unregister_value_factory(String repositoryID) |
| { |
| checkShutdownState(); |
| |
| if (valueFactoryCache.remove(repositoryID) == null) |
| throw wrapper.nullParam() ; |
| } |
| |
| /** |
| * Finds and returns a value factory for the given repository ID. |
| * The value factory returned was previously registered by a call to |
| * {@link #register_value_factory} or is the default factory. |
| * |
| * @param repositoryID the repository ID. |
| * @return the value factory. |
| * @exception org.omg.CORBA.BAD_PARAM if unable to locate a factory. |
| **/ |
| public synchronized ValueFactory lookup_value_factory(String repositoryID) |
| { |
| checkShutdownState(); |
| |
| ValueFactory factory = |
| (ValueFactory)valueFactoryCache.get(repositoryID); |
| |
| if (factory == null) { |
| try { |
| factory = Utility.getFactory(null, null, null, repositoryID); |
| } catch(org.omg.CORBA.MARSHAL ex) { |
| throw wrapper.unableFindValueFactory( ex ) ; |
| } |
| } |
| |
| return factory ; |
| } |
| |
| public OAInvocationInfo peekInvocationInfo() |
| { |
| synchronized (this) { |
| checkShutdownState(); |
| } |
| StackImpl stack = (StackImpl)(OAInvocationInfoStack.get()) ; |
| return (OAInvocationInfo)(stack.peek()) ; |
| } |
| |
| public void pushInvocationInfo( OAInvocationInfo info ) |
| { |
| synchronized (this) { |
| checkShutdownState(); |
| } |
| StackImpl stack = (StackImpl)(OAInvocationInfoStack.get()) ; |
| stack.push( info ) ; |
| } |
| |
| public OAInvocationInfo popInvocationInfo() |
| { |
| synchronized (this) { |
| checkShutdownState(); |
| } |
| StackImpl stack = (StackImpl)(OAInvocationInfoStack.get()) ; |
| return (OAInvocationInfo)(stack.pop()) ; |
| } |
| |
| /** |
| * The bad server id handler is used by the Locator to |
| * send back the location of a persistant server to the client. |
| */ |
| |
| private Object badServerIdHandlerAccessLock = new Object(); |
| |
| public void initBadServerIdHandler() |
| { |
| synchronized (this) { |
| checkShutdownState(); |
| } |
| synchronized (badServerIdHandlerAccessLock) { |
| Class cls = configData.getBadServerIdHandler() ; |
| if (cls != null) { |
| try { |
| Class[] params = new Class[] { org.omg.CORBA.ORB.class }; |
| java.lang.Object[] args = new java.lang.Object[]{this}; |
| Constructor cons = cls.getConstructor(params); |
| badServerIdHandler = |
| (BadServerIdHandler) cons.newInstance(args); |
| } catch (Exception e) { |
| throw wrapper.errorInitBadserveridhandler( e ) ; |
| } |
| } |
| } |
| } |
| |
| public void setBadServerIdHandler( BadServerIdHandler handler ) |
| { |
| synchronized (this) { |
| checkShutdownState(); |
| } |
| synchronized (badServerIdHandlerAccessLock) { |
| badServerIdHandler = handler; |
| } |
| } |
| |
| public void handleBadServerId( ObjectKey okey ) |
| { |
| synchronized (this) { |
| checkShutdownState(); |
| } |
| synchronized (badServerIdHandlerAccessLock) { |
| if (badServerIdHandler == null) |
| throw wrapper.badServerId() ; |
| else |
| badServerIdHandler.handle( okey ) ; |
| } |
| } |
| |
| public synchronized org.omg.CORBA.Policy create_policy( int type, |
| org.omg.CORBA.Any val ) throws org.omg.CORBA.PolicyError |
| { |
| checkShutdownState() ; |
| |
| return pihandler.create_policy( type, val ) ; |
| } |
| |
| /** This is the implementation of the public API used to connect |
| * a servant-skeleton to the ORB. |
| */ |
| public synchronized void connect(org.omg.CORBA.Object servant) |
| { |
| checkShutdownState(); |
| if (getTOAFactory() == null) |
| throw wrapper.noToa() ; |
| |
| try { |
| String codebase = javax.rmi.CORBA.Util.getCodebase( servant.getClass() ) ; |
| getTOAFactory().getTOA( codebase ).connect( servant ) ; |
| } catch ( Exception ex ) { |
| throw wrapper.orbConnectError( ex ) ; |
| } |
| } |
| |
| public synchronized void disconnect(org.omg.CORBA.Object obj) |
| { |
| checkShutdownState(); |
| if (getTOAFactory() == null) |
| throw wrapper.noToa() ; |
| |
| try { |
| getTOAFactory().getTOA().disconnect( obj ) ; |
| } catch ( Exception ex ) { |
| throw wrapper.orbConnectError( ex ) ; |
| } |
| } |
| |
| public int getTransientServerId() |
| { |
| synchronized (this) { |
| checkShutdownState(); |
| } |
| if( configData.getORBServerIdPropertySpecified( ) ) { |
| // ORBServerId is specified then use that value |
| return configData.getPersistentServerId( ); |
| } |
| return transientServerId; |
| } |
| |
| public RequestDispatcherRegistry getRequestDispatcherRegistry() |
| { |
| synchronized (this) { |
| checkShutdownState(); |
| } |
| return requestDispatcherRegistry; |
| } |
| |
| public ServiceContextRegistry getServiceContextRegistry() |
| { |
| synchronized (this) { |
| checkShutdownState(); |
| } |
| return serviceContextRegistry ; |
| } |
| |
| // XXX All of the isLocalXXX checking needs to be revisited. |
| // First of all, all three of these methods are called from |
| // only one place in impl.ior.IORImpl. Second, we have problems |
| // both with multi-homed hosts and with multi-profile IORs. |
| // A possible strategy: like the LocalClientRequestDispatcher, we need |
| // to determine this more abstractly at the ContactInfo level. |
| // This level should probably just get the CorbaContactInfoList from |
| // the IOR, then iterator over ContactInfo. If any ContactInfo is |
| // local, the IOR is local, and we can pick one to create the |
| // LocalClientRequestDispatcher as well. Bottom line: this code needs to move. |
| |
| // XXX What about multi-homed host? |
| public boolean isLocalHost( String hostName ) |
| { |
| synchronized (this) { |
| checkShutdownState(); |
| } |
| return hostName.equals( configData.getORBServerHost() ) || |
| hostName.equals( getLocalHostName() ) ; |
| } |
| |
| public boolean isLocalServerId( int subcontractId, int serverId ) |
| { |
| synchronized (this) { |
| checkShutdownState(); |
| } |
| if ((subcontractId < ORBConstants.FIRST_POA_SCID) || |
| (subcontractId > ORBConstants.MAX_POA_SCID)) |
| return serverId == getTransientServerId( ) ; |
| |
| // XXX isTransient info should be stored in subcontract registry |
| if (ORBConstants.isTransient( subcontractId )) |
| return (serverId == getTransientServerId()) ; |
| else if (configData.getPersistentServerIdInitialized()) |
| return (serverId == configData.getPersistentServerId()) ; |
| else |
| return false ; |
| } |
| |
| /************************************************************************* |
| * The following public methods are for ORB shutdown. |
| *************************************************************************/ |
| |
| private String getHostName(String host) |
| throws java.net.UnknownHostException |
| { |
| return InetAddress.getByName( host ).getHostAddress(); |
| } |
| |
| /* keeping a copy of the getLocalHostName so that it can only be called |
| * internally and the unauthorized clients cannot have access to the |
| * localHost information, originally, the above code was calling |
| * getLocalHostName from Connection.java. If the hostname is cached in |
| * Connection.java, then |
| * it is a security hole, since any unauthorized client has access to |
| * the host information. With this change it is used internally so the |
| * security problem is resolved. Also in Connection.java, the |
| * getLocalHost() implementation has changed to always call the |
| * InetAddress.getLocalHost().getHostAddress() |
| * The above mentioned method has been removed from the connection class |
| */ |
| |
| private static String localHostString = null; |
| |
| private synchronized String getLocalHostName() |
| { |
| if (localHostString == null) { |
| try { |
| localHostString = InetAddress.getLocalHost().getHostAddress(); |
| } catch (Exception ex) { |
| throw wrapper.getLocalHostFailed( ex ) ; |
| } |
| } |
| return localHostString ; |
| } |
| |
| /****************************************************************************** |
| * The following public methods are for ORB shutdown. |
| * |
| ******************************************************************************/ |
| |
| /** This method always returns false because the ORB never needs the |
| * main thread to do work. |
| */ |
| public synchronized boolean work_pending() |
| { |
| checkShutdownState(); |
| throw wrapper.genericNoImpl() ; |
| } |
| |
| /** This method does nothing. It is not required by the spec to do anything! |
| */ |
| public synchronized void perform_work() |
| { |
| checkShutdownState(); |
| throw wrapper.genericNoImpl() ; |
| } |
| |
| public synchronized void set_delegate(java.lang.Object servant){ |
| checkShutdownState(); |
| |
| POAFactory poaFactory = getPOAFactory() ; |
| if (poaFactory != null) |
| ((org.omg.PortableServer.Servant)servant) |
| ._set_delegate( poaFactory.getDelegateImpl() ) ; |
| else |
| throw wrapper.noPoa() ; |
| } |
| |
| //////////////////////////////////////////////////// |
| // |
| // pept.broker.Broker |
| // |
| |
| public ClientInvocationInfo createOrIncrementInvocationInfo() |
| { |
| synchronized (this) { |
| checkShutdownState(); |
| } |
| StackImpl invocationInfoStack = |
| (StackImpl) clientInvocationInfoStack.get(); |
| ClientInvocationInfo clientInvocationInfo = null; |
| if (!invocationInfoStack.empty()) { |
| clientInvocationInfo = |
| (ClientInvocationInfo) invocationInfoStack.peek(); |
| } |
| if ((clientInvocationInfo == null) || |
| (!clientInvocationInfo.isRetryInvocation())) |
| { |
| // This is a new call - not a retry. |
| clientInvocationInfo = new CorbaInvocationInfo(this); |
| startingDispatch(); |
| invocationInfoStack.push(clientInvocationInfo); |
| } |
| // Reset retry so recursive calls will get a new info object. |
| clientInvocationInfo.setIsRetryInvocation(false); |
| clientInvocationInfo.incrementEntryCount(); |
| return clientInvocationInfo; |
| } |
| |
| public void releaseOrDecrementInvocationInfo() |
| { |
| synchronized (this) { |
| checkShutdownState(); |
| } |
| int entryCount = -1; |
| ClientInvocationInfo clientInvocationInfo = null; |
| StackImpl invocationInfoStack = |
| (StackImpl)clientInvocationInfoStack.get(); |
| if (!invocationInfoStack.empty()) { |
| clientInvocationInfo = |
| (ClientInvocationInfo)invocationInfoStack.peek(); |
| } else { |
| throw wrapper.invocationInfoStackEmpty() ; |
| } |
| clientInvocationInfo.decrementEntryCount(); |
| entryCount = clientInvocationInfo.getEntryCount(); |
| if (clientInvocationInfo.getEntryCount() == 0) { |
| // 6763340: don't pop if this is a retry! |
| if (!clientInvocationInfo.isRetryInvocation()) { |
| invocationInfoStack.pop(); |
| } |
| finishedDispatch(); |
| } |
| } |
| |
| public ClientInvocationInfo getInvocationInfo() |
| { |
| synchronized (this) { |
| checkShutdownState(); |
| } |
| StackImpl invocationInfoStack = |
| (StackImpl) clientInvocationInfoStack.get(); |
| return (ClientInvocationInfo) invocationInfoStack.peek(); |
| } |
| |
| //////////////////////////////////////////////////// |
| // |
| // |
| // |
| |
| private Object clientDelegateFactoryAccessorLock = new Object(); |
| |
| public void setClientDelegateFactory( ClientDelegateFactory factory ) |
| { |
| synchronized (this) { |
| checkShutdownState(); |
| } |
| synchronized (clientDelegateFactoryAccessorLock) { |
| clientDelegateFactory = factory ; |
| } |
| } |
| |
| public ClientDelegateFactory getClientDelegateFactory() |
| { |
| synchronized (this) { |
| checkShutdownState(); |
| } |
| synchronized (clientDelegateFactoryAccessorLock) { |
| return clientDelegateFactory ; |
| } |
| } |
| |
| private Object corbaContactInfoListFactoryAccessLock = new Object(); |
| |
| public void setCorbaContactInfoListFactory( CorbaContactInfoListFactory factory ) |
| { |
| synchronized (this) { |
| checkShutdownState(); |
| } |
| synchronized (corbaContactInfoListFactoryAccessLock) { |
| corbaContactInfoListFactory = factory ; |
| } |
| } |
| |
| public synchronized CorbaContactInfoListFactory getCorbaContactInfoListFactory() |
| { |
| checkShutdownState(); |
| return corbaContactInfoListFactory ; |
| } |
| |
| /** Set the resolver used in this ORB. This resolver will be used for list_initial_services |
| * and resolve_initial_references. |
| */ |
| public void setResolver( Resolver resolver ) |
| { |
| synchronized (this) { |
| checkShutdownState(); |
| } |
| synchronized (resolverLock) { |
| this.resolver = resolver ; |
| } |
| } |
| |
| /** Get the resolver used in this ORB. This resolver will be used for list_initial_services |
| * and resolve_initial_references. |
| */ |
| public Resolver getResolver() |
| { |
| synchronized (this) { |
| checkShutdownState(); |
| } |
| synchronized (resolverLock) { |
| return resolver ; |
| } |
| } |
| |
| /** Set the LocalResolver used in this ORB. This LocalResolver is used for |
| * register_initial_reference only. |
| */ |
| public void setLocalResolver( LocalResolver resolver ) |
| { |
| synchronized (this) { |
| checkShutdownState(); |
| } |
| synchronized (resolverLock) { |
| this.localResolver = resolver ; |
| } |
| } |
| |
| /** Get the LocalResolver used in this ORB. This LocalResolver is used for |
| * register_initial_reference only. |
| */ |
| public LocalResolver getLocalResolver() |
| { |
| synchronized (this) { |
| checkShutdownState(); |
| } |
| synchronized (resolverLock) { |
| return localResolver ; |
| } |
| } |
| |
| /** Set the operation used in string_to_object calls. The Operation must expect a |
| * String and return an org.omg.CORBA.Object. |
| */ |
| public void setURLOperation( Operation stringToObject ) |
| { |
| synchronized (this) { |
| checkShutdownState(); |
| } |
| synchronized (urlOperationLock) { |
| urlOperation = stringToObject ; |
| } |
| } |
| |
| /** Get the operation used in string_to_object calls. The Operation must expect a |
| * String and return an org.omg.CORBA.Object. |
| */ |
| public Operation getURLOperation() |
| { |
| synchronized (this) { |
| checkShutdownState(); |
| } |
| synchronized (urlOperationLock) { |
| return urlOperation ; |
| } |
| } |
| |
| public void setINSDelegate( CorbaServerRequestDispatcher sdel ) |
| { |
| synchronized (this) { |
| checkShutdownState(); |
| } |
| synchronized (resolverLock) { |
| insNamingDelegate = sdel ; |
| } |
| } |
| |
| public TaggedComponentFactoryFinder getTaggedComponentFactoryFinder() |
| { |
| synchronized (this) { |
| checkShutdownState(); |
| } |
| return taggedComponentFactoryFinder ; |
| } |
| |
| public IdentifiableFactoryFinder getTaggedProfileFactoryFinder() |
| { |
| synchronized (this) { |
| checkShutdownState(); |
| } |
| return taggedProfileFactoryFinder ; |
| } |
| |
| public IdentifiableFactoryFinder getTaggedProfileTemplateFactoryFinder() |
| { |
| synchronized (this) { |
| checkShutdownState(); |
| } |
| return taggedProfileTemplateFactoryFinder ; |
| } |
| |
| private Object objectKeyFactoryAccessLock = new Object(); |
| |
| public ObjectKeyFactory getObjectKeyFactory() |
| { |
| synchronized (this) { |
| checkShutdownState(); |
| } |
| synchronized (objectKeyFactoryAccessLock) { |
| return objectKeyFactory ; |
| } |
| } |
| |
| public void setObjectKeyFactory( ObjectKeyFactory factory ) |
| { |
| synchronized (this) { |
| checkShutdownState(); |
| } |
| synchronized (objectKeyFactoryAccessLock) { |
| objectKeyFactory = factory ; |
| } |
| } |
| |
| private Object transportManagerAccessorLock = new Object(); |
| |
| public TransportManager getTransportManager() |
| { |
| synchronized (transportManagerAccessorLock) { |
| if (transportManager == null) { |
| transportManager = new CorbaTransportManagerImpl(this); |
| } |
| return transportManager; |
| } |
| } |
| |
| public CorbaTransportManager getCorbaTransportManager() |
| { |
| return (CorbaTransportManager) getTransportManager(); |
| } |
| |
| private Object legacyServerSocketManagerAccessLock = new Object(); |
| |
| public LegacyServerSocketManager getLegacyServerSocketManager() |
| { |
| synchronized (this) { |
| checkShutdownState(); |
| } |
| synchronized (legacyServerSocketManagerAccessLock) { |
| if (legacyServerSocketManager == null) { |
| legacyServerSocketManager = new LegacyServerSocketManagerImpl(this); |
| } |
| return legacyServerSocketManager; |
| } |
| } |
| |
| private Object threadPoolManagerAccessLock = new Object(); |
| |
| public void setThreadPoolManager(ThreadPoolManager mgr) |
| { |
| synchronized (this) { |
| checkShutdownState(); |
| } |
| synchronized (threadPoolManagerAccessLock) { |
| threadpoolMgr = mgr; |
| } |
| } |
| |
| public ThreadPoolManager getThreadPoolManager() |
| { |
| synchronized (this) { |
| checkShutdownState(); |
| } |
| synchronized (threadPoolManagerAccessLock) { |
| if (threadpoolMgr == null) { |
| threadpoolMgr = new ThreadPoolManagerImpl(); |
| orbOwnsThreadPoolManager = true; |
| } |
| return threadpoolMgr; |
| } |
| } |
| |
| public CopierManager getCopierManager() |
| { |
| synchronized (this) { |
| checkShutdownState(); |
| } |
| return copierManager ; |
| } |
| } // Class ORBImpl |
| |
| //////////////////////////////////////////////////////////////////////// |
| /// Helper class for a Synchronization Variable |
| //////////////////////////////////////////////////////////////////////// |
| |
| class SynchVariable |
| { |
| // Synchronization Variable |
| public boolean _flag; |
| |
| // Constructor |
| SynchVariable() |
| { |
| _flag = false; |
| } |
| |
| // set Flag to true |
| public void set() |
| { |
| _flag = true; |
| } |
| |
| // get value |
| public boolean value() |
| { |
| return _flag; |
| } |
| |
| // reset Flag to true |
| public void reset() |
| { |
| _flag = false; |
| } |
| } |
| |
| // End of file. |