Skip to content

Commit cb4bf07

Browse files
authored
flambda-backend: float32 otherlib (#2492)
1 parent 36c1bb8 commit cb4bf07

File tree

20 files changed

+1731
-208
lines changed

20 files changed

+1731
-208
lines changed

boot/ocamllex

1.45 KB
Binary file not shown.

bytecomp/bytegen.ml

+2-1
Original file line numberDiff line numberDiff line change
@@ -868,7 +868,8 @@ let rec comp_expr stack_info env exp sz cont =
868868
end
869869
| Lprim((Popaque _ | Pobj_magic _), [arg], _) ->
870870
comp_expr stack_info env arg sz cont
871-
| Lprim((Pbox_float (Pfloat64, _) | Punbox_float Pfloat64), [arg], _) ->
871+
| Lprim((Pbox_float ((Pfloat64 | Pfloat32), _)
872+
| Punbox_float (Pfloat64 | Pfloat32)), [arg], _) ->
872873
comp_expr stack_info env arg sz cont
873874
| Lprim((Pbox_int _ | Punbox_int _), [arg], _) ->
874875
comp_expr stack_info env arg sz cont

bytecomp/symtable.ml

+5-1
Original file line numberDiff line numberDiff line change
@@ -144,11 +144,15 @@ let output_primitive_table outchan =
144144

145145
(* Translate structured constants *)
146146

147+
(* We cannot use the [float32] type in the compiler, so we represent it as an
148+
opaque [Obj.t]. This is sufficient for interfacing with the runtime. *)
149+
external float32_of_string : string -> Obj.t = "caml_float32_of_string"
150+
147151
let rec transl_const = function
148152
Const_base(Const_int i) -> Obj.repr i
149153
| Const_base(Const_char c) -> Obj.repr c
150154
| Const_base(Const_string (s, _, _)) -> Obj.repr s
151-
| Const_base(Const_float32 f)
155+
| Const_base(Const_float32 f) -> float32_of_string f
152156
| Const_base(Const_float f)
153157
| Const_base(Const_unboxed_float f) -> Obj.repr (float_of_string f)
154158
| Const_base(Const_int32 i)

dune

+1
Original file line numberDiff line numberDiff line change
@@ -67,6 +67,7 @@
6767
(run cat %{input-file})))
6868
parser)))
6969
(library_flags -linkall)
70+
(libraries flambda2_floats)
7071
(modules_without_implementation
7172
annot asttypes cmo_format outcometree parsetree debug_event solver_intf mode_intf)
7273
(modules

otherlibs/alpha/.ocamlformat-enable

+2
Original file line numberDiff line numberDiff line change
@@ -1,2 +1,4 @@
11
alpha.mli
22
alpha.ml
3+
float32.mli
4+
float32.ml

otherlibs/alpha/alpha.ml

+1
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
module Float32 = Float32

otherlibs/alpha/alpha.mli

+1
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
module Float32 = Float32

otherlibs/alpha/dune

+6-1
Original file line numberDiff line numberDiff line change
@@ -41,9 +41,14 @@
4141
(alpha.cmxs as alpha/alpha.cmxs)
4242
(alpha.cma as alpha/alpha.cma)
4343
(alpha.mli as alpha/alpha.mli)
44+
(float32.mli as alpha/float32.mli)
4445
(.alpha.objs/byte/alpha.cmi as alpha/alpha.cmi)
4546
(.alpha.objs/byte/alpha.cmt as alpha/alpha.cmt)
4647
(.alpha.objs/byte/alpha.cmti as alpha/alpha.cmti)
47-
(.alpha.objs/native/alpha.cmx as alpha/alpha.cmx))
48+
(.alpha.objs/native/alpha.cmx as alpha/alpha.cmx)
49+
(.alpha.objs/byte/float32.cmi as alpha/float32.cmi)
50+
(.alpha.objs/byte/float32.cmt as alpha/float32.cmt)
51+
(.alpha.objs/byte/float32.cmti as alpha/float32.cmti)
52+
(.alpha.objs/native/float32.cmx as alpha/float32.cmx))
4853
(section lib)
4954
(package ocaml))

otherlibs/alpha/float32.ml

