From ce583a69951bf9a94ca46bcf9f598cdc94b80e29 Mon Sep 17 00:00:00 2001 From: Cyrille Bagard Date: Mon, 28 Jan 2019 23:41:41 +0100 Subject: Improved handling of NotImplemented exceptions for Python calls. --- plugins/pychrysalide/helpers.c | 78 +++++++++++++++++++++++++----------------- plugins/pychrysalide/helpers.h | 3 -- 2 files changed, 46 insertions(+), 35 deletions(-) diff --git a/plugins/pychrysalide/helpers.c b/plugins/pychrysalide/helpers.c index d4c56e8..a0aa5e7 100644 --- a/plugins/pychrysalide/helpers.c +++ b/plugins/pychrysalide/helpers.c @@ -28,6 +28,7 @@ #include #include #include +#include #include @@ -48,6 +49,14 @@ static bool include_python_type_into_features(PyObject *, PyTypeObject *); +/* --------------------------- CONFORTS CIBLANT PYGOBJECT --------------------------- */ + + +/* Message d'erreur affiché puis recherché. */ +#define NOT_IMPLEMENTED_MSG _("Chrysalide method implementation is missing") + + + /* ---------------------------------------------------------------------------------- */ /* ACCELERATEURS POUR PYTHON UNIQUEMENT */ /* ---------------------------------------------------------------------------------- */ @@ -190,8 +199,9 @@ bool has_python_method(PyObject *module, const char *method) /****************************************************************************** * * -* Paramètres : func = fonction Python à appeler. * -* args = arguments à associer à l'opération. * +* Paramètres : target = propriétaire de la routine visée. * +* method = désignation de la fonction à appeler. * +* args = arguments à associer à l'opération. * * * * Description : Appelle une routine Python. * * * @@ -201,51 +211,55 @@ bool has_python_method(PyObject *module, const char *method) * * ******************************************************************************/ -PyObject *_run_python_method(PyObject *func, PyObject *args) +PyObject *run_python_method(PyObject *module, const char *method, PyObject *args) { PyObject *result; /* Bilan à retourner */ + PyObject *func; /* Fonction visée */ + PyObject *type; /* Type d'exception levée */ + PyObject *value; /* Détails particuliers */ + PyObject *traceback; /* Pile d'appels de l'exception*/ + PyObject *refmsg; /* Message de référence */ + + /* Exécution */ result = NULL; + func = PyObject_GetAttrString(module, method); + if (func == NULL) goto check_error; + if (PyCallable_Check(func)) - { result = PyObject_CallObject(func, args); - if (result == NULL) PyErr_Print(); - } - else if (PyErr_Occurred()) PyErr_Print(); - return result; + Py_DECREF(func); -} + /* Répercutions */ + check_error: -/****************************************************************************** -* * -* Paramètres : target = propriétaire de la routine visée. * -* method = désignation de la fonction à appeler. * -* args = arguments à associer à l'opération. * -* * -* Description : Appelle une routine Python. * -* * -* Retour : Retour obtenu ou NULL si erreur. * -* * -* Remarques : - * -* * -******************************************************************************/ + PyErr_Fetch(&type, &value, &traceback); -PyObject *run_python_method(PyObject *module, const char *method, PyObject *args) -{ - PyObject *result; /* Bilan à retourner */ - PyObject *func; /* Fonction visée */ + if (type != NULL && type == PyExc_NotImplementedError \ + && value != NULL && PyUnicode_Check(value) == 1) + { + refmsg = PyUnicode_FromString(NOT_IMPLEMENTED_MSG); - result = NULL; + if (PyUnicode_Compare(value, refmsg) == 0) + { + Py_DECREF(value); + value = PyUnicode_FromFormat(_("method implementation is missing for '%s'"), method); + } - func = PyObject_GetAttrString(module, method); - if (func == NULL) return NULL; + Py_DECREF(refmsg); - result = _run_python_method(func, args); + } - Py_DECREF(func); + PyErr_Restore(type, value, traceback); + + if (result == NULL && PyErr_Occurred() != NULL) + PyErr_Print(); + + if (result == NULL) + Py_Exit(EXIT_FAILURE); return result; @@ -547,7 +561,7 @@ PyObject *not_yet_implemented_method(PyObject *self, PyObject *args) result = NULL; - PyErr_SetString(PyExc_NotImplementedError, _("Implementated method is missing")); + PyErr_SetString(PyExc_NotImplementedError, NOT_IMPLEMENTED_MSG); return result; diff --git a/plugins/pychrysalide/helpers.h b/plugins/pychrysalide/helpers.h index ffbfe30..edc6686 100644 --- a/plugins/pychrysalide/helpers.h +++ b/plugins/pychrysalide/helpers.h @@ -45,9 +45,6 @@ int convert_to_callable(PyObject *, void *); bool has_python_method(PyObject *, const char *); /* Appelle une routine Python. */ -PyObject *_run_python_method(PyObject *, PyObject *); - -/* Appelle une routine Python. */ PyObject *run_python_method(PyObject *, const char *, PyObject *); /* Ajoute une constante au dictionnaire d'un type Python donné. */ -- cgit v0.11.2-87-g4458