00001 // -*- C++ -*- 00002 /** 00003 * @file EC_ProxySupplier.h 00004 * 00005 * EC_ProxySupplier.h,v 1.49 2006/03/14 06:14:25 jtc Exp 00006 * 00007 * @author Carlos O'Ryan (coryan@cs.wustl.edu) 00008 * 00009 * Based on previous work by Tim Harrison (harrison@cs.wustl.edu) and 00010 * other members of the DOC group. More details can be found in: 00011 * 00012 * http://doc.ece.uci.edu/~coryan/EC/index.html 00013 */ 00014 00015 #ifndef TAO_EC_PROXYSUPPLIER_H 00016 #define TAO_EC_PROXYSUPPLIER_H 00017 00018 #include /**/ "ace/pre.h" 00019 00020 #include "orbsvcs/RtecEventChannelAdminS.h" 00021 00022 #include "orbsvcs/Event/EC_Filter.h" 00023 00024 #if !defined (ACE_LACKS_PRAGMA_ONCE) 00025 # pragma once 00026 #endif /* ACE_LACKS_PRAGMA_ONCE */ 00027 00028 TAO_BEGIN_VERSIONED_NAMESPACE_DECL 00029 00030 class TAO_EC_Event_Channel_Base; 00031 class TAO_EC_ProxyPushConsumer; 00032 00033 /** 00034 * @class TAO_EC_ProxyPushSupplier 00035 * 00036 * @brief ProxyPushSupplier 00037 * 00038 * Implement the RtecEventChannelAdmin::ProxyPushSupplier interface, 00039 * remember that this class is used to communicate with a 00040 * PushConsumer, so, in effect, this is the ambassador for a 00041 * consumer inside the event channel. 00042 * 00043 * <H2>Memory Management</H2> 00044 * It does not assume ownership of the TAO_EC_Dispatching object. 00045 * It makes a copy of the ConsumerQOS and the consumer object 00046 * reference. 00047 * 00048 * <H2>Locking</H2> 00049 * Locking is strategized, the event channel acts as a factory for 00050 * the locking strategies. 00051 * 00052 * @todo We don't need to provide a trivial filter, the object itself 00053 * could short-circuit the filter() ---> push() cycle when the EC 00054 * is properly configured, we need to explore this... 00055 */ 00056 class TAO_RTEvent_Serv_Export TAO_EC_ProxyPushSupplier : public TAO_EC_Filter 00057 { 00058 public: 00059 typedef RtecEventChannelAdmin::ProxyPushSupplier Interface; 00060 typedef RtecEventChannelAdmin::ProxyPushSupplier_var _var_type; 00061 typedef RtecEventChannelAdmin::ProxyPushSupplier_ptr _ptr_type; 00062 00063 /// Constructor... 00064 TAO_EC_ProxyPushSupplier (TAO_EC_Event_Channel_Base* event_channel, int validate_connection); 00065 00066 /// Destructor... 00067 virtual ~TAO_EC_ProxyPushSupplier (void); 00068 00069 /// Activate in the POA 00070 virtual void activate ( 00071 RtecEventChannelAdmin::ProxyPushSupplier_ptr &proxy 00072 ACE_ENV_ARG_DECL) 00073 ACE_THROW_SPEC ((CORBA::SystemException)) = 0; 00074 00075 /// Deactivate from the POA 00076 virtual void deactivate (ACE_ENV_SINGLE_ARG_DECL) 00077 ACE_THROW_SPEC (()); 00078 00079 /// Disconnect this from 00080 virtual void disconnect_push_supplier ( 00081 ACE_ENV_SINGLE_ARG_DECL) = 0; 00082 00083 /// Return 0 if no consumer is connected... 00084 CORBA::Boolean is_connected (void) const; 00085 00086 /// Return 1 if it is suspended. 00087 CORBA::Boolean is_suspended (void) const; 00088 00089 /** 00090 * Return the consumer object reference. It returns nil() if it has 00091 * not connected yet. 00092 */ 00093 RtecEventComm::PushConsumer_ptr consumer (void) const; 00094 00095 /// The QoS (subscription) used to connect to the EC. 00096 const RtecEventChannelAdmin::ConsumerQOS& subscriptions (void) const; 00097 00098 /// Concrete implementations can use this methods to keep track of 00099 /// the suppliers that publish its events. 00100 virtual void connected (TAO_EC_ProxyPushConsumer *consumer 00101 ACE_ENV_ARG_DECL); 00102 virtual void reconnected (TAO_EC_ProxyPushConsumer *consumer 00103 ACE_ENV_ARG_DECL); 00104 virtual void disconnected (TAO_EC_ProxyPushConsumer *consumer 00105 ACE_ENV_ARG_DECL); 00106 00107 /// Usually implemented as no-ops, but some configurations may 00108 /// require this methods. 00109 virtual void connected (TAO_EC_ProxyPushSupplier *supplier 00110 ACE_ENV_ARG_DECL); 00111 virtual void reconnected (TAO_EC_ProxyPushSupplier *supplier 00112 ACE_ENV_ARG_DECL); 00113 virtual void disconnected (TAO_EC_ProxyPushSupplier *supplier 00114 ACE_ENV_ARG_DECL); 00115 00116 /// The event channel is shutting down 00117 virtual void shutdown (ACE_ENV_SINGLE_ARG_DECL); 00118 00119 /// Pushes to the consumer, verifies that it is connected and that it 00120 /// is not suspended. 00121 /** 00122 * These methods take @a consumer argument because during the time 00123 * the filters have been processing the event, this proxy's consumer 00124 * may have changed. 00125 */ 00126 void push_to_consumer (RtecEventComm::PushConsumer_ptr consumer, 00127 const RtecEventComm::EventSet &event 00128 ACE_ENV_ARG_DECL); 00129 void reactive_push_to_consumer (RtecEventComm::PushConsumer_ptr consumer, 00130 const RtecEventComm::EventSet &event 00131 ACE_ENV_ARG_DECL); 00132 00133 /** 00134 * Invoke the _non_existent() pseudo-operation on the consumer. If 00135 * it is disconnected then it returns true and sets the 00136 * <disconnected> flag. 00137 */ 00138 CORBA::Boolean consumer_non_existent (CORBA::Boolean_out disconnected 00139 ACE_ENV_ARG_DECL); 00140 00141 /// Increment and decrement the reference count. 00142 CORBA::ULong _incr_refcnt (void); 00143 CORBA::ULong _decr_refcnt (void); 00144 00145 // = The TAO_EC_Filter methods, only push() is implemented... 00146 virtual int filter (const RtecEventComm::EventSet &event, 00147 TAO_EC_QOS_Info& qos_info 00148 ACE_ENV_ARG_DECL); 00149 virtual int filter_nocopy (RtecEventComm::EventSet &event, 00150 TAO_EC_QOS_Info &qos_info 00151 ACE_ENV_ARG_DECL); 00152 virtual void push (const RtecEventComm::EventSet &event, 00153 TAO_EC_QOS_Info& qos_info 00154 ACE_ENV_ARG_DECL); 00155 virtual void push_nocopy (RtecEventComm::EventSet &event, 00156 TAO_EC_QOS_Info &qos_info 00157 ACE_ENV_ARG_DECL); 00158 virtual void clear (void); 00159 virtual CORBA::ULong max_event_size (void) const; 00160 virtual int can_match (const RtecEventComm::EventHeader &header) const; 00161 virtual int add_dependencies (const RtecEventComm::EventHeader &header, 00162 const TAO_EC_QOS_Info &qos_info 00163 ACE_ENV_ARG_DECL); 00164 00165 protected: 00166 /// Set the consumer, used by some implementations to change the 00167 /// policies used when invoking operations on the consumer. 00168 void consumer (RtecEventComm::PushConsumer_ptr consumer); 00169 void consumer_i (RtecEventComm::PushConsumer_ptr consumer); 00170 00171 void suspend_connection_i (ACE_ENV_SINGLE_ARG_DECL) 00172 ACE_THROW_SPEC ((CORBA::SystemException)); 00173 void resume_connection_i (ACE_ENV_SINGLE_ARG_DECL) 00174 ACE_THROW_SPEC ((CORBA::SystemException)); 00175 void suspend_connection_locked (ACE_ENV_SINGLE_ARG_DECL) 00176 ACE_THROW_SPEC ((CORBA::SystemException)); 00177 void resume_connection_locked (ACE_ENV_SINGLE_ARG_DECL) 00178 ACE_THROW_SPEC ((CORBA::SystemException)); 00179 00180 /// The private version (without locking) of is_connected(). 00181 CORBA::Boolean is_connected_i (void) const; 00182 00183 /// Release the child and the consumer 00184 void cleanup_i (void); 00185 00186 /// The Event Channel that owns this object. 00187 TAO_EC_Event_Channel_Base* event_channel_; 00188 00189 /// The locking strategy. 00190 ACE_Lock* lock_; 00191 00192 /// The reference count. 00193 CORBA::ULong refcount_; 00194 00195 /// The consumer.... 00196 RtecEventComm::PushConsumer_var consumer_; 00197 00198 /// Is this consumer suspended? 00199 CORBA::Boolean suspended_; 00200 00201 /// The subscription and QoS information... 00202 RtecEventChannelAdmin::ConsumerQOS qos_; 00203 00204 /// Store the default POA. 00205 PortableServer::POA_var default_POA_; 00206 00207 /// The filter object 00208 TAO_EC_Filter* child_; 00209 00210 /// Validate the connection to consumer on connect 00211 int consumer_validate_connection_; 00212 private: 00213 00214 /// Template method hooks. 00215 virtual void refcount_zero_hook (void); 00216 virtual void pre_dispatch_hook (RtecEventComm::EventSet& 00217 ACE_ENV_ARG_DECL); 00218 virtual PortableServer::ObjectId 00219 object_id (ACE_ENV_SINGLE_ARG_DECL) 00220 ACE_THROW_SPEC ((CORBA::SystemException)) = 0; 00221 }; 00222 00223 TAO_END_VERSIONED_NAMESPACE_DECL 00224 00225 #if defined (__ACE_INLINE__) 00226 #include "orbsvcs/Event/EC_ProxySupplier.i" 00227 #endif /* __ACE_INLINE__ */ 00228 00229 #include /**/ "ace/post.h" 00230 00231 #endif /* TAO_EC_PROXYSUPPLIER_H */