diff --git a/packages/python/py2pl.c b/packages/python/py2pl.c index 2b4ace5c4..e708cd7b0 100644 --- a/packages/python/py2pl.c +++ b/packages/python/py2pl.c @@ -1,5 +1,55 @@ #include "py4yap.h" +#include + +void YAPPy_ThrowError__(const char *file, const char *function, int lineno, + yap_error_number type, term_t where, ...) { + va_list ap; + char tmpbuf[MAXPATHLEN]; + YAP_Term wheret = YAP_GetFromSlot(where); + + if (PyErr_Occurred()) { + PyErr_Print(); + } else { + PyObject *ptype, *pvalue, *ptraceback; + PyObject *pystr, *module_name, *pyth_module, *pyth_func; + + /* See if we can get a full traceback */ + module_name = PyUnicode_FromString("traceback"); + pyth_module = PyImport_Import(module_name); + Py_DECREF(module_name); + + if (pyth_module != NULL) { + pyth_func = PyObject_GetAttrString(pyth_module, "format_exception"); + if (pyth_func && PyCallable_Check(pyth_func)) { + PyObject *pyth_val; + + pyth_val = PyObject_CallFunctionObjArgs(pyth_func, ptype, pvalue, ptraceback, NULL); + + pystr = PyObject_Str(pyth_val); + fprintf(stderr, "%s", PyUnicode_AsUTF8(pystr)); + Py_DECREF(pyth_val); + } + } + } + PyFrameObject *fr; + if ((fr = PyEval_GetFrame())) { + fprintf(stderr, "at frame %p, line %d\n", fr, PyFrame_GetLineNumber(fr)); + } + va_start(ap, where); + char *format = va_arg(ap, char *); + if (format != NULL) { +#if HAVE_VSNPRINTF + (void)vsnprintf(tmpbuf, MAXPATHLEN - 1, format, ap); +#else + (void)vsprintf(tnpbuf, format, ap); +#endif + // fprintf(stderr, "warning: "); + Yap_ThrowError__(file, function, lineno, type, wheret, tmpbuf); + } else { + Yap_ThrowError__(file, function, lineno, type, wheret); + } +} static foreign_t repr_term(PyObject *pVal, term_t t) { term_t to = PL_new_term_ref(), t1 = PL_new_term_ref(); diff --git a/packages/python/py4yap.h b/packages/python/py4yap.h index 1e3ddb0de..2e6d747bc 100644 --- a/packages/python/py4yap.h +++ b/packages/python/py4yap.h @@ -197,4 +197,9 @@ extern PyObject *PythonLookup(const char *s, PyObject *o); extern PyObject *PythonLookupSpecial(const char *s); +#define YAPPy_ThrowError(id, inp, ...) \ +YAPPy_ThrowError__(__FILE__, __FUNCTION__, __LINE__, id, inp, __VA_ARGS__) + +extern void YAPPy_ThrowError__(const char *file, const char *function, int lineno, + yap_error_number type, term_t where, ...); #endif diff --git a/packages/python/pybips.c b/packages/python/pybips.c index f0e59b75c..732eca6cf 100644 --- a/packages/python/pybips.c +++ b/packages/python/pybips.c @@ -698,7 +698,7 @@ static PyObject *structseq_repr(PyObject *iobj) { PyObject *term_to_nametuple(const char *s, arity_t arity, PyObject *tuple) { PyObject *o; -#if PY_MAJOR_VERSION >= 3 +#if PY_MAJOR_VERSION >= 30 PyTypeObject *typp; PyObject *key = PyUnicode_FromString(s); if (py_F2P && PyDict_Contains(py_F2P, key)) { @@ -716,17 +716,20 @@ PyObject *term_to_nametuple(const char *s, arity_t arity, PyObject *tuple) { desc->n_in_sequence = arity; if (PyStructSequence_InitType2(typp, desc) < 0) return NULL; - typp->tp_flags &= ~Py_TPFLAGS_HEAPTYPE; + // typp->tp_flags &= ~Py_TPFLAGS_HEAPTYPE; + // typp->tp_flags &= ~Py_TPFLAGS_HAVE_GC; // typp->tp_str = structseq_str; typp->tp_repr = structseq_repr; // typp = PyStructSequence_NewType(desc); // don't do this: we cannot add a type as an atribute. - // PyModule_AddObject(py_Main, s, (PyObject *)typp); + // PyModule_AddGObject(py_Main, s, (PyObject *)typp); if (py_F2P) PyDict_SetItem(py_F2P, key, (PyObject *)typp); Py_INCREF(typp); } o = PyStructSequence_New(typp); + Py_INCREF(typp); + fprintf(stderr, "<<< %p\n",typp); arity_t i; for (i = 0; i < arity; i++) { PyObject *pArg = PyTuple_GET_ITEM(tuple, i); diff --git a/packages/python/python.c b/packages/python/python.c index 9899b1161..8cc7ffd71 100644 --- a/packages/python/python.c +++ b/packages/python/python.c @@ -125,8 +125,7 @@ static void add_modules(void) { py_Yapex = PyImport_AddModule("yap4py.yapi"); if (py_Yapex) Py_INCREF(py_Yapex); - //py_F2P = PyObject_GetAttrString(py_Yap, "globals"); - py_F2P = NULL; + py_F2P = PyDict_New(); init_python_stream(); }