|
|
|
|
(*
|
|
|
|
|
* Copyright (c) Facebook, Inc. and its affiliates.
|
|
|
|
|
*
|
|
|
|
|
* This source code is licensed under the MIT license found in the
|
|
|
|
|
* LICENSE file in the root directory of this source tree.
|
|
|
|
|
*)
|
|
|
|
|
|
|
|
|
|
(* [@@@warning "-32"] *)
|
|
|
|
|
|
|
|
|
|
let%test_module _ =
|
|
|
|
|
( module struct
|
|
|
|
|
let () = Trace.init ~margin:68 ()
|
|
|
|
|
|
|
|
|
|
(* let () = Trace.init ~margin:68 ~config:Trace.all () *)
|
|
|
|
|
|
|
|
|
|
open Term
|
|
|
|
|
|
|
|
|
|
let pp = Format.printf "@\n%a@." pp
|
|
|
|
|
let ( ! ) i = integer (Z.of_int i)
|
|
|
|
|
let ( + ) = add
|
|
|
|
|
let ( - ) = sub
|
|
|
|
|
let ( * ) = mul
|
|
|
|
|
let ( = ) = eq
|
|
|
|
|
let ( != ) = dq
|
|
|
|
|
let ( < ) = lt
|
|
|
|
|
let ( <= ) = le
|
|
|
|
|
let ( && ) = and_
|
|
|
|
|
let ( || ) = or_
|
|
|
|
|
let ( ~~ ) = not_
|
|
|
|
|
let wrt = Var.Set.empty
|
|
|
|
|
let y_, wrt = Var.fresh "y" ~wrt
|
|
|
|
|
let z_, _ = Var.fresh "z" ~wrt
|
|
|
|
|
let y = var y_
|
|
|
|
|
let z = var z_
|
|
|
|
|
|
[sledge] Simplify type conversions
Summary:
The treatment of type conversions is too complicated, non-uniform,
etc. This diff attempts to simplify things by separating integer to
integer conversions, which are interpreted, from others, which are
essentially just uninterpreted functions. Integer conversions are now
handled using two expression and term forms: Signed and
Unsigned. These each interpret their argument as either a signed or
unsigned number of a given bitwidth:
```
| Signed of {bits: int}
(** [Ap1 (Signed {bits= n}, dst, arg)] is [arg] interpreted as an
[n]-bit signed integer and injected into the [dst] type. That is,
it two's-complement--decodes the low [n] bits of the infinite
two's-complement encoding of [arg]. The injection into [dst] is a
no-op, so [dst] must be an integer type with bitwidth at least
[n]. *)
| Unsigned of {bits: int}
(** [Ap1 (Unsigned {bits= n}, dst, arg)] is [arg] interpreted as an
[n]-bit unsigned integer and injected into the [dst] type. That
is, it unsigned-binary--decodes the low [n] bits of the infinite
two's-complement encoding of [arg]. The injection into [dst] is a
no-op, so [dst] must be an integer type with bitwidth greater than
[n]. *)
| Convert of {src: Typ.t}
(** [Ap1 (Convert {src}, dst, arg)] is [arg] converted from type [src]
to type [dst], possibly with loss of information. The [src] and
[dst] types must be [Typ.convertible] and must not both be
[Integer] types. *)
```
Reviewed By: ngorogiannis
Differential Revision: D18298140
fbshipit-source-id: 690f065b4
5 years ago
|
|
|
|
let%test "booleans distinct" = is_false (true_ = false_)
|
|
|
|
|
let%test "u1 values distinct" = is_false (one = zero)
|
|
|
|
|
let%test "boolean overflow" = is_true (minus_one = signed 1 one)
|
|
|
|
|
let%test _ = is_true (one = unsigned 1 minus_one)
|
|
|
|
|
|
|
|
|
|
let%test "unsigned boolean overflow" =
|
|
|
|
|
is_true
|
|
|
|
|
(Exp.uge
|
|
|
|
|
(Exp.integer Typ.bool Z.minus_one)
|
[sledge] Simplify type conversions
Summary:
The treatment of type conversions is too complicated, non-uniform,
etc. This diff attempts to simplify things by separating integer to
integer conversions, which are interpreted, from others, which are
essentially just uninterpreted functions. Integer conversions are now
handled using two expression and term forms: Signed and
Unsigned. These each interpret their argument as either a signed or
unsigned number of a given bitwidth:
```
| Signed of {bits: int}
(** [Ap1 (Signed {bits= n}, dst, arg)] is [arg] interpreted as an
[n]-bit signed integer and injected into the [dst] type. That is,
it two's-complement--decodes the low [n] bits of the infinite
two's-complement encoding of [arg]. The injection into [dst] is a
no-op, so [dst] must be an integer type with bitwidth at least
[n]. *)
| Unsigned of {bits: int}
(** [Ap1 (Unsigned {bits= n}, dst, arg)] is [arg] interpreted as an
[n]-bit unsigned integer and injected into the [dst] type. That
is, it unsigned-binary--decodes the low [n] bits of the infinite
two's-complement encoding of [arg]. The injection into [dst] is a
no-op, so [dst] must be an integer type with bitwidth greater than
[n]. *)
| Convert of {src: Typ.t}
(** [Ap1 (Convert {src}, dst, arg)] is [arg] converted from type [src]
to type [dst], possibly with loss of information. The [src] and
[dst] types must be [Typ.convertible] and must not both be
[Integer] types. *)
```
Reviewed By: ngorogiannis
Differential Revision: D18298140
fbshipit-source-id: 690f065b4
5 years ago
|
|
|
|
(Exp.signed 1 (Exp.integer Typ.siz Z.one) ~to_:Typ.bool))
|
|
|
|
|
.term
|
|
|
|
|
|
|
|
|
|
let%expect_test _ =
|
|
|
|
|
pp (!42 + !13) ;
|
|
|
|
|
[%expect {| 55 |}]
|
|
|
|
|
|
|
|
|
|
let%expect_test _ =
|
|
|
|
|
pp (!(-128) && !127) ;
|
|
|
|
|
[%expect {| 0 |}]
|
|
|
|
|
|
|
|
|
|
let%expect_test _ =
|
|
|
|
|
pp (!(-128) || !127) ;
|
|
|
|
|
[%expect {| -1 |}]
|
|
|
|
|
|
|
|
|
|
let%expect_test _ =
|
|
|
|
|
pp (z + !42 + !13) ;
|
|
|
|
|
[%expect {| (%z_2 + 55) |}]
|
|
|
|
|
|
|
|
|
|
let%expect_test _ =
|
|
|
|
|
pp (z + !42 + !(-42)) ;
|
|
|
|
|
[%expect {| %z_2 |}]
|
|
|
|
|
|
|
|
|
|
let%expect_test _ =
|
|
|
|
|
pp (z * y) ;
|
|
|
|
|
[%expect {| (%y_1 × %z_2) |}]
|
|
|
|
|
|
|
|
|
|
let%expect_test _ =
|
|
|
|
|
pp (y * z * y) ;
|
|
|
|
|
[%expect {| (%y_1^2 × %z_2) |}]
|
|
|
|
|
|
|
|
|
|
let%expect_test _ =
|
|
|
|
|
pp ((!2 * z * z) + (!3 * z) + !4) ;
|
|
|
|
|
[%expect {| (3 × %z_2 + 2 × (%z_2^2) + 4) |}]
|
|
|
|
|
|
|
|
|
|
let%expect_test _ =
|
|
|
|
|
pp
|
|
|
|
|
( !1 + (!2 * z) + (!3 * y)
|
|
|
|
|
+ (!4 * z * z)
|
|
|
|
|
+ (!5 * y * y)
|
|
|
|
|
+ (!6 * z * y)
|
|
|
|
|
+ (!7 * y * z * y)
|
|
|
|
|
+ (!8 * z * y * z)
|
|
|
|
|
+ (!9 * z * z * z) ) ;
|
|
|
|
|
[%expect
|
|
|
|
|
{|
|
|
|
|
|
(3 × %y_1 + 2 × %z_2 + 6 × (%y_1 × %z_2) + 8 × (%y_1 × %z_2^2)
|
|
|
|
|
+ 5 × (%y_1^2) + 7 × (%y_1^2 × %z_2) + 4 × (%z_2^2) + 9 × (%z_2^3)
|
|
|
|
|
+ 1) |}]
|
|
|
|
|
|
|
|
|
|
let%expect_test _ =
|
|
|
|
|
pp (!0 * z * y) ;
|
|
|
|
|
[%expect {| 0 |}]
|
|
|
|
|
|
|
|
|
|
let%expect_test _ =
|
|
|
|
|
pp (!1 * z * y) ;
|
|
|
|
|
[%expect {| (%y_1 × %z_2) |}]
|
|
|
|
|
|
|
|
|
|
let%expect_test _ =
|
|
|
|
|
pp (!7 * z * (!2 * y)) ;
|
|
|
|
|
[%expect {| (14 × (%y_1 × %z_2)) |}]
|
|
|
|
|
|
|
|
|
|
let%expect_test _ =
|
|
|
|
|
pp (!13 + (!42 * z)) ;
|
|
|
|
|
[%expect {| (42 × %z_2 + 13) |}]
|
|
|
|
|
|
|
|
|
|
let%expect_test _ =
|
|
|
|
|
pp ((!13 * z) + !42) ;
|
|
|
|
|
[%expect {| (13 × %z_2 + 42) |}]
|
|
|
|
|
|
|
|
|
|
let%expect_test _ =
|
|
|
|
|
pp ((!2 * z) - !3 + ((!(-2) * z) + !3)) ;
|
|
|
|
|
[%expect {| 0 |}]
|
|
|
|
|
|
|
|
|
|
let%expect_test _ =
|
|
|
|
|
pp ((!3 * y) + (!13 * z) + !42) ;
|
|
|
|
|
[%expect {| (3 × %y_1 + 13 × %z_2 + 42) |}]
|
|
|
|
|
|
|
|
|
|
let%expect_test _ =
|
|
|
|
|
pp ((!13 * z) + !42 + (!3 * y)) ;
|
|
|
|
|
[%expect {| (3 × %y_1 + 13 × %z_2 + 42) |}]
|
|
|
|
|
|
|
|
|
|
let%expect_test _ =
|
|
|
|
|
pp ((!13 * z) + !42 + (!3 * y) + (!2 * z)) ;
|
|
|
|
|
[%expect {| (3 × %y_1 + 15 × %z_2 + 42) |}]
|
|
|
|
|
|
|
|
|
|
let%expect_test _ =
|
|
|
|
|
pp ((!13 * z) + !42 + (!3 * y) + (!(-13) * z)) ;
|
|
|
|
|
[%expect {| (3 × %y_1 + 42) |}]
|
|
|
|
|
|
|
|
|
|
let%expect_test _ =
|
|
|
|
|
pp (z + !42 + ((!3 * y) + (!(-1) * z))) ;
|
|
|
|
|
[%expect {| (3 × %y_1 + 42) |}]
|
|
|
|
|
|
|
|
|
|
let%expect_test _ =
|
|
|
|
|
pp (!(-1) * (z + (!(-1) * y))) ;
|
|
|
|
|
[%expect {| (%y_1 + -1 × %z_2) |}]
|
|
|
|
|
|
|
|
|
|
let%expect_test _ =
|
|
|
|
|
pp (((!3 * y) + !2) * (!4 + (!5 * z))) ;
|
|
|
|
|
[%expect {| (12 × %y_1 + 10 × %z_2 + 15 × (%y_1 × %z_2) + 8) |}]
|
|
|
|
|
|
|
|
|
|
let%expect_test _ =
|
|
|
|
|
pp (((!2 * z) - !3 + ((!(-2) * z) + !3)) * (!4 + (!5 * z))) ;
|
|
|
|
|
[%expect {| 0 |}]
|
|
|
|
|
|
|
|
|
|
let%expect_test _ =
|
|
|
|
|
pp ((!13 * z) + !42 - ((!3 * y) + (!13 * z))) ;
|
|
|
|
|
[%expect {| (-3 × %y_1 + 42) |}]
|
|
|
|
|
|
|
|
|
|
let%expect_test _ =
|
|
|
|
|
pp (z = y) ;
|
|
|
|
|
[%expect {| (%y_1 = %z_2) |}]
|
|
|
|
|
|
|
|
|
|
let%expect_test _ =
|
|
|
|
|
pp (z = z) ;
|
|
|
|
|
[%expect {| -1 |}]
|
|
|
|
|
|
|
|
|
|
let%expect_test _ =
|
|
|
|
|
pp (z != z) ;
|
|
|
|
|
[%expect {| 0 |}]
|
|
|
|
|
|
|
|
|
|
let%expect_test _ =
|
|
|
|
|
pp (!1 = !0) ;
|
|
|
|
|
[%expect {| 0 |}]
|
|
|
|
|
|
|
|
|
|
let%expect_test _ =
|
|
|
|
|
pp (!3 * y = z = true_) ;
|
|
|
|
|
[%expect {| (%z_2 = (3 × %y_1)) |}]
|
|
|
|
|
|
|
|
|
|
let%expect_test _ =
|
|
|
|
|
pp (true_ = (!3 * y = z)) ;
|
|
|
|
|
[%expect {| (%z_2 = (3 × %y_1)) |}]
|
|
|
|
|
|
|
|
|
|
let%expect_test _ =
|
|
|
|
|
pp (!3 * y = z = false_) ;
|
|
|
|
|
[%expect {| (%z_2 ≠ (3 × %y_1)) |}]
|
|
|
|
|
|
|
|
|
|
let%expect_test _ =
|
|
|
|
|
pp (false_ = (!3 * y = z)) ;
|
|
|
|
|
[%expect {| (%z_2 ≠ (3 × %y_1)) |}]
|
|
|
|
|
|
|
|
|
|
let%expect_test _ =
|
|
|
|
|
pp (y - (!(-3) * y) + !4) ;
|
|
|
|
|
[%expect {| (4 × %y_1 + 4) |}]
|
|
|
|
|
|
|
|
|
|
let%expect_test _ =
|
|
|
|
|
pp ((!(-3) * y) + !4 - y) ;
|
|
|
|
|
[%expect {| (-4 × %y_1 + 4) |}]
|
|
|
|
|
|
|
|
|
|
let%expect_test _ =
|
|
|
|
|
pp (y = (!(-3) * y) + !4) ;
|
|
|
|
|
[%expect {| (%y_1 = (-3 × %y_1 + 4)) |}]
|
|
|
|
|
|
|
|
|
|
let%expect_test _ =
|
|
|
|
|
pp ((!(-3) * y) + !4 = y) ;
|
|
|
|
|
[%expect {| (%y_1 = (-3 × %y_1 + 4)) |}]
|
|
|
|
|
|
|
|
|
|
let%expect_test _ =
|
|
|
|
|
pp (sub true_ (z = !4)) ;
|
|
|
|
|
[%expect {| (-1 × (%z_2 = 4) + -1) |}]
|
|
|
|
|
|
|
|
|
|
let%expect_test _ =
|
|
|
|
|
pp (add true_ (z = !4) = (z = !4)) ;
|
|
|
|
|
[%expect {| ((%z_2 = 4) = ((%z_2 = 4) + -1)) |}]
|
|
|
|
|
|
|
|
|
|
let%expect_test _ =
|
|
|
|
|
pp ((!13 * z) + !42 = (!3 * y) + (!13 * z)) ;
|
|
|
|
|
[%expect {| ((3 × %y_1 + 13 × %z_2) = (13 × %z_2 + 42)) |}]
|
|
|
|
|
|
|
|
|
|
let%expect_test _ =
|
|
|
|
|
pp ((!13 * z) + !(-42) = (!3 * y) + (!13 * z)) ;
|
|
|
|
|
[%expect {| ((3 × %y_1 + 13 × %z_2) = (13 × %z_2 + -42)) |}]
|
|
|
|
|
|
|
|
|
|
let%expect_test _ =
|
|
|
|
|
pp ((!13 * z) + !42 = (!(-3) * y) + (!13 * z)) ;
|
|
|
|
|
[%expect {| ((-3 × %y_1 + 13 × %z_2) = (13 × %z_2 + 42)) |}]
|
|
|
|
|
|
|
|
|
|
let%expect_test _ =
|
|
|
|
|
pp ((!10 * z) + !42 = (!(-3) * y) + (!13 * z)) ;
|
|
|
|
|
[%expect {| ((-3 × %y_1 + 13 × %z_2) = (10 × %z_2 + 42)) |}]
|
|
|
|
|
|
|
|
|
|
let%expect_test _ =
|
|
|
|
|
pp ~~((!13 * z) + !(-42) != (!3 * y) + (!13 * z)) ;
|
|
|
|
|
[%expect {| ((3 × %y_1 + 13 × %z_2) = (13 × %z_2 + -42)) |}]
|
|
|
|
|
|
|
|
|
|
let%expect_test _ =
|
|
|
|
|
pp ~~(!2 < y && z <= !3) ;
|
|
|
|
|
[%expect {| ((%y_1 ≤ 2) || (3 < %z_2)) |}]
|
|
|
|
|
|
|
|
|
|
let%expect_test _ =
|
|
|
|
|
pp ~~(!2 <= y || z < !3) ;
|
|
|
|
|
[%expect {| ((%y_1 < 2) && (3 ≤ %z_2)) |}]
|
|
|
|
|
|
|
|
|
|
let%expect_test _ =
|
|
|
|
|
pp (eq z null) ;
|
|
|
|
|
pp (eq null z) ;
|
|
|
|
|
pp (dq (eq null z) false_) ;
|
|
|
|
|
[%expect
|
|
|
|
|
{|
|
|
|
|
|
(%z_2 = 0)
|
|
|
|
|
|
|
|
|
|
(%z_2 = 0)
|
|
|
|
|
|
|
|
|
|
(%z_2 = 0) |}]
|
|
|
|
|
|
|
|
|
|
let%expect_test _ =
|
|
|
|
|
let z1 = z + !1 in
|
|
|
|
|
let z1_2 = z1 * z1 in
|
|
|
|
|
pp z1_2 ;
|
|
|
|
|
pp (z1_2 * z1_2) ;
|
|
|
|
|
[%expect
|
|
|
|
|
{|
|
|
|
|
|
(2 × %z_2 + (%z_2^2) + 1)
|
|
|
|
|
|
|
|
|
|
(4 × %z_2 + 6 × (%z_2^2) + 4 × (%z_2^3) + (%z_2^4) + 1) |}]
|
|
|
|
|
end )
|