Public Member Functions | Private Attributes

TAO::ServerRequestInterceptor_Adapter_Impl Class Reference

ServerRequestInterceptor_Adapter_Impl. More...

#include <ServerInterceptorAdapter.h>

Inheritance diagram for TAO::ServerRequestInterceptor_Adapter_Impl:
Inheritance graph
[legend]
Collaboration diagram for TAO::ServerRequestInterceptor_Adapter_Impl:
Collaboration graph
[legend]

List of all members.

Public Member Functions

 ServerRequestInterceptor_Adapter_Impl (void)
 Constructor.
virtual void add_interceptor (PortableInterceptor::ServerRequestInterceptor_ptr interceptor)
 Register an interceptor.
virtual void add_interceptor (PortableInterceptor::ServerRequestInterceptor_ptr interceptor, const CORBA::PolicyList &policies)
virtual void destroy_interceptors (void)
virtual TAO::PICurrent_Impl * allocate_pi_current (void)
virtual void deallocate_pi_current (TAO::PICurrent_Impl *picurrent)
virtual void execute_command (TAO_ServerRequest &server_request, TAO::Upcall_Command &command)
void popTSC (TAO_ORB_Core *orb_core)
void pushTSC (TAO_ORB_Core *orb_core)
PortableInterceptor Server Side Interception Points

Each of these methods corresponds to a server side interception point.

void receive_request_service_contexts (TAO_ServerRequest &server_request, TAO::Argument *const args[], size_t nargs, void *servant_upcall, CORBA::TypeCode_ptr const *exceptions, CORBA::ULong nexceptions)
void receive_request (TAO_ServerRequest &server_request, TAO::Argument *const args[], size_t nargs, void *servant_upcall, CORBA::TypeCode_ptr const *exceptions, CORBA::ULong nexceptions)
 This method an "intermediate" server side interception point.
void send_reply (TAO_ServerRequest &server_request, TAO::Argument *const args[], size_t nargs, void *servant_upcall, CORBA::TypeCode_ptr const *exceptions, CORBA::ULong nexceptions)
void send_exception (TAO_ServerRequest &server_request, TAO::Argument *const args[], size_t nargs, void *servant_upcall, CORBA::TypeCode_ptr const *exceptions, CORBA::ULong nexceptions)
void send_other (TAO_ServerRequest &server_request, TAO::Argument *const args[], size_t nargs, void *servant_upcall, CORBA::TypeCode_ptr const *exceptions, CORBA::ULong nexceptions)

Private Attributes

ServerRequestInterceptor_List interceptor_list_
 List of registered interceptors.

Detailed Description

ServerRequestInterceptor_Adapter_Impl.

A convenient helper class to invoke registered server request interceptor(s).

Definition at line 67 of file ServerInterceptorAdapter.h.


Constructor & Destructor Documentation

TAO::ServerRequestInterceptor_Adapter_Impl::ServerRequestInterceptor_Adapter_Impl ( void   ) 

Constructor.

Definition at line 23 of file ServerInterceptorAdapter.cpp.

{
}


Member Function Documentation

void TAO::ServerRequestInterceptor_Adapter_Impl::add_interceptor ( PortableInterceptor::ServerRequestInterceptor_ptr  interceptor  )  [virtual]

Register an interceptor.

Definition at line 502 of file ServerInterceptorAdapter.cpp.

{
  this->interceptor_list_.add_interceptor (interceptor);
}

void TAO::ServerRequestInterceptor_Adapter_Impl::add_interceptor ( PortableInterceptor::ServerRequestInterceptor_ptr  interceptor,
const CORBA::PolicyList &  policies 
) [virtual]

Definition at line 509 of file ServerInterceptorAdapter.cpp.

{
  this->interceptor_list_.add_interceptor (interceptor, policies);
}

TAO::PICurrent_Impl * TAO::ServerRequestInterceptor_Adapter_Impl::allocate_pi_current ( void   )  [virtual]

Definition at line 523 of file ServerInterceptorAdapter.cpp.

{
  TAO::PICurrent_Impl *pi = 0;
  ACE_NEW_RETURN (pi,
                  TAO::PICurrent_Impl,
                  pi);
  return pi;
}

