1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
include Int32

type t = int32

let wrap_i64 x = Int64.to_int32 x

let trunc_f32_s x =
  if Float32.ne x x then Error `Conversion_to_integer
  else
    let xf = Float32.to_float x in
    if
      let xf = Float64.of_float xf in
      let mif = Int32.(to_float min_int) in
      Float64.(ge xf (of_float ~-.mif)) || Float64.(lt xf (of_float mif))
    then Error `Integer_overflow
    else Ok (Int32.of_float xf)

let trunc_f32_u x =
  if Float32.ne x x then Error `Conversion_to_integer
  else
    let xf = Float32.to_float x in
    if
      let xf = Float64.of_float xf in
      Float64.(ge xf (of_float @@ (-.Int32.(to_float min_int) *. 2.0)))
      || Float64.(le xf (Float64.of_float ~-.1.0))
    then Error `Integer_overflow
    else Ok Int64.(to_int32 (of_float xf))

let trunc_f64_s x =
  if Float64.ne x x then Error `Conversion_to_integer
  else if
    let mif = Int32.(to_float min_int) in
    Float64.(ge x (of_float @@ -.mif))
    || Float64.(le x (of_float @@ (mif -. 1.0)))
  then Error `Integer_overflow
  else Ok (Int32.of_float (Float64.to_float x))

let trunc_f64_u x =
  if Float64.ne x x then Error `Conversion_to_integer
  else if
    let mif = Int32.to_float Int32.min_int in
    Float64.(ge x (of_float @@ (-.mif *. 2.0)))
    || Float64.(le x (of_float ~-.1.0))
  then Error `Integer_overflow
  else Ok Int64.(to_int32 (of_float (Float64.to_float x)))

let trunc_sat_f32_s x =
  if Float32.ne x x then 0l
  else
    let xf = Float32.to_float x |> Float64.of_float in
    let mif = Int32.(to_float min_int) in
    if Float64.(lt xf (of_float mif)) then Int32.min_int
    else if Float64.(ge xf (of_float ~-.mif)) then Int32.max_int
    else Int32.of_float (Float64.to_float xf)

let trunc_sat_f32_u x =
  if Float32.ne x x then 0l
  else
    let xf = Float32.to_float x |> Float64.of_float in
    if Float64.(le xf (of_float ~-.1.0)) then 0l
    else if Float64.(ge xf @@ of_float @@ (~-.Int32.(to_float min_int) *. 2.0))
    then -1l
    else Int64.(to_int32 @@ of_float (Float64.to_float xf))

let trunc_sat_f64_s x =
  if Float64.ne x x then 0l
  else if Float64.(le x @@ of_float @@ Int32.(to_float min_int)) then
    Int32.min_int
  else if Float64.(ge x @@ of_float @@ ~-.Int32.(to_float min_int)) then
    Int32.max_int
  else Int32.of_float @@ Float64.to_float x

let trunc_sat_f64_u x =
  if Float64.ne x x then 0l
  else if Float64.(le x @@ of_float ~-.1.0) then 0l
  else if Float64.(ge x @@ of_float @@ ~-.(Int32.(to_float min_int) *. 2.0))
  then -1l
  else Int64.(to_int32 (of_float @@ Float64.to_float x))

let reinterpret_f32 = Float32.to_bits

let to_bool = function 0l -> false | _i -> true

let of_concrete v = v

let eq_concrete = eq

let pp = Fmt.int32