Skip to content

Commit 47c49f0

Browse files
Merge pull request #204 from araujoms/main
Fix inf and nan bugs
2 parents 9e9d5b3 + 60e845c commit 47c49f0

9 files changed

+50
-34
lines changed

src/math/elementary/explog.jl

+1-1
Original file line numberDiff line numberDiff line change
@@ -259,7 +259,7 @@ end
259259

260260
function log1p(x::DoubleFloat{T}) where {T<:IEEEFloat}
261261
isnan(x) && return x
262-
isinf(x) && !signbit(x) && return
262+
isinf(x) && !signbit(x) && return x
263263
u = 1.0 + x
264264
if u == one(DoubleFloat{T})
265265
x

src/math/ops.jl

+1-1
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,7 @@ isnotfinite(x::Float32) = reinterpret(UInt32,x) & 0x7f800000 === 0x7f800000
66
isqnan(x::Float32) = reinterpret(UInt32,x) & 0x7fc00000 === 0x7fc00000
77
isainf(x::Float32) = reinterpret(UInt32,x) & 0x7fc00000 === 0x7f800000
88

9-
isnotfinite(x::DoubleFloat{T}) where {T<:IEEEFloat} = isnan(LO(x))
9+
isnotfinite(x::DoubleFloat{T}) where {T<:IEEEFloat} = !isfinite(HI(x))
1010
isqnan(x::DoubleFloat{T}) where {T<:IEEEFloat} = isqnan(HI(x))
1111
isainf(x::DoubleFloat{T}) where {T<:IEEEFloat} = isainf(HI(x))
1212

src/math/ops/op_dbdb_db.jl

