Changeset 406

Show
Ignore:
Timestamp:
Thu Jan 17 13:02:09 2008
Author:
danielevarrazzo
Message:

Dynamic loading works on Linux platform.

The crashes reported in r336 were caused by functions in libpython.so called
by other functions in the same library. If the called function is one of
the functions imported in launch.c, the crash happened.
{{{

launch.c libpython.so

PyF -> PyF

|
v

PyG PyG
}}}

Well, I really can't figure why. Anyway all the functions are imported into
variables whose name is prefixed by 'PI_' and used from there.
{{{

launch.c libpython.so

PI_PyF -> PyF

|
v

PI_PyG PyG
}}}

Files:

Legend:

Unmodified
Added
Removed
Modified
  • branches/dl/source/common/launch.h

    r336 r406  
    56 56 #define EXTDECLPROC(result, name, args)\  
    57 57     typedef result (__cdecl *__PROC__##name) args;\  
    58       extern __PROC__##name name;  
      58     extern __PROC__##name PI_##name;  
    58 58  
    59 59 #define EXTDECLVAR(vartyp, name)\  
     
    66 66 #define EXTDECLPROC(result, name, args)\  
    67 67     typedef result (*__PROC__##name) args;\  
    68       extern __PROC__##name name;  
      68     extern __PROC__##name PI_##name;  
    68 68  
    69 69 #define EXTDECLVAR(vartyp, name)\  
     
    78 78  * They are needed to do very basic Python functionality.  
    79 79  */  
    80   typedef _typeobject;  
      80 /*typedef _typeobject;*/  
    80 80 typedef struct _object {  
    81 81     int ob_refcnt;  
     
    139 139 EXTDECLPROC(int, Py_Initialize, (void));  
    140 140 EXTDECLPROC(int, Py_Finalize, (void));  
    141   EXTDECLPROC(PyObject *, Py_CompileString, (char *, char *, int));  
    142 141 EXTDECLPROC(PyObject *, PyImport_ExecCodeModule, (char *, PyObject *));  
    143 142 EXTDECLPROC(int, PyRun_SimpleString, (char *));  
    144   EXTDECLPROC(int, PySys_SetArgv, (int, char **));  
    145 143 EXTDECLPROC(void, Py_SetProgramName, (char *));  
    146 144 EXTDECLPROC(PyObject *, PyImport_ImportModule, (char *));  
     
    150 148 EXTDECLPROC(int, PyList_Append, (PyObject *, PyObject *));  
    151 149 EXTDECLPROC(PyObject *, Py_BuildValue, (char *, ...));  
    152   EXTDECLPROC(PyObject *, PyFile_FromString, (char *, char *));  
    153 150 EXTDECLPROC(PyObject *, PyString_FromStringAndSize, (const char *, int));  
    154 151 EXTDECLPROC(PyObject *, PyObject_CallFunction, (PyObject *, char *, ...));  
    155 152 EXTDECLPROC(PyObject *, PyModule_GetDict, (PyObject *));  
    156 153 EXTDECLPROC(PyObject *, PyDict_GetItemString, (PyObject *, char *));  
    157   EXTDECLPROC(void, PyErr_Clear, () );  
    158   EXTDECLPROC(PyObject *, PyErr_Occurred, () );  
    159   EXTDECLPROC(void, PyErr_Print, () );  
    160   EXTDECLPROC(PyObject *, PyObject_CallObject, (PyObject *, PyObject*) );  
    161   EXTDECLPROC(PyObject *, PyObject_CallMethod, (PyObject *, char *, char *, ...) );  
    162   EXTDECLPROC(void, PySys_AddWarnOption, (char *));  
    163   EXTDECLPROC(void, PyEval_InitThreads, () );  
      154 EXTDECLPROC(void, PyErr_Clear, (void) );  
      155 EXTDECLPROC(PyObject *, PyErr_Occurred, (void) );  
      156 EXTDECLPROC(void, PyErr_Print, (void) );  
      157 EXTDECLPROC(void, PySys_AddWarnOption, (char *));  
      158 EXTDECLPROC(void, PyEval_InitThreads, (void) );  
    164 159 EXTDECLPROC(void, PyEval_AcquireThread, (PyThreadState *) );  
    165 160 EXTDECLPROC(void, PyEval_ReleaseThread, (PyThreadState *) );  
    166   EXTDECLPROC(void, PyEval_AcquireLock, (void) );  
    167   EXTDECLPROC(void, PyEval_ReleaseLock, (void) );  
    168 161 EXTDECLPROC(PyThreadState *, PyThreadState_Swap, (PyThreadState *) );  
    169   EXTDECLPROC(PyThreadState *, PyThreadState_New, (PyInterpreterState *) );  
    170   EXTDECLPROC(void, PyThreadState_Clear, (PyThreadState *) );  
    171   EXTDECLPROC(void, PyThreadState_Delete, (PyThreadState *) );  
    172   EXTDECLPROC(PyInterpreterState *, PyInterpreterState_New, () );  
    173   EXTDECLPROC(PyThreadState *, Py_NewInterpreter, () );  
      162 EXTDECLPROC(PyThreadState *, Py_NewInterpreter, (void) );  
    174 163 EXTDECLPROC(void, Py_EndInterpreter, (PyThreadState *) );  
    175 164 EXTDECLPROC(long, PyInt_AsLong, (PyObject *) );  
     
    182 171  
    183 172 #define DECLPROC(name)\  
    184       __PROC__##name name = NULL;  
      173     __PROC__##name PI_##name = NULL;  
    184 173 #define GETPROC(dll, name)\  
    185       name = (__PROC__##name)GetProcAddress (dll, #name);\  
    186       if (!name) {\  
      174     PI_##name = (__PROC__##name)GetProcAddress (dll, #name);\  
      175     if (!PI_##name) {\  
    187 176         FATALERROR ("Cannot GetProcAddress for " #name);\  
    188 177         return -1;\  
     
    201 190  
    202 191 #define DECLPROC(name)\  
    203       __PROC__##name name = NULL;  
      192     __PROC__##name PI_##name = NULL;  
    203 192 #define GETPROC(dll, name)\  
    204       name = (__PROC__##name *)dlsym (dll, #name);\  
    205       if (!name) {\  
      193     PI_##name = (__PROC__##name)dlsym (dll, #name);\  
      194     if (!PI_##name) {\  
    206 195         FATALERROR ("Cannot dlsym for " #name);\  
    207 196         return -1;\  
  • branches/dl/source/common/launch.c

    r338 r406  
    53 53 DECLPROC(Py_Initialize);  
    54 54 DECLPROC(Py_Finalize);  
    55   DECLPROC(Py_CompileString);  
    56 55 DECLPROC(PyImport_ExecCodeModule);  
    57 56 DECLPROC(PyRun_SimpleString);  
    58   DECLPROC(PySys_SetArgv);  
    59 57 DECLPROC(Py_SetProgramName);  
    60 58 DECLPROC(PyImport_ImportModule);  
     
    64 62 DECLPROC(PyList_Append);  
    65 63 DECLPROC(Py_BuildValue);  
    66   DECLPROC(PyFile_FromString);  
    67 64 DECLPROC(PyString_FromStringAndSize);  
    68 65 DECLPROC(PyObject_CallFunction);  
     
    72 69 DECLPROC(PyErr_Occurred);  
    73 70 DECLPROC(PyErr_Print);  
    74   DECLPROC(PyObject_CallObject);  
    75   DECLPROC(PyObject_CallMethod);  
    76 71 DECLPROC(PySys_AddWarnOption);  
    77 72 DECLPROC(PyEval_InitThreads);  
    78 73 DECLPROC(PyEval_AcquireThread);  
    79 74 DECLPROC(PyEval_ReleaseThread);  
    80   DECLPROC(PyEval_AcquireLock);  
    81   DECLPROC(PyEval_ReleaseLock);  
    82 75 DECLPROC(PyThreadState_Swap);  
    83   DECLPROC(PyThreadState_New);  
    84   DECLPROC(PyThreadState_Clear);  
    85   DECLPROC(PyThreadState_Delete);  
    86   DECLPROC(PyInterpreterState_New);  
    87 76 DECLPROC(Py_NewInterpreter);  
    88 77 DECLPROC(Py_EndInterpreter);  
     
    317 306         GETPROC(dll, Py_Initialize);  
    318 307         GETPROC(dll, Py_Finalize);  
    319           GETPROC(dll, Py_CompileString);  
    320 308         GETPROC(dll, PyImport_ExecCodeModule);  
    321 309         GETPROC(dll, PyRun_SimpleString);  
    322           GETPROC(dll, PySys_SetArgv);  
    323 310         GETPROC(dll, Py_SetProgramName);  
    324 311         GETPROC(dll, PyImport_ImportModule);  
     
    328 315         GETPROC(dll, PyList_Append);  
    329 316         GETPROC(dll, Py_BuildValue);  
    330           GETPROC(dll, PyFile_FromString);  
    331 317         GETPROC(dll, PyString_FromStringAndSize);  
    332 318         GETPROC(dll, PyObject_CallFunction);  
     
    336 322         GETPROC(dll, PyErr_Occurred);  
    337 323         GETPROC(dll, PyErr_Print);  
    338           GETPROC(dll, PyObject_CallObject);  
    339           GETPROC(dll, PyObject_CallMethod);  
    340 324         if (ntohl(f_cookie.pyvers) >= 21) {  
    341 325                 GETPROC(dll, PySys_AddWarnOption);  
     
    344 328         GETPROC(dll, PyEval_AcquireThread);  
    345 329         GETPROC(dll, PyEval_ReleaseThread);  
    346           GETPROC(dll, PyEval_AcquireLock);  
    347           GETPROC(dll, PyEval_ReleaseLock);  
    348 330         GETPROC(dll, PyThreadState_Swap);  
    349           GETPROC(dll, PyThreadState_New);  
    350           GETPROC(dll, PyThreadState_Clear);  
    351           GETPROC(dll, PyThreadState_Delete);  
    352           GETPROC(dll, PyInterpreterState_New);  
    353 331         GETPROC(dll, Py_NewInterpreter);  
    354 332         GETPROC(dll, Py_EndInterpreter);  
    355 333         GETPROC(dll, PyInt_AsLong);  
    356 334         GETPROC(dll, PySys_SetObject);  
      335  
    357 336         return 0;  
    358 337 }  
     
    479 458                         switch (ptoc->name[0]) {  
    480 459                         case 'v':  
    481   #if defined  WIN32  
    482 460                                 *Py_VerboseFlag = 1;  
    483   #else  
    484                                   Py_VerboseFlag = 1;  
    485   #endif  
    486 461                         break;  
    487 462                         case 'u':  
     
    491 466                         case 'W':  
    492 467                                 if (ntohl(f_cookie.pyvers) >= 21) {  
    493                                           PySys_AddWarnOption(&ptoc->name[2]);  
      468                                         PI_PySys_AddWarnOption(&ptoc->name[2]);  
    493 468                                 }  
    494 469                         break;  
    495 470 #endif  
    496 471                         case 's':  
    497   #if defined  WIN32  
    498 472                                 *Py_NoSiteFlag = 0;  
    499   #else  
    500                                   Py_NoSiteFlag = 0;  
    501   #endif  
    502 473                         break;  
    503 474                         case 'O':  
    504   #if defined  WIN32  
    505 475                                 *Py_OptimizeFlag = 1;  
    506   #else  
    507                                   Py_OptimizeFlag = 1;  
    508   #endif  
    509 476                         break;  
    510 477                         }  
     
    579 546         /* Start python. */  
    580 547         /* VS("Loading python\n"); */  
    581   #if defined  WIN32  
    582 548         *Py_NoSiteFlag = 1;     /* maybe changed to 0 by setRuntimeOptions() */  
    583   #else  
    584           Py_NoSiteFlag = 1;  
    585   #endif  
    586 549         setRuntimeOptions();  
    587           Py_SetProgramName(f_archivename); /*XXX*/  
    588           Py_Initialize();  
      550         PI_Py_SetProgramName(f_archivename); /*XXX*/  
      551         PI_Py_Initialize();  
    589 552  
    590 553         /* Set sys.path */  
     
    592 555         strcpy(tmp, f_homepath);  
    593 556         tmp[strlen(tmp)-1] = '\0';  
    594           PyRun_SimpleString("import sys\n");  
    595           PyRun_SimpleString("while sys.path:\n del sys.path[0]\n");  
      557         PI_PyRun_SimpleString("import sys\n");  
      558         PI_PyRun_SimpleString("while sys.path:\n del sys.path[0]\n");  
    596 559         sprintf(cmd, "sys.path.append('%s')", tmp);  
    597           PyRun_SimpleString (cmd);  
      560         PI_PyRun_SimpleString (cmd);  
    597 560         if (pathlen == 2) {  
    598 561                 strcpy(tmp, f_workpath);  
    599 562                 tmp[strlen(tmp)-1] = '\0';  
    600 563                 sprintf(cmd, "sys.path.insert(0, '%s')", tmp);  
    601                   PyRun_SimpleString(cmd);  
      564                 PI_PyRun_SimpleString(cmd);  
    601 564         }  
    602 565  
    603 566         /* Set argv[0] to be the archiveName */  
    604           py_argv = PyList_New(0);  
    605           val = Py_BuildValue("s", f_archivename);  
    606           PyList_Append(py_argv, val);  
      567         py_argv = PI_PyList_New(0);  
      568         val = PI_Py_BuildValue("s", f_archivename);  
      569         PI_PyList_Append(py_argv, val);  
    607 570         for (i = 1; i < argc; ++i) {  
    608                   val = Py_BuildValue ("s", argv[i]);  
    609                   PyList_Append (py_argv, val);  
      571                 val = PI_Py_BuildValue ("s", argv[i]);  
      572                 PI_PyList_Append (py_argv, val);  
    610 573         }  
    611           sys = PyImport_ImportModule("sys");  
      574         sys = PI_PyImport_ImportModule("sys");  
    611 574         /* VS("Setting sys.argv\n"); */  
    612           PyObject_SetAttrString(sys, "argv", py_argv);  
      575         PI_PyObject_SetAttrString(sys, "argv", py_argv);  
    612 575  
    613 576         /* Check for a python error */  
    614           if (PyErr_Occurred())  
      577         if (PI_PyErr_Occurred())  
    614 577         {  
    615 578                 FATALERROR("Error detected starting Python VM.");  
     
    633 596         PyObject *marshaldict;  
    634 597         PyObject *loadfunc;  
    635           PyObject *pyfile;  
    636 598         TOC *ptoc;  
    637 599         PyObject *co;  
    638 600         PyObject *mod;  
    639           PyObject *res;  
    640           char buf[32];  
    641 601  
    642 602         VS("importing modules from CArchive\n");  
     
    646 606                 * Doesn't matter because the objects won't be going away anyway.  
    647 607                 */  
    648           marshal = PyImport_ImportModule("marshal");  
    649           marshaldict = PyModule_GetDict(marshal);  
    650           loadfunc = PyDict_GetItemString(marshaldict, "loads");  
      608         marshal = PI_PyImport_ImportModule("marshal");  
      609         marshaldict = PI_PyModule_GetDict(marshal);  
      610         loadfunc = PI_PyDict_GetItemString(marshaldict, "loads");  
    651 611  
    652 612         /* Iterate through toc looking for module entries (type 'm')  
     
    662 622                          * string directly pointing at the marshalled code.  
    663 623                          */  
    664                           PyObject *mods = PyString_FromStringAndSize(modbuf + 8,  
      624                         PyObject *mods = PI_PyString_FromStringAndSize(modbuf + 8,  
    664 624                                 ntohl(ptoc->ulen) - 8);  
    665 625              
    666 626                         VS("%s\n", ptoc->name);  
    667 627                          
    668                           co = PyObject_CallFunction(loadfunc, "O", mods);  
    669                           mod = PyImport_ExecCodeModule(ptoc->name, co);  
      628                         co = PI_PyObject_CallFunction(loadfunc, "O", mods);  
      629                         mod = PI_PyImport_ExecCodeModule(ptoc->name, co);  
    670 630  
    671 631                         /* Check for errors in loading */  
     
    674 634                                 FATALERROR("mod is NULL - %s", ptoc->name);  
    675 635                         }  
    676                           if (PyErr_Occurred())  
      636                         if (PI_PyErr_Occurred())  
    676 636                         {  
    677                                   PyErr_Print();  
    678                                   PyErr_Clear();  
      637                                 PI_PyErr_Print();  
      638                                 PI_PyErr_Clear();  
    679 639                         }  
    680 640  
     
    701 661         sprintf(cmd, tmpl, f_archivename, zlibpos);  
    702 662         /*VS(cmd);*/  
    703           rc = PyRun_SimpleString(cmd);  
      663         rc = PI_PyRun_SimpleString(cmd);  
    703 663         if (rc != 0)  
    704 664         {  
     
    902 862                         data = extract(ptoc);  
    903 863                         /* Run it */  
    904                           rc = PyRun_SimpleString(data);  
      864                         rc = PI_PyRun_SimpleString(data);  
    904 864                         /* log errors and abort */  
    905 865                         if (rc != 0) {  
     
    930 890         PyObject *func = NULL, *pyresult = NULL;  
    931 891  
    932           mod = PyImport_AddModule("__main__"); /* NO ref added */  
      892         mod = PI_PyImport_AddModule("__main__"); /* NO ref added */  
    932 892         if (!mod) {  
    933 893                 VS("No __main__\n");  
    934 894                 goto done;  
    935 895         }  
    936           dict = PyModule_GetDict(mod); /* NO ref added */  
      896         dict = PI_PyModule_GetDict(mod); /* NO ref added */  
    936 896         if (!mod) {  
    937 897                 VS("No __dict__\n");  
    938 898                 goto done;  
    939 899         }  
    940           func = PyDict_GetItemString(dict, name);  
      900         func = PI_PyDict_GetItemString(dict, name);  
    940 900         if (func == NULL) { /* should explicitly check KeyError */  
    941 901                 VS("CallSimpleEntryPoint can't find the function name\n");  
     
    946 906                 goto done;  
    947 907         }  
    948           pyresult = PyObject_CallFunction(func, "");  
      908         pyresult = PI_PyObject_CallFunction(func, "");  
    948 908         if (pyresult==NULL) goto done;  
    949           PyErr_Clear();  
    950           *presult = PyInt_AsLong(pyresult);  
    951           rc = PyErr_Occurred() ? -1 : 0;  
      909         PI_PyErr_Clear();  
      910         *presult = PI_PyInt_AsLong(pyresult);  
      911         rc = PI_PyErr_Occurred() ? -1 : 0;  
    952 912         VS( rc ? "Finished with failure\n" : "Finished OK\n");  
    953 913         /* all done! */  
     
    960 920         if (rc)  
    961 921                 /* But we will print them 'cos they may be useful */  
    962                   PyErr_Print();  
    963           PyErr_Clear();  
      922                 PI_PyErr_Print();  
      923         PI_PyErr_Clear();  
    964 924         return rc;  
    965 925 }  
     
    995 955  
    996 956         /* a signal to scripts */  
    997           PyRun_SimpleString("import sys;sys.frozen='dll'\n");  
      957         PI_PyRun_SimpleString("import sys;sys.frozen='dll'\n");  
    997 957         VS("set sys.frozen\n");  
    998 958         /* Import modules from archive - this is to bootstrap */  
     
    1009 969                 return -1;  
    1010 970         VS("All scripts run\n");  
    1011           if (PyErr_Occurred()) {  
      971         if (PI_PyErr_Occurred()) {  
    1011 971                 /*PyErr_Clear();*/  
    1012 972                 VS("Some error occurred\n");  
     
    1024 984 int init(char const * archivePath, char  const * archiveName, char const * workpath)  
    1025 985 {  
      986 #ifdef WIN32  
    1026 987         char *p;  
      988 #endif  
    1027 989  
    1028 990         if (workpath) {  
     
    1170 1132 void finalizePython(void)  
    1171 1133 {  
    1172           Py_Finalize();  
      1134         PI_Py_Finalize();  
    1172 1134 }  
    1173 1135  
  • branches/dl/source/windows/dllmain.c

    r330 r406  
    71 71         if (loadedNew) {  
    72 72                 /* Start Python with silly command line */  
    73                   PyEval_InitThreads();  
      73                 PI_PyEval_InitThreads();  
    73 73                 if (startPython(1, (char**)&pathnm))  
    74 74                         return -1;  
    75 75                 VS("Started new Python");  
    76                   thisthread = PyThreadState_Swap(NULL);  
    77                   PyThreadState_Swap(thisthread);  
      76                 thisthread = PI_PyThreadState_Swap(NULL);  
      77                 PI_PyThreadState_Swap(thisthread);  
    78 78         }  
    79 79         else {  
     
    82 82  
    83 83                 /* start a mew interp */  
    84                   thisthread = PyThreadState_Swap(NULL);  
    85                   PyThreadState_Swap(thisthread);  
      84                 thisthread = PI_PyThreadState_Swap(NULL);  
      85                 PI_PyThreadState_Swap(thisthread);  
    86 86                 if (thisthread == NULL) {  
    87                           thisthread = Py_NewInterpreter();  
      87                         thisthread = PI_Py_NewInterpreter();  
    87 87                         VS("created thisthread");  
    88 88                 }  
    89 89                 else  
    90 90                         VS("grabbed thisthread");  
    91                   PyRun_SimpleString("import sys;sys.argv=[]");  
      91                 PI_PyRun_SimpleString("import sys;sys.argv=[]");  
    91 91         }  
    92 92  
    93 93         /* a signal to scripts */  
    94           PyRun_SimpleString("import sys;sys.frozen='dll'\n");  
      94         PI_PyRun_SimpleString("import sys;sys.frozen='dll'\n");  
    94 94         VS("set sys.frozen");  
    95 95         /* Create a 'frozendllhandle' as a counterpart to  
    96 96            sys.dllhandle (which is the Pythonxx.dll handle)  
    97 97         */  
    98           obHandle = Py_BuildValue("i", gInstance);  
    99           PySys_SetObject("frozendllhandle", obHandle);  
      98         obHandle = PI_Py_BuildValue("i", gInstance);  
      99         PI_PySys_SetObject("frozendllhandle", obHandle);  
    100 100         Py_XDECREF(obHandle);  
    101 101     /* Import modules from archive - this is to bootstrap */  
     
    114 114         return -1;  
    115 115         VS("All scripts run");  
    116       if (PyErr_Occurred()) {  
    117                   // PyErr_Print();  
    118                   //PyErr_Clear();  
      116     if (PI_PyErr_Occurred()) {  
      117                 // PI_PyErr_Print();  
      118                 //PI_PyErr_Clear();  
    119 119                 VS("Some error occurred");  
    120 120     }  
    121 121         VS("PGL released");  
    122 122         // Abandon our thread state.  
    123           PyEval_ReleaseThread(thisthread);  
      123         PI_PyEval_ReleaseThread(thisthread);  
    123 123     VS("OK.");  
    124 124     return 0;  
     
    263 263         if (gPythoncom == 0)  
    264 264                 startUp();  
    265           PyEval_AcquireThread(thisthread);  
      265         PI_PyEval_AcquireThread(thisthread);  
    265 265         rc = callSimpleEntryPoint("DllRegisterServer", &pyrc);  
    266           PyEval_ReleaseThread(thisthread);  
      266         PI_PyEval_ReleaseThread(thisthread);  
    266 266         return rc==0 ? pyrc : SELFREG_E_CLASS;  
    267 267 }  
     
    274 274         if (gPythoncom == 0)  
    275 275                 startUp();  
    276           PyEval_AcquireThread(thisthread);  
      276         PI_PyEval_AcquireThread(thisthread);  
    276 276         rc = callSimpleEntryPoint("DllUnregisterServer", &pyrc);  
    277           PyEval_ReleaseThread(thisthread);  
      277         PI_PyEval_ReleaseThread(thisthread);  
    277 277         return rc==0 ? pyrc : SELFREG_E_CLASS;  
    278 278 }