1 // Copyright (C) 2007-2021 CEA/DEN, EDF R&D
3 // This library is free software; you can redistribute it and/or
4 // modify it under the terms of the GNU Lesser General Public
5 // License as published by the Free Software Foundation; either
6 // version 2.1 of the License, or (at your option) any later version.
8 // This library is distributed in the hope that it will be useful,
9 // but WITHOUT ANY WARRANTY; without even the implied warranty of
10 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
11 // Lesser General Public License for more details.
13 // You should have received a copy of the GNU Lesser General Public
14 // License along with this library; if not, write to the Free Software
15 // Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
17 // See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
19 // Author : Anthony Geay (EDF R&D)
21 #ifndef __MEDCOUPLINGDATAARRAYTRAITS_HXX__
22 #define __MEDCOUPLINGDATAARRAYTRAITS_HXX__
24 #include "MEDCouplingMemArray.hxx"
29 #include <numpy/arrayobject.h>
30 #if NPY_API_VERSION <= 0x00000006
31 # define MED_NUMPY_OWNDATA NPY_OWNDATA
33 # define MED_NUMPY_OWNDATA NPY_ARRAY_OWNDATA
38 // specific DataArray deallocator callback. This deallocator is used both in the constructor of DataArray and in the toNumPyArr
39 // method. This dellocator uses weakref to determine if the linked numArr is still alive or not. If alive the ownership is given to it.
40 // if no more alive the "standard" DataArray deallocator is called.
41 void numarrdeal(void *pt, void *wron)
43 void **wronc=(void **)wron;
44 PyObject *weakRefOnOwner=reinterpret_cast<PyObject *>(wronc[0]);
45 PyObject *obj=PyWeakref_GetObject(weakRefOnOwner);
46 int64_t *offset=reinterpret_cast<int64_t*>(wronc[2]);
50 PyArrayObject *objC=reinterpret_cast<PyArrayObject *>(obj);
51 objC->flags|=MED_NUMPY_OWNDATA;
52 Py_XDECREF(weakRefOnOwner);
57 typedef void (*MyDeallocator)(void *,void *);
58 MyDeallocator deall=(MyDeallocator)wronc[1];
60 Py_XDECREF(weakRefOnOwner);
67 template<class MCData>
68 struct PyCallBackDataArraySt {
73 typedef struct PyCallBackDataArraySt<MEDCoupling::DataArrayByte> PyCallBackDataArrayChar;
74 typedef struct PyCallBackDataArraySt<MEDCoupling::DataArrayInt32> PyCallBackDataArrayInt32;
75 typedef struct PyCallBackDataArraySt<MEDCoupling::DataArrayInt64> PyCallBackDataArrayInt64;
76 typedef struct PyCallBackDataArraySt<MEDCoupling::DataArrayFloat> PyCallBackDataArrayFloat;
77 typedef struct PyCallBackDataArraySt<MEDCoupling::DataArrayDouble> PyCallBackDataArrayDouble;
81 static int callbackmcdataarray___init__(PyObject *self, PyObject *args, PyObject *kwargs) { return 0; }
83 static PyObject *callbackmcdataarraychar___new__(PyTypeObject *type, PyObject *args, PyObject *kwargs)
85 PyCallBackDataArrayChar *self = (PyCallBackDataArrayChar *) ( type->tp_alloc(type, 0) );
86 return (PyObject *)self;
89 static PyObject *callbackmcdataarrayint32___new__(PyTypeObject *type, PyObject *args, PyObject *kwargs)
91 PyCallBackDataArrayInt32 *self = (PyCallBackDataArrayInt32 *) ( type->tp_alloc(type, 0) );
92 return (PyObject *)self;
95 static PyObject *callbackmcdataarrayint64___new__(PyTypeObject *type, PyObject *args, PyObject *kwargs)
97 PyCallBackDataArrayInt64 *self = (PyCallBackDataArrayInt64 *) ( type->tp_alloc(type, 0) );
98 return (PyObject *)self;
101 static PyObject *callbackmcdataarrayfloat___new__(PyTypeObject *type, PyObject *args, PyObject *kwargs)
103 PyCallBackDataArrayFloat *self = (PyCallBackDataArrayFloat *) ( type->tp_alloc(type, 0) );
104 return (PyObject *)self;
107 static PyObject *callbackmcdataarraydouble___new__(PyTypeObject *type, PyObject *args, PyObject *kwargs)
109 PyCallBackDataArrayDouble *self = (PyCallBackDataArrayDouble *) ( type->tp_alloc(type, 0) );
110 return (PyObject *)self;
113 static void callbackmcdataarray_dealloc(PyObject *self)
115 Py_TYPE(self)->tp_free(self);
119 // real callback called when a numpy arr having more than one DataArray instance client on it is destroyed.
120 // In this case, all the "weak" clients, except the first one, invoke this call back that desable the content of these "weak" clients.
121 static PyObject *callbackmcdataarraychar_call(PyCallBackDataArrayChar *self, PyObject *args, PyObject *kw)
125 MEDCoupling::MemArray<char>& mma=self->_pt_mc->accessToMemArray();
132 // real callback called when a numpy arr having more than one DataArray instance client on it is destroyed.
133 // In this case, all the "weak" clients, except the first one, invoke this call back that desable the content of these "weak" clients.
134 static PyObject *callbackmcdataarrayint32_call(PyCallBackDataArrayInt32 *self, PyObject *args, PyObject *kw)
138 MEDCoupling::MemArray<int>& mma=self->_pt_mc->accessToMemArray();
145 // real callback called when a numpy arr having more than one DataArray instance client on it is destroyed.
146 // In this case, all the "weak" clients, except the first one, invoke this call back that desable the content of these "weak" clients.
147 static PyObject *callbackmcdataarrayint64_call(PyCallBackDataArrayInt64 *self, PyObject *args, PyObject *kw)
151 MEDCoupling::MemArray<MEDCoupling::Int64>& mma=self->_pt_mc->accessToMemArray();
158 // real callback called when a numpy arr having more than one DataArray instance client on it is destroyed.
159 // In this case, all the "weak" clients, except the first one, invoke this call back that desable the content of these "weak" clients.
160 static PyObject *callbackmcdataarrayfloat_call(PyCallBackDataArrayFloat *self, PyObject *args, PyObject *kw)
164 MEDCoupling::MemArray<float>& mma=self->_pt_mc->accessToMemArray();
171 // real callback called when a numpy arr having more than one DataArray instance client on it is destroyed.
172 // In this case, all the "weak" clients, except the first one, invoke this call back that desable the content of these "weak" clients.
173 static PyObject *callbackmcdataarraydouble_call(PyCallBackDataArrayDouble *self, PyObject *args, PyObject *kw)
177 MEDCoupling::MemArray<double>& mma=self->_pt_mc->accessToMemArray();
185 PyTypeObject PyCallBackDataArrayChar_RefType = {
186 PyVarObject_HEAD_INIT(&PyType_Type, 0)
187 "callbackmcdataarraychar",
188 sizeof(PyCallBackDataArrayChar),
190 callbackmcdataarray_dealloc, /*tp_dealloc*/
197 0, /*tp_as_sequence*/
200 (ternaryfunc)callbackmcdataarraychar_call, /*tp_call*/
205 Py_TPFLAGS_DEFAULT | Py_TPFLAGS_HAVE_GC | Py_TPFLAGS_BASETYPE, /*tp_flags*/
209 0, /*tp_richcompare*/
210 0, /*tp_weaklistoffset*/
221 callbackmcdataarray___init__, /*tp_init*/
222 PyType_GenericAlloc, /*tp_alloc*/
223 callbackmcdataarraychar___new__, /*tp_new*/
224 PyObject_GC_Del, /*tp_free*/
228 PyTypeObject PyCallBackDataArrayInt32_RefType = {
229 PyVarObject_HEAD_INIT(&PyType_Type, 0)
230 "callbackmcdataarrayint32",
231 sizeof(PyCallBackDataArrayInt32),
233 callbackmcdataarray_dealloc, /*tp_dealloc*/
240 0, /*tp_as_sequence*/
243 (ternaryfunc)callbackmcdataarrayint32_call, /*tp_call*/
248 Py_TPFLAGS_DEFAULT | Py_TPFLAGS_HAVE_GC | Py_TPFLAGS_BASETYPE, /*tp_flags*/
252 0, /*tp_richcompare*/
253 0, /*tp_weaklistoffset*/
264 callbackmcdataarray___init__, /*tp_init*/
265 PyType_GenericAlloc, /*tp_alloc*/
266 callbackmcdataarrayint32___new__, /*tp_new*/
267 PyObject_GC_Del, /*tp_free*/
271 PyTypeObject PyCallBackDataArrayInt64_RefType = {
272 PyVarObject_HEAD_INIT(&PyType_Type, 0)
273 "callbackmcdataarrayint64",
274 sizeof(PyCallBackDataArrayInt64),
276 callbackmcdataarray_dealloc, /*tp_dealloc*/
283 0, /*tp_as_sequence*/
286 (ternaryfunc)callbackmcdataarrayint64_call, /*tp_call*/
291 Py_TPFLAGS_DEFAULT | Py_TPFLAGS_HAVE_GC | Py_TPFLAGS_BASETYPE, /*tp_flags*/
295 0, /*tp_richcompare*/
296 0, /*tp_weaklistoffset*/
307 callbackmcdataarray___init__, /*tp_init*/
308 PyType_GenericAlloc, /*tp_alloc*/
309 callbackmcdataarrayint64___new__, /*tp_new*/
310 PyObject_GC_Del, /*tp_free*/
313 PyTypeObject PyCallBackDataArrayFloat_RefType = {
314 PyVarObject_HEAD_INIT(&PyType_Type, 0)
315 "callbackmcdataarraydouble",
316 sizeof(PyCallBackDataArrayFloat),
318 callbackmcdataarray_dealloc, /*tp_dealloc*/
325 0, /*tp_as_sequence*/
328 (ternaryfunc)callbackmcdataarraydouble_call, /*tp_call*/
333 Py_TPFLAGS_DEFAULT | Py_TPFLAGS_HAVE_GC | Py_TPFLAGS_BASETYPE, /*tp_flags*/
337 0, /*tp_richcompare*/
338 0, /*tp_weaklistoffset*/
349 callbackmcdataarray___init__, /*tp_init*/
350 PyType_GenericAlloc, /*tp_alloc*/
351 callbackmcdataarrayfloat___new__, /*tp_new*/
352 PyObject_GC_Del, /*tp_free*/
355 PyTypeObject PyCallBackDataArrayDouble_RefType = {
356 PyVarObject_HEAD_INIT(&PyType_Type, 0)
357 "callbackmcdataarraydouble",
358 sizeof(PyCallBackDataArrayDouble),
360 callbackmcdataarray_dealloc, /*tp_dealloc*/
367 0, /*tp_as_sequence*/
370 (ternaryfunc)callbackmcdataarraydouble_call, /*tp_call*/
375 Py_TPFLAGS_DEFAULT | Py_TPFLAGS_HAVE_GC | Py_TPFLAGS_BASETYPE, /*tp_flags*/
379 0, /*tp_richcompare*/
380 0, /*tp_weaklistoffset*/
391 callbackmcdataarray___init__, /*tp_init*/
392 PyType_GenericAlloc, /*tp_alloc*/
393 callbackmcdataarraydouble___new__, /*tp_new*/
394 PyObject_GC_Del, /*tp_free*/
404 struct NPYTraits<double>
406 static const int NPYObjectType=NPY_DOUBLE;
407 static PyTypeObject *NPYFunc;
408 static PyObject *Array_SWIGTYPE;
412 struct NPYTraits<float>
414 static const int NPYObjectType=NPY_FLOAT;
415 static PyTypeObject *NPYFunc;
416 static PyObject *Array_SWIGTYPE;
420 struct NPYTraits<int>
422 static const int NPYObjectType=NPY_INT32;
423 static PyTypeObject *NPYFunc;
424 static PyObject *Array_SWIGTYPE;
428 struct NPYTraits<MEDCoupling::Int64>
430 static const int NPYObjectType=NPY_INT64;
431 static PyTypeObject *NPYFunc;
432 static PyObject *Array_SWIGTYPE;