+8-8
Original file line numberDiff line numberDiff line change
@@ -12,41 +12,41 @@ Base.:(/)(x::Tuple{T,T}, y::DoubleFloat{T}) where {T<:IEEEFloat} = DoubleFloat{T
1212

1313

1414
@inline function add_dbdb_db(x::DoubleFloat{T}, y::DoubleFloat{T}) where {T<:IEEEFloat}
15-
(isnan(LO(x)) | isnan(LO(y))) && return add_dbdb_db_nonfinite(x,y)
15+
(isnotfinite(x) | isnotfinite(y)) && return add_dbdb_db_nonfinite(x,y)
1616
return DoubleFloat{T}(add_dddd_dd(HILO(x), HILO(y)))
1717
end
1818

1919
@inline function sub_dbdb_db(x::DoubleFloat{T}, y::DoubleFloat{T}) where {T<:IEEEFloat}
20-
(isnan(LO(x)) | isnan(LO(y))) && return sub_dbdb_db_nonfinite(x,y)
20+
(isnotfinite(x) | isnotfinite(y)) && return sub_dbdb_db_nonfinite(x,y)
2121
return DoubleFloat{T}(sub_dddd_dd(HILO(x), HILO(y)))
2222
end
2323

2424
@inline function mul_dbdb_db(x::DoubleFloat{T}, y::DoubleFloat{T}) where {T<:IEEEFloat}
25-
(isnan(LO(x)) | isnan(LO(y))) && return mul_dbdb_db_nonfinite(x,y)
25+
(isnotfinite(x) | isnotfinite(y)) && return mul_dbdb_db_nonfinite(x,y)
2626
return DoubleFloat{T}(mul_dddd_dd(HILO(x), HILO(y)))
2727
end
2828

2929
@inline function dvi_dbdb_db(x::DoubleFloat{T}, y::DoubleFloat{T}) where {T<:IEEEFloat}
30-
(iszero(HI(y)) | isnan(LO(x)) | isnan(LO(y))) && return dvi_dbdb_db_nonfinite(x,y)
30+
(iszero(HI(y)) | isnotfinite(x) | isnotfinite(y)) && return dvi_dbdb_db_nonfinite(x,y)
3131
return DoubleFloat{T}(dvi_dddd_dd(HILO(x), HILO(y)))
3232
end
3333

3434
@inline function add_dbdb_db_nonfinite(x::DoubleFloat{T}, y::DoubleFloat{T}) where {T<:IEEEFloat}
3535
z = HI(x) + HI(y)
36-
return DoubleFloat{T}(z, T(NaN))
36+
return DoubleFloat{T}(z, z)
3737
end
3838

3939
@inline function sub_dbdb_db_nonfinite(x::DoubleFloat{T}, y::DoubleFloat{T}) where {T<:IEEEFloat}
4040
z = HI(x) - HI(y)
41-
return DoubleFloat{T}(z, T(NaN))
41+
return DoubleFloat{T}(z, z)
4242
end
4343

4444
@inline function mul_dbdb_db_nonfinite(x::DoubleFloat{T}, y::DoubleFloat{T}) where {T<:IEEEFloat}
4545
z = HI(x) * HI(y)
46-
return DoubleFloat{T}(z, T(NaN))
46+
return DoubleFloat{T}(z, z)
4747
end
4848

4949
@inline function dvi_dbdb_db_nonfinite(x::DoubleFloat{T}, y::DoubleFloat{T}) where {T<:IEEEFloat}
5050
z = HI(x) / HI(y)
51-
return DoubleFloat{T}(z, T(NaN))
51+
return DoubleFloat{T}(z, z)
5252
end

src/math/ops/op_dbfp_db.jl

+8-8
Original file line numberDiff line numberDiff line change
@@ -1,39 +1,39 @@
11
@inline function add_dbfp_db(x::DoubleFloat{T}, y::T) where {T<:IEEEFloat}
2-
(isqnan(LO(x)) | isnotfinite(y)) && return add_dbfp_db_nonfinite(x,y)
2+
(isnotfinite(x) | isnotfinite(y)) && return add_dbfp_db_nonfinite(x,y)
33
return DoubleFloat{T}(add_ddfp_dd(HILO(x), y))
44
end
55

66
@inline function sub_dbfp_db(x::DoubleFloat{T}, y::T) where {T<:IEEEFloat}
7-
(isqnan(LO(x)) | isnotfinite(y)) && return sub_dbfp_db_nonfinite(x,y)
7+
(isnotfinite(x) | isnotfinite(y)) && return sub_dbfp_db_nonfinite(x,y)
88
return DoubleFloat{T}(sub_ddfp_dd(HILO(x), y))
99
end
1010

1111
@inline function mul_dbfp_db(x::DoubleFloat{T}, y::T) where {T<:IEEEFloat}
12-
(isqnan(LO(x)) | isnotfinite(y)) && return mul_dbfp_db_nonfinite(x,y)
12+
(isnotfinite(x) | isnotfinite(y)) && return mul_dbfp_db_nonfinite(x,y)
1313
return DoubleFloat{T}(mul_ddfp_dd(HILO(x), y))
1414
end
1515

1616
@inline function dvi_dbfp_db(x::DoubleFloat{T}, y::T) where {T<:IEEEFloat}
17-
(isqnan(LO(x)) | isnotfinite(y)) && return dvi_dbfp_db_nonfinite(x,y)
17+
(isnotfinite(x) | isnotfinite(y)) && return dvi_dbfp_db_nonfinite(x,y)
1818
return DoubleFloat{T}(dvi_ddfp_dd(HILO(x), y))
1919
end
2020

2121
@inline function add_dbfp_db_nonfinite(x::DoubleFloat{T}, y::T) where {T<:IEEEFloat}
2222
z = HI(x) + y
23-
return DoubleFloat{T}(z, T(NaN))
23+
return DoubleFloat{T}(z, z)
2424
end
2525

2626
@inline function sub_dbfp_db_nonfinite(x::DoubleFloat{T}, y::T) where {T<:IEEEFloat}
2727
z = HI(x) - y
28-
return DoubleFloat{T}(z, T(NaN))
28+
return DoubleFloat{T}(z, z)
2929
end
3030

3131
@inline function mul_dbfp_db_nonfinite(x::DoubleFloat{T}, y::T) where {T<:IEEEFloat}
3232
z = HI(x) * y
33-
return DoubleFloat{T}(z, T(NaN))
33+
return DoubleFloat{T}(z, z)
3434
end
3535

3636
@inline function dvi_dbfp_db_nonfinite(x::DoubleFloat{T}, y::T) where {T<:IEEEFloat}
3737
z = HI(x) / y
38-
return DoubleFloat{T}(z, T(NaN))
38+
return DoubleFloat{T}(z, z)
3939
end

src/math/ops/op_dd_dd.jl

+3-2
Original file line numberDiff line numberDiff line change
@@ -56,8 +56,9 @@ end
5656
end
5757

5858
function sqrt_dd_dd(x::Tuple{T,T}) where {T<:IEEEFloat}
59-
iszero(HI(x)) && return x
60-
signbit(HI(x)) && throw(DomainError("sqrt(x) expects x >= 0"))
59+
(isnan(HI(x)) | iszero(HI(x))) && return x
60+
signbit(HI(x)) && Base.Math.throw_complex_domainerror(:sqrt, HI(x))
61+
isinf(HI(x)) && return x
6162

6263
ahi, alo = HILO(x)
6364
s = sqrt(ahi)

src/math/ops/op_fpdb_db.jl

+8-8
Original file line numberDiff line numberDiff line change
@@ -1,39 +1,39 @@
11
@inline function add_fpdb_db(x::T, y::DoubleFloat{T}) where {T<:IEEEFloat}
2-
(isnotfinite(x) | isqnan(LO(y))) && return add_fpdb_db_nonfinite(x,y)
2+
(isnotfinite(x) | isnotfinite(y)) && return add_fpdb_db_nonfinite(x,y)
33
return DoubleFloat{T}(add_fpdd_dd(x, HILO(y)))
44
end
55

66
@inline function sub_fpdb_db(x::T, y::DoubleFloat{T}) where {T<:IEEEFloat}
7-
(isnotfinite(x) | isqnan(LO(y))) && return sub_fpdb_db_nonfinite(x,y)
7+
(isnotfinite(x) | isnotfinite(y)) && return sub_fpdb_db_nonfinite(x,y)
88
return DoubleFloat{T}(sub_fpdd_dd(x, HILO(y)))
99
end
1010

1111
@inline function mul_fpdb_db(x::T, y::DoubleFloat{T}) where {T<:IEEEFloat}
12-
(isnotfinite(x) | isqnan(LO(y))) && return mul_fpdb_db_nonfinite(x,y)
12+
(isnotfinite(x) | isnotfinite(y)) && return mul_fpdb_db_nonfinite(x,y)
1313
return DoubleFloat{T}(mul_fpdd_dd(x, HILO(y)))
1414
end
1515

1616
@inline function dvi_fpdb_db(x::T, y::DoubleFloat{T}) where {T<:IEEEFloat}
17-
(isnotfinite(x) | isqnan(LO(y))) && return dvi_fpdb_db_nonfinite(x,y)
17+
(isnotfinite(x) | isnotfinite(y)) && return dvi_fpdb_db_nonfinite(x,y)
1818
return DoubleFloat{T}(dvi_fpdd_dd(x, HILO(y)))
1919
end
2020

2121
@inline function add_fpdb_db_nonfinite(x::T, y::DoubleFloat{T}) where {T<:IEEEFloat}
2222
z = x + HI(y)
23-
return DoubleFloat{T}(z, T(NaN))
23+
return DoubleFloat{T}(z, z)
2424
end
2525

2626
@inline function sub_fpdb_db_nonfinite(x::T, y::DoubleFloat{T}) where {T<:IEEEFloat}
2727
z = x - HI(y)
28-
return DoubleFloat{T}(z, T(NaN))
28+
return DoubleFloat{T}(z, z)
2929
end
3030

3131
@inline function mul_fpdb_db_nonfinite(x::T, y::DoubleFloat{T}) where {T<:IEEEFloat}
3232
z = x * HI(y)
33-
return DoubleFloat{T}(z, T(NaN))
33+
return DoubleFloat{T}(z, z)
3434
end
3535

3636
@inline function dvi_fpdb_db_nonfinite(x::T, y::DoubleFloat{T}) where {T<:IEEEFloat}
3737
z = x / HI(y)
38-
return DoubleFloat{T}(z, T(NaN))
38+
return DoubleFloat{T}(z, z)
3939
end

src/type/predicates.jl

+3-3
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
""""
1+
"""
22
__Predicates__ are functions that ask "yes or no" questions of their argument[s].
33
You can ask of a number "Is this zero?" or "Is this one?" and these predicates
44
(`iszero`, `isone`) will work as expected with almost all numerical types.
@@ -87,10 +87,10 @@ isinf(x::DoubleFloat{T}) where {T<:IEEEFloat} =
8787
"""
8888
isposinf(x)
8989
90-
Tests whether a number positive and infinite.
90+
Tests whether a number is positive and infinite.
9191
"""
9292
isposinf(x::DoubleFloat{T}) where {T<:IEEEFloat} =
93-
isinf(HI(x))
93+
isinf(HI(x)) && !signbit(HI(x))
9494

9595
"""
9696
isneginf(x)

src/type/specialvalues.jl

+3-3
Original file line numberDiff line numberDiff line change
@@ -2,9 +2,9 @@ zero(::Type{DoubleFloat{T}}) where {T<:IEEEFloat} = DoubleFloat{T}(zero(T), zero
22
one(::Type{DoubleFloat{T}}) where {T<:IEEEFloat} = DoubleFloat{T}(one(T), zero(T))
33

44
nan(::Type{DoubleFloat{T}}) where {T<:IEEEFloat} = DoubleFloat{T}(T(NaN), T(NaN))
5-
inf(::Type{DoubleFloat{T}}) where {T<:IEEEFloat} = DoubleFloat{T}(T(Inf), T(NaN))
6-
posinf(::Type{DoubleFloat{T}}) where {T<:IEEEFloat} = DoubleFloat{T}(T(Inf), T(NaN))
7-
neginf(::Type{DoubleFloat{T}}) where {T<:IEEEFloat} = DoubleFloat{T}(T(-Inf), T(NaN))
5+
inf(::Type{DoubleFloat{T}}) where {T<:IEEEFloat} = DoubleFloat{T}(T(Inf), T(Inf))
6+
posinf(::Type{DoubleFloat{T}}) where {T<:IEEEFloat} = DoubleFloat{T}(T(Inf), T(Inf))
7+
neginf(::Type{DoubleFloat{T}}) where {T<:IEEEFloat} = DoubleFloat{T}(T(-Inf), T(-Inf))
88

99
typemax(::Type{DoubleFloat{T}}) where {T<:IEEEFloat} = DoubleFloat{T}(typemax(T))
1010
typemin(::Type{DoubleFloat{T}}) where {T<:IEEEFloat} = DoubleFloat{T}(typemin(T))

test/specialvalues.jl

+15
Original file line numberDiff line numberDiff line change
@@ -13,16 +13,19 @@ end
1313
@test isinf(T(Inf)) == isinf(inf(T))
1414
@test isinf(T(Inf)) == isposinf(posinf(T))
1515
@test isinf(T(-Inf)) == isneginf(neginf(T))
16+
@test isinf(T(-Inf)) == !isposinf(neginf(T))
1617
@test isnan(T(NaN)) == isnan(nan(T))
1718

1819
@test isinf(T(Inf32)) == isinf(inf(T))
1920
@test isinf(T(Inf32)) == isposinf(posinf(T))
2021
@test isinf(T(-Inf32)) == isneginf(neginf(T))
22+
@test isinf(T(-Inf32)) == !isposinf(neginf(T))
2123
@test isnan(T(NaN32)) == isnan(nan(T))
2224

2325
@test isinf(T(Inf16)) == isinf(inf(T))
2426
@test isinf(T(Inf16)) == isposinf(posinf(T))
2527
@test isinf(T(-Inf16)) == isneginf(neginf(T))
28+
@test isinf(T(-Inf16)) == !isposinf(neginf(T))
2629
@test isnan(T(NaN16)) == isnan(nan(T))
2730
end
2831

@@ -76,6 +79,18 @@ end
7679
@test isnan(asech(T(NaN)))
7780
@test isnan(acoth(T(NaN)))
7881
end
82+
83+
@testset "Inf and NaN function values $T" for T in (Double16, Double32, Double64)
84+
@test isnan(sqrt(T(0)/T(0)))
85+
@test isinf(sqrt(T(Inf)))
86+
@test isinf(exp(T(Inf)))
87+
@test isinf(log(T(Inf)))
88+
@test isinf(log2(T(Inf)))
89+
@test isinf(log10(T(Inf)))
90+
@test isinf(log1p(T(Inf)))
91+
@test isinf(T(Inf)*T(1))
92+
@test isinf(T(1)*T(Inf))
93+
end
7994

8095
@testset "floatmin2 $T" for T in (Double16, Double32, Double64)
8196
trueval = (twopar = 2one(T); twopar^trunc(Integer,log(floatmin(T)/eps(T))/log(twopar)/twopar))

0 commit comments

Comments
 (0)