- /*
- * @(#)ServerRequestImpl.java 1.73 04/04/07
- *
- * 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.corba;
-
- import org.omg.CORBA.Any;
- import org.omg.CORBA.Context;
- import org.omg.CORBA.NamedValue;
- import org.omg.CORBA.NVList;
- import org.omg.CORBA.TypeCode;
- import org.omg.CORBA.TCKind;
- import org.omg.CORBA.ServerRequest;
- import org.omg.CORBA.Bounds;
- import org.omg.CORBA.portable.InputStream;
- import org.omg.CORBA.portable.OutputStream;
- import org.omg.CORBA.CompletionStatus;
-
- import com.sun.corba.se.spi.orb.ORB ;
- import com.sun.corba.se.spi.protocol.CorbaMessageMediator;
-
- import com.sun.corba.se.spi.logging.CORBALogDomains ;
- import com.sun.corba.se.impl.logging.ORBUtilSystemException ;
-
- public class ServerRequestImpl extends ServerRequest {
-
- ///////////////////////////////////////////////////////////////////////////
- // data members
-
- private ORB _orb = null;
- private ORBUtilSystemException _wrapper = null;
- private String _opName = null;
- private NVList _arguments = null;
- private Context _ctx = null;
- private InputStream _ins = null;
-
- // booleans to check for various operation invocation restrictions
- private boolean _paramsCalled = false;
- private boolean _resultSet = false;
- private boolean _exceptionSet = false;
- private Any _resultAny = null;
- private Any _exception = null;
-
-
- public ServerRequestImpl (CorbaMessageMediator req, ORB orb) {
- _opName = req.getOperationName();
- _ins = (InputStream)req.getInputObject();
- _ctx = null; // if we support contexts, this would
- // presumably also be available on
- // the server invocation
- _orb = orb;
- _wrapper = ORBUtilSystemException.get( orb,
- CORBALogDomains.OA_INVOCATION ) ;
- }
-
- public String operation() {
- return _opName;
- }
-
- public void arguments(NVList args)
- {
- if (_paramsCalled)
- throw _wrapper.argumentsCalledMultiple() ;
-
- if (_exceptionSet)
- throw _wrapper.argumentsCalledAfterException() ;
-
- if (args == null )
- throw _wrapper.argumentsCalledNullArgs() ;
-
- _paramsCalled = true;
-
- NamedValue arg = null;
- for (int i=0; i < args.count() ; i++) {
- try {
- arg = args.item(i);
- } catch (Bounds e) {
- throw _wrapper.boundsCannotOccur(e) ;
- }
-
- try {
- if ((arg.flags() == org.omg.CORBA.ARG_IN.value) ||
- (arg.flags() == org.omg.CORBA.ARG_INOUT.value)) {
- // unmarshal the value into the Any
- arg.value().read_value(_ins, arg.value().type());
- }
- } catch ( Exception ex ) {
- throw _wrapper.badArgumentsNvlist( ex ) ;
- }
- }
-
- // hang on to the NVList for marshaling the result
- _arguments = args;
-
- _orb.getPIHandler().setServerPIInfo( _arguments );
- _orb.getPIHandler().invokeServerPIIntermediatePoint();
- }
-
- public void set_result(Any res) {
- // check for invocation restrictions
- if (!_paramsCalled)
- throw _wrapper.argumentsNotCalled() ;
- if (_resultSet)
- throw _wrapper.setResultCalledMultiple() ;
- if (_exceptionSet)
- throw _wrapper.setResultAfterException() ;
- if ( res == null )
- throw _wrapper.setResultCalledNullArgs() ;
-
- _resultAny = res;
- _resultSet = true;
-
- // Notify portable interceptors of the result so that
- // ServerRequestInfo.result() functions as desired.
- _orb.getPIHandler().setServerPIInfo( _resultAny );
-
- // actual marshaling of the reply msg header and params takes place
- // after the DSI returns control to the ORB.
- }
-
- public void set_exception(Any exc)
- {
- // except can be called by the DIR at any time (CORBA 2.2 section 6.3).
-
- if ( exc == null )
- throw _wrapper.setExceptionCalledNullArgs() ;
-
- // Ensure that the Any contains a SystemException or a
- // UserException. If the UserException is not a declared exception,
- // the client will get an UNKNOWN exception.
- TCKind kind = exc.type().kind();
- if ( kind != TCKind.tk_except )
- throw _wrapper.setExceptionCalledBadType() ;
-
- _exception = exc;
-
- // Inform Portable interceptors of the exception that was set
- // so sending_exception can return the right value.
- _orb.getPIHandler().setServerPIExceptionInfo( _exception );
-
- // The user can only call arguments once and not at all after
- // set_exception. (internal flags ensure this). However, the user
- // can call set_exception multiple times. Therefore, we only
- // invoke receive_request the first time set_exception is
- // called (if they haven't already called arguments).
- if( !_exceptionSet && !_paramsCalled ) {
- // We need to invoke intermediate points here.
- _orb.getPIHandler().invokeServerPIIntermediatePoint();
- }
-
- _exceptionSet = true;
-
- // actual marshaling of the reply msg header and exception takes place
- // after the DSI returns control to the ORB.
- }
-
-
- /** This is called from the ORB after the DynamicImplementation.invoke
- * returns. Here we set the result if result() has not already been called.
- * @return the exception if there is one (then ORB will not call
- * marshalReplyParams()) otherwise return null.
- */
- public Any checkResultCalled()
- {
- // Two things to be checked (CORBA 2.2 spec, section 6.3):
- // 1. Unless it calls set_exception(), the DIR must call arguments()
- // exactly once, even if the operation signature contains
- // no parameters.
- // 2. Unless set_exception() is called, if the invoked operation has a
- // non-void result type, set_result() must be called exactly once
- // before the DIR returns.
-
- if ( _paramsCalled && _resultSet ) // normal invocation return
- return null;
- else if ( _paramsCalled && !_resultSet && !_exceptionSet ) {
- try {
- // Neither a result nor an exception has been set.
- // Assume that the return type is void. If this is not so,
- // the client will throw a MARSHAL exception while
- // unmarshaling the return value.
- TypeCode result_tc = _orb.get_primitive_tc(
- org.omg.CORBA.TCKind.tk_void);
- _resultAny = _orb.create_any();
- _resultAny.type(result_tc);
- _resultSet = true;
-
- return null;
- } catch ( Exception ex ) {
- throw _wrapper.dsiResultException(
- CompletionStatus.COMPLETED_MAYBE, ex ) ;
- }
- } else if ( _exceptionSet )
- return _exception;
- else {
- throw _wrapper.dsimethodNotcalled(
- CompletionStatus.COMPLETED_MAYBE ) ;
- }
- }
-
- /** This is called from the ORB after the DynamicImplementation.invoke
- * returns. Here we marshal the return value and inout/out params.
- */
- public void marshalReplyParams(OutputStream os)
- {
- // marshal the operation return value
- _resultAny.write_value(os);
-
- // marshal the inouts/outs
- NamedValue arg = null;
-
- for (int i=0; i < _arguments.count() ; i++) {
- try {
- arg = _arguments.item(i);
- } catch (Bounds e) {}
-
- if ((arg.flags() == org.omg.CORBA.ARG_OUT.value) ||
- (arg.flags() == org.omg.CORBA.ARG_INOUT.value)) {
- arg.value().write_value(os);
- }
- }
- }
-
- public Context ctx()
- {
- if ( !_paramsCalled || _resultSet || _exceptionSet )
- throw _wrapper.contextCalledOutOfOrder() ;
-
- throw _wrapper.contextNotImplemented() ;
- }
- }