1 // SUPERV GraphExecutor : contains classes that permit execution of graphs and particularly the execution automaton
3 // Copyright (C) 2003 CEA/DEN, EDF R&D
7 // File : DataFlowExecutor_PyDynInvoke.cxx
8 // Author : Jean Rahuel, CEA
17 #include "DataFlowExecutor_InNode.hxx"
19 using namespace CORBA ;
21 static PyObject * MyPyObjRef = NULL ;
22 static PyObject * MyPyObjIor = NULL ;
23 static PyObject * MyPyRunMethod = NULL ;
25 static PyMethodDef MethodPyRunMethod[] = {
26 { "RunMethod", PyRunMethod, METH_VARARGS },
30 bool GraphExecutor::InNode::InitPython() {
31 cdebug_in << "InitPython" << endl ;
33 // PyObject * Module = Py_InitModule( "InitPyRunMethod" , MethodPyRunMethod ) ;
34 Py_InitModule( "InitPyRunMethod" , MethodPyRunMethod ) ;
35 // PyObject * Dictionnary = PyModule_GetDict( Module ) ;
36 // InitPyDynInvokeError = PyErr_NewException( "InitPyDynInvokeError" , NULL , NULL ) ;
37 // PyDict_SetItemString( Dictionnary , InitPyDynInvokeError ) ;
38 cdebug << ThreadNo() << "Py_Initialized() " << endl ;
41 // aPyFunc = "print 'InitPyRunMethod'\n" ;
42 aPyFunc = "import InitPyRunMethod\n" ;
43 // aPyFunc += "print 'sys'\n" ;
44 aPyFunc += "import sys\n" ;
45 // aPyFunc += "print 'CORBA'\n" ;
46 aPyFunc += "import CORBA\n" ;
47 // aPyFunc += "print 'omniORB'\n" ;
48 aPyFunc += "import omniORB\n" ;
49 // aPyFunc += "print 'PyObjRef'\n" ;
50 aPyFunc += "def PyObjRef( IORObjStr ) :\n" ;
51 // aPyFunc += " print 'PyObjRef',IORObjStr\n" ;
52 aPyFunc += " orb = CORBA.ORB_init( sys.argv , CORBA.ORB_ID )\n" ;
53 // aPyFunc += " print 'PyObjRef orb',orb\n" ;
54 aPyFunc += " objref = orb.string_to_object( IORObjStr )\n" ;
55 // aPyFunc += " print 'PyObjRef IORObjStr objref',IORObjStr,objref\n" ;
56 aPyFunc += " return objref\n" ;
57 aPyFunc += "InitPyRunMethod.RunMethod( PyObjRef )\n" ;
58 if ( PyRun_SimpleString( (char *) aPyFunc.c_str() ) ) {
59 cdebug << ThreadNo() << " PyRun_SimpleString ERROR " << endl << aPyFunc << endl ;
62 MyPyObjRef = MyPyRunMethod ;
64 aPyFunc = "import InitPyRunMethod\n" ;
65 aPyFunc += "import sys\n" ;
66 aPyFunc += "import CORBA\n" ;
67 aPyFunc += "import omniORB\n" ;
68 aPyFunc += "def PyObjIor( ObjRef ) :\n" ;
69 // aPyFunc += " print 'PyObjIor',ObjRef\n" ;
70 aPyFunc += " orb = CORBA.ORB_init( sys.argv , CORBA.ORB_ID )\n" ;
71 // aPyFunc += " print 'PyObjIor orb',orb\n" ;
72 aPyFunc += " objIor = orb.object_to_string( ObjRef )\n" ;
73 // aPyFunc += " print 'PyObjIor ObjRef objIor',ObjRef,objIor\n" ;
74 aPyFunc += " return objIor\n" ;
75 aPyFunc += "InitPyRunMethod.RunMethod( PyObjIor )\n" ;
76 if ( PyRun_SimpleString( (char *) aPyFunc.c_str() ) ) {
77 cdebug << ThreadNo() << " PyRun_SimpleString ERROR " << endl << aPyFunc << endl ;
80 MyPyObjIor = MyPyRunMethod ;
82 cdebug_out << "InitPython" << endl ;
86 PyObject * GraphExecutor::InNode::InitPyDynInvoke(
88 const SUPERV::ListOfStrings * aPythonFunction ) {
92 cdebug_in << "InitPyDynInvoke '" << PyFuncName << "' length "
93 << (*aPythonFunction).length() << endl ;
95 if ( (*aPythonFunction).length() ) {
97 aPyFunc += "import InitPyRunMethod\n" ;
98 for ( i = 0 ; i < (*aPythonFunction).length() ; i++ ) {
99 aPyFunc += (*aPythonFunction)[ i ] ;
102 aPyFunc += "InitPyRunMethod.RunMethod( " ;
103 aPyFunc += PyFuncName ;
105 cdebug << "InitPyDynInvoke PyRun_SimpleString " << endl << aPyFunc << endl ;
106 if ( PyRun_SimpleString( (char *) aPyFunc.c_str() ) ) {
107 cdebug << ThreadNo() << " PyRun_SimpleString ERROR " << endl << aPyFunc << endl ;
111 PyFuncRunned( true ) ;
112 // _MyPyRunMethod = MyPyRunMethod ; // To mutex
113 cdebug << ThreadNo() << "PyRun_SimpleString( " << (*aPythonFunction)[ 0 ]
116 cdebug_out << "InitPyDynInvoke" << endl ;
118 return MyPyRunMethod ;
125 extern "C" PyObject * PyRunMethod( PyObject * dummy , PyObject * Args ) {
126 // cout << "PyRunMethod -->" << endl ;
127 PyObject * Result = NULL ;
128 PyObject * Temp = NULL ;
129 if ( PyArg_ParseTuple( Args , "O:set_callback" , & Temp ) ) {
130 // cout << "PyArg_ParsedTuple" << endl ;
131 if ( !PyCallable_Check( Temp ) ) {
132 // PyErr_SetString( PyExc_TypeError , "PyRunMethod must be callable" ) ;
133 // cout << "PyRunMethod must be callable" << endl ;
137 Py_XDECREF( MyPyRunMethod ) ;
138 MyPyRunMethod = Temp ;
139 Py_INCREF( Py_None ) ;
142 // cout << "<-- PyRunMethod" << endl ;
146 bool GraphExecutor::InNode::PyDynInvoke( PyObject * MyPyRunMethod ,
148 ServicesAnyData * inParams , int nInParams ,
149 ServicesAnyData * outParams , int nOutParams ) {
154 int n_in = nInParams ;
155 int n_out = nOutParams ;
158 cdebug_in << ThreadNo() << "GraphExecutor::InNode::PyDynInvoke " << method << " " << n_in
159 << " InArgs " << n_out << " OutArgs" << endl ;
163 PyObject * ArgsList = NULL ;
164 PyObject * ArgValue = NULL ;
165 PyObject * Result = NULL ;
166 PyObject * MyPyObjRefList = NULL ;
167 PyObject * ResultObj = NULL ;
168 PyObject * MyPyObjIorList = NULL ;
169 PyObject * ResultIor = NULL ;
171 CORBA::Object_ptr ObjRef ;
174 ArgsList = PyTuple_New( n_in ) ;
176 for ( i = 0 ; i < n_in ; i++ ) {
177 data = inParams[i].Value ;
178 sname = inParams[i].Name.c_str() ;
179 switch ( data.type()->kind() ) {
180 case CORBA::tk_string : {
183 ArgValue = Py_BuildValue( "s" , t ) ;
184 PyTuple_SetItem( ArgsList , i , ArgValue ) ;
185 cdebug << "ArgIn" << i << " : " << sname << " " << method << " Value " << t << " (string) "
186 << " ArgsList->ob_refcnt" << ArgsList->ob_refcnt << " ArgValue->ob_refcnt"
187 << ArgValue->ob_refcnt << endl ;
190 case CORBA::tk_boolean : {
192 data >>= (CORBA::Any::to_boolean ) b ;
193 ArgValue = Py_BuildValue( "b" , b ) ;
194 PyTuple_SetItem( ArgsList , i , ArgValue ) ;
195 cdebug << "ArgIn" << i << " : " << sname << " " << method << " Value " << b
196 << " (boolean) ArgsList->ob_refcnt" << ArgsList->ob_refcnt << " ArgValue->ob_refcnt"
197 << ArgValue->ob_refcnt << endl ;
200 case CORBA::tk_char : {
202 data >>= (CORBA::Any::to_char ) c ;
203 ArgValue = Py_BuildValue( "c" , c ) ;
204 PyTuple_SetItem( ArgsList , i , ArgValue ) ;
205 cdebug << "ArgIn" << i << " : " << sname << " " << method << " Value " << c
206 << " (char) ArgsList->ob_refcnt" << ArgsList->ob_refcnt << " ArgValue->ob_refcnt"
207 << ArgValue->ob_refcnt << endl ;
210 case CORBA::tk_short : {
213 ArgValue = Py_BuildValue( "h" , s ) ;
214 PyTuple_SetItem( ArgsList , i , ArgValue ) ;
215 cdebug << "ArgIn" << i << " : " << sname << " " << method << " Value " << s
216 << " (short) ArgsList->ob_refcnt" << ArgsList->ob_refcnt << " ArgValue->ob_refcnt"
217 << ArgValue->ob_refcnt << endl ;
220 case CORBA::tk_long : {
223 ArgValue = Py_BuildValue( "l" , l ) ;
224 PyTuple_SetItem( ArgsList , i , ArgValue ) ;
225 cdebug << "ArgIn" << i << " : " << sname << " " << method << " Value " << l
226 << " (long) ArgsList->ob_refcnt" << ArgsList->ob_refcnt << " ArgValue->ob_refcnt"
227 << ArgValue->ob_refcnt << endl ;
230 case CORBA::tk_float : {
233 ArgValue = Py_BuildValue( "f" , f ) ;
234 PyTuple_SetItem( ArgsList , i , ArgValue ) ;
235 cdebug << "ArgIn" << i << " : " << sname << " " << method << " Value " << f
236 << " (float) ArgsList->ob_refcnt" << ArgsList->ob_refcnt << " ArgValue->ob_refcnt"
237 << ArgValue->ob_refcnt << endl ;
240 case CORBA::tk_double : {
243 ArgValue = Py_BuildValue( "d" , d ) ;
244 PyTuple_SetItem( ArgsList , i , ArgValue ) ;
245 cdebug << "ArgIn" << i << " : " << sname << " " << method << " Value " << d
246 << " (double) ArgsList->ob_refcnt" << ArgsList->ob_refcnt << " ArgValue->ob_refcnt"
247 << ArgValue->ob_refcnt << endl ;
250 case CORBA::tk_objref : {
251 MyPyObjRefList = PyTuple_New( 1 ) ;
252 PyObject * ObjValue ;
254 IORObjRef = ObjectToString( ObjRef ) ;
255 ObjValue = Py_BuildValue( "s" , IORObjRef ) ;
256 PyTuple_SetItem( MyPyObjRefList , 0 , ObjValue ) ;
257 cdebug << "ArgIn" << i << " : " << sname << " " << method << " " << " Value " << IORObjRef << " (objref) "
258 << MyPyObjRef->ob_refcnt << "/" << MyPyObjRefList->ob_refcnt << endl ;
259 ResultObj = PyEval_CallObject( MyPyObjRef , MyPyObjRefList ) ;
260 cdebug << "ObjValue->ob_refcnt" << ObjValue->ob_refcnt << endl ;
261 ArgValue = Py_BuildValue( "O" , ResultObj ) ;
262 PyTuple_SetItem( ArgsList , i , ArgValue ) ;
263 cdebug << "ArgIn" << i << " : " << sname << " " << method << " Value (objref) ArgsList->ob_refcnt"
264 << ArgsList->ob_refcnt << " ArgValue->ob_refcnt" << ArgValue->ob_refcnt << endl ;
265 cdebug << "MyPyObjRefList->ob_refcnt " << MyPyObjRefList->ob_refcnt-1 << endl ;
266 Py_DECREF( MyPyObjRefList ) ;
267 if ( CORBA::is_nil( ObjRef ) ) {
271 cdebug << "ResultObj->ob_refcnt " << ResultObj->ob_refcnt-1 << endl ;
272 Py_DECREF( ResultObj ) ;
277 cdebug << "ArgIn" << i << " : " << sname << " Value " << "(other ERROR)" << endl ;
282 if (!PyCallable_Check( MyPyRunMethod )) {
287 Result = PyEval_CallObject( MyPyRunMethod , ArgsList ) ;
288 cdebug << "ArgsList->ob_refcnt" << ArgsList->ob_refcnt << endl ;
290 if ( Result == NULL ) {
291 cdebug_out << "GraphExecutor::InNode::PyDynInvoke " << method << " Error Result == NULL" << endl ;
295 for ( i = 0 ; i < n_out ; i++ ) {
296 data = outParams[i].Value ;
297 sname = outParams[i].Name.c_str() ;
298 switch ( data.type()->kind() ) {
299 case CORBA::tk_string : {
301 if ( PyTuple_Check( Result ) ) {
302 ArgValue = PyTuple_GetItem( Result , i ) ;
307 if ( !PyString_Check( ArgValue ) ) {
308 cdebug << "ArgOut" << i << " : " << sname << " " << method << " ERROR (string)" << endl ;
311 t = PyString_AsString( ArgValue ) ;
314 cdebug << "ArgOut" << i << " : " << sname << " " << method << " Value " << t << " (string)"
315 << " ArgsList->ob_refcnt" << ArgsList->ob_refcnt << " ArgValue->ob_refcnt"
316 << ArgValue->ob_refcnt << endl ;
319 case CORBA::tk_boolean : {
321 if ( PyTuple_Check( Result ) ) {
322 ArgValue = PyTuple_GetItem( Result , i ) ;
327 if ( !PyInt_Check( ArgValue ) ) {
328 cdebug << "ArgOut" << i << " : " << sname << " " << method << " ERROR (boolean)" << endl ;
331 b = PyInt_AsLong( ArgValue ) ;
333 data <<= (CORBA::Any::from_boolean ) b ;
334 cdebug << "ArgOut" << i << " : " << sname << " " << method << " Value " << b << " (boolean)"
335 << " ArgsList->ob_refcnt" << ArgsList->ob_refcnt << " ArgValue->ob_refcnt"
336 << ArgValue->ob_refcnt << endl ;
339 case CORBA::tk_char : {
340 unsigned char c = 0 ;
341 if ( PyTuple_Check( Result ) ) {
342 ArgValue = PyTuple_GetItem( Result , i ) ;
347 if ( !PyInt_Check( ArgValue ) ) {
348 cdebug << "ArgOut" << i << " : " << sname << " " << method << " ERROR (char)" << endl ;
351 c = PyInt_AsLong( ArgValue ) ;
353 data <<= (CORBA::Any::from_char ) c ;
354 cdebug << "ArgOut" << i << " : " << sname << " " << method << " Value " << c << " (char)"
355 << " ArgsList->ob_refcnt" << ArgsList->ob_refcnt << " ArgValue->ob_refcnt"
356 << ArgValue->ob_refcnt << endl ;
359 case CORBA::tk_short : {
361 if ( PyTuple_Check( Result ) ) {
362 ArgValue = PyTuple_GetItem( Result , i ) ;
367 if ( !PyInt_Check( ArgValue ) ) {
368 cdebug << "ArgOut" << i << " : " << sname << " " << method << " ERROR (short)" << endl ;
371 s = PyInt_AsLong( ArgValue ) ;
374 cdebug << "ArgOut" << i << " : " << sname << " " << method << " Value " << s << " (short)"
375 << " ArgsList->ob_refcnt" << ArgsList->ob_refcnt << " ArgValue->ob_refcnt"
376 << ArgValue->ob_refcnt << endl ;
379 case CORBA::tk_long : {
381 if ( PyTuple_Check( Result ) ) {
382 ArgValue = PyTuple_GetItem( Result , i ) ;
387 if ( PyLong_Check( ArgValue ) ) {
388 l = PyLong_AsLong( ArgValue ) ;
390 else if ( PyInt_Check( ArgValue ) ) {
391 l = PyInt_AsLong( ArgValue ) ;
394 cdebug << "ArgOut" << i << " : " << sname << " " << method << " ERROR (CORBA::tk_long)" << endl ;
397 cdebug << "ArgOut" << i << " : " << sname << " " << method << " Value " << l << " (long)"
398 << " ArgsList->ob_refcnt" << ArgsList->ob_refcnt << " ArgValue->ob_refcnt"
399 << ArgValue->ob_refcnt << endl ;
402 case CORBA::tk_float : {
404 if ( PyTuple_Check( Result ) ) {
405 ArgValue = PyTuple_GetItem( Result , i ) ;
410 if ( !PyFloat_Check( ArgValue ) ) {
411 cdebug << "ArgOut" << i << " : " << sname << " " << method << " ERROR (float)" << endl ;
414 f = PyFloat_AsDouble( ArgValue ) ;
417 cdebug << "ArgOut" << i << " : " << sname << " " << method << " Value " << f << " (float)"
418 << " ArgsList->ob_refcnt" << ArgsList->ob_refcnt << " ArgValue->ob_refcnt"
419 << ArgValue->ob_refcnt << endl ;
422 case CORBA::tk_double : {
424 if ( PyTuple_Check( Result ) ) {
425 ArgValue = PyTuple_GetItem( Result , i ) ;
430 if ( !PyFloat_Check( ArgValue ) ) {
431 cdebug << "ArgOut" << i << " : " << sname << " " << method << " ERROR (double)" << endl ;
434 d = PyFloat_AsDouble( ArgValue ) ;
437 cdebug << "ArgOut" << i << " : " << sname << " " << method << " Value " << d << " (double)"
438 << " ArgsList->ob_refcnt" << ArgsList->ob_refcnt << " ArgValue->ob_refcnt"
439 << ArgValue->ob_refcnt << endl ;
442 case CORBA::tk_objref : {
444 MyPyObjIorList = PyTuple_New( 1 ) ;
445 if ( PyTuple_Check( Result ) ) {
446 ObjIor = PyTuple_GetItem( Result , i ) ;
451 cdebug << "ArgOut" << i << " : " << sname << " " << method << " Value " << "(object reference) "
452 << " ArgsList->ob_refcnt" << ArgsList->ob_refcnt << " ObjIor->ob_refcnt"
453 << ObjIor->ob_refcnt << endl ;
454 Py_INCREF( ObjIor ) ;
455 // PyObject_Print( ObjIor , stdout , 0 ) ;
456 PyTuple_SetItem( MyPyObjIorList , 0 , ObjIor ) ;
457 ResultIor = PyEval_CallObject( MyPyObjIor , MyPyObjIorList ) ;
458 cdebug << "ObjIor->ob_refcnt " << ObjIor->ob_refcnt-1 << endl ;
459 Py_DECREF( ObjIor ) ;
460 cdebug << "MyPyObjIorList->ob_refcnt " << MyPyObjIorList->ob_refcnt-1 << endl ;
461 Py_DECREF( MyPyObjIorList ) ;
462 cdebug << "MyPyObjIor->ob_refcnt " << MyPyObjIor->ob_refcnt << endl ;
465 IOR = PyString_AsString( ResultIor ) ;
466 ObjRef = StringToObject( IOR ) ;
468 IORObjRef = ObjectToString( ObjRef ) ;
469 cdebug << "ArgOut" << i << " : " << sname << " " << method << " Value " << IORObjRef << " (objref) "
471 if ( CORBA::is_nil( ObjRef ) ) {
475 cdebug << "ResultIor->ob_refcnt " << ResultIor->ob_refcnt-1 << endl ;
476 Py_DECREF( ResultIor ) ;
480 cdebug_out << "GraphExecutor::InNode::PyDynInvoke Error ResultIor == NULL"
481 << method << " " << endl ;
487 cdebug << "ArgOut" << i << " : " << sname << " " << method << " Value " << "(other ERROR)" << endl ;
490 outParams[i].Value = data ;
493 cdebug << "Result->ob_refcnt" << Result->ob_refcnt-1 << endl ;
494 Py_DECREF( Result ) ;
497 cdebug << "GraphExecutor::InNode::PyDynInvoke ArgsList->ob_refcnt"
498 << ArgsList->ob_refcnt-1 << endl ;
499 Py_DECREF( ArgsList ) ;
501 cdebug_out << "GraphExecutor::InNode::PyDynInvoke " << method << endl ;