MCPcopy Create free account
hub / github.com/numpy/numpy / ufunc_generic_fastcall

Function ufunc_generic_fastcall

numpy/core/src/umath/ufunc_object.c:4706–5047  ·  view source on GitHub ↗

* Main ufunc call implementation. * * This implementation makes use of the "fastcall" way of passing keyword * arguments and is called directly from `ufunc_generic_vectorcall` when * Python has `tp_vectorcall` (Python 3.8+). * If `tp_vectorcall` is not available, the dictionary `kwargs` are unpacked in * `ufunc_generic_call` with fairly little overhead. */

Source from the content-addressed store, hash-verified

4704 * `ufunc_generic_call` with fairly little overhead.
4705 */
4706static PyObject *
4707ufunc_generic_fastcall(PyUFuncObject *ufunc,
4708 PyObject *const *args, Py_ssize_t len_args, PyObject *kwnames,
4709 npy_bool outer)
4710{
4711 int errval;
4712 int nin = ufunc->nin, nout = ufunc->nout, nop = ufunc->nargs;
4713
4714 /* All following variables are cleared in the `fail` error path */
4715 ufunc_full_args full_args;
4716 PyArrayObject *wheremask = NULL;
4717
4718 PyArray_DTypeMeta *signature[NPY_MAXARGS];
4719 PyArrayObject *operands[NPY_MAXARGS];
4720 PyArray_DTypeMeta *operand_DTypes[NPY_MAXARGS];
4721 PyArray_Descr *operation_descrs[NPY_MAXARGS];
4722 PyObject *output_array_prepare[NPY_MAXARGS];
4723 /* Initialize all arrays (we usually only need a small part) */
4724 memset(signature, 0, nop * sizeof(*signature));
4725 memset(operands, 0, nop * sizeof(*operands));
4726 memset(operand_DTypes, 0, nop * sizeof(*operation_descrs));
4727 memset(operation_descrs, 0, nop * sizeof(*operation_descrs));
4728 memset(output_array_prepare, 0, nout * sizeof(*output_array_prepare));
4729
4730 /*
4731 * Note that the input (and possibly output) arguments are passed in as
4732 * positional arguments. We extract these first and check for `out`
4733 * passed by keyword later.
4734 * Outputs and inputs are stored in `full_args.in` and `full_args.out`
4735 * as tuples (or NULL when no outputs are passed).
4736 */
4737
4738 /* Check number of arguments */
4739 if (NPY_UNLIKELY((len_args < nin) || (len_args > nop))) {
4740 PyErr_Format(PyExc_TypeError,
4741 "%s() takes from %d to %d positional arguments but "
4742 "%zd were given",
4743 ufunc_get_name_cstr(ufunc) , nin, nop, len_args);
4744 return NULL;
4745 }
4746
4747 /* Fetch input arguments. */
4748 full_args.in = PyArray_TupleFromItems(ufunc->nin, args, 0);
4749 if (full_args.in == NULL) {
4750 return NULL;
4751 }
4752
4753 /*
4754 * If there are more arguments, they define the out args. Otherwise
4755 * full_args.out is NULL for now, and the `out` kwarg may still be passed.
4756 */
4757 npy_bool out_is_passed_by_position = len_args > nin;
4758 if (out_is_passed_by_position) {
4759 npy_bool all_none = NPY_TRUE;
4760
4761 full_args.out = PyTuple_New(nout);
4762 if (full_args.out == NULL) {
4763 goto fail;

Callers 2

ufunc_generic_vectorcallFunction · 0.85
ufunc_outerFunction · 0.85

Calls 15

ufunc_get_name_cstrFunction · 0.85
PyArray_TupleFromItemsFunction · 0.85
_set_full_args_outFunction · 0.85
PyUFunc_CheckOverrideFunction · 0.85
_get_fixed_signatureFunction · 0.85
convert_ufunc_argumentsFunction · 0.85
resolve_descriptorsFunction · 0.85
PyArray_FLAGSFunction · 0.85
PyArray_EquivTypesFunction · 0.85

Tested by

no test coverage detected