diff options
author | Charles Harris <charlesr.harris@gmail.com> | 2013-10-24 15:30:22 -0700 |
---|---|---|
committer | Charles Harris <charlesr.harris@gmail.com> | 2013-10-24 15:30:22 -0700 |
commit | a3e8c12ed88c6db2aa89cfbb7a69fc863e8a40dc (patch) | |
tree | c3fe316ad8bc6044f20e39abdb785b6219ef7507 | |
parent | 8988715e1aea7b10b230115aecae029cf6e80d66 (diff) | |
parent | 3a01f4e11874be9db17fb24fa17c649fd45a8aff (diff) | |
download | numpy-a3e8c12ed88c6db2aa89cfbb7a69fc863e8a40dc.tar.gz |
Merge pull request #3965 from seberg/valgrind
MAINT: Initialize strides in NpyIter and silence valgrind
-rw-r--r-- | numpy/core/src/multiarray/convert_datatype.c | 2 | ||||
-rw-r--r-- | numpy/core/src/multiarray/multiarraymodule.c | 1 | ||||
-rw-r--r-- | numpy/core/src/multiarray/nditer_constr.c | 38 | ||||
-rw-r--r-- | numpy/core/src/multiarray/number.c | 20 | ||||
-rw-r--r-- | numpy/core/src/umath/test_rational.c.src | 3 | ||||
-rw-r--r-- | numpy/core/src/umath/ufunc_object.c | 2 | ||||
-rw-r--r-- | numpy/core/tests/test_api.py | 16 | ||||
-rw-r--r-- | numpy/core/tests/test_multiarray.py | 2 | ||||
-rw-r--r-- | numpy/core/tests/test_regression.py | 10 | ||||
-rw-r--r-- | numpy/linalg/tests/test_linalg.py | 2 |
10 files changed, 61 insertions, 35 deletions
diff --git a/numpy/core/src/multiarray/convert_datatype.c b/numpy/core/src/multiarray/convert_datatype.c index a75a1c22e..4f0202ffb 100644 --- a/numpy/core/src/multiarray/convert_datatype.c +++ b/numpy/core/src/multiarray/convert_datatype.c @@ -1396,7 +1396,7 @@ static int min_scalar_type_num(char *valueptr, int type_num, break; } case NPY_CLONGDOUBLE: { - npy_cdouble value = *(npy_cdouble *)valueptr; + npy_clongdouble value = *(npy_clongdouble *)valueptr; /* if (value.imag == 0) { return min_scalar_type_num((char *)&value.real, diff --git a/numpy/core/src/multiarray/multiarraymodule.c b/numpy/core/src/multiarray/multiarraymodule.c index ea879c226..a89e27595 100644 --- a/numpy/core/src/multiarray/multiarraymodule.c +++ b/numpy/core/src/multiarray/multiarraymodule.c @@ -1548,6 +1548,7 @@ _prepend_ones(PyArrayObject *arr, int nd, int ndmin, NPY_ORDER order) PyArray_FLAGS(arr), (PyObject *)arr); if (ret == NULL) { + Py_DECREF(arr); return NULL; } /* steals a reference to arr --- so don't increment here */ diff --git a/numpy/core/src/multiarray/nditer_constr.c b/numpy/core/src/multiarray/nditer_constr.c index 053777f6a..a12457a1e 100644 --- a/numpy/core/src/multiarray/nditer_constr.c +++ b/numpy/core/src/multiarray/nditer_constr.c @@ -1161,11 +1161,7 @@ npyiter_prepare_operands(int nop, PyArrayObject **op_in, /* Check the readonly/writeonly flags, and fill in op_itflags */ if (!npyiter_check_per_op_flags(op_flags[iop], &op_itflags[iop])) { - for (i = 0; i <= iop; ++i) { - Py_XDECREF(op[i]); - Py_XDECREF(op_dtype[i]); - } - return 0; + goto fail_iop; } /* Extract the operand which is for masked iteration */ @@ -1174,11 +1170,7 @@ npyiter_prepare_operands(int nop, PyArrayObject **op_in, PyErr_SetString(PyExc_ValueError, "Only one iterator operand may receive an " "ARRAYMASK flag"); - for (i = 0; i <= iop; ++i) { - Py_XDECREF(op[i]); - Py_XDECREF(op_dtype[i]); - } - return 0; + goto fail_iop; } maskop = iop; @@ -1199,11 +1191,7 @@ npyiter_prepare_operands(int nop, PyArrayObject **op_in, &op_dtype[iop], flags, op_flags[iop], &op_itflags[iop])) { - for (i = 0; i <= iop; ++i) { - Py_XDECREF(op[i]); - Py_XDECREF(op_dtype[i]); - } - return 0; + goto fail_iop; } } @@ -1217,13 +1205,9 @@ npyiter_prepare_operands(int nop, PyArrayObject **op_in, } } if (all_null) { - for (i = 0; i < nop; ++i) { - Py_XDECREF(op[i]); - Py_XDECREF(op_dtype[i]); - } PyErr_SetString(PyExc_ValueError, "At least one iterator operand must be non-NULL"); - return 0; + goto fail_nop; } } @@ -1232,17 +1216,26 @@ npyiter_prepare_operands(int nop, PyArrayObject **op_in, "An iterator operand was flagged as WRITEMASKED, " "but no ARRAYMASK operand was given to supply " "the mask"); - return 0; + goto fail_nop; } else if (!any_writemasked_ops && maskop >= 0) { PyErr_SetString(PyExc_ValueError, "An iterator operand was flagged as the ARRAYMASK, " "but no WRITEMASKED operands were given to use " "the mask"); - return 0; + goto fail_nop; } return 1; + + fail_nop: + iop = nop; + fail_iop: + for (i = 0; i < iop; ++i) { + Py_XDECREF(op[i]); + Py_XDECREF(op_dtype[i]); + } + return 0; } static const char * @@ -1565,6 +1558,7 @@ npyiter_fill_axisdata(NpyIter *iter, npy_uint32 flags, npyiter_opitflags *op_itf NAD_SHAPE(axisdata) = 1; NAD_INDEX(axisdata) = 0; memcpy(NAD_PTRS(axisdata), op_dataptr, NPY_SIZEOF_INTP*nop); + memset(NAD_STRIDES(axisdata), 0, NPY_SIZEOF_INTP*nop); } /* Now process the operands, filling in the axisdata */ diff --git a/numpy/core/src/multiarray/number.c b/numpy/core/src/multiarray/number.c index 2ad65bbe8..bb281835b 100644 --- a/numpy/core/src/multiarray/number.c +++ b/numpy/core/src/multiarray/number.c @@ -771,6 +771,7 @@ array_int(PyArrayObject *v) PyDataType_REFCHK(PyArray_DESCR((PyArrayObject *)pv))) { PyErr_SetString(PyExc_TypeError, "object array may be self-referencing"); + Py_DECREF(pv); return NULL; } @@ -812,6 +813,7 @@ array_float(PyArrayObject *v) PyDataType_REFCHK(PyArray_DESCR((PyArrayObject *)pv))) { PyErr_SetString(PyExc_TypeError, "object array may be self-referencing"); + Py_DECREF(pv); return NULL; } pv2 = Py_TYPE(pv)->tp_as_number->nb_float(pv); @@ -831,14 +833,19 @@ array_long(PyArrayObject *v) return NULL; } pv = PyArray_DESCR(v)->f->getitem(PyArray_DATA(v), v); + if (pv == NULL) { + return NULL; + } if (Py_TYPE(pv)->tp_as_number == 0) { PyErr_SetString(PyExc_TypeError, "cannot convert to an int; "\ "scalar object is not a number"); + Py_DECREF(pv); return NULL; } if (Py_TYPE(pv)->tp_as_number->nb_long == 0) { PyErr_SetString(PyExc_TypeError, "don't know how to convert "\ "scalar number to long"); + Py_DECREF(pv); return NULL; } /* @@ -849,6 +856,7 @@ array_long(PyArrayObject *v) PyDataType_REFCHK(PyArray_DESCR((PyArrayObject *)pv))) { PyErr_SetString(PyExc_TypeError, "object array may be self-referencing"); + Py_DECREF(pv); return NULL; } pv2 = Py_TYPE(pv)->tp_as_number->nb_long(pv); @@ -866,14 +874,19 @@ array_oct(PyArrayObject *v) return NULL; } pv = PyArray_DESCR(v)->f->getitem(PyArray_DATA(v), v); + if (pv == NULL) { + return NULL; + } if (Py_TYPE(pv)->tp_as_number == 0) { PyErr_SetString(PyExc_TypeError, "cannot convert to an int; "\ "scalar object is not a number"); + Py_DECREF(pv); return NULL; } if (Py_TYPE(pv)->tp_as_number->nb_oct == 0) { PyErr_SetString(PyExc_TypeError, "don't know how to convert "\ "scalar number to oct"); + Py_DECREF(pv); return NULL; } /* @@ -884,6 +897,7 @@ array_oct(PyArrayObject *v) PyDataType_REFCHK(PyArray_DESCR((PyArrayObject *)pv))) { PyErr_SetString(PyExc_TypeError, "object array may be self-referencing"); + Py_DECREF(pv); return NULL; } pv2 = Py_TYPE(pv)->tp_as_number->nb_oct(pv); @@ -901,14 +915,19 @@ array_hex(PyArrayObject *v) return NULL; } pv = PyArray_DESCR(v)->f->getitem(PyArray_DATA(v), v); + if (pv == NULL) { + return NULL; + } if (Py_TYPE(pv)->tp_as_number == 0) { PyErr_SetString(PyExc_TypeError, "cannot convert to an int; "\ "scalar object is not a number"); + Py_DECREF(pv); return NULL; } if (Py_TYPE(pv)->tp_as_number->nb_hex == 0) { PyErr_SetString(PyExc_TypeError, "don't know how to convert "\ "scalar number to hex"); + Py_DECREF(pv); return NULL; } /* @@ -919,6 +938,7 @@ array_hex(PyArrayObject *v) PyDataType_REFCHK(PyArray_DESCR((PyArrayObject *)pv))) { PyErr_SetString(PyExc_TypeError, "object array may be self-referencing"); + Py_DECREF(pv); return NULL; } pv2 = Py_TYPE(pv)->tp_as_number->nb_hex(pv); diff --git a/numpy/core/src/umath/test_rational.c.src b/numpy/core/src/umath/test_rational.c.src index 1650dd1d3..d8f90f9e5 100644 --- a/numpy/core/src/umath/test_rational.c.src +++ b/numpy/core/src/umath/test_rational.c.src @@ -1242,12 +1242,15 @@ PyMODINIT_FUNC inittest_rational(void) { PyErr_Format(PyExc_AssertionError, \ "ufunc %s takes %d arguments, our loop takes %ld", \ #name, ufunc->nargs, sizeof(_types)/sizeof(int)); \ + Py_DECREF(ufunc); \ goto fail; \ } \ if (PyUFunc_RegisterLoopForType((PyUFuncObject*)ufunc, npy_rational, \ rational_ufunc_##name, _types, 0) < 0) { \ + Py_DECREF(ufunc); \ goto fail; \ } \ + Py_DECREF(ufunc); \ } #define REGISTER_UFUNC_BINARY_RATIONAL(name) \ REGISTER_UFUNC(name, {npy_rational, npy_rational, npy_rational}) diff --git a/numpy/core/src/umath/ufunc_object.c b/numpy/core/src/umath/ufunc_object.c index 38091d5ff..a47d9a96c 100644 --- a/numpy/core/src/umath/ufunc_object.c +++ b/numpy/core/src/umath/ufunc_object.c @@ -5083,7 +5083,7 @@ ufunc_at(PyUFuncObject *ufunc, PyObject *args) } else { Py_INCREF(PyArray_DESCR(op1_array)); - array_operands[2] = new_array_op(op1_array, iter->dataptr); + array_operands[1] = new_array_op(op1_array, iter->dataptr); array_operands[2] = NULL; } diff --git a/numpy/core/tests/test_api.py b/numpy/core/tests/test_api.py index d642a2237..c4c9ad1b3 100644 --- a/numpy/core/tests/test_api.py +++ b/numpy/core/tests/test_api.py @@ -122,13 +122,13 @@ def test_array_array(): # Try with lists... assert_equal(np.array([None] * 10, dtype=np.float64), - np.empty((10,), dtype=np.float64) + np.nan) + np.full((10,), np.nan, dtype=np.float64)) assert_equal(np.array([[None]] * 10, dtype=np.float64), - np.empty((10, 1), dtype=np.float64) + np.nan) + np.full((10, 1), np.nan, dtype=np.float64)) assert_equal(np.array([[None] * 10], dtype=np.float64), - np.empty((1, 10), dtype=np.float64) + np.nan) + np.full((1, 10), np.nan, dtype=np.float64)) assert_equal(np.array([[None] * 10] * 10, dtype=np.float64), - np.empty((10, 10), dtype=np.float64) + np.nan) + np.full((10, 10), np.nan, dtype=np.float64)) assert_equal(np.array([1.0] * 10, dtype=np.float64), np.ones((10,), dtype=np.float64)) @@ -141,13 +141,13 @@ def test_array_array(): # Try with tuples assert_equal(np.array((None,) * 10, dtype=np.float64), - np.empty((10,), dtype=np.float64) + np.nan) + np.full((10,), np.nan, dtype=np.float64)) assert_equal(np.array([(None,)] * 10, dtype=np.float64), - np.empty((10, 1), dtype=np.float64) + np.nan) + np.full((10, 1), np.nan, dtype=np.float64)) assert_equal(np.array([(None,) * 10], dtype=np.float64), - np.empty((1, 10), dtype=np.float64) + np.nan) + np.full((1, 10), np.nan, dtype=np.float64)) assert_equal(np.array([(None,) * 10] * 10, dtype=np.float64), - np.empty((10, 10), dtype=np.float64) + np.nan) + np.full((10, 10), np.nan, dtype=np.float64)) assert_equal(np.array((1.0,) * 10, dtype=np.float64), np.ones((10,), dtype=np.float64)) diff --git a/numpy/core/tests/test_multiarray.py b/numpy/core/tests/test_multiarray.py index 9f333a4a2..9d191da35 100644 --- a/numpy/core/tests/test_multiarray.py +++ b/numpy/core/tests/test_multiarray.py @@ -1624,7 +1624,7 @@ class TestBinop(object): # Check behavior against both bare ndarray objects and a # ndarray subclasses with and without their own override - obj = cls((1,)) + obj = cls((1,), buffer=np.ones(1,)) arr_objs = [np.array([1]), np.array([2]).view(OtherNdarraySubclass), diff --git a/numpy/core/tests/test_regression.py b/numpy/core/tests/test_regression.py index 02cf1b8df..b98746e1b 100644 --- a/numpy/core/tests/test_regression.py +++ b/numpy/core/tests/test_regression.py @@ -1654,6 +1654,14 @@ class TestRegression(TestCase): assert_raises(TypeError, oct, a) assert_raises(TypeError, hex, a) + # Test the same for a circular reference. + b = np.array(a, dtype=object) + a[()] = b + assert_raises(TypeError, int, a) + # Numpy has no tp_traverse currently, so circular references + # cannot be detected. So resolve it: + a[()] = 0 + # This was causing a to become like the above a = np.array(0, dtype=object) a[...] += 1 @@ -1661,7 +1669,7 @@ class TestRegression(TestCase): def test_object_array_self_copy(self): # An object array being copied into itself DECREF'ed before INCREF'ing - # causing segmentation faults (gh-3787) + # causing segmentation faults (gh-3787) a = np.array(object(), dtype=object) np.copyto(a, a) assert_equal(sys.getrefcount(a[()]), 2) diff --git a/numpy/linalg/tests/test_linalg.py b/numpy/linalg/tests/test_linalg.py index d40157904..cc1404bf1 100644 --- a/numpy/linalg/tests/test_linalg.py +++ b/numpy/linalg/tests/test_linalg.py @@ -616,7 +616,7 @@ class TestLstsq(LinalgTestCase, LinalgNonsquareTestCase): expect_resids.shape = (1,) assert_equal(residuals.shape, expect_resids.shape) else: - expect_resids = type(x)([]) + expect_resids = np.array([]).view(type(x)) assert_almost_equal(residuals, expect_resids) assert_(np.issubdtype(residuals.dtype, np.floating)) assert_(imply(isinstance(b, matrix), isinstance(x, matrix))) |