std::unordered_map<size_t, D_ParseNode*> generateD_ParseNodeTable(const std::unordered_map<size_t, size_t>& indexes, void **_children, int _offset) { std::unordered_map<size_t, D_ParseNode*> table; for (auto element : indexes) { table[element.first] = &(*(D_PN(_children[element.second], _offset))); } return table; }
static int my_action(void *new_ps, void **children, int n_children, int pn_offset, struct D_Parser *parser, int speculative) { D_ParseNode *dd = D_PN(new_ps, pn_offset); PyObject *result = NULL; PyObject *children_list, *string_list = NULL; PNode *pn = (PNode *)new_ps; int action_index = pn->reduction->action_index; PyObject *tuple = NULL; PyObject *arg_types = NULL; D_ParserPyInterface *ppi = d_interface(parser); int takes_speculative = 0; PyObject *action = 0; if (PyErr_Occurred()) { /* just keep returning until finished parsing. Need a way to tell dparser to quit */ return 0; } if (action_index != -1) { tuple = PyList_GetItem(ppi->actions, action_index); PyArg_ParseTuple(tuple, "OOi", &action, &arg_types, &takes_speculative); } if (ppi->takes_globals) { inc_global_state(parser, dd); } if (ppi->print_debug_info && tuple) { print_debug_info(dd, tuple, speculative, ppi->print_debug_info); } if (takes_speculative == -1 && !speculative) { /* user.t and user.s were already set when this was called speculatively */ return 0; } if (ppi->takes_strings) { string_list = pylist_children(parser, dd, 1); if (string_list == NULL) { return -1; } } /* this function owns string_list */ if (takes_speculative == 0 && speculative) { Py_INCREF(Py_None); Py_XDECREF(dd->user.t); /* if (dd->user.s) printf("freeing2:%d\n", dd->user.s);*/ Py_XDECREF(dd->user.s); dd->user.t = Py_None; // printf("dd1:%d\n", dd); dd->user.s = NULL; Py_XDECREF(string_list); /* printf("setting:%d\n", string_list);*/ //dd->user.s = string_list; return 0; } children_list = pylist_children(parser, dd, 0); if (children_list == NULL) { /* if (string_list) printf("freeing3:%d\n", string_list);*/ Py_XDECREF(string_list); return -1; } /* this function owns children_list */ if (action_index != -1) { result = take_action(arg_types, children_list, speculative, dd, string_list, n_children, parser, children, pn_offset, action); Py_DECREF(children_list); } else { result = children_list; } /* function now owns result, string_list */ if (result == ppi->reject || result == NULL) { /* if (string_list) printf("freeing4:%d\n", string_list);*/ Py_XDECREF(result); Py_XDECREF(string_list); return -1; /* user rejected */ } Py_XDECREF(dd->user.t); /* these may have been set in a speculative pass */ /* if(dd->user.s) printf("freeing5:%d\n", dd->user.s);*/ Py_XDECREF(dd->user.s); /* if(dd->user.s) printf("setting2:%d\n", string_list);*/ // printf("dd2:%d\n", dd); dd->user.t = result; dd->user.s = string_list; return 0; }
static PyObject* take_action(PyObject *arg_types, PyObject *children_list, int speculative, D_ParseNode *dd, PyObject *string_list, int n_children, struct D_Parser *parser, void **children, int pn_offset, PyObject *action) { int i; int arg_count = PyList_Size(arg_types); D_ParserPyInterface *ppi = d_interface(parser); PyObject *arglist = PyTuple_New(arg_count); PyObject *globals_holder = NULL; PyObject *result = NULL; Py_INCREF(children_list); PyTuple_SetItem(arglist, 0, children_list); for (i=1; i<arg_count; i++) { PyObject *item = PyList_GetItem(arg_types, i); int type = PyInt_AsLong(item); if (type == 1) { PyTuple_SetItem(arglist, i, Py_BuildValue("i", speculative)); } else if (type == 2) { if (!dd->user.inced_global_state) { dd->user.inced_global_state = 1; } globals_holder = PyList_New(1); Py_INCREF(dd->globals); PyList_SetItem(globals_holder, 0, dd->globals); PyTuple_SetItem(arglist, i, globals_holder); } else if (type == 3) { Py_INCREF(string_list); PyTuple_SetItem(arglist, i, string_list); } else if (type == 4) { PyObject* nodes = PyList_New(n_children); int j; for (j=0; j<n_children; j++) { PyList_SetItem(nodes, j, make_py_node(parser, D_PN(children[j], pn_offset))); } PyTuple_SetItem(arglist, i, nodes); } else if (type == 5) { PyTuple_SetItem(arglist, i, make_py_node(parser, dd)); } else if (type == 6) { Py_INCREF(Py_None); PyTuple_SetItem(arglist, i, Py_None); } else if (type == 7) { Py_INCREF(ppi->self); PyTuple_SetItem(arglist, i, ppi->self); } } result = PyEval_CallObject(action, arglist); if (globals_holder) { Py_DECREF(dd->globals); dd->globals = PyList_GetItem(globals_holder, 0); Py_INCREF(dd->globals); } Py_DECREF(arglist); return result; }