Module ValObsEq.
(** Strong injections on values *)
Inductive val_obs (mi : memren) : val -> val -> Prop :=
obs_int : forall i : int, val_obs mi (Vint i) (Vint i)
| obs_long : forall i : int64, val_obs mi (Vlong i) (Vlong i)
| obs_float : forall f : Floats.float,
val_obs mi (Vfloat f) (Vfloat f)
| obs_single : forall f : Floats.float32,
val_obs mi (Vsingle f) (Vsingle f)
| obs_ptr : forall (b1 b2 : block) (ofs : ptrofs),
mi b1 = Some b2 ->
val_obs mi (Vptr b1 ofs) (Vptr b2 ofs)
| obs_undef : val_obs mi Vundef Vundef.
(** Strong injections on memory values*)
Inductive memval_obs_eq (f : memren) : memval -> memval -> Prop :=
| memval_obs_byte : forall n : byte,
memval_obs_eq f (Byte n) (Byte n)
| memval_obs_frag : forall (v1 v2 : val) (q : quantity) (n : nat)
(Hval_obs: val_obs f v1 v2),
memval_obs_eq f (Fragment v1 q n) (Fragment v2 q n)
| memval_obs_undef : memval_obs_eq f Undef Undef.
Inductive val_obs_list (mi : memren) : seq val -> seq val -> Prop :=
val_obs_list_nil : val_obs_list mi [::] [::]
| val_obs_list_cons : forall (v v' : val) (vl vl' : seq val),
val_obs mi v v' ->
val_obs_list mi vl vl' ->
val_obs_list mi (v :: vl) (v' :: vl').
Hint Constructors val_obs : val_renamings.
Proof with eauto with val_renamings.
intros.
destruct v; inversion Hval_obs; subst...
Qed.
Proof with eauto with val_renamings.
intros v v' v'' f f' f'' Hval'' Hval' Hf.
inversion Hval'; subst; inversion Hval''; subst...
Qed.
Proof with eauto with val_renamings.
intros.
destruct v...
destruct Hvalid as [b' Hf].
specialize (Hid _ _ Hf);
subst...
Qed.
Proof with eauto with val_renamings.
intros;
destruct v; inversion H; subst;
simpl...
Qed.
Proof with eauto with val_renamings.
intros;
destruct v; inversion H; subst;
simpl...
Qed.
Proof with eauto with val_renamings.
intros;
destruct vhi; inversion Hobs_hi; subst; simpl...
destruct vlo; inversion Hobs_lo...
Qed.
Proof with eauto with val_renamings.
intros;
destruct v; inversion Hval_obs; subst;
destruct chunk; simpl...
Qed.
Proof with eauto with val_renamings.
intros; destruct v; inversion Hval_obs; subst; simpl...
Qed.
Definition val_obsC f v :=
match v with
| Vptr b n => match f b with
| Some b' => Vptr b' n
| None => Vundef
end
| _ => v
end.
(* Lemma val_has_type_obs: *)
(*   forall f v v' ty *)
(*     (Hval_obs: val_obs f v v'), *)
(*     val_casted.val_has_type_func v ty <-> val_casted.val_has_type_func v' ty. *)
(* Proof. *)
(*   intros. *)
(*   destruct v; inversion Hval_obs; subst; simpl; *)
(*     by tauto. *)
(* Qed. *)
(* Lemma val_has_type_list_obs: *)
(*   forall f vs vs' ts *)
(*     (Hval_obs: val_obs_list f vs vs'), *)
(*     val_casted.val_has_type_list_func vs ts <-> *)
(*     val_casted.val_has_type_list_func vs' ts. *)
(* Proof. *)
(*   intros. *)
(*   generalize dependent vs'. *)
(*   generalize dependent ts. *)
(*   induction vs; *)
(*     intros. inversion Hval_obs; subst. *)
(*   simpl; destruct ts; split; *)
(*     by auto. *)
(*   inversion Hval_obs; subst. *)
(*   destruct ts; simpl; first by split; auto. *)
(*   split; intros; move/andP:H=>[H H']; *)
(*     apply/andP. *)
(*   split; *)
(*     [erewrite <- val_has_type_obs; eauto | *)
(*      destruct (IHvs ts _ H3); eauto]. *)
(*   split; *)
(*     [erewrite val_has_type_obs; eauto | *)
(*      destruct (IHvs ts _ H3); eauto]. *)
(* Qed. *)
(* Lemma vals_defined_obs: *)
(*   forall f vs vs' *)
(*     (Hval_obs: val_obs_list f vs vs'), *)
(*     val_casted.vals_defined vs <-> val_casted.vals_defined vs'. *)
(* Proof. *)
(*   intros. *)
(*   induction Hval_obs; *)
(*     simpl; try tauto. *)
(*   destruct v; inversion H; *)
(*     by tauto. *)
(* Qed. *)
Proof with eauto with val_renamings.
intros.
destruct v1, v1'; inversion Hval_obs;
inversion Hval_obs'; subst;
solve [simpl; eauto with val_renamings ||
destruct Archi.ptr64; simpl; eauto with val_renamings].
Qed.

Lemma val_obs_addl:
forall f v1 v2 v1' v2'
(Hval_obs': val_obs f v1' v2')
(Hval_obs: val_obs f v1 v2),
val_obs f (Val.addl v1 v1') (Val.addl v2 v2').