Salome HOME
Join modifications from BR_Dev_For_4_0 tag V4_1_1.
[modules/superv.git] / src / GraphExecutor / DataFlowExecutor_OutNode.cxx
index fd8c1a177c3d0e3133f86c99e8a639c1308a4aed..55d1df53023bad3f10ca2cbbadbbdf49f5bda57a 100644 (file)
@@ -31,6 +31,7 @@ using namespace std;
 #include "DataFlowExecutor_OutNode.hxx"
 
 #include "DataFlowEditor_DataFlow.hxx"
+#include "DataFlowExecutor_DataFlow.hxx"
 
 // asv : 20.01.05 : changes involved with switching to old (HEAD) KERNEL    
 //extern Engines_Container_i * _TheContainer ;
@@ -55,6 +56,7 @@ GraphExecutor::OutNode::OutNode() {
   _ControlState = SUPERV::VoidState ;
   _State = GraphExecutor::UnKnownState ;
   _PyInitialized = false ;
+  _run_func_thread = 0;
   pthread_mutex_init( &_MutexWait , NULL ) ;
   pthread_mutex_init( &_PyMutexWait , NULL ) ;
   if ( pthread_cond_init( &_EventWait , NULL ) ) {
@@ -96,6 +98,7 @@ GraphExecutor::OutNode::OutNode( CORBA::ORB_ptr ORB,
   _ControlState = SUPERV::VoidState ;
   _State = GraphExecutor::UnKnownState ;
   _PyInitialized = false ;
+  _run_func_thread = 0;
   _Orb = CORBA::ORB::_duplicate( ORB ) ;
   pthread_mutex_init( &_MutexWait , NULL ) ;
   pthread_mutex_init( &_PyMutexWait , NULL ) ;
@@ -159,6 +162,7 @@ GraphExecutor::OutNode::OutNode( CORBA::ORB_ptr ORB,
   _ControlState = SUPERV::VoidState ;
   _State = GraphExecutor::UnKnownState ;
   _PyInitialized = false ;
+  _run_func_thread = 0;
   _Orb = CORBA::ORB::_duplicate( ORB ) ;
   pthread_mutex_init( &_MutexWait , NULL ) ;
   pthread_mutex_init( &_PyMutexWait , NULL ) ;
@@ -519,6 +523,7 @@ bool GraphExecutor::OutNode::Run( const bool AndSuspend ) {
     _JustStarted = true ;
     RetVal = true ;
     int i ;
+    bool again = true ;
     for ( i = 0 ; i < Graph()->GraphNodesSize() ; i++ ) {
       GraphExecutor::InNode * anInNode = (GraphExecutor::InNode *) Graph()->GraphNodes( i )->GetInNode() ;
       anInNode->OutNode( this ) ;
@@ -536,7 +541,12 @@ bool GraphExecutor::OutNode::Run( const bool AndSuspend ) {
       }
       anInNode->InitialState() ;
       if ( anInNode->IsOneOfInLineNodes() ) {
-        anInNode->InitPythonFunctions( false ) ;
+       //JR with Python2.3.4, we may get an error because of a normal previous error
+        bool sts = anInNode->InitPythonFunctions( false ) ;
+        if ( again && !sts ) {
+          sts = anInNode->InitPythonFunctions( false ) ;
+          again = false ;
+       }
       }
     }
 // One more time because inline nodes may share one definition of the same function
@@ -573,6 +583,9 @@ bool GraphExecutor::OutNode::Run( const bool AndSuspend ) {
       }
     }
     */
+    //JR Debug : if there was an error in initialisation of python functions,
+    //           we must not try to execute the graph.
+    if ( RetVal ) {
     if ( Graph()->GraphMacroLevel() != 0 ) {
       cdebug << "GraphExecutor::OutNode::Run Execution starting GraphExecutor::Action_DataOk_RunService Node "
              << Name() << " GraphMacroLevel " << Graph()->GraphMacroLevel() << endl ;
@@ -700,6 +713,19 @@ bool GraphExecutor::OutNode::Run( const bool AndSuspend ) {
 //      Graph()->ObjImpl()->sendMessage( NOTIF_STEP, astr.str().c_str() ) ;
       RetVal = true ;
     }
+    //JR Debug
+    }
+    else {
+      State( GraphExecutor::ErroredState ) ;
+      Done( true ) ;
+      if ( IsDone() && Graph()->GraphMacroLevel() == 0 ) {
+        cdebug << " ==> theAutomaton->Executed() " << endl ;
+        theAutomaton->Executed() ;
+      }
+      else {
+        cdebug << " NO theAutomaton->Executed() " << endl ;
+      }
+    }
   }
   else {
 // PAL 8515
@@ -712,7 +738,7 @@ bool GraphExecutor::OutNode::Run( const bool AndSuspend ) {
 //              two graphs execution with two different python functions with the same name
 //              give aborted state for the second one
 //Example : GraphLoopSwitchOfSwitchNOTValid, GraphLoopSwitchs and GraphLoopSwitchsBranches
-    if ( IsDone() ) {
+    if ( IsDone() && Graph()->GraphMacroLevel() == 0 ) {
       cdebug << " ==> theAutomaton->Executed() " << endl ;
       theAutomaton->Executed() ;
     }
@@ -814,9 +840,33 @@ void GraphExecutor::OutNode::CheckAllDone() {
     MESSAGE("================================================================================") ;
     cdebug << "================================================================================" << endl ;
     cdebug << Name() << " IS DONE : " <<  theAutomaton->StateName( AutomatonState() ) << " EventQSize "
-             << EventQSize() << endl  ;
+            << EventQSize() << endl  ;
     cdebug << "================================================================================" << endl ;
 
+    if ( Graph()->GraphMacroLevel() != 0 ) {
+//JR NPAL14110 09.02.2007 : That must be done only at the end of SubGraph because we may
+//                          have an output of the SubGraph in a Loop !...
+//                          So that code must be done in CheckAllDone instead of OutParametersSet
+      cdebug << "CheckAllDone ToNodeName " << Name() << " CoupledNode "
+             << Graph()->CoupledNodeName() << Graph()->CoupledNode()
+             << endl ;
+      cdebug << "CheckAllDone GraphExecutor " << Graph()->CoupledNode()->GraphEditor()->Executor() << endl ;
+      const GraphBase::InPort * anInPort ;
+      GraphBase::OutPort * anOutPort ;
+      int i ;
+      for ( i = 0 ; i <  Graph()->GetNodeOutDataNodePortsSize() ; i++ ) {
+         anInPort = Graph()->GetNodeOutDataNodePort( i ) ;
+         if ( !anInPort->IsGate() ) {
+           anOutPort = anInPort->GetOutPort() ;
+           Graph()->CoupledNode()->GraphEditor()->Executor()->OutputOfAny( Graph()->CoupledNodeName() ,
+                                                                           anInPort->PortName() ,
+                                                                           anOutPort->Value() ) ;
+           cdebug << "CheckAllDone OutputOfAny( " << Graph()->CoupledNodeName() << " , "
+                  << anInPort->PortName() << " , value ) done" << endl ;
+         }
+      }
+    }
+
 //PAL8520
 //JR 23.02.2005, Debug : siftEvents() must be inside the pthread_mutex_lock
     if ( pthread_mutex_lock( &_MutexWait ) ) {
@@ -935,7 +985,8 @@ void GraphExecutor::OutNode::ExitThread( pthread_t ThreadNumber ) {
     cdebug << pthread_self() << " ExitThread( " << ThreadNumber << " ) " << _Threads
            << " running threads " << _SuspendedThreads << " suspended threads IsDone() "
            << IsDone() ;
-    if ( IsDone() ) {
+    _run_func_thread = 0 ; // mkr : IPAL14711
+    if ( IsDone() && Graph()->GraphMacroLevel() == 0 ) {
       cdebug << " ==> theAutomaton->Executed() " << endl ;
       theAutomaton->Executed() ;
     }
@@ -2122,6 +2173,11 @@ bool GraphExecutor::OutNode::DoneWait() {
     perror("pthread_mutex_lock _DoneWait") ;
     exit( 0 ) ;
   }
+  while ( _run_func_thread || theAutomaton->ThreadsNumber() ) {
+    // mkr : IPAL14711
+    // waiting for pthread_join in FiniteStateMachine
+  }
+  if ( Done() || IsKilled() ) Graph()->GraphEditor()->Editing(); // mkr : IPAL14572 : calling Editing() to indicate stop of execution
   cdebug_out << pthread_self() << " GraphExecutor::DoneWait " << this << " " << Name()
              << " " << State() << " : " << aret << endl ;
   return aret ;