00001 #ifndef _ACS_DAEMON_IMPL_H_
00002 #define _ACS_DAEMON_IMPL_H_
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033 #ifndef __cplusplus
00034 #error This is a C++ include file and cannot be used from plain C
00035 #endif
00036
00037 #include "acsdaemonS.h"
00038 #include <ace/SString.h>
00039 #include "logging.h"
00040 #include <getopt.h>
00041 #include <acsutilPorts.h>
00042 #include <tao/IORTable/IORTable.h>
00043 #include <acserr.h>
00044 #include <acsdaemonErrType.h>
00045 #include <ACSErrTypeCommon.h>
00046 #include "acsdaemonORBTask.h"
00047
00054 template <typename T>
00055 class ACSDaemonServiceImpl {
00056
00057 public:
00058
00062 ACSDaemonServiceImpl(LoggingProxy &logProxy, bool isProtected);
00063
00067 virtual ~ACSDaemonServiceImpl();
00068
00072 bool
00073 isInitialized() { return m_isInitialized; }
00074
00078 bool
00079 isProtected() { return m_isProtected; }
00080
00081
00085 std::string
00086 getPort() { return handler.getPort(); }
00087
00091 std::string
00092 getName() { return handler.getName(); }
00093
00097 int
00098 startup (int argc, char *argv[]);
00099
00104 int
00105 run ();
00106
00110 void
00111 shutdown (bool wait_for_completition);
00112
00116 const char*
00117 getIOR() const { return m_ior.in(); };
00118
00119 protected:
00123 virtual int
00124 init_ORB (int& argc, char *argv []);
00125
00126
00127
00129 bool m_isInitialized;
00130
00132 bool m_isProtected;
00133
00135 bool m_blockTermination;
00136
00138 CORBA::ORB_var m_orb;
00139
00141 LoggingProxy &m_logProxy;
00142
00144 CORBA::String_var m_ior;
00145
00147 T handler;
00148 };
00149
00150 template <typename T>
00151 ACSDaemonServiceImpl<T>::ACSDaemonServiceImpl (LoggingProxy &logProxy, bool isProtected) :
00152 m_isInitialized(false), m_logProxy(logProxy)
00153 {
00154
00155
00156 m_isInitialized = true;
00157
00158 m_isProtected = isProtected;
00159
00160 m_blockTermination = false;
00161
00162 ACS_CHECK_LOGGER;
00163
00164 Logging::Logger::setGlobalLogger(getNamedLogger(handler.getName()));
00165
00166 handler.setService(this);
00167 }
00168
00169 template <typename T>
00170 ACSDaemonServiceImpl<T>::~ACSDaemonServiceImpl (void)
00171 {
00172 }
00173
00174 template <typename T>
00175 int ACSDaemonServiceImpl<T>::startup (int argc, char *argv[])
00176 {
00177 ACS_SHORT_LOG ((LM_INFO, "Starting up the %s...", handler.getName().c_str()));
00178
00179
00180 if (init_ORB (argc, argv) != 0)
00181 {
00182 return -1;
00183 }
00184
00185
00186 if (!ACSError::init(m_orb.in()))
00187 {
00188 ACS_SHORT_LOG ((LM_ERROR, "Failed to initalize the ACS Error System."));
00189 return -1;
00190 }
00191
00192 ACS_SHORT_LOG ((LM_INFO, "%s is initialized.", handler.getName().c_str()));
00193
00194 return 0;
00195 }
00196
00197 template <typename T>
00198 int ACSDaemonServiceImpl<T>::run (void)
00199 {
00200 ACS_SHORT_LOG ((LM_INFO, "%s is up and running...", handler.getName().c_str()));
00201
00202
00203 try
00204 {
00205 handler.initialize(m_orb.in());
00206
00207
00208
00209 ORBTask task (this->m_orb.in(), &m_logProxy);
00210 const int m_serverThreads = 5;
00211
00212 if (task.activate (THR_NEW_LWP | THR_JOINABLE, m_serverThreads) == 0)
00213
00214 task.thr_mgr()->wait ();
00215 else
00216 {
00217
00218 ACS_LOG(LM_RUNTIME_CONTEXT, "ACSDaemonServiceImpl<T>::run", (LM_INFO, "Failed to activate CORBA ORB request handler threads..."));
00219 return -1;
00220 }
00221
00222 }
00223 catch(...)
00224 {
00225 return -1;
00226 }
00227
00228 return 0;
00229 }
00230
00231 template <typename T>
00232 void ACSDaemonServiceImpl<T>::shutdown (bool wait_for_completition)
00233 {
00234 if (!m_blockTermination)
00235 {
00236 ACS_SHORT_LOG ((LM_INFO, "Stopping the %s...", this->getName().c_str()));
00237 m_blockTermination=true;
00238
00239 if (!CORBA::is_nil (m_orb.in ()))
00240 {
00241 handler.dispose(m_orb.in());
00242 this->m_orb->shutdown (wait_for_completition);
00243 }
00244
00245 ACSError::done();
00246 }
00247 }
00248
00249 template <typename T>
00250 int ACSDaemonServiceImpl<T>::init_ORB (int& argc, char *argv [])
00251 {
00252 m_orb = CORBA::ORB_init(argc, argv, "TAO");
00253
00254 try
00255 {
00256
00257 CORBA::Object_var obj = m_orb->resolve_initial_references("RootPOA");
00258 PortableServer::POA_var root_poa = PortableServer::POA::_narrow(obj.in());
00259 PortableServer::POAManager_var poa_manager = root_poa->the_POAManager();
00260
00261
00262 CORBA::PolicyList policy_list;
00263 policy_list.length(5);
00264 policy_list[0] = root_poa->create_request_processing_policy(PortableServer::USE_DEFAULT_SERVANT);
00265 policy_list[1] = root_poa->create_id_uniqueness_policy(PortableServer::MULTIPLE_ID);
00266 policy_list[2] = root_poa->create_id_assignment_policy(PortableServer::USER_ID);
00267 policy_list[3] = root_poa->create_servant_retention_policy(PortableServer::NON_RETAIN);
00268 policy_list[4] = root_poa->create_lifespan_policy(PortableServer::PERSISTENT);
00269
00270
00271 PortableServer::POA_var poa = root_poa->create_POA(handler.getType().c_str(), poa_manager.in(), policy_list);
00272
00273
00274 for (CORBA::ULong i = 0; i < policy_list.length(); ++i)
00275 {
00276 CORBA::Policy_ptr policy = policy_list[i];
00277 policy->destroy();
00278 }
00279
00280
00281 poa->set_servant(&handler);
00282
00283
00284 PortableServer::ObjectId_var oid = PortableServer::string_to_ObjectId(handler.getType().c_str());
00285 obj = poa->create_reference_with_id (oid.in(), handler._interface_repository_id());
00286 m_ior = m_orb->object_to_string(obj.in());
00287
00288
00289 CORBA::Object_var table_object = m_orb->resolve_initial_references("IORTable");
00290 IORTable::Table_var adapter = IORTable::Table::_narrow(table_object.in());
00291
00292 if (CORBA::is_nil(adapter.in()))
00293 {
00294 ACS_SHORT_LOG ((LM_ERROR, "Nil IORTable"));
00295 return -1;
00296 }
00297 else
00298 {
00299 adapter->bind(handler.getType().c_str(), m_ior.in());
00300 }
00301
00302
00303 poa_manager->activate();
00304
00305 ACS_SHORT_LOG((LM_INFO, "%s is waiting for incoming requests.", handler.getName().c_str()));
00306
00307 }
00308 catch( CORBA::Exception &ex )
00309 {
00310 ACE_PRINT_EXCEPTION (ex, "EXCEPTION CAUGHT");
00311 return -1;
00312 }
00313
00314 return 0;
00315 }
00316
00324 template <typename T>
00325 class acsDaemonImpl
00326 {
00327
00328 public:
00329
00333 acsDaemonImpl(int argc, char *argv[]);
00334
00338 ~acsDaemonImpl();
00339
00343 void usage(const char *argv);
00344
00348 int run();
00349
00353 void shutdown();
00354
00355 private:
00356
00358 ACSDaemonServiceImpl<T> *service;
00359
00361 ACE_CString iorFile;
00362
00364 ACE_CString ORBEndpoint;
00365
00367 int nargc;
00368 char** nargv;
00369
00371 LoggingProxy *m_logger;
00372 };
00373
00374
00376 static struct option long_options[] = {
00377 {"help", no_argument, 0, 'h'},
00378 {"outfile", required_argument, 0, 'o'},
00379 {"ORBEndpoint", required_argument, 0, 'O'},
00380 {"unprotected", no_argument, 0, 'u'},
00381 {0, 0, 0, '\0'}};
00382
00383 template <typename T>
00384 void acsDaemonImpl<T>::usage(const char *argv)
00385 {
00386 ACE_OS::printf ("\n\tusage: %s {-h} [-O iiop://ip:port] [-o iorfile]\n", argv);
00387 ACE_OS::printf ("\t -h, --help show this help message\n");
00388 ACE_OS::printf ("\t -O, --ORBEndpoint ORB end point\n");
00389 ACE_OS::printf ("\t -o, --outfile IOR output file\n");
00390 ACE_OS::printf ("\t -u, --unprotected start in unprotected mode\n");
00391 }
00392
00393 template <typename T>
00394 acsDaemonImpl<T>::acsDaemonImpl(int argc, char *argv[])
00395 {
00396 nargc = 0;
00397 nargv = 0;
00398 service = 0;
00399 m_logger = 0;
00400 bool unprotected = false;
00401
00402
00403
00404 int c;
00405 for(;;)
00406 {
00407 int option_index = 0;
00408 c = getopt_long (argc, argv, "ho:O:u",
00409 long_options, &option_index);
00410 if (c==-1) break;
00411 switch(c)
00412 {
00413 case 'h':
00414 usage(argv[0]);
00415 return;
00416 case 'o':
00417 iorFile = optarg;
00418 break;
00419 case 'O':
00420 ORBEndpoint = optarg;
00421 break;
00422 case 'u':
00423 unprotected = true;
00424 break;
00425 default:
00426 ACE_OS::printf("Ignoring unrecognized option %s",
00427 argv[option_index]);
00428 }
00429 }
00430
00431
00432
00433 const char* hostName = ACSPorts::getIP();
00434
00435
00436 LoggingProxy::ProcessName(argv[0]);
00437 LoggingProxy::ThreadName("main");
00438 ACE_Log_Msg::instance()->local_host(hostName);
00439 m_logger = new LoggingProxy (0, 0, 31, 0);
00440
00441 LoggingProxy::init (m_logger);
00442
00443
00444 service = new ACSDaemonServiceImpl<T>(*m_logger, !unprotected);
00445
00446
00447 ACE_CString argStr;
00448
00449 if(ORBEndpoint.length()<=0)
00450 {
00451 argStr = ACE_CString("-ORBEndpoint iiop://") + hostName + ":";
00452 argStr = argStr + service->getPort().c_str();
00453 }
00454 else
00455 {
00456 argStr = ACE_CString("-ORBEndpoint ") + ORBEndpoint;
00457 }
00458
00459 ACS_SHORT_LOG((LM_INFO, "Command line is: %s", argStr.c_str()));
00460 ACE_OS::string_to_argv ((ACE_TCHAR*)argStr.c_str(), nargc, nargv);
00461 }
00462
00463 template <typename T>
00464 acsDaemonImpl<T>::~acsDaemonImpl()
00465 {
00466 if (service != 0) delete service;
00467 if (m_logger != 0)
00468 {
00469 LoggingProxy::done();
00470 delete m_logger;
00471 }
00472 }
00473
00474
00475 template <typename T>
00476 int acsDaemonImpl<T>::run()
00477 {
00478 ACS_TRACE("acsDaemonImpl<T>::run");
00479 if (!service || !service->isInitialized())
00480 {
00481 return -1;
00482 }
00483 try
00484 {
00485 if (service->startup (nargc, nargv) != 0)
00486 {
00487 return -1;
00488 }
00489
00490
00491 if (iorFile.length() > 0)
00492 {
00493 FILE *output_file = ACE_OS::fopen (iorFile.c_str(), "w");
00494 if (output_file == 0)
00495 {
00496 ACS_SHORT_LOG ((LM_ERROR, "Cannot open output file '%s' to write IOR.", iorFile.c_str()));
00497 return -1;
00498 }
00499
00500 int result = ACE_OS::fprintf (output_file, "%s", service->getIOR());
00501 if (result < 0)
00502 {
00503 ACS_SHORT_LOG ((LM_ERROR, "ACE_OS::fprintf failed to write IOR."));
00504 return -1;
00505 }
00506
00507 ACE_OS::fclose (output_file);
00508 ACS_SHORT_LOG((LM_INFO, "%s IOR has been written into file '%s'.", service->getName().c_str(), iorFile.c_str()));
00509 }
00510
00511
00512 if (service->run () == -1)
00513 {
00514 this->shutdown ();
00515 ACS_SHORT_LOG ((LM_ERROR, "Failed to run the %s.", service->getName().c_str()));
00516 return 1;
00517 }
00518 }
00519 catch(...)
00520 {
00521 ACS_SHORT_LOG((LM_ERROR, "Failed to start the %s.", service->getName().c_str()));
00522 return 1;
00523 }
00524
00525
00526 this->shutdown();
00527
00528 ACS_SHORT_LOG ((LM_INFO, "%s stopped.", service->getName().c_str()));
00529
00530 return 0;
00531 }
00532
00533 template <typename T>
00534 void acsDaemonImpl<T>::shutdown()
00535 {
00536 service->shutdown(true);
00537 }
00538
00539 #endif