Salome HOME
Join modifications from BR_Dev_For_4_0 tag V4_1_1.
[modules/superv.git] / src / GraphExecutor / DataFlowExecutor_OutNode.cxx
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.salome-platform.org/ or email : webmaster.salome@opencascade.com
21 //
22 //
23 //
24 //  File   : DataFlowBase_OutNode.cxx
25 //  Author : Jean Rahuel, CEA
26 //  Module : SUPERV
27 //  $Header:
28
29 using namespace std;
30
31 #include "DataFlowExecutor_OutNode.hxx"
32
33 #include "DataFlowEditor_DataFlow.hxx"
34 #include "DataFlowExecutor_DataFlow.hxx"
35
36 // asv : 20.01.05 : changes involved with switching to old (HEAD) KERNEL    
37 //extern Engines_Container_i * _TheContainer ;
38
39 extern GraphExecutor::FiniteStateMachine * theAutomaton ;
40
41 // static const char *ComponentName = "SalomeSuperVisionComponent" ;
42
43 extern int _ArgC ;
44 extern char ** _ArgV ;
45
46 GraphExecutor::OutNode::OutNode() {
47 //               Graph() {
48   // asv : 20.01.05 : changes involved with switching to old (HEAD) KERNEL    
49   //_SuperVisionContainer = _TheContainer ;
50   //_MainThreadId = SuperVisionContainer()->MainThreadId() ;
51   _Valid = false ;
52   _Executable = false ;
53   _Done = false ;
54   _NodeAborted = false ;
55   _Threads = 0 ;
56   _ControlState = SUPERV::VoidState ;
57   _State = GraphExecutor::UnKnownState ;
58   _PyInitialized = false ;
59   _run_func_thread = 0;
60   pthread_mutex_init( &_MutexWait , NULL ) ;
61   pthread_mutex_init( &_PyMutexWait , NULL ) ;
62   if ( pthread_cond_init( &_EventWait , NULL ) ) {
63     perror("pthread_cond_init( &_EventWait , NULL )") ;
64     exit( 0 ) ;
65   }
66   if ( pthread_cond_init( &_JoinWait , NULL ) ) {
67     perror("pthread_cond_init( &_JoinWait , NULL )") ;
68     exit( 0 ) ;
69   }
70 }
71
72 GraphExecutor::OutNode::OutNode( CORBA::ORB_ptr ORB, 
73                                  SALOME_NamingService* ptrNamingService ,
74                                  const char *DataFlowName ,
75                                  const char * DebugFileName ,
76                                  const SUPERV::KindOfNode aKindOfNode ) {
77   Set_prof_debug( ORB , DebugFileName ) ;
78   cdebug_in << "GraphExecutor::OutNode::OutNode(" << DataFlowName << " , " << DebugFileName
79             << " , " << aKindOfNode << ")" << endl;
80   if ( aKindOfNode == SUPERV::DataFlowGraph ) {
81     _StreamGraph = NULL ;
82     _Graph = new GraphBase::Graph( ORB , ptrNamingService , DataFlowName , aKindOfNode ,
83                                    _prof_debug , _fdebug ) ;
84   }
85   else if ( aKindOfNode == SUPERV::DataStreamGraph ) {
86     _StreamGraph = new GraphBase::StreamGraph( ORB , ptrNamingService , DataFlowName , aKindOfNode ,
87                                                _prof_debug , _fdebug ) ;
88     _Graph = _StreamGraph ;
89   }
90   // asv : 20.01.05 : changes involved with switching to old (HEAD) KERNEL    
91   //_SuperVisionContainer = _TheContainer ;
92   //_MainThreadId = SuperVisionContainer()->MainThreadId() ;
93   _Valid = false ;
94   _Executable = false ;
95   _Done = false ;
96   _NodeAborted = false ;
97   _Threads = 0 ;
98   _ControlState = SUPERV::VoidState ;
99   _State = GraphExecutor::UnKnownState ;
100   _PyInitialized = false ;
101   _run_func_thread = 0;
102   _Orb = CORBA::ORB::_duplicate( ORB ) ;
103   pthread_mutex_init( &_MutexWait , NULL ) ;
104   pthread_mutex_init( &_PyMutexWait , NULL ) ;
105   if ( pthread_cond_init( &_EventWait , NULL ) ) {
106     perror("pthread_cond_init( &_EventWait , NULL )") ;
107     exit( 0 ) ;
108   }
109   if ( pthread_cond_init( &_JoinWait , NULL ) ) {
110     perror("pthread_cond_init( &_JoinWait , NULL )") ;
111     exit( 0 ) ;
112   }
113   cdebug_out << "GraphExecutor::OutNode::OutNode" << endl;
114 }
115
116 GraphExecutor::OutNode::OutNode( CORBA::ORB_ptr ORB, 
117                                  SALOME_NamingService* ptrNamingService ,
118                                  const SALOME_ModuleCatalog::Service& DataFlowService ,
119                                  const char *DataFlowComponentName ,
120                                  const char *DataFlowInterfaceName ,
121                                  const char *DataFlowName ,
122                                  const SUPERV::KindOfNode DataFlowkind ,
123                                  const SUPERV::SDate DataFlowFirstCreation ,
124                                  const SUPERV::SDate DataFlowLastModification ,
125                                  const char * DataFlowEditorRelease ,
126                                  const char * DataFlowAuthor ,
127                                  const char * DataFlowComputer ,
128                                  const char * DataFlowComment ,
129                                  const char * DebugFileName ) {
130   Set_prof_debug( ORB , DebugFileName ) ;
131
132   cdebug_in << "GraphExecutor::OutNode::OutNode(" << DataFlowComponentName << " , "
133             << DataFlowInterfaceName << " , " << DataFlowName << " , " << DataFlowkind << ")"
134             << " , ... , " << DebugFileName << ")" << endl;
135   if ( DataFlowkind == SUPERV::DataFlowGraph ) {
136     _StreamGraph = NULL ;
137     _Graph = new GraphBase::Graph( ORB , ptrNamingService , DataFlowService , DataFlowComponentName ,
138                                    DataFlowInterfaceName , DataFlowName , DataFlowkind ,
139                                    DataFlowFirstCreation , DataFlowLastModification  ,
140                                    DataFlowEditorRelease , DataFlowAuthor ,
141                                    DataFlowComputer , DataFlowComment ,
142                                    _prof_debug , _fdebug ) ;
143 //                                   DataFlowComputer , DataFlowComment , DebugFileName ) ;
144   }
145   else if ( DataFlowkind == SUPERV::DataStreamGraph ) {
146     _StreamGraph = new GraphBase::StreamGraph( ORB , ptrNamingService , DataFlowService , DataFlowComponentName ,
147                                                DataFlowInterfaceName , DataFlowName , DataFlowkind ,
148                                                DataFlowFirstCreation , DataFlowLastModification  ,
149                                                DataFlowEditorRelease , DataFlowAuthor ,
150                                                DataFlowComputer , DataFlowComment ,
151                                                _prof_debug , _fdebug ) ;
152     _Graph = _StreamGraph ;
153   }
154   // asv : 20.01.05 : changes involved with switching to old (HEAD) KERNEL    
155   //_SuperVisionContainer = _TheContainer ;
156   //_MainThreadId = SuperVisionContainer()->MainThreadId() ;
157   _Valid = false ;
158   _Executable = false ;
159   _Done = false ;
160   _NodeAborted = false ;
161   _Threads = 0 ;
162   _ControlState = SUPERV::VoidState ;
163   _State = GraphExecutor::UnKnownState ;
164   _PyInitialized = false ;
165   _run_func_thread = 0;
166   _Orb = CORBA::ORB::_duplicate( ORB ) ;
167   pthread_mutex_init( &_MutexWait , NULL ) ;
168   pthread_mutex_init( &_PyMutexWait , NULL ) ;
169   if ( pthread_cond_init( &_EventWait , NULL ) ) {
170     perror("pthread_cond_init( &_EventWait , NULL )") ;
171     exit( 0 ) ;
172   }
173   if ( pthread_cond_init( &_JoinWait , NULL ) ) {
174     perror("pthread_cond_init( &_JoinWait , NULL )") ;
175     exit( 0 ) ;
176   }
177 }
178
179 GraphExecutor::OutNode::~OutNode() {
180 }
181
182 void GraphExecutor::OutNode::Set_prof_debug( CORBA::ORB_ptr ORB ,
183                                              const char * DebugFileName ) {
184   _Graph_prof_debug = 0 ;
185   if ( DebugFileName ) {
186     _fdebug = new ofstream( DebugFileName );
187     SetDebug( ORB , &_Graph_prof_debug , _fdebug ) ;
188     MESSAGE( endl << "Trace redirected to file " << DebugFileName << endl)
189   }
190 }
191
192 bool GraphExecutor::OutNode::LoadDataFlow(const GraphBase::SGraph * aDataFlow ) {
193   bool RetVal = false ;
194   cdebug_in << "GraphExecutor::OutNode::LoadDataFlow " << (*aDataFlow).Info.theName << endl ;
195   RetVal = LoadInfo( (*aDataFlow).Info ) ;
196   if ( Graph()->ServiceName() != NULL ) {
197 //    MESSAGE( "GraphExecutor::OutNode::LoadDataFlow" );
198     if ( RetVal ) {
199       RetVal = LoadNodes( (*aDataFlow).Nodes ) ;
200       if ( RetVal ) {
201         RetVal = LoadLinks( (*aDataFlow).Links ) ;
202         if ( RetVal ) {
203           IsValid() ;
204           RetVal = LoadDatas( (*aDataFlow).Datas ) ;
205 //          IsExecutable() ;
206           if ( !RetVal) {
207             cdebug << "GraphExecutor::OutNode::LoadDataFlow LoadDatas Error."
208                    << endl ;
209           }
210         }
211         else {
212           cdebug << "GraphExecutor::OutNode::LoadDataFlow LoadLinks Error."
213                << endl ;
214         }
215       }
216       else {
217         cdebug << "GraphExecutor::OutNode::LoadDataFlow LoadNodes Error."
218              << endl ;
219       }
220     }
221     else {
222       cdebug << "GraphExecutor::OutNode::LoadDataFlow LoadInfo Error."
223            << endl ;
224     }
225   }
226   else {
227     cdebug << "GraphExecutor::OutNode::LoadDataFlow ServiceName Error." << endl ;
228   }
229   cdebug_out << "GraphExecutor::OutNode::LoadDataFlow " << Name() << " RetVal "
230              << RetVal << endl ;
231   return RetVal ;
232 }
233
234 #if 0
235 bool GraphExecutor::OutNode::LoadXml( const char* myFileName ) {
236   bool RetVal = false ;
237   GraphBase::ListOfSGraphs aListOfDataFlows ;
238   if ( Graph()->LoadXml( _Orb , myFileName , aListOfDataFlows ) ) {
239     RetVal = LoadDataFlow( aListOfDataFlows ) ;
240 //    if ( aConstructor && RetVal )
241 //      RetVal = Name( aDataFlow.Info.theName.c_str() ) ;
242   }
243   return RetVal ;
244 }
245 #endif
246
247 bool GraphExecutor::OutNode::LoadInfo(const GraphBase::SNode &aDataFlowInfo ) {
248   cdebug << "GraphExecutor::OutNode::LoadInfo _StreamGraph " << _StreamGraph << endl ;
249 //  ComponentName( aDataFlowInfo.theComponentName.c_str()  ) ;
250   Graph()->Name( aDataFlowInfo.theName.c_str()  ) ;
251   Graph()->Kind( aDataFlowInfo.theKind ) ;
252   if ( Graph()->IsDataStreamNode() && aDataFlowInfo.theKind == SUPERV::DataStreamGraph ) {
253     StreamGraph()->SetStreamParams( aDataFlowInfo.theTimeout , aDataFlowInfo.theDataStreamTrace , aDataFlowInfo.theDeltaTime ) ;
254   }
255   Graph()->DataService( _Orb , aDataFlowInfo.theService , _prof_debug , _fdebug ) ;
256   Graph()->FirstCreation( aDataFlowInfo.theFirstCreation ) ;
257   Graph()->LastModification( aDataFlowInfo.theLastModification ) ;
258   Graph()->EditorRelease( aDataFlowInfo.theEditorRelease.c_str()  ) ;
259   Graph()->Author( aDataFlowInfo.theAuthor.c_str()   ) ;
260 //  Graph()->Computer( aDataFlowInfo.theContainer.c_str()  ) ;
261   Graph()->Comment( aDataFlowInfo.theComment.c_str()  ) ;
262 // Not in OutNode/DataFlow but in InNode/DataFlow_in_an_other_DataFlow
263 //  Graph()->Coordinates( aDataFlowInfo.theX , aDataFlowInfo.theY ) ;
264   return true ;
265 }
266
267 bool GraphExecutor::OutNode::LoadNodes(const GraphBase::ListOfSNodes &aListOfNodes ) {
268   bool RetVal = true ;
269   GraphExecutor::InNode * anInNode ;
270   cdebug << "GraphExecutor::OutNode::LoadNodes" << endl ;
271   int i ;
272   for ( i = 0 ; i < (int ) aListOfNodes.size() ; i++ ) {
273     GraphBase::SNode aNode = aListOfNodes[ i ] ;
274     anInNode = AddNode( aNode.theService ,
275                         aNode.theListOfFuncName ,
276                         aNode.theListOfPythonFunctions ,
277                         aNode.theComponentName.c_str() ,
278                         aNode.theInterfaceName.c_str()  , aNode.theName.c_str() ,
279                         aNode.theKind ,
280                         aNode.theFirstCreation , aNode.theLastModification ,
281                         aNode.theEditorRelease.c_str() ,
282                         aNode.theAuthor.c_str()  , aNode.theContainer.c_str() ,
283                         aNode.theComment.c_str() ,
284                         aNode.theCoords.theX , aNode.theCoords.theY ) ;
285     if ( !anInNode ) {
286       RetVal = false ;
287       break ;
288     }
289     if ( anInNode->IsOneOfInLineNodes() || anInNode->IsMacroNode() ) {
290       anInNode->GraphExecutor::InNode::InLineNode()->DefPortsOfNode(
291                                 _Orb , aNode.theService , anInNode->NamePtr() ,
292                                 anInNode->Kind() ,
293                                 _prof_debug , _fdebug ) ;
294     }
295 //    GraphBase::ComputingNode * theNode = Graph()->GetChangeGraphNode( aNode.theName.c_str() ) ;
296
297     unsigned int j ;
298     for ( j = 0 ; j < aNode.theListOfInDataStreams.size() ; j++ ) {
299       GraphBase::InPort * anInPort ;
300       anInPort = anInNode->ComputingNode()->AddInDataStreamPort( aNode.theListOfInDataStreams[ j ].theDataStreamParameter.Parametername ,
301                                                                  aNode.theListOfInDataStreams[ j ].theDataStreamParameter.Parametertype ,
302                                                                  aNode.theListOfInDataStreams[ j ].theDataStreamParameter.Parameterdependency ,
303                                                                  SUPERV::DataStreamParameter ) ;
304       ((GraphBase::InDataStreamPort * ) anInPort)->SetParams( aNode.theListOfInDataStreams[ j ].theKindOfSchema ,
305                                                               aNode.theListOfInDataStreams[ j ].theKindOfInterpolation ,
306                                                               aNode.theListOfInDataStreams[ j ].theKindOfExtrapolation ) ;
307     }
308     for ( j = 0 ; j < aNode.theListOfOutDataStreams.size() ; j++ ) {
309       GraphBase::OutPort * anOutPort ;
310       anOutPort = anInNode->ComputingNode()->AddOutDataStreamPort( aNode.theListOfOutDataStreams[ j ].theDataStreamParameter.Parametername ,
311                                                                    aNode.theListOfOutDataStreams[ j ].theDataStreamParameter.Parametertype ,
312                                                                    aNode.theListOfOutDataStreams[ j ].theDataStreamParameter.Parameterdependency ,
313                                                                    SUPERV::DataStreamParameter ) ;
314       ((GraphBase::OutDataStreamPort * ) anOutPort)->NumberOfValues( aNode.theListOfOutDataStreams[ j ].theNumberOfValues ) ;
315     }
316
317
318 //    theNode->DataStreamInPortsNumber( aNode.theDataStreamInArgsNumber ) ;
319 //    theNode->DataStreamOutPortsNumber( aNode.theDataStreamOutArgsNumber ) ;
320 //    cdebug << "GraphExecutor::OutNode::LoadNodes " << anInNode->Name()
321 //           << " InPortsSize " << theNode->GetNodeInPortsSize()
322 //           << " OutPortsSize " << theNode->GetNodeOutPortsSize()
323 //           << " DataStreamInPortsNumber " << aNode.theDataStreamInArgsNumber
324 //           << " DataStreamOutPortsNumber " << aNode.theDataStreamOutArgsNumber
325 //           << endl ;
326 //    int j ;
327 //    if ( aNode.theDataStreamInArgsNumber ) { // -1 because of Gates
328 //      for ( j = theNode->GetNodeInPortsSize() - aNode.theDataStreamInArgsNumber - 1 ; j < theNode->GetNodeInPortsSize() - 1 ; j++ ) {
329 //        cdebug << "GraphExecutor::OutNode::LoadNodes " << anInNode->Name()
330 //               << " InPort " << theNode->GetChangeNodeInPort( j )->PortName()
331 //               << " Kind( DataStreamParameter)" << endl ;
332 //        theNode->GetChangeNodeInPort( j )->Kind( SUPERV::DataStreamParameter ) ;
333 //      }
334 //    }
335 //    if ( aNode.theDataStreamOutArgsNumber ) {
336 //      int withgate = 1 ;
337 //      if ( theNode->IsLoopNode() || theNode->IsEndLoopNode() ) {
338 //        withgate = 0 ;
339 //      }
340 //      for ( j = theNode->GetNodeOutPortsSize() - aNode.theDataStreamOutArgsNumber - withgate ; j < theNode->GetNodeOutPortsSize() - withgate ; j++ ) {
341 //        cdebug << "GraphExecutor::OutNode::LoadNodes " << anInNode->Name()
342 //               << " OutPort " << theNode->GetChangeNodeOutPort( j )->PortName()
343 //               << " Kind( DataStreamParameter)" << endl ;
344 //        theNode->GetChangeNodeOutPort( j )->Kind( SUPERV::DataStreamParameter ) ;
345 //      }
346 //    }
347   }
348   for ( i = 0 ; i < (int ) aListOfNodes.size() ; i++ ) {
349     GraphBase::SNode aNode = aListOfNodes[ i ] ;
350     anInNode = (GraphExecutor::InNode * ) Graph()->GetChangeGraphNode( aNode.theName.c_str() )->GetInNode() ;
351     cdebug << "GraphExecutor::OutNode::LoadNodes " << anInNode->Name() << " IsOneOfGOTONodes "
352            << anInNode->IsOneOfGOTONodes() << " " << aNode.theCoupledNode.c_str() << endl ;
353     if ( anInNode->IsOneOfGOTONodes() && strlen( aNode.theCoupledNode.c_str() ) ) {
354       GraphBase::GOTONode * aCoupledNode ;
355       aCoupledNode = (GraphBase::GOTONode * ) Graph()->GetGraphNode( aNode.theName.c_str() ) ;
356       GraphBase::GOTONode * aCoupledCoupledNode ;
357       aCoupledCoupledNode = (GraphBase::GOTONode * ) Graph()->GetChangeGraphNode( aNode.theCoupledNode.c_str() ) ;
358       if ( aCoupledCoupledNode != NULL ) {
359         aCoupledNode->CoupledNode( aCoupledCoupledNode ) ;
360       }
361       else {
362         aCoupledNode->CoupledNodeName( aNode.theCoupledNode.c_str() ) ;
363       }
364     }
365   }
366   return RetVal ;
367 }
368
369 bool GraphExecutor::OutNode::LoadLinks(const GraphBase::ListOfSLinks &aListOfLinks ) {
370   bool RetVal = true ;
371   cdebug << "GraphExecutor::OutNode::LoadLinks " << aListOfLinks.size()
372          << endl ;
373   int i ;
374   for ( i = 0 ; i < (int ) aListOfLinks.size() ; i++ ) {
375     GraphBase::SLink aLink = aListOfLinks[ i ] ;
376     RetVal = Graph()->AddLink( aLink.FromNodeName.c_str() ,
377                                aLink.FromServiceParameterName.c_str() ,
378                                aLink.ToNodeName.c_str() ,
379                                aLink.ToServiceParameterName.c_str() ) ;
380 //                               , aLink.aLinkValue ) ;
381     if ( !RetVal )
382       break ;
383   }
384   return RetVal ;
385 }
386
387 bool GraphExecutor::OutNode::LoadDatas(const GraphBase::ListOfSLinks &aListOfDatas ) {
388   bool RetVal = true ;
389   cdebug << "GraphExecutor::OutNode::LoadDatas " << aListOfDatas.size()
390          << endl ;
391   int i ;
392   for ( i = 0 ; i < (int ) aListOfDatas.size() ; i++ ) {
393     GraphBase::SLink aLink = aListOfDatas[ i ] ;
394     if ( !strcmp( aLink.FromNodeName.c_str() , Name() ) )
395       RetVal = Graph()->AddInputData( aLink.ToNodeName.c_str() ,
396                                       aLink.ToServiceParameterName.c_str() ,
397                                       aLink.aLinkValue ) ;
398 //    else if ( !strcmp( aLink.ToNodeName.c_str() , Name() ) ) {
399 //      RetVal = Graph()->AddOutputData( aLink.FromNodeName.c_str() ,
400 //                                       aLink.FromServiceParameterName.c_str() ) ;
401 //      Graph()->AddLink( aLink.FromNodeName.c_str() , (GraphBase::ComputingNode *) this ) ;
402 //    }
403     else {
404       cdebug << "GraphExecutor::OutNode::LoadDatas Error " << aLink.FromNodeName
405            << " and " << aLink.ToNodeName << " differents from " << Name()
406            << endl ;
407       RetVal = false ;
408     }
409     if ( !RetVal )
410       break ;
411   }
412   return RetVal ;
413 }
414
415 GraphExecutor::InNode *GraphExecutor::OutNode::AddNode(
416                       const SALOME_ModuleCatalog::Service& NodeService ,
417                       GraphBase::ListOfFuncName aFuncName ,
418                       GraphBase::ListOfPythonFunctions aPythonFunction ,
419                       const char * NodeComponentName ,
420                       const char * NodeInterfaceName ,
421                       const char * NodeName ,
422                       const SUPERV::KindOfNode NodeKindOfNode ,
423                       const SUPERV::SDate NodeFirstCreation ,
424                       const SUPERV::SDate NodeLastModification  ,
425                       const char * NodeEditorRelease ,
426                       const char * NodeAuthor ,
427                       const char * NodeComputer ,
428                       const char * NodeComment ,
429                       const int NodeX ,
430                       const int NodeY ) {
431   cdebug_in << "GraphExecutor::OutNode::AddNode(" << NodeComponentName << " , "
432             << NodeName << ")" << endl;
433   GraphExecutor::InNode *Nd = NULL ;
434   Nd = new GraphExecutor::InNode( _Orb, Graph()->NamingService() , NodeService ,
435                                   NodeComponentName , NodeInterfaceName ,
436                                   NodeName , NodeKindOfNode ,
437                                   aFuncName , aPythonFunction ,
438                                   NodeFirstCreation , NodeLastModification ,
439                                   NodeEditorRelease , NodeAuthor ,
440                                   NodeComputer , NodeComment , false , NodeX , NodeY ,
441                                   _prof_debug , _fdebug ) ;
442   Graph()->AddNode( Nd->ComputingNode() ) ;
443   cdebug_out << "GraphExecutor::OutNode::AddNode" << endl;
444   return Nd ;
445 }
446
447
448 bool GraphExecutor::OutNode::Valid() {
449   cdebug_in << "GraphExecutor::OutNode::Valid" << endl;
450   bool RetVal = true ;
451   Graph()->ReSetMessages() ; // ==> Only one set of errors messages ...
452   if ( _Valid )
453     return true ;
454
455   _Executable = false ;
456
457   if ( !Graph()->CreateService() ) {
458     cdebug_out << "This DataFlow has invalid type(s)." << endl ;
459     RetVal = false ;
460   }
461   int SubStreamGraphsNumber = 0 ;
462   if ( !Graph()->Sort( SubStreamGraphsNumber ) ) {
463     cdebug_out << "This DataFlow is not valid." << endl ;
464     RetVal = false ;
465   }
466   if ( Graph()->IsDataStreamNode() ) {
467     StreamGraph()->SubStreamGraphsNumber( SubStreamGraphsNumber ) ;
468   }
469   Graph()->InLineServices() ;
470
471   if ( !Graph()->ValidLoops() ) {
472     cdebug_out << "This DataFlow have not valid Loops." << endl ;
473     RetVal = false ;
474   }
475   if ( !Graph()->ValidSwitchs() ) {
476     cdebug_out << "This DataFlow have not valid Switchs." << endl ;
477     RetVal = false ;
478   }
479
480 //  CreateService() ;
481
482   Graph()->ComputingNodes() ;
483   if ( RetVal ) {
484     _Valid = true ;
485   }
486
487   cdebug_out << "GraphExecutor::OutNode::Valid " << _Valid << " RetVal " << RetVal << endl;
488   return RetVal ;
489 }
490
491 bool GraphExecutor::OutNode::Executable() {
492   cdebug_in << "GraphExecutor::OutNode::Executable" << endl;
493   bool RetVal = true ;
494   if ( !IsValid() ) {
495     RetVal = false ;
496   }
497
498   if ( Graph()->DataServerNodes() ) {
499     if ( RetVal ) {
500       _Executable = true ;
501     }
502   }
503   else {
504     cdebug << "This DataFlow is not executable." << endl ;
505     _Executable = false ;
506     RetVal = false ;
507   }
508
509   cdebug_out << "GraphExecutor::OutNode::Executable " << _Executable << endl;
510   return _Executable ;
511 }
512
513 bool GraphExecutor::OutNode::Run( const bool AndSuspend ) {
514   bool RetVal = false ;
515   cdebug_in << pthread_self() << "GraphExecutor::OutNode::Run( AndSuspend " << AndSuspend
516             << " ) State " << theAutomaton->StateName( State() ) << endl;
517
518   if ( Executable() ) {
519     _ControlState = SUPERV::VoidState ;
520     _SuspendedThreads = 0 ;
521     Graph()->ThreadNo( pthread_self() ) ;
522     Done( false ) ;
523     _JustStarted = true ;
524     RetVal = true ;
525     int i ;
526     bool again = true ;
527     for ( i = 0 ; i < Graph()->GraphNodesSize() ; i++ ) {
528       GraphExecutor::InNode * anInNode = (GraphExecutor::InNode *) Graph()->GraphNodes( i )->GetInNode() ;
529       anInNode->OutNode( this ) ;
530 // Initialize in python interpretor the python functions
531       if ( !PyInitialized() && anInNode->IsOneOfInLineNodes() ) {
532         if ( !Py_IsInitialized() ) {
533 //          PyEval_InitThreads() ;
534 //          Py_Initialize() ;
535           // asv : 20.01.05 : changes involved with switching to old (HEAD) KERNEL  
536           //                  1 line below uncommented
537           PySys_SetArgv( _ArgC , _ArgV ) ;
538         }
539         anInNode->InitPython() ;
540         PyInitialized( true ) ;
541       }
542       anInNode->InitialState() ;
543       if ( anInNode->IsOneOfInLineNodes() ) {
544         //JR with Python2.3.4, we may get an error because of a normal previous error
545         bool sts = anInNode->InitPythonFunctions( false ) ;
546         if ( again && !sts ) {
547           sts = anInNode->InitPythonFunctions( false ) ;
548           again = false ;
549         }
550       }
551     }
552 // One more time because inline nodes may share one definition of the same function
553     for ( i = 0 ; i < Graph()->GraphNodesSize() ; i++ ) {
554       GraphExecutor::InNode * anInNode = (GraphExecutor::InNode *) Graph()->GraphNodes( i )->GetInNode() ;
555       if ( anInNode->IsOneOfInLineNodes() ) {
556         if ( !anInNode->InitPythonFunctions( true ) ) {
557           anInNode->State( GraphExecutor::ErroredState ) ;
558 // PAL 8515
559 //JR 24.03.2005 debug : State and done flags were missing
560           State( GraphExecutor::ErroredState ) ;
561           Done( true ) ;
562           cdebug_out << "GraphExecutor::OutNode::Run InitPythonFunctions ERROR "
563                      << anInNode->Name() << endl ;
564           RetVal = false ;
565         }
566       }
567     }
568     /* asv : 29.09.04 : commented out because it does not do anything useful 
569     for ( i = 0 ; i < Graph()->GraphNodesSize() ; i++ ) {
570       GraphExecutor::InNode * anInNode = (GraphExecutor::InNode *) Graph()->GraphNodes( i )->GetInNode() ;
571       if ( RetVal && anInNode->IsMacroNode() ) {
572         GraphBase::Graph * aMacroGraph = anInNode->GraphMacroNode() ;
573         cdebug << "GraphExecutor::OutNode::Run " << anInNode << " MacroNode " << aMacroGraph
574                << aMacroGraph->Name() << endl ;
575         SUPERV::Graph_var iobject = anInNode->GraphMacroNode()->MacroObject() ;
576         if ( CORBA::is_nil( iobject ) ) {
577           cdebug << "GraphExecutor::OutNode::Run MacroObject() is a nil object. Error" << endl ;
578           RetVal = false ;
579         }
580         else {
581           cdebug << "GraphExecutor::OutNode::Run MacroObject() is NOT a nil object." << endl ;
582         }
583       }
584     }
585     */
586     //JR Debug : if there was an error in initialisation of python functions,
587     //           we must not try to execute the graph.
588     if ( RetVal ) {
589     if ( Graph()->GraphMacroLevel() != 0 ) {
590       cdebug << "GraphExecutor::OutNode::Run Execution starting GraphExecutor::Action_DataOk_RunService Node "
591              << Name() << " GraphMacroLevel " << Graph()->GraphMacroLevel() << endl ;
592       PushEvent( NULL , GraphExecutor::NoDataReadyEvent ,
593                  GraphExecutor::DataUndefState ) ; 
594     }
595     else {
596       cdebug << "Execution starting GraphExecutor::Action_DataOk_RunService Node "
597              << Name() << " GraphMacroLevel " << Graph()->GraphMacroLevel() << endl ;
598       PushEvent( NULL , GraphExecutor::ReadyEvent ,
599                  GraphExecutor::DataReadyState ) ; 
600       State( GraphExecutor::DataReadyState ) ;
601
602       cdebug << pthread_self() << " GraphExecutor::OutNode::Run Start of the " << Graph()->HeadNodesSize()
603              << " HeadNodes" << endl ;
604       for ( i = 0 ; i < Graph()->HeadNodesSize() ; i++ ) {
605         GraphExecutor::InNode * anInNode = (GraphExecutor::InNode *) Graph()->HeadNodes( i )->GetInNode() ;
606         cdebug << pthread_self() <<  "GraphExecutor::OutNode::Run Start of HeadNode " << i << " "
607                << anInNode->Name() << endl ;
608         if ( anInNode->State() != GraphExecutor::DataReadyState ) {
609 // PAL 8515
610 //JR 24.03.2005 debug : State and done flags were missing
611           State( GraphExecutor::ErroredState ) ;
612           Done( true ) ;
613           cdebug << "GraphExecutor::OutNode::Run inconsistency State of Node "
614                  << anInNode->Name() << " : " << anInNode->State() << endl ;
615           cdebug_out << "GraphExecutor::OutNode::Run State ERROR" << endl ;
616           return false ;
617         }
618 //        PushEvent( anInNode , GraphExecutor::ReadyEvent ,
619 //                   GraphExecutor::DataReadyState ) ; 
620 // We say that we have to create a thread for that HeadNode 'anInNode'
621         if ( !anInNode->IsMacroNode() ) {
622           anInNode->CreateNewThread( true ) ;
623           IncrCreatedThreads() ;
624         }
625         anInNode->DataFromNode( Name() ) ;
626 // AndSuspend == true <==> Start()
627         if ( AndSuspend ) {
628           anInNode->State( GraphExecutor::DataWaitingState ) ;
629           anInNode->ControlState( SUPERV::ToSuspendStartState ) ;
630 // We send SomeDataReadyEvent
631 // It is a HeadNode ==> AllDataReadyEvent ==> InNode::executeAction() ==> pthread_create
632           if ( !anInNode->SendEvent( GraphExecutor::SomeDataReadyEvent ) ) {
633 // PAL 8515
634 //JR 24.03.2005 debug : State and done flags were missing
635             State( GraphExecutor::ErroredState ) ;
636             Done( true ) ;
637             cdebug << "InNode::SendEvent( SomeDataReadyEvent ) ERROR Node "
638                    << anInNode->Name() << endl ;
639             cdebug_out << "GraphExecutor::OutNode::Run SendEvent ERROR" << endl ;
640             return false ;
641           }
642 // ==> We wait for SuspendedState
643           anInNode->SuspendedWait() ;
644         }
645 // AndSuspend == false <==> Run()
646         else if ( anInNode->IsMacroNode() ) {
647           if ( !anInNode->SendEvent( GraphExecutor::SomeDataReadyEvent ) ) {
648 // PAL 8515
649 //JR 24.03.2005 debug : State and done flags were missing
650             State( GraphExecutor::ErroredState ) ;
651             Done( true ) ;
652             cdebug << "InNode::SendEvent( SomeDataReadyEvent ) ERROR Node "
653                    << anInNode->Name() << endl ;
654             cdebug_out << "GraphExecutor::OutNode::Run SendEvent ERROR" << endl ;
655             return false ;
656           }
657 //JR 15.04.2005 Debug PAL8624 RetroConception :
658           anInNode->CreateNewThread( true ) ;
659           IncrCreatedThreads() ;
660           if ( anInNode->HasAllDataReady() ) {
661             if ( !anInNode->SendEvent( GraphExecutor::AllDataReadyEvent ) ) { // ==> Ready to execute
662               cdebug <<  "GraphExecutor::OutNode::Run SendEvent(AllDataReadyEvent) ERROR "
663                      << " Node " << anInNode->Name() << endl ;
664               cdebug_out << "GraphExecutor::OutNode::Run SendEvent ERROR" << endl ;
665               return false ;
666             }
667           }
668           else {
669             State( GraphExecutor::ErroredState ) ;
670             Done( true ) ;
671             cdebug <<  "GraphExecutor::OutNode::Run HasAllDataReady " << anInNode->HasAllDataReady()
672                    << " Node " << anInNode->Name() << endl ;
673             cdebug_out << "GraphExecutor::OutNode::Run HasAllDataReady ERROR" << endl ;
674             return false ;
675           }
676           cdebug << pthread_self() << " GraphExecutor::OutNode::Run " << anInNode->Name() << "->RunningWait"
677                  << endl ;
678 // ==> We wait for RunningState
679           anInNode->RunningWait() ;
680           cdebug << pthread_self() << " GraphExecutor::OutNode::Run " << anInNode->Name() << "->RunningWaited"
681                  << endl ;
682         }
683         else if ( !anInNode->IsMacroNode() ) {
684 // It is a HeadNode ==> AllDataReadyEvent ==> InNode::executeAction() ==> pthread_create
685           if ( !anInNode->SendEvent( GraphExecutor::ExecuteEvent ) ) {
686 // PAL 8515
687 //JR 24.03.2005 debug : State and done flags were missing
688             State( GraphExecutor::ErroredState ) ;
689             Done( true ) ;
690             cdebug << "InNode::SendEvent( ExecuteEvent ) ERROR Node "
691                    << anInNode->Name() << endl ;
692             cdebug_out << "GraphExecutor::OutNode::Run SendEvent ERROR" << endl ;
693             return false ;
694           }
695 // ==> We wait for RunningState
696           anInNode->RunningWait() ;
697         }
698       }
699
700       if ( AndSuspend ) {
701         PushEvent( NULL , GraphExecutor::SuspendedReadyEvent ,
702                    GraphExecutor::SuspendedReadyState ) ; 
703       }
704       else {
705         PushEvent( NULL , GraphExecutor::ExecutingEvent ,
706                    GraphExecutor::ExecutingState ) ; 
707         if (AutomatonState() == GraphExecutor::DataReadyState) {
708             State( GraphExecutor::ExecutingState ) ;
709         };
710       }
711 //      ostringstream astr ;
712 //      astr << "Graph " << Name() << " is running" ;
713 //      Graph()->ObjImpl()->sendMessage( NOTIF_STEP, astr.str().c_str() ) ;
714       RetVal = true ;
715     }
716     //JR Debug
717     }
718     else {
719       State( GraphExecutor::ErroredState ) ;
720       Done( true ) ;
721       if ( IsDone() && Graph()->GraphMacroLevel() == 0 ) {
722         cdebug << " ==> theAutomaton->Executed() " << endl ;
723         theAutomaton->Executed() ;
724       }
725       else {
726         cdebug << " NO theAutomaton->Executed() " << endl ;
727       }
728     }
729   }
730   else {
731 // PAL 8515
732 //JR 24.03.2005 debug : State and done flags were missing
733     State( GraphExecutor::ErroredState ) ;
734     Done( true ) ;
735 //JR 17.06.2005 debug call to executed was missing ===>
736 //              _GraphExecutingNumber field of FiniteStateMachine was not decremented ===>
737 //              register of python functions was de-activated ==>
738 //              two graphs execution with two different python functions with the same name
739 //              give aborted state for the second one
740 //Example : GraphLoopSwitchOfSwitchNOTValid, GraphLoopSwitchs and GraphLoopSwitchsBranches
741     if ( IsDone() && Graph()->GraphMacroLevel() == 0 ) {
742       cdebug << " ==> theAutomaton->Executed() " << endl ;
743       theAutomaton->Executed() ;
744     }
745     else {
746       cdebug << " NO theAutomaton->Executed() " << endl ;
747     }
748     cdebug_out << "GraphExecutor::OutNode::Run Not Executable ERROR " << endl ;
749     return false ;
750   }
751
752   cdebug_out << pthread_self() << "GraphExecutor::OutNode::Run " << Name()
753              << " State " << theAutomaton->StateName( State() ) << " GraphMacroLevel "
754              << Graph()->GraphMacroLevel() << " RetVal " << RetVal << endl ;
755   return RetVal ;
756 }
757
758 void GraphExecutor::OutNode::CheckAllDone() {
759   int j ;
760   cdebug_in << "GraphExecutor::OutNode::CheckAllDone " << endl;
761   GraphExecutor::AutomatonState OutNodeState = GraphExecutor::SuccessedState ;
762   GraphExecutor::AutomatonState InNodeState ;
763   bool AllDone = true ;
764   if ( !Done() ) {
765     for ( j = 0 ; j < Graph()->QueueNodesSize() ; j++ ) {
766       InNodeState = ( (GraphExecutor::InNode * ) Graph()->QueueNodes( j )->GetInNode() )->State() ;
767       cdebug << j << ". "
768              << ( (GraphExecutor::InNode * ) Graph()->QueueNodes( j )->GetInNode() )->Name()
769              << " " << theAutomaton->StateName( InNodeState ) << endl ;
770       if ( InNodeState != GraphExecutor::SuccessedState &&
771            InNodeState != GraphExecutor::ErroredState &&
772            InNodeState != GraphExecutor::DataWaitingState ) {
773         if ( !IsNodeAborted() ) {
774           AllDone = false ;
775         }
776       }
777       if ( InNodeState != GraphExecutor::SuccessedState &&
778            InNodeState != GraphExecutor::DataWaitingState &&
779            InNodeState != GraphExecutor::DataReadyState ) {
780         OutNodeState = InNodeState ;
781       }
782     }
783     if ( AllDone ) {
784       if( _Threads == 0 && _SuspendedThreads == 0 ) {
785         if ( OutNodeState != GraphExecutor::ErroredState ) {
786           OutNodeState = GraphExecutor::SuccessedState ;
787         }
788       }
789       else {
790         AllDone = false ;
791       }
792     }
793     if ( AllDone ) {
794       int alivenodes = 0 ;
795       for ( j = 0 ; j < Graph()->GraphNodesSize()  ; j++ ) {
796         GraphExecutor::InNode * aNode ;
797         aNode = (GraphExecutor::InNode * ) Graph()->GraphNodes( j )->GetInNode() ;
798         SUPERV::GraphState aState = AutomatonGraphState( aNode->State() ) ;
799         cdebug << "GraphExecutor::OutNode::CheckAllDone " << aNode->Name() << " "
800                << theAutomaton->StateName( aNode->State() ) << " CreateNewThread " << aNode->CreateNewThread()
801                << endl ;
802         if ( aState == SUPERV::ErrorState ||
803              aState == SUPERV::SuspendErroredState ||
804              aState == SUPERV::KillState ||
805              aState == SUPERV::StopState ) {
806           OutNodeState = aNode->State() ;
807           State( OutNodeState ) ;
808         }
809         else if ( aState == SUPERV::ReadyState ||
810                   aState == SUPERV::SuspendReadyState ||
811                   aState == SUPERV::RunningState ||
812                   aState == SUPERV::SuspendDoneState ||
813                   aState == SUPERV::SuspendErroredState ||
814                   aState == SUPERV::SuspendState ) {
815           if ( !IsNodeAborted() ) {
816             alivenodes += 1 ;
817           }
818         }
819         aNode->SuspendedAction() ;
820         aNode->DoneAction() ;
821       }
822 // PushEvent AFTER State and _Done ! ...
823       if ( alivenodes == 0 ) {
824         State( OutNodeState ) ;
825         Done( true ) ;
826         _JustStarted = false ;
827       }
828       cdebug << Name() << " alivenodes " << alivenodes << " OutNodeState " << OutNodeState
829              << endl ;
830       PushEvent( NULL , GraphExecutor::EndExecuteEvent ,
831                  OutNodeState ) ;
832 //      Py_Finalize() ;
833 //      PyInitialized( false ) ;
834     }
835   }
836   if ( IsDone() ) {
837     MESSAGE("================================================================================") ;
838     MESSAGE( Name() << " IS DONE : " <<  theAutomaton->StateName( AutomatonState() ) << " EventQSize "
839              << EventQSize() ) ;
840     MESSAGE("================================================================================") ;
841     cdebug << "================================================================================" << endl ;
842     cdebug << Name() << " IS DONE : " <<  theAutomaton->StateName( AutomatonState() ) << " EventQSize "
843              << EventQSize() << endl  ;
844     cdebug << "================================================================================" << endl ;
845
846     if ( Graph()->GraphMacroLevel() != 0 ) {
847 //JR NPAL14110 09.02.2007 : That must be done only at the end of SubGraph because we may
848 //                          have an output of the SubGraph in a Loop !...
849 //                          So that code must be done in CheckAllDone instead of OutParametersSet
850       cdebug << "CheckAllDone ToNodeName " << Name() << " CoupledNode "
851              << Graph()->CoupledNodeName() << Graph()->CoupledNode()
852              << endl ;
853       cdebug << "CheckAllDone GraphExecutor " << Graph()->CoupledNode()->GraphEditor()->Executor() << endl ;
854       const GraphBase::InPort * anInPort ;
855       GraphBase::OutPort * anOutPort ;
856       int i ;
857       for ( i = 0 ; i <  Graph()->GetNodeOutDataNodePortsSize() ; i++ ) {
858          anInPort = Graph()->GetNodeOutDataNodePort( i ) ;
859          if ( !anInPort->IsGate() ) {
860            anOutPort = anInPort->GetOutPort() ;
861            Graph()->CoupledNode()->GraphEditor()->Executor()->OutputOfAny( Graph()->CoupledNodeName() ,
862                                                                            anInPort->PortName() ,
863                                                                            anOutPort->Value() ) ;
864            cdebug << "CheckAllDone OutputOfAny( " << Graph()->CoupledNodeName() << " , "
865                   << anInPort->PortName() << " , value ) done" << endl ;
866          }
867       }
868     }
869
870 //PAL8520
871 //JR 23.02.2005, Debug : siftEvents() must be inside the pthread_mutex_lock
872     if ( pthread_mutex_lock( &_MutexWait ) ) {
873       perror("EventLoop pthread_mutex_lock ") ;
874       exit( 0 ) ;
875     }
876     // asv : fix for 6798 and other bugs: "sift" the event queue after execution
877     siftEvents();
878     if ( pthread_mutex_unlock( &_MutexWait ) ) {
879       perror("PushEvent pthread_mutex_unlock ") ;
880       exit( 0 ) ;
881     }
882
883     // asv : 25.10.04 : calling Editing() to indicate stop of execution
884     Graph()->GraphEditor()->Editing();
885   }
886   cdebug_out << "GraphExecutor::OutNode::CheckAllDone " << IsDone() << " this " << this << " "
887              << Name() << " GraphAutomatonState "
888              << theAutomaton->StateName( AutomatonState() )
889              << " State " << State() << " Threads " << _Threads << " SuspendedThreads "
890              << _SuspendedThreads << " EventQSize " << EventQSize() << endl ;
891 }
892
893 // asv : 20.01.05 : changes involved with switching to old (HEAD) KERNEL    
894 //Engines_Container_i * GraphExecutor::OutNode::SuperVisionContainer() {
895 //  return _SuperVisionContainer ;
896 //}
897
898 //const pthread_t GraphExecutor::OutNode::MainThreadId() const {
899 //  return _MainThreadId ;
900 //}
901
902 void GraphExecutor::OutNode::PThreadLock( pthread_mutex_t * aMutex , char * errmsg ) {
903 //  if ( strcmp( errmsg , "EventLoop" ) && strcmp( errmsg , "EventW" ) ) {
904 //    cdebug << "GraphExecutor::OutNode::PThreadLock " << pthread_self() << " " << aMutex << " "
905 //           << errmsg << endl ;
906 //  }
907   if ( pthread_mutex_lock( aMutex ) ) {
908     perror( errmsg ) ;
909     exit( 0 ) ;
910   }
911 //  if ( strcmp( errmsg , "EventLoop" ) && strcmp( errmsg , "EventW" ) ) {
912 //    cdebug << "GraphExecutor::OutNode::PThreadLocked " << pthread_self() << " " << aMutex << " "
913 //           << errmsg << endl ;
914 //  }
915 }
916
917 void GraphExecutor::OutNode::PThreadUnLock( pthread_mutex_t * aMutex , char * errmsg ) {
918 //  if ( strcmp( errmsg , "EventLoop" ) && strcmp( errmsg , "EventW" ) ) {
919 //    cdebug << " GraphExecutor::OutNode::PThreadUnLock " << pthread_self() << " " << aMutex << " "
920 //           << errmsg << endl ;
921 //  }
922   if ( pthread_mutex_unlock( aMutex ) ) {
923     perror( errmsg ) ;
924     exit( 0 ) ;
925   }
926 }
927
928 void GraphExecutor::OutNode::PyThreadLock() {
929 //  cout << " GraphExecutor::OutNode::PyThreadLock " << pthread_self() << endl ;
930   if ( pthread_mutex_lock( &_PyMutexWait ) ) {
931     perror( "GraphExecutor::OutNode::PyThreadLock" ) ;
932     exit( 0 ) ;
933   }
934   theAutomaton->PyLock() ;
935 //  cout << " GraphExecutor::OutNode::PyThreadLocked " << pthread_self() << endl ;
936 }
937
938 void GraphExecutor::OutNode::PyThreadUnLock() {
939 //  cout << " GraphExecutor::OutNode::PyThreadUnLock " << pthread_self() << endl ;
940   if ( pthread_mutex_unlock( &_PyMutexWait ) ) {
941     perror( "GraphExecutor::OutNode::PyThreadUnLock" ) ;
942     exit( 0 ) ;
943   }
944   theAutomaton->PyUnLock() ;
945 //  cout << " GraphExecutor::OutNode::PyThreadUnLocked " << pthread_self() << endl ;
946 }
947
948 void GraphExecutor::OutNode::NewThread() {
949   if ( pthread_mutex_lock( &_MutexWait ) ) {
950     perror("pthread_mutex_lock _NewThread") ;
951     exit( 0 ) ;
952   }
953   _Threads += 1 ;
954 //  cdebug << "NewThread : " << _Threads << " running threads "
955 //         << _SuspendedThreads << " suspended threads"
956 //         << endl ;
957   if ( pthread_mutex_unlock( &_MutexWait ) ) {
958     perror("pthread_mutex_unlock _NewThread") ;
959     exit( 0 ) ;
960   }
961 }
962
963 void GraphExecutor::OutNode::ExitThread( pthread_t ThreadNumber ) {
964   if ( pthread_mutex_lock( &_MutexWait ) ) {
965     perror("pthread_mutex_lock _ExitThread") ;
966     exit( 0 ) ;
967   }
968   if ( ThreadNumber == 0 ) {
969     ThreadNumber = pthread_self() ;
970   }
971   _Threads -= 1 ;
972 //  cdebug << pthread_self() << " ExitThread( " << ThreadNumber << " ) " << _Threads << " running threads "
973 //         << _SuspendedThreads << " suspended threads"
974 //         << endl ;
975   theAutomaton->JoinThread( ThreadNumber ) ;
976   if ( pthread_cond_signal( &_JoinWait ) ) {
977     perror("ExitThread pthread_cond_signal ") ;
978   }
979   if ( pthread_mutex_unlock( &_MutexWait ) ) {
980     perror("pthread_mutex_unlock _ExitThread") ;
981     exit( 0 ) ;
982   }
983   if ( _Threads == 0 && _SuspendedThreads == 0 ) {
984     CheckAllDone() ;
985     cdebug << pthread_self() << " ExitThread( " << ThreadNumber << " ) " << _Threads
986            << " running threads " << _SuspendedThreads << " suspended threads IsDone() "
987            << IsDone() ;
988     _run_func_thread = 0 ; // mkr : IPAL14711
989     if ( IsDone() && Graph()->GraphMacroLevel() == 0 ) {
990       cdebug << " ==> theAutomaton->Executed() " << endl ;
991       theAutomaton->Executed() ;
992     }
993     else {
994       cdebug << " NO theAutomaton->Executed() " << endl ;
995     }
996   }
997 }
998 void GraphExecutor::OutNode::JoinedWait() {
999   if ( pthread_mutex_lock( &_MutexWait ) ) {
1000     perror("pthread_mutex_lock JoinedWait") ;
1001     exit( 0 ) ;
1002   }
1003   while ( _Threads ) {
1004     if ( pthread_cond_wait( &_JoinWait , &_MutexWait ) ) {
1005       perror("JoinedWait pthread_cond_wait ") ;
1006     }
1007   }
1008   if ( pthread_mutex_unlock( &_MutexWait ) ) {
1009     perror("pthread_mutex_unlock JoinedWait") ;
1010     exit( 0 ) ;
1011   }
1012 }
1013
1014 void GraphExecutor::OutNode::SuspendThread() {
1015   if ( pthread_mutex_lock( &_MutexWait ) ) {
1016     perror("pthread_mutex_lock _SuspendThread") ;
1017     exit( 0 ) ;
1018   }
1019   _SuspendedThreads += 1 ;
1020   cdebug << "SuspendThread : " << _Threads << " running threads "
1021          << _SuspendedThreads << " suspended threads"
1022          << endl ;
1023   if ( pthread_mutex_unlock( &_MutexWait ) ) {
1024     perror("pthread_mutex_unlock _SuspendThread") ;
1025     exit( 0 ) ;
1026   }
1027   if ( IsSuspended() ) {
1028     PushEvent( NULL , GraphExecutor::SuspendEvent , GraphExecutor::SuspendedState ) ;
1029   }
1030 }
1031 void GraphExecutor::OutNode::ResumeThread() {
1032   if ( pthread_mutex_lock( &_MutexWait ) ) {
1033     perror("pthread_mutex_lock _ResumeThread") ;
1034     exit( 0 ) ;
1035   }
1036   _SuspendedThreads -= 1 ;
1037   cdebug << "ResumeThread : " << _Threads << " running threads "
1038          << _SuspendedThreads << " suspended threads"
1039          << endl ;
1040   if ( pthread_mutex_unlock( &_MutexWait ) ) {
1041     perror("pthread_mutex_unlock _ResumeThread") ;
1042     exit( 0 ) ;
1043   }
1044 }
1045
1046 long GraphExecutor::OutNode::Thread( const char * aNodeName ) {
1047   long RetVal = 0 ;
1048   GraphExecutor::InNode *anInNode = (GraphExecutor::InNode *) Graph()->GetGraphNode( aNodeName )->GetInNode() ;
1049   if ( anInNode ) {
1050     RetVal = anInNode->ThreadNo() ;
1051   }
1052   return RetVal ;
1053 }
1054
1055 SUPERV::GraphEvent GraphExecutor::OutNode::AutomatonGraphEvent(GraphExecutor::NodeEvent anEvent ) {
1056   SUPERV::GraphEvent aGraphEvent ;
1057   switch ( anEvent ) {
1058   case GraphExecutor::UndefinedEvent : {
1059     aGraphEvent = SUPERV::UndefinedEvent ;
1060     break ;
1061   }
1062   case GraphExecutor::NewThreadEvent : {
1063     aGraphEvent = SUPERV::NewThreadEvent ;
1064     break ;
1065   }
1066   case GraphExecutor::SuspendEvent : {
1067     aGraphEvent = SUPERV::SuspendEvent ;
1068     break ;
1069   }
1070   case GraphExecutor::ResumeEvent : {
1071     aGraphEvent = SUPERV::ResumeEvent ;
1072     break ;
1073   }
1074   case GraphExecutor::KillEvent : {
1075     aGraphEvent = SUPERV::KillEvent ;
1076     break ;
1077   }
1078   case GraphExecutor::StopEvent : {
1079     aGraphEvent = SUPERV::StopEvent ;
1080     break ;
1081   }
1082   case GraphExecutor::ExecuteEvent : {
1083     aGraphEvent = SUPERV::RunningEvent ;
1084     break ;
1085   }
1086   case GraphExecutor::SuccessEvent : {
1087     aGraphEvent = SUPERV::DoneEvent ;
1088     break ;
1089   }
1090   case GraphExecutor::ErrorEvent : {
1091     aGraphEvent = SUPERV::ErroredEvent ;
1092     break ;
1093   }
1094   case GraphExecutor::NoDataReadyEvent : {
1095     aGraphEvent = SUPERV::WaitingEvent ;
1096     break ;
1097   }
1098   case GraphExecutor::SomeDataReadyEvent : {
1099     aGraphEvent = SUPERV::WaitingEvent ;
1100     break ;
1101   }
1102   case GraphExecutor::NotAllDataReadyEvent : {
1103     aGraphEvent = SUPERV::WaitingEvent ;
1104     break ;
1105   }
1106   case GraphExecutor::AllDataReadyEvent : {
1107     aGraphEvent = SUPERV::ReadyEvent ;
1108     break ;
1109   }
1110   case GraphExecutor::ReadyEvent : {
1111     aGraphEvent = SUPERV::ReadyEvent ;
1112     break ;
1113   }
1114   case GraphExecutor::SuspendedReadyEvent : {
1115     aGraphEvent = SUPERV::SuspendEvent ;
1116     break ;
1117   }
1118   case GraphExecutor::ResumedReadyEvent : {
1119     aGraphEvent = SUPERV::ResumeEvent ;
1120     break ;
1121   }
1122   case GraphExecutor::KilledReadyEvent : {
1123     aGraphEvent = SUPERV::KillEvent ;
1124     break ;
1125   }
1126   case GraphExecutor::StoppedReadyEvent : {
1127     aGraphEvent = SUPERV::StopEvent ;
1128     break ;
1129   }
1130   case GraphExecutor::ExecutingEvent : {
1131     aGraphEvent = SUPERV::RunningEvent ;
1132     break ;
1133   }
1134   case GraphExecutor::SuspendedExecutingEvent : {
1135     aGraphEvent = SUPERV::SuspendEvent ;
1136     break ;
1137   }
1138   case GraphExecutor::ResumedExecutingEvent : {
1139     aGraphEvent = SUPERV::ResumeEvent ;
1140     break ;
1141   }
1142   case GraphExecutor::KilledExecutingEvent : {
1143     aGraphEvent = SUPERV::KillEvent ;
1144     break ;
1145   }
1146   case GraphExecutor::StoppedExecutingEvent : {
1147     aGraphEvent = SUPERV::StopEvent ;
1148     break ;
1149   }
1150   case GraphExecutor::SuccessedExecutingEvent : {
1151     aGraphEvent = SUPERV::DoneEvent ;
1152     break ;
1153   }
1154   case GraphExecutor::ErroredExecutingEvent : {
1155     aGraphEvent = SUPERV:: ErroredEvent;
1156     break ;
1157   }
1158   case GraphExecutor::SuspendedSuccessedEvent : {
1159     aGraphEvent = SUPERV::SuspendEvent ;
1160     break ;
1161   }
1162   case GraphExecutor::SuspendedErroredEvent : {
1163     aGraphEvent = SUPERV::SuspendEvent ;
1164     break ;
1165   }
1166   case GraphExecutor::ResumedSuccessedEvent : {
1167     aGraphEvent = SUPERV::ResumeEvent ;
1168     break ;
1169   }
1170   case GraphExecutor::ResumedErroredEvent : {
1171     aGraphEvent = SUPERV::ResumeEvent ;
1172     break ;
1173   }
1174   case GraphExecutor::KilledEvent : {
1175     aGraphEvent = SUPERV::KillEvent ;
1176     break ;
1177   }
1178   case GraphExecutor::StoppedEvent : {
1179     aGraphEvent = SUPERV::StopEvent ;
1180     break ;
1181   }
1182   case GraphExecutor::EndExecuteEvent : {
1183     aGraphEvent = SUPERV::DoneEvent ;
1184     break ;
1185   }
1186   default : {
1187     cdebug << " GraphExecutor::OutNode::AutomatonGraphEvent Error Undefined Event : "
1188            << anEvent << endl ;
1189     aGraphEvent = SUPERV::UndefinedEvent ;
1190   }
1191   }
1192   return aGraphEvent ;
1193 }
1194
1195 SUPERV::GraphState GraphExecutor::OutNode::AutomatonGraphState(GraphExecutor::AutomatonState aState ) {
1196   SUPERV::GraphState aGraphState ;
1197   switch ( aState ) {
1198   case GraphExecutor::UnKnownState : {
1199     aGraphState = SUPERV::UndefinedState ;
1200     break ;
1201   }
1202   case GraphExecutor::DataUndefState : {
1203     aGraphState = SUPERV::UndefinedState ;
1204     break ;
1205   }
1206   case GraphExecutor::DataWaitingState : {
1207     aGraphState = SUPERV::WaitingState ;
1208     break ;
1209   }
1210   case GraphExecutor::DataReadyState : {
1211     aGraphState = SUPERV::ReadyState ;
1212     break ;
1213   }
1214   case GraphExecutor::SuspendedReadyState : {
1215     aGraphState = SUPERV::SuspendReadyState ;
1216     break ;
1217   }
1218   case GraphExecutor::ResumedReadyState : {
1219     aGraphState = SUPERV::ReadyState ;
1220     break ;
1221   }
1222   case GraphExecutor::KilledReadyState : {
1223     aGraphState = SUPERV::KillState ;
1224     break ;
1225   }
1226   case GraphExecutor::StoppedReadyState : {
1227     aGraphState = SUPERV::StopState ;
1228     break ;
1229   }
1230   case GraphExecutor::ExecutingState : {
1231     aGraphState = SUPERV::RunningState ;
1232     break ;
1233   }
1234   case GraphExecutor::SuspendedExecutingState : {
1235     aGraphState = SUPERV::SuspendState ;
1236     break ;
1237   }
1238   case GraphExecutor::ResumedExecutingState : {
1239     aGraphState = SUPERV::RunningState ;
1240     break ;
1241   }
1242   case GraphExecutor::KilledExecutingState : {
1243     aGraphState = SUPERV::KillState ;
1244     break ;
1245   }
1246   case GraphExecutor::StoppedExecutingState : {
1247     aGraphState = SUPERV::StopState ;
1248     break ;
1249   }
1250   case GraphExecutor::SuccessedExecutingState : {
1251     aGraphState = SUPERV::DoneState ;
1252     break ;
1253   }
1254   case GraphExecutor::ErroredExecutingState : {
1255     aGraphState = SUPERV::ErrorState ;
1256     break ;
1257   }
1258   case GraphExecutor::SuspendedSuccessedState : {
1259     aGraphState = SUPERV::SuspendDoneState ;
1260     break ;
1261   }
1262   case GraphExecutor::SuspendedErroredState : {
1263     aGraphState = SUPERV::SuspendErroredState ;
1264     break ;
1265   }
1266   case GraphExecutor::ResumedSuccessedState : {
1267     aGraphState = SUPERV::DoneState ;
1268     break ;
1269   }
1270   case GraphExecutor::ResumedErroredState : {
1271     aGraphState = SUPERV::ErrorState ;
1272     break ;
1273   }
1274   case GraphExecutor::KilledSuccessedState : {
1275     aGraphState = SUPERV::KillState ;
1276     break ;
1277   }
1278   case GraphExecutor::KilledErroredState : {
1279     aGraphState = SUPERV::KillState ;
1280     break ;
1281   }
1282   case GraphExecutor::StoppedSuccessedState : {
1283     aGraphState = SUPERV::StopState ;
1284     break ;
1285   }
1286   case GraphExecutor::StoppedErroredState : {
1287     aGraphState = SUPERV::StopState ;
1288     break ;
1289   }
1290   case GraphExecutor::SuccessedState : {
1291     aGraphState = SUPERV::DoneState ;
1292     break ;
1293   }
1294   case GraphExecutor::ErroredState : {
1295     aGraphState = SUPERV::ErrorState ;
1296     break ;
1297   }
1298   case GraphExecutor::SuspendedState : {
1299     aGraphState = SUPERV::SuspendState ;
1300     break ;
1301   }
1302   case GraphExecutor::KilledState : {
1303     aGraphState = SUPERV::KillState ;
1304     break ;
1305   }
1306   case GraphExecutor::StoppedState : {
1307     aGraphState = SUPERV::StopState ;
1308     break ;
1309   }
1310   case GraphExecutor::LoadingState : {
1311     aGraphState = SUPERV::LoadingState ;
1312     break;
1313   }
1314   default : {
1315     cdebug << " GraphExecutor::OutNode::AutomatonGraphState Error Undefined State : "
1316            << aGraphState << endl ;
1317     aGraphState = SUPERV::UndefinedState ;
1318   }
1319   }
1320   return aGraphState ;
1321 }
1322
1323 //JR 07.04.2005, Debug :  access to _EventNodes must be inside the pthread_mutex_lock
1324 int GraphExecutor::OutNode::GetListSize() {
1325   if ( pthread_mutex_lock( &_MutexWait ) ) {
1326     perror("PushEvent pthread_mutex_lock ") ;
1327     exit( 0 ) ;
1328   }
1329   int eventnbr = _EventNodes.size();
1330   if ( pthread_mutex_unlock( &_MutexWait ) ) {
1331     perror("PushEvent pthread_mutex_unlock ") ;
1332     exit( 0 ) ;
1333   }
1334   return eventnbr ;
1335 }
1336
1337 bool GraphExecutor::OutNode::PushEvent( GraphExecutor::InNode * aNode ,
1338                                         GraphExecutor::NodeEvent anEvent ,
1339                                         GraphExecutor::AutomatonState aState ) {
1340 //  cdebug_in << "PushEvent Threads " << Threads() << " SuspendedThreads "
1341 //            << SuspendedThreads() << endl ;
1342   if ( pthread_mutex_lock( &_MutexWait ) ) {
1343     perror("PushEvent pthread_mutex_lock ") ;
1344     exit( 0 ) ;
1345   }
1346   char* aNodeName = aNode ? aNode->Name() : Name() ;
1347   _EventNodes.push_back( aNodeName ) ;
1348   _Events.push_back( anEvent ) ;
1349   _States.push_back( aState ) ;
1350
1351   pthread_cond_broadcast( &_EventWait );
1352 //  cdebug << pthread_self() << " PushEvent Threads " << Threads() << " SuspendedThreads "
1353 //         << SuspendedThreads() << " pthread_cond_broadcast _EventWait " << &_EventWait << endl ;
1354   if ( aNode ) {
1355 //    cdebug << aNode->ThreadNo() << " PushEvent " << aNode->Name() ;
1356 //    cdebug << " " << aNode->Automaton()->EventName( anEvent )
1357 //           << " " << aNode->Automaton()->StateName( aState )
1358 //           << " ControleState "
1359 //           << aNode->Automaton()->ControlStateName( aNode->ControlState() ) ;
1360   }
1361   else {
1362 //    cdebug << "PushEvent " << Name() ;
1363 //    cdebug << " " << theAutomaton->EventName( anEvent ) << " "
1364 //           << theAutomaton->StateName( aState ) ;
1365   }
1366 //  cdebug_out << "PushEvent Threads " << Threads() << " SuspendedThreads "
1367 //             << SuspendedThreads() << endl ;
1368
1369 //PAL8520
1370 //JR 21.02.2005 Debug : old events should be removed at creation time for python-clients
1371   int EventNodesSize = _EventNodes.size() ;
1372   if ( EventNodesSize > Graph()->GraphNodesSize()*70 ) {
1373     siftEvents();
1374 //    cdebug << "OutNode::PushEvent " << _EventNodes.size() << " in queue instead of "
1375 //           << EventNodesSize << endl ;
1376   }
1377
1378   if ( pthread_mutex_unlock( &_MutexWait ) ) {
1379     perror("PushEvent pthread_mutex_unlock ") ;
1380     exit( 0 ) ;
1381   }
1382   return true ;
1383 }
1384
1385 bool GraphExecutor::OutNode::StateWait( SUPERV::GraphState aState ) {
1386   return false ;
1387 }
1388
1389 bool GraphExecutor::OutNode::Event( char ** aNodeName ,
1390                                     SUPERV::GraphEvent & anEvent ,
1391                                     SUPERV::GraphState & aState ,
1392                                     bool WithWait ) {
1393 //PAL8520
1394 //JR 23.02.2005, Debug : siftEvents() must be inside the pthread_mutex_lock
1395   if ( pthread_mutex_lock( &_MutexWait ) ) {
1396     perror("EventLoop pthread_mutex_lock ") ;
1397     exit( 0 ) ;
1398   }
1399   // asv : fixing problem of loops with large number of iterations (>5000)
1400   // experimentally was found that number of non-handled by GUI events = (number_of_nodes x 7)
1401   // or 7 events for each node - so what we want to do here is remove "old" events for nodes
1402   // "on the fly".  Once again it is done in Stop(), Kill(), Done() functions.
1403   int EventNodessize = _EventNodes.size() ;
1404   if ( EventNodessize > Graph()->GraphNodesSize()*7 )
1405     siftEvents();
1406
1407   int ThreadsNumber ;
1408   int SuspendedThreadsNumber ;
1409   bool cdebuginout = false ;
1410   if ( _EventNodes.size() > 0 ) {
1411 //    cdebug_in << "GraphExecutor::OutNode::Event " << _EventNodes.size() << " in queue instead of "
1412 //              << EventNodessize << endl ;
1413     cdebuginout = true ;
1414   }
1415   _JustStarted = false ;
1416   ThreadsNumber = Threads() ;
1417   SuspendedThreadsNumber = SuspendedThreads() ;
1418   bool RetVal = ( ThreadsNumber - SuspendedThreadsNumber) != 0 ||
1419                 _EventNodes.size() > 0 ;
1420   char * NodeName = "" ;
1421   GraphExecutor::NodeEvent theEvent = GraphExecutor::UndefinedEvent ;
1422   GraphExecutor::AutomatonState theState = GraphExecutor::UnKnownState ;
1423   anEvent = SUPERV::UndefinedEvent ;
1424   aState = SUPERV::UndefinedState ;
1425   if ( ( Done() || IsKilled() || IsStopped() ) && _EventNodes.size() == 0 ) {
1426 //    cdebug << "EventLoop Done()/IsKilled()/IsStopped() && _EventNodes.size() == 0" << endl ;
1427     RetVal = false ;
1428   }
1429   else if ( !WithWait && _EventNodes.size() == 0 ) {
1430     anEvent = SUPERV::NoEvent ;
1431     aState = SUPERV::NoState ;
1432     RetVal = true ;
1433   }
1434   else if ( RetVal ) {
1435     while ( !IsSuspended() && _EventNodes.size() == 0 ) {
1436 //      cdebug << "EventLoop pthread_cond_wait _EventWait" << endl ;
1437       pthread_cond_wait( &_EventWait , &_MutexWait );
1438 //      cdebug << "EventLoop pthread_cond_waited _EventWait"
1439 //             << " _EventNodes.size() " << _EventNodes.size() << endl ;
1440     }
1441     if ( _EventNodes.size() ) {
1442       ThreadsNumber = Threads() ;
1443       NodeName = _EventNodes.front() ;
1444       _EventNodes.pop_front() ;
1445       theEvent = _Events.front() ;
1446       anEvent = AutomatonGraphEvent( theEvent ) ;
1447       _Events.pop_front() ;
1448       theState = _States.front() ;
1449       aState = AutomatonGraphState( theState ) ;
1450       _States.pop_front() ;
1451     }
1452   }
1453   *aNodeName = NodeName ;
1454   if ( IsSuspended() && _EventNodes.size() == 0 ) {
1455     RetVal = false ;
1456   }
1457   if ( anEvent != SUPERV::NoEvent ) {
1458 //    cdebug << pthread_self() << "EventLoop "
1459 //           << NodeName << " " << theAutomaton->StateName( theState )
1460 //           << " _EventNodes.size() " << _EventNodes.size()
1461 //           << " Threads " << Threads() << " SuspendedThreads "
1462 //           << SuspendedThreads() << " RetVal " << RetVal << endl ;
1463   }
1464   if ( pthread_mutex_unlock( &_MutexWait ) ) {
1465     perror("EventLoop pthread_mutex_lock ") ;
1466     exit( 0 ) ;
1467   }
1468   if ( cdebuginout ) {
1469 //    cdebug_out << "GraphExecutor::OutNode::Event " << _EventNodes.size() << " in queue"
1470 //               << *aNodeName << " " << anEvent << " " << aState << endl ;
1471   }
1472   return RetVal ;
1473 }
1474
1475 bool GraphExecutor::OutNode::EventW( char ** aNodeName ,
1476                                      SUPERV::GraphEvent & anEvent ,
1477                                      SUPERV::GraphState & aState ) {
1478   bool sts = true ;
1479   char * NodeName ;
1480   aState = SUPERV::UndefinedState ;
1481   while ( sts &&
1482           aState != SUPERV::SuspendReadyState &&
1483           aState != SUPERV::RunningState &&
1484           aState != SUPERV::SuspendDoneState &&
1485           aState != SUPERV::SuspendErroredState ) {
1486     NodeName = Name() ;
1487     while ( sts && !strcmp( NodeName , Name() ) ) {
1488       sts = EventWait( aNodeName , anEvent , aState ) ;
1489       NodeName = *aNodeName ;
1490     }
1491   }
1492   return sts ;
1493 }
1494
1495 bool GraphExecutor::OutNode::EventWait( char ** aNodeName ,
1496                                         SUPERV::GraphEvent & anEvent ,
1497                                         SUPERV::GraphState & aState ) {
1498   if ( pthread_mutex_lock( &_MutexWait ) ) {
1499     perror("EventW pthread_mutex_lock ") ;
1500     exit( 0 ) ;
1501   }
1502   int ThreadsNumber ;
1503   int SuspendedThreadsNumber ;
1504   ThreadsNumber = Threads() ;
1505   SuspendedThreadsNumber = SuspendedThreads() ;
1506   bool RetVal = ( ThreadsNumber - SuspendedThreadsNumber) != 0 ||
1507                 _EventNodes.size() > 0 ;
1508   cdebug << "--> EventW RetVal " << RetVal << endl ;
1509   char * NodeName = "" ;
1510   GraphExecutor::NodeEvent theEvent = GraphExecutor::UndefinedEvent ;
1511   GraphExecutor::AutomatonState theState = GraphExecutor::UnKnownState ;
1512   anEvent = SUPERV::UndefinedEvent ;
1513   aState = SUPERV::UndefinedState ;
1514   if ( IsDone() && _EventNodes.size() == 0 ) {
1515     cdebug << "EventW IsDone() && _EventNodes.size() == 0" << endl ;
1516     RetVal = 0 ;
1517   }
1518   else if ( RetVal ) {
1519     GraphExecutor::InNode * aNode = NULL ;
1520     while ( aNode == NULL && RetVal ) {
1521       NodeName = _EventNodes.front() ;
1522       theEvent = _Events.front() ;
1523       anEvent = AutomatonGraphEvent( theEvent ) ;
1524       theState = _States.front() ;
1525       aState = AutomatonGraphState( theState ) ;
1526
1527       if ( _JustStarted ) {
1528         _JustStarted = false ;
1529       }
1530       else {
1531         _EventNodes.pop_front() ;
1532         _Events.pop_front() ;
1533         _States.pop_front() ;
1534       }
1535
1536       aNode = ((GraphExecutor::InNode *) Graph()->GetGraphNode( NodeName )->GetInNode()) ;
1537       cdebug << "EventW Previous Node " << NodeName << " ThreadsNumber "
1538              << ThreadsNumber
1539              << " _EventNodes.size() " << _EventNodes.size() << " "
1540              << theAutomaton->StateName( theState )
1541              << " Threads " << Threads() << " SuspendedThreads "
1542              << SuspendedThreads() << endl ;
1543       if ( aNode ) {
1544       }
1545       else if ( IsDone() && _EventNodes.size() == 0 ) {
1546         cdebug << "EventW IsDone() && _EventNodes.size() == 0" << endl ;
1547         RetVal = 0 ;
1548       }
1549       else {
1550         cdebug << "EventW Not InNode " << NodeName
1551                << " _EventNodes.size() " << _EventNodes.size() << endl ;
1552         while ( _EventNodes.size() == 0 ) {
1553           pthread_cond_wait( &_EventWait , &_MutexWait );
1554         }
1555         cdebug << "EventW pthread_cond_waited Not InNode " << NodeName
1556                << " _EventNodes.size() " << _EventNodes.size() << endl ;
1557       }
1558     }
1559
1560     if ( aNode ) {
1561       if ( aState == SUPERV::SuspendState ||
1562            aState == SUPERV::SuspendReadyState ||
1563            aState == SUPERV::SuspendDoneState ||
1564            aState == SUPERV::SuspendErroredState ) {
1565         aNode->ControlState( SUPERV::ToSuspendState ) ;
1566         if ( aNode->IsSuspended() ) {
1567           if ( pthread_mutex_unlock( &_MutexWait ) ) {
1568             perror("EventW pthread_mutex_lock ") ;
1569             exit( 0 ) ;
1570           }
1571           cdebug << "EventW " << aNode->Name() << " ResumeAction" << endl ;
1572           aNode->ResumeAction( GraphExecutor::ToResumeEvent ) ;
1573           cdebug << "EventW " << aNode->Name() << " ResumedAction" << endl ;
1574           if ( pthread_mutex_lock( &_MutexWait ) ) {
1575             perror("EventW pthread_mutex_lock ") ;
1576             exit( 0 ) ;
1577           }
1578         }
1579         else {
1580           cdebug << "EventW inconsistent SuspendState" << endl ;
1581           RetVal = false ; 
1582         }
1583       }
1584       else {
1585         if ( aNode->IsDone() ) {
1586           RetVal = true ;
1587         }
1588         else {
1589           cdebug << "EventW NOT SuspendedState _EventNodes.size() "
1590                  << _EventNodes.size() << endl ;
1591           RetVal = true ;
1592         }
1593       }
1594       if ( RetVal ) {
1595         cdebug << "EventW " << aNode->Name() << " pthread_cond_wait" << endl ;
1596         while ( _EventNodes.size() == 0 ) {
1597           pthread_cond_wait( &_EventWait , &_MutexWait );
1598         }
1599         ThreadsNumber = Threads() ;
1600         NodeName = _EventNodes.front() ;
1601         theEvent = _Events.front() ;
1602         anEvent = AutomatonGraphEvent( theEvent ) ;
1603         theState = _States.front() ;
1604         aState = AutomatonGraphState( theState ) ;
1605       }
1606     }
1607   }
1608   *aNodeName = NodeName ;
1609   cdebug << "<-- EventW RetVal " << RetVal << " " << NodeName
1610          << " Threads " << Threads() << " SuspendedThreads "
1611          << SuspendedThreads()
1612          << " _EventNodes.size() " << _EventNodes.size()
1613          << " " << theAutomaton->EventName( theEvent ) << " "
1614          << theAutomaton->StateName( theState ) << endl ;
1615   if ( pthread_mutex_unlock( &_MutexWait ) ) {
1616     perror("EventW pthread_mutex_lock ") ;
1617     exit( 0 ) ;
1618   }
1619   return RetVal ;
1620 }
1621 long GraphExecutor::OutNode::EventQSize() {
1622   return _EventNodes.size() ;
1623 }
1624
1625 void GraphExecutor::OutNode::EventList() {
1626   if ( pthread_mutex_lock( &_MutexWait ) ) {
1627     perror("EventList pthread_mutex_lock ") ;
1628     exit( 0 ) ;
1629   }
1630   list< char * >::iterator itEventNodes = _EventNodes.begin() ;
1631   list< GraphExecutor::NodeEvent >::iterator itEvents = _Events.begin() ;
1632   list< GraphExecutor::AutomatonState >::iterator itStates = _States.begin() ;
1633   while ( itEventNodes != _EventNodes.end() ) {
1634     cdebug << pthread_self() << "EVENTSTACK "
1635            << *itEventNodes << " " << *itEvents << " "
1636            << theAutomaton->StateName( *itStates )
1637            << " Threads " << Threads() << " SuspendedThreads " << SuspendedThreads() << endl ;
1638     itEventNodes++ ;
1639     itEvents++ ;
1640     itStates++ ;
1641   }
1642   if ( pthread_mutex_unlock( &_MutexWait ) ) {
1643     perror("EventList pthread_mutex_lock ") ;
1644     exit( 0 ) ;
1645   }
1646 }
1647
1648 void GraphExecutor::OutNode::SendSomeDataReady( const char * aNodeName ) {
1649   cdebug_in << "GraphExecutor::OutNode::SendSomeDataReady " << aNodeName << "->SendSomeDataReady( "
1650             << Name() << " )" << endl;
1651   int sts ;
1652   sts = ((GraphExecutor::InNode * ) Graph()->GetChangeGraphNode( aNodeName )->GetInNode())->SendSomeDataReady( Name() ) ;
1653   cdebug_out << "GraphExecutor::OutNode::SendSomeDataReady sts " << sts << endl ;
1654 }
1655
1656 void GraphExecutor::OutNode::State(GraphExecutor::AutomatonState aState ) {
1657 //  cdebug << "GraphExecutor::OutNode::State " << Name() << " "
1658 //         << theAutomaton->StateName( AutomatonGraphState( _State ) ) << " ---> "
1659 //         << theAutomaton->StateName( AutomatonGraphState( aState ) ) << endl ;
1660   _State = aState ;
1661 }
1662
1663 SUPERV::GraphState GraphExecutor::OutNode::State() {
1664 //  cdebug_in << "GraphExecutor::OutNode::State" << endl;
1665 //  cdebug_out << "GraphExecutor::OutNode::State" << endl ;
1666 //  cdebug << "GraphExecutor::OutNode::State GraphState "
1667 //         << theAutomaton->StateName( AutomatonGraphState( _State ) ) << endl ;
1668   return AutomatonGraphState( _State ) ;
1669 }
1670
1671 SUPERV::GraphState GraphExecutor::OutNode::State( const char * NodeName ) {
1672 //  cdebug_in << "GraphExecutor::OutNode::State " << NodeName << endl;
1673   GraphExecutor::AutomatonState aret = GraphExecutor::UnKnownState ;
1674   const GraphBase::ComputingNode * aCNode =  Graph()->GetGraphNode( NodeName ) ;
1675   if ( aCNode ) {
1676     GraphExecutor::InNode *anInNode = (GraphExecutor::InNode *)aCNode->GetInNode() ;
1677     if ( anInNode ) {
1678       aret = anInNode->State() ;
1679       // asv 27.01.05 - fix for PAL7849, return "Loading" state only if internal state is SUPERV::RunningState
1680       if ( ( aret == GraphExecutor::ExecutingState || 
1681              aret == GraphExecutor::ResumedExecutingState ) && 
1682           anInNode->IsLoading() )
1683         aret = GraphExecutor::LoadingState;
1684 //      cdebug << "GraphExecutor::OutNode::State( " << NodeName << " ) "
1685 //             << theAutomaton->StateName( AutomatonGraphState( aret ) ) << endl ;
1686     }
1687   }
1688 //  cdebug_out << "GraphExecutor::OutNode::State" << endl ;
1689   return AutomatonGraphState( aret ) ;
1690 }
1691
1692 SUPERV::GraphState GraphExecutor::OutNode::State( const char * NodeName ,
1693                                                   const char * ServiceParameterName )  {
1694 //  cdebug_in << "GraphExecutor::OutNode::State " << NodeName << " "
1695 //            << ServiceParameterName<< endl;
1696   SUPERV::GraphState aret = Graph()->PortState( NodeName , ServiceParameterName ) ;
1697 //  cdebug_out << "GraphExecutor::OutNode::State" << endl ;
1698   return aret ;
1699 }
1700
1701 GraphExecutor::AutomatonState GraphExecutor::OutNode::AutomatonState() {
1702 //  cdebug_in << "GraphExecutor::OutNode::AutomatonState" << endl;
1703 //  cdebug_out << "GraphExecutor::OutNode::AutomatonState" << endl ;
1704   return _State ;
1705 }
1706
1707 GraphExecutor::AutomatonState GraphExecutor::OutNode::AutomatonState( const char * NodeName ) {
1708 //  cdebug_in << "GraphExecutor::OutNode::AutomatonState " << NodeName << endl;
1709   GraphExecutor::AutomatonState aret = GraphExecutor::UnKnownState ;
1710   const GraphBase::ComputingNode * aNode = Graph()->GetGraphNode( NodeName ) ;
1711   if ( aNode ) {
1712     GraphExecutor::InNode *anInNode = (GraphExecutor::InNode *) aNode->GetInNode() ;
1713     if ( anInNode ) {
1714       aret = anInNode->State() ;
1715     }
1716   }
1717 //  cdebug_out << "GraphExecutor::OutNode::AutomatonState" << endl ;
1718   return aret ;
1719 }
1720
1721 SUPERV::ControlState GraphExecutor::OutNode::ControlState() {
1722 //  cdebug_in << "GraphExecutor::OutNode::ControlState" << endl;
1723 //  cdebug_out << "GraphExecutor::OutNode::ControlState" << endl ;
1724   return _ControlState ;
1725 }
1726
1727 SUPERV::ControlState GraphExecutor::OutNode::ControlState( const char * NodeName ) {
1728 //  cdebug_in << "GraphExecutor::OutNode::ControlState " << NodeName << endl;
1729   SUPERV::ControlState aret = SUPERV::VoidState ;
1730   const GraphBase::ComputingNode * aNode = Graph()->GetGraphNode( NodeName ) ;
1731   if ( aNode ) {
1732     GraphExecutor::InNode *anInNode = (GraphExecutor::InNode *) aNode->GetInNode() ;
1733     if ( anInNode ) {
1734       aret = anInNode->ControlState() ;
1735     }
1736   }
1737 //  cdebug_out << "GraphExecutor::OutNode::ControlState" << endl ;
1738   return aret ;
1739 }
1740
1741 void GraphExecutor::OutNode::ControlClear() {
1742 //  cdebug_in << "GraphExecutor::OutNode::ControlClear" << endl;
1743 //  cdebug_out << "GraphExecutor::OutNode::ControlClear" << endl ;
1744   _ControlState = SUPERV::VoidState;
1745 }
1746
1747 void GraphExecutor::OutNode::ControlClear( const char * NodeName ) {
1748 //  cdebug_in << "GraphExecutor::OutNode::ControlClear " << NodeName << endl;
1749   const GraphBase::ComputingNode * aNode = Graph()->GetGraphNode( NodeName ) ;
1750   if ( aNode ) {
1751     GraphExecutor::InNode *anInNode = (GraphExecutor::InNode *) aNode->GetInNode() ;
1752     if ( anInNode ) {
1753       anInNode->ControlClear() ;
1754     }
1755   }
1756 //  cdebug_out << "GraphExecutor::OutNode::ControlClear" << endl ;
1757 }
1758
1759 bool GraphExecutor::OutNode::IsWaiting() {
1760 //  cdebug_in << "GraphExecutor::OutNode::IsWaiting" << endl;
1761 //  cdebug_out << "GraphExecutor::OutNode::IsWaiting" << endl ;
1762   return !IsDone() ;
1763 }
1764
1765 bool GraphExecutor::OutNode::IsReady() {
1766 //  cdebug_in << "GraphExecutor::OutNode::IsReady" << endl;
1767 //  cdebug_out << "GraphExecutor::OutNode::IsReady" << endl ;
1768   return !IsDone() ;
1769 }
1770
1771 bool GraphExecutor::OutNode::IsRunning() {
1772 //  cdebug_in << "GraphExecutor::OutNode::IsRunning" << endl;
1773 //  cdebug_out << "GraphExecutor::OutNode::IsRunning" << endl ;
1774   return !IsDone() ;
1775 }
1776
1777 bool GraphExecutor::OutNode::IsDone() {
1778 //  cdebug_in << "GraphExecutor::OutNode::IsDone" << endl;
1779 //  cdebug_out << "GraphExecutor::OutNode::IsDone" << endl ;
1780   return ( Done() || IsKilled() || IsStopped() ) ;
1781 }
1782
1783 bool GraphExecutor::OutNode::IsSuspended() {
1784 //  cdebug_in << "GraphExecutor::OutNode::IsSuspended" << endl;
1785   bool aret = false ;
1786 //  if ( _SuspendedThreads == _Threads && _Threads != 0 ) {
1787   if ( AutomatonGraphState( _State ) ==  SUPERV::SuspendState ) {
1788     aret = true ;
1789   }
1790 //  cdebug_out << "GraphExecutor::OutNode::IsSuspended" << endl ;
1791   return aret ;
1792 }
1793
1794 bool GraphExecutor::OutNode::IsKilled() {
1795 //  cdebug_in << "GraphExecutor::OutNode::IsKilled" << endl;
1796   bool aret = false ;
1797   if ( AutomatonGraphState( _State ) == SUPERV::KillState ) {
1798     aret = true ;
1799   }
1800 //  cdebug_out << "GraphExecutor::OutNode::IsKilled" << endl ;
1801   return aret ;
1802 }
1803
1804 bool GraphExecutor::OutNode::IsStopped() {
1805 //  cdebug_in << "GraphExecutor::OutNode::IsStopped" << endl;
1806   bool aret = false ;
1807   if ( AutomatonGraphState( _State ) == SUPERV::StopState ) {
1808     aret = true ;
1809   }
1810 //  cdebug_out << "GraphExecutor::OutNode::IsStopped" << endl ;
1811   return aret ;
1812 }
1813
1814 bool GraphExecutor::OutNode::IsWaiting( const char * NodeName ) {
1815   bool aret = false ;
1816 //  cdebug_in << "GraphExecutor::OutNode::IsWaiting " << NodeName << endl;
1817   GraphExecutor::InNode *anInNode = (GraphExecutor::InNode *) Graph()->GetGraphNode( NodeName )->GetInNode() ;
1818   if ( anInNode ) {
1819     aret = anInNode->IsWaiting() ;
1820   }
1821 //  cdebug_out << "GraphExecutor::OutNode::IsWaiting" << endl ;
1822   return aret ;
1823 }
1824
1825 bool GraphExecutor::OutNode::IsReady( const char * NodeName ) {
1826   bool aret = false ;
1827 //  cdebug_in << "GraphExecutor::OutNode::IsReady " << NodeName << endl;
1828   GraphExecutor::InNode *anInNode = (GraphExecutor::InNode *) Graph()->GetGraphNode( NodeName )->GetInNode() ;
1829   if ( anInNode ) {
1830     aret = anInNode->IsReady() ;
1831   }
1832 //  cdebug_out << "GraphExecutor::OutNode::IsReady" << endl ;
1833   return aret ;
1834 }
1835
1836 bool GraphExecutor::OutNode::IsRunning( const char * NodeName ) {
1837   bool aret = false ;
1838 //  cdebug_in << "GraphExecutor::OutNode::IsRunning " << NodeName << endl;
1839   GraphExecutor::InNode *anInNode = (GraphExecutor::InNode *) Graph()->GetGraphNode( NodeName )->GetInNode() ;
1840   if ( anInNode ) {
1841     aret = anInNode->IsRunning() ;
1842   }
1843 //  cdebug_out << "GraphExecutor::OutNode::IsRunning" << endl ;
1844   return aret ;
1845 }
1846
1847 bool GraphExecutor::OutNode::IsDone( const char * NodeName ) {
1848   bool aret = false ;
1849 //  cdebug_in << "GraphExecutor::OutNode::IsDone " << NodeName << endl;
1850   GraphExecutor::InNode *anInNode = (GraphExecutor::InNode *) Graph()->GetGraphNode( NodeName )->GetInNode() ;
1851   if ( anInNode ) {
1852     aret = anInNode->IsDone() ;
1853   }
1854 //  cdebug_out << "GraphExecutor::OutNode::IsDone" << endl ;
1855   return aret ;
1856 }
1857
1858 bool GraphExecutor::OutNode::IsSuspended( const char * NodeName ) {
1859   bool aret = false ;
1860 //  cdebug_in << "GraphExecutor::OutNode::IsSuspended " << NodeName << endl;
1861   GraphExecutor::InNode *anInNode = (GraphExecutor::InNode *) Graph()->GetGraphNode( NodeName )->GetInNode() ;
1862   if ( anInNode ) {
1863     aret = anInNode->IsSuspended() ;
1864   }
1865 //  cdebug_out << "GraphExecutor::OutNode::IsSuspended" << endl ;
1866   return aret ;
1867 }
1868
1869 bool GraphExecutor::OutNode::PortDone( const char * NodeName ,
1870                                        const char * ServiceParameterName )  {
1871 //  cdebug_in << "GraphExecutor::OutNode::IsDone " << NodeName << " "
1872 //            << ServiceParameterName<< endl;
1873   bool aret = Graph()->PortDone( NodeName , ServiceParameterName ) ;
1874 //  cdebug_out << "GraphExecutor::OutNode::IsDone" << endl ;
1875   return aret ;
1876 }
1877
1878 bool GraphExecutor::OutNode::ContainerKill() {
1879   bool RetVal = true ;
1880   cdebug_in << "GraphExecutor::OutNode::ContainerKill" << endl;
1881   _ControlState = SUPERV::ToSuspendState ;
1882   int i ;
1883   for ( i = 0 ; i < Graph()->GraphNodesSize() ; i++ ) {
1884     GraphExecutor::InNode * aNode = (GraphExecutor::InNode * ) Graph()->GraphNodes( i )->GetInNode() ;
1885     bool sts = aNode->ContainerKill() ;
1886     if ( sts && aNode->IsKilled() ) {
1887       cdebug << aNode->Name() << " killed" << endl ;
1888     }
1889     else if ( aNode->IsWaiting() || aNode->IsDone() ) {
1890       cdebug << aNode->Name() << " not killed : "
1891              << theAutomaton->StateName( aNode->State() ) << endl ;
1892     }
1893     else {
1894       cdebug << aNode->Name() << " cannot be killed : "
1895              << theAutomaton->StateName( aNode->State() ) << endl ;
1896       RetVal = false ;
1897     }
1898   }
1899   if ( !RetVal || Threads() != 0 ) {
1900     for ( i = 0 ; i < Graph()->GraphNodesSize() ; i++ ) {
1901       GraphExecutor::InNode * aNode = (GraphExecutor::InNode * ) Graph()->GraphNodes( i )->GetInNode() ;
1902       if ( !aNode->IsKilled() && !aNode->IsWaiting() && !aNode->IsDone() ) {
1903         aNode->KilledAction() ;
1904       }
1905     }
1906     RetVal = true ;
1907   }
1908   State( GraphExecutor::KilledState ) ;
1909   cdebug_out << "GraphExecutor::OutNode::ContainerKill" << endl ;
1910   return RetVal ;
1911 }
1912
1913 bool GraphExecutor::OutNode::Suspend() {
1914   int RetVal = 0 ;
1915   cdebug_in << "GraphExecutor::OutNode::Suspend" << endl;
1916 //  _ControlState = SUPERV::ToSuspendState ;
1917   int i ;
1918   for ( i = 0 ; i < Graph()->GraphNodesSize() ; i++ ) {
1919     GraphExecutor::InNode * aNode = (GraphExecutor::InNode * ) Graph()->GraphNodes( i )->GetInNode() ;
1920     bool sts = aNode->Suspend() ;
1921     if ( sts && aNode->IsSuspended() ) {
1922       RetVal += 1 ;
1923       cdebug << aNode->Name() << " Suspended" << endl ;
1924     }
1925     else if ( aNode->IsWaiting() || aNode->IsReady() ) {
1926       RetVal += 1 ;
1927       cdebug << aNode->Name() << " will be Suspended" << endl ;
1928     }
1929     else if ( aNode->IsDone() ) {
1930       cdebug << aNode->Name() << " not Suspended : "
1931              << theAutomaton->StateName( aNode->State() ) << endl ;
1932     }
1933     else {
1934 //      RetVal += 1 ;
1935       cdebug << aNode->Name() << " cannot be Suspended : "
1936              << theAutomaton->StateName( aNode->State() ) << endl ;
1937     }
1938   }
1939   if ( RetVal ) {
1940     State( GraphExecutor::SuspendedState ) ;
1941     MESSAGE("================================================================================") ;
1942     MESSAGE( Name() << " IS SUSPENDED" ) ;
1943     MESSAGE("================================================================================") ;
1944   }
1945   else {
1946     MESSAGE("================================================================================") ;
1947     MESSAGE( Name() << " IS NOT SUSPENDED" ) ;
1948     MESSAGE("================================================================================") ;
1949   }
1950   for ( i = 0 ; i < Graph()->GraphNodesSize() ; i++ ) {
1951     GraphExecutor::InNode * aNode = (GraphExecutor::InNode * ) Graph()->GraphNodes( i )->GetInNode() ;
1952     MESSAGE(aNode->Name() << " " << theAutomaton->StateName( aNode->State() ) ) ;
1953     cdebug << aNode->Name() << " " << theAutomaton->StateName( aNode->State() ) << endl ;
1954   }
1955   cdebug_out << "GraphExecutor::OutNode::Suspend " << theAutomaton->StateName( State() )
1956              << " EventQSize " << EventQSize() << endl ;
1957   return RetVal ;
1958 }
1959
1960 bool GraphExecutor::OutNode::Resume() {
1961   int RetVal = 0 ;
1962   cdebug_in << "GraphExecutor::OutNode::Resume "
1963             << theAutomaton->StateName( State() ) << endl;
1964   if ( IsSuspended() ) {
1965     State( GraphExecutor::ExecutingState ) ;
1966     int i ;
1967     for ( i = 0 ; i < Graph()->GraphNodesSize() ; i++ ) {
1968       GraphExecutor::InNode * aNode = (GraphExecutor::InNode * ) Graph()->GraphNodes( i )->GetInNode() ;
1969       aNode->ControlState( SUPERV::VoidState ) ;
1970       if ( aNode->IsSuspended() ) {
1971         cdebug << aNode->Name() << "->Resume " << theAutomaton->StateName( aNode->State() )
1972                << endl ;
1973         if ( aNode->Resume() ) {
1974           cdebug << aNode->Name() << " Resumed " << theAutomaton->StateName( aNode->State() )
1975                  << endl ;
1976           RetVal += 1 ;
1977         }
1978         else {
1979           cdebug << aNode->Name() << " Resume failed"
1980                  << theAutomaton->StateName( aNode->State() ) << endl ;
1981         }
1982       }
1983       else {
1984         cdebug << aNode->Name() << " " << theAutomaton->StateName( aNode->State() )
1985                << endl ;
1986       }
1987     }
1988   }
1989   else {
1990     cdebug << Name() << " not suspended " << theAutomaton->StateName( State() ) << endl ;
1991   }
1992   if ( RetVal ) {
1993     MESSAGE("================================================================================") ;
1994     MESSAGE( Name() << " IS RESUMED" ) ;
1995     MESSAGE("================================================================================") ;
1996   }
1997   else {
1998     MESSAGE("================================================================================") ;
1999     MESSAGE( Name() << " IS NOT RESUMED" ) ;
2000     MESSAGE("================================================================================") ;
2001   }
2002   int i ;
2003   for ( i = 0 ; i < Graph()->GraphNodesSize() ; i++ ) {
2004     GraphExecutor::InNode * aNode = (GraphExecutor::InNode * ) Graph()->GraphNodes( i )->GetInNode() ;
2005     MESSAGE(aNode->Name() << " " << theAutomaton->StateName( aNode->State() ) ) ;
2006     cdebug << aNode->Name() << " " << theAutomaton->StateName( aNode->State() ) << endl ;
2007   }
2008   cdebug_out << "GraphExecutor::OutNode::Resume" << theAutomaton->StateName( State() ) << " " << RetVal
2009              << " EventQSize " << EventQSize() << endl ;
2010   return RetVal ;
2011 }
2012
2013 bool GraphExecutor::OutNode::Kill() {
2014   bool RetVal = false ;
2015   cdebug_in << "GraphExecutor::OutNode::Kill"
2016             << " EventQSize " << EventQSize() << " State "
2017             << theAutomaton->StateName( State() ) << endl;
2018   if ( IsDone() ) {
2019     cdebug_out << "GraphExecutor::OutNode::Kill " << RetVal
2020                << " Threads " << _Threads << " SuspendedThreads " << _SuspendedThreads
2021                << " EventQSize " << EventQSize() << " State "
2022                << theAutomaton->StateName( State() ) << endl ;
2023     return RetVal ;
2024   }
2025   _ControlState = SUPERV::ToSuspendState ;
2026   int i ;
2027   for ( i = 0 ; i < Graph()->GraphNodesSize() ; i++ ) {
2028     GraphExecutor::InNode * aNode = (GraphExecutor::InNode * ) Graph()->GraphNodes( i )->GetInNode() ;
2029     bool sts = aNode->Kill() ;
2030     if ( sts && Threads() != 0 ) {
2031       if ( !aNode->IsKilled() ) {
2032         cdebug << aNode->Name() << " not killed : "
2033                << theAutomaton->StateName( aNode->State() ) << " " << aNode->Name() << "->"
2034                << "KilledAction()" << endl ;
2035         MESSAGE( aNode->Name() << " not killed : KilledAction()" ) ;
2036         aNode->KilledAction() ;
2037       }
2038       if ( aNode->IsKilled() ) {
2039         cdebug << aNode->Name() << " killed" << endl ;
2040         RetVal = true ;
2041       }
2042     }
2043 //PAL8003
2044 // JR 24.03.2005 Debug : the node may have been killed
2045     else if ( aNode->IsKilled() ) {
2046       cdebug << aNode->Name() << " killed" << endl ;
2047       RetVal = true ;
2048     }
2049     else if ( aNode->IsWaiting() || aNode->IsDone() ) {
2050       cdebug << aNode->Name() << " not killed : "
2051              << theAutomaton->StateName( aNode->State() ) << endl ;
2052     }
2053     else {
2054       cdebug << aNode->Name() << " cannot be killed : "
2055              << theAutomaton->StateName( aNode->State() ) << endl ;
2056     }
2057   }
2058   if ( RetVal ) {
2059     State( GraphExecutor::KilledState ) ;
2060     MESSAGE("================================================================================") ;
2061     MESSAGE( Name() << " IS KILLED" <<  theAutomaton->StateName( AutomatonState() ) << " EventQSize "
2062              << EventQSize() ) ;
2063     MESSAGE("================================================================================") ;
2064   }
2065   else {
2066     MESSAGE("================================================================================") ;
2067     MESSAGE( Name() << " IS NOT KILLED" ) ;
2068     MESSAGE("================================================================================") ;
2069   }
2070   for ( i = 0 ; i < Graph()->GraphNodesSize() ; i++ ) {
2071     GraphExecutor::InNode * aNode = (GraphExecutor::InNode * ) Graph()->GraphNodes( i )->GetInNode() ;
2072     MESSAGE(aNode->Name() << " " << theAutomaton->StateName( aNode->State() ) ) ;
2073     cdebug << aNode->Name() << " " << theAutomaton->StateName( aNode->State() ) << endl ;
2074   }
2075
2076   if ( pthread_mutex_lock( &_MutexWait ) ) {
2077     perror("EventLoop pthread_mutex_lock ") ;
2078     exit( 0 ) ;
2079   }
2080 //PAL8520
2081 //JR 23.02.2005, Debug : siftEvents() must be inside the pthread_mutex_lock
2082   // remove "extra" events from the event queue
2083   siftEvents();
2084   if ( pthread_mutex_unlock( &_MutexWait ) ) {
2085     perror("PushEvent pthread_mutex_unlock ") ;
2086     exit( 0 ) ;
2087   }
2088
2089   // asv : 25.10.04 : calling Editing() to indicate stop of execution
2090   if ( RetVal ) // mkr : IPAL10722 : we have to indicate stop of execution if only execution was successfully killed
2091     Graph()->GraphEditor()->Editing();
2092
2093   cdebug_out << "GraphExecutor::OutNode::Kill " << RetVal
2094              << " Threads " << _Threads << " SuspendedThreads " << _SuspendedThreads
2095              << " EventQSize " << EventQSize() << endl ;
2096
2097   return RetVal ;
2098 }
2099
2100 bool GraphExecutor::OutNode::Stop() {
2101   bool RetVal = false ;
2102   cdebug_in << "GraphExecutor::OutNode::Stop" << endl;
2103   RetVal = Kill() ;
2104   cdebug_out << "GraphExecutor::OutNode::Stop" << endl ;
2105   if ( RetVal ) {
2106     MESSAGE("================================================================================") ;
2107     MESSAGE( Name() << " IS STOPPED" ) ;
2108     MESSAGE("================================================================================") ;
2109   }
2110   return RetVal ;
2111 }
2112
2113 bool GraphExecutor::OutNode::ReadyWait() {
2114   cdebug_in << "GraphExecutor::OutNode::ReadyWait" << endl;
2115   bool aret ;
2116   if ( pthread_mutex_lock( &_MutexWait ) ) {
2117     perror("pthread_mutex_lock _ReadyWait") ;
2118     exit( 0 ) ;
2119   }
2120   aret = IsReady() ;
2121   if ( !aret ) {
2122     Suspend() ;
2123     pthread_cond_wait( &_EventWait , &_MutexWait );
2124     aret = IsReady() ;
2125   }
2126   if ( pthread_mutex_unlock( &_MutexWait ) ) {
2127     perror("pthread_mutex_lock _ReadyWait") ;
2128     exit( 0 ) ;
2129   }
2130   cdebug_out << "GraphExecutor::OutNode::ReadyWait" << endl ;
2131   return aret ;
2132 }
2133
2134 bool GraphExecutor::OutNode::RunningWait() {
2135   cdebug_in << "GraphExecutor::OutNode::RunningWait" << endl;
2136   bool aret ;
2137   if ( pthread_mutex_lock( &_MutexWait ) ) {
2138     perror("pthread_mutex_lock _RunningWait") ;
2139     exit( 0 ) ;
2140   }
2141   aret = IsRunning() ;
2142   if ( !aret ) {
2143     cdebug << "RunningWait pthread_cond_wait _EventWait" << endl;
2144     pthread_cond_wait( &_EventWait , &_MutexWait );
2145     aret = IsRunning() ;
2146     cdebug << "RunningWait pthread_cond_waited _EventWait " << aret << endl;
2147   }
2148   if ( pthread_mutex_unlock( &_MutexWait ) ) {
2149     perror("pthread_mutex_lock _RunningWait") ;
2150     exit( 0 ) ;
2151   }
2152   cdebug_out << "GraphExecutor::OutNode::RunningWait " << aret << endl ;
2153   return aret ;
2154 }
2155
2156 bool GraphExecutor::OutNode::DoneWait() {
2157   cdebug_in << pthread_self() << " GraphExecutor::DoneWait " << this << " " << Name() << endl;
2158   bool aret ;
2159   if ( pthread_mutex_lock( &_MutexWait ) ) {
2160     perror("pthread_mutex_lock _DoneWait") ;
2161     exit( 0 ) ;
2162   }
2163   aret = IsDone() ;
2164   while ( !aret && !IsSuspended() && IsRunning() ) {
2165     cdebug << pthread_self() << " GraphExecutor::DoneWait " << this << " " << Name()
2166            << " DoneWait pthread_cond_wait _EventWait " << &_EventWait << endl;
2167     pthread_cond_wait( &_EventWait , &_MutexWait );
2168     aret = IsDone() ;
2169     cdebug << pthread_self() << " GraphExecutor::DoneWait " << this << " " << Name()
2170            << " DoneWait pthread_cond_waited _EventWaited " << &_EventWait << " : "<< aret << endl;
2171   }
2172   if ( pthread_mutex_unlock( &_MutexWait ) ) {
2173     perror("pthread_mutex_lock _DoneWait") ;
2174     exit( 0 ) ;
2175   }
2176   while ( _run_func_thread || theAutomaton->ThreadsNumber() ) {
2177     // mkr : IPAL14711
2178     // waiting for pthread_join in FiniteStateMachine
2179   }
2180   if ( Done() || IsKilled() ) Graph()->GraphEditor()->Editing(); // mkr : IPAL14572 : calling Editing() to indicate stop of execution
2181   cdebug_out << pthread_self() << " GraphExecutor::DoneWait " << this << " " << Name()
2182              << " " << State() << " : " << aret << endl ;
2183   return aret ;
2184 }
2185
2186 bool GraphExecutor::OutNode::SuspendedWait() {
2187   cdebug_in << "GraphExecutor::OutNode::SuspendedWait" << endl;
2188   bool aret ;
2189   if ( pthread_mutex_lock( &_MutexWait ) ) {
2190     perror("pthread_mutex_lock _SuspendedWait") ;
2191     exit( 0 ) ;
2192   }
2193   aret = IsSuspended() ;
2194   while ( !aret && !IsDone() ) {
2195     pthread_cond_wait( &_EventWait , &_MutexWait );
2196     aret = IsSuspended() ;
2197   }
2198   if ( pthread_mutex_unlock( &_MutexWait ) ) {
2199     perror("pthread_mutex_lock _SuspendedWait") ;
2200     exit( 0 ) ;
2201   }
2202   cdebug_out << "GraphExecutor::OutNode::SuspendedWait" << endl ;
2203   return aret ;
2204 }
2205
2206 bool GraphExecutor::OutNode::ReadyWait( const char * NodeName ) {
2207   bool aret = false ;
2208   cdebug_in << "GraphExecutor::OutNode::ReadyWait " << NodeName << endl;
2209   GraphExecutor::InNode *anInNode = (GraphExecutor::InNode *) Graph()->GetGraphNode( NodeName )->GetInNode() ;
2210   if ( anInNode ) {
2211     aret = anInNode->ReadyWait() ;
2212   }
2213   cdebug_out << "GraphExecutor::OutNode::ReadyWait" << endl ;
2214   return aret ;
2215 }
2216
2217 bool GraphExecutor::OutNode::RunningWait( const char * NodeName ) {
2218   bool aret = false ;
2219   cdebug_in << "GraphExecutor::OutNode::RunningWait " << NodeName << endl;
2220   GraphExecutor::InNode *anInNode = (GraphExecutor::InNode *) Graph()->GetGraphNode( NodeName )->GetInNode() ;
2221   if ( anInNode ) {
2222     aret = anInNode->RunningWait() ;
2223   }
2224   cdebug_out << "GraphExecutor::OutNode::RunningWait" << endl ;
2225   return aret ;
2226 }
2227
2228 bool GraphExecutor::OutNode::DoneWait( const char * NodeName ) {
2229   bool aret = false ;
2230   cdebug_in << "GraphExecutor::OutNode::DoneWait " << NodeName << endl;
2231   GraphExecutor::InNode *anInNode = (GraphExecutor::InNode *) Graph()->GetGraphNode( NodeName )->GetInNode() ;
2232   if ( anInNode ) {
2233     aret = anInNode->DoneWait() ;
2234   }
2235   cdebug_out << "GraphExecutor::OutNode::DoneWait" << endl ;
2236   return aret ;
2237 }
2238
2239 bool GraphExecutor::OutNode::SuspendedWait( const char * NodeName ) {
2240   bool aret = false ;
2241   cdebug_in << "GraphExecutor::OutNode::SuspendedWait " << NodeName << endl;
2242   GraphExecutor::InNode *anInNode = (GraphExecutor::InNode *) Graph()->GetGraphNode( NodeName )->GetInNode() ;
2243   if ( anInNode ) {
2244     aret = anInNode->SuspendedWait() ;
2245   }
2246   cdebug_out << "GraphExecutor::OutNode::SuspendedWait" << endl ;
2247   return aret ;
2248 }
2249
2250 long GraphExecutor::OutNode::LastLevelDone() {
2251   int RetVal = -1 ;
2252   int i , j ;
2253   for ( i = 0 ; i <= Graph()->LevelMax() ; i++ ) {
2254     for ( j = 0 ; j <= Graph()->NodesNumber( i ) ; j++ ) {
2255       GraphBase::ComputingNode * aNode = Graph()->SortedNodes( i , j ) ;
2256       if ( !IsDone( aNode->Name() ) ) {
2257         break ;
2258       }
2259     }
2260     if ( j != Graph()->NodesNumber( i ) + 1 )
2261       break ;
2262     RetVal = i ;
2263   }
2264   return RetVal ;
2265 }
2266
2267
2268 //JR 30.03.2005const CORBA::Any *GraphExecutor::OutNode::GetInData( const char * NodeName ,
2269 const CORBA::Any GraphExecutor::OutNode::GetInData( const char * NodeName ,
2270                                                     const char * ServiceParameterName ) {
2271 //  cdebug_in << "GraphExecutor::OutNode::GetInData " << NodeName << " "
2272 //            << ServiceParameterName << endl ;
2273 //JR 30.03.2005  const CORBA::Any * retdata = Graph()->PortInData( NodeName , ServiceParameterName ) ;
2274   const CORBA::Any retdata = Graph()->PortInData( NodeName , ServiceParameterName ) ;
2275 //  cdebug_out << "GraphExecutor::OutNode::GetInData" << endl ;
2276   return retdata ;
2277 }
2278
2279 //JR 30.03.2005const CORBA::Any *GraphExecutor::OutNode::GetOutData( const char * NodeName ,
2280 const CORBA::Any GraphExecutor::OutNode::GetOutData( const char * NodeName ,
2281                                                       const char * ServiceParameterName ) {
2282 //  cdebug_in << "GraphExecutor::OutNode::GetOutData " << NodeName << " "
2283 //            << ServiceParameterName << endl ;
2284 //JR 30.03.2005  const CORBA::Any * retdata = Graph()->PortOutData( NodeName , ServiceParameterName ) ;
2285   const CORBA::Any retdata = Graph()->PortOutData( NodeName , ServiceParameterName ) ;
2286 //  cdebug_out << "GraphExecutor::OutNode::GetOutData" << endl ;
2287   return retdata ;
2288 }
2289
2290 const long GraphExecutor::OutNode::CpuUsed() {
2291   return Graph()->CpuUsed() ;
2292 }
2293
2294 const long GraphExecutor::OutNode::CpuUsed( const char * aNodeName ) {
2295   GraphBase::ComputingNode * aNode = Graph()->GetChangeGraphNode( aNodeName ) ;
2296   if ( aNode ) {
2297     GraphExecutor::InNode * anInNode = (GraphExecutor::InNode * ) aNode->GetInNode() ;
2298     if ( anInNode ) {
2299       return anInNode->CpuUsed() ;
2300     }
2301   }
2302   return 0 ;
2303 }
2304
2305 // remove equal sets "Node-Event-State" from _EventNodes/_Events/_States queues
2306 void GraphExecutor::OutNode::siftEvents() {
2307   list<char*>::reverse_iterator itNodes = _EventNodes.rbegin();
2308   list<GraphExecutor::NodeEvent>::reverse_iterator itEvents = _Events.rbegin();
2309   list<GraphExecutor::AutomatonState>::reverse_iterator itStates = _States.rbegin();
2310   list<char*> _NewEventNodes;
2311   list<GraphExecutor::NodeEvent> _NewEvents;
2312   list<GraphExecutor::AutomatonState> _NewStates;
2313   for ( ; itNodes != _EventNodes.rend() ; ++itNodes, ++itEvents, ++itStates) {
2314     //cout << "----- aNodeName ==> " << *itNodes;
2315     list<char*>::reverse_iterator itNewNodes = _NewEventNodes.rbegin();
2316     bool found = false;
2317     for ( ; itNewNodes != _NewEventNodes.rend() ; ++itNewNodes ) {
2318       if ( !strcmp( *itNewNodes, *itNodes ) ) {
2319         found = true;
2320         break;
2321       }
2322     }
2323
2324     if ( found ) {
2325       //cout << "   FOUND";
2326     }
2327     else {
2328       _NewEventNodes.push_back( *itNodes );
2329       _NewEvents.push_back( *itEvents );
2330       _NewStates.push_back( *itStates );
2331     }
2332     //cout << endl;
2333   }
2334   _EventNodes = _NewEventNodes;
2335   _Events = _NewEvents;
2336   _States = _NewStates;
2337 }