1
1
__precompile__ ()
2
2
module Quadmath
3
+ using Requires
3
4
4
- export Float128, Complex256
5
+ export Float128, ComplexF128
5
6
6
7
import Base: (* ), + , - , / , < , <= , == , ^ , convert,
7
8
reinterpret, sign_mask, exponent_mask, exponent_one, exponent_half,
8
9
significand_mask,
9
10
promote_rule, widen,
10
- string, print, show, showcompact, parse,
11
+ string, print, show, parse,
11
12
acos, acosh, asin, asinh, atan, atanh, cosh, cos,
12
- erf, erfc, exp, expm1, log, log2, log10, log1p, sin, sinh, sqrt,
13
+ exp, expm1, log, log2, log10, log1p, sin, sinh, sqrt,
13
14
tan, tanh,
14
- besselj, besselj0, besselj1, bessely, bessely0, bessely1,
15
- ceil, floor, trunc, round, fma,
16
- atan2, copysign, max, min, hypot,
17
- gamma, lgamma,
15
+ ceil, floor, trunc, round, fma,
16
+ copysign, max, min, hypot,
18
17
abs, imag, real, conj, angle, cis,
19
- eps, realmin, realmax, isinf, isnan, isfinite
18
+ eps, isinf, isnan, isfinite,
19
+ Int32,Int64,Float64
20
20
21
- if is_apple ()
21
+ if Sys . isapple ()
22
22
const quadoplib = " libquadmath.0"
23
23
const libquadmath = " libquadmath.0"
24
- elseif is_unix ()
25
- const quadoplib = " libgcc_s"
24
+ elseif Sys . isunix ()
25
+ const quadoplib = " libgcc_s.so.1 "
26
26
const libquadmath = " libquadmath.so.0"
27
- elseif is_windows ()
27
+ elseif Sys . iswindows ()
28
28
const quadoplib = " libgcc_s_seh-1.dll"
29
29
const libquadmath = " libquadmath-0.dll"
30
30
end
31
31
32
-
33
- @static if is_unix ()
32
+ @static if Sys. isunix ()
34
33
# we use this slightly cumbersome definition to ensure that the value is passed
35
34
# on the xmm registers, matching the x86_64 ABI for __float128.
36
- typealias Cfloat128 NTuple{2 ,VecElement{Float64}}
35
+ const Cfloat128 = NTuple{2 ,VecElement{Float64}}
37
36
38
- immutable Float128 <: AbstractFloat
37
+ struct Float128 <: AbstractFloat
39
38
data:: Cfloat128
40
39
end
41
- Float128 ( x:: Number ) = convert ( Float128, x)
40
+ convert ( :: Type{Float128} , x:: Number ) = Float128 ( x)
42
41
43
- typealias Complex256 Complex{Float128}
42
+ const ComplexF128 = Complex{Float128}
44
43
45
44
Base. cconvert (:: Type{Cfloat128} , x:: Float128 ) = x. data
46
45
62
61
reinterpret (Int128, reinterpret (UInt128, x))
63
62
reinterpret (:: Type{Float128} , x:: Int128 ) =
64
63
reinterpret (Float128, reinterpret (UInt128, x))
65
-
66
- elseif is_windows ()
67
- bitstype 128 Float128
68
- typealias Cfloat128 Float128
64
+
65
+ elseif Sys. iswindows ()
66
+ primitive type Float128 <: AbstractFloat 128
67
+ end
68
+ const Cfloat128 = Float128
69
+ end
70
+
71
+ function __init__ ()
72
+ @require SpecialFunctions= " 276daf66-3868-5448-9aa4-cd146d93841b" begin
73
+ using SpecialFunctions
74
+
75
+ SpecialFunctions. erf (x:: Float128 ) = Float128 (ccall ((:erfq , libquadmath), Cfloat128, (Cfloat128, ), x))
76
+ SpecialFunctions. erfc (x:: Float128 ) = Float128 (ccall ((:erfcq , libquadmath), Cfloat128, (Cfloat128, ), x))
77
+
78
+ SpecialFunctions. besselj0 (x:: Float128 ) = Float128 (ccall ((:j0q , libquadmath), Cfloat128, (Cfloat128, ), x))
79
+ SpecialFunctions. besselj1 (x:: Float128 ) = Float128 (ccall ((:j1q , libquadmath), Cfloat128, (Cfloat128, ), x))
80
+ SpecialFunctions. bessely0 (x:: Float128 ) = Float128 (ccall ((:y0q , libquadmath), Cfloat128, (Cfloat128, ), x))
81
+ SpecialFunctions. bessely1 (x:: Float128 ) = Float128 (ccall ((:y1q , libquadmath), Cfloat128, (Cfloat128, ), x))
82
+ SpecialFunctions. besselj (n:: Cint , x:: Float128 ) = Float128 (ccall ((:jnq , libquadmath), Cfloat128, (Cint, Cfloat128), n, x))
83
+ SpecialFunctions. bessely (n:: Cint , x:: Float128 ) = Float128 (ccall ((:ynq , libquadmath), Cfloat128, (Cint, Cfloat128), n, x))
84
+
85
+ SpecialFunctions. gamma (x:: Float128 ) = Float128 (ccall ((:tgammaq , libquadmath), Cfloat128, (Cfloat128, ), x))
86
+ SpecialFunctions. lgamma (x:: Float128 ) = Float128 (ccall ((:lgammaq , libquadmath), Cfloat128, (Cfloat128, ), x))
87
+ end
69
88
end
70
89
90
+
71
91
sign_mask (:: Type{Float128} ) = 0x8000_0000_0000_0000_0000_0000_0000_0000
72
92
exponent_mask (:: Type{Float128} ) = 0x7fff_0000_0000_0000_0000_0000_0000_0000
73
93
exponent_one (:: Type{Float128} ) = 0x3fff_0000_0000_0000_0000_0000_0000_0000
@@ -77,26 +97,28 @@ significand_mask(::Type{Float128}) = 0x0000_ffff_ffff_ffff_ffff_ffff_ffff_ffff
77
97
fpinttype (:: Type{Float128} ) = UInt128
78
98
79
99
# conversion
100
+ Float128 (x:: Float128 ) = x
80
101
81
102
# # Float64
82
- convert ( :: Type{ Float128} , x:: Float64 ) =
103
+ Float128 ( x:: Float64 ) =
83
104
Float128 (ccall ((:__extenddftf2 , quadoplib), Cfloat128, (Cdouble,), x))
84
- convert ( :: Type{ Float64} , x:: Float128 ) =
105
+ Float64 ( x:: Float128 ) =
85
106
ccall ((:__trunctfdf2 , quadoplib), Cdouble, (Cfloat128,), x)
86
107
87
- convert ( :: Type{ Int32} , x:: Float128 ) =
108
+ Int32 ( x:: Float128 ) =
88
109
ccall ((:__fixtfsi , quadoplib), Int32, (Cfloat128,), x)
89
- convert ( :: Type{ Float128} , x:: Int32 ) =
110
+ Float128 ( x:: Int32 ) =
90
111
Float128 (ccall ((:__floatsitf , quadoplib), Cfloat128, (Int32,), x))
91
112
92
- convert ( :: Type{ Float128} , x:: UInt32 ) =
113
+ Float128 ( x:: UInt32 ) =
93
114
Float128 (ccall ((:__floatunsitf , quadoplib), Cfloat128, (UInt32,), x))
94
115
95
- convert ( :: Type{ Int64} , x:: Float128 ) =
116
+ Int64 ( x:: Float128 ) =
96
117
ccall ((:__fixtfdi , quadoplib), Int64, (Cfloat128,), x)
97
- convert ( :: Type{ Float128} , x:: Int64 ) =
118
+ Float128 ( x:: Int64 ) =
98
119
Float128 (ccall ((:__floatditf , quadoplib), Cfloat128, (Int64,), x))
99
120
121
+ Float128 (x:: Rational{T} ) where T = Float128 (numerator (x))/ Float128 (denominator (x))
100
122
101
123
# comparison
102
124
@@ -121,37 +143,37 @@ convert(::Type{Float128}, x::Int64) =
121
143
Float128 (ccall ((:__divtf3 ,quadoplib), Cfloat128, (Cfloat128,Cfloat128), x, y))
122
144
(- )(x:: Float128 ) =
123
145
Float128 (ccall ((:__negtf2 ,quadoplib), Cfloat128, (Cfloat128,), x))
124
-
146
+ (^ )(x:: Float128 , y:: Float128 ) =
147
+ Float128 (ccall ((:powq , libquadmath), Cfloat128, (Cfloat128,Cfloat128), x, y))
125
148
# math
126
149
127
150
# # one argument
128
151
for f in (:acos , :acosh , :asin , :asinh , :atan , :atanh , :cosh , :cos ,
129
152
:erf , :erfc , :exp , :expm1 , :log , :log2 , :log10 , :log1p ,
130
- :sin , :sinh , :sqrt , :tan , :tanh ,
131
- :ceil , :floor , :trunc , :lgamma , )
153
+ :sin , :sinh , :sqrt , :tan , :tanh ,
154
+ :ceil , :floor , :trunc , )
132
155
@eval function $f (x:: Float128 )
133
156
Float128 (ccall (($ (string (f,:q )), libquadmath), Cfloat128, (Cfloat128, ), x))
134
157
end
135
158
end
136
159
for (f,fc) in (:abs => :fabs ,
137
- :round => :rint ,
138
- :gamma => :tgamma ,
139
- :besselj0 => :j0 ,
140
- :besselj1 => :j1 ,
141
- :bessely0 => :y0 ,
142
- :bessely1 => :y1 ,)
160
+ :round => :rint ,)
143
161
@eval function $f (x:: Float128 )
144
162
Float128 (ccall (($ (string (fc,:q )), libquadmath), Cfloat128, (Cfloat128, ), x))
145
163
end
146
164
end
147
165
148
166
# # two argument
149
- for f in (:atan2 , : copysign , :hypot , )
167
+ for f in (:copysign , :hypot , )
150
168
@eval function $f (x:: Float128 , y:: Float128 )
151
169
Float128 (ccall (($ (string (f,:q )), libquadmath), Cfloat128, (Cfloat128, Cfloat128), x, y))
152
170
end
153
171
end
154
172
173
+ function atan (x:: Float128 , y:: Float128 )
174
+ Float128 (ccall ((:atan2q , libquadmath), Cfloat128, (Cfloat128, Cfloat128), x, y))
175
+ end
176
+
155
177
# # misc
156
178
fma (x:: Float128 , y:: Float128 , z:: Float128 ) =
157
179
Float128 (ccall ((:fmaq ,libquadmath), Cfloat128, (Cfloat128, Cfloat128, Cfloat128), x, y, z))
@@ -163,12 +185,11 @@ isinf(x::Float128) =
163
185
isfinite (x:: Float128 ) =
164
186
0 != ccall ((:finiteq ,libquadmath), Cint, (Cfloat128, ), x)
165
187
166
- besselj (n:: Cint , x:: Float128 ) =
167
- Float128 (ccall ((:jnq , libquadmath), Cfloat128, (Cint, Cfloat128), n, x))
168
- bessely (n:: Cint , x:: Float128 ) =
169
- Float128 (ccall ((:ynq , libquadmath), Cfloat128, (Cint, Cfloat128), n, x))
170
-
171
-
188
+ eps (:: Type{Float128} ) = reinterpret (Float128, 0x3f8f0000000000000000000000000000 )
189
+ realmin (:: Type{Float128} ) = reinterpret (Float128, 0x00010000000000000000000000000000 )
190
+ realmax (:: Type{Float128} ) = reinterpret (Float128, 0x7ffeffffffffffffffffffffffffffff )
191
+ Float128 (:: Irrational{:π} ) = reinterpret (Float128, 0x4000921fb54442d18469898cc51701b8 )
192
+ Float128 (:: Irrational{:e} ) = reinterpret (Float128, 0x40005bf0a8b1457695355fb8ac404e7a )
172
193
173
194
174
195
ldexp (x:: Float128 , n:: Cint ) =
@@ -181,12 +202,11 @@ function frexp(x::Float128)
181
202
Float128 (ccall ((:frexpq , libquadmath), Cfloat128, (Cfloat128, Ptr{Cint}), x, r))
182
203
return x, Int (r[])
183
204
end
184
-
185
-
186
-
187
205
206
+ promote_rule (:: Type{Float128} , :: Type{Float16} ) = Float128
188
207
promote_rule (:: Type{Float128} , :: Type{Float32} ) = Float128
189
208
promote_rule (:: Type{Float128} , :: Type{Float64} ) = Float128
209
+ promote_rule (:: Type{Float128} , :: Type{<:Integer} ) = Float128
190
210
191
211
# widen(::Type{Float64}) = Float128
192
212
widen (:: Type{Float128} ) = BigFloat
@@ -197,14 +217,13 @@ function parse(::Type{Float128}, s::AbstractString)
197
217
end
198
218
199
219
function string (x:: Float128 )
200
- lng = 64
201
- buf = Array ( UInt8, lng + 1 )
220
+ lng = 64
221
+ buf = Array { UInt8} (undef , lng + 1 )
202
222
lng = ccall ((:quadmath_snprintf ,libquadmath), Cint, (Ptr{UInt8}, Csize_t, Ptr{UInt8}, Cfloat128... ), buf, lng + 1 , " %.35Qe" , x)
203
- return unsafe_string ( pointer (buf) , lng)
223
+ return String ( resize! (buf, lng) )
204
224
end
205
225
206
226
print (io:: IO , b:: Float128 ) = print (io, string (b))
207
227
show (io:: IO , b:: Float128 ) = print (io, string (b))
208
- showcompact (io:: IO , b:: Float128 ) = print (io, string (b))
209
228
210
229
end # modeule Quadmath
0 commit comments