(** Translation of conditions *)

(* Specifications: *)
Lemma compare_int_spec:
forall rs v1 v2 m,
let rs1 := nextinstr (compare_int rs v1 v2 m) in
rs1#CN = Val.negative (Val.sub v1 v2)
/\ rs1#CZ = Val.cmpu (Mem.valid_pointer m) Ceq v1 v2
/\ rs1#CC = Val.cmpu (Mem.valid_pointer m) Cge v1 v2
/\ rs1#CV = Val.sub_overflow v1 v2.
Lemma compare_int_inv:
forall rs v1 v2 m,
let rs1 := nextinstr (compare_int rs v1 v2 m) in
forall r', data_preg r' = true -> rs1#r' = rs#r'.
Lemma int_signed_eq:
forall x y, Int.eq x y = zeq (Int.signed x) (Int.signed y).
Lemma int_not_lt:
forall x y, negb (Int.lt y x) = (Int.lt x y || Int.eq x y).
Lemma int_lt_not:
forall x y, Int.lt y x = negb (Int.lt x y) && negb (Int.eq x y).
Lemma int_not_ltu:
forall x y, negb (Int.ltu y x) = (Int.ltu x y || Int.eq x y).
Lemma int_ltu_not:
forall x y, Int.ltu y x = negb (Int.ltu x y) && negb (Int.eq x y).
Lemma cond_for_signed_cmp_correct:
forall c v1 v2 rs m b,
Val.cmp_bool c v1 v2 = Some b ->
eval_testcond (cond_for_signed_cmp c)
(nextinstr (compare_int rs v1 v2 m)) = Some b.
Lemma cond_for_unsigned_cmp_correct:
forall c v1 v2 rs m b,
Val.cmpu_bool (Mem.valid_pointer m) c v1 v2 = Some b ->
eval_testcond (cond_for_unsigned_cmp c)
(nextinstr (compare_int rs v1 v2 m)) = Some b.
Lemma compare_float_spec:
forall rs f1 f2,
let rs1 := nextinstr (compare_float rs (Vfloat f1) (Vfloat f2)) in
rs1#CN = Val.of_bool (Float.cmp Clt f1 f2)
/\ rs1#CZ = Val.of_bool (Float.cmp Ceq f1 f2)
/\ rs1#CC = Val.of_bool (negb (Float.cmp Clt f1 f2))
/\ rs1#CV = Val.of_bool (negb (Float.cmp Ceq f1 f2 || Float.cmp Clt f1 f2 || Float.cmp Cgt f1 f2)).
Lemma compare_float_inv:
forall rs v1 v2,
let rs1 := nextinstr (compare_float rs v1 v2) in
forall r', data_preg r' = true -> rs1#r' = rs#r'.
Lemma compare_float_nextpc:
forall rs v1 v2,
nextinstr (compare_float rs v1 v2) PC = Val.offset_ptr (rs PC) Ptrofs.one.
Lemma cond_for_float_cmp_correct:
forall c n1 n2 rs,
eval_testcond (cond_for_float_cmp c)
(nextinstr (compare_float rs (Vfloat n1) (Vfloat n2))) =
Some(Float.cmp c n1 n2).
Lemma cond_for_float_not_cmp_correct:
forall c n1 n2 rs,
eval_testcond (cond_for_float_not_cmp c)
(nextinstr (compare_float rs (Vfloat n1) (Vfloat n2)))=
Some(negb(Float.cmp c n1 n2)).
Lemma compare_float32_spec:
forall rs f1 f2,
let rs1 := nextinstr (compare_float32 rs (Vsingle f1) (Vsingle f2)) in
rs1#CN = Val.of_bool (Float32.cmp Clt f1 f2)
/\ rs1#CZ = Val.of_bool (Float32.cmp Ceq f1 f2)
/\ rs1#CC = Val.of_bool (negb (Float32.cmp Clt f1 f2))
/\ rs1#CV = Val.of_bool (negb (Float32.cmp Ceq f1 f2 || Float32.cmp Clt f1 f2 || Float32.cmp Cgt f1 f2)).
Lemma compare_float32_inv:
forall rs v1 v2,
let rs1 := nextinstr (compare_float32 rs v1 v2) in
forall r', data_preg r' = true -> rs1#r' = rs#r'.
Lemma compare_float32_nextpc:
forall rs v1 v2,
nextinstr (compare_float32 rs v1 v2) PC = Val.offset_ptr (rs PC) Ptrofs.one.
Lemma cond_for_float32_cmp_correct:
forall c n1 n2 rs,
eval_testcond (cond_for_float_cmp c)
(nextinstr (compare_float32 rs (Vsingle n1) (Vsingle n2))) =
Some(Float32.cmp c n1 n2).
Lemma cond_for_float32_not_cmp_correct:
forall c n1 n2 rs,
eval_testcond (cond_for_float_not_cmp c)
(nextinstr (compare_float32 rs (Vsingle n1) (Vsingle n2)))=
Some(negb(Float32.cmp c n1 n2)).