void TAO::ServerRequestInterceptor_Adapter_Impl::deallocate_pi_current ( TAO::PICurrent_Impl *  picurrent  )  [virtual]

Definition at line 533 of file ServerInterceptorAdapter.cpp.

{
  delete picurrent;
}

void TAO::ServerRequestInterceptor_Adapter_Impl::destroy_interceptors ( void   )  [virtual]

Definition at line 517 of file ServerInterceptorAdapter.cpp.

{
  this->interceptor_list_.destroy_interceptors ();
}

void TAO::ServerRequestInterceptor_Adapter_Impl::execute_command ( TAO_ServerRequest server_request,
TAO::Upcall_Command &  command 
) [virtual]

Definition at line 540 of file ServerInterceptorAdapter.cpp.

{
  TAO::PICurrent_Guard const pi_guard (server_request,
                                       true  /* Copy TSC to RSC */);

  // The actual upcall.
  command.execute ();
}

void TAO::ServerRequestInterceptor_Adapter_Impl::popTSC ( TAO_ORB_Core orb_core  )  [inline]
void TAO::ServerRequestInterceptor_Adapter_Impl::pushTSC ( TAO_ORB_Core orb_core  )  [inline]
void TAO::ServerRequestInterceptor_Adapter_Impl::receive_request ( TAO_ServerRequest server_request,
TAO::Argument *const   args[],
size_t  nargs,
void *  servant_upcall,
CORBA::TypeCode_ptr const *  exceptions,
CORBA::ULong  nexceptions 
)

This method an "intermediate" server side interception point.

Definition at line 231 of file ServerInterceptorAdapter.cpp.

{
  // This method implements an "intermediate" server side interception
  // point.  Interceptors are invoked in the same order they were
  // pushed on to the flow stack.

  if (this->interceptor_list_.size() != server_request.interceptor_count ())
    {
      // This method (i.e. the receive_request() interception point)
      // should only be invoked if all of the interceptors registered
      // with the ORB were pushed on to the flow stack by one of the
      // starting endpoints (such as
      // receive_request_service_contexts()).  If the above condition
      // evaluates to "true," then it is likely that a starting
      // interception point was never invoked.  This is of course, an
      // internal error that must be corrected.
      throw ::CORBA::INTERNAL ();
    }

  TAO::ServerRequestInfo request_info (server_request,
                                       args,
                                       nargs,
                                       servant_upcall,
                                       exceptions,
                                       nexceptions);

  try
    {
      bool is_remote_request = !server_request.collocated ();

      for (size_t i = 0; i < server_request.interceptor_count (); ++i)
        {
          ServerRequestInterceptor_List::RegisteredInterceptor& registered =
            this->interceptor_list_.registered_interceptor (i);

          if (registered.details_.should_be_processed (is_remote_request))
            {
              registered.interceptor_->receive_request (&request_info);
            }

          // Note that no interceptors are pushed on to or popped off
          // of the flow stack in this interception point since it is
          // an intermediate interception point.
        }
    }
  catch (const ::PortableInterceptor::ForwardRequest& exc)
    {
      server_request.forward_location (exc.forward.in ());
      server_request.pi_reply_status (PortableInterceptor::LOCATION_FORWARD);
      server_request.reply_status (GIOP::LOCATION_FORWARD);
      this->send_other (server_request,
                        args,
                        nargs,
                        servant_upcall,
                        exceptions,
                        nexceptions);
    }

}

void TAO::ServerRequestInterceptor_Adapter_Impl::receive_request_service_contexts ( TAO_ServerRequest server_request,
TAO::Argument *const   args[],
size_t  nargs,
void *  servant_upcall,
CORBA::TypeCode_ptr const *  exceptions,
CORBA::ULong  nexceptions 
)

This method implements the "intermediate" server side interception point if the above ifdef is set to 1 and a starting intercetion point if it is not set to 1.

Note:
This method should have been the "starting" interception point according to the interceptor spec. This will be fixed once Bug 1369 is completely done.

NOTE: Yes, we have two versions of this. This is easier than messing around things in the same function, which is harder to read and could make the code buggier.

Definition at line 169 of file ServerInterceptorAdapter.cpp.

