Theory BigStep

chapter ‹Generated by Lem from semantics/alt_semantics/bigStep.lem›.›

theory "BigStep" 

imports
  Main
  "HOL-Library.Datatype_Records"
  "LEM.Lem_pervasives_extra"
  "Lib"
  "Namespace"
  "Ast"
  "SemanticPrimitives"
  "Ffi"
  "SmallStep"

begin 

― ‹open import Pervasives_extra›
― ‹open import Lib›
― ‹open import Namespace›
― ‹open import Ast›
― ‹open import SemanticPrimitives›
― ‹open import Ffi›

― ‹ To get the definition of expression divergence to use in defining definition
 * divergence ›
― ‹open import SmallStep›

― ‹ ------------------------ Big step semantics -------------------------- ›

― ‹ If the first argument is true, the big step semantics counts down how many
   functions applications have happened, and raises an exception when the counter
   runs out. ›

inductive
evaluate_match  :: " bool (v)sem_env  'ffi state  v (pat*exp0)list  v  'ffi state*((v),(v))result  bool "  
      and
evaluate_list  :: " bool (v)sem_env  'ffi state (exp0)list  'ffi state*(((v)list),(v))result  bool "  
      and
evaluate  :: " bool (v)sem_env  'ffi state  exp0  'ffi state*((v),(v))result  bool "  where

"lit" : "  ck env l s.

evaluate ck env s (Lit l) (s, Rval (Litv l))"

|

"raise1" : "  ck env e s1 s2 v1.
evaluate ck s1 env e (s2, Rval v1)
==>
evaluate ck s1 env (Raise e) (s2, Rerr (Rraise v1))"

|

"raise2" : "  ck env e s1 s2 err.
evaluate ck s1 env e (s2, Rerr err)
==>
evaluate ck s1 env (Raise e) (s2, Rerr err)"

|

"handle1" : "  ck s1 s2 env e v1 pes.
evaluate ck s1 env e (s2, Rval v1)
==>
evaluate ck s1 env (Handle e pes) (s2, Rval v1)"

|

"handle2" : "  ck s1 s2 env e pes v1 bv.
evaluate ck env s1 e (s2, Rerr (Rraise v1)) 
evaluate_match ck env s2 v1 pes v1 bv
==>
evaluate ck env s1 (Handle e pes) bv "

|

"handle3" : "  ck s1 s2 env e pes a.
evaluate ck env s1 e (s2, Rerr (Rabort a))
==>
evaluate ck env s1 (Handle e pes) (s2, Rerr (Rabort a))"

|

"con1" : "  ck env cn es vs s s' v1.
do_con_check(c   env) cn (List.length es) 
((build_conv(c   env) cn (List.rev vs) = Some v1) 
evaluate_list ck env s (List.rev es) (s', Rval vs))
==>
evaluate ck env s (Con cn es) (s', Rval v1)"

|

"con2" : "  ck env cn es s.
¬ (do_con_check(c   env) cn (List.length es))
==>
evaluate ck env s (Con cn es) (s, Rerr (Rabort Rtype_error))"

|

"con3" : "  ck env cn es err s s'.
do_con_check(c   env) cn (List.length es) 
evaluate_list ck env s (List.rev es) (s', Rerr err)
==>
evaluate ck env s (Con cn es) (s', Rerr err)"

|

"var1" : "  ck env n v1 s.
nsLookup(v   env) n = Some v1
==>
evaluate ck env s (Var n) (s, Rval v1)"

|

"var2" : "  ck env n s.
nsLookup(v   env) n = None
==>
evaluate ck env s (Var n) (s, Rerr (Rabort Rtype_error))"

|

"fn" : "  ck env n e s.

evaluate ck env s (Fun n e) (s, Rval (Closure env n e))"

|

"app1" : "  ck env es vs env' e bv s1 s2.
evaluate_list ck env s1 (List.rev es) (s2, Rval vs) 
((do_opapp (List.rev vs) = Some (env', e)) 
((ck  ¬ ((clock   s2) =(( 0 :: nat)))) 
evaluate ck env' (if ck then ( s2 (| clock := ((clock   s2) -( 1 :: nat)) |)) else s2) e bv))
==>
evaluate ck env s1 (App Opapp es) bv "

|

"app2" : "  ck env es vs env' e s1 s2.
evaluate_list ck env s1 (List.rev es) (s2, Rval vs) 
((do_opapp (List.rev vs) = Some (env', e)) 
(((clock   s2) =( 0 :: nat)) 
ck))
==>
evaluate ck env s1 (App Opapp es) (s2, Rerr (Rabort Rtimeout_error))"

|

"app3" : "  ck env es vs s1 s2.
evaluate_list ck env s1 (List.rev es) (s2, Rval vs) 
(do_opapp (List.rev vs) = None)
==>
evaluate ck env s1 (App Opapp es) (s2, Rerr (Rabort Rtype_error))"

|

"app4" : "  ck env op0 es vs res s1 s2 refs' ffi'.
evaluate_list ck env s1 (List.rev es) (s2, Rval vs) 
((do_app ((refs   s2),(ffi   s2)) op0 (List.rev vs) = Some ((refs',ffi'), res)) 
(op0  Opapp))
==>
evaluate ck env s1 (App op0 es) (( s2 (| refs := refs', ffi :=ffi' |)), res)"

|

"app5" : "  ck env op0 es vs s1 s2.
evaluate_list ck env s1 (List.rev es) (s2, Rval vs) 
((do_app ((refs   s2),(ffi   s2)) op0 (List.rev vs) = None) 
(op0  Opapp))
==>
evaluate ck env s1 (App op0 es) (s2, Rerr (Rabort Rtype_error))"

|

"app6" : "  ck env op0 es err s1 s2.
evaluate_list ck env s1 (List.rev es) (s2, Rerr err)
==>
evaluate ck env s1 (App op0 es) (s2, Rerr err)"

|

"log1" : "  ck env op0 e1 e2 v1 e' bv s1 s2.
evaluate ck env s1 e1 (s2, Rval v1) 
((do_log op0 v1 e2 = Some (Exp e')) 
evaluate ck env s2 e' bv)
==>
evaluate ck env s1 (Log op0 e1 e2) bv "

|

"log2" : "  ck env op0 e1 e2 v1 bv s1 s2.
evaluate ck env s1 e1 (s2, Rval v1) 
(do_log op0 v1 e2 = Some (Val bv))
==>
evaluate ck env s1 (Log op0 e1 e2) (s2, Rval bv)"

|

"log3" : "  ck env op0 e1 e2 v1 s1 s2.
evaluate ck env s1 e1 (s2, Rval v1) 
(do_log op0 v1 e2 = None)
==>
evaluate ck env s1 (Log op0 e1 e2) (s2, Rerr (Rabort Rtype_error))"

|

"log4" : "  ck env op0 e1 e2 err s s'.
evaluate ck env s e1 (s', Rerr err)
==>
evaluate ck env s (Log op0 e1 e2) (s', Rerr err)"

|

"if1" : "  ck env e1 e2 e3 v1 e' bv s1 s2.
evaluate ck env s1 e1 (s2, Rval v1) 
((do_if v1 e2 e3 = Some e') 
evaluate ck env s2 e' bv)
==>
evaluate ck env s1 (If e1 e2 e3) bv "

|

"if2" : "  ck env e1 e2 e3 v1 s1 s2.
evaluate ck env s1 e1 (s2, Rval v1) 
(do_if v1 e2 e3 = None)
==>
evaluate ck env s1 (If e1 e2 e3) (s2, Rerr (Rabort Rtype_error))"

|

"if3" : "  ck env e1 e2 e3 err s s'.
evaluate ck env s e1 (s', Rerr err)
==>
evaluate ck env s (If e1 e2 e3) (s', Rerr err)"

|

"mat1" : "  ck env e pes v1 bv s1 s2.
evaluate ck env s1 e (s2, Rval v1) 
evaluate_match ck env s2 v1 pes (Conv (Some ((''Bind''), TypeExn (Short (''Bind'')))) []) bv
==>
evaluate ck env s1 (Mat e pes) bv "

|

"mat2" : "  ck env e pes err s s'.
evaluate ck env s e (s', Rerr err)
==>
evaluate ck env s (Mat e pes) (s', Rerr err)"

|

"let1" : "  ck env n e1 e2 v1 bv s1 s2.
evaluate ck env s1 e1 (s2, Rval v1) 
evaluate ck ( env (| v := (nsOptBind n v1(v   env)) |)) s2 e2 bv
==>
evaluate ck env s1 (Let n e1 e2) bv "

|

"let2" : "  ck env n e1 e2 err s s'.
evaluate ck env s e1 (s', Rerr err)
==>
evaluate ck env s (Let n e1 e2) (s', Rerr err)"

|

"letrec1" : "  ck env funs e bv s.
Lem_list.allDistinct (List.map ( λx .  
  (case  x of (x,y,z) => x )) funs) 
evaluate ck ( env (| v := (build_rec_env funs env(v   env)) |)) s e bv
==>
evaluate ck env s (Letrec funs e) bv "

|

"letrec2" : "  ck env funs e s.
¬ (Lem_list.allDistinct (List.map ( λx .  
  (case  x of (x,y,z) => x )) funs))
==>
evaluate ck env s (Letrec funs e) (s, Rerr (Rabort Rtype_error))"

|

"tannot" : "  ck env e t0 s bv.
evaluate ck env s e bv
==>
evaluate ck env s (Tannot e t0) bv "

|

"locannot" : "  ck env e l s bv.
evaluate ck env s e bv
==>
evaluate ck env s (Lannot e l) bv "

|

"empty" : "  ck env s.

evaluate_list ck env s [] (s, Rval [])"

|

"cons1" : "  ck env e es v1 vs s1 s2 s3.
evaluate ck env s1 e (s2, Rval v1) 
evaluate_list ck env s2 es (s3, Rval vs)
==>
evaluate_list ck env s1 (e # es) (s3, Rval (v1 # vs))"

|

"cons2" : "  ck env e es err s s'.
evaluate ck env s e (s', Rerr err)
==>
evaluate_list ck env s (e # es) (s', Rerr err)"

|

"cons3" : "  ck env e es v1 err s1 s2 s3.
evaluate ck env s1 e (s2, Rval v1) 
evaluate_list ck env s2 es (s3, Rerr err)
==>
evaluate_list ck env s1 (e # es) (s3, Rerr err)"

|

"mat_empty" : "  ck env v1 err_v s.

evaluate_match ck env s v1 [] err_v (s, Rerr (Rraise err_v))"

|

"mat_cons1" : "  ck env env' v1 p pes e bv err_v s.
Lem_list.allDistinct (pat_bindings p []) 
((pmatch(c   env)(refs   s) p v1 [] = Match env') 
evaluate ck ( env (| v := (nsAppend (alist_to_ns env')(v   env)) |)) s e bv)
==>
evaluate_match ck env s v1 ((p,e)# pes) err_v bv "

|

"mat_cons2" : "  ck env v1 p e pes bv s err_v.
Lem_list.allDistinct (pat_bindings p []) 
((pmatch(c   env)(refs   s) p v1 [] = No_match) 
evaluate_match ck env s v1 pes err_v bv)
==>
evaluate_match ck env s v1 ((p,e)# pes) err_v bv "

|

"mat_cons3" : "  ck env v1 p e pes s err_v.
pmatch(c   env)(refs   s) p v1 [] = Match_type_error
==>
evaluate_match ck env s v1 ((p,e)# pes) err_v (s, Rerr (Rabort Rtype_error))"

|

"mat_cons4" : "  ck env v1 p e pes s err_v.
¬ (Lem_list.allDistinct (pat_bindings p []))
==>
evaluate_match ck env s v1 ((p,e)# pes) err_v (s, Rerr (Rabort Rtype_error))"

― ‹ The set tid_or_exn part of the state tracks all of the types and exceptions
 * that have been declared ›
inductive
evaluate_dec  :: " bool (modN)list (v)sem_env  'ffi state  dec  'ffi state*(((v)sem_env),(v))result  bool "  where

"dlet1" : "  ck mn env p e v1 env' s1 s2 locs.
evaluate ck env s1 e (s2, Rval v1) 
(Lem_list.allDistinct (pat_bindings p []) 
(pmatch(c   env)(refs   s2) p v1 [] = Match env'))
==>
evaluate_dec ck mn env s1 (Dlet locs p e) (s2, Rval (| v = (alist_to_ns env'), c = nsEmpty |))"

|

"dlet2" : "  ck mn env p e v1 s1 s2 locs.
evaluate ck env s1 e (s2, Rval v1) 
(Lem_list.allDistinct (pat_bindings p []) 
(pmatch(c   env)(refs   s2) p v1 [] = No_match))
==>
evaluate_dec ck mn env s1 (Dlet locs p e) (s2, Rerr (Rraise Bindv))"

|

"dlet3" : "  ck mn env p e v1 s1 s2 locs.
evaluate ck env s1 e (s2, Rval v1) 
(Lem_list.allDistinct (pat_bindings p []) 
(pmatch(c   env)(refs   s2) p v1 [] = Match_type_error))
==>
evaluate_dec ck mn env s1 (Dlet locs p e) (s2, Rerr (Rabort Rtype_error))"

|

"dlet4" : "  ck mn env p e s locs.
¬ (Lem_list.allDistinct (pat_bindings p []))
==>
evaluate_dec ck mn env s (Dlet locs p e) (s, Rerr (Rabort Rtype_error))"

|

"dlet5" : "  ck mn env p e err s s' locs.
evaluate ck env s e (s', Rerr err) 
Lem_list.allDistinct (pat_bindings p [])
==>
evaluate_dec ck mn env s (Dlet locs p e) (s', Rerr err)"

|

"dletrec1" : "  ck mn env funs s locs.
Lem_list.allDistinct (List.map ( λx .  
  (case  x of (x,y,z) => x )) funs)
==>
evaluate_dec ck mn env s (Dletrec locs funs) (s, Rval (| v = (build_rec_env funs env nsEmpty), c = nsEmpty |))"

|

"dletrec2" : "  ck mn env funs s locs.
¬ (Lem_list.allDistinct (List.map ( λx .  
  (case  x of (x,y,z) => x )) funs))
==>
evaluate_dec ck mn env s (Dletrec locs funs) (s, Rerr (Rabort Rtype_error))"

|

"dtype1" : "  ck mn env tds s new_tdecs locs.
check_dup_ctors tds 
((new_tdecs = type_defs_to_new_tdecs mn tds) 
(disjnt new_tdecs(defined_types   s) 
Lem_list.allDistinct (List.map ( λx .  
  (case  x of (tvs,tn,ctors) => tn )) tds)))
==>
evaluate_dec ck mn env s (Dtype locs tds) (( s (| defined_types := (new_tdecs (defined_types   s)) |)), Rval (| v = nsEmpty, c = (build_tdefs mn tds) |))"

|

"dtype2" : "  ck mn env tds s locs.
¬ (check_dup_ctors tds) 
(¬ (disjnt (type_defs_to_new_tdecs mn tds)(defined_types   s)) 
¬ (Lem_list.allDistinct (List.map ( λx .  
  (case  x of (tvs,tn,ctors) => tn )) tds)))
==>
evaluate_dec ck mn env s (Dtype locs tds) (s, Rerr (Rabort Rtype_error))"

|

"dtabbrev" : "  ck mn env tvs tn t0 s locs.

evaluate_dec ck mn env s (Dtabbrev locs tvs tn t0) (s, Rval (| v = nsEmpty, c = nsEmpty |))"

|

"dexn1" : "  ck mn env cn ts s locs.
¬ (TypeExn (mk_id mn cn) (defined_types   s))
==>
evaluate_dec ck mn env s (Dexn locs cn ts) (( s (| defined_types := ({TypeExn (mk_id mn cn)} (defined_types   s)) |)), Rval  (| v = nsEmpty, c = (nsSing cn (List.length ts, TypeExn (mk_id mn cn))) |))"

|

"dexn2" : "  ck mn env cn ts s locs.
TypeExn (mk_id mn cn) (defined_types   s)
==>
evaluate_dec ck mn env s (Dexn locs cn ts) (s, Rerr (Rabort Rtype_error))"

inductive
evaluate_decs  :: " bool (modN)list (v)sem_env  'ffi state (dec)list  'ffi state*(((v)sem_env),(v))result  bool "  where

"empty" : "  ck mn env s.

evaluate_decs ck mn env s [] (s, Rval (| v = nsEmpty, c = nsEmpty |))"

|

"cons1" : "  ck mn s1 s2 env d ds e.
evaluate_dec ck mn env s1 d (s2, Rerr e)
==>
evaluate_decs ck mn env s1 (d # ds) (s2, Rerr e)"

|

"cons2" : "  ck mn s1 s2 s3 env d ds new_env r.
evaluate_dec ck mn env s1 d (s2, Rval new_env) 
evaluate_decs ck mn (extend_dec_env new_env env) s2 ds (s3, r)
==>
evaluate_decs ck mn env s1 (d # ds) (s3, combine_dec_result new_env r)"

inductive
evaluate_top  :: " bool (v)sem_env  'ffi state  top0  'ffi state*(((v)sem_env),(v))result  bool "  where

"tdec1" : "  ck s1 s2 env d new_env.
evaluate_dec ck [] env s1 d (s2, Rval new_env)
==>
evaluate_top ck env s1 (Tdec d) (s2, Rval new_env)"
|

"tdec2" : "  ck s1 s2 env d err.
evaluate_dec ck [] env s1 d (s2, Rerr err)
==>
evaluate_top ck env s1 (Tdec d) (s2, Rerr err)"

|

"tmod1" : "  ck s1 s2 env ds mn specs new_env.
¬ ([mn] (defined_mods   s1)) 
(no_dup_types ds 
evaluate_decs ck [mn] env s1 ds (s2, Rval new_env))
==>
evaluate_top ck env s1 (Tmod mn specs ds) (( s2 (| defined_mods := ({[mn]} (defined_mods   s2)) |)), Rval (| v = (nsLift mn(v   new_env)), c = (nsLift mn(c   new_env)) |))"

|

"tmod2" : "  ck s1 s2 env ds mn specs err.
¬ ([mn] (defined_mods   s1)) 
(no_dup_types ds 
evaluate_decs ck [mn] env s1 ds (s2, Rerr err))
==>
evaluate_top ck env s1 (Tmod mn specs ds) (( s2 (| defined_mods := ({[mn]} (defined_mods   s2)) |)), Rerr err)"

|

"tmod3" : "  ck s1 env ds mn specs.
¬ (no_dup_types ds)
==>
evaluate_top ck env s1 (Tmod mn specs ds) (s1, Rerr (Rabort Rtype_error))"

|

"tmod4" : "  ck env s mn specs ds.
[mn] (defined_mods   s)
==>
evaluate_top ck env s (Tmod mn specs ds) (s, Rerr (Rabort Rtype_error))"

inductive
evaluate_prog  :: " bool (v)sem_env  'ffi state  prog  'ffi state*(((v)sem_env),(v))result  bool "  where

"empty" : "  ck env s.

evaluate_prog ck env s [] (s, Rval (| v = nsEmpty, c = nsEmpty |))"

|

"cons1" : "  ck s1 s2 s3 env top0 tops new_env r.
evaluate_top ck env s1 top0 (s2, Rval new_env) 
evaluate_prog ck (extend_dec_env new_env env) s2 tops (s3,r)
==>
evaluate_prog ck env s1 (top0 # tops) (s3, combine_dec_result new_env r)"

|

"cons2" : "  ck s1 s2 env top0 tops err.
evaluate_top ck env s1 top0 (s2, Rerr err)
==>
evaluate_prog ck env s1 (top0 # tops) (s2, Rerr err)"


― ‹val evaluate_whole_prog : forall 'ffi. Eq 'ffi => bool -> sem_env v -> state 'ffi -> prog ->
          state 'ffi * result (sem_env v) v -> bool›
fun evaluate_whole_prog  :: " bool (v)sem_env  'ffi state (top0)list  'ffi state*(((v)sem_env),(v))result  bool "  where 
     " evaluate_whole_prog ck env s1 tops (s2, res) = (
  if no_dup_mods tops(defined_mods   s1)  no_dup_top_types tops(defined_types   s1) then
    evaluate_prog ck env s1 tops (s2, res)
  else
    (s1 = s2)  (res = Rerr (Rabort Rtype_error)))"


― ‹val dec_diverges : forall 'ffi. sem_env v -> state 'ffi -> dec -> bool›
fun dec_diverges  :: "(v)sem_env  'ffi state  dec  bool "  where 
     " dec_diverges env st (Dlet locs p e) = ( Lem_list.allDistinct (pat_bindings p [])  e_diverges env ((refs   st),(ffi   st)) e )"
|" dec_diverges env st (Dletrec locs funs) = ( False )"
|" dec_diverges env st (Dtype locs tds) = ( False )"
|" dec_diverges env st (Dtabbrev locs tvs tn t1) = ( False )"
|" dec_diverges env st (Dexn locs cn ts) = ( False )"


inductive
decs_diverges  :: "(modN)list (v)sem_env  'ffi state  decs  bool "  where

"cons1" : "  mn st env d ds.
dec_diverges env st d
==>
decs_diverges mn env st (d # ds)"

|

"cons2" : "  mn s1 s2 env d ds new_env.
evaluate_dec False mn env s1 d (s2, Rval new_env) 
decs_diverges mn (extend_dec_env new_env env) s2 ds
==>
decs_diverges mn env s1 (d # ds)"

inductive
top_diverges  :: "(v)sem_env  'ffi state  top0  bool "  where

"tdec" : "  st env d.
dec_diverges env st d
==>
top_diverges env st (Tdec d)"

|

"tmod" : "  env s1 ds mn specs.
¬ ([mn] (defined_mods   s1)) 
(no_dup_types ds 
decs_diverges [mn] env s1 ds)
==>
top_diverges env s1 (Tmod mn specs ds)"

inductive
prog_diverges  :: "(v)sem_env  'ffi state  prog  bool "  where

"cons1" : "  st env top0 tops.
top_diverges env st top0
==>
prog_diverges env st (top0 # tops)"

|

"cons2" : "  s1 s2 env top0 tops new_env.
evaluate_top False env s1 top0 (s2, Rval new_env) 
prog_diverges (extend_dec_env new_env env) s2 tops
==>
prog_diverges env s1 (top0 # tops)"
end