diff options
author | William R. Otte <wotte@dre.vanderbilt.edu> | 2006-07-24 15:50:21 +0000 |
---|---|---|
committer | William R. Otte <wotte@dre.vanderbilt.edu> | 2006-07-24 15:50:21 +0000 |
commit | 0e49389337be86641451a5c36c24bf742fe97523 (patch) | |
tree | 197c810e5f5bce17b1233a7cb8d7b50c0bcd25e2 /TAO/orbsvcs/tests/EC_Multiple/EC_Multiple.h | |
parent | 8008dd09ccf88d4edef237a184a698cac42f2952 (diff) | |
download | ATCD-0e49389337be86641451a5c36c24bf742fe97523.tar.gz |
Repo restructuring
Diffstat (limited to 'TAO/orbsvcs/tests/EC_Multiple/EC_Multiple.h')
-rw-r--r-- | TAO/orbsvcs/tests/EC_Multiple/EC_Multiple.h | 387 |
1 files changed, 387 insertions, 0 deletions
diff --git a/TAO/orbsvcs/tests/EC_Multiple/EC_Multiple.h b/TAO/orbsvcs/tests/EC_Multiple/EC_Multiple.h new file mode 100644 index 00000000000..4bf7784e0cd --- /dev/null +++ b/TAO/orbsvcs/tests/EC_Multiple/EC_Multiple.h @@ -0,0 +1,387 @@ +/* -*- C++ -*- */ +// $Id$ +// +// ============================================================================ +// +// = DESCRIPTION +// This test attempts to communicate several Event Channels. +// The test hardcodes all the objects involved (consumers, +// suppliers, proxies, etc.); the objective is to gain understanding +// on the architecture needed to exploit locality in the Event +// cycle, not to provide a definite solution. +// +// ============================================================================ + +#ifndef EC_MULTIPLE_H +#define EC_MULTIPLE_H + +#include "ace/SString.h" + +#if !defined (ACE_LACKS_PRAGMA_ONCE) +# pragma once +#endif /* ACE_LACKS_PRAGMA_ONCE */ + +#include "ace/High_Res_Timer.h" +#include "ace/Condition_Thread_Mutex.h" +#include "orbsvcs/RtecEventChannelAdminC.h" +#include "orbsvcs/RtecEventCommS.h" +#include "orbsvcs/Channel_Clients_T.h" +#include "orbsvcs/Event/EC_Gateway_Sched.h" +#include "orbsvcs/CosNamingC.h" + +class Test_ECG; + +class Test_Supplier : public POA_RtecEventComm::PushSupplier +{ + // + // = TITLE + // Helper class to implement the different tests within Test_ECG. + // + // = DESCRIPTION + // Test_ECG can be configured to have a single or multiple + // suppliers, to use the EC or short-circuit it, to use the + // Gateway or not; this class connects as a consumer for timeouts + // in the EC, at each timeout it delegates on the Test_ECG class + // to execute the proper test. +public: + Test_Supplier (Test_ECG* test, void* cookie); + + void open (const char* name, + int event_a, int event_b, + int message_count, + const RtecScheduler::Period_t& rate, + RtecEventChannelAdmin::EventChannel_ptr ec + ACE_ENV_ARG_DECL); + // This method connects the supplier to the EC. + + void close (ACE_ENV_SINGLE_ARG_DECL); + // Disconnect from the EC. + + void activate (const char* name, + const RtecScheduler::Period_t& rate, + RtecEventChannelAdmin::EventChannel_ptr ec + ACE_ENV_ARG_DECL); + + void push (const RtecEventComm::EventSet& events + ACE_ENV_ARG_DECL); + void disconnect_push_consumer (ACE_ENV_SINGLE_ARG_DECL_NOT_USED); + // Implement the callbacks for our consumer personality. + + + virtual void disconnect_push_supplier (ACE_ENV_SINGLE_ARG_DECL_NOT_USED) + ACE_THROW_SPEC ((CORBA::SystemException)); + // The methods in the skeleton. + + RtecEventComm::EventSourceID supplier_id (void) const; + // The supplier ID. + +private: + Test_ECG* test_; + + void *cookie_; + // The test provide us a cookie so we can give back our identity. + + RtecEventComm::EventSourceID supplier_id_; + // We generate an id based on the name.... + + int event_a_; + int event_b_; + // The two types of events we may generate... + + int message_count_; + // The number of events sent by this supplier. + + RtecEventChannelAdmin::ProxyPushConsumer_var consumer_proxy_; + // We talk to the EC (as a supplier) using this proxy. + + ACE_PushConsumer_Adapter<Test_Supplier> consumer_; + // We also connect to the EC as a consumer so we can receive the + // timeout events. + + RtecEventChannelAdmin::ProxyPushSupplier_var supplier_proxy_; + // We talk to the EC (as a supplier) using this proxy. + +}; + +class Test_Consumer : public POA_RtecEventComm::PushConsumer +{ + // + // = TITLE + // Helper class to implement the different tests within Test_ECG. + // + // = DESCRIPTION + // Test_ECG must collect events destined to many consumers, but + // needs to distinguish through which consumer it is receiving the + // event. The easiest way is to create a shallow class that + // forwards the events to the EC, but passing back some cookie to + // identify the consumer. +public: + Test_Consumer (Test_ECG* test, void *cookie); + + void open (const char* name, + int event_a, int event_b, + RtecEventChannelAdmin::EventChannel_ptr ec + ACE_ENV_ARG_DECL); + // This method connects the consumer to the EC. + + void close (ACE_ENV_SINGLE_ARG_DECL); + // Disconnect from the EC. + + virtual void push (const RtecEventComm::EventSet& events + ACE_ENV_ARG_DECL) + ACE_THROW_SPEC ((CORBA::SystemException)); + virtual void disconnect_push_consumer (ACE_ENV_SINGLE_ARG_DECL_NOT_USED) + ACE_THROW_SPEC ((CORBA::SystemException)); + // The skeleton methods. + +private: + Test_ECG* test_; + // The test class. + + void *cookie_; + // The magic cookie that serves as our ID. + + RtecEventChannelAdmin::ProxyPushSupplier_var supplier_proxy_; + // We talk to the EC using this proxy. +}; + +class Test_ECG +{ + // + // = TITLE + // Test and demonstrate the use of TAO_EC_Gateway. + // + // = DESCRIPTION + // This class is design to exercise several features of the EC_Gateway + // class and the multiple EC architecture. + // We want to create two EC, each one having a single supplier and a + // single consumer. + // + To test the remote facilities the consumer register for both a + // local event and a remote one. + // + To test the remote filtering features the remote consumer only + // wants one of the local events, and this event is generated less + // frequently. + // + // This class creates the local EC_Gateway a consumer and a + // supplier, it uses the command line to figure the subscriptions + // and publications list. + // +public: + Test_ECG (void); + + enum { + MAX_EVENTS = 1024, + // Maximum number of events to send... + + MAX_CONSUMERS = 1024, + // Maximum number of consumers. + + MAX_SUPPLIERS = 1024 + // Maximum number of suppliers. + }; + + int run (int argc, char* argv[]); + // Execute the test. + + void push_supplier (void* supplier_cookie, + RtecEventChannelAdmin::ProxyPushConsumer_ptr consumer, + const RtecEventComm::EventSet &events + ACE_ENV_ARG_DECL_NOT_USED); + // Callback method for suppliers, we push for them to their + // consumers and take statistics on the way. + // It is possible that we ignore the <consumer> parameter when + // testing the short-circuit case. + + void push_consumer (void* consumer_cookie, + ACE_hrtime_t arrival, + const RtecEventComm::EventSet& events + ACE_ENV_ARG_DECL_NOT_USED); + // Callback method for consumers, if any of our consumers has + // received events it will invoke this method. + + void shutdown_supplier (void* supplier_cookie, + RtecEventComm::PushConsumer_ptr consumer + ACE_ENV_ARG_DECL); + // One of the suppliers has completed its work. + +private: + RtecEventChannelAdmin::EventChannel_ptr + get_ec (CosNaming::NamingContext_ptr naming_context, + const char* ec_name + ACE_ENV_ARG_DECL); + // Helper routine to obtain an EC given its name. + + void connect_suppliers (RtecEventChannelAdmin::EventChannel_ptr local_ec + ACE_ENV_ARG_DECL); + void disconnect_suppliers (ACE_ENV_SINGLE_ARG_DECL); + // Connect the suppliers. + + void activate_suppliers (RtecEventChannelAdmin::EventChannel_ptr local_ec + ACE_ENV_ARG_DECL); + // Activate the suppliers, i.e. they start generating events. + + void connect_ecg (RtecEventChannelAdmin::EventChannel_ptr local_ec, + RtecEventChannelAdmin::EventChannel_ptr remote_ec, + RtecScheduler::Scheduler_ptr remote_sch + ACE_ENV_ARG_DECL); + // Connect the EC gateway, it builds the Subscriptions and the + // Publications list. + + void connect_consumers (RtecEventChannelAdmin::EventChannel_ptr local_ec + ACE_ENV_ARG_DECL); + void disconnect_consumers (ACE_ENV_SINGLE_ARG_DECL); + // Connect and disconnect the consumers. + + int shutdown (ACE_ENV_SINGLE_ARG_DECL_NOT_USED); + // Called when the main thread (i.e. not the scavenger thread) is + // shutting down. + + int parse_args (int argc, char* argv[]); + // parse the command line args + + void dump_results (void); + // Dump the results to the standard output. + + void wait_until_ready (void); + // Block event delivery until all the consumers are ready. + + struct Stats; + void dump_results (const char* name, Stats& stats); + // Dump the results for a particular consumer. + + int local_source (RtecEventComm::EventSourceID id) const; + // Check if <id> correspond to a local supplier. + + void shutdown_consumer (int id); + // One of the consumers has completed its work. + +private: + const char* lcl_name_; + // The name of the "local" EC. + + const char* rmt_name_; + // The name of the "remote" EC. + + TAO_EC_Gateway_Sched ecg_; + // The proxy used to connect both event channels. + + enum { + ss_global, + ss_local, + ss_runtime + }; + int scheduling_type_; + // The type of scheduling service to use: + // "global" is a remote scheduling service, usually to perform + // simultaneous scheduling across all the processes. + // "local" instantiate a local config time scheduling service. + // "runtime" instantiates a local rumtime scheduling service. + + int consumer_disconnects_; + int supplier_disconnects_; + // How many times to disconnect the consumers (and suppliers) before + // the final connection. This is useful to test the disconnection in + // the EC. + + int short_circuit_; + // Don't send the messages through the EC. This is needed to measure + // the overhead introduced by the EC. + + Test_Supplier* suppliers_[Test_ECG::MAX_SUPPLIERS]; + Test_Consumer* consumers_[Test_ECG::MAX_CONSUMERS]; + // The suppliers and consumer arrays, the sizes are controlled using + // {lp,hp}_{suppliers,consumers}_ + + // @@ TODO it looks like the HP and LP data could be encapsulated. + + int hp_suppliers_; + // The number of high priority suppliers in this test. + + int hp_consumers_; + // The number of high priority consumers. + + int hp_workload_; + // The number of iterations of ACE::is_prime() to execute in high + // priority consumers. + + int hp_interval_; + // The high priority events are generated using this interval. + + int hp_message_count_; + // How many messages we will send in the HP suppliers + + int hps_event_a_; + int hps_event_b_; + int hpc_event_a_; + int hpc_event_b_; + // Each supplier send two types of events, each consumer receives + // two other types. The types for high-priority clients can be + // different from the types to low priority clients. + + int lp_suppliers_; + // The number of low priority suppliers in this test. + + int lp_consumers_; + // The number of low priority consumers. + + int lp_workload_; + // The number of iterations of ACE::is_prime() to execute in low + // priority consumers. + + int lp_interval_; + // The low priority events are generated using this interval. + + int lp_message_count_; + // How many messages we will send in the LP suppliers + + int lps_event_a_; + int lps_event_b_; + int lpc_event_a_; + int lpc_event_b_; + // Each supplier send two types of events, each consumer receives + // two other types. The types for high-priority clients can be + // different from the types to low priority clients. + + const char* schedule_file_; + // Ask the schedule to compute and dump its schedule after the test + // execution. + + const char* pid_file_name_; + // The name of a file where the process stores its pid + + struct Stats { + ACE_hrtime_t total_time_; + float laxity_[MAX_EVENTS]; + ACE_hrtime_t lcl_latency_[MAX_EVENTS]; + ACE_hrtime_t end_[MAX_EVENTS]; + int lcl_count_; + // We keep laxity and total_time stats only for the local events. + + ACE_hrtime_t rmt_latency_[MAX_EVENTS]; + int rmt_count_; + }; + Stats stats_[Test_ECG::MAX_CONSUMERS]; + // Store the measurements for local and remote events.. + + int ready_; + TAO_SYNCH_MUTEX ready_mtx_; + TAO_SYNCH_CONDITION ready_cnd_; + // Before accepting any events the suppliers must wait for the test + // to setup all the consumers. + // The suppliers wait on the condition variable. + + ACE_Atomic_Op<TAO_SYNCH_MUTEX,int> running_suppliers_; + // keep track of how many suppliers are still running so we shutdown + // at the right moment. + + ACE_Atomic_Op<TAO_SYNCH_MUTEX,int> running_consumers_; + // keep track of how many consumers are still running so we shutdown + // at the right moment. + + ACE_hrtime_t test_start_; + ACE_hrtime_t test_stop_; + // Measure the test elapsed time as well as mark the beginning of + // the frames. +}; + +#endif /* EC_MULTIPLE_H */ |