wenzelm@12857: (* Title: HOL/Bali/AxCompl.thy schirmer@13688: Author: David von Oheimb and Norbert Schirmer schirmer@12854: *) schirmer@12854: wenzelm@58887: subsection {* schirmer@12854: Completeness proof for Axiomatic semantics of Java expressions and statements schirmer@12854: *} schirmer@12854: haftmann@16417: theory AxCompl imports AxSem begin schirmer@12854: schirmer@12854: text {* schirmer@12854: design issues: schirmer@12854: \begin{itemize} schirmer@12854: \item proof structured by Most General Formulas (-> Thomas Kleymann) schirmer@12854: \end{itemize} schirmer@12854: *} schirmer@12925: schirmer@12925: schirmer@12925: schirmer@13688: wenzelm@58887: subsubsection "set of not yet initialzed classes" schirmer@12854: wenzelm@37956: definition wenzelm@37956: nyinitcls :: "prog \ state \ qtname set" wenzelm@37956: where "nyinitcls G s = {C. is_class G C \ \ initd C s}" schirmer@12854: schirmer@12854: lemma nyinitcls_subset_class: "nyinitcls G s \ {C. is_class G C}" schirmer@12854: apply (unfold nyinitcls_def) schirmer@12854: apply fast schirmer@12854: done schirmer@12854: schirmer@12854: lemmas finite_nyinitcls [simp] = wenzelm@45605: finite_is_class [THEN nyinitcls_subset_class [THEN finite_subset]] schirmer@12854: schirmer@12854: lemma card_nyinitcls_bound: "card (nyinitcls G s) \ card {C. is_class G C}" schirmer@12854: apply (rule nyinitcls_subset_class [THEN finite_is_class [THEN card_mono]]) schirmer@12854: done schirmer@12854: schirmer@12854: lemma nyinitcls_set_locals_cong [simp]: schirmer@12854: "nyinitcls G (x,set_locals l s) = nyinitcls G (x,s)" wenzelm@48001: by (simp add: nyinitcls_def) schirmer@12854: schirmer@12854: lemma nyinitcls_abrupt_cong [simp]: "nyinitcls G (f x, y) = nyinitcls G (x, y)" wenzelm@48001: by (simp add: nyinitcls_def) schirmer@12854: wenzelm@48001: lemma nyinitcls_abupd_cong [simp]: "nyinitcls G (abupd f s) = nyinitcls G s" wenzelm@48001: by (simp add: nyinitcls_def) schirmer@12854: schirmer@12854: lemma card_nyinitcls_abrupt_congE [elim!]: wenzelm@48001: "card (nyinitcls G (x, s)) \ n \ card (nyinitcls G (y, s)) \ n" wenzelm@48001: unfolding nyinitcls_def by auto schirmer@12854: schirmer@12854: lemma nyinitcls_new_xcpt_var [simp]: wenzelm@48001: "nyinitcls G (new_xcpt_var vn s) = nyinitcls G s" wenzelm@48001: by (induct s) (simp_all add: nyinitcls_def) schirmer@12854: schirmer@12854: lemma nyinitcls_init_lvars [simp]: schirmer@12854: "nyinitcls G ((init_lvars G C sig mode a' pvs) s) = nyinitcls G s" wenzelm@48001: by (induct s) (simp add: init_lvars_def2 split add: split_if) schirmer@12854: schirmer@12854: lemma nyinitcls_emptyD: "\nyinitcls G s = {}; is_class G C\ \ initd C s" wenzelm@48001: unfolding nyinitcls_def by fast schirmer@12854: schirmer@13688: lemma card_Suc_lemma: schirmer@13688: "\card (insert a A) \ Suc n; a\A; finite A\ \ card A \ n" wenzelm@48001: by auto schirmer@12854: schirmer@12854: lemma nyinitcls_le_SucD: schirmer@12854: "\card (nyinitcls G (x,s)) \ Suc n; \inited C (globs s); class G C=Some y\ \ schirmer@12854: card (nyinitcls G (x,init_class_obj G C s)) \ n" schirmer@12854: apply (subgoal_tac schirmer@12854: "nyinitcls G (x,s) = insert C (nyinitcls G (x,init_class_obj G C s))") schirmer@12854: apply clarsimp wenzelm@59807: apply (erule_tac V="nyinitcls G (x, s) = rhs" for rhs in thin_rl) schirmer@12854: apply (rule card_Suc_lemma [OF _ _ finite_nyinitcls]) schirmer@12854: apply (auto dest!: not_initedD elim!: schirmer@12854: simp add: nyinitcls_def inited_def split add: split_if_asm) schirmer@12854: done schirmer@12854: schirmer@13688: lemma inited_gext': "\s\|s';inited C (globs s)\ \ inited C (globs s')" wenzelm@48001: by (rule inited_gext) schirmer@12854: schirmer@12854: lemma nyinitcls_gext: "snd s\|snd s' \ nyinitcls G s' \ nyinitcls G s" wenzelm@48001: unfolding nyinitcls_def by (force dest!: inited_gext') schirmer@12854: schirmer@12854: lemma card_nyinitcls_gext: schirmer@12854: "\snd s\|snd s'; card (nyinitcls G s) \ n\\ card (nyinitcls G s') \ n" schirmer@12854: apply (rule le_trans) schirmer@12854: apply (rule card_mono) schirmer@12854: apply (rule finite_nyinitcls) schirmer@12854: apply (erule nyinitcls_gext) schirmer@12854: apply assumption schirmer@12854: done schirmer@12854: schirmer@12854: wenzelm@58887: subsubsection "init-le" schirmer@12854: wenzelm@37956: definition wenzelm@37956: init_le :: "prog \ nat \ state \ bool" ("_\init\_" [51,51] 50) wenzelm@37956: where "G\init\n = (\s. card (nyinitcls G s) \ n)" schirmer@12854: schirmer@12854: lemma init_le_def2 [simp]: "(G\init\n) s = (card (nyinitcls G s)\n)" schirmer@12854: apply (unfold init_le_def) schirmer@12854: apply auto schirmer@12854: done schirmer@12854: schirmer@13688: lemma All_init_leD: schirmer@13688: "\n::nat. G,(A::'a triple set)\{P \. G\init\n} t\ {Q::'a assn} schirmer@13688: \ G,A\{P} t\ {Q}" schirmer@12854: apply (drule spec) schirmer@12854: apply (erule conseq1) schirmer@12854: apply clarsimp schirmer@12854: apply (rule card_nyinitcls_bound) schirmer@12854: done schirmer@12854: wenzelm@58887: subsubsection "Most General Triples and Formulas" schirmer@12854: wenzelm@37956: definition wenzelm@37956: remember_init_state :: "state assn" ("\") wenzelm@37956: where "\ \ \Y s Z. s = Z" schirmer@12854: schirmer@12854: lemma remember_init_state_def2 [simp]: "\ Y = op =" schirmer@12854: apply (unfold remember_init_state_def) schirmer@12854: apply (simp (no_asm)) schirmer@12854: done schirmer@12854: wenzelm@37956: definition schirmer@12854: MGF ::"[state assn, term, prog] \ state triple" ("{_} _\ {_\}"[3,65,3]62) wenzelm@37956: where "{P} t\ {G\} = {P} t\ {\Y s' s. G\s \t\\ (Y,s')}" schirmer@12854: wenzelm@37956: definition wenzelm@37956: MGFn :: "[nat, term, prog] \ state triple" ("{=:_} _\ {_\}"[3,65,3]62) wenzelm@37956: where "{=:n} t\ {G\} = {\ \. G\init\n} t\ {G\}" schirmer@12854: schirmer@12854: (* unused *) schirmer@12925: lemma MGF_valid: "wf_prog G \ G,{}\{\} t\ {G\}" schirmer@12854: apply (unfold MGF_def) schirmer@12925: apply (simp add: ax_valids_def triple_valid_def2) schirmer@12925: apply (auto elim: evaln_eval) schirmer@12854: done schirmer@12854: schirmer@12925: schirmer@12854: lemma MGF_res_eq_lemma [simp]: schirmer@12854: "(\Y' Y s. Y = Y' \ P s \ Q s) = (\s. P s \ Q s)" wenzelm@48001: by auto schirmer@12854: schirmer@12854: lemma MGFn_def2: schirmer@12854: "G,A\{=:n} t\ {G\} = G,A\{\ \. G\init\n} schirmer@12854: t\ {\Y s' s. G\s \t\\ (Y,s')}" wenzelm@48001: unfolding MGFn_def MGF_def by fast schirmer@12854: schirmer@13688: lemma MGF_MGFn_iff: schirmer@13688: "G,(A::state triple set)\{\} t\ {G\} = (\n. G,A\{=:n} t\ {G\})" wenzelm@48001: apply (simp add: MGFn_def2 MGF_def) schirmer@12854: apply safe schirmer@12854: apply (erule_tac [2] All_init_leD) schirmer@12854: apply (erule conseq1) schirmer@12854: apply clarsimp schirmer@12854: done schirmer@12854: schirmer@12854: lemma MGFnD: schirmer@13688: "G,(A::state triple set)\{=:n} t\ {G\} \ schirmer@12854: G,A\{(\Y' s' s. s' = s \ P s) \. G\init\n} schirmer@12854: t\ {(\Y' s' s. G\s\t\\(Y',s') \ P s) \. G\init\n}" schirmer@12854: apply (unfold init_le_def) schirmer@12854: apply (simp (no_asm_use) add: MGFn_def2) schirmer@12854: apply (erule conseq12) schirmer@12854: apply clarsimp schirmer@12854: apply (erule (1) eval_gext [THEN card_nyinitcls_gext]) schirmer@12854: done schirmer@12854: lemmas MGFnD' = MGFnD [of _ _ _ _ "\x. True"] schirmer@12854: schirmer@13688: text {* To derive the most general formula, we can always assume a normal schirmer@13688: state in the precondition, since abrupt cases can be handled uniformally by schirmer@13688: the abrupt rule. schirmer@13688: *} schirmer@12854: lemma MGFNormalI: "G,A\{Normal \} t\ {G\} \ schirmer@12854: G,(A::state triple set)\{\::state assn} t\ {G\}" schirmer@12854: apply (unfold MGF_def) schirmer@12854: apply (rule ax_Normal_cases) schirmer@12854: apply (erule conseq1) schirmer@12854: apply clarsimp schirmer@12854: apply (rule ax_derivs.Abrupt [THEN conseq1]) schirmer@12854: apply (clarsimp simp add: Let_def) schirmer@12854: done schirmer@12854: schirmer@13688: lemma MGFNormalD: schirmer@13688: "G,(A::state triple set)\{\} t\ {G\} \ G,A\{Normal \} t\ {G\}" schirmer@12854: apply (unfold MGF_def) schirmer@12854: apply (erule conseq1) schirmer@12854: apply clarsimp schirmer@12854: done schirmer@12854: schirmer@13688: text {* Additionally to @{text MGFNormalI}, we also expand the definition of schirmer@13688: the most general formula here *} schirmer@12854: lemma MGFn_NormalI: schirmer@12854: "G,(A::state triple set)\{Normal((\Y' s' s. s'=s \ normal s) \. G\init\n)}t\ schirmer@12854: {\Y s' s. G\s \t\\ (Y,s')} \ G,A\{=:n}t\{G\}" schirmer@12854: apply (simp (no_asm_use) add: MGFn_def2) schirmer@12854: apply (rule ax_Normal_cases) schirmer@12854: apply (erule conseq1) schirmer@12854: apply clarsimp schirmer@12854: apply (rule ax_derivs.Abrupt [THEN conseq1]) schirmer@12854: apply (clarsimp simp add: Let_def) schirmer@12854: done schirmer@12854: schirmer@13688: text {* To derive the most general formula, we can restrict ourselves to schirmer@13688: welltyped terms, since all others can be uniformally handled by the hazard schirmer@13688: rule. *} schirmer@12854: lemma MGFn_free_wt: schirmer@12854: "(\T L C. \prg=G,cls=C,lcl=L\\t\T) schirmer@12854: \ G,(A::state triple set)\{=:n} t\ {G\} schirmer@12854: \ G,A\{=:n} t\ {G\}" schirmer@12854: apply (rule MGFn_NormalI) schirmer@12854: apply (rule ax_free_wt) schirmer@12854: apply (auto elim: conseq12 simp add: MGFn_def MGF_def) schirmer@12854: done schirmer@12854: schirmer@13688: text {* To derive the most general formula, we can restrict ourselves to schirmer@13688: welltyped terms and assume that the state in the precondition conforms to the schirmer@13688: environment. All type violations can be uniformally handled by the hazard schirmer@13688: rule. *} schirmer@12925: lemma MGFn_free_wt_NormalConformI: schirmer@13688: "(\ T L C . \prg=G,cls=C,lcl=L\\t\T schirmer@12925: \ G,(A::state triple set) schirmer@12925: \{Normal((\Y' s' s. s'=s \ normal s) \. G\init\n) \. (\ s. s\\(G, L))} schirmer@12925: t\ schirmer@12925: {\Y s' s. G\s \t\\ (Y,s')}) schirmer@12925: \ G,A\{=:n}t\{G\}" schirmer@12925: apply (rule MGFn_NormalI) schirmer@12925: apply (rule ax_no_hazard) schirmer@12925: apply (rule ax_escape) schirmer@12925: apply (intro strip) schirmer@12925: apply (simp only: type_ok_def peek_and_def) schirmer@12925: apply (erule conjE)+ schirmer@13688: apply (erule exE,erule exE, erule exE, erule exE,erule conjE,drule (1) mp, schirmer@13688: erule conjE) schirmer@12925: apply (drule spec,drule spec, drule spec, drule (1) mp) schirmer@12925: apply (erule conseq12) schirmer@12925: apply blast schirmer@12925: done schirmer@12925: schirmer@13688: text {* To derive the most general formula, we can restrict ourselves to schirmer@13688: welltyped terms and assume that the state in the precondition conforms to the schirmer@13688: environment and that the term is definetly assigned with respect to this state. schirmer@13688: All type violations can be uniformally handled by the hazard rule. *} schirmer@13688: lemma MGFn_free_wt_da_NormalConformI: schirmer@13688: "(\ T L C B. \prg=G,cls=C,lcl=L\\t\T schirmer@13688: \ G,(A::state triple set) schirmer@13688: \{Normal((\Y' s' s. s'=s \ normal s) \. G\init\n) \. (\ s. s\\(G, L)) schirmer@13688: \. (\ s. \prg=G,cls=C,lcl=L\\dom (locals (store s))\t\B)} schirmer@13688: t\ schirmer@13688: {\Y s' s. G\s \t\\ (Y,s')}) schirmer@13688: \ G,A\{=:n}t\{G\}" schirmer@13688: apply (rule MGFn_NormalI) schirmer@13688: apply (rule ax_no_hazard) schirmer@13688: apply (rule ax_escape) schirmer@13688: apply (intro strip) schirmer@13688: apply (simp only: type_ok_def peek_and_def) schirmer@13688: apply (erule conjE)+ schirmer@13688: apply (erule exE,erule exE, erule exE, erule exE,erule conjE,drule (1) mp, schirmer@13688: erule conjE) schirmer@13688: apply (drule spec,drule spec, drule spec,drule spec, drule (1) mp) schirmer@13688: apply (erule conseq12) schirmer@13688: apply blast schirmer@13688: done schirmer@12854: wenzelm@58887: subsubsection "main lemmas" schirmer@12854: schirmer@13688: lemma MGFn_Init: schirmer@13688: assumes mgf_hyp: "\m. Suc m\n \ (\t. G,A\{=:m} t\ {G\})" schirmer@13688: shows "G,(A::state triple set)\{=:n} \Init C\\<^sub>s\ {G\}" schirmer@13688: proof (rule MGFn_free_wt [rule_format],elim exE,rule MGFn_NormalI) schirmer@13688: fix T L accC schirmer@13688: assume "\prg=G, cls=accC, lcl= L\\\Init C\\<^sub>s\T" schirmer@13688: hence is_cls: "is_class G C" schirmer@13688: by cases simp schirmer@13688: show "G,A\{Normal ((\Y' s' s. s' = s \ normal s) \. G\init\n)} schirmer@13688: .Init C. schirmer@13688: {\Y s' s. G\s \\Init C\\<^sub>s\\ (Y, s')}" schirmer@13688: (is "G,A\{Normal ?P} .Init C. {?R}") schirmer@13688: proof (rule ax_cases [where ?C="initd C"]) schirmer@13688: show "G,A\{Normal ?P \. initd C} .Init C. {?R}" nipkow@44890: by (rule ax_derivs.Done [THEN conseq1]) (fastforce intro: init_done) schirmer@13688: next schirmer@13688: have "G,A\{Normal (?P \. Not \ initd C)} .Init C. {?R}" schirmer@13688: proof (cases n) schirmer@13688: case 0 schirmer@13688: with is_cls schirmer@13688: show ?thesis nipkow@44890: by - (rule ax_impossible [THEN conseq1],fastforce dest: nyinitcls_emptyD) schirmer@13688: next schirmer@13688: case (Suc m) schirmer@13688: with mgf_hyp have mgf_hyp': "\ t. G,A\{=:m} t\ {G\}" wenzelm@32960: by simp schirmer@13688: from is_cls obtain c where c: "the (class G C) = c" wenzelm@32960: by auto schirmer@13688: let ?Q= "(\Y s' (x,s) . schirmer@13688: G\ (x,init_class_obj G C s) schirmer@13688: \ (if C=Object then Skip else Init (super (the (class G C))))\ s' schirmer@13688: \ x=None \ \inited C (globs s)) \. G\init\m" schirmer@13688: from c schirmer@13688: show ?thesis schirmer@13688: proof (rule ax_derivs.Init [where ?Q="?Q"]) wenzelm@32960: let ?P' = "Normal ((\Y s' s. s' = supd (init_class_obj G C) s schirmer@13688: \ normal s \ \ initd C s) \. G\init\m)" wenzelm@32960: show "G,A\{Normal (?P \. Not \ initd C ;. supd (init_class_obj G C))} schirmer@13688: .(if C = Object then Skip else Init (super c)). schirmer@13688: {?Q}" wenzelm@32960: proof (rule conseq1 [where ?P'="?P'"]) wenzelm@32960: show "G,A\{?P'} .(if C = Object then Skip else Init (super c)). {?Q}" wenzelm@32960: proof (cases "C=Object") wenzelm@32960: case True wenzelm@32960: have "G,A\{?P'} .Skip. {?Q}" wenzelm@32960: by (rule ax_derivs.Skip [THEN conseq1]) wenzelm@32960: (auto simp add: True intro: eval.Skip) schirmer@13688: with True show ?thesis wenzelm@32960: by simp wenzelm@32960: next wenzelm@32960: case False wenzelm@32960: from mgf_hyp' wenzelm@32960: have "G,A\{?P'} .Init (super c). {?Q}" nipkow@44890: by (rule MGFnD' [THEN conseq12]) (fastforce simp add: False c) wenzelm@32960: with False show ?thesis wenzelm@32960: by simp wenzelm@32960: qed wenzelm@32960: next wenzelm@32960: from Suc is_cls wenzelm@32960: show "Normal (?P \. Not \ initd C ;. supd (init_class_obj G C)) schirmer@13688: \ ?P'" nipkow@44890: by (fastforce elim: nyinitcls_le_SucD) wenzelm@32960: qed schirmer@13688: next wenzelm@32960: from mgf_hyp' wenzelm@32960: show "\l. G,A\{?Q \. (\s. l = locals (snd s)) ;. set_lvars empty} schirmer@13688: .init c. schirmer@13688: {set_lvars l .; ?R}" wenzelm@32960: apply (rule MGFnD' [THEN conseq12, THEN allI]) wenzelm@32960: apply (clarsimp simp add: split_paired_all) wenzelm@32960: apply (rule eval.Init [OF c]) wenzelm@32960: apply (insert c) wenzelm@32960: apply auto wenzelm@32960: done schirmer@13688: qed schirmer@13688: qed schirmer@13688: thus "G,A\{Normal ?P \. Not \ initd C} .Init C. {?R}" schirmer@13688: by clarsimp schirmer@13688: qed schirmer@13688: qed schirmer@12854: lemmas MGFn_InitD = MGFn_Init [THEN MGFnD, THEN ax_NormalD] schirmer@12854: schirmer@12854: lemma MGFn_Call: schirmer@13688: assumes mgf_methds: schirmer@13688: "\C sig. G,(A::state triple set)\{=:n} \(Methd C sig)\\<^sub>e\ {G\}" schirmer@13688: and mgf_e: "G,A\{=:n} \e\\<^sub>e\ {G\}" schirmer@13688: and mgf_ps: "G,A\{=:n} \ps\\<^sub>l\ {G\}" schirmer@13688: and wf: "wf_prog G" schirmer@13688: shows "G,A\{=:n} \{accC,statT,mode}e\mn({pTs'}ps)\\<^sub>e\ {G\}" schirmer@13688: proof (rule MGFn_free_wt_da_NormalConformI [rule_format],clarsimp) schirmer@13688: note inj_term_simps [simp] schirmer@13688: fix T L accC' E schirmer@13688: assume wt: "\prg=G,cls=accC',lcl = L\\\({accC,statT,mode}e\mn( {pTs'}ps))\\<^sub>e\T" schirmer@13688: then obtain pTs statDeclT statM where schirmer@13688: wt_e: "\prg=G,cls=accC,lcl=L\\e\-RefT statT" and schirmer@13688: wt_args: "\prg=G,cls=accC,lcl=L\\ps\\pTs" and schirmer@13688: statM: "max_spec G accC statT \name=mn,parTs=pTs\ schirmer@13688: = {((statDeclT,statM),pTs')}" and schirmer@13688: mode: "mode = invmode statM e" and schirmer@13688: T: "T =Inl (resTy statM)" and schirmer@13688: eq_accC_accC': "accC=accC'" nipkow@44890: by cases fastforce+ schirmer@13688: let ?Q="(\Y s1 (x,s) . x = None \ schirmer@13688: (\a. G\Norm s \e-\a\ s1 \ schirmer@13688: (normal s1 \ G, store s1\a\\RefT statT) schirmer@13688: \ Y = In1 a) \ schirmer@13688: (\ P. normal s1 schirmer@13688: \ \prg=G,cls=accC',lcl=L\\dom (locals (store s1))\\ps\\<^sub>l\P)) schirmer@13688: \. G\init\n \. (\ s. s\\(G, L))::state assn" schirmer@13688: let ?R="\a. ((\Y (x2,s2) (x,s) . x = None \ schirmer@13688: (\s1 pvs. G\Norm s \e-\a\ s1 \ schirmer@13688: (normal s1 \ G, store s1\a\\RefT statT)\ schirmer@13688: Y = \pvs\\<^sub>l \ G\s1 \ps\\pvs\ (x2,s2))) schirmer@13688: \. G\init\n \. (\ s. s\\(G, L)))::state assn" schirmer@12925: schirmer@13688: show "G,A\{Normal ((\Y' s' s. s' = s \ abrupt s = None) \. G\init\n \. schirmer@13688: (\s. s\\(G, L)) \. schirmer@13688: (\s. \prg=G, cls=accC',lcl=L\ \ dom (locals (store s)) schirmer@13688: \ \{accC,statT,mode}e\mn( {pTs'}ps)\\<^sub>e\ E))} schirmer@13688: {accC,statT,mode}e\mn( {pTs'}ps)-\ schirmer@13688: {\Y s' s. \v. Y = \v\\<^sub>e \ schirmer@13688: G\s \{accC,statT,mode}e\mn( {pTs'}ps)-\v\ s'}" schirmer@13688: (is "G,A\{Normal ?P} {accC,statT,mode}e\mn( {pTs'}ps)-\ {?S}") schirmer@13688: proof (rule ax_derivs.Call [where ?Q="?Q" and ?R="?R"]) schirmer@13688: from mgf_e schirmer@13688: show "G,A\{Normal ?P} e-\ {?Q}" schirmer@13688: proof (rule MGFnD' [THEN conseq12],clarsimp) schirmer@13688: fix s0 s1 a schirmer@13688: assume conf_s0: "Norm s0\\(G, L)" schirmer@13688: assume da: "\prg=G,cls=accC',lcl=L\\ schirmer@13688: dom (locals s0) \\{accC,statT,mode}e\mn( {pTs'}ps)\\<^sub>e\ E" schirmer@13688: assume eval_e: "G\Norm s0 \e-\a\ s1" schirmer@13688: show "(abrupt s1 = None \ G,store s1\a\\RefT statT) \ schirmer@13688: (abrupt s1 = None \ schirmer@13688: (\P. \prg=G,cls=accC',lcl=L\\ dom (locals (store s1)) \\ps\\<^sub>l\ P)) schirmer@13688: \ s1\\(G, L)" schirmer@13688: proof - wenzelm@32960: from da obtain C where wenzelm@32960: da_e: "\prg=G,cls=accC,lcl=L\\ schirmer@13688: dom (locals (store ((Norm s0)::state)))\\e\\<^sub>e\ C" and wenzelm@32960: da_ps: "\prg=G,cls=accC,lcl=L\\ nrm C \\ps\\<^sub>l\ E" wenzelm@32960: by cases (simp add: eq_accC_accC') wenzelm@32960: from eval_e conf_s0 wt_e da_e wf wenzelm@32960: obtain "(abrupt s1 = None \ G,store s1\a\\RefT statT)" wenzelm@32960: and "s1\\(G, L)" wenzelm@32960: by (rule eval_type_soundE) simp wenzelm@32960: moreover wenzelm@32960: { wenzelm@32960: assume normal_s1: "normal s1" wenzelm@32960: have "\P. \prg=G,cls=accC,lcl=L\\ dom (locals (store s1)) \\ps\\<^sub>l\ P" wenzelm@32960: proof - wenzelm@32960: from eval_e wt_e da_e wf normal_s1 wenzelm@32960: have "nrm C \ dom (locals (store s1))" wenzelm@32960: by (cases rule: da_good_approxE') iprover wenzelm@32960: with da_ps show ?thesis wenzelm@32960: by (rule da_weakenE) iprover wenzelm@32960: qed wenzelm@32960: } wenzelm@32960: ultimately show ?thesis wenzelm@32960: using eq_accC_accC' by simp schirmer@13688: qed schirmer@13688: qed schirmer@13688: next schirmer@13688: show "\a. G,A\{?Q\In1 a} ps\\ {?R a}" (is "\ a. ?PS a") schirmer@13688: proof schirmer@13688: fix a schirmer@13688: show "?PS a" schirmer@13688: proof (rule MGFnD' [OF mgf_ps, THEN conseq12], schirmer@13688: clarsimp simp add: eq_accC_accC' [symmetric]) wenzelm@32960: fix s0 s1 s2 vs wenzelm@32960: assume conf_s1: "s1\\(G, L)" wenzelm@32960: assume eval_e: "G\Norm s0 \e-\a\ s1" wenzelm@32960: assume conf_a: "abrupt s1 = None \ G,store s1\a\\RefT statT" wenzelm@32960: assume eval_ps: "G\s1 \ps\\vs\ s2" wenzelm@32960: assume da_ps: "abrupt s1 = None \ schirmer@13688: (\P. \prg=G,cls=accC,lcl=L\\ schirmer@13688: dom (locals (store s1)) \\ps\\<^sub>l\ P)" wenzelm@32960: show "(\s1. G\Norm s0 \e-\a\ s1 \ schirmer@13688: (abrupt s1 = None \ G,store s1\a\\RefT statT) \ schirmer@13688: G\s1 \ps\\vs\ s2) \ schirmer@13688: s2\\(G, L)" wenzelm@32960: proof (cases "normal s1") wenzelm@32960: case True wenzelm@32960: with da_ps obtain P where wenzelm@32960: "\prg=G,cls=accC,lcl=L\\ dom (locals (store s1)) \\ps\\<^sub>l\ P" wenzelm@32960: by auto wenzelm@32960: from eval_ps conf_s1 wt_args this wf wenzelm@32960: have "s2\\(G, L)" wenzelm@32960: by (rule eval_type_soundE) wenzelm@32960: with eval_e conf_a eval_ps wenzelm@32960: show ?thesis wenzelm@32960: by auto wenzelm@32960: next wenzelm@32960: case False wenzelm@32960: with eval_ps have "s2=s1" by auto wenzelm@32960: with eval_e conf_a eval_ps conf_s1 wenzelm@32960: show ?thesis wenzelm@32960: by auto wenzelm@32960: qed schirmer@13688: qed schirmer@13688: qed schirmer@13688: next schirmer@13688: show "\a vs invC declC l. schirmer@13688: G,A\{?R a\\vs\\<^sub>l \. schirmer@13688: (\s. declC = schirmer@13688: invocation_declclass G mode (store s) a statT schirmer@13688: \name=mn, parTs=pTs'\ \ schirmer@13688: invC = invocation_class mode (store s) a statT \ schirmer@13688: l = locals (store s)) ;. schirmer@13688: init_lvars G declC \name=mn, parTs=pTs'\ mode a vs \. schirmer@13688: (\s. normal s \ G\mode\invC\statT)} schirmer@13688: Methd declC \name=mn,parTs=pTs'\-\ schirmer@13688: {set_lvars l .; ?S}" schirmer@13688: (is "\ a vs invC declC l. ?METHD a vs invC declC l") schirmer@13688: proof (intro allI) schirmer@13688: fix a vs invC declC l schirmer@13688: from mgf_methds [rule_format] schirmer@13688: show "?METHD a vs invC declC l" schirmer@13688: proof (rule MGFnD' [THEN conseq12],clarsimp) wenzelm@32960: fix s4 s2 s1::state wenzelm@32960: fix s0 v wenzelm@32960: let ?D= "invocation_declclass G mode (store s2) a statT schirmer@13688: \name=mn,parTs=pTs'\" wenzelm@32960: let ?s3= "init_lvars G ?D \name=mn, parTs=pTs'\ mode a vs s2" wenzelm@32960: assume inv_prop: "abrupt ?s3=None schirmer@13688: \ G\mode\invocation_class mode (store s2) a statT\statT" wenzelm@32960: assume conf_s2: "s2\\(G, L)" wenzelm@32960: assume conf_a: "abrupt s1 = None \ G,store s1\a\\RefT statT" wenzelm@32960: assume eval_e: "G\Norm s0 \e-\a\ s1" wenzelm@32960: assume eval_ps: "G\s1 \ps\\vs\ s2" wenzelm@32960: assume eval_mthd: "G\?s3 \Methd ?D \name=mn,parTs=pTs'\-\v\ s4" wenzelm@32960: show "G\Norm s0 \{accC,statT,mode}e\mn( {pTs'}ps)-\v schirmer@13688: \ (set_lvars (locals (store s2))) s4" wenzelm@32960: proof - wenzelm@32960: obtain D where D: "D=?D" by simp wenzelm@32960: obtain s3 where s3: "s3=?s3" by simp wenzelm@32960: obtain s3' where wenzelm@32960: s3': "s3' = check_method_access G accC statT mode schirmer@13688: \name=mn,parTs=pTs'\ a s3" wenzelm@32960: by simp wenzelm@32960: have eq_s3'_s3: "s3'=s3" wenzelm@32960: proof - wenzelm@32960: from inv_prop s3 mode wenzelm@32960: have "normal s3 \ schirmer@13688: G\invmode statM e\invocation_class mode (store s2) a statT\statT" wenzelm@32960: by auto wenzelm@32960: with eval_ps wt_e statM conf_s2 conf_a [rule_format] wenzelm@32960: have "check_method_access G accC statT (invmode statM e) schirmer@13688: \name=mn,parTs=pTs'\ a s3 = s3" wenzelm@32960: by (rule error_free_call_access) (auto simp add: s3 mode wf) wenzelm@32960: thus ?thesis wenzelm@32960: by (simp add: s3' mode) wenzelm@32960: qed wenzelm@32960: with eval_mthd D s3 wenzelm@32960: have "G\s3' \Methd D \name=mn,parTs=pTs'\-\v\ s4" wenzelm@32960: by simp wenzelm@32960: with eval_e eval_ps D _ s3' wenzelm@32960: show ?thesis wenzelm@32960: by (rule eval_Call) (auto simp add: s3 mode D) wenzelm@32960: qed schirmer@13688: qed schirmer@13688: qed schirmer@13688: qed schirmer@13688: qed wenzelm@32960: schirmer@13688: lemma eval_expression_no_jump': schirmer@13688: assumes eval: "G\s0 \e-\v\ s1" schirmer@13688: and no_jmp: "abrupt s0 \ Some (Jump j)" schirmer@13688: and wt: "\prg=G, cls=C,lcl=L\\e\-T" schirmer@13688: and wf: "wf_prog G" schirmer@13688: shows "abrupt s1 \ Some (Jump j)" schirmer@13688: using eval no_jmp wt wf schirmer@13688: by - (rule eval_expression_no_jump schirmer@13688: [where ?Env="\prg=G, cls=C,lcl=L\",simplified],auto) schirmer@12854: schirmer@13688: schirmer@13688: text {* To derive the most general formula for the loop statement, we need to schirmer@13688: come up with a proper loop invariant, which intuitively states that we are schirmer@13688: currently inside the evaluation of the loop. To define such an invariant, we schirmer@13688: unroll the loop in iterated evaluations of the expression and evaluations of schirmer@13688: the loop body. *} schirmer@13688: wenzelm@37956: definition wenzelm@37956: unroll :: "prog \ label \ expr \ stmt \ (state \ state) set" where wenzelm@37956: "unroll G l e c = {(s,t). \ v s1 s2. schirmer@13688: G\s \e-\v\ s1 \ the_Bool v \ normal s1 \ schirmer@13688: G\s1 \c\ s2 \ t=(abupd (absorb (Cont l)) s2)}" schirmer@13688: schirmer@13688: schirmer@13688: lemma unroll_while: schirmer@13688: assumes unroll: "(s, t) \ (unroll G l e c)\<^sup>*" schirmer@13688: and eval_e: "G\t \e-\v\ s'" schirmer@13688: and normal_termination: "normal s' \ \ the_Bool v" schirmer@13688: and wt: "\prg=G,cls=C,lcl=L\\e\-T" schirmer@13688: and wf: "wf_prog G" schirmer@13688: shows "G\s \l\ While(e) c\ s'" schirmer@13688: using unroll (* normal_s *) schirmer@13688: proof (induct rule: converse_rtrancl_induct) schirmer@13688: show "G\t \l\ While(e) c\ s'" schirmer@13688: proof (cases "normal t") schirmer@13688: case False schirmer@13688: with eval_e have "s'=t" by auto schirmer@13688: with False show ?thesis by auto schirmer@13688: next schirmer@13688: case True schirmer@13688: note normal_t = this schirmer@13688: show ?thesis schirmer@13688: proof (cases "normal s'") schirmer@13688: case True schirmer@13688: with normal_t eval_e normal_termination schirmer@13688: show ?thesis wenzelm@32960: by (auto intro: eval.Loop) schirmer@13688: next schirmer@13688: case False schirmer@13688: note abrupt_s' = this schirmer@13688: from eval_e _ wt wf schirmer@13688: have no_cont: "abrupt s' \ Some (Jump (Cont l))" wenzelm@32960: by (rule eval_expression_no_jump') (insert normal_t,simp) schirmer@13688: have wenzelm@32960: "if the_Bool v schirmer@13688: then (G\s' \c\ s' \ schirmer@13688: G\(abupd (absorb (Cont l)) s') \l\ While(e) c\ s') wenzelm@32960: else s' = s'" schirmer@13688: proof (cases "the_Bool v") wenzelm@32960: case False thus ?thesis by simp schirmer@13688: next wenzelm@32960: case True wenzelm@32960: with abrupt_s' have "G\s' \c\ s'" by auto wenzelm@32960: moreover from abrupt_s' no_cont wenzelm@32960: have no_absorb: "(abupd (absorb (Cont l)) s')=s'" wenzelm@32960: by (cases s') (simp add: absorb_def split: split_if) wenzelm@32960: moreover wenzelm@32960: from no_absorb abrupt_s' wenzelm@32960: have "G\(abupd (absorb (Cont l)) s') \l\ While(e) c\ s'" wenzelm@32960: by auto wenzelm@32960: ultimately show ?thesis wenzelm@32960: using True by simp schirmer@13688: qed schirmer@13688: with eval_e schirmer@13688: show ?thesis wenzelm@32960: using normal_t by (auto intro: eval.Loop) schirmer@13688: qed schirmer@13688: qed schirmer@13688: next schirmer@13688: fix s s3 schirmer@13688: assume unroll: "(s,s3) \ unroll G l e c" schirmer@13688: assume while: "G\s3 \l\ While(e) c\ s'" schirmer@13688: show "G\s \l\ While(e) c\ s'" schirmer@13688: proof - schirmer@13688: from unroll obtain v s1 s2 where schirmer@13688: normal_s1: "normal s1" and schirmer@13688: eval_e: "G\s \e-\v\ s1" and schirmer@13688: continue: "the_Bool v" and schirmer@13688: eval_c: "G\s1 \c\ s2" and schirmer@13688: s3: "s3=(abupd (absorb (Cont l)) s2)" schirmer@13688: by (unfold unroll_def) fast schirmer@13688: from eval_e normal_s1 have schirmer@13688: "normal s" schirmer@13688: by (rule eval_no_abrupt_lemma [rule_format]) schirmer@13688: with while eval_e continue eval_c s3 show ?thesis schirmer@13688: by (auto intro!: eval.Loop) schirmer@13688: qed schirmer@13688: qed schirmer@12854: schirmer@13688: lemma MGFn_Loop: schirmer@13688: assumes mfg_e: "G,(A::state triple set)\{=:n} \e\\<^sub>e\ {G\}" schirmer@13688: and mfg_c: "G,A\{=:n} \c\\<^sub>s\ {G\}" schirmer@13688: and wf: "wf_prog G" schirmer@13688: shows "G,A\{=:n} \l\ While(e) c\\<^sub>s\ {G\}" schirmer@13688: proof (rule MGFn_free_wt [rule_format],elim exE) schirmer@13688: fix T L C schirmer@13688: assume wt: "\prg = G, cls = C, lcl = L\\\l\ While(e) c\\<^sub>s\T" schirmer@13688: then obtain eT where schirmer@13688: wt_e: "\prg = G, cls = C, lcl = L\\e\-eT" schirmer@13688: by cases simp schirmer@13688: show ?thesis schirmer@13688: proof (rule MGFn_NormalI) schirmer@13688: show "G,A\{Normal ((\Y' s' s. s' = s \ normal s) \. G\init\n)} schirmer@13688: .l\ While(e) c. schirmer@13688: {\Y s' s. G\s \In1r (l\ While(e) c)\\ (Y, s')}" schirmer@13688: proof (rule conseq12 schirmer@13688: [where ?P'="(\ Y s' s. (s,s') \ (unroll G l e c)\<^sup>* ) \. G\init\n" schirmer@13688: and ?Q'="((\ Y s' s. (\ t b. (s,t) \ (unroll G l e c)\<^sup>* \ schirmer@13688: Y=\b\\<^sub>e \ G\t \e-\b\ s')) schirmer@13688: \. G\init\n)\=False\=\"]) schirmer@13688: show "G,A\{(\Y s' s. (s, s') \ (unroll G l e c)\<^sup>*) \. G\init\n} schirmer@13688: .l\ While(e) c. schirmer@13688: {((\Y s' s. (\t b. (s, t) \ (unroll G l e c)\<^sup>* \ schirmer@13688: Y = In1 b \ G\t \e-\b\ s')) schirmer@13688: \. G\init\n)\=False\=\}" schirmer@13688: proof (rule ax_derivs.Loop) wenzelm@32960: from mfg_e wenzelm@32960: show "G,A\{(\Y s' s. (s, s') \ (unroll G l e c)\<^sup>*) \. G\init\n} schirmer@13688: e-\ schirmer@13688: {(\Y s' s. (\t b. (s, t) \ (unroll G l e c)\<^sup>* \ schirmer@13688: Y = In1 b \ G\t \e-\b\ s')) schirmer@13688: \. G\init\n}" wenzelm@32960: proof (rule MGFnD' [THEN conseq12],clarsimp) wenzelm@32960: fix s Z s' v wenzelm@32960: assume "(Z, s) \ (unroll G l e c)\<^sup>*" wenzelm@32960: moreover wenzelm@32960: assume "G\s \e-\v\ s'" wenzelm@32960: ultimately wenzelm@32960: show "\t. (Z, t) \ (unroll G l e c)\<^sup>* \ G\t \e-\v\ s'" wenzelm@32960: by blast wenzelm@32960: qed schirmer@13688: next wenzelm@32960: from mfg_c wenzelm@32960: show "G,A\{Normal (((\Y s' s. \t b. (s, t) \ (unroll G l e c)\<^sup>* \ schirmer@13688: Y = \b\\<^sub>e \ G\t \e-\b\ s') schirmer@13688: \. G\init\n)\=True)} schirmer@13688: .c. schirmer@13688: {abupd (absorb (Cont l)) .; schirmer@13688: ((\Y s' s. (s, s') \ (unroll G l e c)\<^sup>*) \. G\init\n)}" wenzelm@32960: proof (rule MGFnD' [THEN conseq12],clarsimp) wenzelm@32960: fix Z s' s v t wenzelm@32960: assume unroll: "(Z, t) \ (unroll G l e c)\<^sup>*" wenzelm@32960: assume eval_e: "G\t \e-\v\ Norm s" wenzelm@32960: assume true: "the_Bool v" wenzelm@32960: assume eval_c: "G\Norm s \c\ s'" wenzelm@32960: show "(Z, abupd (absorb (Cont l)) s') \ (unroll G l e c)\<^sup>*" wenzelm@32960: proof - wenzelm@32960: note unroll wenzelm@32960: also wenzelm@32960: from eval_e true eval_c wenzelm@32960: have "(t,abupd (absorb (Cont l)) s') \ unroll G l e c" wenzelm@32960: by (unfold unroll_def) force wenzelm@32960: ultimately show ?thesis .. wenzelm@32960: qed wenzelm@32960: qed schirmer@13688: qed schirmer@13688: next schirmer@13688: show wenzelm@32960: "\Y s Z. schirmer@13688: (Normal ((\Y' s' s. s' = s \ normal s) \. G\init\n)) Y s Z schirmer@13688: \ (\Y' s'. schirmer@13688: (\Y Z'. schirmer@13688: ((\Y s' s. (s, s') \ (unroll G l e c)\<^sup>*) \. G\init\n) Y s Z' schirmer@13688: \ (((\Y s' s. \t b. (s,t) \ (unroll G l e c)\<^sup>* schirmer@13688: \ Y=\b\\<^sub>e \ G\t \e-\b\ s') schirmer@13688: \. G\init\n)\=False\=\) Y' s' Z') schirmer@13688: \ G\Z \\l\ While(e) c\\<^sub>s\\ (Y', s'))" schirmer@13688: proof (clarsimp) wenzelm@32960: fix Y' s' s wenzelm@32960: assume asm: wenzelm@32960: "\Z'. (Z', Norm s) \ (unroll G l e c)\<^sup>* schirmer@13688: \ card (nyinitcls G s') \ n \ schirmer@13688: (\v. (\t. (Z', t) \ (unroll G l e c)\<^sup>* \ G\t \e-\v\ s') \ schirmer@13688: (fst s' = None \ \ the_Bool v)) \ Y' = \" wenzelm@32960: show "Y' = \ \ G\Norm s \l\ While(e) c\ s'" wenzelm@32960: proof - wenzelm@32960: from asm obtain v t where wenzelm@32960: -- {* @{term "Z'"} gets instantiated with @{term "Norm s"} *} wenzelm@32960: unroll: "(Norm s, t) \ (unroll G l e c)\<^sup>*" and schirmer@13688: eval_e: "G\t \e-\v\ s'" and schirmer@13688: normal_termination: "normal s' \ \ the_Bool v" and wenzelm@32960: Y': "Y' = \" wenzelm@32960: by auto wenzelm@32960: from unroll eval_e normal_termination wt_e wf wenzelm@32960: have "G\Norm s \l\ While(e) c\ s'" wenzelm@32960: by (rule unroll_while) wenzelm@32960: with Y' wenzelm@32960: show ?thesis wenzelm@32960: by simp wenzelm@32960: qed schirmer@13688: qed schirmer@13688: qed schirmer@13688: qed schirmer@13688: qed schirmer@12854: schirmer@12925: lemma MGFn_FVar: schirmer@13688: fixes A :: "state triple set" schirmer@13688: assumes mgf_init: "G,A\{=:n} \Init statDeclC\\<^sub>s\ {G\}" schirmer@13688: and mgf_e: "G,A\{=:n} \e\\<^sub>e\ {G\}" schirmer@13688: and wf: "wf_prog G" schirmer@13688: shows "G,A\{=:n} \{accC,statDeclC,stat}e..fn\\<^sub>v\ {G\}" schirmer@13688: proof (rule MGFn_free_wt_da_NormalConformI [rule_format],clarsimp) schirmer@13688: note inj_term_simps [simp] schirmer@13688: fix T L accC' V schirmer@13688: assume wt: "\prg = G, cls = accC', lcl = L\\\{accC,statDeclC,stat}e..fn\\<^sub>v\T" schirmer@13688: then obtain statC f where schirmer@13688: wt_e: "\prg=G, cls=accC', lcl=L\\e\-Class statC" and schirmer@13688: accfield: "accfield G accC' statC fn = Some (statDeclC,f )" and schirmer@13688: eq_accC: "accC=accC'" and schirmer@13688: stat: "stat=is_static f" schirmer@13688: by (cases) (auto simp add: member_is_static_simp) schirmer@13688: let ?Q="(\Y s1 (x,s) . x = None \ schirmer@13688: (G\Norm s \Init statDeclC\ s1) \ schirmer@13688: (\ E. \prg=G,cls=accC',lcl=L\\dom (locals (store s1)) \\e\\<^sub>e\ E)) schirmer@13688: \. G\init\n \. (\ s. s\\(G, L))" schirmer@13688: show "G,A\{Normal schirmer@13688: ((\Y' s' s. s' = s \ abrupt s = None) \. G\init\n \. schirmer@13688: (\s. s\\(G, L)) \. schirmer@13688: (\s. \prg=G,cls=accC',lcl=L\ schirmer@13688: \ dom (locals (store s)) \ \{accC,statDeclC,stat}e..fn\\<^sub>v\ V)) schirmer@13688: } {accC,statDeclC,stat}e..fn=\ schirmer@13688: {\Y s' s. \vf. Y = \vf\\<^sub>v \ schirmer@13688: G\s \{accC,statDeclC,stat}e..fn=\vf\ s'}" schirmer@13688: (is "G,A\{Normal ?P} {accC,statDeclC,stat}e..fn=\ {?R}") schirmer@13688: proof (rule ax_derivs.FVar [where ?Q="?Q" ]) schirmer@13688: from mgf_init schirmer@13688: show "G,A\{Normal ?P} .Init statDeclC. {?Q}" schirmer@13688: proof (rule MGFnD' [THEN conseq12],clarsimp) schirmer@13688: fix s s' schirmer@13688: assume conf_s: "Norm s\\(G, L)" schirmer@13688: assume da: "\prg=G,cls=accC',lcl=L\ schirmer@13688: \ dom (locals s) \\{accC,statDeclC,stat}e..fn\\<^sub>v\ V" schirmer@13688: assume eval_init: "G\Norm s \Init statDeclC\ s'" schirmer@13688: show "(\E. \prg=G, cls=accC', lcl=L\\ dom (locals (store s')) \\e\\<^sub>e\ E) \ schirmer@13688: s'\\(G, L)" schirmer@13688: proof - wenzelm@32960: from da wenzelm@32960: obtain E where wenzelm@32960: "\prg=G, cls=accC', lcl=L\\ dom (locals s) \\e\\<^sub>e\ E" wenzelm@32960: by cases simp wenzelm@32960: moreover wenzelm@32960: from eval_init wenzelm@32960: have "dom (locals s) \ dom (locals (store s'))" wenzelm@32960: by (rule dom_locals_eval_mono [elim_format]) simp wenzelm@32960: ultimately obtain E' where wenzelm@32960: "\prg=G, cls=accC', lcl=L\\ dom (locals (store s')) \\e\\<^sub>e\ E'" wenzelm@32960: by (rule da_weakenE) wenzelm@32960: moreover wenzelm@32960: have "s'\\(G, L)" wenzelm@32960: proof - wenzelm@32960: have wt_init: "\prg=G, cls=accC, lcl=L\\(Init statDeclC)\\" wenzelm@32960: proof - wenzelm@32960: from wf wt_e wenzelm@32960: have iscls_statC: "is_class G statC" wenzelm@32960: by (auto dest: ty_expr_is_type type_is_class) wenzelm@32960: with wf accfield wenzelm@32960: have iscls_statDeclC: "is_class G statDeclC" wenzelm@32960: by (auto dest!: accfield_fields dest: fields_declC) wenzelm@32960: thus ?thesis by simp wenzelm@32960: qed wenzelm@32960: obtain I where wenzelm@32960: da_init: "\prg=G,cls=accC,lcl=L\ schirmer@13688: \ dom (locals (store ((Norm s)::state))) \\Init statDeclC\\<^sub>s\ I" wenzelm@32960: by (auto intro: da_Init [simplified] assigned.select_convs) wenzelm@32960: from eval_init conf_s wt_init da_init wf wenzelm@32960: show ?thesis wenzelm@32960: by (rule eval_type_soundE) wenzelm@32960: qed wenzelm@32960: ultimately show ?thesis by iprover schirmer@13688: qed schirmer@13688: qed schirmer@13688: next schirmer@13688: from mgf_e schirmer@13688: show "G,A\{?Q} e-\ {\Val:a:. fvar statDeclC stat fn a ..; ?R}" schirmer@13688: proof (rule MGFnD' [THEN conseq12],clarsimp) schirmer@13688: fix s0 s1 s2 E a schirmer@13688: let ?fvar = "fvar statDeclC stat fn a s2" schirmer@13688: assume eval_init: "G\Norm s0 \Init statDeclC\ s1" schirmer@13688: assume eval_e: "G\s1 \e-\a\ s2" schirmer@13688: assume conf_s1: "s1\\(G, L)" schirmer@13688: assume da_e: "\prg=G,cls=accC',lcl=L\\ dom (locals (store s1)) \\e\\<^sub>e\ E" schirmer@13688: show "G\Norm s0 \{accC,statDeclC,stat}e..fn=\fst ?fvar\ snd ?fvar" schirmer@13688: proof - wenzelm@32960: obtain v s2' where wenzelm@32960: v: "v=fst ?fvar" and s2': "s2'=snd ?fvar" wenzelm@32960: by simp wenzelm@32960: obtain s3 where wenzelm@32960: s3: "s3= check_field_access G accC' statDeclC fn stat a s2'" wenzelm@32960: by simp wenzelm@32960: have eq_s3_s2': "s3=s2'" wenzelm@32960: proof - wenzelm@32960: from eval_e conf_s1 wt_e da_e wf obtain wenzelm@32960: conf_s2: "s2\\(G, L)" and wenzelm@32960: conf_a: "normal s2 \ G,store s2\a\\Class statC" wenzelm@32960: by (rule eval_type_soundE) simp wenzelm@32960: from accfield wt_e eval_init eval_e conf_s2 conf_a _ wf wenzelm@32960: show ?thesis wenzelm@32960: by (rule error_free_field_access schirmer@13688: [where ?v=v and ?s2'=s2',elim_format]) wenzelm@32960: (simp add: s3 v s2' stat)+ schirmer@13688: qed wenzelm@32960: from eval_init eval_e wenzelm@32960: show ?thesis wenzelm@32960: apply (rule eval.FVar [where ?s2'=s2']) wenzelm@32960: apply (simp add: s2') wenzelm@32960: apply (simp add: s3 [symmetric] eq_s3_s2' eq_accC s2' [symmetric]) wenzelm@32960: done schirmer@13688: qed schirmer@13688: qed schirmer@13688: qed schirmer@13688: qed schirmer@12925: schirmer@13337: schirmer@13688: lemma MGFn_Fin: schirmer@13688: assumes wf: "wf_prog G" schirmer@13688: and mgf_c1: "G,A\{=:n} \c1\\<^sub>s\ {G\}" schirmer@13688: and mgf_c2: "G,A\{=:n} \c2\\<^sub>s\ {G\}" wenzelm@61076: shows "G,(A::state triple set)\{=:n} \c1 Finally c2\\<^sub>s\ {G\}" schirmer@13688: proof (rule MGFn_free_wt_da_NormalConformI [rule_format],clarsimp) schirmer@13688: fix T L accC C schirmer@13688: assume wt: "\prg=G,cls=accC,lcl=L\\In1r (c1 Finally c2)\T" schirmer@13688: then obtain schirmer@13688: wt_c1: "\prg=G,cls=accC,lcl=L\\c1\\" and schirmer@13688: wt_c2: "\prg=G,cls=accC,lcl=L\\c2\\" schirmer@13688: by cases simp schirmer@13688: let ?Q = "(\Y' s' s. normal s \ G\s \c1\ s' \ schirmer@13688: (\ C1. \prg=G,cls=accC,lcl=L\\dom (locals (store s)) \\c1\\<^sub>s\ C1) schirmer@13688: \ s\\(G, L)) schirmer@13688: \. G\init\n" schirmer@13688: show "G,A\{Normal schirmer@13688: ((\Y' s' s. s' = s \ abrupt s = None) \. G\init\n \. schirmer@13688: (\s. s\\(G, L)) \. schirmer@13688: (\s. \prg=G,cls=accC,lcl =L\ schirmer@13688: \dom (locals (store s)) \\c1 Finally c2\\<^sub>s\ C))} schirmer@13688: .c1 Finally c2. schirmer@13688: {\Y s' s. Y = \ \ G\s \c1 Finally c2\ s'}" schirmer@13688: (is "G,A\{Normal ?P} .c1 Finally c2. {?R}") schirmer@13688: proof (rule ax_derivs.Fin [where ?Q="?Q"]) schirmer@13688: from mgf_c1 schirmer@13688: show "G,A\{Normal ?P} .c1. {?Q}" schirmer@13688: proof (rule MGFnD' [THEN conseq12],clarsimp) schirmer@13688: fix s0 schirmer@13688: assume "\prg=G,cls=accC,lcl=L\\ dom (locals s0) \\c1 Finally c2\\<^sub>s\ C" schirmer@13688: thus "\C1. \prg=G,cls=accC,lcl=L\\ dom (locals s0) \\c1\\<^sub>s\ C1" wenzelm@32960: by cases (auto simp add: inj_term_simps) schirmer@13688: qed schirmer@13688: next schirmer@13688: from mgf_c2 schirmer@13688: show "\abr. G,A\{?Q \. (\s. abr = abrupt s) ;. abupd (\abr. None)} .c2. schirmer@13688: {abupd (abrupt_if (abr \ None) abr) .; ?R}" schirmer@13688: proof (rule MGFnD' [THEN conseq12, THEN allI],clarsimp) schirmer@13688: fix s0 s1 s2 C1 schirmer@13688: assume da_c1:"\prg=G,cls=accC,lcl=L\\ dom (locals s0) \\c1\\<^sub>s\ C1" schirmer@13688: assume conf_s0: "Norm s0\\(G, L)" schirmer@13688: assume eval_c1: "G\Norm s0 \c1\ s1" schirmer@13688: assume eval_c2: "G\abupd (\abr. None) s1 \c2\ s2" schirmer@13688: show "G\Norm s0 \c1 Finally c2 schirmer@13688: \ abupd (abrupt_if (\y. abrupt s1 = Some y) (abrupt s1)) s2" schirmer@13688: proof - wenzelm@32960: obtain abr1 str1 where s1: "s1=(abr1,str1)" wenzelm@32960: by (cases s1) wenzelm@32960: with eval_c1 eval_c2 obtain wenzelm@32960: eval_c1': "G\Norm s0 \c1\ (abr1,str1)" and wenzelm@32960: eval_c2': "G\Norm str1 \c2\ s2" wenzelm@32960: by simp wenzelm@32960: obtain s3 where wenzelm@32960: s3: "s3 = (if \err. abr1 = Some (Error err) wenzelm@32960: then (abr1, str1) schirmer@13688: else abupd (abrupt_if (abr1 \ None) abr1) s2)" wenzelm@32960: by simp wenzelm@32960: from eval_c1' conf_s0 wt_c1 _ wf wenzelm@32960: have "error_free (abr1,str1)" wenzelm@32960: by (rule eval_type_soundE) (insert da_c1,auto) wenzelm@32960: with s3 have eq_s3: "s3=abupd (abrupt_if (abr1 \ None) abr1) s2" wenzelm@32960: by (simp add: error_free_def) wenzelm@32960: from eval_c1' eval_c2' s3 wenzelm@32960: show ?thesis wenzelm@32960: by (rule eval.Fin [elim_format]) (simp add: s1 eq_s3) schirmer@13688: qed schirmer@13688: qed schirmer@13688: qed schirmer@13688: qed schirmer@13688: schirmer@13688: lemma Body_no_break: schirmer@13688: assumes eval_init: "G\Norm s0 \Init D\ s1" schirmer@13688: and eval_c: "G\s1 \c\ s2" schirmer@13688: and jmpOk: "jumpNestingOkS {Ret} c" schirmer@13688: and wt_c: "\prg=G, cls=C, lcl=L\\c\\" schirmer@13688: and clsD: "class G D=Some d" schirmer@13688: and wf: "wf_prog G" schirmer@13688: shows "\ l. abrupt s2 \ Some (Jump (Break l)) \ schirmer@13688: abrupt s2 \ Some (Jump (Cont l))" schirmer@13688: proof schirmer@13688: fix l show "abrupt s2 \ Some (Jump (Break l)) \ schirmer@13688: abrupt s2 \ Some (Jump (Cont l))" schirmer@13688: proof - wenzelm@26932: fix accC from clsD have wt_init: "\prg=G, cls=accC, lcl=L\\(Init D)\\" schirmer@13688: by auto schirmer@13688: from eval_init wf schirmer@13688: have s1_no_jmp: "\ j. abrupt s1 \ Some (Jump j)" schirmer@13688: by - (rule eval_statement_no_jump [OF _ _ _ wt_init],auto) schirmer@13688: from eval_c _ wt_c wf schirmer@13688: show ?thesis schirmer@13688: apply (rule jumpNestingOk_eval [THEN conjE, elim_format]) schirmer@13688: using jmpOk s1_no_jmp schirmer@13688: apply auto schirmer@13688: done schirmer@13688: qed schirmer@13688: qed schirmer@12854: schirmer@13688: lemma MGFn_Body: schirmer@13688: assumes wf: "wf_prog G" schirmer@13688: and mgf_init: "G,A\{=:n} \Init D\\<^sub>s\ {G\}" schirmer@13688: and mgf_c: "G,A\{=:n} \c\\<^sub>s\ {G\}" wenzelm@61076: shows "G,(A::state triple set)\{=:n} \Body D c\\<^sub>e\ {G\}" schirmer@13688: proof (rule MGFn_free_wt_da_NormalConformI [rule_format],clarsimp) schirmer@13688: fix T L accC E schirmer@13688: assume wt: "\prg=G, cls=accC,lcl=L\\\Body D c\\<^sub>e\T" schirmer@13688: let ?Q="(\Y' s' s. normal s \ G\s \Init D\ s' \ jumpNestingOkS {Ret} c) schirmer@13688: \. G\init\n" schirmer@13688: show "G,A\{Normal schirmer@13688: ((\Y' s' s. s' = s \ fst s = None) \. G\init\n \. schirmer@13688: (\s. s\\(G, L)) \. schirmer@13688: (\s. \prg=G,cls=accC,lcl=L\ schirmer@13688: \ dom (locals (store s)) \\Body D c\\<^sub>e\ E))} schirmer@13688: Body D c-\ schirmer@13688: {\Y s' s. \v. Y = In1 v \ G\s \Body D c-\v\ s'}" schirmer@13688: (is "G,A\{Normal ?P} Body D c-\ {?R}") schirmer@13688: proof (rule ax_derivs.Body [where ?Q="?Q"]) schirmer@13688: from mgf_init schirmer@13688: show "G,A\{Normal ?P} .Init D. {?Q}" schirmer@13688: proof (rule MGFnD' [THEN conseq12],clarsimp) schirmer@13688: fix s0 schirmer@13688: assume da: "\prg=G,cls=accC,lcl=L\\ dom (locals s0) \\Body D c\\<^sub>e\ E" schirmer@13688: thus "jumpNestingOkS {Ret} c" wenzelm@32960: by cases simp schirmer@13688: qed schirmer@13688: next schirmer@13688: from mgf_c schirmer@13688: show "G,A\{?Q}.c.{\s.. abupd (absorb Ret) .; ?R\\the (locals s Result)\\<^sub>e}" schirmer@13688: proof (rule MGFnD' [THEN conseq12],clarsimp) schirmer@13688: fix s0 s1 s2 schirmer@13688: assume eval_init: "G\Norm s0 \Init D\ s1" schirmer@13688: assume eval_c: "G\s1 \c\ s2" schirmer@13688: assume nestingOk: "jumpNestingOkS {Ret} c" schirmer@13688: show "G\Norm s0 \Body D c-\the (locals (store s2) Result) schirmer@13688: \ abupd (absorb Ret) s2" schirmer@13688: proof - wenzelm@32960: from wt obtain d where schirmer@13688: d: "class G D=Some d" and schirmer@13688: wt_c: "\prg = G, cls = accC, lcl = L\\c\\" wenzelm@32960: by cases auto wenzelm@32960: obtain s3 where wenzelm@32960: s3: "s3= (if \l. fst s2 = Some (Jump (Break l)) \ schirmer@13688: fst s2 = Some (Jump (Cont l)) schirmer@13688: then abupd (\x. Some (Error CrossMethodJump)) s2 schirmer@13688: else s2)" wenzelm@32960: by simp wenzelm@32960: from eval_init eval_c nestingOk wt_c d wf wenzelm@32960: have eq_s3_s2: "s3=s2" wenzelm@32960: by (rule Body_no_break [elim_format]) (simp add: s3) wenzelm@32960: from eval_init eval_c s3 wenzelm@32960: show ?thesis wenzelm@32960: by (rule eval.Body [elim_format]) (simp add: eq_s3_s2) schirmer@13688: qed schirmer@13688: qed schirmer@13688: qed schirmer@13688: qed schirmer@13337: schirmer@13688: lemma MGFn_lemma: schirmer@13688: assumes mgf_methds: schirmer@13688: "\ n. \ C sig. G,(A::state triple set)\{=:n} \Methd C sig\\<^sub>e\ {G\}" schirmer@13688: and wf: "wf_prog G" schirmer@13688: shows "\ t. G,A\{=:n} t\ {G\}" schirmer@13688: proof (induct rule: full_nat_induct) schirmer@13688: fix n t schirmer@13688: assume hyp: "\ m. Suc m \ n \ (\ t. G,A\{=:m} t\ {G\})" schirmer@13688: show "G,A\{=:n} t\ {G\}" schirmer@13688: proof - schirmer@13688: { schirmer@13688: fix v e c es schirmer@13688: have "G,A\{=:n} \v\\<^sub>v\ {G\}" and schirmer@13688: "G,A\{=:n} \e\\<^sub>e\ {G\}" and schirmer@13688: "G,A\{=:n} \c\\<^sub>s\ {G\}" and schirmer@13688: "G,A\{=:n} \es\\<^sub>l\ {G\}" blanchet@58251: proof (induct rule: compat_var.induct compat_expr.induct compat_stmt.induct compat_expr_list.induct) schirmer@13688: case (LVar v) schirmer@13688: show "G,A\{=:n} \LVar v\\<^sub>v\ {G\}" wenzelm@32960: apply (rule MGFn_NormalI) wenzelm@32960: apply (rule ax_derivs.LVar [THEN conseq1]) wenzelm@32960: apply (clarsimp) wenzelm@32960: apply (rule eval.LVar) wenzelm@32960: done schirmer@13688: next schirmer@13688: case (FVar accC statDeclC stat e fn) wenzelm@23366: from MGFn_Init [OF hyp] and `G,A\{=:n} \e\\<^sub>e\ {G\}` and wf schirmer@13688: show ?case wenzelm@32960: by (rule MGFn_FVar) schirmer@13688: next schirmer@13688: case (AVar e1 e2) wenzelm@23366: note mgf_e1 = `G,A\{=:n} \e1\\<^sub>e\ {G\}` wenzelm@23366: note mgf_e2 = `G,A\{=:n} \e2\\<^sub>e\ {G\}` schirmer@13688: show "G,A\{=:n} \e1.[e2]\\<^sub>v\ {G\}" wenzelm@32960: apply (rule MGFn_NormalI) wenzelm@32960: apply (rule ax_derivs.AVar) wenzelm@32960: apply (rule MGFnD [OF mgf_e1, THEN ax_NormalD]) wenzelm@32960: apply (rule allI) wenzelm@32960: apply (rule MGFnD' [OF mgf_e2, THEN conseq12]) nipkow@44890: apply (fastforce intro: eval.AVar) wenzelm@32960: done schirmer@13688: next schirmer@13688: case (InsInitV c v) schirmer@13688: show ?case wenzelm@32960: by (rule MGFn_NormalI) (rule ax_derivs.InsInitV) schirmer@13688: next schirmer@13688: case (NewC C) schirmer@13688: show ?case wenzelm@32960: apply (rule MGFn_NormalI) wenzelm@32960: apply (rule ax_derivs.NewC) wenzelm@32960: apply (rule MGFn_InitD [OF hyp, THEN conseq2]) nipkow@44890: apply (fastforce intro: eval.NewC) wenzelm@32960: done schirmer@13688: next schirmer@13688: case (NewA T e) schirmer@13688: thus ?case wenzelm@32960: apply - wenzelm@32960: apply (rule MGFn_NormalI) wenzelm@32960: apply (rule ax_derivs.NewA schirmer@13688: [where ?Q = "(\Y' s' s. normal s \ G\s \In1r (init_comp_ty T) schirmer@13688: \\ (Y',s')) \. G\init\n"]) wenzelm@32960: apply (simp add: init_comp_ty_def split add: split_if) wenzelm@32960: apply (rule conjI, clarsimp) wenzelm@32960: apply (rule MGFn_InitD [OF hyp, THEN conseq2]) wenzelm@32960: apply (clarsimp intro: eval.Init) wenzelm@32960: apply clarsimp wenzelm@32960: apply (rule ax_derivs.Skip [THEN conseq1]) wenzelm@32960: apply (clarsimp intro: eval.Skip) wenzelm@32960: apply (erule MGFnD' [THEN conseq12]) nipkow@44890: apply (fastforce intro: eval.NewA) wenzelm@32960: done schirmer@13688: next schirmer@13688: case (Cast C e) schirmer@13688: thus ?case wenzelm@32960: apply - wenzelm@32960: apply (rule MGFn_NormalI) wenzelm@32960: apply (erule MGFnD'[THEN conseq12,THEN ax_derivs.Cast]) nipkow@44890: apply (fastforce intro: eval.Cast) wenzelm@32960: done schirmer@13688: next schirmer@13688: case (Inst e C) schirmer@13688: thus ?case wenzelm@32960: apply - wenzelm@32960: apply (rule MGFn_NormalI) wenzelm@32960: apply (erule MGFnD'[THEN conseq12,THEN ax_derivs.Inst]) nipkow@44890: apply (fastforce intro: eval.Inst) wenzelm@32960: done schirmer@13688: next schirmer@13688: case (Lit v) schirmer@13688: show ?case wenzelm@32960: apply - wenzelm@32960: apply (rule MGFn_NormalI) wenzelm@32960: apply (rule ax_derivs.Lit [THEN conseq1]) nipkow@44890: apply (fastforce intro: eval.Lit) wenzelm@32960: done schirmer@13688: next schirmer@13688: case (UnOp unop e) schirmer@13688: thus ?case wenzelm@32960: apply - wenzelm@32960: apply (rule MGFn_NormalI) wenzelm@32960: apply (rule ax_derivs.UnOp) wenzelm@32960: apply (erule MGFnD' [THEN conseq12]) nipkow@44890: apply (fastforce intro: eval.UnOp) wenzelm@32960: done schirmer@13688: next schirmer@13688: case (BinOp binop e1 e2) schirmer@13688: thus ?case wenzelm@32960: apply - wenzelm@32960: apply (rule MGFn_NormalI) wenzelm@32960: apply (rule ax_derivs.BinOp) wenzelm@32960: apply (erule MGFnD [THEN ax_NormalD]) wenzelm@32960: apply (rule allI) wenzelm@32960: apply (case_tac "need_second_arg binop v1") wenzelm@32960: apply simp wenzelm@32960: apply (erule MGFnD' [THEN conseq12]) nipkow@44890: apply (fastforce intro: eval.BinOp) wenzelm@32960: apply simp wenzelm@32960: apply (rule ax_Normal_cases) wenzelm@32960: apply (rule ax_derivs.Skip [THEN conseq1]) wenzelm@32960: apply clarsimp wenzelm@32960: apply (rule eval_BinOp_arg2_indepI) wenzelm@32960: apply simp wenzelm@32960: apply simp wenzelm@32960: apply (rule ax_derivs.Abrupt [THEN conseq1], clarsimp simp add: Let_def) nipkow@44890: apply (fastforce intro: eval.BinOp) wenzelm@32960: done schirmer@13688: next schirmer@13688: case Super schirmer@13688: show ?case wenzelm@32960: apply - wenzelm@32960: apply (rule MGFn_NormalI) wenzelm@32960: apply (rule ax_derivs.Super [THEN conseq1]) nipkow@44890: apply (fastforce intro: eval.Super) wenzelm@32960: done schirmer@13688: next schirmer@13688: case (Acc v) schirmer@13688: thus ?case wenzelm@32960: apply - wenzelm@32960: apply (rule MGFn_NormalI) wenzelm@32960: apply (erule MGFnD'[THEN conseq12,THEN ax_derivs.Acc]) nipkow@44890: apply (fastforce intro: eval.Acc simp add: split_paired_all) wenzelm@32960: done schirmer@13688: next schirmer@13688: case (Ass v e) schirmer@13688: thus "G,A\{=:n} \v:=e\\<^sub>e\ {G\}" wenzelm@32960: apply - wenzelm@32960: apply (rule MGFn_NormalI) wenzelm@32960: apply (rule ax_derivs.Ass) wenzelm@32960: apply (erule MGFnD [THEN ax_NormalD]) wenzelm@32960: apply (rule allI) wenzelm@32960: apply (erule MGFnD'[THEN conseq12]) nipkow@44890: apply (fastforce intro: eval.Ass simp add: split_paired_all) wenzelm@32960: done schirmer@13688: next schirmer@13688: case (Cond e1 e2 e3) schirmer@13688: thus "G,A\{=:n} \e1 ? e2 : e3\\<^sub>e\ {G\}" wenzelm@32960: apply - wenzelm@32960: apply (rule MGFn_NormalI) wenzelm@32960: apply (rule ax_derivs.Cond) wenzelm@32960: apply (erule MGFnD [THEN ax_NormalD]) wenzelm@32960: apply (rule allI) wenzelm@32960: apply (rule ax_Normal_cases) wenzelm@32960: prefer 2 wenzelm@32960: apply (rule ax_derivs.Abrupt [THEN conseq1],clarsimp simp add: Let_def) nipkow@44890: apply (fastforce intro: eval.Cond) wenzelm@32960: apply (case_tac "b") wenzelm@32960: apply simp wenzelm@32960: apply (erule MGFnD'[THEN conseq12]) nipkow@44890: apply (fastforce intro: eval.Cond) wenzelm@32960: apply simp wenzelm@32960: apply (erule MGFnD'[THEN conseq12]) nipkow@44890: apply (fastforce intro: eval.Cond) wenzelm@32960: done schirmer@13688: next schirmer@13688: case (Call accC statT mode e mn pTs' ps) wenzelm@23366: note mgf_e = `G,A\{=:n} \e\\<^sub>e\ {G\}` wenzelm@23366: note mgf_ps = `G,A\{=:n} \ps\\<^sub>l\ {G\}` schirmer@13688: from mgf_methds mgf_e mgf_ps wf schirmer@13688: show "G,A\{=:n} \{accC,statT,mode}e\mn({pTs'}ps)\\<^sub>e\ {G\}" wenzelm@32960: by (rule MGFn_Call) schirmer@13688: next schirmer@13688: case (Methd D mn) schirmer@13688: from mgf_methds schirmer@13688: show "G,A\{=:n} \Methd D mn\\<^sub>e\ {G\}" wenzelm@32960: by simp schirmer@13688: next schirmer@13688: case (Body D c) wenzelm@23366: note mgf_c = `G,A\{=:n} \c\\<^sub>s\ {G\}` schirmer@13688: from wf MGFn_Init [OF hyp] mgf_c schirmer@13688: show "G,A\{=:n} \Body D c\\<^sub>e\ {G\}" wenzelm@32960: by (rule MGFn_Body) schirmer@13688: next schirmer@13688: case (InsInitE c e) schirmer@13688: show ?case wenzelm@32960: by (rule MGFn_NormalI) (rule ax_derivs.InsInitE) schirmer@13688: next schirmer@13688: case (Callee l e) schirmer@13688: show ?case wenzelm@32960: by (rule MGFn_NormalI) (rule ax_derivs.Callee) schirmer@13688: next schirmer@13688: case Skip schirmer@13688: show ?case wenzelm@32960: apply - wenzelm@32960: apply (rule MGFn_NormalI) wenzelm@32960: apply (rule ax_derivs.Skip [THEN conseq1]) nipkow@44890: apply (fastforce intro: eval.Skip) wenzelm@32960: done schirmer@13688: next schirmer@13688: case (Expr e) schirmer@13688: thus ?case wenzelm@32960: apply - wenzelm@32960: apply (rule MGFn_NormalI) wenzelm@32960: apply (erule MGFnD'[THEN conseq12,THEN ax_derivs.Expr]) nipkow@44890: apply (fastforce intro: eval.Expr) wenzelm@32960: done schirmer@13688: next schirmer@13688: case (Lab l c) schirmer@13688: thus "G,A\{=:n} \l\ c\\<^sub>s\ {G\}" wenzelm@32960: apply - wenzelm@32960: apply (rule MGFn_NormalI) wenzelm@32960: apply (erule MGFnD' [THEN conseq12, THEN ax_derivs.Lab]) nipkow@44890: apply (fastforce intro: eval.Lab) wenzelm@32960: done schirmer@13688: next schirmer@13688: case (Comp c1 c2) schirmer@13688: thus "G,A\{=:n} \c1;; c2\\<^sub>s\ {G\}" wenzelm@32960: apply - wenzelm@32960: apply (rule MGFn_NormalI) wenzelm@32960: apply (rule ax_derivs.Comp) wenzelm@32960: apply (erule MGFnD [THEN ax_NormalD]) wenzelm@32960: apply (erule MGFnD' [THEN conseq12]) nipkow@44890: apply (fastforce intro: eval.Comp) wenzelm@32960: done schirmer@13688: next wenzelm@24783: case (If' e c1 c2) schirmer@13688: thus "G,A\{=:n} \If(e) c1 Else c2\\<^sub>s\ {G\}" wenzelm@32960: apply - wenzelm@32960: apply (rule MGFn_NormalI) wenzelm@32960: apply (rule ax_derivs.If) wenzelm@32960: apply (erule MGFnD [THEN ax_NormalD]) wenzelm@32960: apply (rule allI) wenzelm@32960: apply (rule ax_Normal_cases) wenzelm@32960: prefer 2 wenzelm@32960: apply (rule ax_derivs.Abrupt [THEN conseq1],clarsimp simp add: Let_def) nipkow@44890: apply (fastforce intro: eval.If) wenzelm@32960: apply (case_tac "b") wenzelm@32960: apply simp wenzelm@32960: apply (erule MGFnD' [THEN conseq12]) nipkow@44890: apply (fastforce intro: eval.If) wenzelm@32960: apply simp wenzelm@32960: apply (erule MGFnD' [THEN conseq12]) nipkow@44890: apply (fastforce intro: eval.If) wenzelm@32960: done schirmer@13688: next schirmer@13688: case (Loop l e c) wenzelm@23366: note mgf_e = `G,A\{=:n} \e\\<^sub>e\ {G\}` wenzelm@23366: note mgf_c = `G,A\{=:n} \c\\<^sub>s\ {G\}` schirmer@13688: from mgf_e mgf_c wf schirmer@13688: show "G,A\{=:n} \l\ While(e) c\\<^sub>s\ {G\}" wenzelm@32960: by (rule MGFn_Loop) schirmer@13688: next schirmer@13688: case (Jmp j) schirmer@13688: thus ?case wenzelm@32960: apply - wenzelm@32960: apply (rule MGFn_NormalI) wenzelm@32960: apply (rule ax_derivs.Jmp [THEN conseq1]) wenzelm@46714: apply (auto intro: eval.Jmp) wenzelm@32960: done schirmer@13688: next schirmer@13688: case (Throw e) schirmer@13688: thus ?case wenzelm@32960: apply - wenzelm@32960: apply (rule MGFn_NormalI) wenzelm@32960: apply (erule MGFnD' [THEN conseq12, THEN ax_derivs.Throw]) nipkow@44890: apply (fastforce intro: eval.Throw) wenzelm@32960: done schirmer@13688: next schirmer@13688: case (TryC c1 C vn c2) schirmer@13688: thus "G,A\{=:n} \Try c1 Catch(C vn) c2\\<^sub>s\ {G\}" wenzelm@32960: apply - wenzelm@32960: apply (rule MGFn_NormalI) wenzelm@32960: apply (rule ax_derivs.Try [where schirmer@13688: ?Q = " (\Y' s' s. normal s \ (\s''. G\s \\c1\\<^sub>s\\ (Y',s'') \ schirmer@13688: G\s'' \sxalloc\ s')) \. G\init\n"]) wenzelm@32960: apply (erule MGFnD [THEN ax_NormalD, THEN conseq2]) nipkow@44890: apply (fastforce elim: sxalloc_gext [THEN card_nyinitcls_gext]) wenzelm@32960: apply (erule MGFnD'[THEN conseq12]) nipkow@44890: apply (fastforce intro: eval.Try) nipkow@44890: apply (fastforce intro: eval.Try) wenzelm@32960: done schirmer@13688: next schirmer@13688: case (Fin c1 c2) wenzelm@23366: note mgf_c1 = `G,A\{=:n} \c1\\<^sub>s\ {G\}` wenzelm@23366: note mgf_c2 = `G,A\{=:n} \c2\\<^sub>s\ {G\}` schirmer@13688: from wf mgf_c1 mgf_c2 schirmer@13688: show "G,A\{=:n} \c1 Finally c2\\<^sub>s\ {G\}" wenzelm@32960: by (rule MGFn_Fin) schirmer@13688: next schirmer@13688: case (FinA abr c) schirmer@13688: show ?case wenzelm@32960: by (rule MGFn_NormalI) (rule ax_derivs.FinA) schirmer@13688: next schirmer@13688: case (Init C) schirmer@13688: from hyp schirmer@13688: show "G,A\{=:n} \Init C\\<^sub>s\ {G\}" wenzelm@32960: by (rule MGFn_Init) schirmer@13688: next blanchet@58287: case Nil_expr schirmer@13688: show "G,A\{=:n} \[]\\<^sub>l\ {G\}" wenzelm@32960: apply - wenzelm@32960: apply (rule MGFn_NormalI) wenzelm@32960: apply (rule ax_derivs.Nil [THEN conseq1]) nipkow@44890: apply (fastforce intro: eval.Nil) wenzelm@32960: done schirmer@13688: next blanchet@58287: case (Cons_expr e es) schirmer@13688: thus "G,A\{=:n} \e# es\\<^sub>l\ {G\}" wenzelm@32960: apply - wenzelm@32960: apply (rule MGFn_NormalI) wenzelm@32960: apply (rule ax_derivs.Cons) wenzelm@32960: apply (erule MGFnD [THEN ax_NormalD]) wenzelm@32960: apply (rule allI) wenzelm@32960: apply (erule MGFnD'[THEN conseq12]) nipkow@44890: apply (fastforce intro: eval.Cons) wenzelm@32960: done schirmer@13688: qed schirmer@13688: } schirmer@13688: thus ?thesis schirmer@13688: by (cases rule: term_cases) auto schirmer@13688: qed schirmer@13688: qed schirmer@12854: schirmer@12925: lemma MGF_asm: schirmer@12925: "\\C sig. is_methd G C sig \ G,A\{\} In1l (Methd C sig)\ {G\}; wf_prog G\ schirmer@12925: \ G,(A::state triple set)\{\} t\ {G\}" schirmer@12854: apply (simp (no_asm_use) add: MGF_MGFn_iff) schirmer@12854: apply (rule allI) schirmer@12854: apply (rule MGFn_lemma) schirmer@12854: apply (intro strip) schirmer@12854: apply (rule MGFn_free_wt) schirmer@12854: apply (force dest: wt_Methd_is_methd) schirmer@12925: apply assumption (* wf_prog G *) schirmer@12854: done schirmer@12854: wenzelm@58887: subsubsection "nested version" schirmer@12854: schirmer@13688: lemma nesting_lemma' [rule_format (no_asm)]: schirmer@13688: assumes ax_derivs_asm: "\A ts. ts \ A \ P A ts" schirmer@13688: and MGF_nested_Methd: "\A pn. \b\bdy pn. P (insert (mgf_call pn) A) {mgf b} schirmer@13688: \ P A {mgf_call pn}" schirmer@13688: and MGF_asm: "\A t. \pn\U. P A {mgf_call pn} \ P A {mgf t}" schirmer@13688: and finU: "finite U" schirmer@13688: and uA: "uA = mgf_call`U" schirmer@13688: shows "\A. A \ uA \ n \ card uA \ card A = card uA - n schirmer@13688: \ (\t. P A {mgf t})" schirmer@13688: using finU uA schirmer@13688: apply - schirmer@13688: apply (induct_tac "n") wenzelm@42793: apply (tactic "ALLGOALS (clarsimp_tac @{context})") wenzelm@60754: apply (tactic {* dresolve_tac @{context} [Thm.permute_prems 0 1 @{thm card_seteq}] 1 *}) schirmer@13688: apply simp schirmer@13688: apply (erule finite_imageI) schirmer@13688: apply (simp add: MGF_asm ax_derivs_asm) schirmer@13688: apply (rule MGF_asm) schirmer@13688: apply (rule ballI) schirmer@13688: apply (case_tac "mgf_call pn : A") schirmer@13688: apply (fast intro: ax_derivs_asm) schirmer@13688: apply (rule MGF_nested_Methd) schirmer@13688: apply (rule ballI) schirmer@13688: apply (drule spec, erule impE, erule_tac [2] impE, erule_tac [3] spec) thomas@57492: apply hypsubst_thin schirmer@13688: apply fast schirmer@13688: apply (drule finite_subset) schirmer@13688: apply (erule finite_imageI) schirmer@13688: apply auto schirmer@13688: done schirmer@12854: schirmer@13688: schirmer@13688: lemma nesting_lemma [rule_format (no_asm)]: schirmer@13688: assumes ax_derivs_asm: "\A ts. ts \ A \ P A ts" schirmer@13688: and MGF_nested_Methd: "\A pn. \b\bdy pn. P (insert (mgf (f pn)) A) {mgf b} schirmer@13688: \ P A {mgf (f pn)}" schirmer@13688: and MGF_asm: "\A t. \pn\U. P A {mgf (f pn)} \ P A {mgf t}" schirmer@13688: and finU: "finite U" schirmer@13688: shows "P {} {mgf t}" schirmer@13688: using ax_derivs_asm MGF_nested_Methd MGF_asm finU schirmer@13688: by (rule nesting_lemma') (auto intro!: le_refl) schirmer@13688: schirmer@12854: schirmer@12854: lemma MGF_nested_Methd: "\ schirmer@13688: G,insert ({Normal \} \Methd C sig\\<^sub>e \{G\}) A schirmer@13688: \{Normal \} \body G C sig\\<^sub>e \{G\} schirmer@13688: \ \ G,A\{Normal \} \Methd C sig\\<^sub>e \{G\}" schirmer@12854: apply (unfold MGF_def) schirmer@12854: apply (rule ax_MethdN) schirmer@12854: apply (erule conseq2) schirmer@12854: apply clarsimp schirmer@12854: apply (erule MethdI) schirmer@12854: done schirmer@12854: schirmer@12925: lemma MGF_deriv: "wf_prog G \ G,({}::state triple set)\{\} t\ {G\}" schirmer@12854: apply (rule MGFNormalI) schirmer@12854: apply (rule_tac mgf = "\t. {Normal \} t\ {G\}" and schirmer@13688: bdy = "\ (C,sig) .{\body G C sig\\<^sub>e }" and schirmer@13688: f = "\ (C,sig) . \Methd C sig\\<^sub>e " in nesting_lemma) schirmer@12854: apply (erule ax_derivs.asm) schirmer@12854: apply (clarsimp simp add: split_tupled_all) schirmer@12854: apply (erule MGF_nested_Methd) schirmer@12925: apply (erule_tac [2] finite_is_methd [OF wf_ws_prog]) schirmer@12854: apply (rule MGF_asm [THEN MGFNormalD]) schirmer@12925: apply (auto intro: MGFNormalI) schirmer@12854: done schirmer@12854: schirmer@12854: wenzelm@58887: subsubsection "simultaneous version" schirmer@12854: schirmer@12854: lemma MGF_simult_Methd_lemma: "finite ms \ schirmer@13688: G,A \ (\(C,sig). {Normal \} \Methd C sig\\<^sub>e\ {G\}) ` ms schirmer@13688: |\(\(C,sig). {Normal \} \body G C sig\\<^sub>e\ {G\}) ` ms \ schirmer@13688: G,A|\(\(C,sig). {Normal \} \Methd C sig\\<^sub>e\ {G\}) ` ms" schirmer@12854: apply (unfold MGF_def) schirmer@12854: apply (rule ax_derivs.Methd [unfolded mtriples_def]) schirmer@12854: apply (erule ax_finite_pointwise) schirmer@12854: prefer 2 schirmer@12854: apply (rule ax_derivs.asm) schirmer@12854: apply fast schirmer@12854: apply clarsimp schirmer@12854: apply (rule conseq2) schirmer@12854: apply (erule (1) ax_methods_spec) schirmer@12854: apply clarsimp schirmer@12854: apply (erule eval_Methd) schirmer@12854: done schirmer@12854: schirmer@12925: lemma MGF_simult_Methd: "wf_prog G \ schirmer@13688: G,({}::state triple set)|\(\(C,sig). {Normal \} \Methd C sig\\<^sub>e\ {G\}) haftmann@61424: ` Collect (case_prod (is_methd G)) " schirmer@12925: apply (frule finite_is_methd [OF wf_ws_prog]) schirmer@12854: apply (rule MGF_simult_Methd_lemma) schirmer@12854: apply assumption schirmer@12854: apply (erule ax_finite_pointwise) schirmer@12854: prefer 2 schirmer@12854: apply (rule ax_derivs.asm) schirmer@12854: apply blast schirmer@12854: apply clarsimp schirmer@12854: apply (rule MGF_asm [THEN MGFNormalD]) schirmer@12925: apply (auto intro: MGFNormalI) schirmer@12854: done schirmer@12854: schirmer@12854: wenzelm@58887: subsubsection "corollaries" schirmer@12854: schirmer@12925: lemma eval_to_evaln: "\G\s \t\\ (Y', s');type_ok G t s; wf_prog G\ schirmer@12925: \ \n. G\s \t\\n\ (Y', s')" schirmer@12925: apply (cases "normal s") schirmer@12925: apply (force simp add: type_ok_def intro: eval_evaln) schirmer@12925: apply (force intro: evaln.Abrupt) schirmer@12925: done schirmer@12925: schirmer@13688: lemma MGF_complete: schirmer@13688: assumes valid: "G,{}\{P} t\ {Q}" schirmer@13688: and mgf: "G,({}::state triple set)\{\} t\ {G\}" schirmer@13688: and wf: "wf_prog G" schirmer@13688: shows "G,({}::state triple set)\{P::state assn} t\ {Q}" schirmer@13688: proof (rule ax_no_hazard) schirmer@13688: from mgf schirmer@13688: have "G,({}::state triple set)\{\} t\ {\Y s' s. G\s \t\\ (Y, s')}" schirmer@13688: by (unfold MGF_def) schirmer@13688: thus "G,({}::state triple set)\{P \. type_ok G t} t\ {Q}" schirmer@13688: proof (rule conseq12,clarsimp) schirmer@13688: fix Y s Z Y' s' schirmer@13688: assume P: "P Y s Z" schirmer@13688: assume type_ok: "type_ok G t s" schirmer@13688: assume eval_t: "G\s \t\\ (Y', s')" schirmer@13688: show "Q Y' s' Z" schirmer@13688: proof - schirmer@13688: from eval_t type_ok wf schirmer@13688: obtain n where evaln: "G\s \t\\n\ (Y', s')" wenzelm@32960: by (rule eval_to_evaln [elim_format]) iprover schirmer@13688: from valid have wenzelm@32960: valid_expanded: wenzelm@32960: "\n Y s Z. P Y s Z \ type_ok G t s schirmer@13688: \ (\Y' s'. G\s \t\\n\ (Y', s') \ Q Y' s' Z)" wenzelm@32960: by (simp add: ax_valids_def triple_valid_def) schirmer@13688: from P type_ok evaln schirmer@13688: show "Q Y' s' Z" wenzelm@32960: by (rule valid_expanded [rule_format]) schirmer@13688: qed schirmer@13688: qed schirmer@13688: qed schirmer@13688: schirmer@13688: theorem ax_complete: schirmer@13688: assumes wf: "wf_prog G" schirmer@13688: and valid: "G,{}\{P::state assn} t\ {Q}" schirmer@13688: shows "G,({}::state triple set)\{P} t\ {Q}" schirmer@13688: proof - schirmer@13688: from wf have "G,({}::state triple set)\{\} t\ {G\}" schirmer@13688: by (rule MGF_deriv) schirmer@13688: from valid this wf schirmer@13688: show ?thesis schirmer@13688: by (rule MGF_complete) schirmer@13688: qed schirmer@13688: schirmer@12854: end