Hi,

There is a problem in the current $CRYSTAL/plugins/cscript/cspython, in that 
the csPython::Call functions have no implementation. Naturally I want to fill 
out these functions, but it would make and break the current iScript object.
Not to be bullish, but

bool csPython::LoadModule(const char* name)
{
  csString s;
  s << "import " << name;
  return RunText(s);
}

is bad, since the only way I can explicitly load python files 
(i.e ./data/custom.py), is to modify PYTHONPATH (which CS doesn't have a 
function for as far as I'm aware and is platform dependent), then import that 
module.
Take this code (minus the error checking and INC/DECREF's for clarity)

-- amir.py --
def foo(a, b):
  return a * b

-- main.cpp --
#include <iostream>
#include <Python.h>

int main()
{
  Py_Initialize();

  /*PyObject* pyIntObject = PyInt_FromLong(5);
  if (pyIntObject == NULL) ; // Error

  Py_DECREF(pyIntObject);

  PyRun_SimpleString("print 'hello'");*/

  // open file and load module
  FILE *file = fopen("amir.py", "r");
  PyRun_SimpleFile(file, "amir.py");

  // get main module
  PyObject *main_module = PyImport_AddModule("__main__");
  PyObject *global_dict = PyModule_GetDict(main_module);

  // get function from global namespace
  /*! this bit I'm unsure of... can I load the function, explicitly
  from the loaded file? I remember being able to do so, but can't
  find out how... */
  PyObject *foo = PyDict_GetItemString(global_dict, "foo");;
  PyObject *arg1 = PyInt_FromLong(2), *arg2 = PyInt_FromLong(8);

  // make tuple of arguments
  PyObject *args = PyTuple_New(2);
  PyTuple_SetItem(args, 0, arg1);
  PyTuple_SetItem(args, 1, arg2);

  // call function and get return object
  PyObject *ret = PyObject_CallObject(foo, args);

  int result = PyInt_AsLong(ret);
  std::cout << result << "!\n";

  Py_Finalize();
  return 0;
}

There are 2 changes that would be made here
1) csPython::LoadModule(..) would load absolute paths as opposed to pythonic 
module style
is->LoadModule("x.k") becomes is->LoadModule("../some/path/maybe/vfs/x/k.py")
2) the csPython::Call functions get implemented.

I've already modified cspython and the pysimp to get a working prototype

  int result = 0;
  is->Call("foo", result, "");
  printf("result : [%i]\n",result);

The problem here is that functions exist in the global namespace :S, each 
function must have a unique identifier.

Here is another alternative which I haven't yet tried. (better from a python 
POV, but maybe not the best for CS)

#include <Python.h>

int main()
{
  char *cstrret;

  Py_Initialize();

  PyObject *module = PyImport_ImportModule("amir");

  PyObject *foo = PyObject_GetAttrString(mymod, "foo");

  PyObject *args = ...; // build value or whatever

  PyObject *ret = PyEval_CallObject(foo, args);

  Py_Finalize();
  return 0;
}

This is a different approach, which I would prefer where it not for the 
structural changes it would bring to iScript. For a start the module 
references would have to be stored somehow (hash map or iScriptModule?), and 
then the functions called by doing
iscript->FindLoadedModule("amir")->Call("foo", &i, 2, 8);

Preferrably if it is possible to mix first one (so can load python files from 
VFS paths) and second one (being explicit about which function the module is 
called from)- it should be, but I can't remember/find out how.

What do you all think?


-------------------------------------------------------
This SF.net email is sponsored by: Splunk Inc. Do you grep through log files
for problems?  Stop!  Download the new AJAX search engine that makes
searching your log files as easy as surfing the  web.  DOWNLOAD SPLUNK!
http://sel.as-us.falkag.net/sel?cmd=lnk&kid=103432&bid=230486&dat=121642
_______________________________________________
Crystal-main mailing list
[email protected]
https://lists.sourceforge.net/lists/listinfo/crystal-main
Unsubscribe: mailto:[EMAIL PROTECTED]

Reply via email to