Trying to get this packaged for Gentoo linux on the RISC-V architecture and ran into two failures. Note: we already include your 32-bit patch from #60 (though this isn't a 32-bit system).
=================================================================== short test summary info ===================================================================
FAILED test/test_encode.py::test_encode[binary64] - OverflowError: Python int too large to convert to C long
FAILED test/test_encode.py::test_encode_edges[encode_ndarray-binary64] - OverflowError: Python int too large to convert to C long
========================================================== 2 failed, 453 passed in 335.29s (0:05:35) ==========================================================
And the full failures.
____________________________________________________________________ test_encode[binary64] ____________________________________________________________________
fi = FormatInfo(name='binary64', k=64, precision=53, bias=1023, is_signed=True, domain=<Domain.Extended: 2>, has_nz=True, num_high_nans=4503599627370495, has_subnormals=True, is_twos_complement=False)
@pytest.mark.parametrize("fi", sample_formats)
def test_encode(fi: FormatInfo) -> None:
dec = lambda v: decode_float(fi, v).fval
if fi.bits <= 8:
step = 1
elif fi.bits <= 16:
step = 13
elif fi.bits <= 32:
step = 73013
elif fi.bits <= 64:
step = (73013 << 32) + 39
for i in range(0, 2**fi.bits, step):
fv = decode_float(fi, i)
code = encode_float(fi, fv.fval)
assert (i == code) or (np.isnan(fv.fval) and code == fi.code_of_nan)
fv2 = decode_float(fi, code)
np.testing.assert_equal(fv2.fval, fv.fval)
codes = np.arange(0, 2**fi.bits, step, dtype=np.uint64)
fvals = np.array([decode_float(fi, int(i)).fval for i in codes])
> enc_codes = encode_ndarray(fi, fvals)
^^^^^^^^^^^^^^^^^^^^^^^^^
code = 18446744073709551615
codes = array([ 0, 313588447182887, 627176894365774,
..., 18445899640191779114, 18446213228638962001,
18446526817086144888], shape=(58825,), dtype=uint64)
dec = <function test_encode.<locals>.<lambda> at 0x3bae800460>
fi = FormatInfo(name='binary64',
k=64,
precision=53,
bias=1023,
is_signed=True,
domain=<Domain.Extended: 2>,
has_nz=True,
num_high_nans=4503599627370495,
has_subnormals=True,
is_twos_complement=False)
fv = FloatValue(code=18446526817086144888,
fval=nan,
exp=2047,
expval=1024,
significand=4286343003963768,
fsignificand=1.9517593388883068,
signbit=1,
fclass=<FloatClass.NAN: 5>)
fv2 = FloatValue(code=18446744073709551615,
fval=nan,
exp=2047,
expval=1024,
significand=4503599627370495,
fsignificand=1.9999999999999998,
signbit=1,
fclass=<FloatClass.NAN: 5>)
fvals = array([0.00000000e+000, 1.54933279e-309, 3.09866557e-309, ...,
nan, nan, nan], shape=(58825,))
i = 18446526817086144888
step = 313588447182887
test/test_encode.py:35:
_ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
fi = FormatInfo(name='binary64', k=64, precision=53, bias=1023, is_signed=True, domain=<Domain.Extended: 2>, has_nz=True, num_high_nans=4503599627370495, has_subnormals=True, is_twos_complement=False)
v = array([0.00000000e+000, 1.54933279e-309, 3.09866557e-309, ...,
nan, nan, nan], shape=(58825,))
def encode_ndarray(fi: FormatInfo, v: npt.NDArray) -> npt.NDArray:
"""
Vectorized version of :meth:`encode_float`.
Encode inputs to the given :py:class:`FormatInfo`.
Will round toward zero if :paramref:`v` is not in the value set.
Will saturate to `Inf`, `NaN`, `fi.max` in order of precedence.
Encode -0 to 0 if not `fi.has_nz`
For other roundings and saturations, call :func:`round_ndarray` first.
Args:
fi (FormatInfo): Describes the target format
v (float array): The value to be encoded.
Returns:
The integer code point
"""
k = fi.bits
p = fi.precision
t = p - 1
sign = np.signbit(v) & fi.is_signed
vpos = np.where(sign, -v, v)
nan_mask = np.isnan(v)
code = np.zeros_like(v, dtype=np.uint64)
if fi.num_nans > 0:
code[nan_mask] = fi.code_of_nan
else:
assert not np.any(nan_mask)
if fi.domain == Domain.Extended:
code[v > fi.max] = fi.code_of_posinf
if fi.is_signed:
code[v < fi.min] = fi.code_of_neginf
else:
code[v > fi.max] = fi.code_of_nan if fi.num_nans > 0 else fi.code_of_max
if fi.is_signed:
code[v < fi.min] = fi.code_of_nan if fi.num_nans > 0 else fi.code_of_min
if fi.has_zero:
if fi.has_nz:
> code[v == 0] = np.where(sign[v == 0], fi.code_of_negzero, fi.code_of_zero)
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
E OverflowError: Python int too large to convert to C long
code = array([ 0, 0, 0,
..., 18446744073709551615, 18446744073709551615,
18446744073709551615], shape=(58825,), dtype=uint64)
fi = FormatInfo(name='binary64',
k=64,
precision=53,
bias=1023,
is_signed=True,
domain=<Domain.Extended: 2>,
has_nz=True,
num_high_nans=4503599627370495,
has_subnormals=True,
is_twos_complement=False)
k = 64
nan_mask = array([False, False, False, ..., True, True, True], shape=(58825,))
p = 53
sign = array([False, False, False, ..., False, False, False], shape=(58825,))
t = 52
v = array([0.00000000e+000, 1.54933279e-309, 3.09866557e-309, ...,
nan, nan, nan], shape=(58825,))
vpos = array([0.00000000e+000, 1.54933279e-309, 3.09866557e-309, ...,
nan, nan, nan], shape=(58825,))
../gfloat-0.5.2-python3_14/install/usr/lib/python3.14/site-packages/gfloat/encode_ndarray.py:54: OverflowError
_________________________________________________________ test_encode_edges[encode_ndarray-binary64] __________________________________________________________
fi = FormatInfo(name='binary64', k=64, precision=53, bias=1023, is_signed=True, domain=<Domain.Extended: 2>, has_nz=True, num_high_nans=4503599627370495, has_subnormals=True, is_twos_complement=False)
enc = <function test_encode_edges.<locals>.<lambda> at 0x3bae845220>
@pytest.mark.parametrize("fi", sample_formats)
@pytest.mark.parametrize("enc", (encode_float, encode_ndarray))
def test_encode_edges(fi: FormatInfo, enc: Callable) -> None:
if enc == encode_ndarray:
enc = lambda fi, x: encode_ndarray(fi, np.array([x])).item()
> assert enc(fi, fi.max) == fi.code_of_max
^^^^^^^^^^^^^^^
enc = <function test_encode_edges.<locals>.<lambda> at 0x3bae845220>
fi = FormatInfo(name='binary64',
k=64,
precision=53,
bias=1023,
is_signed=True,
domain=<Domain.Extended: 2>,
has_nz=True,
num_high_nans=4503599627370495,
has_subnormals=True,
is_twos_complement=False)
test/test_encode.py:51:
_ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
test/test_encode.py:49: in <lambda>
enc = lambda fi, x: encode_ndarray(fi, np.array([x])).item()
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
fi = FormatInfo(name='binary64',
k=64,
precision=53,
bias=1023,
is_signed=True,
domain=<Domain.Extended: 2>,
has_nz=True,
num_high_nans=4503599627370495,
has_subnormals=True,
is_twos_complement=False)
x = 1.7976931348623157e+308
_ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
fi = FormatInfo(name='binary64', k=64, precision=53, bias=1023, is_signed=True, domain=<Domain.Extended: 2>, has_nz=True, num_high_nans=4503599627370495, has_subnormals=True, is_twos_complement=False)
v = array([1.79769313e+308])
def encode_ndarray(fi: FormatInfo, v: npt.NDArray) -> npt.NDArray:
"""
Vectorized version of :meth:`encode_float`.
Encode inputs to the given :py:class:`FormatInfo`.
Will round toward zero if :paramref:`v` is not in the value set.
Will saturate to `Inf`, `NaN`, `fi.max` in order of precedence.
Encode -0 to 0 if not `fi.has_nz`
For other roundings and saturations, call :func:`round_ndarray` first.
Args:
fi (FormatInfo): Describes the target format
v (float array): The value to be encoded.
Returns:
The integer code point
"""
k = fi.bits
p = fi.precision
t = p - 1
sign = np.signbit(v) & fi.is_signed
vpos = np.where(sign, -v, v)
nan_mask = np.isnan(v)
code = np.zeros_like(v, dtype=np.uint64)
if fi.num_nans > 0:
code[nan_mask] = fi.code_of_nan
else:
assert not np.any(nan_mask)
if fi.domain == Domain.Extended:
code[v > fi.max] = fi.code_of_posinf
if fi.is_signed:
code[v < fi.min] = fi.code_of_neginf
else:
code[v > fi.max] = fi.code_of_nan if fi.num_nans > 0 else fi.code_of_max
if fi.is_signed:
code[v < fi.min] = fi.code_of_nan if fi.num_nans > 0 else fi.code_of_min
if fi.has_zero:
if fi.has_nz:
> code[v == 0] = np.where(sign[v == 0], fi.code_of_negzero, fi.code_of_zero)
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
E OverflowError: Python int too large to convert to C long
code = array([0], dtype=uint64)
fi = FormatInfo(name='binary64',
k=64,
precision=53,
bias=1023,
is_signed=True,
domain=<Domain.Extended: 2>,
has_nz=True,
num_high_nans=4503599627370495,
has_subnormals=True,
is_twos_complement=False)
k = 64
nan_mask = array([False])
p = 53
sign = array([False])
t = 52
v = array([1.79769313e+308])
vpos = array([1.79769313e+308])
../gfloat-0.5.2-python3_14/install/usr/lib/python3.14/site-packages/gfloat/encode_ndarray.py:54: OverflowError
Trying to get this packaged for Gentoo linux on the RISC-V architecture and ran into two failures. Note: we already include your 32-bit patch from #60 (though this isn't a 32-bit system).
If it helps,
sizeof(long) == 8on this machine.Summary:
And the full failures.
test_encode[binary64]:
test_encode_edges[encode_ndarray-binary64]: