summaryrefslogtreecommitdiff
path: root/numpy
diff options
context:
space:
mode:
authorMeekail Zain <34613774+Micky774@users.noreply.github.com>2022-06-13 16:55:04 -0400
committerGitHub <noreply@github.com>2022-06-13 13:55:04 -0700
commitcadfd83cb1e1df466eb91eb9c38dd2775455d64d (patch)
tree6ed4c3805fe0a5861345df3c8e56c5479d350524 /numpy
parent80e55b2dcecbd1475f74324847fa806d8159b9da (diff)
downloadnumpy-cadfd83cb1e1df466eb91eb9c38dd2775455d64d.tar.gz
ENH: issue overflow warning when using `abs` on `np.int8(-128)` (#21648)
Checks condition a == NPY_MIN_@NAME@ to determine whether an overflow error has occurred for np.int8 type. See #21289 and #21188 (comment) for reference. This also adds error integer overflow handling to the `-scalar` paths and "activates" a test for the unsigned versions. A few tests are skipped, because the tests were buggy (they never ran). These paths require followups to fix.
Diffstat (limited to 'numpy')
-rw-r--r--numpy/core/src/umath/scalarmath.c.src22
-rw-r--r--numpy/core/tests/test_scalarmath.py10
-rw-r--r--numpy/typing/tests/data/pass/arithmetic.py6
3 files changed, 31 insertions, 7 deletions
diff --git a/numpy/core/src/umath/scalarmath.c.src b/numpy/core/src/umath/scalarmath.c.src
index 4993546f8..412f171ec 100644
--- a/numpy/core/src/umath/scalarmath.c.src
+++ b/numpy/core/src/umath/scalarmath.c.src
@@ -584,10 +584,15 @@ static NPY_INLINE int
/**begin repeat
* #name = byte, short, int, long, longlong#
* #type = npy_byte, npy_short, npy_int, npy_long, npy_longlong#
+ * #NAME = BYTE, SHORT, INT, LONG, LONGLONG#
*/
static NPY_INLINE int
@name@_ctype_absolute(@type@ a, @type@ *out)
{
+ if (a == NPY_MIN_@NAME@) {
+ *out = a;
+ return NPY_FPE_OVERFLOW;
+ }
*out = (a < 0 ? -a : a);
return 0;
}
@@ -1564,8 +1569,23 @@ static PyObject *
val = PyArrayScalar_VAL(a, @Name@);
+ int retstatus = @name@_ctype_@oper@(val, &out);
- @name@_ctype_@oper@(val, &out);
+ if (retstatus) {
+ int bufsize, errmask;
+ PyObject *errobj;
+
+ if (PyUFunc_GetPyValues("@name@_scalars", &bufsize, &errmask,
+ &errobj) < 0) {
+ return NULL;
+ }
+ int first = 1;
+ if (PyUFunc_handlefperr(errmask, errobj, retstatus, &first)) {
+ Py_XDECREF(errobj);
+ return NULL;
+ }
+ Py_XDECREF(errobj);
+ }
/*
* TODO: Complex absolute should check floating point flags.
diff --git a/numpy/core/tests/test_scalarmath.py b/numpy/core/tests/test_scalarmath.py
index b7fe5183e..57937a7a9 100644
--- a/numpy/core/tests/test_scalarmath.py
+++ b/numpy/core/tests/test_scalarmath.py
@@ -897,8 +897,11 @@ def test_scalar_integer_operation_overflow(dtype, operation):
@pytest.mark.parametrize("dtype", np.typecodes["Integer"])
@pytest.mark.parametrize("operation", [
lambda min, neg_1: abs(min),
- lambda min, neg_1: min * neg_1,
- lambda min, neg_1: min // neg_1], ids=["abs", "*", "//"])
+ pytest.param(lambda min, neg_1: min * neg_1,
+ marks=pytest.mark.xfail(reason="broken on some platforms")),
+ pytest.param(lambda min, neg_1: min // neg_1,
+ marks=pytest.mark.skip(reason="broken on some platforms"))],
+ ids=["abs", "*", "//"])
def test_scalar_signed_integer_overflow(dtype, operation):
# The minimum signed integer can "overflow" for some additional operations
st = np.dtype(dtype).type
@@ -910,8 +913,7 @@ def test_scalar_signed_integer_overflow(dtype, operation):
@pytest.mark.parametrize("dtype", np.typecodes["UnsignedInteger"])
-@pytest.mark.xfail # TODO: the check is quite simply missing!
-def test_scalar_signed_integer_overflow(dtype):
+def test_scalar_unsigned_integer_overflow(dtype):
val = np.dtype(dtype).type(8)
with pytest.warns(RuntimeWarning, match="overflow encountered"):
-val
diff --git a/numpy/typing/tests/data/pass/arithmetic.py b/numpy/typing/tests/data/pass/arithmetic.py
index 4ed69c923..07a990127 100644
--- a/numpy/typing/tests/data/pass/arithmetic.py
+++ b/numpy/typing/tests/data/pass/arithmetic.py
@@ -2,6 +2,7 @@ from __future__ import annotations
from typing import Any
import numpy as np
+import pytest
c16 = np.complex128(1)
f8 = np.float64(1)
@@ -330,8 +331,9 @@ AR_O **= AR_LIKE_O
-f4
-i8
-i4
--u8
--u4
+with pytest.warns(RuntimeWarning):
+ -u8
+ -u4
-td
-AR_f