src/HOL/Bali/Eval.thy
changeset 13688 a0b16d42d489
parent 13601 fd3e3d6b37b2
child 14981 e73f8140af78
equal deleted inserted replaced
13687:22dce9134953 13688:a0b16d42d489
    95       modelled
    95       modelled
    96 \item exceptions in initializations not replaced by ExceptionInInitializerError
    96 \item exceptions in initializations not replaced by ExceptionInInitializerError
    97 \end{itemize}
    97 \end{itemize}
    98 *}
    98 *}
    99 
    99 
       
   100 
   100 types vvar  =         "val \<times> (val \<Rightarrow> state \<Rightarrow> state)"
   101 types vvar  =         "val \<times> (val \<Rightarrow> state \<Rightarrow> state)"
   101       vals  =        "(val, vvar, val list) sum3"
   102       vals  =        "(val, vvar, val list) sum3"
   102 translations
   103 translations
   103      "vvar" <= (type) "val \<times> (val \<Rightarrow> state \<Rightarrow> state)"
   104      "vvar" <= (type) "val \<times> (val \<Rightarrow> state \<Rightarrow> state)"
   104      "vals" <= (type)"(val, vvar, val list) sum3"
   105      "vals" <= (type)"(val, vvar, val list) sum3" 
       
   106 
       
   107 text {* To avoid redundancy and to reduce the number of rules, there is only 
       
   108  one evaluation rule for each syntactic term. This is also true for variables
       
   109  (e.g. see the rules below for @{text LVar}, @{text FVar} and @{text AVar}). 
       
   110  So evaluation of a variable must capture both possible further uses: 
       
   111  read (rule @{text Acc}) or write (rule @{text Ass}) to the variable. 
       
   112  Therefor a variable evaluates to a special value @{term vvar}, which is 
       
   113  a pair, consisting of the current value (for later read access) and an update 
       
   114  function (for later write access). Because
       
   115  during assignment to an array variable an exception may occur if the types
       
   116  don't match, the update function is very generic: it transforms the 
       
   117  full state. This generic update function causes some technical trouble during
       
   118  some proofs (e.g. type safety, correctness of definite assignment). There we
       
   119  need to prove some additional invariant on this update function to prove the
       
   120  assignment correct, since the update function could potentially alter the whole
       
   121  state in an arbitrary manner. This invariant must be carried around through
       
   122  the whole induction.
       
   123  So for future approaches it may be better not to take
       
   124  such a generic update function, but only to store the address and the kind
       
   125  of variable (array (+ element type), local variable or field) for later 
       
   126  assignment. 
       
   127 *}
   105 
   128 
   106 syntax (xsymbols)
   129 syntax (xsymbols)
   107   dummy_res :: "vals" ("\<diamondsuit>")
   130   dummy_res :: "vals" ("\<diamondsuit>")
   108 translations
   131 translations
   109   "\<diamondsuit>" == "In1 Unit"
   132   "\<diamondsuit>" == "In1 Unit"
       
   133 
       
   134 syntax 
       
   135   val_inj_vals:: "expr \<Rightarrow> term" ("\<lfloor>_\<rfloor>\<^sub>e" 1000)
       
   136   var_inj_vals::  "var \<Rightarrow> term"  ("\<lfloor>_\<rfloor>\<^sub>v" 1000)
       
   137   lst_inj_vals:: "expr list \<Rightarrow> term" ("\<lfloor>_\<rfloor>\<^sub>l" 1000)
       
   138 
       
   139 translations 
       
   140   "\<lfloor>e\<rfloor>\<^sub>e" \<rightharpoonup> "In1 e"
       
   141   "\<lfloor>v\<rfloor>\<^sub>v" \<rightharpoonup> "In2 v"
       
   142   "\<lfloor>es\<rfloor>\<^sub>l" \<rightharpoonup> "In3 es"
   110 
   143 
   111 constdefs
   144 constdefs
   112   arbitrary3 :: "('al + 'ar, 'b, 'c) sum3 \<Rightarrow> vals"
   145   arbitrary3 :: "('al + 'ar, 'b, 'c) sum3 \<Rightarrow> vals"
   113  "arbitrary3 \<equiv> sum3_case (In1 \<circ> sum_case (\<lambda>x. arbitrary) (\<lambda>x. Unit))
   146  "arbitrary3 \<equiv> sum3_case (In1 \<circ> sum_case (\<lambda>x. arbitrary) (\<lambda>x. Unit))
   114                      (\<lambda>x. In2 arbitrary) (\<lambda>x. In3 arbitrary)"
   147                      (\<lambda>x. In2 arbitrary) (\<lambda>x. In3 arbitrary)"
   177   "G,(Some (Xcpt (Loc a)),s)\<turnstile>catch C = G,s\<turnstile>Addr a fits Class C"
   210   "G,(Some (Xcpt (Loc a)),s)\<turnstile>catch C = G,s\<turnstile>Addr a fits Class C"
   178 apply (unfold catch_def)
   211 apply (unfold catch_def)
   179 apply (simp (no_asm))
   212 apply (simp (no_asm))
   180 done
   213 done
   181 
   214 
       
   215 lemma catch_Jump [simp]: "\<not>G,(Some (Jump j),s)\<turnstile>catch tn"
       
   216 apply (unfold catch_def)
       
   217 apply (simp (no_asm))
       
   218 done
       
   219 
       
   220 lemma catch_Error [simp]: "\<not>G,(Some (Error e),s)\<turnstile>catch tn"
       
   221 apply (unfold catch_def)
       
   222 apply (simp (no_asm))
       
   223 done
       
   224 
   182 constdefs
   225 constdefs
   183   new_xcpt_var :: "vname \<Rightarrow> state \<Rightarrow> state"
   226   new_xcpt_var :: "vname \<Rightarrow> state \<Rightarrow> state"
   184  "new_xcpt_var vn \<equiv> 
   227  "new_xcpt_var vn \<equiv> 
   185      \<lambda>(x,s). Norm (lupd(VName vn\<mapsto>Addr (the_Loc (the_Xcpt (the x)))) s)"
   228      \<lambda>(x,s). Norm (lupd(VName vn\<mapsto>Addr (the_Loc (the_Xcpt (the x)))) s)"
   186 
   229 
   227 
   270 
   228 lemma assign_Some [simp]: 
   271 lemma assign_Some [simp]: 
   229 "assign f v (Some x,s) = (Some x,s)" 
   272 "assign f v (Some x,s) = (Some x,s)" 
   230 by (simp add: assign_def Let_def split_beta)
   273 by (simp add: assign_def Let_def split_beta)
   231 
   274 
       
   275 lemma assign_Some1 [simp]:  "\<not> normal s \<Longrightarrow> assign f v s = s" 
       
   276 by (auto simp add: assign_def Let_def split_beta)
       
   277 
   232 lemma assign_supd [simp]: 
   278 lemma assign_supd [simp]: 
   233 "assign (\<lambda>v. supd (f v)) v (x,s)  
   279 "assign (\<lambda>v. supd (f v)) v (x,s)  
   234   = (x, if x = None then f v s else s)"
   280   = (x, if x = None then f v s else s)"
   235 apply auto
   281 apply auto
   236 done
   282 done
   239   "assign (\<lambda>v (x,s). ((raise_if (b s v) xcpt) x, f v s)) v (x, s) =  
   285   "assign (\<lambda>v (x,s). ((raise_if (b s v) xcpt) x, f v s)) v (x, s) =  
   240   (raise_if (b s v) xcpt x, if x=None \<and> \<not>b s v then f v s else s)"
   286   (raise_if (b s v) xcpt x, if x=None \<and> \<not>b s v then f v s else s)"
   241 apply (case_tac "x = None")
   287 apply (case_tac "x = None")
   242 apply auto
   288 apply auto
   243 done
   289 done
       
   290 
   244 
   291 
   245 (*
   292 (*
   246 lemma assign_raise_if [simp]: 
   293 lemma assign_raise_if [simp]: 
   247   "assign (\<lambda>v s. \<lparr>abrupt=(raise_if (b (store s) v) xcpt) (abrupt s),
   294   "assign (\<lambda>v s. \<lparr>abrupt=(raise_if (b (store s) v) xcpt) (abrupt s),
   248                   store = f v (store s)\<rparr>) v s =  
   295                   store = f v (store s)\<rparr>) v s =  
   264 apply (simp (no_asm))
   311 apply (simp (no_asm))
   265 done
   312 done
   266 
   313 
   267 constdefs
   314 constdefs
   268 
   315 
   269 (*
       
   270   target  :: "inv_mode \<Rightarrow> st \<Rightarrow> val \<Rightarrow> ref_ty \<Rightarrow> qtname"
       
   271  "target m s a' t 
       
   272     \<equiv> if m = IntVir
       
   273 	 then obj_class (lookup_obj s a') 
       
   274          else the_Class (RefT t)"
       
   275 *)
       
   276 
       
   277  invocation_class  :: "inv_mode \<Rightarrow> st \<Rightarrow> val \<Rightarrow> ref_ty \<Rightarrow> qtname"
   316  invocation_class  :: "inv_mode \<Rightarrow> st \<Rightarrow> val \<Rightarrow> ref_ty \<Rightarrow> qtname"
   278  "invocation_class m s a' statT 
   317  "invocation_class m s a' statT 
   279     \<equiv> (case m of
   318     \<equiv> (case m of
   280          Static \<Rightarrow> if (\<exists> statC. statT = ClassT statC) 
   319          Static \<Rightarrow> if (\<exists> statC. statT = ClassT statC) 
   281                       then the_Class (RefT statT) 
   320                       then the_Class (RefT statT) 
   294 by (simp add: invocation_class_def)
   333 by (simp add: invocation_class_def)
   295 
   334 
   296 lemma dynclass_SuperM [simp]: 
   335 lemma dynclass_SuperM [simp]: 
   297  "invocation_class SuperM s a' statT = the_Class (RefT statT)"
   336  "invocation_class SuperM s a' statT = the_Class (RefT statT)"
   298 by (simp add: invocation_class_def)
   337 by (simp add: invocation_class_def)
   299 (*
       
   300 lemma invocation_class_notIntVir [simp]: 
       
   301  "m \<noteq> IntVir \<Longrightarrow> invocation_class m s a' statT = the_Class (RefT statT)"
       
   302 by (simp add: invocation_class_def)
       
   303 *)
       
   304 
   338 
   305 lemma invocation_class_Static [simp]: 
   339 lemma invocation_class_Static [simp]: 
   306   "invocation_class Static s a' statT = (if (\<exists> statC. statT = ClassT statC) 
   340   "invocation_class Static s a' statT = (if (\<exists> statC. statT = ClassT statC) 
   307                                             then the_Class (RefT statT) 
   341                                             then the_Class (RefT statT) 
   308                                             else Object)"
   342                                             else Object)"
   316       let m = mthd (the (methd G C sig));
   350       let m = mthd (the (methd G C sig));
   317           l = \<lambda> k. 
   351           l = \<lambda> k. 
   318               (case k of
   352               (case k of
   319                  EName e 
   353                  EName e 
   320                    \<Rightarrow> (case e of 
   354                    \<Rightarrow> (case e of 
   321                          VNam v \<Rightarrow> (init_vals (table_of (lcls (mbody m)))
   355                          VNam v \<Rightarrow> (empty ((pars m)[\<mapsto>]pvs)) v
   322                                                      ((pars m)[\<mapsto>]pvs)) v
   356                        | Res    \<Rightarrow> None)
   323                        | Res    \<Rightarrow> Some (default_val (resTy m)))
       
   324                | This 
   357                | This 
   325                    \<Rightarrow> (if mode=Static then None else Some a'))
   358                    \<Rightarrow> (if mode=Static then None else Some a'))
   326       in set_lvars l (if mode = Static then x else np a' x,s)"
   359       in set_lvars l (if mode = Static then x else np a' x,s)"
   327 
   360 
   328 
   361 
   329 
   362 
   330 lemma init_lvars_def2: "init_lvars G C sig mode a' pvs (x,s) =  
   363 lemma init_lvars_def2: --{* better suited for simplification *} 
       
   364 "init_lvars G C sig mode a' pvs (x,s) =  
   331   set_lvars 
   365   set_lvars 
   332     (\<lambda> k. 
   366     (\<lambda> k. 
   333        (case k of
   367        (case k of
   334           EName e 
   368           EName e 
   335             \<Rightarrow> (case e of 
   369             \<Rightarrow> (case e of 
   336                   VNam v 
   370                   VNam v 
   337                   \<Rightarrow> (init_vals 
   371                   \<Rightarrow> (empty ((pars (mthd (the (methd G C sig))))[\<mapsto>]pvs)) v
   338                        (table_of (lcls (mbody (mthd (the (methd G C sig))))))
   372                | Res \<Rightarrow> None)
   339                                  ((pars (mthd (the (methd G C sig))))[\<mapsto>]pvs)) v
       
   340                | Res \<Rightarrow> Some (default_val (resTy (mthd (the (methd G C sig))))))
       
   341         | This 
   373         | This 
   342             \<Rightarrow> (if mode=Static then None else Some a')))
   374             \<Rightarrow> (if mode=Static then None else Some a')))
   343     (if mode = Static then x else np a' x,s)"
   375     (if mode = Static then x else np a' x,s)"
   344 apply (unfold init_lvars_def)
   376 apply (unfold init_lvars_def)
   345 apply (simp (no_asm) add: Let_def)
   377 apply (simp (no_asm) add: Let_def)
   348 constdefs
   380 constdefs
   349   body :: "prog \<Rightarrow> qtname \<Rightarrow> sig \<Rightarrow> expr"
   381   body :: "prog \<Rightarrow> qtname \<Rightarrow> sig \<Rightarrow> expr"
   350  "body G C sig \<equiv> let m = the (methd G C sig) 
   382  "body G C sig \<equiv> let m = the (methd G C sig) 
   351                  in Body (declclass m) (stmt (mbody (mthd m)))"
   383                  in Body (declclass m) (stmt (mbody (mthd m)))"
   352 
   384 
   353 lemma body_def2: 
   385 lemma body_def2: --{* better suited for simplification *} 
   354 "body G C sig = Body  (declclass (the (methd G C sig))) 
   386 "body G C sig = Body  (declclass (the (methd G C sig))) 
   355                       (stmt (mbody (mthd (the (methd G C sig)))))"
   387                       (stmt (mbody (mthd (the (methd G C sig)))))"
   356 apply (unfold body_def Let_def)
   388 apply (unfold body_def Let_def)
   357 apply auto
   389 apply auto
   358 done
   390 done
   369     \<equiv> let (oref,xf) = if stat then (Stat C,id)
   401     \<equiv> let (oref,xf) = if stat then (Stat C,id)
   370                               else (Heap (the_Addr a'),np a');
   402                               else (Heap (the_Addr a'),np a');
   371 	          n = Inl (fn,C); 
   403 	          n = Inl (fn,C); 
   372                   f = (\<lambda>v. supd (upd_gobj oref n v)) 
   404                   f = (\<lambda>v. supd (upd_gobj oref n v)) 
   373       in ((the (values (the (globs (store s) oref)) n),f),abupd xf s)"
   405       in ((the (values (the (globs (store s) oref)) n),f),abupd xf s)"
   374 (*
   406 
   375  "fvar C stat fn a' s 
       
   376     \<equiv> let (oref,xf) = if stat then (Stat C,id)
       
   377                               else (Heap (the_Addr a'),np a');
       
   378 	          n = Inl (fn,C); 
       
   379                   f = (\<lambda>v. supd (upd_gobj oref n v)) 
       
   380       in ((the (values (the (globs (store s) oref)) n),f),abupd xf s)"
       
   381 *)
       
   382   avar :: "prog \<Rightarrow> val \<Rightarrow> val \<Rightarrow> state \<Rightarrow> vvar \<times> state"
   407   avar :: "prog \<Rightarrow> val \<Rightarrow> val \<Rightarrow> state \<Rightarrow> vvar \<times> state"
   383  "avar G i' a' s 
   408  "avar G i' a' s 
   384     \<equiv> let   oref = Heap (the_Addr a'); 
   409     \<equiv> let   oref = Heap (the_Addr a'); 
   385                i = the_Intg i'; 
   410                i = the_Intg i'; 
   386                n = Inr i;
   411                n = Inr i;
   389                                            ArrStore x
   414                                            ArrStore x
   390                               ,upd_gobj oref n v s)) 
   415                               ,upd_gobj oref n v s)) 
   391       in ((the (cs n),f)
   416       in ((the (cs n),f)
   392          ,abupd (raise_if (\<not>i in_bounds k) IndOutBound \<circ> np a') s)"
   417          ,abupd (raise_if (\<not>i in_bounds k) IndOutBound \<circ> np a') s)"
   393 
   418 
   394 lemma fvar_def2: "fvar C stat fn a' s =  
   419 lemma fvar_def2: --{* better suited for simplification *} 
       
   420 "fvar C stat fn a' s =  
   395   ((the 
   421   ((the 
   396      (values 
   422      (values 
   397       (the (globs (store s) (if stat then Stat C else Heap (the_Addr a')))) 
   423       (the (globs (store s) (if stat then Stat C else Heap (the_Addr a')))) 
   398       (Inl (fn,C)))
   424       (Inl (fn,C)))
   399    ,(\<lambda>v. supd (upd_gobj (if stat then Stat C else Heap (the_Addr a')) 
   425    ,(\<lambda>v. supd (upd_gobj (if stat then Stat C else Heap (the_Addr a')) 
   403   "
   429   "
   404 apply (unfold fvar_def)
   430 apply (unfold fvar_def)
   405 apply (simp (no_asm) add: Let_def split_beta)
   431 apply (simp (no_asm) add: Let_def split_beta)
   406 done
   432 done
   407 
   433 
   408 lemma avar_def2: "avar G i' a' s =  
   434 lemma avar_def2: --{* better suited for simplification *} 
       
   435 "avar G i' a' s =  
   409   ((the ((snd(snd(the_Arr (globs (store s) (Heap (the_Addr a')))))) 
   436   ((the ((snd(snd(the_Arr (globs (store s) (Heap (the_Addr a')))))) 
   410            (Inr (the_Intg i')))
   437            (Inr (the_Intg i')))
   411    ,(\<lambda>v (x,s').  (raise_if (\<not>G,s'\<turnstile>v fits (fst(the_Arr (globs (store s)
   438    ,(\<lambda>v (x,s').  (raise_if (\<not>G,s'\<turnstile>v fits (fst(the_Arr (globs (store s)
   412                                                    (Heap (the_Addr a')))))) 
   439                                                    (Heap (the_Addr a')))))) 
   413                             ArrStore x
   440                             ArrStore x
   445         (error_if (\<not> G\<turnstile>Methd sig dynM in invC dyn_accessible_from accC)
   472         (error_if (\<not> G\<turnstile>Methd sig dynM in invC dyn_accessible_from accC)
   446                   AccessViolation)
   473                   AccessViolation)
   447         s"
   474         s"
   448        
   475        
   449 section "evaluation judgments"
   476 section "evaluation judgments"
   450 
       
   451 consts eval_unop :: "unop \<Rightarrow> val \<Rightarrow> val"
       
   452 primrec
       
   453 "eval_unop UPlus   v = Intg (the_Intg v)"
       
   454 "eval_unop UMinus  v = Intg (- (the_Intg v))"
       
   455 "eval_unop UBitNot v = Intg 42"                -- "FIXME: Not yet implemented"
       
   456 "eval_unop UNot    v = Bool (\<not> the_Bool v)"
       
   457 
       
   458 consts eval_binop :: "binop \<Rightarrow> val \<Rightarrow> val \<Rightarrow> val"
       
   459 primrec
       
   460 "eval_binop Mul     v1 v2 = Intg ((the_Intg v1) * (the_Intg v2))" 
       
   461 "eval_binop Div     v1 v2 = Intg ((the_Intg v1) div (the_Intg v2))"
       
   462 "eval_binop Mod     v1 v2 = Intg ((the_Intg v1) mod (the_Intg v2))"
       
   463 "eval_binop Plus    v1 v2 = Intg ((the_Intg v1) + (the_Intg v2))"
       
   464 "eval_binop Minus   v1 v2 = Intg ((the_Intg v1) - (the_Intg v2))"
       
   465 
       
   466 -- "Be aware of the explicit coercion of the shift distance to nat"
       
   467 "eval_binop LShift  v1 v2 = Intg ((the_Intg v1) *   (2^(nat (the_Intg v2))))"
       
   468 "eval_binop RShift  v1 v2 = Intg ((the_Intg v1) div (2^(nat (the_Intg v2))))"
       
   469 "eval_binop RShiftU v1 v2 = Intg 42" --"FIXME: Not yet implemented"
       
   470 
       
   471 "eval_binop Less    v1 v2 = Bool ((the_Intg v1) < (the_Intg v2))" 
       
   472 "eval_binop Le      v1 v2 = Bool ((the_Intg v1) \<le> (the_Intg v2))"
       
   473 "eval_binop Greater v1 v2 = Bool ((the_Intg v2) < (the_Intg v1))"
       
   474 "eval_binop Ge      v1 v2 = Bool ((the_Intg v2) \<le> (the_Intg v1))"
       
   475 
       
   476 "eval_binop Eq      v1 v2 = Bool (v1=v2)"
       
   477 "eval_binop Neq     v1 v2 = Bool (v1\<noteq>v2)"
       
   478 "eval_binop BitAnd  v1 v2 = Intg 42" -- "FIXME: Not yet implemented"
       
   479 "eval_binop And     v1 v2 = Bool ((the_Bool v1) \<and> (the_Bool v2))"
       
   480 "eval_binop BitXor  v1 v2 = Intg 42" -- "FIXME: Not yet implemented"
       
   481 "eval_binop Xor     v1 v2 = Bool ((the_Bool v1) \<noteq> (the_Bool v2))"
       
   482 "eval_binop BitOr   v1 v2 = Intg 42" -- "FIXME: Not yet implemented"
       
   483 "eval_binop Or      v1 v2 = Bool ((the_Bool v1) \<or> (the_Bool v2))"
       
   484 "eval_binop CondAnd v1 v2 = Bool ((the_Bool v1) \<and> (the_Bool v2))"
       
   485 "eval_binop CondOr  v1 v2 = Bool ((the_Bool v1) \<or> (the_Bool v2))"
       
   486 
       
   487 constdefs need_second_arg :: "binop \<Rightarrow> val \<Rightarrow> bool"
       
   488 "need_second_arg binop v1 \<equiv> \<not> ((binop=CondAnd \<and>  \<not> the_Bool v1) \<or>
       
   489                                (binop=CondOr  \<and> the_Bool v1))"
       
   490 text {* @{term CondAnd} and @{term CondOr} only evalulate the second argument
       
   491  if the value isn't already determined by the first argument*}
       
   492 
       
   493 lemma need_second_arg_CondAnd [simp]: "need_second_arg CondAnd (Bool b) = b" 
       
   494 by (simp add: need_second_arg_def)
       
   495 
       
   496 lemma need_second_arg_CondOr [simp]: "need_second_arg CondOr (Bool b) = (\<not> b)" 
       
   497 by (simp add: need_second_arg_def)
       
   498 
       
   499 lemma need_second_arg_strict[simp]: 
       
   500  "\<lbrakk>binop\<noteq>CondAnd; binop\<noteq>CondOr\<rbrakk> \<Longrightarrow> need_second_arg binop b"
       
   501 by (cases binop) 
       
   502    (simp_all add: need_second_arg_def)
       
   503 
   477 
   504 consts
   478 consts
   505   eval   :: "prog \<Rightarrow> (state \<times> term    \<times> vals \<times> state) set"
   479   eval   :: "prog \<Rightarrow> (state \<times> term    \<times> vals \<times> state) set"
   506   halloc::  "prog \<Rightarrow> (state \<times> obj_tag \<times> loc  \<times> state) set"
   480   halloc::  "prog \<Rightarrow> (state \<times> obj_tag \<times> loc  \<times> state) set"
   507   sxalloc:: "prog \<Rightarrow> (state                  \<times> state) set"
   481   sxalloc:: "prog \<Rightarrow> (state                  \<times> state) set"
   544   "G\<turnstile>s \<midarrow>halloc oi\<succ>a\<rightarrow> (x,s')" <= "(s,oi,a,x,s') \<in> halloc G"
   518   "G\<turnstile>s \<midarrow>halloc oi\<succ>a\<rightarrow> (x,s')" <= "(s,oi,a,x,s') \<in> halloc G"
   545   "G\<turnstile>s \<midarrow>halloc oi\<succ>a\<rightarrow>    s' " == "(s,oi,a,  s') \<in> halloc G"
   519   "G\<turnstile>s \<midarrow>halloc oi\<succ>a\<rightarrow>    s' " == "(s,oi,a,  s') \<in> halloc G"
   546   "G\<turnstile>s \<midarrow>sxalloc\<rightarrow>     (x,s')" <= "(s     ,x,s') \<in> sxalloc G"
   520   "G\<turnstile>s \<midarrow>sxalloc\<rightarrow>     (x,s')" <= "(s     ,x,s') \<in> sxalloc G"
   547   "G\<turnstile>s \<midarrow>sxalloc\<rightarrow>        s' " == "(s     ,  s') \<in> sxalloc G"
   521   "G\<turnstile>s \<midarrow>sxalloc\<rightarrow>        s' " == "(s     ,  s') \<in> sxalloc G"
   548 
   522 
   549 inductive "halloc G" intros (* allocating objects on the heap, cf. 12.5 *)
   523 inductive "halloc G" intros --{* allocating objects on the heap, cf. 12.5 *}
   550 
   524 
   551   Abrupt: 
   525   Abrupt: 
   552   "G\<turnstile>(Some x,s) \<midarrow>halloc oi\<succ>arbitrary\<rightarrow> (Some x,s)"
   526   "G\<turnstile>(Some x,s) \<midarrow>halloc oi\<succ>arbitrary\<rightarrow> (Some x,s)"
   553 
   527 
   554   New:	  "\<lbrakk>new_Addr (heap s) = Some a; 
   528   New:	  "\<lbrakk>new_Addr (heap s) = Some a; 
   555 	    (x,oi') = (if atleast_free (heap s) (Suc (Suc 0)) then (None,oi)
   529 	    (x,oi') = (if atleast_free (heap s) (Suc (Suc 0)) then (None,oi)
   556 		       else (Some (Xcpt (Loc a)),CInst (SXcpt OutOfMemory)))\<rbrakk>
   530 		       else (Some (Xcpt (Loc a)),CInst (SXcpt OutOfMemory)))\<rbrakk>
   557             \<Longrightarrow>
   531             \<Longrightarrow>
   558 	    G\<turnstile>Norm s \<midarrow>halloc oi\<succ>a\<rightarrow> (x,init_obj G oi' (Heap a) s)"
   532 	    G\<turnstile>Norm s \<midarrow>halloc oi\<succ>a\<rightarrow> (x,init_obj G oi' (Heap a) s)"
   559 
   533 
   560 inductive "sxalloc G" intros (* allocating exception objects for
   534 inductive "sxalloc G" intros --{* allocating exception objects for
   561 	 	 	      standard exceptions (other than OutOfMemory) *)
   535 	 	 	      standard exceptions (other than OutOfMemory) *}
   562 
   536 
   563   Norm:	 "G\<turnstile> Norm              s   \<midarrow>sxalloc\<rightarrow>  Norm             s"
   537   Norm:	 "G\<turnstile> Norm              s   \<midarrow>sxalloc\<rightarrow>  Norm             s"
       
   538 
       
   539   Jmp:   "G\<turnstile>(Some (Jump j), s)  \<midarrow>sxalloc\<rightarrow> (Some (Jump j), s)"
       
   540 
       
   541   Error: "G\<turnstile>(Some (Error e), s)  \<midarrow>sxalloc\<rightarrow> (Some (Error e), s)"
   564 
   542 
   565   XcptL: "G\<turnstile>(Some (Xcpt (Loc a) ),s)  \<midarrow>sxalloc\<rightarrow> (Some (Xcpt (Loc a)),s)"
   543   XcptL: "G\<turnstile>(Some (Xcpt (Loc a) ),s)  \<midarrow>sxalloc\<rightarrow> (Some (Xcpt (Loc a)),s)"
   566 
   544 
   567   SXcpt: "\<lbrakk>G\<turnstile>Norm s0 \<midarrow>halloc (CInst (SXcpt xn))\<succ>a\<rightarrow> (x,s1)\<rbrakk> \<Longrightarrow>
   545   SXcpt: "\<lbrakk>G\<turnstile>Norm s0 \<midarrow>halloc (CInst (SXcpt xn))\<succ>a\<rightarrow> (x,s1)\<rbrakk> \<Longrightarrow>
   568 	  G\<turnstile>(Some (Xcpt (Std xn)),s0) \<midarrow>sxalloc\<rightarrow> (Some (Xcpt (Loc a)),s1)"
   546 	  G\<turnstile>(Some (Xcpt (Std xn)),s0) \<midarrow>sxalloc\<rightarrow> (Some (Xcpt (Loc a)),s1)"
       
   547 
   569 
   548 
   570 text {* 
   549 text {* 
   571 \par
   550 \par
   572 *} (* dummy text command to break paragraph for latex;
   551 *} (* dummy text command to break paragraph for latex;
   573               large paragraphs exhaust memory of debian pdflatex *)
   552               large paragraphs exhaust memory of debian pdflatex *)
   574 
   553 
       
   554 
   575 inductive "eval G" intros
   555 inductive "eval G" intros
   576 
   556 
   577 (* propagation of abrupt completion *)
   557 --{* propagation of abrupt completion *}
   578 
   558 
   579   (* cf. 14.1, 15.5 *)
   559   --{* cf. 14.1, 15.5 *}
   580   Abrupt: 
   560   Abrupt: 
   581    "G\<turnstile>(Some xc,s) \<midarrow>t\<succ>\<rightarrow> (arbitrary3 t,(Some xc,s))"
   561    "G\<turnstile>(Some xc,s) \<midarrow>t\<succ>\<rightarrow> (arbitrary3 t,(Some xc,s))"
   582 
   562 
   583 
   563 
   584 (* execution of statements *)
   564 --{* execution of statements *}
   585 
   565 
   586   (* cf. 14.5 *)
   566   --{* cf. 14.5 *}
   587   Skip:	 			    "G\<turnstile>Norm s \<midarrow>Skip\<rightarrow> Norm s"
   567   Skip:	 			    "G\<turnstile>Norm s \<midarrow>Skip\<rightarrow> Norm s"
   588 
   568 
   589   (* cf. 14.7 *)
   569   --{* cf. 14.7 *}
   590   Expr:	"\<lbrakk>G\<turnstile>Norm s0 \<midarrow>e-\<succ>v\<rightarrow> s1\<rbrakk> \<Longrightarrow>
   570   Expr:	"\<lbrakk>G\<turnstile>Norm s0 \<midarrow>e-\<succ>v\<rightarrow> s1\<rbrakk> \<Longrightarrow>
   591 				  G\<turnstile>Norm s0 \<midarrow>Expr e\<rightarrow> s1"
   571 				  G\<turnstile>Norm s0 \<midarrow>Expr e\<rightarrow> s1"
   592 
   572 
   593   Lab:  "\<lbrakk>G\<turnstile>Norm s0 \<midarrow>c \<rightarrow> s1\<rbrakk> \<Longrightarrow>
   573   Lab:  "\<lbrakk>G\<turnstile>Norm s0 \<midarrow>c \<rightarrow> s1\<rbrakk> \<Longrightarrow>
   594                                 G\<turnstile>Norm s0 \<midarrow>l\<bullet> c\<rightarrow> abupd (absorb l) s1"
   574                                 G\<turnstile>Norm s0 \<midarrow>l\<bullet> c\<rightarrow> abupd (absorb l) s1"
   595   (* cf. 14.2 *)
   575   --{* cf. 14.2 *}
   596   Comp:	"\<lbrakk>G\<turnstile>Norm s0 \<midarrow>c1 \<rightarrow> s1;
   576   Comp:	"\<lbrakk>G\<turnstile>Norm s0 \<midarrow>c1 \<rightarrow> s1;
   597 	  G\<turnstile>     s1 \<midarrow>c2 \<rightarrow> s2\<rbrakk> \<Longrightarrow>
   577 	  G\<turnstile>     s1 \<midarrow>c2 \<rightarrow> s2\<rbrakk> \<Longrightarrow>
   598 				 G\<turnstile>Norm s0 \<midarrow>c1;; c2\<rightarrow> s2"
   578 				 G\<turnstile>Norm s0 \<midarrow>c1;; c2\<rightarrow> s2"
   599 
   579 
   600 
   580   --{* cf. 14.8.2 *}
   601   (* cf. 14.8.2 *)
       
   602   If:	"\<lbrakk>G\<turnstile>Norm s0 \<midarrow>e-\<succ>b\<rightarrow> s1;
   581   If:	"\<lbrakk>G\<turnstile>Norm s0 \<midarrow>e-\<succ>b\<rightarrow> s1;
   603 	  G\<turnstile>     s1\<midarrow>(if the_Bool b then c1 else c2)\<rightarrow> s2\<rbrakk> \<Longrightarrow>
   582 	  G\<turnstile>     s1\<midarrow>(if the_Bool b then c1 else c2)\<rightarrow> s2\<rbrakk> \<Longrightarrow>
   604 		       G\<turnstile>Norm s0 \<midarrow>If(e) c1 Else c2 \<rightarrow> s2"
   583 		       G\<turnstile>Norm s0 \<midarrow>If(e) c1 Else c2 \<rightarrow> s2"
   605 
   584 
   606   (* cf. 14.10, 14.10.1 *)
   585   --{* cf. 14.10, 14.10.1 *}
   607   (*      G\<turnstile>Norm s0 \<midarrow>If(e) (c;; While(e) c) Else Skip\<rightarrow> s3 *)
   586   
   608   (* A "continue jump" from the while body c is handled by 
   587   --{* A continue jump from the while body @{term c} is handled by 
   609      this rule. If a continue jump with the proper label was invoked inside c
   588      this rule. If a continue jump with the proper label was invoked inside 
   610      this label (Cont l) is deleted out of the abrupt component of the state 
   589      @{term c} this label (Cont l) is deleted out of the abrupt component of 
   611      before the iterative evaluation of the while statement.
   590      the state before the iterative evaluation of the while statement.
   612      A "break jump" is handled by the Lab Statement (Lab l (while\<dots>).
   591      A break jump is handled by the Lab Statement @{text "Lab l (while\<dots>)"}.
   613   *)
   592   *}
   614   Loop:	"\<lbrakk>G\<turnstile>Norm s0 \<midarrow>e-\<succ>b\<rightarrow> s1;
   593   Loop:	"\<lbrakk>G\<turnstile>Norm s0 \<midarrow>e-\<succ>b\<rightarrow> s1;
   615 	  if normal s1 \<and> the_Bool b 
   594 	  if the_Bool b 
   616              then (G\<turnstile>s1 \<midarrow>c\<rightarrow> s2 \<and> 
   595              then (G\<turnstile>s1 \<midarrow>c\<rightarrow> s2 \<and> 
   617                    G\<turnstile>(abupd (absorb (Cont l)) s2) \<midarrow>l\<bullet> While(e) c\<rightarrow> s3)
   596                    G\<turnstile>(abupd (absorb (Cont l)) s2) \<midarrow>l\<bullet> While(e) c\<rightarrow> s3)
   618 	     else s3 = s1\<rbrakk> \<Longrightarrow>
   597 	     else s3 = s1\<rbrakk> \<Longrightarrow>
   619 			      G\<turnstile>Norm s0 \<midarrow>l\<bullet> While(e) c\<rightarrow> s3"
   598 			      G\<turnstile>Norm s0 \<midarrow>l\<bullet> While(e) c\<rightarrow> s3"
   620 
   599 
   621   Do: "G\<turnstile>Norm s \<midarrow>Do j\<rightarrow> (Some (Jump j), s)"
   600   Jmp: "G\<turnstile>Norm s \<midarrow>Jmp j\<rightarrow> (Some (Jump j), s)"
   622    
   601    
   623   (* cf. 14.16 *)
   602   --{* cf. 14.16 *}
   624   Throw: "\<lbrakk>G\<turnstile>Norm s0 \<midarrow>e-\<succ>a'\<rightarrow> s1\<rbrakk> \<Longrightarrow>
   603   Throw: "\<lbrakk>G\<turnstile>Norm s0 \<midarrow>e-\<succ>a'\<rightarrow> s1\<rbrakk> \<Longrightarrow>
   625 				 G\<turnstile>Norm s0 \<midarrow>Throw e\<rightarrow> abupd (throw a') s1"
   604 				 G\<turnstile>Norm s0 \<midarrow>Throw e\<rightarrow> abupd (throw a') s1"
   626 
   605 
   627   (* cf. 14.18.1 *)
   606   --{* cf. 14.18.1 *}
   628   Try:	"\<lbrakk>G\<turnstile>Norm s0 \<midarrow>c1\<rightarrow> s1; G\<turnstile>s1 \<midarrow>sxalloc\<rightarrow> s2; 
   607   Try:	"\<lbrakk>G\<turnstile>Norm s0 \<midarrow>c1\<rightarrow> s1; G\<turnstile>s1 \<midarrow>sxalloc\<rightarrow> s2; 
   629 	  if G,s2\<turnstile>catch C then G\<turnstile>new_xcpt_var vn s2 \<midarrow>c2\<rightarrow> s3 else s3 = s2\<rbrakk> \<Longrightarrow>
   608 	  if G,s2\<turnstile>catch C then G\<turnstile>new_xcpt_var vn s2 \<midarrow>c2\<rightarrow> s3 else s3 = s2\<rbrakk> \<Longrightarrow>
   630 		  G\<turnstile>Norm s0 \<midarrow>Try c1 Catch(C vn) c2\<rightarrow> s3"
   609 		  G\<turnstile>Norm s0 \<midarrow>Try c1 Catch(C vn) c2\<rightarrow> s3"
   631 
   610 
   632   (* cf. 14.18.2 *)
   611   --{* cf. 14.18.2 *}
   633   Fin:	"\<lbrakk>G\<turnstile>Norm s0 \<midarrow>c1\<rightarrow> (x1,s1);
   612   Fin:	"\<lbrakk>G\<turnstile>Norm s0 \<midarrow>c1\<rightarrow> (x1,s1);
   634 	  G\<turnstile>Norm s1 \<midarrow>c2\<rightarrow> s2;
   613 	  G\<turnstile>Norm s1 \<midarrow>c2\<rightarrow> s2;
   635           s3=(if (\<exists> err. x1=Some (Error err)) 
   614           s3=(if (\<exists> err. x1=Some (Error err)) 
   636               then (x1,s1) 
   615               then (x1,s1) 
   637               else abupd (abrupt_if (x1\<noteq>None) x1) s2) \<rbrakk> 
   616               else abupd (abrupt_if (x1\<noteq>None) x1) s2) \<rbrakk> 
   638           \<Longrightarrow>
   617           \<Longrightarrow>
   639           G\<turnstile>Norm s0 \<midarrow>c1 Finally c2\<rightarrow> s3"
   618           G\<turnstile>Norm s0 \<midarrow>c1 Finally c2\<rightarrow> s3"
   640   (* cf. 12.4.2, 8.5 *)
   619   --{* cf. 12.4.2, 8.5 *}
   641   Init:	"\<lbrakk>the (class G C) = c;
   620   Init:	"\<lbrakk>the (class G C) = c;
   642 	  if inited C (globs s0) then s3 = Norm s0
   621 	  if inited C (globs s0) then s3 = Norm s0
   643 	  else (G\<turnstile>Norm (init_class_obj G C s0) 
   622 	  else (G\<turnstile>Norm (init_class_obj G C s0) 
   644 		  \<midarrow>(if C = Object then Skip else Init (super c))\<rightarrow> s1 \<and>
   623 		  \<midarrow>(if C = Object then Skip else Init (super c))\<rightarrow> s1 \<and>
   645 	       G\<turnstile>set_lvars empty s1 \<midarrow>init c\<rightarrow> s2 \<and> s3 = restore_lvars s1 s2)\<rbrakk> 
   624 	       G\<turnstile>set_lvars empty s1 \<midarrow>init c\<rightarrow> s2 \<and> s3 = restore_lvars s1 s2)\<rbrakk> 
   646               \<Longrightarrow>
   625               \<Longrightarrow>
   647 		 G\<turnstile>Norm s0 \<midarrow>Init C\<rightarrow> s3"
   626 		 G\<turnstile>Norm s0 \<midarrow>Init C\<rightarrow> s3"
   648    (* This class initialisation rule is a little bit inaccurate. Look at the
   627    --{* This class initialisation rule is a little bit inaccurate. Look at the
   649       exact sequence:
   628       exact sequence:
   650       1. The current class object (the static fields) are initialised
   629       (1) The current class object (the static fields) are initialised
   651          (init_class_obj)
   630            (@{text init_class_obj}),
   652       2. Then the superclasses are initialised
   631       (2) the superclasses are initialised,
   653       3. The static initialiser of the current class is invoked
   632       (3) the static initialiser of the current class is invoked.
   654       More precisely we should expect another ordering, namely 2 1 3.
   633       More precisely we should expect another ordering, namely 2 1 3.
   655       But we can't just naively toggle 1 and 2. By calling init_class_obj 
   634       But we can't just naively toggle 1 and 2. By calling 
   656       before initialising the superclasses we also implicitly record that
   635       @{text init_class_obj} 
       
   636       before initialising the superclasses, we also implicitly record that
   657       we have started to initialise the current class (by setting an 
   637       we have started to initialise the current class (by setting an 
   658       value for the class object). This becomes 
   638       value for the class object). This becomes 
   659       crucial for the completeness proof of the axiomatic semantics 
   639       crucial for the completeness proof of the axiomatic semantics 
   660       (AxCompl.thy). Static initialisation requires an induction on the number 
   640       @{text "AxCompl.thy"}. Static initialisation requires an induction on 
   661       of classes not yet initialised (or to be more precise, classes where the
   641       the number of classes not yet initialised (or to be more precise, 
   662       initialisation has not yet begun). 
   642       classes were the initialisation has not yet begun). 
   663       So we could first assign a dummy value to the class before
   643       So we could first assign a dummy value to the class before
   664       superclass initialisation and afterwards set the correct values.
   644       superclass initialisation and afterwards set the correct values.
   665       But as long as we don't take memory overflow into account 
   645       But as long as we don't take memory overflow into account 
   666       when allocating class objects, and don't model definite assignment in
   646       when allocating class objects, we can leave things as they are for 
   667       the static initialisers, we can leave things as they are for convenience. 
   647       convenience. 
   668    *)
   648    *}
   669 (* evaluation of expressions *)
   649 --{* evaluation of expressions *}
   670 
   650 
   671   (* cf. 15.8.1, 12.4.1 *)
   651   --{* cf. 15.8.1, 12.4.1 *}
   672   NewC:	"\<lbrakk>G\<turnstile>Norm s0 \<midarrow>Init C\<rightarrow> s1;
   652   NewC:	"\<lbrakk>G\<turnstile>Norm s0 \<midarrow>Init C\<rightarrow> s1;
   673 	  G\<turnstile>     s1 \<midarrow>halloc (CInst C)\<succ>a\<rightarrow> s2\<rbrakk> \<Longrightarrow>
   653 	  G\<turnstile>     s1 \<midarrow>halloc (CInst C)\<succ>a\<rightarrow> s2\<rbrakk> \<Longrightarrow>
   674 	                          G\<turnstile>Norm s0 \<midarrow>NewC C-\<succ>Addr a\<rightarrow> s2"
   654 	                          G\<turnstile>Norm s0 \<midarrow>NewC C-\<succ>Addr a\<rightarrow> s2"
   675 
   655 
   676   (* cf. 15.9.1, 12.4.1 *)
   656   --{* cf. 15.9.1, 12.4.1 *}
   677   NewA:	"\<lbrakk>G\<turnstile>Norm s0 \<midarrow>init_comp_ty T\<rightarrow> s1; G\<turnstile>s1 \<midarrow>e-\<succ>i'\<rightarrow> s2; 
   657   NewA:	"\<lbrakk>G\<turnstile>Norm s0 \<midarrow>init_comp_ty T\<rightarrow> s1; G\<turnstile>s1 \<midarrow>e-\<succ>i'\<rightarrow> s2; 
   678 	  G\<turnstile>abupd (check_neg i') s2 \<midarrow>halloc (Arr T (the_Intg i'))\<succ>a\<rightarrow> s3\<rbrakk> \<Longrightarrow>
   658 	  G\<turnstile>abupd (check_neg i') s2 \<midarrow>halloc (Arr T (the_Intg i'))\<succ>a\<rightarrow> s3\<rbrakk> \<Longrightarrow>
   679 	                        G\<turnstile>Norm s0 \<midarrow>New T[e]-\<succ>Addr a\<rightarrow> s3"
   659 	                        G\<turnstile>Norm s0 \<midarrow>New T[e]-\<succ>Addr a\<rightarrow> s3"
   680 
   660 
   681   (* cf. 15.15 *)
   661   --{* cf. 15.15 *}
   682   Cast:	"\<lbrakk>G\<turnstile>Norm s0 \<midarrow>e-\<succ>v\<rightarrow> s1;
   662   Cast:	"\<lbrakk>G\<turnstile>Norm s0 \<midarrow>e-\<succ>v\<rightarrow> s1;
   683 	  s2 = abupd (raise_if (\<not>G,store s1\<turnstile>v fits T) ClassCast) s1\<rbrakk> \<Longrightarrow>
   663 	  s2 = abupd (raise_if (\<not>G,store s1\<turnstile>v fits T) ClassCast) s1\<rbrakk> \<Longrightarrow>
   684 			        G\<turnstile>Norm s0 \<midarrow>Cast T e-\<succ>v\<rightarrow> s2"
   664 			        G\<turnstile>Norm s0 \<midarrow>Cast T e-\<succ>v\<rightarrow> s2"
   685 
   665 
   686   (* cf. 15.19.2 *)
   666   --{* cf. 15.19.2 *}
   687   Inst:	"\<lbrakk>G\<turnstile>Norm s0 \<midarrow>e-\<succ>v\<rightarrow> s1;
   667   Inst:	"\<lbrakk>G\<turnstile>Norm s0 \<midarrow>e-\<succ>v\<rightarrow> s1;
   688 	  b = (v\<noteq>Null \<and> G,store s1\<turnstile>v fits RefT T)\<rbrakk> \<Longrightarrow>
   668 	  b = (v\<noteq>Null \<and> G,store s1\<turnstile>v fits RefT T)\<rbrakk> \<Longrightarrow>
   689 			      G\<turnstile>Norm s0 \<midarrow>e InstOf T-\<succ>Bool b\<rightarrow> s1"
   669 			      G\<turnstile>Norm s0 \<midarrow>e InstOf T-\<succ>Bool b\<rightarrow> s1"
   690 
   670 
   691   (* cf. 15.7.1 *)
   671   --{* cf. 15.7.1 *}
   692   Lit:	"G\<turnstile>Norm s \<midarrow>Lit v-\<succ>v\<rightarrow> Norm s"
   672   Lit:	"G\<turnstile>Norm s \<midarrow>Lit v-\<succ>v\<rightarrow> Norm s"
   693 
   673 
   694   UnOp: "\<lbrakk>G\<turnstile>Norm s0 \<midarrow>e-\<succ>v\<rightarrow> s1\<rbrakk> 
   674   UnOp: "\<lbrakk>G\<turnstile>Norm s0 \<midarrow>e-\<succ>v\<rightarrow> s1\<rbrakk> 
   695          \<Longrightarrow> G\<turnstile>Norm s0 \<midarrow>UnOp unop e-\<succ>(eval_unop unop v)\<rightarrow> s1"
   675          \<Longrightarrow> G\<turnstile>Norm s0 \<midarrow>UnOp unop e-\<succ>(eval_unop unop v)\<rightarrow> s1"
   696  
   676  
   698           G\<turnstile>s1 \<midarrow>(if need_second_arg binop v1 then (In1l e2) else (In1r Skip))
   678           G\<turnstile>s1 \<midarrow>(if need_second_arg binop v1 then (In1l e2) else (In1r Skip))
   699                 \<succ>\<rightarrow> (In1 v2,s2)
   679                 \<succ>\<rightarrow> (In1 v2,s2)
   700           \<rbrakk> 
   680           \<rbrakk> 
   701          \<Longrightarrow> G\<turnstile>Norm s0 \<midarrow>BinOp binop e1 e2-\<succ>(eval_binop binop v1 v2)\<rightarrow> s2"
   681          \<Longrightarrow> G\<turnstile>Norm s0 \<midarrow>BinOp binop e1 e2-\<succ>(eval_binop binop v1 v2)\<rightarrow> s2"
   702    
   682    
   703   (* cf. 15.10.2 *)
   683   --{* cf. 15.10.2 *}
   704   Super: "G\<turnstile>Norm s \<midarrow>Super-\<succ>val_this s\<rightarrow> Norm s"
   684   Super: "G\<turnstile>Norm s \<midarrow>Super-\<succ>val_this s\<rightarrow> Norm s"
   705 
   685 
   706   (* cf. 15.2 *)
   686   --{* cf. 15.2 *}
   707   Acc:	"\<lbrakk>G\<turnstile>Norm s0 \<midarrow>va=\<succ>(v,f)\<rightarrow> s1\<rbrakk> \<Longrightarrow>
   687   Acc:	"\<lbrakk>G\<turnstile>Norm s0 \<midarrow>va=\<succ>(v,f)\<rightarrow> s1\<rbrakk> \<Longrightarrow>
   708 	                          G\<turnstile>Norm s0 \<midarrow>Acc va-\<succ>v\<rightarrow> s1"
   688 	                          G\<turnstile>Norm s0 \<midarrow>Acc va-\<succ>v\<rightarrow> s1"
   709 
   689 
   710   (* cf. 15.25.1 *)
   690   --{* cf. 15.25.1 *}
   711   Ass:	"\<lbrakk>G\<turnstile>Norm s0 \<midarrow>va=\<succ>(w,f)\<rightarrow> s1;
   691   Ass:	"\<lbrakk>G\<turnstile>Norm s0 \<midarrow>va=\<succ>(w,f)\<rightarrow> s1;
   712           G\<turnstile>     s1 \<midarrow>e-\<succ>v  \<rightarrow> s2\<rbrakk> \<Longrightarrow>
   692           G\<turnstile>     s1 \<midarrow>e-\<succ>v  \<rightarrow> s2\<rbrakk> \<Longrightarrow>
   713 				   G\<turnstile>Norm s0 \<midarrow>va:=e-\<succ>v\<rightarrow> assign f v s2"
   693 				   G\<turnstile>Norm s0 \<midarrow>va:=e-\<succ>v\<rightarrow> assign f v s2"
   714 
   694 
   715   (* cf. 15.24 *)
   695   --{* cf. 15.24 *}
   716   Cond:	"\<lbrakk>G\<turnstile>Norm s0 \<midarrow>e0-\<succ>b\<rightarrow> s1;
   696   Cond:	"\<lbrakk>G\<turnstile>Norm s0 \<midarrow>e0-\<succ>b\<rightarrow> s1;
   717           G\<turnstile>     s1 \<midarrow>(if the_Bool b then e1 else e2)-\<succ>v\<rightarrow> s2\<rbrakk> \<Longrightarrow>
   697           G\<turnstile>     s1 \<midarrow>(if the_Bool b then e1 else e2)-\<succ>v\<rightarrow> s2\<rbrakk> \<Longrightarrow>
   718 			    G\<turnstile>Norm s0 \<midarrow>e0 ? e1 : e2-\<succ>v\<rightarrow> s2"
   698 			    G\<turnstile>Norm s0 \<midarrow>e0 ? e1 : e2-\<succ>v\<rightarrow> s2"
   719 
   699 
   720 
   700 
   721   (* cf. 15.11.4.1, 15.11.4.2, 15.11.4.4, 15.11.4.5 *)
   701 -- {* The interplay of  @{term Call}, @{term Methd} and @{term Body}:
       
   702       Method invocation is split up into these three rules:
       
   703       \begin{itemize}
       
   704       \item [@{term Call}] Calculates the target address and evaluates the
       
   705                            arguments of the method, and then performs dynamic
       
   706                            or static lookup of the method, corresponding to the
       
   707                            call mode. Then the @{term Methd} rule is evaluated
       
   708                            on the calculated declaration class of the method
       
   709                            invocation.
       
   710       \item [@{term Methd}] A syntactic bridge for the folded method body.
       
   711                             It is used by the axiomatic semantics to add the
       
   712                             proper hypothesis for recursive calls of the method.
       
   713       \item [@{term Body}] An extra syntactic entity for the unfolded method
       
   714                            body was introduced to properly trigger class 
       
   715                            initialisation. Without class initialisation we 
       
   716                            could just evaluate the body statement. 
       
   717       \end{itemize}
       
   718    *}
       
   719   --{* cf. 15.11.4.1, 15.11.4.2, 15.11.4.4, 15.11.4.5 *}
   722   Call:	
   720   Call:	
   723   "\<lbrakk>G\<turnstile>Norm s0 \<midarrow>e-\<succ>a'\<rightarrow> s1; G\<turnstile>s1 \<midarrow>args\<doteq>\<succ>vs\<rightarrow> s2;
   721   "\<lbrakk>G\<turnstile>Norm s0 \<midarrow>e-\<succ>a'\<rightarrow> s1; G\<turnstile>s1 \<midarrow>args\<doteq>\<succ>vs\<rightarrow> s2;
   724     D = invocation_declclass G mode (store s2) a' statT \<lparr>name=mn,parTs=pTs\<rparr>;
   722     D = invocation_declclass G mode (store s2) a' statT \<lparr>name=mn,parTs=pTs\<rparr>;
   725     s3=init_lvars G D \<lparr>name=mn,parTs=pTs\<rparr> mode a' vs s2;
   723     s3=init_lvars G D \<lparr>name=mn,parTs=pTs\<rparr> mode a' vs s2;
   726     s3' = check_method_access G accC statT mode \<lparr>name=mn,parTs=pTs\<rparr> a' s3;
   724     s3' = check_method_access G accC statT mode \<lparr>name=mn,parTs=pTs\<rparr> a' s3;
   727     G\<turnstile>s3' \<midarrow>Methd D \<lparr>name=mn,parTs=pTs\<rparr>-\<succ>v\<rightarrow> s4\<rbrakk>
   725     G\<turnstile>s3' \<midarrow>Methd D \<lparr>name=mn,parTs=pTs\<rparr>-\<succ>v\<rightarrow> s4\<rbrakk>
   728    \<Longrightarrow>
   726    \<Longrightarrow>
   729        G\<turnstile>Norm s0 \<midarrow>{accC,statT,mode}e\<cdot>mn({pTs}args)-\<succ>v\<rightarrow> (restore_lvars s2 s4)"
   727        G\<turnstile>Norm s0 \<midarrow>{accC,statT,mode}e\<cdot>mn({pTs}args)-\<succ>v\<rightarrow> (restore_lvars s2 s4)"
   730 (* The accessibility check is after init_lvars, to keep it simple. Init_lvars 
   728 --{* The accessibility check is after @{term init_lvars}, to keep it simple. 
   731    already tests for the absence of a null-pointer reference in case of an
   729    @{term init_lvars} already tests for the absence of a null-pointer 
   732    instance method invocation
   730    reference in case of an instance method invocation.
   733 *)
   731 *}
   734 
   732 
   735   Methd:	"\<lbrakk>G\<turnstile>Norm s0 \<midarrow>body G D sig-\<succ>v\<rightarrow> s1\<rbrakk> \<Longrightarrow>
   733   Methd:	"\<lbrakk>G\<turnstile>Norm s0 \<midarrow>body G D sig-\<succ>v\<rightarrow> s1\<rbrakk> \<Longrightarrow>
   736 				G\<turnstile>Norm s0 \<midarrow>Methd D sig-\<succ>v\<rightarrow> s1"
   734 				G\<turnstile>Norm s0 \<midarrow>Methd D sig-\<succ>v\<rightarrow> s1"
   737   (* The local variables l are just a dummy here. The are only used by
   735   
   738      the smallstep semantics *)
   736   Body:	"\<lbrakk>G\<turnstile>Norm s0 \<midarrow>Init D\<rightarrow> s1; G\<turnstile>s1 \<midarrow>c\<rightarrow> s2; 
   739   (* cf. 14.15, 12.4.1 *)
   737           s3 = (if (\<exists> l. abrupt s2 = Some (Jump (Break l)) \<or>  
   740   Body:	"\<lbrakk>G\<turnstile>Norm s0 \<midarrow>Init D\<rightarrow> s1; G\<turnstile>s1 \<midarrow>c\<rightarrow> s2\<rbrakk> \<Longrightarrow>
   738                          abrupt s2 = Some (Jump (Cont l)))
   741            G\<turnstile>Norm s0 \<midarrow>Body D c
   739                   then abupd (\<lambda> x. Some (Error CrossMethodJump)) s2 
   742             -\<succ>the (locals (store s2) Result)\<rightarrow>abupd (absorb Ret) s2"
   740                   else s2)\<rbrakk> \<Longrightarrow>
   743   (* The local variables l are just a dummy here. The are only used by
   741            G\<turnstile>Norm s0 \<midarrow>Body D c-\<succ>the (locals (store s2) Result)
   744      the smallstep semantics *)
   742               \<rightarrow>abupd (absorb Ret) s3"
   745 (* evaluation of variables *)
   743   --{* cf. 14.15, 12.4.1 *}
   746 
   744   --{* We filter out a break/continue in @{term s2}, so that we can proof 
   747   (* cf. 15.13.1, 15.7.2 *)
   745      definite assignment
       
   746      correct, without the need of conformance of the state. By this the
       
   747      different parts of the typesafety proof can be disentangled a little. *}
       
   748 
       
   749 --{* evaluation of variables *}
       
   750 
       
   751   --{* cf. 15.13.1, 15.7.2 *}
   748   LVar:	"G\<turnstile>Norm s \<midarrow>LVar vn=\<succ>lvar vn s\<rightarrow> Norm s"
   752   LVar:	"G\<turnstile>Norm s \<midarrow>LVar vn=\<succ>lvar vn s\<rightarrow> Norm s"
   749 
   753 
   750   (* cf. 15.10.1, 12.4.1 *)
   754   --{* cf. 15.10.1, 12.4.1 *}
   751   FVar:	"\<lbrakk>G\<turnstile>Norm s0 \<midarrow>Init statDeclC\<rightarrow> s1; G\<turnstile>s1 \<midarrow>e-\<succ>a\<rightarrow> s2;
   755   FVar:	"\<lbrakk>G\<turnstile>Norm s0 \<midarrow>Init statDeclC\<rightarrow> s1; G\<turnstile>s1 \<midarrow>e-\<succ>a\<rightarrow> s2;
   752 	  (v,s2') = fvar statDeclC stat fn a s2;
   756 	  (v,s2') = fvar statDeclC stat fn a s2;
   753           s3 = check_field_access G accC statDeclC fn stat a s2' \<rbrakk> \<Longrightarrow>
   757           s3 = check_field_access G accC statDeclC fn stat a s2' \<rbrakk> \<Longrightarrow>
   754 	  G\<turnstile>Norm s0 \<midarrow>{accC,statDeclC,stat}e..fn=\<succ>v\<rightarrow> s3"
   758 	  G\<turnstile>Norm s0 \<midarrow>{accC,statDeclC,stat}e..fn=\<succ>v\<rightarrow> s3"
   755  (* The accessibility check is after fvar, to keep it simple. Fvar already
   759  --{* The accessibility check is after @{term fvar}, to keep it simple. 
   756     tests for the absence of a null-pointer reference in case of an instance
   760     @{term fvar} already tests for the absence of a null-pointer reference 
   757     field
   761     in case of an instance field
   758   *)
   762   *}
   759 
   763 
   760   (* cf. 15.12.1, 15.25.1 *)
   764   --{* cf. 15.12.1, 15.25.1 *}
   761   AVar:	"\<lbrakk>G\<turnstile> Norm s0 \<midarrow>e1-\<succ>a\<rightarrow> s1; G\<turnstile>s1 \<midarrow>e2-\<succ>i\<rightarrow> s2;
   765   AVar:	"\<lbrakk>G\<turnstile> Norm s0 \<midarrow>e1-\<succ>a\<rightarrow> s1; G\<turnstile>s1 \<midarrow>e2-\<succ>i\<rightarrow> s2;
   762 	  (v,s2') = avar G i a s2\<rbrakk> \<Longrightarrow>
   766 	  (v,s2') = avar G i a s2\<rbrakk> \<Longrightarrow>
   763 	              G\<turnstile>Norm s0 \<midarrow>e1.[e2]=\<succ>v\<rightarrow> s2'"
   767 	              G\<turnstile>Norm s0 \<midarrow>e1.[e2]=\<succ>v\<rightarrow> s2'"
   764 
   768 
   765 
   769 
   766 (* evaluation of expression lists *)
   770 --{* evaluation of expression lists *}
   767 
   771 
   768   (* cf. 15.11.4.2 *)
   772   --{* cf. 15.11.4.2 *}
   769   Nil:
   773   Nil:
   770 				    "G\<turnstile>Norm s0 \<midarrow>[]\<doteq>\<succ>[]\<rightarrow> Norm s0"
   774 				    "G\<turnstile>Norm s0 \<midarrow>[]\<doteq>\<succ>[]\<rightarrow> Norm s0"
   771 
   775 
   772   (* cf. 15.6.4 *)
   776   --{* cf. 15.6.4 *}
   773   Cons:	"\<lbrakk>G\<turnstile>Norm s0 \<midarrow>e -\<succ> v \<rightarrow> s1;
   777   Cons:	"\<lbrakk>G\<turnstile>Norm s0 \<midarrow>e -\<succ> v \<rightarrow> s1;
   774           G\<turnstile>     s1 \<midarrow>es\<doteq>\<succ>vs\<rightarrow> s2\<rbrakk> \<Longrightarrow>
   778           G\<turnstile>     s1 \<midarrow>es\<doteq>\<succ>vs\<rightarrow> s2\<rbrakk> \<Longrightarrow>
   775 				   G\<turnstile>Norm s0 \<midarrow>e#es\<doteq>\<succ>v#vs\<rightarrow> s2"
   779 				   G\<turnstile>Norm s0 \<midarrow>e#es\<doteq>\<succ>v#vs\<rightarrow> s2"
   776 
   780 
   777 (* Rearrangement of premisses:
   781 (* Rearrangement of premisses:
   778 [0,1(Abrupt),2(Skip),8(Do),4(Lab),30(Nil),31(Cons),27(LVar),17(Cast),18(Inst),
   782 [0,1(Abrupt),2(Skip),8(Jmp),4(Lab),30(Nil),31(Cons),27(LVar),17(Cast),18(Inst),
   779  17(Lit),18(UnOp),19(BinOp),20(Super),21(Acc),3(Expr),5(Comp),25(Methd),26(Body),23(Cond),6(If),
   783  17(Lit),18(UnOp),19(BinOp),20(Super),21(Acc),3(Expr),5(Comp),25(Methd),26(Body),23(Cond),6(If),
   780  7(Loop),11(Fin),9(Throw),13(NewC),14(NewA),12(Init),22(Ass),10(Try),28(FVar),
   784  7(Loop),11(Fin),9(Throw),13(NewC),14(NewA),12(Init),22(Ass),10(Try),28(FVar),
   781  29(AVar),24(Call)]
   785  29(AVar),24(Call)]
   782 *)
   786 *)
       
   787 
   783 ML {*
   788 ML {*
   784 bind_thm ("eval_induct_", rearrange_prems 
   789 bind_thm ("eval_induct_", rearrange_prems 
   785 [0,1,2,8,4,30,31,27,15,16,
   790 [0,1,2,8,4,30,31,27,15,16,
   786  17,18,19,20,21,3,5,25,26,23,6,
   791  17,18,19,20,21,3,5,25,26,23,6,
   787  7,11,9,13,14,12,22,10,28,
   792  7,11,9,13,14,12,22,10,28,
   805   "G\<turnstile>(Some xc,s) \<midarrow>halloc oi\<succ>a\<rightarrow> s'"
   810   "G\<turnstile>(Some xc,s) \<midarrow>halloc oi\<succ>a\<rightarrow> s'"
   806   "G\<turnstile>(Norm    s) \<midarrow>halloc oi\<succ>a\<rightarrow> s'"
   811   "G\<turnstile>(Norm    s) \<midarrow>halloc oi\<succ>a\<rightarrow> s'"
   807 
   812 
   808 inductive_cases sxalloc_elim_cases:
   813 inductive_cases sxalloc_elim_cases:
   809  	"G\<turnstile> Norm                 s  \<midarrow>sxalloc\<rightarrow> s'"
   814  	"G\<turnstile> Norm                 s  \<midarrow>sxalloc\<rightarrow> s'"
   810  	"G\<turnstile>(Some (Xcpt (Loc a )),s) \<midarrow>sxalloc\<rightarrow> s'"
   815         "G\<turnstile>(Some (Jump j),s) \<midarrow>sxalloc\<rightarrow> s'"
       
   816  	"G\<turnstile>(Some (Error e),s) \<midarrow>sxalloc\<rightarrow> s'"
       
   817         "G\<turnstile>(Some (Xcpt (Loc a )),s) \<midarrow>sxalloc\<rightarrow> s'"
   811  	"G\<turnstile>(Some (Xcpt (Std xn)),s) \<midarrow>sxalloc\<rightarrow> s'"
   818  	"G\<turnstile>(Some (Xcpt (Std xn)),s) \<midarrow>sxalloc\<rightarrow> s'"
   812 inductive_cases sxalloc_cases: "G\<turnstile>s \<midarrow>sxalloc\<rightarrow> s'"
   819 inductive_cases sxalloc_cases: "G\<turnstile>s \<midarrow>sxalloc\<rightarrow> s'"
   813 
   820 
   814 lemma sxalloc_elim_cases2: "\<lbrakk>G\<turnstile>s \<midarrow>sxalloc\<rightarrow> s';  
   821 lemma sxalloc_elim_cases2: "\<lbrakk>G\<turnstile>s \<midarrow>sxalloc\<rightarrow> s';  
   815        \<And>s.   \<lbrakk>s' = Norm s\<rbrakk> \<Longrightarrow> P;  
   822        \<And>s.   \<lbrakk>s' = Norm s\<rbrakk> \<Longrightarrow> P;  
       
   823        \<And>j s. \<lbrakk>s' = (Some (Jump j),s)\<rbrakk> \<Longrightarrow> P;
       
   824        \<And>e s. \<lbrakk>s' = (Some (Error e),s)\<rbrakk> \<Longrightarrow> P;
   816        \<And>a s. \<lbrakk>s' = (Some (Xcpt (Loc a)),s)\<rbrakk> \<Longrightarrow> P  
   825        \<And>a s. \<lbrakk>s' = (Some (Xcpt (Loc a)),s)\<rbrakk> \<Longrightarrow> P  
   817       \<rbrakk> \<Longrightarrow> P"
   826       \<rbrakk> \<Longrightarrow> P"
   818 apply cut_tac 
   827 apply cut_tac 
   819 apply (erule sxalloc_cases)
   828 apply (erule sxalloc_cases)
   820 apply blast+
   829 apply blast+
   825 ML_setup {*
   834 ML_setup {*
   826 simpset_ref() := simpset() delloop "split_all_tac"
   835 simpset_ref() := simpset() delloop "split_all_tac"
   827 *}
   836 *}
   828 inductive_cases eval_cases: "G\<turnstile>s \<midarrow>t\<succ>\<rightarrow> vs'"
   837 inductive_cases eval_cases: "G\<turnstile>s \<midarrow>t\<succ>\<rightarrow> vs'"
   829 
   838 
   830 inductive_cases eval_elim_cases:
   839 inductive_cases eval_elim_cases [cases set]:
   831         "G\<turnstile>(Some xc,s) \<midarrow>t                              \<succ>\<rightarrow> vs'"
   840         "G\<turnstile>(Some xc,s) \<midarrow>t                              \<succ>\<rightarrow> vs'"
   832 	"G\<turnstile>Norm s \<midarrow>In1r Skip                           \<succ>\<rightarrow> xs'"
   841 	"G\<turnstile>Norm s \<midarrow>In1r Skip                           \<succ>\<rightarrow> xs'"
   833         "G\<turnstile>Norm s \<midarrow>In1r (Do j)                         \<succ>\<rightarrow> xs'"
   842         "G\<turnstile>Norm s \<midarrow>In1r (Jmp j)                        \<succ>\<rightarrow> xs'"
   834         "G\<turnstile>Norm s \<midarrow>In1r (l\<bullet> c)                         \<succ>\<rightarrow> xs'"
   843         "G\<turnstile>Norm s \<midarrow>In1r (l\<bullet> c)                         \<succ>\<rightarrow> xs'"
   835 	"G\<turnstile>Norm s \<midarrow>In3  ([])                           \<succ>\<rightarrow> vs'"
   844 	"G\<turnstile>Norm s \<midarrow>In3  ([])                           \<succ>\<rightarrow> vs'"
   836 	"G\<turnstile>Norm s \<midarrow>In3  (e#es)                         \<succ>\<rightarrow> vs'"
   845 	"G\<turnstile>Norm s \<midarrow>In3  (e#es)                         \<succ>\<rightarrow> vs'"
   837 	"G\<turnstile>Norm s \<midarrow>In1l (Lit w)                        \<succ>\<rightarrow> vs'"
   846 	"G\<turnstile>Norm s \<midarrow>In1l (Lit w)                        \<succ>\<rightarrow> vs'"
   838         "G\<turnstile>Norm s \<midarrow>In1l (UnOp unop e)                  \<succ>\<rightarrow> vs'"
   847         "G\<turnstile>Norm s \<midarrow>In1l (UnOp unop e)                  \<succ>\<rightarrow> vs'"
   880 apply (induct_tac "t")
   889 apply (induct_tac "t")
   881 apply (induct_tac "a")
   890 apply (induct_tac "a")
   882 apply auto
   891 apply auto
   883 done
   892 done
   884 
   893 
   885 
   894 text {* The following simplification procedures set up the proper injections of
       
   895  terms and their corresponding values in the evaluation relation:
       
   896  E.g. an expression 
       
   897  (injection @{term In1l} into terms) always evaluates to ordinary values 
       
   898  (injection @{term In1} into generalised values @{term vals}). 
       
   899 *}
   886 ML_setup {*
   900 ML_setup {*
   887 fun eval_fun nam inj rhs =
   901 fun eval_fun nam inj rhs =
   888 let
   902 let
   889   val name = "eval_" ^ nam ^ "_eq"
   903   val name = "eval_" ^ nam ^ "_eq"
   890   val lhs = "G\<turnstile>s \<midarrow>" ^ inj ^ " t\<succ>\<rightarrow> (w, s')"
   904   val lhs = "G\<turnstile>s \<midarrow>" ^ inj ^ " t\<succ>\<rightarrow> (w, s')"
  1130 apply clarsimp+
  1144 apply clarsimp+
  1131 apply (erule eval.Methd)
  1145 apply (erule eval.Methd)
  1132 apply (drule eval_abrupt_lemma)
  1146 apply (drule eval_abrupt_lemma)
  1133 apply force
  1147 apply force
  1134 done
  1148 done
       
  1149 
       
  1150 lemma eval_Body: "\<lbrakk>G\<turnstile>Norm s0 \<midarrow>Init D\<rightarrow> s1; G\<turnstile>s1 \<midarrow>c\<rightarrow> s2;
       
  1151                    res=the (locals (store s2) Result);
       
  1152                    s3 = (if (\<exists> l. abrupt s2 = Some (Jump (Break l)) \<or>
       
  1153                                   abrupt s2 = Some (Jump (Cont l))) 
       
  1154                    then abupd (\<lambda> x. Some (Error CrossMethodJump)) s2 
       
  1155                    else s2);
       
  1156                    s4=abupd (absorb Ret) s3\<rbrakk> \<Longrightarrow>
       
  1157  G\<turnstile>Norm s0 \<midarrow>Body D c-\<succ>res\<rightarrow>s4"
       
  1158 by (auto elim: eval.Body)
  1135 
  1159 
  1136 lemma eval_binop_arg2_indep:
  1160 lemma eval_binop_arg2_indep:
  1137 "\<not> need_second_arg binop v1 \<Longrightarrow> eval_binop binop v1 x = eval_binop binop v1 y"
  1161 "\<not> need_second_arg binop v1 \<Longrightarrow> eval_binop binop v1 x = eval_binop binop v1 y"
  1138 by (cases binop)
  1162 by (cases binop)
  1139    (simp_all add: need_second_arg_def)
  1163    (simp_all add: need_second_arg_def)
  1193 done
  1217 done
  1194 
  1218 
  1195 lemma split_pairD: "(x,y) = p \<Longrightarrow> x = fst p & y = snd p"
  1219 lemma split_pairD: "(x,y) = p \<Longrightarrow> x = fst p & y = snd p"
  1196 by auto
  1220 by auto
  1197 
  1221 
  1198 lemma eval_Body: "\<lbrakk>G\<turnstile>Norm s0 \<midarrow>Init D\<rightarrow> s1; G\<turnstile>s1 \<midarrow>c\<rightarrow> s2;
  1222 
  1199                    res=the (locals (store s2) Result);
       
  1200                    s3=abupd (absorb Ret) s2\<rbrakk> \<Longrightarrow>
       
  1201  G\<turnstile>Norm s0 \<midarrow>Body D c-\<succ>res\<rightarrow>s3"
       
  1202 by (auto elim: eval.Body)
       
  1203 
  1223 
  1204 lemma unique_eval [rule_format (no_asm)]: 
  1224 lemma unique_eval [rule_format (no_asm)]: 
  1205   "G\<turnstile>s \<midarrow>t\<succ>\<rightarrow> ws \<Longrightarrow> (\<forall>ws'. G\<turnstile>s \<midarrow>t\<succ>\<rightarrow> ws' \<longrightarrow> ws' = ws)"
  1225   "G\<turnstile>s \<midarrow>t\<succ>\<rightarrow> ws \<Longrightarrow> (\<forall>ws'. G\<turnstile>s \<midarrow>t\<succ>\<rightarrow> ws' \<longrightarrow> ws' = ws)"
  1206 apply (case_tac "ws")
  1226 apply (case_tac "ws")
  1207 apply hypsubst
  1227 apply hypsubst