00001
00020 #ifndef RTC_MANAGER_H
00021 #define RTC_MANAGER_H
00022
00023 #include <rtm/RTC.h>
00024
00025 #include <iostream>
00026 #include <string>
00027 #include <vector>
00028
00029 #include <coil/Mutex.h>
00030 #include <coil/Guard.h>
00031 #include <coil/Task.h>
00032
00033 #include <rtm/Factory.h>
00034 #include <rtm/ECFactory.h>
00035 #include <rtm/ObjectManager.h>
00036 #include <rtm/SystemLogger.h>
00037
00038 namespace RTM
00039 {
00040 class ManagerServant;
00041 }
00042
00043 namespace coil
00044 {
00045 class Timer;
00046 };
00047
00048 namespace RTC
00049 {
00050
00051 class CorbaNaming;
00052 class ModuleManager;
00053 class NamingManager;
00054 class Manager;
00055 class RTObject_impl;
00056 typedef RTObject_impl RtcBase;
00057
00058 typedef void (*ModuleInitProc)(Manager* manager);
00059
00080 class Manager
00081 {
00082 typedef coil::Mutex Mutex;
00083 typedef coil::Guard<Mutex> Guard;
00084 protected:
00098 Manager();
00099
00117 Manager(const Manager& manager);
00118
00119
00120 public:
00173 static Manager* init(int argc, char** argv);
00174
00197 static Manager& instance();
00198
00199
00200
00201
00202
00216 void terminate();
00217
00233 void shutdown();
00234
00248 void join();
00249
00267 LogStreamBuf& getLogStreamBuf() {return m_logStreamBuf;}
00268
00286 std::string& getLogLevel() {return m_config["logger.log_level"];}
00287
00305 coil::Properties& getConfig() { return m_config;}
00306
00331 void setModuleInitProc(ModuleInitProc proc);
00332
00365 bool activateManager();
00366
00397 void runManager(bool no_block = false);
00398
00399
00400
00401
00424 void load(const char* fname, const char* initfunc);
00425
00445 void unload(const char* fname);
00446
00462 void unloadAll();
00463
00481 std::vector<coil::Properties> getLoadedModules();
00482
00502 std::vector<coil::Properties> getLoadableModules();
00503
00504
00505
00506
00533 bool registerFactory(coil::Properties& profile,
00534 RtcNewFunc new_func,
00535 RtcDeleteFunc delete_func);
00536
00554 std::vector<coil::Properties> getFactoryProfiles();
00555
00582 bool registerECFactory(const char* name,
00583 ECNewFunc new_func,
00584 ECDeleteFunc delete_func);
00585
00603 std::vector<std::string> getModulesFactories();
00604
00605
00606
00607
00666 RTObject_impl* createComponent(const char* comp_args);
00680 ExecutionContextBase* createContext(const char* ec_args);
00681
00700 void cleanupComponent(RTObject_impl* comp);
00701
00715 void cleanupComponents();
00716
00735 void notifyFinalized(RTObject_impl* comp);
00736
00760 bool registerComponent(RTObject_impl* comp);
00761
00783 bool unregisterComponent(RTObject_impl* comp);
00784
00785
00807 void deleteComponent(RTObject_impl* comp);
00808
00831 void deleteComponent(const char* instance_name);
00832
00833
00857 RTObject_impl* getComponent(const char* instance_name);
00858
00876 std::vector<RTObject_impl*> getComponents();
00877
00878
00879
00880
00898 CORBA::ORB_ptr getORB();
00899
00917 PortableServer::POA_ptr getPOA();
00918
00936 PortableServer::POAManager_ptr getPOAManager();
00937
00938
00939
00940
00941 protected:
00942
00943
00944
00945
00973 void initManager(int argc, char** argv);
00974
00990 void shutdownManager();
00991
01008 void shutdownOnNoRtcs();
01009
01010
01011
01012
01034 bool initLogger();
01035
01053 void shutdownLogger();
01054
01055
01056
01057
01075 bool initORB();
01076
01096 std::string createORBOptions();
01097
01115 void createORBEndpoints(coil::vstring& endpoints);
01116
01130 void createORBEndpointOption(std::string& opt, coil::vstring& endpoint);
01131
01150 void shutdownORB();
01151
01152
01153
01154
01186 bool initNaming();
01187
01203 void shutdownNaming();
01204
01205
01206
01207
01223 void shutdownComponents();
01224
01225
01273 bool procComponentArgs(const char* comp_arg,
01274 coil::Properties& comp_id,
01275 coil::Properties& comp_conf);
01316 bool procContextArgs(const char* ec_args,
01317 std::string& ec_id,
01318 coil::Properties& ec_conf);
01319
01342 void configureComponent(RTObject_impl* comp, const coil::Properties& prop);
01343
01365 bool initExecContext();
01366
01382 bool initComposite();
01383
01405 bool initFactories();
01406
01426 bool initTimer();
01427
01441 bool initManagerServant();
01442
01450 RTM::ManagerServant* m_mgrservant;
01451
01477 bool mergeProperty(coil::Properties& prop, const char* file_name);
01478
01527 std::string formatString(const char* naming_format,
01528 coil::Properties& prop);
01529
01530
01531
01532
01533
01534
01535
01536
01537
01538
01546 static Manager* manager;
01547
01555 static Mutex mutex;
01556
01557
01558
01559
01567 CORBA::ORB_var m_pORB;
01568
01576 PortableServer::POA_var m_pPOA;
01577
01585 PortableServer::POAManager_var m_pPOAManager;
01586
01587
01588
01589
01597 ModuleInitProc m_initProc;
01598
01606 coil::Properties m_config;
01607
01615 ModuleManager* m_module;
01616
01624 NamingManager* m_namingManager;
01625
01633 coil::Timer* m_timer;
01634
01635
01636
01637
01645 LogStreamBuf m_logStreamBuf;
01646
01654 Logger rtclog;
01655
01663 std::vector<std::filebuf*> m_logfiles;
01664
01665
01666
01667
01668
01669 struct InstanceName
01670 {
01671 InstanceName(RTObject_impl* comp);
01672 InstanceName(const char* name);
01673 InstanceName(const std::string name);
01674 bool operator()(RTObject_impl* comp);
01675 std::string m_name;
01676 };
01677
01678 typedef ObjectManager<std::string, RTObject_impl, InstanceName> ComponentManager;
01679
01687 ComponentManager m_compManager;
01688
01689
01690
01691
01692
01693 class FactoryPredicate
01694 {
01695 public:
01696 FactoryPredicate(const char* imple_id)
01697 : m_vendor(""), m_category(""), m_impleid(imple_id), m_version("")
01698 {
01699 }
01700 FactoryPredicate(const coil::Properties& prop)
01701 : m_vendor(prop["vendor"]),
01702 m_category(prop["category"]),
01703 m_impleid(prop["implementation_id"]),
01704 m_version(prop["version"])
01705 {
01706 }
01707 FactoryPredicate(FactoryBase* factory)
01708 : m_vendor(factory->profile()["vendor"]),
01709 m_category(factory->profile()["category"]),
01710 m_impleid(factory->profile()["implementation_id"]),
01711 m_version(factory->profile()["version"])
01712 {
01713 }
01714 bool operator()(FactoryBase* factory)
01715 {
01716
01717 if (m_impleid.empty()) return false;
01718
01719 const coil::Properties& prop(factory->profile());
01720
01721 if (m_impleid != prop["implementation_id"])
01722 return false;
01723 if (!m_vendor.empty() && m_vendor != prop["vendor"])
01724 return false;
01725 if (!m_category.empty() && m_category != prop["category"])
01726 return false;
01727 if (!m_version.empty() && m_version != prop["version"])
01728 return false;
01729
01730 return true;
01731 }
01732 private:
01733 std::string m_vendor;
01734 std::string m_category;
01735 std::string m_impleid;
01736 std::string m_version;
01737 };
01738
01739 class ModulePredicate
01740 {
01741 coil::Properties& m_prop;
01742 public:
01743 ModulePredicate(coil::Properties& prop)
01744 : m_prop(prop)
01745 {
01746 }
01747 bool operator()(coil::Properties& prop)
01748 {
01749 if (m_prop["implementation_id"] != prop["implementation_id"])
01750 {
01751 return false;
01752 }
01753 if (!m_prop["vendor"].empty() &&
01754 m_prop["vendor"] != prop["vendor"]) { return false; }
01755 if (!m_prop["category"].empty() &&
01756 m_prop["category"] != prop["category"]) { return false; }
01757 if (!m_prop["version"].empty() &&
01758 m_prop["version"] != prop["version"]) { return false; }
01759 return true;
01760 }
01761 };
01762
01770 typedef ObjectManager<const coil::Properties, FactoryBase,
01771 FactoryPredicate> FactoryManager;
01772
01780 FactoryManager m_factory;
01781
01782
01783
01784
01785
01786 struct ECFactoryPredicate
01787 {
01788 ECFactoryPredicate(const char* name) : m_name(name){};
01789 ECFactoryPredicate(ECFactoryBase* factory)
01790 : m_name(factory->name()) {};
01791 bool operator()(ECFactoryBase* factory)
01792 {
01793 return m_name == factory->name();
01794 }
01795 std::string m_name;
01796 };
01797 typedef ObjectManager<const char*,
01798 ECFactoryBase,
01799 ECFactoryPredicate> ECFactoryManager;
01800
01808 ECFactoryManager m_ecfactory;
01809
01817 std::vector<ExecutionContextBase*> m_ecs;
01818
01819
01820 struct ModuleFactories
01821 {
01822 void operator()(FactoryBase* f)
01823 {
01824 modlist.push_back(f->profile().getProperty("implementation_id"));
01825 }
01826 std::vector<std::string> modlist;
01827 };
01828
01829
01830
01831
01851 class OrbRunner
01852 : public coil::Task
01853 {
01854 public:
01868 OrbRunner(CORBA::ORB_ptr orb) : m_pORB(orb)
01869 {
01870 open(0);
01871 };
01872
01894 virtual int open(void *args)
01895 {
01896 activate();
01897 return 0;
01898 }
01899
01917 virtual int svc(void)
01918 {
01919 m_pORB->run();
01920
01921 return 0;
01922 }
01923
01945 virtual int close(unsigned long flags)
01946 {
01947 return 0;
01948 }
01949 private:
01950 CORBA::ORB_ptr m_pORB;
01951 };
01959 OrbRunner* m_runner;
01960
01961
01962
01963
01983 class Terminator
01984 : public coil::Task
01985 {
01986 public:
02004 Terminator(Manager* manager) : m_manager(manager) {};
02005
02019 void terminate()
02020 {
02021 open(0);
02022 }
02023
02045 virtual int open(void *args)
02046 {
02047 activate();
02048 return 0;
02049 }
02050
02068 virtual int svc(void)
02069 {
02070 Manager::instance().shutdown();
02071 return 0;
02072 }
02073 Manager* m_manager;
02074 };
02075
02083 Terminator* m_terminator;
02084
02085 struct Term
02086 {
02087 int waiting;
02088 Mutex mutex;
02089 };
02103 Term m_terminate;
02104
02105 struct Finalized
02106 {
02107 Mutex mutex;
02108 std::vector<RTObject_impl*> comps;
02109 };
02110 Finalized m_finalized;
02111
02112
02113 };
02114 };
02115
02116 #endif // RTC_MANAGER_H