+280
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,280 @@
1+
(**************************************************************************)
2+
(* *)
3+
(* OCaml *)
4+
(* *)
5+
(* Xavier Leroy, projet Cristal, INRIA Rocquencourt *)
6+
(* Nicolas Ojeda Bar, LexiFi *)
7+
(* *)
8+
(* Copyright 2018 Institut National de Recherche en Informatique et *)
9+
(* en Automatique. *)
10+
(* *)
11+
(* All rights reserved. This file is distributed under the terms of *)
12+
(* the GNU Lesser General Public License version 2.1, with the *)
13+
(* special exception on linking described in the file LICENSE. *)
14+
(* *)
15+
(**************************************************************************)
16+
17+
[@@@ocaml.flambda_o3]
18+
19+
type t = float32
20+
21+
external float32_of_bits : int32 -> float32
22+
= "caml_float32_of_bits_bytecode" "caml_float32_of_bits"
23+
[@@unboxed] [@@noalloc]
24+
25+
external neg : (float32[@local_opt]) -> (float32[@local_opt]) = "%negfloat32"
26+
27+
external add :
28+
(float32[@local_opt]) -> (float32[@local_opt]) -> (float32[@local_opt])
29+
= "%addfloat32"
30+
31+
external sub :
32+
(float32[@local_opt]) -> (float32[@local_opt]) -> (float32[@local_opt])
33+
= "%subfloat32"
34+
35+
external mul :
36+
(float32[@local_opt]) -> (float32[@local_opt]) -> (float32[@local_opt])
37+
= "%mulfloat32"
38+
39+
external div :
40+
(float32[@local_opt]) -> (float32[@local_opt]) -> (float32[@local_opt])
41+
= "%divfloat32"
42+
43+
external pow : float32 -> float32 -> float32
44+
= "caml_power_float32_bytecode" "powf"
45+
[@@unboxed] [@@noalloc]
46+
47+
module Operators = struct
48+
external ( ~-. ) : (float32[@local_opt]) -> (float32[@local_opt])
49+
= "%negfloat32"
50+
51+
external ( +. ) :
52+
(float32[@local_opt]) -> (float32[@local_opt]) -> (float32[@local_opt])
53+
= "%addfloat32"
54+
55+
external ( -. ) :
56+
(float32[@local_opt]) -> (float32[@local_opt]) -> (float32[@local_opt])
57+
= "%subfloat32"
58+
59+
external ( *. ) :
60+
(float32[@local_opt]) -> (float32[@local_opt]) -> (float32[@local_opt])
61+
= "%mulfloat32"
62+
63+
external ( /. ) :
64+
(float32[@local_opt]) -> (float32[@local_opt]) -> (float32[@local_opt])
65+
= "%divfloat32"
66+
67+
external ( ** ) : float32 -> float32 -> float32
68+
= "caml_power_float32_bytecode" "powf"
69+
[@@unboxed] [@@noalloc]
70+
end
71+
72+
external fma : float32 -> float32 -> float32 -> float32
73+
= "caml_fma_float32_bytecode" "fmaf"
74+
[@@unboxed] [@@noalloc]
75+
76+
external rem : float32 -> float32 -> float32
77+
= "caml_fmod_float32_bytecode" "fmodf"
78+
[@@unboxed] [@@noalloc]
79+
80+
external abs : (float32[@local_opt]) -> (float32[@local_opt]) = "%absfloat32"
81+
82+
let zero = 0.s
83+
let one = 1.s
84+
let minus_one = -1.s
85+
let infinity = float32_of_bits 0x7f800000l
86+
let neg_infinity = float32_of_bits 0xff800000l
87+
let nan = float32_of_bits 0x7f800001l
88+
let is_finite (x : float32) = sub x x = 0.s
89+
let is_infinite (x : float32) = div 1.s x = 0.s
90+
let is_nan (x : float32) = x <> x
91+
let pi = 0x1.921fb6p+1s
92+
let max_float = float32_of_bits 0x7f7fffffl
93+
let min_float = float32_of_bits 0x00800000l
94+
let epsilon = float32_of_bits 0x34000000l
95+
96+
external of_int : int -> float32 = "%float32ofint"
97+
external to_int : (float32[@local_opt]) -> int = "%intoffloat32"
98+
external of_float : (float[@local_opt]) -> float32 = "%float32offloat"
99+
external to_float : (float32[@local_opt]) -> float = "%floatoffloat32"
100+
101+
external of_bits : (int32[@local_opt]) -> float32
102+
= "caml_float32_of_bits_bytecode" "caml_float32_of_bits"
103+
[@@unboxed] [@@noalloc]
104+
105+
external to_bits : (float32[@local_opt]) -> int32
106+
= "caml_float32_to_bits_bytecode" "caml_float32_to_bits"
107+
[@@unboxed] [@@noalloc]
108+
109+
external of_string : string -> float32 = "caml_float32_of_string"
110+
111+
let of_string_opt s = try Some (of_string s) with Failure _ -> None
112+
113+
external format : string -> float32 -> string = "caml_format_float32"
114+
115+
let to_string f = Stdlib.valid_float_lexem (format "%.9g" f)
116+
117+
type fpclass = Stdlib.fpclass =
118+
| FP_normal
119+
| FP_subnormal
120+
| FP_zero
121+
| FP_infinite
122+
| FP_nan
123+
124+
external classify_float : (float32[@unboxed]) -> fpclass
125+
= "caml_classify_float32_bytecode" "caml_classify_float32"
126+
[@@noalloc]
127+
128+
external sqrt : float32 -> float32 = "caml_sqrt_float32_bytecode" "sqrtf"
129+
[@@unboxed] [@@noalloc]
130+
131+
external cbrt : float32 -> float32 = "caml_cbrt_float32_bytecode" "cbrtf"
132+
[@@unboxed] [@@noalloc]
133+
134+
external exp : float32 -> float32 = "caml_exp_float32_bytecode" "expf"
135+
[@@unboxed] [@@noalloc]
136+
137+
external exp2 : float32 -> float32 = "caml_exp2_float32_bytecode" "exp2f"
138+
[@@unboxed] [@@noalloc]
139+
140+
external log : float32 -> float32 = "caml_log_float32_bytecode" "logf"
141+
[@@unboxed] [@@noalloc]
142+
143+
external log10 : float32 -> float32 = "caml_log10_float32_bytecode" "log10f"
144+
[@@unboxed] [@@noalloc]
145+
146+
external log2 : float32 -> float32 = "caml_log2_float32_bytecode" "log2f"
147+
[@@unboxed] [@@noalloc]
148+
149+
external expm1 : float32 -> float32 = "caml_expm1_float32_bytecode" "expm1f"
150+
[@@unboxed] [@@noalloc]
151+
152+
external log1p : float32 -> float32 = "caml_log1p_float32_bytecode" "log1pf"
153+
[@@unboxed] [@@noalloc]
154+
155+
external cos : float32 -> float32 = "caml_cos_float32_bytecode" "cosf"
156+
[@@unboxed] [@@noalloc]
157+
158+
external sin : float32 -> float32 = "caml_sin_float32_bytecode" "sinf"
159+
[@@unboxed] [@@noalloc]
160+
161+
external tan : float32 -> float32 = "caml_tan_float32_bytecode" "tanf"
162+
[@@unboxed] [@@noalloc]
163+
164+
external acos : float32 -> float32 = "caml_acos_float32_bytecode" "acosf"
165+
[@@unboxed] [@@noalloc]
166+
167+
external asin : float32 -> float32 = "caml_asin_float32_bytecode" "asinf"
168+
[@@unboxed] [@@noalloc]
169+
170+
external atan : float32 -> float32 = "caml_atan_float32_bytecode" "atanf"
171+
[@@unboxed] [@@noalloc]
172+
173+
external atan2 : float32 -> float32 -> float32
174+
= "caml_atan2_float32_bytecode" "atan2f"
175+
[@@unboxed] [@@noalloc]
176+
177+
external hypot : float32 -> float32 -> float32
178+
= "caml_hypot_float32_bytecode" "hypotf"
179+
[@@unboxed] [@@noalloc]
180+
181+
external cosh : float32 -> float32 = "caml_cosh_float32_bytecode" "coshf"
182+
[@@unboxed] [@@noalloc]
183+
184+
external sinh : float32 -> float32 = "caml_sinh_float32_bytecode" "sinhf"
185+
[@@unboxed] [@@noalloc]
186+
187+
external tanh : float32 -> float32 = "caml_tanh_float32_bytecode" "tanhf"
188+
[@@unboxed] [@@noalloc]
189+
190+
external acosh : float32 -> float32 = "caml_acosh_float32_bytecode" "acoshf"
191+
[@@unboxed] [@@noalloc]
192+
193+
external asinh : float32 -> float32 = "caml_asinh_float32_bytecode" "asinhf"
194+
[@@unboxed] [@@noalloc]
195+
196+
external atanh : float32 -> float32 = "caml_atanh_float32_bytecode" "atanhf"
197+
[@@unboxed] [@@noalloc]
198+
199+
external erf : float32 -> float32 = "caml_erf_float32_bytecode" "erff"
200+
[@@unboxed] [@@noalloc]
201+
202+
external erfc : float32 -> float32 = "caml_erfc_float32_bytecode" "erfcf"
203+
[@@unboxed] [@@noalloc]
204+
205+
external trunc : float32 -> float32 = "caml_trunc_float32_bytecode" "truncf"
206+
[@@unboxed] [@@noalloc]
207+
208+
external round : float32 -> float32 = "caml_round_float32_bytecode" "roundf"
209+
[@@unboxed] [@@noalloc]
210+
211+
external ceil : float32 -> float32 = "caml_ceil_float32_bytecode" "ceilf"
212+
[@@unboxed] [@@noalloc]
213+
214+
external floor : float32 -> float32 = "caml_floor_float32_bytecode" "floorf"
215+
[@@unboxed] [@@noalloc]
216+
217+
let is_integer x = x = trunc x && is_finite x
218+
219+
external next_after : float32 -> float32 -> float32
220+
= "caml_nextafter_float32_bytecode" "nextafterf"
221+
[@@unboxed] [@@noalloc]
222+
223+
let succ x = next_after x infinity
224+
let pred x = next_after x neg_infinity
225+
226+
external copy_sign : float32 -> float32 -> float32
227+
= "caml_copysign_float32_bytecode" "copysignf"
228+
[@@unboxed] [@@noalloc]
229+
230+
external sign_bit : (float32[@unboxed]) -> bool
231+
= "caml_signbit_float32_bytecode" "caml_signbit_float32"
232+
[@@noalloc]
233+
234+
external frexp : float32 -> float32 * int = "caml_frexp_float32"
235+
236+
external ldexp : (float32[@unboxed]) -> (int[@untagged]) -> (float32[@unboxed])
237+
= "caml_ldexp_float32_bytecode" "caml_ldexp_float32"
238+
[@@noalloc]
239+
240+
external modf : float32 -> float32 * float32 = "caml_modf_float32"
241+
external compare : float32 -> float32 -> int = "%compare"
242+
243+
let equal x y = compare x y = 0
244+
245+
let[@inline] min (x : float32) (y : float32) =
246+
if y > x || ((not (sign_bit y)) && sign_bit x) then if is_nan y then y else x
247+
else if is_nan x then x
248+
else y
249+
250+
let[@inline] max (x : float32) (y : float32) =
251+
if y > x || ((not (sign_bit y)) && sign_bit x) then if is_nan x then x else y
252+
else if is_nan y then y
253+
else x
254+
255+
let[@inline] min_max (x : float32) (y : float32) =
256+
if is_nan x || is_nan y then (nan, nan)
257+
else if y > x || ((not (sign_bit y)) && sign_bit x) then (x, y)
258+
else (y, x)
259+
260+
let[@inline] min_num (x : float32) (y : float32) =
261+
if y > x || ((not (sign_bit y)) && sign_bit x) then if is_nan x then y else x
262+
else if is_nan y then x
263+
else y
264+
265+
let[@inline] max_num (x : float32) (y : float32) =
266+
if y > x || ((not (sign_bit y)) && sign_bit x) then if is_nan y then x else y
267+
else if is_nan x then y
268+
else x
269+
270+
let[@inline] min_max_num (x : float32) (y : float32) =
271+
if is_nan x then (y, y)
272+
else if is_nan y then (x, x)
273+
else if y > x || ((not (sign_bit y)) && sign_bit x) then (x, y)
274+
else (y, x)
275+
276+
external seeded_hash_param : int -> int -> int -> 'a -> int = "caml_hash_exn"
277+
[@@noalloc]
278+
279+
let seeded_hash seed x = seeded_hash_param 10 100 seed x
280+
let hash x = seeded_hash_param 10 100 0 x

0 commit comments

Comments
 (0)