1 #include "SALOME_ContainerManager.hxx"
2 #include "SALOME_NamingService.hxx"
9 #include "Utils_CorbaException.hxx"
11 #define TIME_OUT_TO_LAUNCH_CONT 21
15 const char *SALOME_ContainerManager::_ContainerManagerNameInNS =
18 //=============================================================================
22 * Define a CORBA single thread policy for the server, which avoid to deal
23 * with non thread-safe usage like Change_Directory in SALOME naming service
25 //=============================================================================
27 SALOME_ContainerManager::SALOME_ContainerManager(CORBA::ORB_ptr orb)
29 MESSAGE("constructor");
30 _NS = new SALOME_NamingService(orb);
31 _ResManager = new SALOME_ResourcesManager(orb);
33 PortableServer::POA_var root_poa = PortableServer::POA::_the_root_poa();
34 PortableServer::POAManager_var pman = root_poa->the_POAManager();
35 PortableServer::POA_var my_poa;
37 CORBA::PolicyList policies;
39 PortableServer::ThreadPolicy_var threadPol =
40 root_poa->create_thread_policy(PortableServer::SINGLE_THREAD_MODEL);
41 policies[0] = PortableServer::ThreadPolicy::_duplicate(threadPol);
44 root_poa->create_POA("SThreadPOA",pman,policies);
46 PortableServer::ObjectId_var id = my_poa->activate_object(this);
47 CORBA::Object_var obj = my_poa->id_to_reference(id);
48 Engines::ContainerManager_var refContMan =
49 Engines::ContainerManager::_narrow(obj);
51 _NS->Register(refContMan,_ContainerManagerNameInNS);
52 MESSAGE("constructor end");
55 //=============================================================================
59 //=============================================================================
61 SALOME_ContainerManager::~SALOME_ContainerManager()
63 MESSAGE("destructor");
68 //=============================================================================
70 * shutdown all the containers, then the ContainerManager servant
72 //=============================================================================
74 void SALOME_ContainerManager::Shutdown()
78 PortableServer::ObjectId_var oid = _default_POA()->servant_to_id(this);
79 _default_POA()->deactivate_object(oid);
84 //=============================================================================
86 * Loop on all the containers listed in naming service, ask shutdown on each
88 //=============================================================================
90 void SALOME_ContainerManager::ShutdownContainers()
92 MESSAGE("ShutdownContainers");
93 _NS->Change_Directory("/Containers");
94 vector<string> vec = _NS->list_directory_recurs();
95 for(vector<string>::iterator iter = vec.begin();iter!=vec.end();iter++)
98 CORBA::Object_var obj=_NS->Resolve((*iter).c_str());
99 Engines::Container_var cont=Engines::Container::_narrow(obj);
100 if(!CORBA::is_nil(cont))
102 MESSAGE("ShutdownContainers: " << (*iter));
105 else MESSAGE("ShutdownContainers: no container ref for " << (*iter));
109 //=============================================================================
111 * Find a suitable Container in a list of machines, or start one
112 * \param params Machine Parameters required for the container
113 * \param possibleComputers list of machines usable for find or start
115 //=============================================================================
117 Engines::Container_ptr
118 SALOME_ContainerManager::
119 FindOrStartContainer(const Engines::MachineParameters& params,
120 const Engines::MachineList& possibleComputers)
123 string containerNameInNS;
124 char idc[3*sizeof(long)];
126 Engines::Container_ptr ret = FindContainer(params,possibleComputers);
127 if(!CORBA::is_nil(ret))
129 MESSAGE("Container doesn't exist try to launch it ...");
130 MESSAGE("SALOME_ContainerManager::FindOrStartContainer " <<
131 possibleComputers.length());
132 //vector<string> vector;
133 string theMachine=_ResManager->FindBest(possibleComputers);
134 MESSAGE("try to launch it on " << theMachine);
136 // Get Id for container: a parallel container registers in Naming Service
137 // on the machine where is process 0. ContainerManager does'nt know the name
138 // of this machine before the launch of the parallel container. So to get
139 // the IOR of the parallel container in Naming Service, ContainerManager
140 // gives a unique Id. The parallel container registers his name under
141 // /ContainerManager/Id directory in NamingService
143 id = GetIdForContainer();
148 MESSAGE("SALOME_ContainerManager::FindOrStartContainer : " <<
149 "no possible computer");
150 return Engines::Container::_nil();
152 else if(theMachine==GetHostname())
154 command=_ResManager->BuildCommandToLaunchLocalContainer(params,id);
158 _ResManager->BuildCommandToLaunchRemoteContainer(theMachine,params,id);
160 _ResManager->RmTmpFile();
161 int status=system(command.c_str());
164 MESSAGE("SALOME_LifeCycleCORBA::StartOrFindContainer rsh failed " <<
165 "(system command status -1)");
166 return Engines::Container::_nil();
168 else if (status == 217)
170 MESSAGE("SALOME_LifeCycleCORBA::StartOrFindContainer rsh failed " <<
171 "(system command status 217)");
172 return Engines::Container::_nil();
176 int count=TIME_OUT_TO_LAUNCH_CONT;
177 while ( CORBA::is_nil(ret) && count )
186 MESSAGE( count << ". Waiting for FactoryServer on " << theMachine);
189 containerNameInNS = "/ContainerManager/id";
190 sprintf(idc,"%ld",id);
191 containerNameInNS += idc;
195 _NS->BuildContainerNameForNS(params,theMachine.c_str());
196 SCRUTE(containerNameInNS);
197 CORBA::Object_var obj = _NS->Resolve(containerNameInNS.c_str());
198 ret=Engines::Container::_narrow(obj);
200 if ( CORBA::is_nil(ret) )
202 MESSAGE("SALOME_LifeCycleCORBA::StartOrFindContainer rsh failed");
208 //=============================================================================
212 //=============================================================================
214 Engines::MachineList *
215 SALOME_ContainerManager::
216 GetFittingResources(const Engines::MachineParameters& params,
217 const char *componentName)
219 MESSAGE("SALOME_ContainerManager::GetFittingResources");
220 Engines::MachineList *ret=new Engines::MachineList;
224 vec = _ResManager->GetFittingResources(params,componentName);
226 catch(const SALOME_Exception &ex)
228 INFOS("Caught exception.");
229 THROW_SALOME_CORBA_EXCEPTION(ex.what(),SALOME::BAD_PARAM);
233 MESSAGE("Machine list length "<<vec.size());
234 ret->length(vec.size());
235 for(unsigned int i=0;i<vec.size();i++)
237 (*ret)[i]=(vec[i]).c_str();
242 //=============================================================================
246 //=============================================================================
249 SALOME_ContainerManager::
250 FindBest(const Engines::MachineList& possibleComputers)
252 string theMachine=_ResManager->FindBest(possibleComputers);
253 return CORBA::string_dup(theMachine.c_str());
256 //=============================================================================
260 //=============================================================================
262 Engines::Container_ptr
263 SALOME_ContainerManager::
264 FindContainer(const Engines::MachineParameters& params,
265 const char *theMachine)
267 string containerNameInNS(_NS->BuildContainerNameForNS(params,theMachine));
268 CORBA::Object_var obj = _NS->Resolve(containerNameInNS.c_str());
269 if( !CORBA::is_nil(obj) )
270 return Engines::Container::_narrow(obj);
272 return Engines::Container::_nil();
275 //=============================================================================
279 //=============================================================================
281 Engines::Container_ptr
282 SALOME_ContainerManager::
283 FindContainer(const Engines::MachineParameters& params,
284 const Engines::MachineList& possibleComputers)
286 MESSAGE("FindContainer "<<possibleComputers.length());
287 for(unsigned int i=0;i<possibleComputers.length();i++)
289 MESSAGE("FindContainer possible " << possibleComputers[i]);
290 Engines::Container_ptr cont = FindContainer(params,possibleComputers[i]);
291 if( !CORBA::is_nil(cont) )
294 MESSAGE("FindContainer: not found");
295 return Engines::Container::_nil();
298 //=============================================================================
300 * Get Id for container: a parallel container registers in Naming Service
301 * on the machine where is process 0. ContainerManager does'nt know the name
302 * of this machine before the launch of the parallel container. So to get
303 * the IOR of the parallel container in Naming Service, ContainerManager
304 * gives a unique Id. The parallel container registers his name under
305 * /ContainerManager/Id directory in NamingService
307 //=============================================================================
310 long SALOME_ContainerManager::GetIdForContainer(void)