{
  // This method implements one of the "starting" server side
  // interception point if extended interceptors are not in place.

  try
    {
      // Copy the request scope current (RSC) to the thread scope
      // current (TSC) upon leaving this scope, i.e. just after the
      // receive_request_service_contexts() completes.  A "guard" is
      // used to make the copy also occur if an exception is thrown.
      TAO::PICurrent_Guard const pi_guard (server_request,
                                           false /* Copy RSC to TSC */);

      bool is_remote_request = !server_request.collocated ();

      TAO::ServerRequestInfo request_info (server_request,
                                           args,
                                           nargs,
                                           servant_upcall,
                                           exceptions,
                                           nexceptions);

      for (size_t i = 0 ; i < this->interceptor_list_.size(); ++i)
        {
          ServerRequestInterceptor_List::RegisteredInterceptor& registered =
            this->interceptor_list_.registered_interceptor (i);

          if (registered.details_.should_be_processed (is_remote_request))
            {
              registered.interceptor_->
                receive_request_service_contexts (&request_info);
            }

          // The starting interception point completed successfully.
          // Push the interceptor on to the flow stack.
          ++server_request.interceptor_count ();
        }
    }
  catch (const ::PortableInterceptor::ForwardRequest& exc)
    {
      server_request.forward_location (exc.forward.in ());
      server_request.pi_reply_status (PortableInterceptor::LOCATION_FORWARD);
      server_request.reply_status (GIOP::LOCATION_FORWARD);
      (void) this->send_other (server_request,
                               args,
                               nargs,
                               servant_upcall,
                               exceptions,
                               nexceptions);
    }
}

void TAO::ServerRequestInterceptor_Adapter_Impl::send_exception ( TAO_ServerRequest server_request,
TAO::Argument *const   args[],
size_t  nargs,
void *  servant_upcall,
CORBA::TypeCode_ptr const *  exceptions,
CORBA::ULong  nexceptions 
)

This method implements one of the "ending" server side interception points.

Definition at line 349 of file ServerInterceptorAdapter.cpp.

{
  // This is an "ending" server side interception point so we only
  // process the interceptors pushed on to the flow stack.

  bool is_remote_request = !server_request.collocated ();

  // Notice that the interceptors are processed in the opposite order
  // they were pushed onto the stack since this is an "ending" server
  // side interception point.

  TAO::ServerRequestInfo request_info (server_request,
                                       args,
                                       nargs,
                                       servant_upcall,
                                       exceptions,
                                       nexceptions);

  try
    {
      // Unwind the flow stack.
      size_t const len = server_request.interceptor_count ();
      for (size_t i = 0; i < len; ++i)
        {
          // Pop the interceptor off of the flow stack before it is
          // invoked.  This is necessary to prevent an interceptor
          // already invoked in this "ending" interception point from
          // being invoked in another "ending" interception point.
          --server_request.interceptor_count ();

          ServerRequestInterceptor_List::RegisteredInterceptor& registered =
            this->interceptor_list_.registered_interceptor (
              server_request.interceptor_count ());

          if (registered.details_.should_be_processed (is_remote_request))
            {
              registered.interceptor_->send_exception (&request_info);
            }
        }
    }
  catch (const ::PortableInterceptor::ForwardRequest& exc)
    {
      server_request.forward_location (exc.forward.in ());
      server_request.pi_reply_status (PortableInterceptor::LOCATION_FORWARD);
      server_request.reply_status (GIOP::LOCATION_FORWARD);
      this->send_other (server_request,
                        args,
                        nargs,
                        servant_upcall,
                        exceptions,
                        nexceptions);
    }
  catch ( ::CORBA::Exception& ex)
    {
      // The send_exception() interception point in the remaining
      // interceptors must be called so call this method (not the
      // interceptor's corresponding method) recursively.  The call is
      // made recursively since the caught exception must survive
      // until the remaining interceptors have been called.
      //
      // Note that the recursion will stop once the flow stack size
      // drops to zero, i.e., once each interceptor has been invoked.
      // This prevents infinite recursion from occuring.

      server_request.caught_exception (&ex);

      this->send_exception (server_request,
                            args,
                            nargs,
                            servant_upcall,
                            exceptions,
                            nexceptions);

      PortableInterceptor::ReplyStatus status =
        server_request.pi_reply_status ();

      // Only re-throw the exception if it hasn't been transformed by
      // the send_exception() interception point (e.g. to a
      // LOCATION_FORWARD).
      if (status == PortableInterceptor::SYSTEM_EXCEPTION
          || status == PortableInterceptor::USER_EXCEPTION)
        throw;
    }
}

