Commit 303dc53e authored by Robert Bradshaw's avatar Robert Bradshaw

Merge branch 'common-types' into pristine

parents 7aa4bfde baf76aac
......@@ -7236,7 +7236,7 @@ class PyCFunctionNode(ExprNode, ModuleNameMixin):
flags = '0'
code.putln(
'%s = %s(&%s, %s, %s, %s, %s, %s); %s' % (
'%s = %s(&%s, %s, %s, %s, %s, %s, %s); %s' % (
self.result(),
constructor,
self.pymethdef_cname,
......@@ -7244,6 +7244,7 @@ class PyCFunctionNode(ExprNode, ModuleNameMixin):
self.get_py_qualified_name(code),
self.self_result_code(),
self.get_py_mod_name(code),
"PyModule_GetDict(%s)" % Naming.module_cname,
code_object_result,
code.error_goto_if_null(self.result(), self.pos)))
......
......@@ -532,6 +532,9 @@ class ModuleNode(Nodes.Node, Nodes.BlockNode):
code.putln(" #error Cython requires Python 2.4+.")
code.putln("#else")
code.globalstate["end"].putln("#endif /* Py_PYTHON_H */")
from Cython import __version__
code.putln('#define CYTHON_ABI "%s"' % __version__.replace('.', '_'))
code.put(UtilityCode.load_as_string("CModulePreamble", "ModuleSetupCode.c")[1])
......
/////////////// FetchCommonType.proto ///////////////
static PyTypeObject* __Pyx_FetchCommonType(PyTypeObject* type);
/////////////// FetchCommonType ///////////////
static PyTypeObject* __Pyx_FetchCommonType(PyTypeObject* type) {
static PyObject* fake_module = NULL;
PyObject* args = NULL;
PyTypeObject* cached_type = NULL;
const char* cython_module = "_cython_" CYTHON_ABI;
if (fake_module == NULL) {
PyObject* sys_modules = PyImport_GetModuleDict(); // borrowed
fake_module = PyDict_GetItemString(sys_modules, cython_module); // borrowed
if (fake_module != NULL) {
Py_INCREF(fake_module);
} else {
PyObject* py_cython_module;
args = PyTuple_New(1); if (args == NULL) goto bad;
#if PY_MAJOR_VERSION >= 3
py_cython_module = PyUnicode_DecodeUTF8(cython_module, strlen(cython_module), NULL);
#else
py_cython_module = PyBytes_FromString(cython_module);
#endif
if (py_cython_module == NULL) goto bad;
PyTuple_SET_ITEM(args, 0, py_cython_module);
fake_module = PyObject_Call((PyObject*) &PyModule_Type, args, NULL);
if (PyDict_SetItemString(sys_modules, cython_module, fake_module) < 0)
goto bad;
}
}
if (PyObject_HasAttrString(fake_module, type->tp_name)) {
cached_type = (PyTypeObject*) PyObject_GetAttrString(fake_module, type->tp_name);
} else {
if (PyType_Ready(type) < 0) goto bad;
if (PyObject_SetAttrString(fake_module, type->tp_name, (PyObject*) type) < 0)
goto bad;
cached_type = type;
}
cleanup:
Py_XDECREF(args);
return cached_type;
bad:
cached_type = NULL;
goto cleanup;
}
......@@ -27,6 +27,7 @@ typedef struct {
PyObject *func_name;
PyObject *func_qualname;
PyObject *func_doc;
PyObject *func_globals;
PyObject *func_code;
PyObject *func_closure;
PyObject *func_classobj; /* No-args super() class cell */
......@@ -44,12 +45,13 @@ typedef struct {
static PyTypeObject *__pyx_CyFunctionType = 0;
#define __Pyx_CyFunction_NewEx(ml, flags, qualname, self, module, code) \
__Pyx_CyFunction_New(__pyx_CyFunctionType, ml, flags, qualname, self, module, code)
#define __Pyx_CyFunction_NewEx(ml, flags, qualname, self, module, globals, code) \
__Pyx_CyFunction_New(__pyx_CyFunctionType, ml, flags, qualname, self, module, globals, code)
static PyObject *__Pyx_CyFunction_New(PyTypeObject *, PyMethodDef *ml,
int flags, PyObject* qualname,
PyObject *self, PyObject *module,
PyObject *self,
PyObject *module, PyObject *globals,
PyObject* code);
static CYTHON_INLINE void *__Pyx_CyFunction_InitDefaults(PyObject *m,
......@@ -67,6 +69,7 @@ static int __Pyx_CyFunction_init(void);
//////////////////// CythonFunction ////////////////////
//@substitute: naming
//@requires: CommonTypes.c::FetchCommonType
static PyObject *
__Pyx_CyFunction_get_doc(__pyx_CyFunctionObject *op, CYTHON_UNUSED void *closure)
......@@ -212,18 +215,11 @@ __Pyx_CyFunction_set_dict(__pyx_CyFunctionObject *op, PyObject *value)
return 0;
}
// TODO: we implicitly use the global module to get func_globals. This
// will need to be passed into __Pyx_CyFunction_NewEx() if we share
// this type across modules. We currently avoid doing this to reduce
// the overhead of creating a function object, and to avoid keeping a
// reference to the module dict as long as we don't need to.
static PyObject *
__Pyx_CyFunction_get_globals(CYTHON_UNUSED __pyx_CyFunctionObject *op)
__Pyx_CyFunction_get_globals(__pyx_CyFunctionObject *op)
{
PyObject* dict = PyModule_GetDict(${module_cname});
Py_XINCREF(dict);
return dict;
Py_INCREF(op->func_globals);
return op->func_globals;
}
static PyObject *
......@@ -399,7 +395,7 @@ static PyMethodDef __pyx_CyFunction_methods[] = {
static PyObject *__Pyx_CyFunction_New(PyTypeObject *type, PyMethodDef *ml, int flags, PyObject* qualname,
PyObject *closure, PyObject *module, PyObject* code) {
PyObject *closure, PyObject *module, PyObject* globals, PyObject* code) {
__pyx_CyFunctionObject *op = PyObject_GC_New(__pyx_CyFunctionObject, type);
if (op == NULL)
return NULL;
......@@ -417,6 +413,8 @@ static PyObject *__Pyx_CyFunction_New(PyTypeObject *type, PyMethodDef *ml, int f
op->func_qualname = qualname;
op->func_doc = NULL;
op->func_classobj = NULL;
op->func_globals = globals;
Py_INCREF(op->func_globals);
Py_XINCREF(code);
op->func_code = code;
/* Dynamic Default args */
......@@ -439,6 +437,7 @@ __Pyx_CyFunction_clear(__pyx_CyFunctionObject *m)
Py_CLEAR(m->func_name);
Py_CLEAR(m->func_qualname);
Py_CLEAR(m->func_doc);
Py_CLEAR(m->func_globals);
Py_CLEAR(m->func_code);
Py_CLEAR(m->func_classobj);
Py_CLEAR(m->defaults_tuple);
......@@ -476,6 +475,7 @@ static int __Pyx_CyFunction_traverse(__pyx_CyFunctionObject *m, visitproc visit,
Py_VISIT(m->func_name);
Py_VISIT(m->func_qualname);
Py_VISIT(m->func_doc);
Py_VISIT(m->func_globals);
Py_VISIT(m->func_code);
Py_VISIT(m->func_classobj);
Py_VISIT(m->defaults_tuple);
......@@ -645,9 +645,10 @@ static int __Pyx_CyFunction_init(void) {
// avoid a useless level of call indirection
__pyx_CyFunctionType_type.tp_call = PyCFunction_Call;
#endif
if (PyType_Ready(&__pyx_CyFunctionType_type) < 0)
__pyx_CyFunctionType = __Pyx_FetchCommonType(&__pyx_CyFunctionType_type);
if (__pyx_CyFunctionType == NULL) {
return -1;
__pyx_CyFunctionType = &__pyx_CyFunctionType_type;
}
return 0;
}
......@@ -706,11 +707,12 @@ typedef struct {
PyObject *self;
} __pyx_FusedFunctionObject;
#define __pyx_FusedFunction_NewEx(ml, flags, qualname, self, module, code) \
__pyx_FusedFunction_New(__pyx_FusedFunctionType, ml, flags, qualname, self, module, code)
#define __pyx_FusedFunction_NewEx(ml, flags, qualname, self, module, globals, code) \
__pyx_FusedFunction_New(__pyx_FusedFunctionType, ml, flags, qualname, self, module, globals, code)
static PyObject *__pyx_FusedFunction_New(PyTypeObject *type,
PyMethodDef *ml, int flags,
PyObject *qualname, PyObject *self, PyObject *module,
PyObject *qualname, PyObject *self,
PyObject *module, PyObject *globals,
PyObject *code);
static int __pyx_FusedFunction_clear(__pyx_FusedFunctionObject *self);
......@@ -725,11 +727,12 @@ static int __pyx_FusedFunction_init(void);
static PyObject *
__pyx_FusedFunction_New(PyTypeObject *type, PyMethodDef *ml, int flags,
PyObject *qualname, PyObject *self,
PyObject *module, PyObject *code)
PyObject *module, PyObject *globals,
PyObject *code)
{
__pyx_FusedFunctionObject *fusedfunc =
(__pyx_FusedFunctionObject *) __Pyx_CyFunction_New(type, ml, flags, qualname,
self, module, code);
self, module, globals, code);
if (!fusedfunc)
return NULL;
......@@ -787,6 +790,7 @@ __pyx_FusedFunction_descr_get(PyObject *self, PyObject *obj, PyObject *type)
((__pyx_CyFunctionObject *) func)->func_qualname,
((__pyx_CyFunctionObject *) func)->func_closure,
((PyCFunctionObject *) func)->m_module,
((__pyx_CyFunctionObject *) func)->func_globals,
((__pyx_CyFunctionObject *) func)->func_code);
if (!meth)
return NULL;
......@@ -1088,10 +1092,10 @@ static PyTypeObject __pyx_FusedFunctionType_type = {
};
static int __pyx_FusedFunction_init(void) {
if (PyType_Ready(&__pyx_FusedFunctionType_type) < 0) {
__pyx_FusedFunctionType = __Pyx_FetchCommonType(&__pyx_FusedFunctionType_type);
if (__pyx_FusedFunctionType == NULL) {
return -1;
}
__pyx_FusedFunctionType = &__pyx_FusedFunctionType_type;
return 0;
}
......
......@@ -57,6 +57,7 @@ static int __Pyx_PyGen_FetchStopIterationValue(PyObject **pvalue);
//@requires: Exceptions.c::SwapException
//@requires: Exceptions.c::RaiseException
//@requires: ObjectHandling.c::PyObjectCallMethod
//@requires: CommonTypes.c::FetchCommonType
static PyObject *__Pyx_Generator_Next(PyObject *self);
static PyObject *__Pyx_Generator_Send(PyObject *self, PyObject *value);
......@@ -653,9 +654,10 @@ static int __pyx_Generator_init(void) {
/* on Windows, C-API functions can't be used in slots statically */
__pyx_GeneratorType_type.tp_getattro = PyObject_GenericGetAttr;
__pyx_GeneratorType_type.tp_iter = PyObject_SelfIter;
if (PyType_Ready(&__pyx_GeneratorType_type)) {
__pyx_GeneratorType = __Pyx_FetchCommonType(&__pyx_GeneratorType_type);
if (__pyx_GeneratorType == NULL) {
return -1;
}
__pyx_GeneratorType = &__pyx_GeneratorType_type;
return 0;
}
PYTHON setup.py build_ext --inplace
PYTHON -c "import runner"
######## setup.py ########
from Cython.Build.Dependencies import cythonize
from distutils.core import setup
setup(
ext_modules = cythonize("*.pyx"),
)
######## a.pyx ########
# cython: binding=True
def funcA():
return
######## b.pyx ########
# cython: binding=True
def funcB():
return
######## runner.py ########
print("importing...")
import a, b
print(type(a.funcA))
assert type(a.funcA).__name__ == 'cython_function_or_method'
assert type(a.funcA) is type(b.funcB)
assert a.funcA.func_globals is a.__dict__
assert b.funcB.func_globals is b.__dict__
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment