- /*
- * @(#)CorbaServerRequestDispatcherImpl.java 1.76 04/06/21
- *
- * Copyright 2004 Sun Microsystems, Inc. All rights reserved.
- * SUN PROPRIETARY/CONFIDENTIAL. Use is subject to license terms.
- */
- /*
- * Licensed Materials - Property of IBM
- * RMI-IIOP v1.0
- * Copyright IBM Corp. 1998 1999 All Rights Reserved
- *
- * US Government Users Restricted Rights - Use, duplication or
- * disclosure restricted by GSA ADP Schedule Contract with IBM Corp.
- */
-
-
- package com.sun.corba.se.impl.protocol;
-
- import org.omg.PortableServer.Servant ;
-
- import org.omg.CORBA.SystemException;
- import org.omg.CORBA.INTERNAL;
- import org.omg.CORBA.UNKNOWN;
- import org.omg.CORBA.CompletionStatus;
- import org.omg.CORBA.Any;
-
- import org.omg.CORBA.portable.InvokeHandler;
- import org.omg.CORBA.portable.InputStream;
- import org.omg.CORBA.portable.OutputStream;
- import org.omg.CORBA.portable.UnknownException;
- import org.omg.CORBA.portable.ResponseHandler;
-
- import com.sun.org.omg.SendingContext.CodeBase;
-
- import com.sun.corba.se.pept.encoding.OutputObject;
- import com.sun.corba.se.pept.protocol.MessageMediator;
-
- import com.sun.corba.se.spi.orb.ORB;
- import com.sun.corba.se.spi.orb.ORBVersion;
- import com.sun.corba.se.spi.orb.ORBVersionFactory;
- import com.sun.corba.se.spi.ior.IOR ;
- import com.sun.corba.se.spi.ior.ObjectKey;
- import com.sun.corba.se.spi.ior.ObjectKeyTemplate;
- import com.sun.corba.se.spi.ior.ObjectAdapterId;
- import com.sun.corba.se.spi.oa.ObjectAdapterFactory;
- import com.sun.corba.se.spi.oa.ObjectAdapter;
- import com.sun.corba.se.spi.oa.OAInvocationInfo;
- import com.sun.corba.se.spi.oa.OADestroyed;
- import com.sun.corba.se.spi.oa.NullServant;
- import com.sun.corba.se.spi.protocol.CorbaMessageMediator;
- import com.sun.corba.se.spi.protocol.CorbaServerRequestDispatcher;
- import com.sun.corba.se.spi.protocol.ForwardException ;
- import com.sun.corba.se.spi.protocol.RequestDispatcherRegistry;
- import com.sun.corba.se.spi.transport.CorbaConnection;
- import com.sun.corba.se.spi.logging.CORBALogDomains;
- import com.sun.corba.se.spi.ior.iiop.GIOPVersion;
-
- import com.sun.corba.se.impl.protocol.SpecialMethod ;
- import com.sun.corba.se.spi.servicecontext.ServiceContext;
- import com.sun.corba.se.spi.servicecontext.ServiceContexts;
- import com.sun.corba.se.spi.servicecontext.UEInfoServiceContext;
- import com.sun.corba.se.spi.servicecontext.CodeSetServiceContext;
- import com.sun.corba.se.spi.servicecontext.SendingContextServiceContext;
- import com.sun.corba.se.spi.servicecontext.ORBVersionServiceContext;
-
- import com.sun.corba.se.impl.corba.ServerRequestImpl ;
- import com.sun.corba.se.impl.encoding.MarshalInputStream;
- import com.sun.corba.se.impl.encoding.MarshalOutputStream;
- import com.sun.corba.se.impl.encoding.CodeSetComponentInfo;
- import com.sun.corba.se.impl.encoding.OSFCodeSetRegistry;
- import com.sun.corba.se.impl.orbutil.ORBConstants;
- import com.sun.corba.se.impl.orbutil.ORBUtility;
- import com.sun.corba.se.impl.protocol.RequestCanceledException;
- import com.sun.corba.se.impl.logging.ORBUtilSystemException;
- import com.sun.corba.se.impl.logging.POASystemException;
-
- public class CorbaServerRequestDispatcherImpl
- implements CorbaServerRequestDispatcher
- {
- protected ORB orb; // my ORB instance
- private ORBUtilSystemException wrapper ;
- private POASystemException poaWrapper ;
-
- // Added from last version because it broke the build - RTW
- // XXX remove me and rebuild: probably no longer needed
- // public static final int UNKNOWN_EXCEPTION_INFO_ID = 9;
-
- public CorbaServerRequestDispatcherImpl(ORB orb)
- {
- this.orb = orb;
- wrapper = ORBUtilSystemException.get( orb,
- CORBALogDomains.RPC_PROTOCOL ) ;
- poaWrapper = POASystemException.get( orb,
- CORBALogDomains.RPC_PROTOCOL ) ;
- }
-
- /** XXX/REVISIT:
- * We do not want to look for a servant in the POA/ServantManager case,
- * but we could in most other cases. The OA could have a method that
- * returns true if the servant MAY exist, and false only if the servant
- * definitely DOES NOT exist.
- *
- * XXX/REVISIT:
- * We may wish to indicate OBJECT_HERE by some mechanism other than
- * returning a null result.
- *
- * Called from ORB.locate when a LocateRequest arrives.
- * Result is not always absolutely correct: may indicate OBJECT_HERE
- * for non-existent objects, which is resolved on invocation. This
- * "bug" is unavoidable, since in general the object may be destroyed
- * between a locate and a request. Note that this only checks that
- * the appropriate ObjectAdapter is available, not that the servant
- * actually exists.
- * Need to signal one of OBJECT_HERE, OBJECT_FORWARD, OBJECT_NOT_EXIST.
- * @return Result is null if object is (possibly) implemented here, otherwise
- * an IOR indicating objref to forward the request to.
- * @exception OBJECT_NOT_EXIST is thrown if we know the object does not
- * exist here, and we are not forwarding.
- */
- public IOR locate(ObjectKey okey)
- {
- try {
- if (orb.subcontractDebugFlag)
- dprint(".locate->");
-
- ObjectKeyTemplate oktemp = okey.getTemplate() ;
-
- try {
- checkServerId(okey);
- } catch (ForwardException fex) {
- return fex.getIOR() ;
- }
-
- // Called only for its side-effect of throwing appropriate exceptions
- findObjectAdapter(oktemp);
-
- return null ;
- } finally {
- if (orb.subcontractDebugFlag)
- dprint(".locate<-");
- }
- }
-
- public void dispatch(MessageMediator messageMediator)
- {
- CorbaMessageMediator request = (CorbaMessageMediator) messageMediator;
- try {
- if (orb.subcontractDebugFlag) {
- dprint(".dispatch->: " + opAndId(request));
- }
-
- // to set the codebase information, if any transmitted; and also
- // appropriate ORB Version.
- consumeServiceContexts(request);
-
- // Now that we have the service contexts processed and the
- // correct ORBVersion set, we must finish initializing the
- // stream.
- ((MarshalInputStream)request.getInputObject())
- .performORBVersionSpecificInit();
-
- ObjectKey okey = request.getObjectKey();
-
- // Check that this server is the right server
- try {
- checkServerId(okey);
- } catch (ForwardException fex) {
- if (orb.subcontractDebugFlag) {
- dprint(".dispatch: " + opAndId(request)
- + ": bad server id");
- }
-
- request.getProtocolHandler()
- .createLocationForward(request, fex.getIOR(), null);
- return;
- }
-
- String operation = request.getOperationName();
- ObjectAdapter objectAdapter = null ;
-
- try {
- byte[] objectId = okey.getId().getId() ;
- ObjectKeyTemplate oktemp = okey.getTemplate() ;
- objectAdapter = findObjectAdapter(oktemp);
-
- java.lang.Object servant = getServantWithPI(request, objectAdapter,
- objectId, oktemp, operation);
-
- dispatchToServant(servant, request, objectId, objectAdapter);
- } catch (ForwardException ex) {
- if (orb.subcontractDebugFlag) {
- dprint(".dispatch: " + opAndId(request)
- + ": ForwardException caught");
- }
-
- // Thrown by Portable Interceptors from InterceptorInvoker,
- // through Response constructor.
- request.getProtocolHandler()
- .createLocationForward(request, ex.getIOR(), null);
- } catch (OADestroyed ex) {
- if (orb.subcontractDebugFlag) {
- dprint(".dispatch: " + opAndId(request)
- + ": OADestroyed exception caught");
- }
-
- // DO NOT CALL THIS HERE:
- // releaseServant(objectAdapter);
- // The problem is that OADestroyed is only thrown by oa.enter, in
- // which case oa.exit should NOT be called, and neither should
- // the invocationInfo stack be popped.
-
- // Destroyed POAs can be recreated by normal adapter activation.
- // So just restart the dispatch.
- dispatch(request);
- } catch (RequestCanceledException ex) {
- if (orb.subcontractDebugFlag) {
- dprint(".dispatch: " + opAndId(request)
- + ": RequestCanceledException caught");
- }
-
- // IDLJ generated non-tie based skeletons do not catch the
- // RequestCanceledException. Rethrow the exception, which will
- // cause the worker thread to unwind the dispatch and wait for
- // other requests.
- throw ex;
- } catch (UnknownException ex) {
- if (orb.subcontractDebugFlag) {
- dprint(".dispatch: " + opAndId(request)
- + ": UnknownException caught " + ex);
- }
-
- // RMIC generated tie skeletons convert all Throwable exception
- // types (including RequestCanceledException, ThreadDeath)
- // thrown during reading fragments into UnknownException.
- // If RequestCanceledException was indeed raised,
- // then rethrow it, which will eventually cause the worker
- // thread to unstack the dispatch and wait for other requests.
- if (ex.originalEx instanceof RequestCanceledException) {
- throw (RequestCanceledException) ex.originalEx;
- }
-
- ServiceContexts contexts = new ServiceContexts(orb);
- UEInfoServiceContext usc = new UEInfoServiceContext(
- ex.originalEx);
-
- contexts.put( usc ) ;
-
- SystemException sysex = wrapper.unknownExceptionInDispatch(
- CompletionStatus.COMPLETED_MAYBE, ex ) ;
- request.getProtocolHandler()
- .createSystemExceptionResponse(request, sysex,
- contexts);
- } catch (Throwable ex) {
- if (orb.subcontractDebugFlag) {
- dprint(".dispatch: " + opAndId(request)
- + ": other exception " + ex);
- }
- request.getProtocolHandler()
- .handleThrowableDuringServerDispatch(
- request, ex, CompletionStatus.COMPLETED_MAYBE);
- }
- return;
- } finally {
- if (orb.subcontractDebugFlag) {
- dprint(".dispatch<-: " + opAndId(request));
- }
- }
- }
-
- private void releaseServant(ObjectAdapter objectAdapter)
- {
- try {
- if (orb.subcontractDebugFlag) {
- dprint(".releaseServant->");
- }
-
- if (objectAdapter == null) {
- if (orb.subcontractDebugFlag) {
- dprint(".releaseServant: null object adapter");
- }
- return ;
- }
-
- try {
- objectAdapter.returnServant();
- } finally {
- objectAdapter.exit();
- orb.popInvocationInfo() ;
- }
- } finally {
- if (orb.subcontractDebugFlag) {
- dprint(".releaseServant<-");
- }
- }
- }
-
- // Note that objectAdapter.enter() must be called before getServant.
- private java.lang.Object getServant(ObjectAdapter objectAdapter, byte[] objectId,
- String operation)
- throws OADestroyed
- {
- try {
- if (orb.subcontractDebugFlag) {
- dprint(".getServant->");
- }
-
- OAInvocationInfo info = objectAdapter.makeInvocationInfo(objectId);
- info.setOperation(operation);
- orb.pushInvocationInfo(info);
- objectAdapter.getInvocationServant(info);
- return info.getServantContainer() ;
- } finally {
- if (orb.subcontractDebugFlag) {
- dprint(".getServant<-");
- }
- }
- }
-
- protected java.lang.Object getServantWithPI(CorbaMessageMediator request,
- ObjectAdapter objectAdapter,
- byte[] objectId, ObjectKeyTemplate oktemp, String operation)
- throws OADestroyed
- {
- try {
- if (orb.subcontractDebugFlag) {
- dprint(".getServantWithPI->");
- }
-
- // Prepare Portable Interceptors for a new server request
- // and invoke receive_request_service_contexts. The starting
- // point may throw a SystemException or ForwardException.
- orb.getPIHandler().initializeServerPIInfo(request, objectAdapter,
- objectId, oktemp);
- orb.getPIHandler().invokeServerPIStartingPoint();
-
- objectAdapter.enter() ;
-
- // This must be set just after the enter so that exceptions thrown by
- // enter do not cause
- // the exception reply to pop the thread stack and do an extra oa.exit.
- if (request != null)
- request.setExecuteReturnServantInResponseConstructor(true);
-
- java.lang.Object servant = getServant(objectAdapter, objectId,
- operation);
-
- // Note: we do not know the MDI on a null servant.
- // We only end up in that situation if _non_existent called,
- // so that the following handleNullServant call does not throw an
- // exception.
- String mdi = "unknown" ;
-
- if (servant instanceof NullServant)
- handleNullServant(operation, (NullServant)servant);
- else
- mdi = objectAdapter.getInterfaces(servant, objectId)[0] ;
-
- orb.getPIHandler().setServerPIInfo(servant, mdi);
-
- if (((servant != null) &&
- !(servant instanceof org.omg.CORBA.DynamicImplementation) &&
- !(servant instanceof org.omg.PortableServer.DynamicImplementation)) ||
- (SpecialMethod.getSpecialMethod(operation) != null)) {
- orb.getPIHandler().invokeServerPIIntermediatePoint();
- }
-
- return servant ;
- } finally {
- if (orb.subcontractDebugFlag) {
- dprint(".getServantWithPI<-");
- }
- }
- }
-
- protected void checkServerId(ObjectKey okey)
- {
- try {
- if (orb.subcontractDebugFlag) {
- dprint(".checkServerId->");
- }
-
- ObjectKeyTemplate oktemp = okey.getTemplate() ;
- int sId = oktemp.getServerId() ;
- int scid = oktemp.getSubcontractId() ;
-
- if (!orb.isLocalServerId(scid, sId)) {
- if (orb.subcontractDebugFlag) {
- dprint(".checkServerId: bad server id");
- }
-
- orb.handleBadServerId(okey);
- }
- } finally {
- if (orb.subcontractDebugFlag) {
- dprint(".checkServerId<-");
- }
- }
- }
-
- private ObjectAdapter findObjectAdapter(ObjectKeyTemplate oktemp)
- {
- try {
- if (orb.subcontractDebugFlag) {
- dprint(".findObjectAdapter->");
- }
-
- RequestDispatcherRegistry scr = orb.getRequestDispatcherRegistry() ;
- int scid = oktemp.getSubcontractId() ;
- ObjectAdapterFactory oaf = scr.getObjectAdapterFactory(scid);
- if (oaf == null) {
- if (orb.subcontractDebugFlag) {
- dprint(".findObjectAdapter: failed to find ObjectAdapterFactory");
- }
-
- throw wrapper.noObjectAdapterFactory() ;
- }
-
- ObjectAdapterId oaid = oktemp.getObjectAdapterId() ;
- ObjectAdapter oa = oaf.find(oaid);
-
- if (oa == null) {
- if (orb.subcontractDebugFlag) {
- dprint(".findObjectAdapter: failed to find ObjectAdaptor");
- }
-
- throw wrapper.badAdapterId() ;
- }
-
- return oa ;
- } finally {
- if (orb.subcontractDebugFlag) {
- dprint(".findObjectAdapter<-");
- }
- }
- }
-
- /** Always throws OBJECT_NOT_EXIST if operation is not a special method.
- * If operation is _non_existent or _not_existent, this will just
- * return without performing any action, so that _non_existent can return
- * false. Always throws OBJECT_NOT_EXIST for any other special method.
- * Update for issue 4385.
- */
- protected void handleNullServant(String operation, NullServant nserv )
- {
- try {
- if (orb.subcontractDebugFlag) {
- dprint(".handleNullServant->: " + operation);
- }
-
- SpecialMethod specialMethod =
- SpecialMethod.getSpecialMethod(operation);
-
- if ((specialMethod == null) ||
- !specialMethod.isNonExistentMethod()) {
- if (orb.subcontractDebugFlag) {
- dprint(".handleNullServant: " + operation
- + ": throwing OBJECT_NOT_EXIST");
- }
-
- throw nserv.getException() ;
- }
- } finally {
- if (orb.subcontractDebugFlag) {
- dprint(".handleNullServant<-: " + operation);
- }
- }
- }
-
- protected void consumeServiceContexts(CorbaMessageMediator request)
- {
- try {
- if (orb.subcontractDebugFlag) {
- dprint(".consumeServiceContexts->: "
- + opAndId(request));
- }
-
- ServiceContexts ctxts = request.getRequestServiceContexts();
- ServiceContext sc ;
-
- GIOPVersion giopVersion = request.getGIOPVersion();
-
- // we cannot depend on this since for our local case, we do not send
- // in this service context. Can we rely on just the CodeSetServiceContext?
- // boolean rtSC = false; // Runtime ServiceContext
-
- boolean hasCodeSetContext = processCodeSetContext(request, ctxts);
-
- if (orb.subcontractDebugFlag) {
- dprint(".consumeServiceContexts: " + opAndId(request)
- + ": GIOP version: " + giopVersion);
- dprint(".consumeServiceContexts: " + opAndId(request)
- + ": as code set context? " + hasCodeSetContext);
- }
-
- sc = ctxts.get(
- SendingContextServiceContext.SERVICE_CONTEXT_ID ) ;
-
- if (sc != null) {
- SendingContextServiceContext scsc =
- (SendingContextServiceContext)sc ;
- IOR ior = scsc.getIOR() ;
-
- try {
- ((CorbaConnection)request.getConnection())
- .setCodeBaseIOR(ior);
- } catch (ThreadDeath td) {
- throw td ;
- } catch (Throwable t) {
- throw wrapper.badStringifiedIor( t ) ;
- }
- }
-
- // the RTSC is sent only once during session establishment. We
- // need to find out if the CodeBaseRef is already set. If yes,
- // then also the rtSC flag needs to be set to true
- // this is not possible for the LocalCase since there is no
- // IIOPConnection for the LocalCase
-
- // used for a case where we have JDK 1.3 supporting 1.0 protocol,
- // but sending 2 service contexts, that is not normal as per
- // GIOP rules, based on above information, we figure out that we
- // are talking to the legacy ORB and set the ORB Version Accordingly.
-
- // this special case tell us that it is legacy SUN orb
- // and not a foreign one
- // rtSC is not available for localcase due to which this generic
- // path would fail if relying on rtSC
- //if (giopVersion.equals(GIOPVersion.V1_0) && hasCodeSetContext && rtSC)
- boolean isForeignORB = false;
-
- if (giopVersion.equals(GIOPVersion.V1_0) && hasCodeSetContext) {
- if (orb.subcontractDebugFlag) {
- dprint(".consumeServiceCOntexts: " + opAndId(request)
- + ": Determined to be an old Sun ORB");
- }
-
- orb.setORBVersion(ORBVersionFactory.getOLD()) ;
- // System.out.println("setting legacy ORB version");
- } else {
- // If it didn't include our ORB version service context (below),
- // then it must be a foreign ORB.
- isForeignORB = true;
- }
-
- // try to get the ORBVersion sent as part of the ServiceContext
- // if any
- sc = ctxts.get( ORBVersionServiceContext.SERVICE_CONTEXT_ID ) ;
- if (sc != null) {
- ORBVersionServiceContext ovsc =
- (ORBVersionServiceContext) sc;
-
- ORBVersion version = ovsc.getVersion();
- orb.setORBVersion(version);
-
- isForeignORB = false;
- }
-
- if (isForeignORB) {
- if (orb.subcontractDebugFlag) {
- dprint(".consumeServiceContexts: " + opAndId(request)
- + ": Determined to be a foreign ORB");
- }
-
- orb.setORBVersion(ORBVersionFactory.getFOREIGN());
- }
- } finally {
- if (orb.subcontractDebugFlag) {
- dprint(".consumeServiceContexts<-: " + opAndId(request));
- }
- }
- }
-
- protected CorbaMessageMediator dispatchToServant(
- java.lang.Object servant,
- CorbaMessageMediator req,
- byte[] objectId, ObjectAdapter objectAdapter)
- {
- try {
- if (orb.subcontractDebugFlag) {
- dprint(".dispatchToServant->: " + opAndId(req));
- }
-
- CorbaMessageMediator response = null ;
-
- String operation = req.getOperationName() ;
-
- SpecialMethod method = SpecialMethod.getSpecialMethod(operation) ;
- if (method != null) {
- if (orb.subcontractDebugFlag) {
- dprint(".dispatchToServant: " + opAndId(req)
- + ": Handling special method");
- }
-
- response = method.invoke(servant, req, objectId, objectAdapter);
- return response ;
- }
-
- // Invoke on the servant using the portable DSI skeleton
- if (servant instanceof org.omg.CORBA.DynamicImplementation) {
- if (orb.subcontractDebugFlag) {
- dprint(".dispatchToServant: " + opAndId(req)
- + ": Handling old style DSI type servant");
- }
-
- org.omg.CORBA.DynamicImplementation dynimpl =
- (org.omg.CORBA.DynamicImplementation)servant;
- ServerRequestImpl sreq = new ServerRequestImpl(req, orb);
-
- // Note: When/if dynimpl.invoke calls arguments() or
- // set_exception() then intermediate points are run.
- dynimpl.invoke(sreq);
-
- response = handleDynamicResult(sreq, req);
- } else if (servant instanceof org.omg.PortableServer.DynamicImplementation) {
- if (orb.subcontractDebugFlag) {
- dprint(".dispatchToServant: " + opAndId(req)
- + ": Handling POA DSI type servant");
- }
-
- org.omg.PortableServer.DynamicImplementation dynimpl =
- (org.omg.PortableServer.DynamicImplementation)servant;
- ServerRequestImpl sreq = new ServerRequestImpl(req, orb);
-
- // Note: When/if dynimpl.invoke calls arguments() or
- // set_exception() then intermediate points are run.
- dynimpl.invoke(sreq);
-
- response = handleDynamicResult(sreq, req);
- } else {
- if (orb.subcontractDebugFlag) {
- dprint(".dispatchToServant: " + opAndId(req)
- + ": Handling invoke handler type servant");
- }
-
- InvokeHandler invhandle = (InvokeHandler)servant ;
-
- OutputStream stream =
- (OutputStream)invhandle._invoke(
- operation,
- (org.omg.CORBA.portable.InputStream)req.getInputObject(),
- req);
- response = (CorbaMessageMediator)
- ((OutputObject)stream).getMessageMediator();
- }
-
- return response ;
- } finally {
- if (orb.subcontractDebugFlag) {
- dprint(".dispatchToServant<-: " + opAndId(req));
- }
- }
- }
-
- protected CorbaMessageMediator handleDynamicResult(
- ServerRequestImpl sreq,
- CorbaMessageMediator req)
- {
- try {
- if (orb.subcontractDebugFlag) {
- dprint(".handleDynamicResult->: " + opAndId(req));
- }
-
- CorbaMessageMediator response = null ;
-
- // Check if ServerRequestImpl.result() has been called
- Any excany = sreq.checkResultCalled();
-
- if (excany == null) { // normal return
- if (orb.subcontractDebugFlag) {
- dprint(".handleDynamicResult: " + opAndId(req)
- + ": handling normal result");
- }
-
- // Marshal out/inout/return parameters into the ReplyMessage
- response = sendingReply(req);
- OutputStream os = (OutputStream) response.getOutputObject();
- sreq.marshalReplyParams(os);
- } else {
- if (orb.subcontractDebugFlag) {
- dprint(".handleDynamicResult: " + opAndId(req)
- + ": handling error");
- }
-
- response = sendingReply(req, excany);
- }
-
- return response ;
- } finally {
- if (orb.subcontractDebugFlag) {
- dprint(".handleDynamicResult<-: " + opAndId(req));
- }
- }
- }
-
- protected CorbaMessageMediator sendingReply(CorbaMessageMediator req)
- {
- try {
- if (orb.subcontractDebugFlag) {
- dprint(".sendingReply->: " + opAndId(req));
- }
-
- ServiceContexts scs = new ServiceContexts(orb);
- return req.getProtocolHandler().createResponse(req, scs);
- } finally {
- if (orb.subcontractDebugFlag) {
- dprint(".sendingReply<-: " + opAndId(req));
- }
- }
- }
-
- /** Must always be called, just after the servant's method returns.
- * Creates the ReplyMessage header and puts in the transaction context
- * if necessary.
- */
- protected CorbaMessageMediator sendingReply(CorbaMessageMediator req, Any excany)
- {
- try {
- if (orb.subcontractDebugFlag) {
- dprint(".sendingReply/Any->: " + opAndId(req));
- }
-
- ServiceContexts scs = new ServiceContexts(orb);
-
- // Check if the servant set a SystemException or
- // UserException
- CorbaMessageMediator resp;
- String repId=null;
- try {
- repId = excany.type().id();
- } catch (org.omg.CORBA.TypeCodePackage.BadKind e) {
- throw wrapper.problemWithExceptionTypecode( e ) ;
- }
-
- if (ORBUtility.isSystemException(repId)) {
- if (orb.subcontractDebugFlag) {
- dprint(".sendingReply/Any: " + opAndId(req)
- + ": handling system exception");
- }
-
- // Get the exception object from the Any
- InputStream in = excany.create_input_stream();
- SystemException ex = ORBUtility.readSystemException(in);
- // Marshal the exception back
- resp = req.getProtocolHandler()
- .createSystemExceptionResponse(req, ex, scs);
- } else {
- if (orb.subcontractDebugFlag) {
- dprint(".sendingReply/Any: " + opAndId(req)
- + ": handling user exception");
- }
-
- resp = req.getProtocolHandler()
- .createUserExceptionResponse(req, scs);
- OutputStream os = (OutputStream)resp.getOutputObject();
- excany.write_value(os);
- }
-
- return resp;
- } finally {
- if (orb.subcontractDebugFlag) {
- dprint(".sendingReply/Any<-: " + opAndId(req));
- }
- }
- }
-
- /**
- * Handles setting the connection's code sets if required.
- * Returns true if the CodeSetContext was in the request, false
- * otherwise.
- */
- protected boolean processCodeSetContext(
- CorbaMessageMediator request, ServiceContexts contexts)
- {
- try {
- if (orb.subcontractDebugFlag) {
- dprint(".processCodeSetContext->: " + opAndId(request));
- }
-
- ServiceContext sc = contexts.get(
- CodeSetServiceContext.SERVICE_CONTEXT_ID);
- if (sc != null) {
- // Somehow a code set service context showed up in the local case.
- if (request.getConnection() == null) {
- return true;
- }
-
- // If it's GIOP 1.0, it shouldn't have this context at all. Our legacy
- // ORBs sent it and we need to know if it's here to make ORB versioning
- // decisions, but we don't use the contents.
- if (request.getGIOPVersion().equals(GIOPVersion.V1_0)) {
- return true;
- }
-
- CodeSetServiceContext cssc = (CodeSetServiceContext)sc ;
- CodeSetComponentInfo.CodeSetContext csctx = cssc.getCodeSetContext();
-
- // Note on threading:
- //
- // getCodeSetContext and setCodeSetContext are synchronized
- // on the Connection. At worst, this will result in
- // multiple threads entering this block and calling
- // setCodeSetContext but not actually changing the
- // values on the Connection.
- //
- // Alternative would be to lock the connection for the
- // whole block, but it's fine either way.
-
- // The connection's codeSetContext is null until we've received a
- // request with a code set context with the negotiated code sets.
- if (((CorbaConnection)request.getConnection())
- .getCodeSetContext() == null)
- {
-
- // Use these code sets on this connection
- if (orb.subcontractDebugFlag) {
- dprint(".processCodeSetContext: " + opAndId(request)
- + ": Setting code sets to: " + csctx);
- }
-
- ((CorbaConnection)request.getConnection())
- .setCodeSetContext(csctx);
-
- // We had to read the method name using ISO 8859-1
- // (which is the default in the CDRInputStream for
- // char data), but now we may have a new char
- // code set. If it isn't ISO8859-1, we must tell
- // the CDR stream to null any converter references
- // it has created so that it will reacquire
- // the code sets again using the new info.
- //
- // This should probably compare with the stream's
- // char code set rather than assuming it's ISO8859-1.
- // (However, the operation name is almost certainly
- // ISO8859-1 or ASCII.)
- if (csctx.getCharCodeSet() !=
- OSFCodeSetRegistry.ISO_8859_1.getNumber()) {
- ((MarshalInputStream)request.getInputObject())
- .resetCodeSetConverters();
- }
- }
- }
-
- // If no code set information is ever sent from the client,
- // the server will use ISO8859-1 for char and throw an
- // exception for any wchar transmissions.
- //
- // In the local case, we use ORB provided streams for
- // marshaling and unmarshaling. Currently, they use
- // ISO8859-1 for char/string and UTF16 for wchar/wstring.
- return sc != null ;
- } finally {
- if (orb.subcontractDebugFlag) {
- dprint(".processCodeSetContext<-: " + opAndId(request));
- }
- }
- }
-
- protected void dprint(String msg)
- {
- ORBUtility.dprint("CorbaServerRequestDispatcherImpl", msg);
- }
-
- protected String opAndId(CorbaMessageMediator mediator)
- {
- return ORBUtility.operationNameAndRequestId(mediator);
- }
- }
-
- // End of file.
-