30 mk_program(\<Inter>i \<in> I. Init(F(i)), \<Union>i \<in> I. Acts(F(i)), |
30 mk_program(\<Inter>i \<in> I. Init(F(i)), \<Union>i \<in> I. Acts(F(i)), |
31 \<Inter>i \<in> I. AllowedActs(F(i)))" |
31 \<Inter>i \<in> I. AllowedActs(F(i)))" |
32 |
32 |
33 definition |
33 definition |
34 Join :: "[i, i] => i" (infixl "Join" 65) where |
34 Join :: "[i, i] => i" (infixl "Join" 65) where |
35 "F Join G == mk_program (Init(F) Int Init(G), Acts(F) Un Acts(G), |
35 "F Join G == mk_program (Init(F) \<inter> Init(G), Acts(F) \<union> Acts(G), |
36 AllowedActs(F) Int AllowedActs(G))" |
36 AllowedActs(F) \<inter> AllowedActs(G))" |
37 definition |
37 definition |
38 (*Characterizes safety properties. Used with specifying AllowedActs*) |
38 (*Characterizes safety properties. Used with specifying AllowedActs*) |
39 safety_prop :: "i => o" where |
39 safety_prop :: "i => o" where |
40 "safety_prop(X) == X\<subseteq>program & |
40 "safety_prop(X) == X\<subseteq>program & |
41 SKIP \<in> X & (\<forall>G \<in> program. Acts(G) \<subseteq> (\<Union>F \<in> X. Acts(F)) --> G \<in> X)" |
41 SKIP \<in> X & (\<forall>G \<in> program. Acts(G) \<subseteq> (\<Union>F \<in> X. Acts(F)) \<longrightarrow> G \<in> X)" |
42 |
42 |
43 notation (xsymbols) |
43 notation (xsymbols) |
44 SKIP ("\<bottom>") and |
44 SKIP ("\<bottom>") and |
45 Join (infixl "\<squnion>" 65) |
45 Join (infixl "\<squnion>" 65) |
46 |
46 |
62 lemma reachable_SKIP [simp]: "reachable(SKIP) = state" |
62 lemma reachable_SKIP [simp]: "reachable(SKIP) = state" |
63 by (force elim: reachable.induct intro: reachable.intros) |
63 by (force elim: reachable.induct intro: reachable.intros) |
64 |
64 |
65 text{*Elimination programify from ok and Join*} |
65 text{*Elimination programify from ok and Join*} |
66 |
66 |
67 lemma ok_programify_left [iff]: "programify(F) ok G <-> F ok G" |
67 lemma ok_programify_left [iff]: "programify(F) ok G \<longleftrightarrow> F ok G" |
68 by (simp add: ok_def) |
68 by (simp add: ok_def) |
69 |
69 |
70 lemma ok_programify_right [iff]: "F ok programify(G) <-> F ok G" |
70 lemma ok_programify_right [iff]: "F ok programify(G) \<longleftrightarrow> F ok G" |
71 by (simp add: ok_def) |
71 by (simp add: ok_def) |
72 |
72 |
73 lemma Join_programify_left [simp]: "programify(F) Join G = F Join G" |
73 lemma Join_programify_left [simp]: "programify(F) Join G = F Join G" |
74 by (simp add: Join_def) |
74 by (simp add: Join_def) |
75 |
75 |
76 lemma Join_programify_right [simp]: "F Join programify(G) = F Join G" |
76 lemma Join_programify_right [simp]: "F Join programify(G) = F Join G" |
77 by (simp add: Join_def) |
77 by (simp add: Join_def) |
78 |
78 |
79 subsection{*SKIP and safety properties*} |
79 subsection{*SKIP and safety properties*} |
80 |
80 |
81 lemma SKIP_in_constrains_iff [iff]: "(SKIP \<in> A co B) <-> (A\<subseteq>B & st_set(A))" |
81 lemma SKIP_in_constrains_iff [iff]: "(SKIP \<in> A co B) \<longleftrightarrow> (A\<subseteq>B & st_set(A))" |
82 by (unfold constrains_def st_set_def, auto) |
82 by (unfold constrains_def st_set_def, auto) |
83 |
83 |
84 lemma SKIP_in_Constrains_iff [iff]: "(SKIP \<in> A Co B)<-> (state Int A\<subseteq>B)" |
84 lemma SKIP_in_Constrains_iff [iff]: "(SKIP \<in> A Co B)\<longleftrightarrow> (state \<inter> A\<subseteq>B)" |
85 by (unfold Constrains_def, auto) |
85 by (unfold Constrains_def, auto) |
86 |
86 |
87 lemma SKIP_in_stable [iff]: "SKIP \<in> stable(A) <-> st_set(A)" |
87 lemma SKIP_in_stable [iff]: "SKIP \<in> stable(A) \<longleftrightarrow> st_set(A)" |
88 by (auto simp add: stable_def) |
88 by (auto simp add: stable_def) |
89 |
89 |
90 lemma SKIP_in_Stable [iff]: "SKIP \<in> Stable(A)" |
90 lemma SKIP_in_Stable [iff]: "SKIP \<in> Stable(A)" |
91 by (unfold Stable_def, auto) |
91 by (unfold Stable_def, auto) |
92 |
92 |
97 |
97 |
98 lemma JOIN_in_program [iff,TC]: "JOIN(I,F) \<in> program" |
98 lemma JOIN_in_program [iff,TC]: "JOIN(I,F) \<in> program" |
99 by (unfold JOIN_def, auto) |
99 by (unfold JOIN_def, auto) |
100 |
100 |
101 subsection{*Init, Acts, and AllowedActs of Join and JOIN*} |
101 subsection{*Init, Acts, and AllowedActs of Join and JOIN*} |
102 lemma Init_Join [simp]: "Init(F Join G) = Init(F) Int Init(G)" |
102 lemma Init_Join [simp]: "Init(F Join G) = Init(F) \<inter> Init(G)" |
103 by (simp add: Int_assoc Join_def) |
103 by (simp add: Int_assoc Join_def) |
104 |
104 |
105 lemma Acts_Join [simp]: "Acts(F Join G) = Acts(F) Un Acts(G)" |
105 lemma Acts_Join [simp]: "Acts(F Join G) = Acts(F) \<union> Acts(G)" |
106 by (simp add: Int_Un_distrib2 cons_absorb Join_def) |
106 by (simp add: Int_Un_distrib2 cons_absorb Join_def) |
107 |
107 |
108 lemma AllowedActs_Join [simp]: "AllowedActs(F Join G) = |
108 lemma AllowedActs_Join [simp]: "AllowedActs(F Join G) = |
109 AllowedActs(F) Int AllowedActs(G)" |
109 AllowedActs(F) \<inter> AllowedActs(G)" |
110 apply (simp add: Int_assoc cons_absorb Join_def) |
110 apply (simp add: Int_assoc cons_absorb Join_def) |
111 done |
111 done |
112 |
112 |
113 subsection{*Join's algebraic laws*} |
113 subsection{*Join's algebraic laws*} |
114 |
114 |
146 subsection{*Join is an AC-operator*} |
146 subsection{*Join is an AC-operator*} |
147 lemmas Join_ac = Join_assoc Join_left_absorb Join_commute Join_left_commute |
147 lemmas Join_ac = Join_assoc Join_left_absorb Join_commute Join_left_commute |
148 |
148 |
149 subsection{*Eliminating programify form JN and OK expressions*} |
149 subsection{*Eliminating programify form JN and OK expressions*} |
150 |
150 |
151 lemma OK_programify [iff]: "OK(I, %x. programify(F(x))) <-> OK(I, F)" |
151 lemma OK_programify [iff]: "OK(I, %x. programify(F(x))) \<longleftrightarrow> OK(I, F)" |
152 by (simp add: OK_def) |
152 by (simp add: OK_def) |
153 |
153 |
154 lemma JN_programify [iff]: "JOIN(I, %x. programify(F(x))) = JOIN(I, F)" |
154 lemma JN_programify [iff]: "JOIN(I, %x. programify(F(x))) = JOIN(I, F)" |
155 by (simp add: JOIN_def) |
155 by (simp add: JOIN_def) |
156 |
156 |
226 (*Fails if I=0 because it collapses to SKIP \<in> A co B, i.e. to A\<subseteq>B. So an |
226 (*Fails if I=0 because it collapses to SKIP \<in> A co B, i.e. to A\<subseteq>B. So an |
227 alternative precondition is A\<subseteq>B, but most proofs using this rule require |
227 alternative precondition is A\<subseteq>B, but most proofs using this rule require |
228 I to be nonempty for other reasons anyway.*) |
228 I to be nonempty for other reasons anyway.*) |
229 |
229 |
230 lemma JN_constrains: |
230 lemma JN_constrains: |
231 "i \<in> I==>(\<Squnion>i \<in> I. F(i)) \<in> A co B <-> (\<forall>i \<in> I. programify(F(i)) \<in> A co B)" |
231 "i \<in> I==>(\<Squnion>i \<in> I. F(i)) \<in> A co B \<longleftrightarrow> (\<forall>i \<in> I. programify(F(i)) \<in> A co B)" |
232 |
232 |
233 apply (unfold constrains_def JOIN_def st_set_def, auto) |
233 apply (unfold constrains_def JOIN_def st_set_def, auto) |
234 prefer 2 apply blast |
234 prefer 2 apply blast |
235 apply (rename_tac j act y z) |
235 apply (rename_tac j act y z) |
236 apply (cut_tac F = "F (j) " in Acts_type) |
236 apply (cut_tac F = "F (j) " in Acts_type) |
237 apply (drule_tac x = act in bspec, auto) |
237 apply (drule_tac x = act in bspec, auto) |
238 done |
238 done |
239 |
239 |
240 lemma Join_constrains [iff]: |
240 lemma Join_constrains [iff]: |
241 "(F Join G \<in> A co B) <-> (programify(F) \<in> A co B & programify(G) \<in> A co B)" |
241 "(F Join G \<in> A co B) \<longleftrightarrow> (programify(F) \<in> A co B & programify(G) \<in> A co B)" |
242 by (auto simp add: constrains_def) |
242 by (auto simp add: constrains_def) |
243 |
243 |
244 lemma Join_unless [iff]: |
244 lemma Join_unless [iff]: |
245 "(F Join G \<in> A unless B) <-> |
245 "(F Join G \<in> A unless B) \<longleftrightarrow> |
246 (programify(F) \<in> A unless B & programify(G) \<in> A unless B)" |
246 (programify(F) \<in> A unless B & programify(G) \<in> A unless B)" |
247 by (simp add: Join_constrains unless_def) |
247 by (simp add: Join_constrains unless_def) |
248 |
248 |
249 |
249 |
250 (*Analogous weak versions FAIL; see Misra [1994] 5.4.1, Substitution Axiom. |
250 (*Analogous weak versions FAIL; see Misra [1994] 5.4.1, Substitution Axiom. |
251 reachable (F Join G) could be much bigger than reachable F, reachable G |
251 reachable (F Join G) could be much bigger than reachable F, reachable G |
252 *) |
252 *) |
253 |
253 |
254 lemma Join_constrains_weaken: |
254 lemma Join_constrains_weaken: |
255 "[| F \<in> A co A'; G \<in> B co B' |] |
255 "[| F \<in> A co A'; G \<in> B co B' |] |
256 ==> F Join G \<in> (A Int B) co (A' Un B')" |
256 ==> F Join G \<in> (A \<inter> B) co (A' \<union> B')" |
257 apply (subgoal_tac "st_set (A) & st_set (B) & F \<in> program & G \<in> program") |
257 apply (subgoal_tac "st_set (A) & st_set (B) & F \<in> program & G \<in> program") |
258 prefer 2 apply (blast dest: constrainsD2, simp) |
258 prefer 2 apply (blast dest: constrainsD2, simp) |
259 apply (blast intro: constrains_weaken) |
259 apply (blast intro: constrains_weaken) |
260 done |
260 done |
261 |
261 |
302 apply (auto simp add: invariant_def) |
302 apply (auto simp add: invariant_def) |
303 apply (frule stableD2, force)+ |
303 apply (frule stableD2, force)+ |
304 done |
304 done |
305 |
305 |
306 lemma Join_stable [iff]: |
306 lemma Join_stable [iff]: |
307 " (F Join G \<in> stable(A)) <-> |
307 " (F Join G \<in> stable(A)) \<longleftrightarrow> |
308 (programify(F) \<in> stable(A) & programify(G) \<in> stable(A))" |
308 (programify(F) \<in> stable(A) & programify(G) \<in> stable(A))" |
309 by (simp add: stable_def) |
309 by (simp add: stable_def) |
310 |
310 |
311 lemma initially_JoinI [intro!]: |
311 lemma initially_JoinI [intro!]: |
312 "[| F \<in> initially(A); G \<in> initially(A) |] ==> F Join G \<in> initially(A)" |
312 "[| F \<in> initially(A); G \<in> initially(A) |] ==> F Join G \<in> initially(A)" |
328 |
328 |
329 subsection{*Progress: transient, ensures*} |
329 subsection{*Progress: transient, ensures*} |
330 |
330 |
331 lemma JN_transient: |
331 lemma JN_transient: |
332 "i \<in> I ==> |
332 "i \<in> I ==> |
333 (\<Squnion>i \<in> I. F(i)) \<in> transient(A) <-> (\<exists>i \<in> I. programify(F(i)) \<in> transient(A))" |
333 (\<Squnion>i \<in> I. F(i)) \<in> transient(A) \<longleftrightarrow> (\<exists>i \<in> I. programify(F(i)) \<in> transient(A))" |
334 apply (auto simp add: transient_def JOIN_def) |
334 apply (auto simp add: transient_def JOIN_def) |
335 apply (unfold st_set_def) |
335 apply (unfold st_set_def) |
336 apply (drule_tac [2] x = act in bspec) |
336 apply (drule_tac [2] x = act in bspec) |
337 apply (auto dest: Acts_type [THEN subsetD]) |
337 apply (auto dest: Acts_type [THEN subsetD]) |
338 done |
338 done |
339 |
339 |
340 lemma Join_transient [iff]: |
340 lemma Join_transient [iff]: |
341 "F Join G \<in> transient(A) <-> |
341 "F Join G \<in> transient(A) \<longleftrightarrow> |
342 (programify(F) \<in> transient(A) | programify(G) \<in> transient(A))" |
342 (programify(F) \<in> transient(A) | programify(G) \<in> transient(A))" |
343 apply (auto simp add: transient_def Join_def Int_Un_distrib2) |
343 apply (auto simp add: transient_def Join_def Int_Un_distrib2) |
344 done |
344 done |
345 |
345 |
346 lemma Join_transient_I1: "F \<in> transient(A) ==> F Join G \<in> transient(A)" |
346 lemma Join_transient_I1: "F \<in> transient(A) ==> F Join G \<in> transient(A)" |
351 by (simp add: Join_transient transientD2) |
351 by (simp add: Join_transient transientD2) |
352 |
352 |
353 (*If I=0 it degenerates to (SKIP \<in> A ensures B) = False, i.e. to ~(A\<subseteq>B) *) |
353 (*If I=0 it degenerates to (SKIP \<in> A ensures B) = False, i.e. to ~(A\<subseteq>B) *) |
354 lemma JN_ensures: |
354 lemma JN_ensures: |
355 "i \<in> I ==> |
355 "i \<in> I ==> |
356 (\<Squnion>i \<in> I. F(i)) \<in> A ensures B <-> |
356 (\<Squnion>i \<in> I. F(i)) \<in> A ensures B \<longleftrightarrow> |
357 ((\<forall>i \<in> I. programify(F(i)) \<in> (A-B) co (A Un B)) & |
357 ((\<forall>i \<in> I. programify(F(i)) \<in> (A-B) co (A \<union> B)) & |
358 (\<exists>i \<in> I. programify(F(i)) \<in> A ensures B))" |
358 (\<exists>i \<in> I. programify(F(i)) \<in> A ensures B))" |
359 by (auto simp add: ensures_def JN_constrains JN_transient) |
359 by (auto simp add: ensures_def JN_constrains JN_transient) |
360 |
360 |
361 |
361 |
362 lemma Join_ensures: |
362 lemma Join_ensures: |
363 "F Join G \<in> A ensures B <-> |
363 "F Join G \<in> A ensures B \<longleftrightarrow> |
364 (programify(F) \<in> (A-B) co (A Un B) & programify(G) \<in> (A-B) co (A Un B) & |
364 (programify(F) \<in> (A-B) co (A \<union> B) & programify(G) \<in> (A-B) co (A \<union> B) & |
365 (programify(F) \<in> transient (A-B) | programify(G) \<in> transient (A-B)))" |
365 (programify(F) \<in> transient (A-B) | programify(G) \<in> transient (A-B)))" |
366 |
366 |
367 apply (unfold ensures_def) |
367 apply (unfold ensures_def) |
368 apply (auto simp add: Join_transient) |
368 apply (auto simp add: Join_transient) |
369 done |
369 done |
419 |
419 |
420 lemma ok_SKIP2 [iff]: "F ok SKIP" |
420 lemma ok_SKIP2 [iff]: "F ok SKIP" |
421 by (auto dest: Acts_type [THEN subsetD] simp add: ok_def) |
421 by (auto dest: Acts_type [THEN subsetD] simp add: ok_def) |
422 |
422 |
423 lemma ok_Join_commute: |
423 lemma ok_Join_commute: |
424 "(F ok G & (F Join G) ok H) <-> (G ok H & F ok (G Join H))" |
424 "(F ok G & (F Join G) ok H) \<longleftrightarrow> (G ok H & F ok (G Join H))" |
425 by (auto simp add: ok_def) |
425 by (auto simp add: ok_def) |
426 |
426 |
427 lemma ok_commute: "(F ok G) <->(G ok F)" |
427 lemma ok_commute: "(F ok G) \<longleftrightarrow>(G ok F)" |
428 by (auto simp add: ok_def) |
428 by (auto simp add: ok_def) |
429 |
429 |
430 lemmas ok_sym = ok_commute [THEN iffD1] |
430 lemmas ok_sym = ok_commute [THEN iffD1] |
431 |
431 |
432 lemma ok_iff_OK: "OK({<0,F>,<1,G>,<2,H>}, snd) <-> (F ok G & (F Join G) ok H)" |
432 lemma ok_iff_OK: "OK({<0,F>,<1,G>,<2,H>}, snd) \<longleftrightarrow> (F ok G & (F Join G) ok H)" |
433 by (simp add: ok_def Join_def OK_def Int_assoc cons_absorb |
433 by (simp add: ok_def Join_def OK_def Int_assoc cons_absorb |
434 Int_Un_distrib2 Ball_def, safe, force+) |
434 Int_Un_distrib2 Ball_def, safe, force+) |
435 |
435 |
436 lemma ok_Join_iff1 [iff]: "F ok (G Join H) <-> (F ok G & F ok H)" |
436 lemma ok_Join_iff1 [iff]: "F ok (G Join H) \<longleftrightarrow> (F ok G & F ok H)" |
437 by (auto simp add: ok_def) |
437 by (auto simp add: ok_def) |
438 |
438 |
439 lemma ok_Join_iff2 [iff]: "(G Join H) ok F <-> (G ok F & H ok F)" |
439 lemma ok_Join_iff2 [iff]: "(G Join H) ok F \<longleftrightarrow> (G ok F & H ok F)" |
440 by (auto simp add: ok_def) |
440 by (auto simp add: ok_def) |
441 |
441 |
442 (*useful? Not with the previous two around*) |
442 (*useful? Not with the previous two around*) |
443 lemma ok_Join_commute_I: "[| F ok G; (F Join G) ok H |] ==> F ok (G Join H)" |
443 lemma ok_Join_commute_I: "[| F ok G; (F Join G) ok H |] ==> F ok (G Join H)" |
444 by (auto simp add: ok_def) |
444 by (auto simp add: ok_def) |
445 |
445 |
446 lemma ok_JN_iff1 [iff]: "F ok JOIN(I,G) <-> (\<forall>i \<in> I. F ok G(i))" |
446 lemma ok_JN_iff1 [iff]: "F ok JOIN(I,G) \<longleftrightarrow> (\<forall>i \<in> I. F ok G(i))" |
447 by (force dest: Acts_type [THEN subsetD] elim!: not_emptyE simp add: ok_def) |
447 by (force dest: Acts_type [THEN subsetD] elim!: not_emptyE simp add: ok_def) |
448 |
448 |
449 lemma ok_JN_iff2 [iff]: "JOIN(I,G) ok F <-> (\<forall>i \<in> I. G(i) ok F)" |
449 lemma ok_JN_iff2 [iff]: "JOIN(I,G) ok F \<longleftrightarrow> (\<forall>i \<in> I. G(i) ok F)" |
450 apply (auto elim!: not_emptyE simp add: ok_def) |
450 apply (auto elim!: not_emptyE simp add: ok_def) |
451 apply (blast dest: Acts_type [THEN subsetD]) |
451 apply (blast dest: Acts_type [THEN subsetD]) |
452 done |
452 done |
453 |
453 |
454 lemma OK_iff_ok: "OK(I,F) <-> (\<forall>i \<in> I. \<forall>j \<in> I-{i}. F(i) ok (F(j)))" |
454 lemma OK_iff_ok: "OK(I,F) \<longleftrightarrow> (\<forall>i \<in> I. \<forall>j \<in> I-{i}. F(i) ok (F(j)))" |
455 by (auto simp add: ok_def OK_def) |
455 by (auto simp add: ok_def OK_def) |
456 |
456 |
457 lemma OK_imp_ok: "[| OK(I,F); i \<in> I; j \<in> I; i\<noteq>j|] ==> F(i) ok F(j)" |
457 lemma OK_imp_ok: "[| OK(I,F); i \<in> I; j \<in> I; i\<noteq>j|] ==> F(i) ok F(j)" |
458 by (auto simp add: OK_iff_ok) |
458 by (auto simp add: OK_iff_ok) |
459 |
459 |
460 |
460 |
461 lemma OK_0 [iff]: "OK(0,F)" |
461 lemma OK_0 [iff]: "OK(0,F)" |
462 by (simp add: OK_def) |
462 by (simp add: OK_def) |
463 |
463 |
464 lemma OK_cons_iff: |
464 lemma OK_cons_iff: |
465 "OK(cons(i, I), F) <-> |
465 "OK(cons(i, I), F) \<longleftrightarrow> |
466 (i \<in> I & OK(I, F)) | (i\<notin>I & OK(I, F) & F(i) ok JOIN(I,F))" |
466 (i \<in> I & OK(I, F)) | (i\<notin>I & OK(I, F) & F(i) ok JOIN(I,F))" |
467 apply (simp add: OK_iff_ok) |
467 apply (simp add: OK_iff_ok) |
468 apply (blast intro: ok_sym) |
468 apply (blast intro: ok_sym) |
469 done |
469 done |
470 |
470 |
474 lemma Allowed_SKIP [simp]: "Allowed(SKIP) = program" |
474 lemma Allowed_SKIP [simp]: "Allowed(SKIP) = program" |
475 by (auto dest: Acts_type [THEN subsetD] simp add: Allowed_def) |
475 by (auto dest: Acts_type [THEN subsetD] simp add: Allowed_def) |
476 |
476 |
477 lemma Allowed_Join [simp]: |
477 lemma Allowed_Join [simp]: |
478 "Allowed(F Join G) = |
478 "Allowed(F Join G) = |
479 Allowed(programify(F)) Int Allowed(programify(G))" |
479 Allowed(programify(F)) \<inter> Allowed(programify(G))" |
480 apply (auto simp add: Allowed_def) |
480 apply (auto simp add: Allowed_def) |
481 done |
481 done |
482 |
482 |
483 lemma Allowed_JN [simp]: |
483 lemma Allowed_JN [simp]: |
484 "i \<in> I ==> |
484 "i \<in> I ==> |
485 Allowed(JOIN(I,F)) = (\<Inter>i \<in> I. Allowed(programify(F(i))))" |
485 Allowed(JOIN(I,F)) = (\<Inter>i \<in> I. Allowed(programify(F(i))))" |
486 apply (auto simp add: Allowed_def, blast) |
486 apply (auto simp add: Allowed_def, blast) |
487 done |
487 done |
488 |
488 |
489 lemma ok_iff_Allowed: |
489 lemma ok_iff_Allowed: |
490 "F ok G <-> (programify(F) \<in> Allowed(programify(G)) & |
490 "F ok G \<longleftrightarrow> (programify(F) \<in> Allowed(programify(G)) & |
491 programify(G) \<in> Allowed(programify(F)))" |
491 programify(G) \<in> Allowed(programify(F)))" |
492 by (simp add: ok_def Allowed_def) |
492 by (simp add: ok_def Allowed_def) |
493 |
493 |
494 |
494 |
495 lemma OK_iff_Allowed: |
495 lemma OK_iff_Allowed: |
496 "OK(I,F) <-> |
496 "OK(I,F) \<longleftrightarrow> |
497 (\<forall>i \<in> I. \<forall>j \<in> I-{i}. programify(F(i)) \<in> Allowed(programify(F(j))))" |
497 (\<forall>i \<in> I. \<forall>j \<in> I-{i}. programify(F(i)) \<in> Allowed(programify(F(j))))" |
498 apply (auto simp add: OK_iff_ok ok_iff_Allowed) |
498 apply (auto simp add: OK_iff_ok ok_iff_Allowed) |
499 done |
499 done |
500 |
500 |
501 subsection{*safety_prop, for reasoning about given instances of "ok"*} |
501 subsection{*safety_prop, for reasoning about given instances of "ok"*} |
502 |
502 |
503 lemma safety_prop_Acts_iff: |
503 lemma safety_prop_Acts_iff: |
504 "safety_prop(X) ==> (Acts(G) \<subseteq> cons(id(state), (\<Union>F \<in> X. Acts(F)))) <-> (programify(G) \<in> X)" |
504 "safety_prop(X) ==> (Acts(G) \<subseteq> cons(id(state), (\<Union>F \<in> X. Acts(F)))) \<longleftrightarrow> (programify(G) \<in> X)" |
505 apply (simp (no_asm_use) add: safety_prop_def) |
505 apply (simp (no_asm_use) add: safety_prop_def) |
506 apply clarify |
506 apply clarify |
507 apply (case_tac "G \<in> program", simp_all, blast, safe) |
507 apply (case_tac "G \<in> program", simp_all, blast, safe) |
508 prefer 2 apply force |
508 prefer 2 apply force |
509 apply (force simp add: programify_def) |
509 apply (force simp add: programify_def) |
510 done |
510 done |
511 |
511 |
512 lemma safety_prop_AllowedActs_iff_Allowed: |
512 lemma safety_prop_AllowedActs_iff_Allowed: |
513 "safety_prop(X) ==> |
513 "safety_prop(X) ==> |
514 (\<Union>G \<in> X. Acts(G)) \<subseteq> AllowedActs(F) <-> (X \<subseteq> Allowed(programify(F)))" |
514 (\<Union>G \<in> X. Acts(G)) \<subseteq> AllowedActs(F) \<longleftrightarrow> (X \<subseteq> Allowed(programify(F)))" |
515 apply (simp add: Allowed_def safety_prop_Acts_iff [THEN iff_sym] |
515 apply (simp add: Allowed_def safety_prop_Acts_iff [THEN iff_sym] |
516 safety_prop_def, blast) |
516 safety_prop_def, blast) |
517 done |
517 done |
518 |
518 |
519 |
519 |
520 lemma Allowed_eq: |
520 lemma Allowed_eq: |
521 "safety_prop(X) ==> Allowed(mk_program(init, acts, \<Union>F \<in> X. Acts(F))) = X" |
521 "safety_prop(X) ==> Allowed(mk_program(init, acts, \<Union>F \<in> X. Acts(F))) = X" |
522 apply (subgoal_tac "cons (id (state), Union (RepFun (X, Acts)) Int Pow (state * state)) = Union (RepFun (X, Acts))") |
522 apply (subgoal_tac "cons (id (state), \<Union>(RepFun (X, Acts)) \<inter> Pow (state * state)) = \<Union>(RepFun (X, Acts))") |
523 apply (rule_tac [2] equalityI) |
523 apply (rule_tac [2] equalityI) |
524 apply (simp del: UN_simps add: Allowed_def safety_prop_Acts_iff safety_prop_def, auto) |
524 apply (simp del: UN_simps add: Allowed_def safety_prop_Acts_iff safety_prop_def, auto) |
525 apply (force dest: Acts_type [THEN subsetD] simp add: safety_prop_def)+ |
525 apply (force dest: Acts_type [THEN subsetD] simp add: safety_prop_def)+ |
526 done |
526 done |
527 |
527 |
530 ==> Allowed(F) = X" |
530 ==> Allowed(F) = X" |
531 by (simp add: Allowed_eq) |
531 by (simp add: Allowed_eq) |
532 |
532 |
533 (*For safety_prop to hold, the property must be satisfiable!*) |
533 (*For safety_prop to hold, the property must be satisfiable!*) |
534 lemma safety_prop_constrains [iff]: |
534 lemma safety_prop_constrains [iff]: |
535 "safety_prop(A co B) <-> (A \<subseteq> B & st_set(A))" |
535 "safety_prop(A co B) \<longleftrightarrow> (A \<subseteq> B & st_set(A))" |
536 by (simp add: safety_prop_def constrains_def st_set_def, blast) |
536 by (simp add: safety_prop_def constrains_def st_set_def, blast) |
537 |
537 |
538 (* To be used with resolution *) |
538 (* To be used with resolution *) |
539 lemma safety_prop_constrainsI [iff]: |
539 lemma safety_prop_constrainsI [iff]: |
540 "[| A\<subseteq>B; st_set(A) |] ==>safety_prop(A co B)" |
540 "[| A\<subseteq>B; st_set(A) |] ==>safety_prop(A co B)" |
541 by auto |
541 by auto |
542 |
542 |
543 lemma safety_prop_stable [iff]: "safety_prop(stable(A)) <-> st_set(A)" |
543 lemma safety_prop_stable [iff]: "safety_prop(stable(A)) \<longleftrightarrow> st_set(A)" |
544 by (simp add: stable_def) |
544 by (simp add: stable_def) |
545 |
545 |
546 lemma safety_prop_stableI: "st_set(A) ==> safety_prop(stable(A))" |
546 lemma safety_prop_stableI: "st_set(A) ==> safety_prop(stable(A))" |
547 by auto |
547 by auto |
548 |
548 |
549 lemma safety_prop_Int [simp]: |
549 lemma safety_prop_Int [simp]: |
550 "[| safety_prop(X) ; safety_prop(Y) |] ==> safety_prop(X Int Y)" |
550 "[| safety_prop(X) ; safety_prop(Y) |] ==> safety_prop(X \<inter> Y)" |
551 apply (simp add: safety_prop_def, safe, blast) |
551 apply (simp add: safety_prop_def, safe, blast) |
552 apply (drule_tac [2] B = "Union (RepFun (X Int Y, Acts))" and C = "Union (RepFun (Y, Acts))" in subset_trans) |
552 apply (drule_tac [2] B = "\<Union>(RepFun (X \<inter> Y, Acts))" and C = "\<Union>(RepFun (Y, Acts))" in subset_trans) |
553 apply (drule_tac B = "Union (RepFun (X Int Y, Acts))" and C = "Union (RepFun (X, Acts))" in subset_trans) |
553 apply (drule_tac B = "\<Union>(RepFun (X \<inter> Y, Acts))" and C = "\<Union>(RepFun (X, Acts))" in subset_trans) |
554 apply blast+ |
554 apply blast+ |
555 done |
555 done |
556 |
556 |
557 (* If I=0 the conclusion becomes safety_prop(0) which is false *) |
557 (* If I=0 the conclusion becomes safety_prop(0) which is false *) |
558 lemma safety_prop_Inter: |
558 lemma safety_prop_Inter: |
565 apply clarify |
565 apply clarify |
566 apply (frule major) |
566 apply (frule major) |
567 apply (drule_tac [2] i = xa in major) |
567 apply (drule_tac [2] i = xa in major) |
568 apply (frule_tac [4] i = xa in major) |
568 apply (frule_tac [4] i = xa in major) |
569 apply (auto simp add: safety_prop_def) |
569 apply (auto simp add: safety_prop_def) |
570 apply (drule_tac B = "Union (RepFun (Inter (RepFun (I, X)), Acts))" and C = "Union (RepFun (X (xa), Acts))" in subset_trans) |
570 apply (drule_tac B = "\<Union>(RepFun (\<Inter>(RepFun (I, X)), Acts))" and C = "\<Union>(RepFun (X (xa), Acts))" in subset_trans) |
571 apply blast+ |
571 apply blast+ |
572 done |
572 done |
573 |
573 |
574 lemma def_UNION_ok_iff: |
574 lemma def_UNION_ok_iff: |
575 "[| F == mk_program(init,acts, \<Union>G \<in> X. Acts(G)); safety_prop(X) |] |
575 "[| F == mk_program(init,acts, \<Union>G \<in> X. Acts(G)); safety_prop(X) |] |
576 ==> F ok G <-> (programify(G) \<in> X & acts Int Pow(state*state) \<subseteq> AllowedActs(G))" |
576 ==> F ok G \<longleftrightarrow> (programify(G) \<in> X & acts \<inter> Pow(state*state) \<subseteq> AllowedActs(G))" |
577 apply (unfold ok_def) |
577 apply (unfold ok_def) |
578 apply (drule_tac G = G in safety_prop_Acts_iff) |
578 apply (drule_tac G = G in safety_prop_Acts_iff) |
579 apply (cut_tac F = G in AllowedActs_type) |
579 apply (cut_tac F = G in AllowedActs_type) |
580 apply (cut_tac F = G in Acts_type, auto) |
580 apply (cut_tac F = G in Acts_type, auto) |
581 done |
581 done |