1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798991001011021031041051061071081091101111121131141151161171181191201211221231241251261271281291301311321331341351361371381391401411421431441451461471481491501511521531541551561571581591601611621631641651661671681691701711721731741751761771781791801811821831841851861871881891901911921931941951961971981992002012022032042052062072082092102112122132142152162172182192202212222232242252262272282292302312322332342352362372382392402412422432442452462472482492502512522532542552562572582592602612622632642652662672682692702712722732742752762772782792802812822832842852862872882892902912922932942952962972982993003013023033043053063073083093103113123133143153163173183193203213223233243253263273283293303313323333343353363373383393403413423433443453463473483493503513523533543553563573583593603613623633643653663673683693703713723733743753763773783793803813823833843853863873883893903913923933943953963973983994004014024034044054064074084094104114124134144154164174184194204214224234244254264274284294304314324334344354364374384394404414424434444454464474484494504514524534544554564574584594604614624634644654664674684694704714724734744754764774784794804814824834844854864874884894904914924934944954964974984995005015025035045055065075085095105115125135145155165175185195205215225235245255265275285295305315325335345355365375385395405415425435445455465475485495505515525535545555565575585595605615625635645655665675685695705715725735745755765775785795805815825835845855865875885895905915925935945955965975985996006016026036046056066076086096106116126136146156166176186196206216226236246256266276286296306316326336346356366376386396406416426436446456466476486496506516526536546556566576586596606616626636646656666676686696706716726736746756766776786796806816826836846856866876886896906916926936946956966976986997007017027037047057067077087097107117127137147157167177187197207217227237247257267277287297307317327337347357367377387397407417427437447457467477487497507517527537547557567577587597607617627637647657667677687697707717727737747757767777787797807817827837847857867877887897907917927937947957967977987998008018028038048058068078088098108118128138148158168178188198208218228238248258268278288298308318328338348358368378388398408418428438448458468478488498508518528538548558568578588598608618628638648658668678688698708718728738748758768778788798808818828838848858868878888898908918928938948958968978988999009019029039049059069079089099109119129139149159169179189199209219229239249259269279289299309319329339349359369379389399409419429439449459469479489499509519529539549559569579589599609619629639649659669679689699709719729739749759769779789799809819829839849859869879889899909919929939949959969979989991000100110021003100410051006100710081009101010111012101310141015101610171018 |
- #include "python_if.h"
- /**@file python_if.c
- * @brief Python RPNIterExpr type definition
- * @ingroup python_ext
- * @ingroup pymod_pyrpn_RPNExprIter
- */
-
- /**@brief @ref pymod_pyrpn_RPNExprIter methods definition
- * @ingroup pymod_pyrpn_RPNExprIter */
- static PyMethodDef RPNIterExpr_methods[] = {
- PYRPN_method("get_params", rpnif_get_params,
- METH_NOARGS,
- "self, /",
- "Get a name tuple with parameters"),
- PYRPN_method("keys", rpnif_keys,
- METH_NOARGS,
- "self, /",
- "Return items keys (see dict.keys)"),
- PYRPN_method("values", rpnif_values,
- METH_NOARGS,
- "self, /",
- "Return items values (see dict.values)"),
- PYRPN_method("items", rpnif_items,
- METH_NOARGS,
- "self, /",
- "Return items (key, value) list (see dict.items)"),
- PYRPN_method("step", rpnif_step,
- METH_O,
- "self, position, /",
- "Run an IF given a position and return a new position"),
- PYRPN_method("__getstate__", rpnif_getstate,
- METH_NOARGS,
- "self, /",
- "Pickling method (see pickle module).\n"
- "Return a bytes representation of the expression state."),
- PYRPN_method("__setstate__", rpnif_setstate,
- METH_O,
- "self, state, /",
- "Unpickling method (see pickle module)."),
- {NULL} //Sentinel
- };
-
- /**@brief @ref pymod_pyrpn_RPNExprIter members definition
- * @ingroup pymod_pyrpn_RPNExprIter */
- static PyMemberDef RPNIterExpr_members[] = {
- {"expressions", T_OBJECT, offsetof(PyRPNIterExpr_t, expr), READONLY,
- "The tuple of expressions"},
- {NULL}
- };
-
- /**@brief @ref pymod_pyrpn_RPNExprIter sequence methods definition
- * @ingroup pymod_pyrpn_RPNExprIter */
- static PySequenceMethods RPNIterExpr_seq_methods = {
- .sq_length = rpnif_len,
- .sq_item = rpnif_expr_item,
- .sq_ass_item = rpnif_expr_ass_item,
- };
-
- /**@brief @ref pymod_pyrpn_RPNExprIter mapping methods definition
- * @ingroup pymod_pyrpn_RPNExprIter */
- static PyMappingMethods RPNIterExpr_mapping_methods = {
- .mp_length = rpnif_len,
- .mp_subscript = rpnif_subscript,
- .mp_ass_subscript = rpnif_ass_subscript,
- };
-
- /**@brief @ref pymod_pyrpn_RPNExprIter attributes definition
- * @ingroup pymod_pyrpn_RPNExprIter */
- static PyGetSetDef RPNIterExpr_getset[] = {
- {NULL}
- };
-
- /**@brief @ref pymod_pyrpn_RPNExprIter buffer methods definition
- * @ingroup pymod_pyrpn_RPNExprIter */
- static PyBufferProcs RPNIterExpr_as_buffer = {
- (getbufferproc)rpnif_getbuffer,
- (releasebufferproc)rpnif_releasebuffer,
- };
-
- PyTypeObject RPNIterExprType = {
- PyVarObject_HEAD_INIT(NULL, 0)
- .tp_name = "pyrpn.RPNIterExpr",
- .tp_basicsize = sizeof(PyRPNIterExpr_t),
- .tp_itemsize = 0,
- .tp_del = rpnif_del,
- .tp_repr = rpnif_repr,
- .tp_as_sequence = &RPNIterExpr_seq_methods,
- .tp_as_mapping = &RPNIterExpr_mapping_methods,
- .tp_str = rpnif_str,
- .tp_as_buffer = &RPNIterExpr_as_buffer,
- .tp_flags = Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE,
- .tp_doc = "RPN expression evaluator",
- .tp_methods = RPNIterExpr_methods,
- .tp_members = RPNIterExpr_members,
- .tp_getset = RPNIterExpr_getset,
- .tp_init = rpnif_init,
- .tp_new = rpnif_new,
- };
-
- PyObject* rpnif_new(PyTypeObject *subtype, PyObject *args, PyObject* kwds)
- {
- PyObject *ret, *err;
- PyRPNIterExpr_t *expr;
- ret = PyType_GenericNew(subtype, args, kwds);
- if((err = PyErr_Occurred()))
- {
- Py_DECREF(err);
- return ret;
- }
- expr = (PyRPNIterExpr_t*)ret;
- expr->rif = NULL;
-
- return ret;
- }
-
-
- int rpnif_init(PyObject *self, PyObject *args, PyObject *kwds)
- {
- PyRPNIterExpr_t *expr_self;
- char *names[] = {"pos_flag", "res_flag", "size_lim", "const_values", "stack_size", NULL};
- unsigned short pos_flag, res_flag, stack_size;
- PyObject *lim_obj, *const_values_obj;
- int ndim;
-
- char err_str[256];
-
- expr_self = (PyRPNIterExpr_t*)self;
-
- stack_size = 16;
- const_values_obj = lim_obj = NULL;
- expr_self->rif = NULL;
-
- if(!PyArg_ParseTupleAndKeywords(args, kwds, "HHO|OH:RPNIterExpr.__init__", names,
- &pos_flag, &res_flag, &lim_obj, &const_values_obj, &stack_size))
- {
- return -1;
- }
-
- // Args checking
- if(stack_size < 4 || stack_size > 255)
- {
- snprintf(err_str, 128,
- "Stack size should be in [0..255] but %u given",
- stack_size);
- PyErr_SetString(PyExc_ValueError, err_str);
- return -1;
- }
-
- // Checks flags & fetch expected sizes for size_lim & const_values
- short expt_sizes[2];
- if(rpn_if_sizes_from_flag(pos_flag, res_flag, expt_sizes) < 0)
- {
- if(expt_sizes[0] < 0)
- {
- PyErr_SetString(PyExc_ValueError,
- "Invalid position flag given");
- }
- else
- {
- PyErr_SetString(PyExc_ValueError,
- "Invalid result flag given");
- }
- return -1;
- }
-
- //Check & convert lim
- PyObject *tmp;
- tmp = lim_obj;
- if(!PyTuple_Check(tmp))
- {
- PyErr_SetString(PyExc_ValueError,
- "Invalid type for size_lim argument");
- return -1;
- }
- Py_ssize_t lim_obj_sz = PyTuple_Size(tmp);
- ndim = lim_obj_sz;
- if(PyErr_Occurred())
- {
- return -1;
- }
- if(lim_obj_sz < 1)
- {
- PyErr_SetString(PyExc_ValueError,
- "Size limits cannot be empty");
- }
-
- if(pos_flag == RPN_IF_POSITION_XDIM)
- {
- PyObject *item = PyTuple_GET_ITEM(tmp, 0);
- Py_ssize_t tmp = PyLong_AsSsize_t(item);
- if(PyErr_Occurred())
- {
- PyErr_SetString(PyExc_ValueError,
- "Unable to convert size_lim[0] to int");
- return -1;
- }
- if(lim_obj_sz != tmp + 1)
- {
- PyErr_Format(PyExc_ValueError,
- "Xdim indicate %d size_lim but len(size_lim)=%d",
- tmp+1, lim_obj_sz);
- return -1;
- }
- expt_sizes[0] = ndim = tmp;
- }
- else
- {
- if(lim_obj_sz != expt_sizes[0])
- {
- PyErr_Format(PyExc_ValueError,
- "Expected %d size_lim but len(size_lim)=%d",
- expt_sizes[0], lim_obj_sz);
- return -1;
- }
- }
-
- size_t sz_limits[lim_obj_sz];
- for(Py_ssize_t i = 0; i<lim_obj_sz; i++)
- {
- PyObject *item = PyTuple_GET_ITEM(tmp, i);
- sz_limits[i] = PyLong_AsSize_t(item);
- if(PyErr_Occurred())
- {
- PyErr_Format(PyExc_ValueError,
- "Unable to convert size_lim[%d] to unsigned int",
- i);
- return -1;
- }
- }
-
- expr_self->ndim = ndim;
-
- //Check & convert const values
- Py_ssize_t values_obj_sz = 0;
- tmp = NULL;
- if(expt_sizes[1] > 0)
- {
- tmp = const_values_obj;
- if(!PyTuple_Check(tmp))
- {
- PyErr_SetString(PyExc_ValueError,
- "Invalid type for const_values argument");
- return -1;
- }
- values_obj_sz = PyTuple_Size(tmp);
- if(values_obj_sz != expt_sizes[1])
- {
- PyErr_Format(PyExc_ValueError,
- "Expected %d const_values but len(const_values)=%d",
- expt_sizes[1], values_obj_sz);
- return -1;
- }
- }
-
- rpn_value_t const_values[values_obj_sz];
- for(Py_ssize_t i = 0; i<values_obj_sz; i++)
- {
- PyObject *item = PyTuple_GET_ITEM(tmp, i);
- const_values[i] = PyLong_AsRpnValue_t(item);
- if(PyErr_Occurred())
- {
- PyErr_Format(PyExc_ValueError,
- "Unable to convert size_lim[%d] to unsigned int",
- i);
- return -1;
- }
- }
-
-
- // Creating rif params
- rpn_if_param_t *rif_params;
-
- if(!(rif_params = rpn_if_default_params(pos_flag, res_flag,
- sz_limits, const_values, stack_size)))
- {
- PyErr_SetString(PyExc_ValueError, "Unable to create parameters \
- with given arguments");
- return -1;
- }
-
- // Creating rif with a new memory map
- expr_self->rif = rpn_if_new(rif_params, NULL);
-
- // Creating the tuple holding RPNExpr instances of expressions
- expr_self->expr = PyTuple_New(expr_self->rif->params->rpn_sz);
- for(size_t i=0; i<expr_self->rif->params->rpn_sz;i++)
- {
- rpn_expr_t *expr = &expr_self->rif->rpn[i];
- PyObject *instance = rpnexpr_init_borrowing(expr);
- if(!instance)
- {
- return -1;
- }
- PyTuple_SET_ITEM(expr_self->expr, i, instance);
- }
-
- return 0;
- }
-
- /**@brief Returns the parameters in a named tuple */
- PyObject *rpnif_get_params(PyObject *self)
- {
- PyRPNIterExpr_t *expr_self = (PyRPNIterExpr_t*)self;
- PyObject *res, *val;
- rpn_if_default_data_t *params;
-
- params = (rpn_if_default_data_t*)(expr_self->rif->params->data);
-
- short expt_sizes[2];
- if(rpn_if_sizes_from_flag(params->pos_flag, params->res_flag, expt_sizes) < 0)
- {
- PyErr_SetString(PyExc_RuntimeError, "Invalid internal state");
- return NULL;
- }
-
- res = PyStructSequence_New(&rpnif_params_SeqDesc);
- if(!res)
- {
- return NULL;
- }
- val = PyLong_FromLong(expr_self->rif->params->rpn_argc);
- PyStructSequence_SET_ITEM(res, 0, val);
-
- val = PyLong_FromLong(params->pos_flag);
- PyStructSequence_SET_ITEM(res, 1, val);
-
- val = PyLong_FromLong(params->res_flag);
- PyStructSequence_SET_ITEM(res, 2, val);
-
- if(params->pos_flag == RPN_IF_POSITION_XDIM)
- {
- expt_sizes[0] = params->size_lim[0] + 1;
- }
-
- PyObject *lim = PyTuple_New(expt_sizes[0]);
- if(!lim)
- {
- Py_DECREF(res);
- return NULL;
- }
- PyStructSequence_SET_ITEM(res, 3, lim);
-
- for(Py_ssize_t i=0; i<expt_sizes[0]; i++)
- {
- val = PyLong_FromSize_t(params->size_lim[i]);
- PyTuple_SET_ITEM(lim, i, val);
- }
-
- if(!params->const_val)
- {
- Py_INCREF(Py_None);
- PyTuple_SET_ITEM(res, 4, Py_None);
- }
- else
- {
- PyObject *values = PyTuple_New(expt_sizes[1]);
- if(!values)
- {
- Py_DECREF(res);
- return NULL;
- }
- PyStructSequence_SET_ITEM(res, 4, values);
- for(Py_ssize_t i=0; i<expt_sizes[1]; i++)
- {
- val = PyLong_FromRpnValue_t(params->const_val[i]);
- PyTuple_SET_ITEM(values, i, val);
- }
- }
- return res;
- }
-
-
- PyObject *rpnif_step(PyObject *self, PyObject* opos)
- {
- PyRPNIterExpr_t *expr_self = (PyRPNIterExpr_t*)self;
- if(!PyLong_Check(opos))
- {
- PyErr_SetString(PyExc_TypeError, "Expected position to be an int");
- return NULL;
- }
- size_t pos = PyLong_AsSize_t(opos);
- if(PyErr_Occurred())
- {
- return NULL;
- }
-
- pos = rpn_if_step(expr_self->rif, pos);
-
- return PyLong_FromSize_t(pos);
- }
-
-
- PyObject *rpnif_keys(PyObject *self)
- {
- PyRPNIterExpr_t *expr_self = (PyRPNIterExpr_t*)self;
- rpn_if_default_data_t *rif_data = (rpn_if_default_data_t*)expr_self->rif->params->data;
-
- Py_ssize_t ret_idx = 0;
- char xdim_key[64];
-
- PyObject *ret = PyTuple_New(expr_self->rif->params->rpn_sz);
- if(PyErr_Occurred())
- {
- return NULL;
- }
-
- #define _ret_append(key) PyTuple_SET_ITEM(ret, ret_idx++, \
- PyUnicode_FromString(key))
-
- switch(rif_data->pos_flag)
- {
- case RPN_IF_POSITION_XY:
- _ret_append("X");
- _ret_append("Y");
- break;
- case RPN_IF_POSITION_LINEAR:
- _ret_append("X");
- break;
- case RPN_IF_POSITION_XDIM:
- for(size_t i=0; i<rif_data->size_lim[0];i++)
- {
- snprintf(xdim_key, 64, "D%ld", i);
- _ret_append(xdim_key);
- }
- break;
- default:
- PyErr_SetString(PyExc_RuntimeError,
- "UNKOWN POS_FLAG3");
- return NULL;
- }
- switch(rif_data->res_flag)
- {
- case RPN_IF_RES_BOOL:
- case RPN_IF_RES_XFUN:
- _ret_append("R");
- break;
- case RPN_IF_RES_RGB:
- _ret_append("R");
- _ret_append("G");
- _ret_append("B");
- break;
- case RPN_IF_RES_RGBA:
- _ret_append("R");
- _ret_append("G");
- _ret_append("B");
- _ret_append("A");
- break;
- default:
- break;
- }
-
- if(PyErr_Occurred())
- {
- return NULL;
- }
-
- return ret;
-
- #undef _ret_append
- }
-
-
- PyObject *rpnif_values(PyObject *self)
- {
- PyRPNIterExpr_t *expr_self = (PyRPNIterExpr_t*)self;
- Py_INCREF(expr_self->expr);
- return expr_self->expr;
- }
-
-
- PyObject *rpnif_items(PyObject *self)
- {
- size_t i;
- PyRPNIterExpr_t *expr_self = (PyRPNIterExpr_t*)self;
- PyObject *ret = PyTuple_New(expr_self->rif->params->rpn_sz);
- if(PyErr_Occurred())
- {
- return NULL;
- }
- PyObject *keys = rpnif_keys(self);
- for(i=0; i<expr_self->rif->params->rpn_sz; i++)
- {
- PyObject *tmp = PyTuple_New(2);
- if(PyErr_Occurred())
- {
- goto err_loop_newtuple;
- }
- PyObject *key = PyTuple_GET_ITEM(keys, i);
- PyObject *value = PyTuple_GET_ITEM(expr_self->expr, i);
- Py_INCREF(key);
- Py_INCREF(value);
- PyTuple_SET_ITEM(tmp, 0, key);
- PyTuple_SET_ITEM(tmp, 1, value);
- PyTuple_SET_ITEM(ret, i, tmp);
- if(PyErr_Occurred())
- {
- goto err_loop_setitem;
- }
-
-
- }
-
- return ret;
-
- /** @todo cleanup seems wrong... */
- for(i=i; i>=0; i--)
- {
- err_loop_setitem:
- PyObject *key = PyTuple_GET_ITEM(keys, i);
- PyObject *value = PyTuple_GET_ITEM(expr_self->expr, i);
- Py_DECREF(key);
- Py_DECREF(value);
- err_loop_newtuple:
- }
- Py_DECREF(ret);
- return NULL;
- }
-
-
- void rpnif_del(PyObject *self)
- {
- PyRPNIterExpr_t *expr_self = (PyRPNIterExpr_t*)self;
- if(expr_self->rif)
- {
- rpn_if_free(expr_self->rif);
- expr_self->rif = NULL;
- }
- }
-
-
- Py_ssize_t rpnif_len(PyObject *self)
- {
- PyRPNIterExpr_t *expr_self = (PyRPNIterExpr_t*)self;
- return expr_self->rif->params->rpn_sz;
- }
-
- PyObject* rpnif_expr_item(PyObject *self, Py_ssize_t idx)
- {
- Py_ssize_t _idx = idx;
- PyRPNIterExpr_t *expr_self = (PyRPNIterExpr_t*)self;
-
- if(idx < 0)
- {
- idx = expr_self->rif->params->rpn_sz - 1 + idx;
- }
- if(idx < 0 || (size_t) idx >= expr_self->rif->params->rpn_sz)
- {
- PyErr_Format(PyExc_IndexError,
- "No expression %ld with given options",
- _idx);
- return NULL;
- }
- PyObject *ret = PyTuple_GET_ITEM(expr_self->expr, idx);
- Py_INCREF(ret);
- return ret;
- }
-
-
- int rpnif_expr_ass_item(PyObject *self, Py_ssize_t idx, PyObject* elt)
- {
- PyRPNIterExpr_t *expr_self = (PyRPNIterExpr_t*)self;
-
- if(!PyUnicode_Check(elt))
- {
- PyErr_SetString(PyExc_TypeError, "RPNExpr expected");
- return -1;
- }
-
- PyObject *bytes_str = PyUnicode_AsASCIIString(elt);
- if(PyErr_Occurred())
- {
- return -1;
- }
- const char *code = PyBytes_AS_STRING(bytes_str);
-
- rpn_expr_t *expr = &(expr_self->rif->rpn[idx]);
-
- if(rpn_expr_recompile(expr, code) < 0)
- {
- PyErr_Format(PyExc_ValueError,
- "Error during expression '%s' compilation : %s",
- code, expr->err_reason);
- return -1;
- }
-
- return 0;
- }
-
- /** Convert key to integer index
- * @param self @ref PyRPNIterExpr_t instance
- * @param _key An expression name (str)
- * @return The expression index or -1 on error (raise python exception)
- */
- static Py_ssize_t _rpnif_subscript_idx(PyObject *self, PyObject *_key)
- {
- if(!PyUnicode_Check(_key))
- {
- PyErr_SetString(PyExc_TypeError, "Key should be a str");
- return -1;
- }
- PyObject *bytes_str = PyUnicode_AsASCIIString(_key);
- if(PyErr_Occurred())
- {
- return -1;
- }
- const char *key = PyBytes_AS_STRING(bytes_str);
- PyRPNIterExpr_t *expr_self = (PyRPNIterExpr_t*)self;
- rpn_if_default_data_t *rif_data = (rpn_if_default_data_t*)expr_self->rif->params->data;
-
- Py_ssize_t idx = -1;
- Py_ssize_t res_idx = -1;
-
- switch(rif_data->pos_flag)
- {
- case RPN_IF_POSITION_XY:
- res_idx = 2;
- if(key[1] != '\0') { break; }
- switch(key[0])
- {
- case 'X':
- idx=0;
- break;
- case 'Y':
- idx=1;
- break;
- }
- break;
- case RPN_IF_POSITION_LINEAR:
- res_idx = 1;
- if(!strcmp("X", key))
- {
- idx = 0;
- }
- break;
- case RPN_IF_POSITION_XDIM:
- size_t ndim = rif_data->size_lim[0];
- res_idx = ndim;
- char possible_key[64];
- for(size_t i=0; i<ndim; i++)
- {
- snprintf(possible_key, 64, "D%ld", i);
- if(!strcmp(possible_key, key))
- {
- idx = i;
- break;
- }
- }
- break;
- default:
- PyErr_SetString(PyExc_RuntimeError,
- "UNKOWN POS_FLAG");
- return -1;
- }
- if(idx < 0)
- {
- // not found yet, looking for result key
- switch(rif_data->res_flag)
- {
- case RPN_IF_RES_BOOL:
- case RPN_IF_RES_XFUN:
- if(!strcmp("R", key))
- {
- idx = res_idx;
- }
- break;
- case RPN_IF_RES_RGBA:
- if(!strcmp("A", key))
- {
- idx = res_idx + 3;
- }
- case RPN_IF_RES_RGB:
- if(key[1] != '\0')
- {
- break;
- }
- switch(key[0])
- {
- case 'R':
- idx=res_idx;
- break;
- case 'G':
- idx=res_idx+1;
- break;
- case 'B':
- idx=res_idx+2;
- break;
- }
- break;
- default:
- // not implemented, not unknown....
- PyErr_SetString(PyExc_RuntimeError,
- "UNKOWN RES_FLAG");
- return -1;
- }
- }
- return idx;
- }
-
- PyObject* rpnif_subscript(PyObject *self, PyObject *key)
- {
- PyRPNIterExpr_t *expr_self = (PyRPNIterExpr_t*)self;
-
- Py_ssize_t idx = _rpnif_subscript_idx(self, key);
- if(idx < 0)
- {
- PyErr_Format(PyExc_IndexError,
- "No expression '%s' with given parameters",
- key);
- return NULL;
- }
- PyObject *expr = PyTuple_GET_ITEM(expr_self->expr, idx);
- Py_INCREF(expr);
- return expr;
- }
-
- int rpnif_ass_subscript(PyObject *self, PyObject *key, PyObject *elt)
- {
- Py_ssize_t idx = _rpnif_subscript_idx(self, key);
- if(idx < 0)
- {
- PyErr_Format(PyExc_IndexError,
- "Cannot set expression '%s' that do not exists with this parameters",
- key);
- return -1;
- }
-
- return rpnif_expr_ass_item(self, idx, elt);
- }
-
- int rpnif_getbuffer(PyObject *self, Py_buffer *view, int flags)
- {
- PyRPNIterExpr_t *expr_self;
- expr_self = (PyRPNIterExpr_t*)self;
-
- rpn_if_default_data_t *data = (rpn_if_default_data_t*)expr_self->rif->params->data;
-
- view->buf = expr_self->rif->mem;
- view->obj = self;
- view->len = expr_self->rif->params->mem_sz * expr_self->rif->params->value_sz;
- view->readonly = 0;
- //view->itemsize = expr_self->rif->params->value_sz;
- view->itemsize = sizeof(rpn_value_t);
- if(flags & PyBUF_FORMAT)
- {
- view->format = "L";
- }
- else
- {
- view->format = NULL;
- }
- view->ndim = 1;
- view->shape = NULL;
- if(flags & PyBUF_ND)
- {
- view->ndim = expr_self->ndim;
-
- // !! Error if value_sz < sizeof(rpn_value_t) !!
- short nval = view->itemsize / sizeof(rpn_value_t);
- if(nval > 1)
- {
- view->ndim++;
- }
- view->shape = malloc(sizeof(Py_ssize_t) * view->ndim); /**@todo check error*/
- for(size_t i=0; i<expr_self->ndim; i++)
- {
- int idx = i;
- if(data->pos_flag == RPN_IF_POSITION_XDIM)
- {
- idx++;
- }
- view->shape[i] = data->size_lim[idx];
- }
- if(nval>1)
- {
- view->shape[expr_self->ndim] = nval;
- }
- }
- view->strides = NULL;
- view->suboffsets = NULL;
-
- Py_INCREF(self);
- return 0;
- }
-
- void rpnif_releasebuffer(PyObject *self, Py_buffer *view)
- {
- free(view->shape);
- }
-
- PyObject* rpnif_str(PyObject *self)
- {
- PyRPNIterExpr_t *expr_self = (PyRPNIterExpr_t*)self;
- rpn_if_default_data_t *rif_data = \
- (rpn_if_default_data_t*)expr_self->rif->params->data;
- const size_t rpn_sz = expr_self->rif->params->rpn_sz;
- const char pyfmt[] = "%VA%ld=%U=\"%S\";";
-
- size_t i;
- PyObject *buf, *tmp, *items;
-
- buf = NULL;
- items = rpnif_items(self);
- if(PyErr_Occurred()) { return NULL; }
-
-
- for(i=0; i<rpn_sz; i++)
- {
- PyObject *key, *value, *elt;
- elt = PyTuple_GET_ITEM(items, i);
- key = PyTuple_GET_ITEM(elt, 0);
- value = PyTuple_GET_ITEM(elt, 1);
-
- tmp = PyUnicode_FromFormat(pyfmt,
- buf, "",
- i, key, value);
- if(buf) { Py_DECREF(buf); }
- if(PyErr_Occurred()) { return NULL; }
- buf = tmp;
- }
-
-
- switch(rif_data->res_flag)
- {
- case RPN_IF_RES_CONST:
- tmp = PyUnicode_FromFormat("%U A%ld=C(*)=%lld",
- buf, i+1, rif_data->const_val[0]);
- Py_DECREF(buf);
- buf=tmp;
- break;
- case RPN_IF_RES_CONST_RGBA:
- tmp = PyUnicode_FromFormat("%U A%ld=R(*)=%lld A%ld=G(*)=%lld A%ld=B(*)=%lld A%ld=A(*)=%lld",
- buf,
- i+1, rif_data->const_val[0],
- i+2, rif_data->const_val[1],
- i+3, rif_data->const_val[2],
- i+4, rif_data->const_val[3]);
- Py_DECREF(buf);
- buf=tmp;
- break;
- }
-
- Py_INCREF(buf);
- return buf;
- }
-
- /** Return a string representation of expressions dict
- * @param self @ref PyRPNIterExpr_t instance
- * @return a str instance */
- static PyObject* _rpnif_expr_repr(PyObject *self)
- {
- PyRPNIterExpr_t *expr_self = (PyRPNIterExpr_t*)self;
- rpn_if_default_data_t *rif_data = \
- (rpn_if_default_data_t*)expr_self->rif->params->data;
-
- PyObject *buf, *tmp, *items, *const_res;
- const char pyfmt[] = "%V\"%U\":\"%S\"%V";
-
- buf = const_res = NULL;
-
- items = rpnif_items(self);
- if(PyErr_Occurred()) { return NULL; }
-
- #define _const_res_key ",\"const_res\":"
- switch(rif_data->res_flag)
- {
- case RPN_IF_RES_CONST:
- const_res = PyUnicode_FromFormat(
- _const_res_key "{\"r\":%llu}}",
- rif_data->const_val[0]);
- break;
- /*
- case RPN_IF_RES_CONST_RGB:
- const_res = PyUnicode_FromFormat(
- "\"const_res\": {\"r\":%llu, \"g\":%llu, \"b\":%llu}}",
- rif_data->const_val[0],
- rif_data->const_val[1],
- rif_data->const_val[2])
- break;
- */
- case RPN_IF_RES_CONST_RGBA:
- const_res = PyUnicode_FromFormat(
- _const_res_key \
- "{\"r\":%llu,\"g\":%llu,\"b\":%llu,\"a\":%llu}}",
- rif_data->const_val[0],
- rif_data->const_val[1],
- rif_data->const_val[2],
- rif_data->const_val[3]);
- break;
- default:
- const_res = PyUnicode_FromFormat("}");
- break;
- }
- #undef _const_res_key
-
- const size_t rpn_sz = expr_self->rif->params->rpn_sz;
-
- for(size_t i=0; i<rpn_sz; i++)
- {
- PyObject *key, *value, *elt;
- elt = PyTuple_GET_ITEM(items, i);
- key = PyTuple_GET_ITEM(elt, 0);
- value = PyTuple_GET_ITEM(elt, 1);
-
- tmp = PyUnicode_FromFormat(pyfmt,
- buf, "{", key, value,
- i==rpn_sz-1?const_res:NULL, ",");
- if(buf)
- {
- Py_DECREF(buf);
- }
- if(PyErr_Occurred())
- {
- return NULL;
- }
- buf = tmp;
- }
-
-
- return buf;
- }
-
- PyObject* rpnif_repr(PyObject *self)
- {
- PyRPNIterExpr_t *expr_self = (PyRPNIterExpr_t*)self;
- rpn_if_default_data_t *rif_data = (rpn_if_default_data_t*)expr_self->rif->params->data;
-
- char *str_pos, *str_res;
- char tmp[64];
-
- PyObject *expr_repr = _rpnif_expr_repr(self);
- if(PyErr_Occurred()) { return NULL; }
-
- switch(rif_data->pos_flag)
- {
- case RPN_IF_POSITION_XY:
- str_pos = "XY";
- break;
- case RPN_IF_POSITION_LINEAR:
- str_pos = "LINEAR";
- break;
- case RPN_IF_POSITION_XDIM:
- snprintf(tmp, 64, "XDIM%ld", rif_data->size_lim[0]);
- str_pos = tmp;
- break;
- default:
- PyErr_SetString(PyExc_RuntimeError,
- "UNKOWN POS_FLAG2");
- return NULL;
- }
-
- PyObject *const_res = NULL;
-
- switch(rif_data->res_flag)
- {
- case RPN_IF_RES_BOOL:
- str_res = "BOOL";
- break;
- case RPN_IF_RES_CONST:
- str_res = "CONST";
- const_res = PyTuple_New(1);
- break;
- case RPN_IF_RES_CONST_RGBA:
- str_res = "CONST_RGBA";
- break;
- case RPN_IF_RES_COUNT:
- str_res = "COUNT";
- break;
- case RPN_IF_RES_XFUN:
- str_res = "XFUN";
- break;
- case RPN_IF_RES_RGB:
- str_res = "RGB";
- break;
- case RPN_IF_RES_RGBA:
- str_res = "RGBA";
- break;
- default:
- PyErr_SetString(PyExc_RuntimeError,
- "UNKOWN RES_FLAG2");
- return NULL;
- }
-
- PyObject *res;
-
- const_res = const_res?const_res:Py_None;
-
- res = PyUnicode_FromFormat(
- "<RPNIterExpr pos_flag:%s res_flag:%s expr:'%U' const_res:%S>",
- str_pos, str_res, expr_repr, const_res);
- if(PyErr_Occurred()) { return NULL; }
- return res;
- }
-
- PyObject* rpnif_getstate(PyObject *self, PyObject *noargs)
- {
- PyErr_SetString(PyExc_NotImplementedError,
- "getstate Not implemented");
- return NULL;
- /**@todo TODO write the function */
- Py_RETURN_NONE;
- }
-
- PyObject* rpnif_setstate(PyObject *self, PyObject *state_bytes)
- {
- PyErr_SetString(PyExc_NotImplementedError,
- "setstate Not implemented");
- return NULL;
- /**@todo TODO write the function */
- Py_RETURN_NONE;
- }
-
- /**@def _ret_append(key)
- * @hiderefs
- * local macro */
- /**@def _const_res_key()
- * @hiderefs
- * local macro*/
|