void TAO::ServerRequestInterceptor_Adapter_Impl::send_other ( TAO_ServerRequest server_request,
TAO::Argument *const   args[],
size_t  nargs,
void *  servant_upcall,
CORBA::TypeCode_ptr const *  exceptions,
CORBA::ULong  nexceptions 
)

This method implements one of the "ending" server side interception points.

Definition at line 441 of file ServerInterceptorAdapter.cpp.

{
  // This is an "ending" server side interception point so we only
  // process the interceptors pushed on to the flow stack.

  bool is_remote_request = !server_request.collocated ();

  TAO::ServerRequestInfo request_info (server_request,
                                       args,
                                       nargs,
                                       servant_upcall,
                                       exceptions,
                                       nexceptions);

  // Notice that the interceptors are processed in the opposite order
  // they were pushed onto the stack since this is an "ending" server
  // side interception point.

  try
    {
      // Unwind the flow stack.
      size_t const len = server_request.interceptor_count ();
      for (size_t i = 0; i < len; ++i)
        {
          // Pop the interceptor off of the flow stack before it is
          // invoked.  This is necessary to prevent an interceptor
          // already invoked in this "ending" interception point from
          // being invoked in another "ending" interception point.
          --server_request.interceptor_count ();

          ServerRequestInterceptor_List::RegisteredInterceptor& registered =
            this->interceptor_list_.registered_interceptor (
              server_request.interceptor_count ());

          if (registered.details_.should_be_processed (is_remote_request))
            {
              registered.interceptor_->send_other (&request_info);
            }
        }
    }
  catch (const ::PortableInterceptor::ForwardRequest& exc)
    {
      server_request.forward_location (exc.forward.in ());
      server_request.pi_reply_status (PortableInterceptor::LOCATION_FORWARD);
      server_request.reply_status (GIOP::LOCATION_FORWARD);
      this->send_other (server_request,
                        args,
                        nargs,
                        servant_upcall,
                        exceptions,
                        nexceptions);
    }
}

void TAO::ServerRequestInterceptor_Adapter_Impl::send_reply ( TAO_ServerRequest server_request,
TAO::Argument *const   args[],
size_t  nargs,
void *  servant_upcall,
CORBA::TypeCode_ptr const *  exceptions,
CORBA::ULong  nexceptions 
)

This method implements one of the "ending" server side interception points.

Definition at line 299 of file ServerInterceptorAdapter.cpp.

{
  // This is an "ending" interception point so we only process the
  // interceptors pushed on to the flow stack.

  bool const is_remote_request = !server_request.collocated ();

  // Notice that the interceptors are processed in the opposite order
  // they were pushed onto the stack since this is an "ending"
  // interception point.

  TAO::ServerRequestInfo request_info (server_request,
                                       args,
                                       nargs,
                                       servant_upcall,
                                       exceptions,
                                       nexceptions);

  // Unwind the stack.
  size_t const len = server_request.interceptor_count ();
  for (size_t i = 0; i < len; ++i)
    {
      // Pop the interceptor off of the flow stack before it is
      // invoked.  This is necessary to prevent an interceptor already
      // invoked in this "ending" interception point from being
      // invoked in another "ending" interception point.
      --server_request.interceptor_count ();

      ServerRequestInterceptor_List::RegisteredInterceptor& registered =
        this->interceptor_list_.registered_interceptor (
          server_request.interceptor_count ());

      if (registered.details_.should_be_processed (is_remote_request))
        {
          registered.interceptor_->send_reply (&request_info);
        }
    }

  // The send_reply() interception point does not raise a
  // PortableInterceptor::ForwardRequest exception so there is no need
  // to attempt to catch it here.
}


Member Data Documentation

ServerRequestInterceptor_List TAO::ServerRequestInterceptor_Adapter_Impl::interceptor_list_ [private]

List of registered interceptors.

Definition at line 177 of file ServerInterceptorAdapter.h.


The documentation for this class was generated from the following files:
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Defines