00001 #ifndef maciContainerImpl_h
00002 #define maciContainerImpl_h
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022 #include <acsutil.h>
00023 #include <maciExport.h>
00024
00025 #include <maciS.h>
00026
00027 #include <cdb.h>
00028
00029 #include <logging.h>
00030
00031 #include <ace/Synch.h>
00032 #include <ace/Hash_Map_Manager.h>
00033 #include <ace/Unbounded_Set.h>
00034
00035 #include <acsContainerServices.h>
00036 #include "maciContainerThreadHook.h"
00037
00038 #include <map>
00039
00040
00041
00043 #define CONTAINER_RELOAD 0
00045 #define CONTAINER_REBOOT 1
00047 #define CONTAINER_EXIT 2
00048
00049 namespace maci {
00050
00051
00062 typedef PortableServer::Servant (*ConstructComponentFunc)(
00063 maci::Handle h,
00064 const char * name,
00065 const char * type,
00066 ContainerServices * containerServices
00067 );
00068
00069
00070
00071
00072 class ContainerServices;
00073 class MACIServantManager;
00074 class LibraryManager;
00075
00103 class maci_EXPORT ContainerImpl :
00104 public virtual POA_maci::Container,
00105 public virtual PortableServer::RefCountServantBase
00106 {
00107 public:
00108
00112 static ContainerImpl * getContainer()
00113 {
00114 return m_container;
00115 }
00116
00119 maci::Container_ptr getContainerCORBAProxy()
00120 {
00121 return m_container_ref.ptr();
00122 }
00123
00126 static LoggingProxy * getLoggerProxy()
00127 {
00128 return m_loggerProxy;
00129 }
00130
00133 char * getProcessName()
00134 {
00135 return m_argv[0];
00136 }
00137
00139 ContainerImpl();
00140
00142 virtual ~ContainerImpl();
00143
00144
00167 maci::Manager_ptr getManager();
00168
00169 bool init(int argc, char *argv[]);
00170 bool connect();
00171 bool run();
00172 bool done();
00173
00175 int getStatus() { return m_status; }
00177 void setStatus(int status) { m_status = status; }
00178
00180 static void initThread(const char * threadName = 0);
00181
00183 static void doneThread();
00184
00186 void etherealizeComponent(const char * id, PortableServer::Servant servant);
00187
00190 int getShutdownAction() { return m_shutdownAction; }
00191
00194 void setShutdownAction(int action) { m_shutdownAction=action; }
00195
00198 maci::Handle getHandle() { return m_handle; }
00199
00202 PortableServer::POA_var getContainerPOA() { return poaContainer; }
00203
00206 PortableServer::POAManager_var getPOAManager() { return poaManager; }
00207
00210 ContainerServices* getContainerServices() { return m_containerServices; }
00211
00214 CORBA::ORB_var getContainerORB() { return orb; }
00215
00216
00217
00218
00219
00243 virtual maci::ComponentInfo * activate_component (maci::Handle h,
00244 maci::ExecutionId execution_id,
00245 const char * name,
00246 const char * exe,
00247 const char * type
00248 );
00249
00259 virtual void deactivate_components (const maci::HandleSeq & h
00260 );
00261
00267 virtual CORBA::Object_ptr restart_component (maci::Handle h
00268 );
00269
00274 virtual void shutdown (CORBA::ULong action
00275 );
00276
00284 virtual maci::ComponentInfoSeq * get_component_info (const maci::HandleSeq & h
00285 );
00286
00292 virtual char * name ();
00293
00298 virtual void disconnect ();
00299
00307 virtual maci::AuthenticationData * authenticate (maci::ExecutionId execution_id, const char * question
00308 );
00309
00315 virtual void message (CORBA::Short type,
00316 const char * message
00317 );
00318
00325 virtual void taggedmessage (CORBA::Short type,
00326 CORBA::Short tag,
00327 const char * message
00328 );
00329
00334 virtual void components_available (const maci::ComponentInfoSeq & components
00335 );
00336
00341 virtual void components_unavailable (const maci::stringSeq & component_names
00342 );
00343
00348 virtual void set_component_shutdown_order(const maci::HandleSeq & h
00349 );
00350
00361 virtual CORBA::Object_ptr get_object(const char *name,
00362 const char *domain,
00363 bool activate
00364 );
00365
00375 template<class T>
00376 T* get_object(const char *name, const char *domain, bool activate)
00377 {
00378 return getComponent<T>(name, domain, activate);
00379 }
00380
00389 template<class T>
00390 T* getComponent(const char *name, const char *domain, bool activate);
00391
00401 template<class T>
00402 T* getService(const char *name, const char *domain, bool activate);
00403
00413 void releaseComponent(const char *name);
00414
00423 virtual CORBA::Boolean ping ();
00424
00429 virtual maci::LoggingConfigurable::LogLevels get_default_logLevels();
00430
00431 virtual void set_default_logLevels(const maci::LoggingConfigurable::LogLevels&);
00432
00433 virtual maci::stringSeq* get_logger_names();
00434
00435
00436
00437
00438 virtual maci::LoggingConfigurable::LogLevels get_logLevels(const char*);
00439
00440
00441
00442
00443 virtual void set_logLevels(const char*, const maci::LoggingConfigurable::LogLevels&);
00444
00445 virtual void refresh_logging_config();
00446
00447 static void configureLogger(const std::string& loggerName);
00448
00449 void loadLoggerConfiguration(const std::string& loggerName);
00450
00451 protected:
00456 Logging::Logger::LoggerSmartPtr
00457 getLogger() {return m_logger;}
00458
00459
00460 private:
00461
00467 int parseArgs (int argc, char *argv[]);
00468
00470 void showUsage(int argc, char *argv[]);
00471
00483 ContainerServices* instantiateContainerServices(
00484 maci::Handle h,
00485 ACE_CString& name,
00486 PortableServer::POA_ptr poa);
00487
00489 const char * m_pid_file_name;
00490
00492 const char * m_manager_ref;
00493
00494
00495 const char * m_container_name;
00496
00497
00498 static ContainerImpl * m_container;
00499
00501 static LibraryManager * m_dllmgr;
00502
00504 static LoggingProxy * m_loggerProxy;
00505
00506 static int m_logLevelRefresh;
00507 static int m_logLevelConfigure;
00508
00510 MACIServantManager * m_servant_mgr;
00511
00513 cdb::Table * m_database;
00514
00515
00516 maci::Container_var m_container_ref;
00517
00518
00519
00520
00521 CORBA::ORB_var orb;
00522 PortableServer::POAManager_var poaManager;
00523 PortableServer::POA_var poaRoot;
00524 PortableServer::POA_var poaContainer;
00525 PortableServer::POA_var poaPersistent;
00526 PortableServer::POA_var poaTransient;
00527
00529 static CORBA::ULong m_invocationTimeout;
00530
00532 maci::Manager_var m_manager;
00533
00535 maci::Handle m_handle;
00536
00539 int m_status;
00540
00542 bool m_shutdown;
00543
00545 struct ContainerComponentInfo
00546 {
00547 int lib;
00548 maci::ComponentInfo info;
00549 };
00550
00551 typedef ACE_Hash_Map_Manager <maci::Handle, ContainerComponentInfo, ACE_Recursive_Thread_Mutex> COMPONENT_HASH_MAP;
00552 typedef ACE_Hash_Map_Iterator <maci::Handle, ContainerComponentInfo, ACE_Recursive_Thread_Mutex> COMPONENT_HASH_MAP_ITER;
00553 typedef ACE_Hash_Map_Entry <maci::Handle, ContainerComponentInfo> COMPONENT_HASH_MAP_ENTRY;
00554
00556 COMPONENT_HASH_MAP m_activeComponents;
00557
00558
00559 typedef ACE_Unbounded_Set <maci::Handle> COMPONENT_LIST;
00560
00562 COMPONENT_LIST m_activeComponentList;
00563
00565 maci::HandleSeq m_componentShutdownOrder;
00566
00568 bool initializeCORBA(int &argc, char *argv[]);
00569
00571 bool doneCORBA();
00572 public:
00574 CORBA::Object_ptr activateCORBAObject(PortableServer::Servant srvnt,
00575 const char * name);
00576
00578 bool deactivateCORBAObject(PortableServer::Servant servant);
00579
00581 bool deactivateCORBAObject(CORBA::Object_ptr servant);
00582 private:
00584 int loadDLL(const char * bame);
00585
00587 maci::Manager_ptr resolveManager(int nSecTimeout);
00588
00589
00590 void logout ();
00591
00592
00593 ACE_CString m_dbPrefix;
00594
00595
00596 ACE_CString m_dbRootPrefix;
00597
00598
00599 int m_argc;
00600
00601
00602 int m_fullargc;
00603
00604
00605 char** m_argv;
00606
00608 int m_shutdownAction;
00609
00611 bool m_hasIFR;
00612
00614 bool m_recovery;
00615
00616
00617
00618
00619
00621 ACE_SYNCH_MUTEX m_shutdownMutex;
00622
00624 ACE_SYNCH_CONDITION m_shutdownDone;
00625
00627 bool m_shutdownDoneSignaled;
00628
00630 int m_serverThreads;
00631
00633 bool m_dynamicContainer;
00634
00636 ContainerServices *m_containerServices;
00637
00639 maci::ContainerThreadHook m_containerThreadHook;
00640
00642 Logging::Logger::LoggerSmartPtr m_logger;
00643
00644
00645 maci::LoggingConfigurable::LogLevels m_defaultLogLevels;
00646
00647
00648 std::map<std::string, maci::LoggingConfigurable::LogLevels> m_logLevels;
00649
00650
00651 maci::ExecutionId m_executionId;
00652
00653
00654 ACS::Time m_startTime;
00655 };
00656
00658
00661 template<class T>
00662 T* ContainerImpl::getComponent(const char *name, const char *domain, bool activate)
00663 {
00664 T* object = T::_nil();
00665
00666 if(!name)
00667 {
00668 ACS_SHORT_LOG((LM_DEBUG, "Name parameter is null."));
00669 return T::_nil();
00670 }
00671
00675 ACE_CString curl = "curl://";
00676 if (domain)
00677 curl += domain;
00678
00679 curl += ACE_CString("/");
00680
00681 curl += name;
00682
00683 ACS_SHORT_LOG((LM_DEBUG, "Getting component: '%s'.", curl.c_str()));
00684
00685
00686 while (m_handle==0)
00687 {
00688 ACS_SHORT_LOG((LM_DEBUG, "Waiting for m_handle"));
00689 ACE_OS::sleep(1);
00690 }
00691
00692 try
00693 {
00694 CORBA::Object_var obj = m_manager->get_component(m_handle, curl.c_str(), activate);
00695
00696 if (CORBA::is_nil(obj.in()))
00697 {
00698 ACS_SHORT_LOG((LM_DEBUG, "Failed to create '%s'.", curl.c_str()));
00699 maciErrType::CannotGetComponentExImpl ex(__FILE__, __LINE__,
00700 "ContainerImpl::getComponent<>");
00701 ex.setCURL(name);
00702 ex.log();
00703
00704 return T::_nil();
00705 }
00706 object = T::_narrow(obj.in());
00707
00708 return object;
00709 }
00710 catch(maciErrType::ComponentNotAlreadyActivatedEx &_ex)
00711 {
00712 maciErrType::CannotGetComponentExImpl ex(_ex, __FILE__, __LINE__,
00713 "maci::ContainerImpl::getComponent<>");
00714 ex.setCURL(name);
00715 ex.log();
00717 return T::_nil();
00718 }
00719 catch(maciErrType::ComponentConfigurationNotFoundEx &_ex)
00720 {
00721 maciErrType::CannotGetComponentExImpl ex(_ex, __FILE__, __LINE__,
00722 "maci::ContainerImpl::getComponent<>");
00723 ex.setCURL(name);
00724 ex.log();
00726 return T::_nil();
00727 }
00728 catch( CORBA::SystemException &_ex )
00729 {
00730 ACSErrTypeCommon::CORBAProblemExImpl corbaProblemEx(__FILE__, __LINE__,
00731 "ContainerServices::getComponent<>");
00732 corbaProblemEx.setMinor(_ex.minor());
00733 corbaProblemEx.setCompletionStatus(_ex.completed());
00734 corbaProblemEx.setInfo(_ex._info().c_str());
00735 maciErrType::CannotGetComponentExImpl ex(corbaProblemEx, __FILE__, __LINE__,
00736 "ContainerImpl::getComponent<>");
00737 ex.setCURL(name);
00738 ex.log();
00740 return T::_nil();
00741 }
00742 catch(...)
00743 {
00744 ACSErrTypeCommon::UnexpectedExceptionExImpl uex(__FILE__, __LINE__,
00745 "ContainerImpl::getComponent<>");
00746 maciErrType::CannotGetComponentExImpl ex(uex, __FILE__, __LINE__,
00747 "ContainerImpl::getComponent<>");
00748 ex.setCURL(name);
00749 ex.log();
00751 return T::_nil();
00752 }
00753 }
00755
00758 template<class T>
00759 T* ContainerImpl::getService(const char *name, const char *domain, bool activate)
00760 {
00761 ACS_TRACE("ContainerImpl::getService<>");
00762 T* object = T::_nil();
00763
00764 if(!name)
00765 {
00766 ACSErrTypeCommon::NullPointerExImpl nullEx(__FILE__, __LINE__,
00767 "ContainerImpl::getService<>");
00768 nullEx.setVariable("(parameter) name");
00769 maciErrType::CannotGetServiceExImpl ex(nullEx, __FILE__, __LINE__,
00770 "ContainerImpl::getService<>");
00771 ex.setCURL("NULL");
00772 throw ex;
00773 }
00774
00775
00776 ACE_CString curl = "curl://";
00777 if (domain)
00778 curl += domain;
00779
00780 curl += ACE_CString("/");
00781
00782 curl += name;
00783
00784 ACS_SHORT_LOG((LM_DEBUG, "Getting service: '%s'.", curl.c_str()));
00785
00786
00787 while (m_handle==0)
00788 {
00789 ACS_SHORT_LOG((LM_DEBUG, "Waiting for m_handle"));
00790 ACE_OS::sleep(1);
00791 }
00792
00793 try
00794 {
00795 CORBA::Object_var obj = m_manager->get_service(m_handle, curl.c_str(), activate);
00796
00797 if (CORBA::is_nil(obj.in()))
00798 {
00799 maciErrType::CannotGetServiceExImpl ex(__FILE__, __LINE__,
00800 "ContainerImpl::getService<>");
00801 ex.setCURL(name);
00802 throw ex;
00803 }
00804 object = T::_narrow(obj.in());
00805
00806 return object;
00807 }
00808 catch(maciErrType::CannotGetComponentEx &_ex)
00809 {
00810 maciErrType::CannotGetServiceExImpl ex(_ex, __FILE__, __LINE__,
00811 "ContainerImpl::getService<>");
00812 ex.setCURL(name);
00813 throw ex;
00814 }
00815 catch(maciErrType::ComponentNotAlreadyActivatedEx &_ex)
00816 {
00817 maciErrType::CannotGetServiceExImpl ex(_ex, __FILE__, __LINE__,
00818 "ContainerImpl::getService<>");
00819 ex.setCURL(name);
00820 throw ex;
00821 }
00822 catch(maciErrType::ComponentConfigurationNotFoundEx &_ex)
00823 {
00824 maciErrType::CannotGetServiceExImpl ex(_ex, __FILE__, __LINE__,
00825 "ContainerImpl::getService<>");
00826 ex.setCURL(name);
00827 throw ex;
00828 }
00829 catch( CORBA::SystemException &_ex )
00830 {
00831 ACSErrTypeCommon::CORBAProblemExImpl corbaProblemEx(__FILE__, __LINE__,
00832 "ContainerImpl::getService<>");
00833 corbaProblemEx.setMinor(_ex.minor());
00834 corbaProblemEx.setCompletionStatus(_ex.completed());
00835 corbaProblemEx.setInfo(_ex._info().c_str());
00836 maciErrType::CannotGetServiceExImpl ex(corbaProblemEx, __FILE__, __LINE__,
00837 "ContainerImpl::getService<>");
00838 ex.setCURL(name);
00839 throw ex;
00840 }
00841 catch(...)
00842 {
00843 ACSErrTypeCommon::UnexpectedExceptionExImpl uex(__FILE__, __LINE__,
00844 "ContainerImpl::getService<>");
00845 maciErrType::CannotGetServiceExImpl ex(uex, __FILE__, __LINE__,
00846 "ContainerImpl::getService<>");
00847 ex.setCURL(name);
00848 throw ex;
00849 }
00850 }
00851
00852 };
00853
00854 #endif // maciContainerImpl_h
00855