diff --git a/lib/clib/CCorresLemmas.thy b/lib/clib/CCorresLemmas.thy index 3618371ae..94a6a6cc0 100644 --- a/lib/clib/CCorresLemmas.thy +++ b/lib/clib/CCorresLemmas.thy @@ -630,6 +630,13 @@ lemma ccorres_liftE: by (fastforce split: xstate.splits simp: liftE_def ccorres_underlying_def bind_def' return_def unif_rrel_def) +lemma ccorres_liftE': + fixes \ + assumes cc: "ccorresG sr \ (r \ Inr) xf P P' hs a c" + shows "ccorresG sr \ r xf P P' hs (liftE a) c" + using cc + by (auto intro!: ccorres_liftE cong: ccorres_context_cong) + lemma ccorres_if_bind: "ccorres_underlying sr Gamm r xf arrel axf G G' hs (if a then (b >>= f) else (c >>= f)) d \ ccorres_underlying sr Gamm r xf arrel axf G G' hs ((if a then b else c) >>= f) d" @@ -871,9 +878,9 @@ proof - qed thus ?thesis using lxs j pn apply (auto simp: init_xs_def word_less_nat_alt neq_Nil_conv unat_word_ariths unat_of_nat push_mods - simp del: unsigned_of_nat elim!: ccorres_guard_imp2 - dest!: spec[where x=Nil]) + dest!: spec[where x=Nil] + cong: ccorres_all_cong) done qed @@ -1151,4 +1158,23 @@ qed lemmas ccorres_While' = ccorres_While[where C'=UNIV, simplified] + +\ \simp rules for rewriting common patterns in the return relations\ +lemma ccorres_dc_o_simp[simp]: + "ccorres_underlying srel \ (dc \ f) xf ar axf P Q hs m c + = ccorres_underlying srel \ dc xf ar axf P Q hs m c" + "ccorres_underlying srel \ r xf (dc \ f) axf P Q hs m c + = ccorres_underlying srel \ r xf dc axf P Q hs m c" + by (simp cong: ccorres_all_cong)+ + +lemma ccorres_inl_rrel_inl_rrel[simp]: + "ccorres_underlying srel \ r xf (inl_rrel (inl_rrel ar)) axf P Q hs m c + = ccorres_underlying srel \ r xf (inl_rrel ar) axf P Q hs m c" + by (simp add: inl_rrel_inl_rrel cong: ccorres_all_cong)+ + +lemma ccorres_inr_rrel_Inr[simp]: + "ccorres_underlying srel \ (inr_rrel r \ Inr) xf ar axf P Q hs m c + = ccorres_underlying srel \ r xf ar axf P Q hs m c" + by (simp cong: ccorres_context_cong)+ + end diff --git a/lib/clib/Corres_UL_C.thy b/lib/clib/Corres_UL_C.thy index a8ab1afb8..20d5c09fc 100644 --- a/lib/clib/Corres_UL_C.thy +++ b/lib/clib/Corres_UL_C.thy @@ -1719,4 +1719,110 @@ lemma ccorres_grab_asm: ccorres_underlying sr G rr xf ar ax (P and K Q) P' hs f g" by (fastforce simp: ccorres_underlying_def) + +\ \ An experimental cong rule for rewriting everywhere reasonable, with full context. + Can cause problems when there are schematic variables or when one of the return relations + takes a pair as a parameter. \ +lemma ccorres_context_cong_helper': + assumes c: "ccorres_underlying sr \ r xf ar axf P Q hs a c" + assumes "\s. P s = P' s" + \ \Don't use membership equality when rewriting Q, as the LHS can be simplified into something + that is unable to unify with the RHS. + assumes "\s s'. \ (s,s') \ sr; P' s \ \ s' \ Q = (s' \ Q')"\ + assumes "\s s'. \ (s, s') \ sr; P' s \ \ Q = Q'" + assumes "hs = hs'" + assumes "\s s'. \ (s, s') \ sr; P' s; s' \ Q' \ \ a s = a' s" + assumes "\s s' s''. \ (s, s') \ sr; P' s; s' \ Q' \ \ semantic_equiv \ s' s'' c c'" + assumes "\s s' t'. + \ (s, s') \ sr; P' s; s' \ Q'; \ \\<^sub>h \c' # hs', s'\ \ (size hs', Normal t') \ \ + xf t' = xf' t'" + assumes "\x s t s' t'. + \ (s, s') \ sr; P' s; s' \ Q'; (t, t') \ sr; (x, t) \ fst (a' s); + \ \\<^sub>h \c' # hs', s'\ \ (size hs', Normal t') \ \ + r x (xf' t') = r' x (xf' t')" + assumes "\s s' t' n. + \ (s, s') \ sr; P' s; s' \ Q'; n \ size hs'; \ \\<^sub>h \c' # hs', s'\ \ (n, Normal t') \ \ + axf t' = axf' t'" + assumes "\x s t s' t' n. + \ (s, s') \ sr; P' s; s' \ Q'; (t, t') \ sr; (x, t) \ fst (a' s); n \ size hs'; + \ \\<^sub>h \c' # hs', s'\ \ (n, Normal t') \ \ + ar x (axf' t') = ar' x (axf' t')" + shows "ccorres_underlying sr \ r' xf' ar' axf' P' Q' hs' a' c'" + using c + apply - + apply (rule ccorresI') + apply (erule (1) ccorresE) + apply (force simp: assms) + apply (force simp: assms) + apply (force simp: assms) + apply (clarsimp simp: assms) + apply (erule exec_handlers_semantic_equivD2) + apply (force simp: assms) + apply (fastforce simp: unif_rrel_def assms) + done + +lemma ccorres_context_cong_helper: + assumes "\s. P s = P' s" + assumes "\s s'. \ (s, s') \ sr; P' s \ \ Q = Q'" + assumes "hs = hs'" + assumes "\s s'. \ (s, s') \ sr; P' s; s' \ Q' \ \ a s = a' s" + assumes "\s s' s''. \ (s, s') \ sr; P' s; s' \ Q' \ \ semantic_equiv \ s' s'' c c'" + assumes "\s s' t'. + \ (s, s') \ sr; P' s; s' \ Q'; \ \\<^sub>h \c' # hs', s'\ \ (size hs', Normal t') \ \ + xf t' = xf' t'" + assumes "\x s t s' t'. + \ (s, s') \ sr; P' s; s' \ Q'; (t, t') \ sr; (x, t) \ fst (a' s); + \ \\<^sub>h \c' # hs', s'\ \ (size hs', Normal t') \ \ + r x (xf' t') = r' x (xf' t')" + assumes "\s s' t' n. + \ (s, s') \ sr; P' s; s' \ Q'; n \ size hs'; \ \\<^sub>h \c' # hs', s'\ \ (n, Normal t') \ \ + axf t' = axf' t'" + assumes "\x s t s' t' n. + \ (s, s') \ sr; P' s; s' \ Q'; (t, t') \ sr; (x, t) \ fst (a' s); n \ size hs'; + \ \\<^sub>h \c' # hs', s'\ \ (n, Normal t') \ \ + ar x (axf' t') = ar' x (axf' t')" + shows "ccorres_underlying sr \ r xf ar axf P Q hs a c + = ccorres_underlying sr \ r' xf' ar' axf' P' Q' hs' a' c'" + using assms + apply - + apply rule + apply (erule ccorres_context_cong_helper'; assumption) + apply (erule ccorres_context_cong_helper') + by (fastforce simp: semantic_equiv_sym exec_handlers_semantic_equiv[where a=c and b=c'])+ + +lemmas ccorres_context_cong = ccorres_context_cong_helper[OF _ _ _ _ semantic_equivI] + +\ \ Only rewrite guards, the handler stack and function bodies, with context. + This is often more useful, as we generally want the return relations and extraction + functions to be stable while working with a ccorres_underlying statement. \ +lemma ccorres_context_weak_cong: + assumes "\s. P s = P' s" + assumes "\s s'. \ (s, s') \ sr; P' s \ \ Q = Q'" + assumes "\s s'. \ (s, s') \ sr; P' s; s' \ Q' \ \ a s = a' s" + assumes "\s s' s''. \ (s, s') \ sr; P' s; s' \ Q' \ \ \\ \c,Normal s'\ \ s'' = \\ \c',Normal s'\ \ s''" + shows "ccorres_underlying sr \ r xf ar axf P Q hs a c + = ccorres_underlying sr \ r xf ar axf P' Q' hs a' c'" + by (clarsimp simp: assms cong: ccorres_context_cong) + +\ \ Even more restrictive: only rewrite the abstract monad. \ +lemma ccorres_abstract_cong: + "\ \s s'. \ (s, s') \ sr; P s ; s' \ P' \ \ a s = b s \ \ + ccorres_underlying sr G r xf ar axf P P' hs a c + = ccorres_underlying sr G r xf ar axf P P' hs b c" + by (clarsimp cong: ccorres_context_weak_cong) + +\ \ Rewrite almost everywhere, without context. This should behave the same as with normal + term rewriting with no cong rule, except it will not rewrite the state relation or function + environment. \ +lemma ccorres_all_cong: + "\ r=r'; xf=xf'; ar=ar'; axf=axf'; P=P'; Q=Q'; hs=hs'; m=m'; c=c' \ \ + ccorres_underlying srel \ r xf ar axf P Q hs m c + = ccorres_underlying srel \ r' xf' ar' axf' P' Q' hs' m' c'" + by (simp cong: ccorres_context_cong) + +\ \ Only rewrite guards, the handler stack and function bodies, without context. + We make this the default behaviour, so that the the return relations and extraction + functions are stable under simplification. \ +lemmas ccorres_weak_cong = ccorres_all_cong[OF refl refl refl refl, cong] + end