Created
May 7, 2011 04:29
-
-
Save Hoikas/960200 to your computer and use it in GitHub Desktop.
PEP 302 Import Hook for External.Release
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
///////////////////////////////////////////////////////////////////////////// | |
// PEP 302 Import Hook | |
///////////////////////////////////////////////////////////////////////////// | |
#ifndef BUILDING_PYPLASMA | |
struct ptImportHook | |
{ | |
PyObject_HEAD | |
}; | |
// First three functions are just so I can be lazy | |
// and use the already existing macros to do my dirty | |
// work. I'm seriously lazy. | |
static PyObject* ptImportHook_new(PyTypeObject* type, PyObject* args, PyObject*) | |
{ | |
ptImportHook* self = (ptImportHook*)type->tp_alloc(type, 0); | |
return (PyObject*)self; | |
} | |
PYTHON_NO_INIT_DEFINITION(ptImportHook) | |
static void ptImportHook_dealloc(ptImportHook *self) | |
{ | |
self->ob_type->tp_free((PyObject*)self); | |
} | |
PYTHON_METHOD_DEFINITION(ptImportHook, find_module, args) | |
{ | |
char* module_name; | |
PyObject* module_path; // Ignored | |
if (!PyArg_ParseTuple(args, "s|O", &module_name, &module_path)) | |
{ | |
PyErr_SetString(PyExc_TypeError, "find_module expects string, string"); | |
PYTHON_RETURN_ERROR; | |
} | |
if (PythonPack::IsItPythonPacked(module_name)) | |
return (PyObject*)self; | |
else | |
PYTHON_RETURN_NONE; | |
} | |
PYTHON_METHOD_DEFINITION(ptImportHook, load_module, args) | |
{ | |
char* module_name; | |
if (!PyArg_ParseTuple(args, "s", &module_name)) | |
{ | |
PyErr_SetString(PyExc_TypeError, "load_module expects string"); | |
PYTHON_RETURN_ERROR; | |
} | |
// Grab sys.__dict__ so we can get started | |
PyObject* sys_mod = PyImport_ImportModule("sys"); | |
PyObject* sys_dict = PyModule_GetDict(sys_mod); | |
Py_INCREF(sys_dict); | |
// We want to check sys.modules for the module first | |
// If it's not in there, we have to load the module | |
// and add it to the sys.modules dict for future reference, | |
// otherwise reload() will not work properly. | |
PyObject* result = nil; | |
PyObject* modules = PyDict_GetItemString(sys_dict, "modules"); | |
Py_INCREF(modules); | |
hsAssert(PyDict_Check(modules), "sys.modules is not a dict"); | |
if (result = PyDict_GetItemString(modules, module_name)) | |
{ | |
if (!PyModule_Check(result)) | |
{ | |
hsAssert(false, "PEP 302 hook found module in sys.modules, but it isn't a module! O.o"); | |
result = nil; | |
PyErr_SetString(PyExc_TypeError, "module in sys.modules isn't a module"); | |
} | |
} | |
else | |
{ | |
if (result = PythonPack::OpenPythonPacked(module_name)) | |
{ | |
PyModule_AddStringConstant(result, "__name__", module_name); | |
PyModule_AddStringConstant(result, "__file__", module_name); | |
PyModule_AddObject(result, "__dict__", PyDict_New()); | |
PyDict_SetItemString(modules, module_name, result); | |
} | |
else | |
PyErr_SetString(PyExc_ImportError, "module not found in python.pak"); | |
} | |
Py_DECREF(modules); | |
Py_DECREF(sys_dict); | |
if (result) | |
return result; | |
else | |
PYTHON_RETURN_ERROR; | |
} | |
PYTHON_START_METHODS_TABLE(ptImportHook) | |
PYTHON_METHOD(ptImportHook, find_module, "Params: module_name,package_path\nChecks to see if a given module exists (NOTE: package_path is not used!)"), | |
PYTHON_METHOD(ptImportHook, load_module, "Params: module_name \\nReturns the module given by module_name, if it exists in python.pak"), | |
PYTHON_END_METHODS_TABLE; | |
PYTHON_TYPE_START(ptImportHook) | |
0, | |
"Plasma.ptImportHook", | |
sizeof(ptImportHook), /* tp_basicsize */ | |
0, /* tp_itemsize */ | |
(destructor)ptImportHook_dealloc, /* tp_dealloc */ | |
0, /* tp_print */ | |
0, /* tp_getattr */ | |
0, /* tp_setattr */ | |
0, /* tp_compare */ | |
0, /* tp_repr */ | |
0, /* tp_as_number */ | |
0, /* tp_as_sequence */ | |
0, /* tp_as_mapping */ | |
0, /* tp_hash */ | |
0, /* tp_call */ | |
0, /* tp_str */ | |
0, /* tp_getattro */ | |
0, /* tp_setattro */ | |
0, /* tp_as_buffer */ | |
Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, /* tp_flags */ | |
"PEP 302 Import Hook", /* tp_doc */ | |
0, /* tp_traverse */ | |
0, /* tp_clear */ | |
0, /* tp_richcompare */ | |
0, /* tp_weaklistoffset */ | |
0, /* tp_iter */ | |
0, /* tp_iternext */ | |
PYTHON_DEFAULT_METHODS_TABLE(ptImportHook), /* tp_methods */ | |
0, /* tp_members */ | |
0, /* tp_getset */ | |
0, /* tp_base */ | |
0, /* tp_dict */ | |
0, /* tp_descr_get */ | |
0, /* tp_descr_set */ | |
0, /* tp_dictoffset */ | |
PYTHON_DEFAULT_INIT(ptImportHook), /* tp_init */ | |
0, /* tp_alloc */ | |
ptImportHook_new /* tp_new */ | |
PYTHON_TYPE_END; | |
void ptImportHook_AddPlasmaClasses(PyObject* m) | |
{ | |
PYTHON_CLASS_IMPORT_START(m); | |
PYTHON_CLASS_IMPORT(m, ptImportHook); | |
PYTHON_CLASS_IMPORT_END(m); | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment