BALTRAD PPC
pyppc_compat.h
Go to the documentation of this file.
1/* --------------------------------------------------------------------
2Copyright (C) 2019 Swedish Meteorological and Hydrological Institute, SMHI,
3
4This file is part of baltrad-ppc.
5
6baltrad-ppc is free software: you can redistribute it and/or modify
7it under the terms of the GNU Lesser General Public License as published by
8the Free Software Foundation, either version 3 of the License, or
9(at your option) any later version.
10
11baltrad-ppc is distributed in the hope that it will be useful,
12but WITHOUT ANY WARRANTY; without even the implied warranty of
13MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14GNU Lesser General Public License for more details.
15
16You should have received a copy of the GNU Lesser General Public License
17along with baltrad-ppc. If not, see <http://www.gnu.org/licenses/>.
18------------------------------------------------------------------------*/
26/* Define this to ensure that we are not using old API:s from Numpy. However, for now we are more interested in getting the
27 * code to build on both 2.7 and 3.x
28 */
29/*
30 * #define NPY_NO_DEPRECATED_API NPY_1_7_API_VERSION
31 */
32#include "Python.h"
33
34#ifndef PYPPCCOMPAT_H
35#define PYPPCCOMPAT_H
36
37
38#ifndef PyInt_Check
39#define PyInt_Check PyLong_Check
40#define PyInt_FromLong PyLong_FromLong
41#define PyInt_AsLong PyLong_AsLong
42#define PyInt_Type PyLong_Type
43#endif
44
45#ifndef PyString_Check
46#define PyString_Check PyUnicode_Check
47#define PyString_AsString PyUnicode_AsUTF8
48#define PyString_FromString PyUnicode_FromString
49#define PyString_FromFormat PyUnicode_FromFormat
50#endif
51
52#if PY_MAJOR_VERSION >= 3
53#define PY_RAVE_ATTRO_NAME_TO_STRING PyUnicode_AsUTF8
54
55#else
56#define PY_RAVE_ATTRO_NAME_TO_STRING PyString_AsString
57
58#endif
59
60#define PY_COMPARE_ATTRO_NAME_WITH_STRING(ptr, name) PyPpcAPI_CompareWithASCIIString(ptr, name)
61
62#define PY_COMPARE_STRING_WITH_ATTRO_NAME(name, ptr) PyPpcAPI_CompareWithASCIIString(ptr, name)
63
64#if PY_MAJOR_VERSION >= 3
65#define MOD_INIT_ERROR NULL
66#define MOD_INIT_SUCCESS(val) val
67#define MOD_INIT(name) PyMODINIT_FUNC PyInit_##name(void)
68#define MOD_INIT_DEF(ob, name, doc, methods) \
69 static struct PyModuleDef moduledef = { \
70 PyModuleDef_HEAD_INIT, name, doc, -1, methods, }; \
71 ob = PyModule_Create(&moduledef);
72
73#if PY_VERSION_HEX < 0x030900A4 && !defined(Py_SET_TYPE)
74static inline void _Py_SET_TYPE(PyObject *ob, PyTypeObject *type)
75{ ob->ob_type = type; }
76#define Py_SET_TYPE(ob, type) _Py_SET_TYPE((PyObject*)(ob), type)
77#endif
78
79#define MOD_INIT_CREATE_CAPI(ptr, name) PyCapsule_New(ptr, name, NULL)
80#define MOD_INIT_IS_CAPI(ptr) PyCapsule_CheckExact(ptr)
81#define MOD_INIT_GET_CAPI(ptr, name) PyCapsule_GetPointer(ptr, name)
82#define MOD_INIT_SETUP_TYPE(itype, otype) Py_SET_TYPE(&itype, otype)
83#define MOD_INIT_VERIFY_TYPE_READY(type) if (PyType_Ready(type) < 0) return MOD_INIT_ERROR
84
85#else
86#define MOD_INIT_ERROR
87#define MOD_INIT_SUCCESS(val)
88#define MOD_INIT(name) void init##name(void)
89#define MOD_INIT_DEF(ob, name, doc, methods) \
90 ob = Py_InitModule3(name, methods, doc);
91#define MOD_INIT_CREATE_CAPI(ptr, name) PyCObject_FromVoidPtr(ptr, name)
92#define MOD_INIT_IS_CAPI(ptr) PyCObject_Check(ptr)
93#define MOD_INIT_GET_CAPI(ptr, name) PyCObject_AsVoidPtr(ptr)
94#define MOD_INIT_SETUP_TYPE(itype, otype) itype.ob_type = otype
95#define MOD_INIT_VERIFY_TYPE_READY(type)
96#endif
97
101#define MOD_DIR_FORWARD_DECLARE(name) static PyObject* _##name##__dir__(name *self)
102
103#define MOD_DIR_REFERENCE(name) _##name##__dir__
104
105#define MOD_DIR_APPEND(list, str) \
106 do { \
107 PyObject *o = PyUnicode_FromString(str); \
108 if (o != NULL) \
109 PyList_Append(list, o); \
110 Py_XDECREF(o); \
111 } while (0)
112
113#define MOD_DIR_FUNCTION(name, method_listing) static PyObject * _##name##__dir__(name *self) { \
114 int i=0; \
115 PyObject* rc = PyList_New(0); \
116 if (!rc) \
117 return NULL; \
118\
119 while (method_listing[i].ml_name != NULL) { \
120 MOD_DIR_APPEND(rc, method_listing[i++].ml_name); \
121 } \
122\
123 return rc; \
124}
125
132static int PyPpcAPI_CompareWithASCIIString(PyObject* ptr, const char* name) {
133 int result = -1;
134 if (!PyString_Check(ptr)){
135#ifdef Py_USING_UNICODE
136 if (PyUnicode_Check(ptr)) {
137 PyObject* tmp = PyUnicode_AsEncodedString(ptr, NULL, NULL);
138 if (tmp != NULL) {
139 result = strcmp(PyString_AsString(tmp), name);
140 Py_DecRef(tmp);
141 }
142 }
143#endif
144 } else {
145 result = strcmp(PyString_AsString(ptr), name);
146 }
147 return result;
148}
149
150#endif