Salome HOME
SMH: 3.0.0 preparation = merged version (POLYWORK + RTVDEBUG01) + adopation for new GUI
[modules/superv.git] / src / GraphExecutor / DataFlowExecutor_InNode.hxx
1 //  SUPERV GraphExecutor : contains classes that permit execution of graphs and particularly the execution automaton
2 //
3 //  Copyright (C) 2003  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. 
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.opencascade.org/SALOME/ or email : webmaster.salome@opencascade.org 
21 //
22 //
23 //
24 //  File   : DataFlowBase_InNode.hxx
25 //  Author : Jean Rahuel, CEA
26 //  Module : SUPERV
27 //  $Header:
28
29 #ifndef _DATAFLOWEXECUTOR_INNODE_HXX
30 #define _DATAFLOWEXECUTOR_INNODE_HXX
31
32 #include <stdio.h>
33
34 #include <Python.h>
35
36 #include "SALOME_Container_i.hxx"
37
38 #include "DataFlowBase_Graph.hxx"
39 #include "DataFlowBase_FactoryNode.hxx"
40 #include "DataFlowBase_GOTONode.hxx"
41 #include "DataFlowBase_LoopNode.hxx"
42 #include "DataFlowBase_EndOfLoopNode.hxx"
43 #include "DataFlowBase_SwitchNode.hxx"
44 #include "DataFlowBase_EndOfSwitchNode.hxx"
45
46 #include "DataFlowExecutor_FiniteStateMachine.hxx"
47
48 #define MAXSTACKTHREADSIZE 127
49
50 void * run_function(void *p);
51
52 extern GraphExecutor::FiniteStateMachine * theAutomaton ;
53
54 extern "C" PyObject * PyRunMethod( PyObject * dummy , PyObject * args ) ;
55
56 namespace GraphExecutor {
57
58   struct ServicesAnyData {
59     string     Name;
60     CORBA::Any Value;
61   };
62
63   class OutNode ;
64
65 //  class InNode : public GraphBase::Node {
66   class InNode : public GraphBase::Base {
67
68     private:
69
70       GraphBase::ComputingNode       * _ComputingNode ;
71       GraphBase::FactoryNode         * _FactoryNode ;
72       GraphBase::InLineNode          * _InLineNode ;
73       GraphBase::GOTONode            * _GOTONode ;
74       GraphBase::LoopNode            * _LoopNode ;
75       GraphBase::EndOfLoopNode       * _EndOfLoopNode ;
76       GraphBase::SwitchNode          * _SwitchNode ;
77       GraphBase::EndOfSwitchNode     * _EndOfSwitchNode ;
78       GraphBase::Graph               * _GraphMacroNode ;
79
80       PyObject                       * _MyPyRunMethod ;
81
82       bool                             _createNewThread ;
83       bool                             _createNewThreadIf ;
84       int                              _RewindStack ;
85       GraphExecutor::AutomatonState    _OldState ;
86       GraphExecutor::AutomatonState    _currentState ;
87       GraphExecutor::NodeEvent         _CurrentEvent ;
88       SUPERV::ControlState             _ControlState ;
89       GraphExecutor::AutomatonState    _NextState ;
90       GraphExecutor::StateEventAction  _NextAction ;
91       bool                             _PyFuncRunned ;
92       bool                             _Loading ;
93     
94       pthread_mutex_t                  _MutexDataWait ;
95       bool                             _DataWait ;
96
97       pthread_mutex_t                  _MutexWait ;
98
99       pthread_cond_t                   _ReadyWait ;
100       pthread_cond_t                   _RunningWait ;
101       pthread_cond_t                   _DoneWait ;
102       pthread_cond_t                   _SuspendedWait ;
103
104       pthread_cond_t                   _SuspendWait ;
105       bool                             _SuspendSync ;
106       pthread_cond_t                   _ResumeWait ;
107       bool                             _ResumeSync ;
108       GraphExecutor::NodeEvent         _aResumeEvent ;
109       GraphExecutor::InNode *          _aReStartNode ;
110       GraphExecutor::NodeEvent         _aReStartEvent ;
111
112       pthread_cond_t                   _KillWait ;
113       bool                             _KillSync ;
114       pthread_cond_t                   _StopWait ;
115
116       pthread_cond_t                   _ThreadStartedWait ;
117       bool                             _ThreadStartedSync ;
118
119       pthread_t                        _Pythread ;
120       long                             _PyCpuUsed ;
121       long                             _PyTotCpuUsed ;
122
123       GraphExecutor::FiniteStateMachine * _Automaton ;
124     
125       CORBA::ORB_ptr                    _Orb;
126
127       GraphExecutor::OutNode          * _OutNode ;
128
129       char                            * _DataFromNode ;
130       bool                              _InitLoop ;
131
132     public:
133
134       InNode() ;
135       InNode( CORBA::ORB_ptr ORB, SALOME_NamingService* ptrNamingService,
136               const SALOME_ModuleCatalog::Service& NodeService ,
137               const char *NodeComponentName ,
138               const char* NodeInterfaceName ,
139               const char *NodeName ,
140               const SUPERV::KindOfNode akind = SUPERV::ComputingNode ,
141               GraphBase::ListOfFuncName aFuncName = GraphBase::ListOfFuncName() ,
142               GraphBase::ListOfPythonFunctions aPythonFunction = GraphBase::ListOfPythonFunctions() ,
143               const SUPERV::SDate NodeFirstCreation = SUPERV::SDate() ,
144               const SUPERV::SDate NodeLastModification = SUPERV::SDate() ,
145               const char * NodeEditorRelease = NULLSTRING ,
146               const char * NodeAuthor = NULLSTRING ,
147               const char * NodeComputer = NULLSTRING ,
148               const char * NodeComment = NULLSTRING ,
149               const bool   GeneratedName = false ,
150               const int NodeX = 0 ,
151               const int NodeY = 0 ,
152               int * Graph_prof_debug = NULL ,
153               ofstream * Graph_fdebug = NULL ) ;
154       virtual ~InNode() ;
155
156       pthread_t ThreadNo() {
157                 return _ComputingNode->ThreadNo() ; } ;
158       void ThreadNo( pthread_t aThread ) {
159            _ComputingNode->ThreadNo ( aThread ) ; } ;
160
161       char * Name() const {
162              return _ComputingNode->Name() ; } ;
163       const char *const * NamePtr() const {
164                           return _ComputingNode->NamePtr() ; } ;
165       SUPERV::KindOfNode Kind() const {
166                          return _ComputingNode->Kind() ; } ;
167       const bool IsComputingNode() const {
168                  return _ComputingNode->IsComputingNode() ; } ;
169       const bool IsFactoryNode() const {
170                  return _ComputingNode->IsFactoryNode() ; } ;
171       const bool IsInLineNode() const {
172                  return _ComputingNode->IsInLineNode() ; } ;
173       const bool IsOneOfInLineNodes() const {
174                  return _ComputingNode->IsOneOfInLineNodes() ; } ;
175       const bool IsOneOfGOTONodes() const {
176                  return _ComputingNode->IsOneOfGOTONodes() ; } ;
177       const bool IsMacroNode() const {
178                  return _ComputingNode->IsMacroNode() ; } ;
179       const bool IsDataFlowNode() const {
180                  return _ComputingNode->IsDataFlowNode() ; } ;
181       const bool IsDataStreamNode() const {
182                  return _ComputingNode->IsDataStreamNode() ; } ;
183       const bool IsLoopNode() const {
184                  return _ComputingNode->IsLoopNode() ; } ;
185       const bool IsEndLoopNode() const {
186                  return _ComputingNode->IsEndLoopNode() ; } ;
187       const bool IsSwitchNode() const {
188                  return _ComputingNode->IsSwitchNode() ; } ;
189       const bool IsEndSwitchNode() const {
190                  return _ComputingNode->IsEndSwitchNode() ; } ;
191       const bool IsGOTONode() const {
192                  return _ComputingNode->IsGOTONode() ; } ;
193       const bool IsHeadNode() const {
194                  return _ComputingNode->IsHeadNode() ; } ;
195       GraphBase::ComputingNode * ComputingNode() {
196                                  return _ComputingNode ; } ;
197       GraphBase::FactoryNode * FactoryNode() {
198                                  return _FactoryNode ; } ;
199       GraphBase::GOTONode * GOTONode() {
200                             if ( _GOTONode )
201                               return _GOTONode ;
202                             if ( _LoopNode )
203                               return _LoopNode ;
204                             if ( _EndOfLoopNode )
205                               return _EndOfLoopNode ;
206                             if ( _SwitchNode )
207                               return _SwitchNode ;
208                             if ( _EndOfSwitchNode )
209                               return _EndOfSwitchNode ;
210                             return NULL ;
211                             } ;
212       GraphBase::InLineNode * InLineNode() {
213                               GraphBase::InLineNode * aNode = GOTONode() ;
214                               if ( aNode == NULL )
215                                 return _InLineNode ;
216                               return aNode ;
217                               } ;
218       GraphBase::LoopNode * LoopNode() {
219                             return _LoopNode ; } ;
220       GraphBase::Graph * GraphMacroNode() {
221                          return _GraphMacroNode ; } ;
222
223       SUPERV::CNode_var ObjRef() const { return _ComputingNode->ObjRef() ; } ;
224       void SetObjRef( SUPERV::CNode_var aNode ) {
225                      _ComputingNode->SetObjRef( aNode ) ; } ;
226
227       CNode_Impl * ObjImpl() const { return _ComputingNode->ObjImpl() ; } ;
228       void SetObjImpl( CNode_Impl * aGraph ) {
229                        _ComputingNode->SetObjImpl( aGraph ) ; } ;
230
231       Engines::Component_var Component() const ;
232       Engines::Container_var Container() const ;
233       void SetContainer(Engines::Container_var aContainer) {
234                         _FactoryNode->SetContainer( aContainer ) ; } ;
235       void SetComponent(Engines::Component_var anObjComponent) {
236                         _FactoryNode->SetComponent( anObjComponent ) ; } ;
237       void ObjInterface( bool k_interface ) {
238                         _ComputingNode->ObjInterface( k_interface ) ; } ;
239       bool ObjInterface() {
240                         return _FactoryNode->ObjInterface() ; } ;
241       char * ComponentName() const { return _FactoryNode->ComponentName() ; } ;
242       char * InterfaceName() const { return _FactoryNode->InterfaceName() ; } ;
243       char * Computer() const { return _FactoryNode->Computer() ; } ;
244       const char * ServiceName() const {
245                    return _ComputingNode->ServiceName() ; } ;
246       const SALOME_ModuleCatalog::ListOfServicesParameter ServiceInParameter() const {
247             return _ComputingNode->ServiceInParameter() ; } ;
248       const SALOME_ModuleCatalog::ListOfServicesParameter ServiceOutParameter() const {
249             return _ComputingNode->ServiceOutParameter() ; } ;
250
251       void CoupledNode( GraphBase::InLineNode * aCoupledNode ) {
252            GOTONode()->CoupledNode( aCoupledNode ) ; } ;
253       GraphBase::InLineNode * CoupledNode() {
254                               return GOTONode()->CoupledNode() ; } ;
255
256       GraphBase::InPort * AddInPort( const char * InputParameterName ,
257                                      const char * InputParameterType ,
258                                      const SUPERV::KindOfPort aKindOfPort ) {
259                           return _ComputingNode->AddInPort( InputParameterName ,
260                                                             InputParameterType ,
261                                                             aKindOfPort ) ; } ;
262       GraphBase::OutPort * AddOutPort( const char * OutputParameterName ,
263                                        const char * OutputParameterType ,
264                                        const SUPERV::KindOfPort aKindOfPort ) {
265                            return _ComputingNode->AddOutPort( OutputParameterName ,
266                                                               OutputParameterType ,
267                                                               aKindOfPort ) ; } ;
268 //      void InOutPort( GraphBase::InPort * InputPort ,
269 //                      GraphBase::OutPort * OutputPort ) {
270 //           return _ComputingNode->InOutPort( InputPort , OutputPort ) ; } ;
271       int LinkedNodesSize() const {
272           return _ComputingNode->LinkedNodesSize() ; } ;
273 //      GraphBase::ComputingNode * LinkedNodes( int i ) const {
274       GraphBase::StreamNode * LinkedNodes( int i ) const {
275                               return _ComputingNode->LinkedNodes( i ) ; } ;
276       const int LinkedInPortsNumber( int i ) const {
277                 return _ComputingNode->LinkedInPortsNumber( i ) ; } ;
278
279       const int GetNodeInPortsSize() const {
280                 return _ComputingNode->GetNodeInPortsSize() ; } ;
281       const GraphBase::InPort *GetNodeInLoop() const {
282                               return _ComputingNode->GetNodeInLoop() ; } ;
283       const GraphBase::InPort *GetNodeInGate() const {
284                               return _ComputingNode->GetNodeInGate() ; } ;
285       const GraphBase::InPort *GetNodeInPort(int i) const {
286                               return _ComputingNode->GetNodeInPort( i ) ; } ;
287       GraphBase::InPort *GetChangeNodeInLoop() const {
288                         return _ComputingNode->GetChangeNodeInLoop() ; } ;
289       GraphBase::InPort *GetChangeNodeInGate() const {
290                         return _ComputingNode->GetChangeNodeInGate() ; } ;
291       GraphBase::InPort *GetChangeNodeInPort(int i) const {
292                         return _ComputingNode->GetChangeNodeInPort( i ) ; } ;
293       const int GetNodeOutPortsSize() const {
294                 return _ComputingNode->GetNodeOutPortsSize() ; } ;
295       const GraphBase::OutPort *GetNodeOutLoop() const {
296                                return _ComputingNode->GetNodeOutLoop() ; } ;
297       const GraphBase::OutPort *GetNodeOutGate() const {
298                                return _ComputingNode->GetNodeOutGate() ; } ;
299       const GraphBase::OutPort *GetNodeOutPort(int i) const {
300                                return _ComputingNode->GetNodeOutPort( i ) ; } ;
301       GraphBase::OutPort *GetChangeNodeOutLoop() const {
302                          return _ComputingNode->GetChangeNodeOutLoop() ; } ;
303       GraphBase::OutPort *GetChangeNodeOutGate() const {
304                          return _ComputingNode->GetChangeNodeOutGate() ; } ;
305       GraphBase::OutPort *GetChangeNodeOutPort(int i) const {
306                          return _ComputingNode->GetChangeNodeOutPort( i ) ; } ;
307
308       const GraphBase::InPort *GetInPort( const char *name ) {
309             return _ComputingNode->GetInPort( name ) ; } ;
310       const GraphBase::OutPort *GetOutPort( const char *name ) {
311             return _ComputingNode->GetOutPort( name ) ; } ;
312       GraphBase::InPort *GetChangeInPort( const char *name ) {
313                         return _ComputingNode->GetChangeInPort( name ) ; } ;
314       GraphBase::OutPort *GetChangeOutPort( const char *name ) {
315                          return _ComputingNode->GetChangeOutPort( name ) ; } ;
316
317       void PyFuncRunned( bool arunned ) {
318            _PyFuncRunned = arunned ; } ;
319       bool PyFuncRunned() {
320            return _PyFuncRunned ; } ;
321
322       void OutNode( GraphExecutor::OutNode * theOutNode ) {
323            _OutNode = theOutNode ; } ;
324
325       bool InitPython() ;
326       PyObject * InitPyDynInvoke( char * PyFuncName ,
327                                   const SUPERV::ListOfStrings * aPythonFunction ,
328                                   bool & Err ) ;
329       void RemovePyDynInvoke( char * PyFuncName ) ;
330
331       void LockDataWait() ;
332       void UnLockDataWait() ;
333       bool IsLockedDataWait() { return _DataWait ; } ;
334
335       bool Ping() ;
336       bool ContainerKill() ;
337
338       bool Kill() ;
339       bool KillDone() ;
340       bool Suspend() ;
341       bool SuspendDone() ;
342       bool Resume() ;
343       bool Stop() ;
344
345       void CreateNewThread( bool k_create ) {
346 //           cdebug << Name() << " CreateNewThread " << k_create << endl ;
347            _createNewThread = k_create ; } ;
348       void CreateNewThreadIf( bool k_create ) {
349 //           cdebug << Name() << " CreateNewThreadIf( " << k_create << " )" << endl ;
350            _createNewThreadIf = k_create ; } ;
351       bool CreateNewThread() { return _createNewThread ; } ;
352       bool CreateNewThreadIf() { return _createNewThreadIf ; } ;
353       void NewThread( pthread_t aThread ) ;
354       void ExitThread() ;
355       void RewindStack( int aRewindStack ) { _RewindStack = aRewindStack ; } ;
356       int RewindStack() const { return _RewindStack ; } ;
357
358       GraphExecutor::AutomatonState State() const {
359              return _currentState; };
360       void State(GraphExecutor::AutomatonState aState ) {
361 //           cdebug << "GraphExecutor::InNode::State( "
362 //                  << Automaton()->StateName( _currentState ) << " --> "
363 //                  << Automaton()->StateName( aState ) << " )"  << endl ;
364            _currentState = aState ; } ;
365       SUPERV::ControlState ControlState() const {
366              return _ControlState; };
367       void ControlState(SUPERV::ControlState aControlState ) {
368            _ControlState = aControlState ; } ;
369       void ControlClear() {
370            _ControlState = SUPERV::VoidState ; } ;
371
372       void SetAutomaton() {
373             _Automaton = theAutomaton ; } ;
374       GraphExecutor::FiniteStateMachine * Automaton() const {
375             return _Automaton ; } ;
376
377       bool IsWaiting() ;
378       bool IsReady() ;
379       bool IsRunning() ;
380       bool IsDone() ;
381       bool IsSuspended() ;
382       bool IsKilled() ;
383       bool IsStopped() ;
384       void IsLoading( bool Loading );
385       bool IsLoading() { return _Loading ; } ;
386
387       bool StateWait( SUPERV::GraphState aState ) ;
388       bool ReadyWait() ;
389       bool RunningWait() ;
390       bool DoneWait() ;
391       bool SuspendedWait() ;
392
393       void InitialState() ;
394       bool InitPythonFunctions(bool WithErr ) ;
395       void SetWaitingStates(GraphExecutor::InNode * EndNode ) ;
396
397       int SendEvent(const GraphExecutor::NodeEvent anEvent ) ;
398       void DataFromNode( char * FromNodeName ) {
399            _DataFromNode = FromNodeName ; } ;
400       const char * DataFromNode() const { return _DataFromNode ; } ;
401
402       int ErrorAction();
403       int VoidAction();
404       void ReadyAction() ;
405       void RunningAction() ;
406       void DoneAction() ;
407       void SuspendedAction() ;
408       GraphExecutor::InNode * SuspendAction() ;
409       bool ResumeAction(GraphExecutor::NodeEvent aResumeEvent ) ;
410       bool ReStartAction( GraphExecutor::InNode * aRestartNode ,
411                           GraphExecutor::NodeEvent anEvent ) ;
412       void KillAction() ;
413       void KilledAction() ;
414       void ThreadStartAction() ;
415       void ThreadStartedAction() ;
416       void StopAction() ;
417       void StoppedAction() ;
418       int executeAction() ; // New Thread or Same Thread
419       int ExecuteAction() ;
420
421       int DataWaiting_SomeDataReadyAction() ;
422       int DataUndef_NotAllDataReadyAction() ;
423       int DataUndef_AllDataReadyAction() ;
424       int DataReady_SuspendAction() ;
425       int SuspendedReady_ResumeAction() ;
426       int DataReady_KillAction() ;
427       int DataReady_StopAction() ;
428       int DataReady_ExecuteAction() ;
429       void DynInvoke( Engines::Component_ptr obj,
430                       const char *method, 
431                       ServicesAnyData * inParams, int nInParams,
432                       ServicesAnyData * outParams, int nOutParams) ;
433       void DynInvoke( Engines::Component_ptr obj,
434                       const char *method, 
435                       const char * aGraphName ,
436                       const char * aNodeName );
437       bool PyDynInvoke( PyObject * MyPyRunMethod ,
438                         const char *method , 
439                         ServicesAnyData * inParams , int nInParams ,
440                         ServicesAnyData * inParams , int nOutParams ) ;
441
442       int Executing_SuspendAction() ;
443       int SuspendedExecuting_ResumeAction() ;
444       int Executing_KillAction() ;
445       int Executing_StopAction() ;
446       int Executing_SuccessAction() ;
447       int Executing_ErrorAction() ;
448       int Successed_SuccessAction() ;
449       bool SendSomeDataReady( char * FromNodeName ) ;
450       int Errored_ErrorAction() ;
451       int Successed_SuspendAction() ;
452       int Errored_SuspendAction() ;
453       int SuspendedSuccessed_ResumeAction() ;
454       int SuspendedErrored_ResumeAction() ;
455       int Successed_KillAction() ;
456       int Errored_KillAction() ;
457       int Successed_StopAction() ;
458       int Errored_StopAction() ;
459       int SuspendedSuccessed_ReStartAction() ;
460       int SuspendedErrored_ReStartAction() ;
461       int SuspendedSuccessed_ReStartAndSuspendAction() ;
462       int SuspendedErrored_ReStartAndSuspendAction() ;
463
464       void InParametersSet( bool & Err ,
465                             int  nInParams ,
466                             ServicesAnyData * InParametersList ) ;
467       void InOutParametersSet( int nOutParams ,
468                                ServicesAnyData * OutParametersList ) ;
469       bool OutParametersSet( bool Err , SUPERV::GraphState PortState ,
470                              int nOutParams ,
471                              ServicesAnyData * OutParametersList ) ;
472       void coutbegin() ;
473       void coutexit() ;
474
475       const long CpuUsed( bool tot = false ) ;
476
477       long PyCpuUsed( bool tot = false ) ;
478       void SetPyCpuUsed() ;
479       long PyCpu() ;
480
481       bool PyRunSimpleString( char* thePyString );
482       PyObject * PyEvalCallObject( const char *method ,
483                                    PyObject * MyPyRunMethod ,
484                                    PyObject * ArgsList ) ;
485     } ;
486
487 } ;
488
489 #endif
490