diff options
author | Gustavo J. A. M. Carneiro <gjc@src.gnome.org> | 2007-04-14 16:21:15 +0000 |
---|---|---|
committer | Gustavo J. A. M. Carneiro <gjc@src.gnome.org> | 2007-04-14 16:21:15 +0000 |
commit | c292a0d1aaa9b6f68ec2a089d3b91914daf49ef9 (patch) | |
tree | d7f12c0cc9c8e20cc390481a7fb77e3b7cd71a10 | |
parent | 66cec4c99c32016388e8c968284f72c8bdbd0e62 (diff) | |
download | pygobject-c292a0d1aaa9b6f68ec2a089d3b91914daf49ef9.tar.gz pygobject-c292a0d1aaa9b6f68ec2a089d3b91914daf49ef9.tar.xz pygobject-c292a0d1aaa9b6f68ec2a089d3b91914daf49ef9.zip |
Bug 419379 – Modernize init_pygobject: use static inline functions instead of macros
svn path=/trunk/; revision=643
-rw-r--r-- | ChangeLog | 3 | ||||
-rw-r--r-- | gobject/pygobject.h | 140 |
2 files changed, 100 insertions, 43 deletions
@@ -1,5 +1,8 @@ 2007-04-14 Gustavo J. A. M. Carneiro <gjc@gnome.org> + * gobject/pygobject.h: Bug #419379: Modernize init_pygobject: use + static inline functions instead of macros. + * gobject/gobjectmodule.c (init_gobject): * gobject/pygobject-private.h: * gobject/pygobject.c (pygobject_data_free, pygobject_data_new), diff --git a/gobject/pygobject.h b/gobject/pygobject.h index 71c7853..045f53a 100644 --- a/gobject/pygobject.h +++ b/gobject/pygobject.h @@ -278,53 +278,107 @@ struct _PyGObject_Functions *_PyGObject_API; PyEval_RestoreThread(_save); \ } G_STMT_END -#define init_pygobject() G_STMT_START { \ - PyObject *gobject = PyImport_ImportModule("gobject"); \ - if (gobject != NULL) { \ - PyObject *mdict = PyModule_GetDict(gobject); \ - PyObject *cobject = PyDict_GetItemString(mdict, "_PyGObject_API"); \ - if (PyCObject_Check(cobject)) \ - _PyGObject_API = (struct _PyGObject_Functions *)PyCObject_AsVoidPtr(cobject); \ - else { \ - PyErr_SetString(PyExc_RuntimeError, \ - "could not find _PyGObject_API object"); \ - return; \ - } \ - } else { \ - PyErr_SetString(PyExc_ImportError, \ - "could not import gobject"); \ - return; \ - } \ + +/** + * pygobject_init: + * @req_major: minimum version major number, or -1 + * @req_minor: minimum version minor number, or -1 + * @req_micro: minimum version micro number, or -1 + * + * Imports and initializes the 'gobject' python module. Can + * optionally check for a required minimum version if @req_major, + * @req_minor, and @req_micro are all different from -1. + * + * Returns: a new reference to the gobject module on success, NULL in + * case of failure (and raises ImportError). + **/ +static inline PyObject * +pygobject_init(int req_major, int req_minor, int req_micro) +{ + PyObject *gobject, *cobject; + + gobject = PyImport_ImportModule("gobject"); + if (!gobject) { + if (PyErr_Occurred()) + { + PyObject *type, *value, *traceback; + PyObject *py_orig_exc; + PyErr_Fetch(&type, &value, &traceback); + py_orig_exc = PyObject_Repr(value); + Py_XDECREF(type); + Py_XDECREF(value); + Py_XDECREF(traceback); + PyErr_Format(PyExc_ImportError, + "could not import gobject (error was: %s)", + PyString_AsString(py_orig_exc)); + Py_DECREF(py_orig_exc); + } else { + PyErr_SetString(PyExc_ImportError, + "could not import gobject (no error given)"); + } + return NULL; + } + + cobject = PyObject_GetAttrString(gobject, "_PyGObject_API"); + if (cobject && PyCObject_Check(cobject)) + _PyGObject_API = (struct _PyGObject_Functions *) PyCObject_AsVoidPtr(cobject); + else { + PyErr_SetString(PyExc_ImportError, + "could not import gobject (could not find _PyGObject_API object)"); + Py_DECREF(gobject); + return NULL; + } + + if (req_major != -1) + { + int found_major, found_minor, found_micro; + PyObject *version; + + version = PyObject_GetAttrString(gobject, "pygobject_version"); + if (!version) + version = PyObject_GetAttrString(gobject, "pygtk_version"); + if (!version) { + PyErr_SetString(PyExc_ImportError, + "could not import gobject (version too old)"); + Py_DECREF(gobject); + return NULL; + } + if (!PyArg_ParseTuple(version, "iii", + &found_major, &found_minor, &found_micro)) { + PyErr_SetString(PyExc_ImportError, + "could not import gobject (version has invalid format)"); + Py_DECREF(version); + Py_DECREF(gobject); + return NULL; + } + Py_DECREF(version); + if (req_major != found_major || + req_minor > found_minor || + (req_minor == found_minor && req_micro > found_micro)) { + PyErr_Format(PyExc_ImportError, + "could not import gobject (version mismatch, %d.%d.%d is required, " + "found %d.%d.%d)", req_major, req_minor, req_micro, + found_major, found_minor, found_micro); + Py_DECREF(gobject); + return NULL; + } + } + return gobject; +} + +/* deprecated macro, use pygobject_init() instead. */ +#define init_pygobject() G_STMT_START { \ + if (!pygobject_init(-1, -1, -1)) \ + return; \ } G_STMT_END -#define init_pygobject_check(req_major, req_minor, req_micro) G_STMT_START { \ - PyObject *gobject, *mdict, *version; \ - int found_major, found_minor, found_micro; \ - init_pygobject(); \ - gobject = PyImport_ImportModule("gobject"); \ - mdict = PyModule_GetDict(gobject); \ - version = PyDict_GetItemString(mdict, "pygobject_version"); \ - if (!version) \ - version = PyDict_GetItemString(mdict, "pygtk_version"); \ - if (!version) { \ - PyErr_SetString(PyExc_ImportError, \ - "PyGObject version too old"); \ - return; \ - } \ - if (!PyArg_ParseTuple(version, "iii", \ - &found_major, &found_minor, &found_micro)) \ - return; \ - if (req_major != found_major || \ - req_minor > found_minor || \ - (req_minor == found_minor && req_micro > found_micro)) { \ - PyErr_Format(PyExc_ImportError, \ - "PyGObject version mismatch, %d.%d.%d is required, " \ - "found %d.%d.%d.", req_major, req_minor, req_micro, \ - found_major, found_minor, found_micro); \ - return; \ - } \ +/* deprecated macro, use pygobject_init() instead. */ +#define init_pygobject_check(req_major, req_minor, req_micro) G_STMT_START { \ + if (!pygobject_init(req_major, req_minor, req_micro)) \ + return; \ } G_STMT_END + #endif /* !_INSIDE_PYGOBJECT_ */ G_END_DECLS |