Salome HOME
updated copyright message
[modules/kernel.git] / src / Container / SALOME_Container_Common.cxx
1 // Copyright (C) 2007-2023  CEA, EDF, OPEN CASCADE
2 //
3 // Copyright (C) 2003-2007  OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
4 // CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
5 //
6 // This library is free software; you can redistribute it and/or
7 // modify it under the terms of the GNU Lesser General Public
8 // License as published by the Free Software Foundation; either
9 // version 2.1 of the License, or (at your option) any later version.
10 //
11 // This library is distributed in the hope that it will be useful,
12 // but WITHOUT ANY WARRANTY; without even the implied warranty of
13 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
14 // Lesser General Public License for more details.
15 //
16 // You should have received a copy of the GNU Lesser General Public
17 // License along with this library; if not, write to the Free Software
18 // Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
19 //
20 // See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
21 //
22
23 //  SALOME Container : implementation of container and engine for Kernel
24 //  File   : SALOME_Container.cxx
25 //  Author : Paul RASCLE, EDF - MARC TAJCHMAN, CEA
26 //  Module : SALOME
27 //  $Header$
28 //
29 #ifdef _MPI_SEQ_CONTAINER_
30   #ifdef HAVE_MPI2
31 #include <mpi.h>
32   #endif
33 #endif
34
35 #include <iostream>
36 #include <sstream>
37 #include <string>
38 #include <stdio.h>
39 #include <time.h>
40 #ifndef WIN32
41 # include <sys/time.h>
42 # include <dlfcn.h>
43 #endif
44
45
46 #ifndef WIN32
47 #include <unistd.h>
48 #else
49 #include <process.h>
50 #endif
51 #include "ArgvKeeper.hxx"
52 #include "SALOME_Container_Common.hxx"
53 #include "SALOME_Container_i.hxx"
54 #include "utilities.h"
55 #include "OpUtil.hxx"
56 #include "KernelBasis.hxx"
57
58 #ifdef CHECKTIME
59 #include <Utils_Timer.hxx>
60 #endif
61
62 #include "Container_init_python.hxx"
63
64 extern "C" void HandleServerSideSignals(CORBA::ORB_ptr theORB);
65
66 #include <stdexcept>
67 #include <signal.h>
68 #include <sys/types.h>
69 #ifndef WIN32
70 # include <sys/wait.h>
71 #endif
72
73 #include <memory>
74
75 void AttachDebugger();
76 void Handler(int);
77 void terminateHandler();
78 void unexpectedHandler();
79
80 #ifndef WIN32
81 void (* setsig(int, void (*)(int)))(int);
82
83 typedef void (*sighandler_t)(int);
84 sighandler_t setsig(int sig, sighandler_t handler)
85 {
86   struct sigaction context, ocontext;
87   context.sa_handler = handler;
88   sigemptyset(&context.sa_mask);
89   context.sa_flags = 0;
90   if (sigaction(sig, &context, &ocontext) == -1)
91     return SIG_ERR;
92   return ocontext.sa_handler;
93 }
94 #endif //WIN32
95
96 void AttachDebugger()
97 {
98 #ifndef WIN32
99   if(getenv ("DEBUGGER"))
100     {
101       std::stringstream exec;
102       exec << "$DEBUGGER SALOME_Container " << getpid() << "&";
103       std::cerr << exec.str() << std::endl;
104       system(exec.str().c_str());
105       while(1);
106     }
107 #endif
108 }
109
110 void Handler(int theSigId)
111 {
112   std::cerr << "Signal= "<< theSigId  << std::endl;
113   AttachDebugger();
114   //to exit or not to exit
115   _exit(1);
116 }
117
118 void terminateHandler(void)
119 {
120   std::cerr << "Terminate: not managed exception !"  << std::endl;
121   AttachDebugger();
122 }
123
124 void unexpectedHandler(void)
125 {
126   std::cerr << "Unexpected: unexpected exception !"  << std::endl;
127   AttachDebugger();
128 }
129
130 template<class ContainerServant>
131 int container_common_main(int argc, char* argv[], std::unique_ptr<SALOME_NamingService_Container_Abstract> ns)
132 {
133   setSSLMode(ns?!ns->IsTrueNS():false);
134 #ifdef _MPI_SEQ_CONTAINER_
135   #ifdef HAVE_MPI2
136   MPI_Init(&argc,&argv);
137   #endif
138 #endif  
139
140 #ifndef WIN32
141   if(getenv ("DEBUGGER"))
142     {
143       setsig(SIGSEGV,&Handler);
144       setsig(SIGFPE,&Handler);
145       std::set_terminate(&terminateHandler);
146       std::set_unexpected(&unexpectedHandler);
147     }
148 #endif
149
150   // Initialise the ORB.
151   //SRN: BugID: IPAL9541, it's necessary to set a size of one message to be at least 100Mb
152   //CORBA::ORB_var orb = CORBA::ORB_init( argc , argv ) ;
153   SetArgcArgv(argc, argv);
154   CORBA::ORB_ptr orb = KERNEL::GetRefToORB();
155
156   //  LocalTraceCollector *myThreadTrace = SALOMETraceCollector::instance(orb);
157   INFOS_COMPILATION;
158   BEGIN_OF(argv[0]);
159
160   ASSERT(argc > 1);
161   SCRUTE(argv[1]);
162
163   KERNEL_PYTHON::init_python(argc,argv);
164     
165   char *containerName = (char *)"";
166   if(argc > 1)
167     {
168       containerName = argv[1] ;
169     }
170
171   try
172     {  
173       CORBA::Object_var obj = orb->resolve_initial_references("RootPOA");
174       ASSERT(!CORBA::is_nil(obj));
175       PortableServer::POA_var root_poa = PortableServer::POA::_narrow(obj);
176
177       PortableServer::POAManager_var pman = root_poa->the_POAManager();
178
179       // add new container to the kill list
180 #ifndef WIN32
181       std::stringstream aCommand ;
182       aCommand << "addToKillList.py " << getpid() << " SALOME_Container" << std::ends ;
183       system(aCommand.str().c_str());
184 #endif
185       
186       new ContainerServant(orb, root_poa, containerName , argc , argv, ns.get() );
187       ns.release();
188
189       pman->activate();
190       
191 #ifdef CHECKTIME
192       Utils_Timer timer;
193       timer.Start();
194       timer.Stop();
195       timer.ShowAbsolute();
196 #endif
197
198       HandleServerSideSignals(orb);
199
200 //#define MEMORYLEAKS
201 #ifdef MEMORYLEAKS
202         PyGILState_Ensure();
203         //Destroy orb from python (for chasing memory leaks)
204         PyRun_SimpleString("from omniORB import CORBA");
205         PyRun_SimpleString("orb=CORBA.ORB_init([''], CORBA.ORB_ID)");
206         PyRun_SimpleString("orb.destroy()");
207         Py_Finalize();
208 #endif
209     }
210   catch(CORBA::SystemException&)
211     {
212       INFOS("Caught CORBA::SystemException.");
213     }
214   catch(PortableServer::POA::ServantAlreadyActive&)
215     {
216       INFOS("Caught CORBA::ServantAlreadyActiveException");
217     }
218   catch(CORBA::Exception&)
219     {
220       INFOS("Caught CORBA::Exception.");
221     }
222   catch(std::exception& exc)
223     {
224       INFOS("Caught std::exception - "<<exc.what()); 
225     }
226   catch(...)
227     {
228       INFOS("Caught unknown exception.");
229     }
230
231 #ifdef _MPI_SEQ_CONTAINER_
232   #ifdef HAVE_MPI2
233   MPI_Finalize();
234   #endif
235 #endif  
236
237   return 0 ;
238 }
239