Welcome to mirror list, hosted at ThFree Co, Russian Federation.

git.blender.org/blender.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorCampbell Barton <ideasman42@gmail.com>2011-02-22 17:19:09 +0300
committerCampbell Barton <ideasman42@gmail.com>2011-02-22 17:19:09 +0300
commitbde2f962579853c9d3bb3a47b01f88ec6a9a3b63 (patch)
tree7205305a43e1b2f103929b2125962fcc81aca313 /source/blender/python/intern/bpy_interface.c
parent79f79e0cacd0dbf2b7202cdf929487b6825aa715 (diff)
blender as module - workaround for not knowing __file__ when the module is initialized.
Diffstat (limited to 'source/blender/python/intern/bpy_interface.c')
-rw-r--r--source/blender/python/intern/bpy_interface.c99
1 files changed, 71 insertions, 28 deletions
diff --git a/source/blender/python/intern/bpy_interface.c b/source/blender/python/intern/bpy_interface.c
index 9ed1865d70d..e14efc7edac 100644
--- a/source/blender/python/intern/bpy_interface.c
+++ b/source/blender/python/intern/bpy_interface.c
@@ -702,41 +702,84 @@ static struct PyModuleDef bpy_proxy_def = {
NULL, /* m_free */
};
-PyMODINIT_FUNC
-PyInit_bpy(void)
+typedef struct {
+ PyObject_HEAD
+ /* Type-specific fields go here. */
+ PyObject *mod;
+} dealloc_obj;
+
+/* call once __file__ is set */
+void bpy_module_delay_init(PyObject *bpy_proxy)
{
- int argc= 1;
- char *argv[2]={NULL, NULL};
+ const int argc= 1;
+ const char *argv[2];
- /* give the CWD as the first arg, blender uses */
- char path[240]= "";
- BLI_getwdN(path, sizeof(path));
- BLI_join_dirfile(path, sizeof(path), path, "bpy");
- argv[0]= path;
- /* done with cwd */
+ const char *filename_rel= PyModule_GetFilename(bpy_proxy); /* can be relative */
+ char filename_abs[1024];
+
+ BLI_strncpy(filename_abs, filename_rel, sizeof(filename_abs));
+ BLI_path_cwd(filename_abs);
+
+ argv[0]= filename_abs;
+ argv[1]= NULL;
+
+ // printf("module found %s\n", argv[0]);
main_python(argc, argv);
/* initialized in BPy_init_modules() */
- if(bpy_package_py) {
- /* Problem:
- * 1) this init function is expected to have a private member defined - 'md_def'
- * but this is only set for C defined modules (not py packages)
- * so we cant return 'bpy_package_py' as is.
- *
- * 2) there is a 'bpy' C module for python to load which is basically all of blender,
- * and there is scripts/bpy/__init__.py,
- * we may end up having to rename this module so there is no naming conflict here eg:
- * 'from blender import bpy' */
- PyObject *bpy_proxy= PyModule_Create(&bpy_proxy_def);
- PyDict_Update(PyModule_GetDict(bpy_proxy), PyModule_GetDict(bpy_package_py));
- return bpy_proxy;
- }
- else {
- PyErr_SetString(PyExc_RuntimeError, "could not import internal bpy package");
- return NULL;
- }
+ PyDict_Update(PyModule_GetDict(bpy_proxy), PyModule_GetDict(bpy_package_py));
+}
+
+static void dealloc_obj_dealloc(PyObject *self);
+
+static PyTypeObject dealloc_obj_Type = {{{0}}};
+
+/* use our own dealloc so we can free a property if we use one */
+static void dealloc_obj_dealloc(PyObject *self)
+{
+ bpy_module_delay_init(((dealloc_obj *)self)->mod);
+
+ /* Note, for subclassed PyObjects we cant just call PyObject_DEL() directly or it will crash */
+ dealloc_obj_Type.tp_free(self);
+}
+
+PyMODINIT_FUNC
+PyInit_bpy(void)
+{
+ PyObject *bpy_proxy= PyModule_Create(&bpy_proxy_def);
+
+ /* Problem:
+ * 1) this init function is expected to have a private member defined - 'md_def'
+ * but this is only set for C defined modules (not py packages)
+ * so we cant return 'bpy_package_py' as is.
+ *
+ * 2) there is a 'bpy' C module for python to load which is basically all of blender,
+ * and there is scripts/bpy/__init__.py,
+ * we may end up having to rename this module so there is no naming conflict here eg:
+ * 'from blender import bpy'
+ *
+ * 3) we dont know the filename at this point, workaround by assigning a dummy value
+ * which calls back when its freed so the real loading can take place.
+ */
+
+ /* assign an object which is freed after __file__ is assigned */
+ dealloc_obj *dob;
+ /* assign dummy type */
+ dealloc_obj_Type.tp_name = "dealloc_obj";
+ dealloc_obj_Type.tp_basicsize = sizeof(dealloc_obj);
+ dealloc_obj_Type.tp_dealloc = dealloc_obj_dealloc;
+ dealloc_obj_Type.tp_flags = Py_TPFLAGS_DEFAULT;
+ if(PyType_Ready(&dealloc_obj_Type) < 0)
+ return NULL;
+
+ dob= (dealloc_obj *) dealloc_obj_Type.tp_alloc(&dealloc_obj_Type, 0);
+ dob->mod= bpy_proxy; /* borrow */
+ PyModule_AddObject(bpy_proxy, "__file__", (PyObject *)dob); /* borrow */
+
+ return bpy_proxy;
}
+
#endif