+ assert (Vptrofs n0 = Vptrofs n) as H by congruence.
rewrite H; rewrite (Vptrofs_inj _ _ H) in *.
rewrite ALLOC0 in ALLOC; inv ALLOC; trivial.
+ inv H5.
rewrite LB0 in LB; inv LB. rewrite <- SZ in SZ0. rewrite (Vptrofs_inj _ _ SZ0); trivial.
+ inv H3; inv H5.
rewrite LB0 in LB; inv LB; trivial.
Qed.
Section CLC_SEM.
Variable g: Clight.genv.
Section CLC_step.
Variable function_entryT: function -> list val -> mem -> env -> temp_env -> mem -> list mem_event -> Prop.
Inductive clc_evstep: state -> mem -> list mem_event -> state -> mem -> Prop :=
| clc_evstep_assign: forall f a1 a2 k e le m loc ofs v2 v m' T1 T2 T3 mx,
eval_lvalueT g e le m a1 loc ofs T1 ->
eval_exprT g e le m a2 v2 T2 ->
sem_cast v2 (typeof a2) (typeof a1) m = Some v ->
assign_locT g (typeof a1) m loc ofs v m' T3 ->
clc_evstep (Clight.State f (Sassign a1 a2) k e le mx) m (T1++T2++T3)
(Clight.State f Sskip k e le m') m'
| clc_evstep_set: forall f id a k e le m v T mx,
eval_exprT g e le m a v T ->
clc_evstep (Clight.State f (Sset id a) k e le mx) m
T (Clight.State f Sskip k e (PTree.set id v le) m) m
| clc_evstep_call: forall f optid a al k e le m tyargs tyres cconv vf vargs fd T1 T2 mx,
classify_fun (typeof a) = fun_case_f tyargs tyres cconv ->
eval_exprT g e le m a vf T1 ->
eval_exprTlist g e le m al tyargs vargs T2 ->
Genv.find_funct g vf = Some fd ->
type_of_fundef fd = Tfunction tyargs tyres cconv ->
clc_evstep (Clight.State f (Scall optid a al) k e le mx) m
(T1++T2) (Clight.Callstate fd vargs (Clight.Kcall optid f e le k) m) m
| clc_evstep_builtin: forall f optid ef tyargs al k e le m vargs t vres m' T1 T2 mx,
eval_exprTlist g e le m al tyargs vargs T1 ->
builtin_event ef m vargs T2 ->
Events.external_call ef g vargs m t vres m' ->
clc_evstep (Clight.State f (Sbuiltin optid ef tyargs al) k e le mx) m
(T1++T2) (Clight.State f Sskip k e (set_opttemp optid vres le) m') m'
| clc_evstep_seq:  forall f s1 s2 k e le m mx,
clc_evstep (Clight.State f (Ssequence s1 s2) k e le mx) m
nil (Clight.State f s1 (Clight.Kseq s2 k) e le m) m
| clc_evstep_skip_seq: forall f s k e le m mx,
(*~ is_call_cont k ->*)
clc_evstep (Clight.State f Sskip (Clight.Kseq s k) e le mx) m
nil (Clight.State f s k e le m) m
| clc_evstep_continue_seq: forall f s k e le m mx,
clc_evstep (Clight.State f Scontinue (Clight.Kseq s k) e le mx) m
nil (Clight.State f Scontinue k e le m) m
| clc_evstep_break_seq: forall f s k e le m mx,
clc_evstep (Clight.State f Sbreak (Clight.Kseq s k) e le mx) m
nil (Clight.State f Sbreak k e le m) m
| clc_evstep_ifthenelse:  forall f a s1 s2 k e le m v1 b T mx,
eval_exprT g e le m a v1 T ->
bool_val v1 (typeof a) m = Some b ->
clc_evstep (Clight.State f (Sifthenelse a s1 s2) k e le mx) m
T (Clight.State f (if b then s1 else s2) k e le m) m
| clc_evstep_loop: forall f s1 s2 k e le m mx,
clc_evstep (Clight.State f (Sloop s1 s2) k e le mx) m
nil (Clight.State f s1 (Clight.Kloop1 s1 s2 k) e le m) m
| clc_evstep_skip_or_continue_loop1:  forall f s1 s2 k e le m x mx,
x = Sskip \/ x = Scontinue ->
clc_evstep (Clight.State f x (Clight.Kloop1 s1 s2 k) e le mx) m
nil (Clight.State f s2 (Clight.Kloop2 s1 s2 k) e le m) m
| clc_evstep_break_loop1:  forall f s1 s2 k e le m mx,
clc_evstep (Clight.State f Sbreak (Clight.Kloop1 s1 s2 k) e le mx) m
nil (Clight.State f Sskip k e le m) m
| clc_evstep_skip_loop2: forall f s1 s2 k e le m mx,
clc_evstep (Clight.State f Sskip (Clight.Kloop2 s1 s2 k) e le mx) m
nil (Clight.State f (Sloop s1 s2) k e le m) m
| clc_evstep_break_loop2: forall f s1 s2 k e le m mx,
clc_evstep (Clight.State f Sbreak (Clight.Kloop2 s1 s2 k) e le mx) m
nil (Clight.State f Sskip k e le m) m
| clc_evstep_return_0: forall f k e le m m' mx,
Mem.free_list m (blocks_of_env g e) = Some m' ->
clc_evstep (Clight.State f (Sreturn None) k e le mx) m
(Free (blocks_of_env g e)::nil) (Returnstate Vundef (Clight.call_cont k) m') m'
| clc_evstep_return_1: forall f a k e le m v v' m' T mx,
eval_exprT g e le m a v T ->
sem_cast v (typeof a) f.(fn_return) m = Some v' ->
Mem.free_list m (blocks_of_env g e) = Some m' ->
clc_evstep (Clight.State f (Sreturn (Some a)) k e le mx) m
(T++Free (blocks_of_env g e)::nil) (Returnstate v' (Clight.call_cont k) m') m'
| clc_evstep_skip_call: forall f k e le m m' mx,
is_call_cont k ->
Mem.free_list m (blocks_of_env g e) = Some m' ->
clc_evstep (Clight.State f Sskip k e le mx) m
(Free (blocks_of_env g e)::nil) (Returnstate Vundef k m') m'
| clc_evstep_switch: forall f a sl k e le m v n T mx,
eval_exprT g e le m a v T ->
sem_switch_arg v (typeof a) = Some n ->
clc_evstep (Clight.State f (Sswitch a sl) k e le mx) m
T (Clight.State f (seq_of_labeled_statement (select_switch n sl)) (Clight.Kswitch k) e le m) m
| clc_evstep_skip_break_switch: forall f x k e le m mx,
x = Sskip \/ x = Sbreak ->
clc_evstep (Clight.State f x (Clight.Kswitch k) e le mx) m
nil (Clight.State f Sskip k e le m) m
| clc_evstep_continue_switch: forall f k e le m mx,
clc_evstep (Clight.State f Scontinue (Clight.Kswitch k) e le mx) m
nil (Clight.State f Scontinue k e le m) m
| clc_evstep_label: forall f lbl s k e le m mx,
clc_evstep (Clight.State f (Slabel lbl s) k e le mx) m
nil (Clight.State f s k e le m) m
| clc_evstep_goto: forall f lbl k e le m s' k' mx,
Clight.find_label lbl f.(fn_body) (Clight.call_cont k) = Some (s', k') ->
clc_evstep (Clight.State f (Sgoto lbl) k e le mx) m
nil (Clight.State f s' k' e le m) m
| clc_evstep_internal_function: forall f vargs k m e le m1 T mx,
function_entryT f vargs m e le m1 T ->
clc_evstep (Clight.Callstate (Internal f) vargs k mx) m
T (Clight.State f f.(fn_body) k e le m1) m1
(* | clc_evstep_external_function: forall ef targs tres cconv vargs k m vres t m', external_call ef ge vargs m t vres m' -> clc_evstep (Clight.Callstate (External ef targs tres cconv) vargs k m) t (Clight.Returnstate vres k m')*)
| clc_evstep_returnstate: forall v optid f e le k m mx,
clc_evstep (Clight.Returnstate v (Clight.Kcall optid f e le k) mx) m
nil (Clight.State f Sskip k e (set_opttemp optid v le) m) m.

(* Specifications: *)
Lemma clc_ax1
(HFe: forall f vargs m e le m1 T,
function_entryT f vargs m e le m1 T -> function_entry2 g f vargs m e le m1):
forall c m T c' m', clc_evstep c m T c' m' ->
Clight.at_external (set_mem c m) = None /\
m' = get_mem c' /\
exists t, step g (function_entry2 g) (set_mem c m) t c'.
Lemma clc_ax2
(Hfe: forall f vargs m e le m1, function_entry2 g f vargs m e le m1 ->
exists T, function_entryT f vargs m e le m1 T):
forall d t c'
(H: step g (function_entry2 g) d t c')
c m (HD : d = set_mem c m)
(AE : Clight.at_external d = None),
exists T : list mem_event, clc_evstep c m T c' (get_mem c').
Lemma clc_fun (HFe: forall f vargs m e1 le1 m1 T1 (FE1:function_entryT f vargs m e1 le1 m1 T1)
e2 le2 m2 T2 (FE2:function_entryT f vargs m e2 le2 m2 T2), T1=T2):
forall c m T1 c1 m1 T2 c2 m2 (EX1: clc_evstep c m T1 c1 m1)
(EX2:clc_evstep c m T2 c2 m2), T1 = T2.
Lemma extcall_ev_elim: forall ef g vargs m t vres m' ev
(Hext: Events.external_call ef g vargs m t vres m')
(Hev: builtin_event ef m vargs ev)
(Hef: match ef with EF_malloc | EF_free | EF_memcpy _ _ => False | _ => True end),
ev_elim m ev m'.
Lemma clc_ev_elim (FE: forall f vargs m e le m1 T (E:function_entryT f vargs m e le m1 T), ev_elim m T m1):
forall c m T c' m' (E: clc_evstep c m T c' m'), ev_elim m T m'.