1(*  Title:      HOL/Auth/Kerberos_BAN.thy
2    Author:     Giampaolo Bella, Cambridge University Computer Laboratory
3    Copyright   1998  University of Cambridge
4*)
5
6section\<open>The Kerberos Protocol, BAN Version\<close>
7
8theory Kerberos_BAN imports Public begin
9
10text\<open>From page 251 of
11  Burrows, Abadi and Needham (1989).  A Logic of Authentication.
12  Proc. Royal Soc. 426
13
14  Confidentiality (secrecy) and authentication properties are also
15  given in a termporal version: strong guarantees in a little abstracted 
16  - but very realistic - model.
17\<close>
18
19(* Temporal model of accidents: session keys can be leaked
20                                ONLY when they have expired *)
21
22consts
23
24    (*Duration of the session key*)
25    sesKlife   :: nat
26
27    (*Duration of the authenticator*)
28    authlife :: nat
29
30text\<open>The ticket should remain fresh for two journeys on the network at least\<close>
31specification (sesKlife)
32  sesKlife_LB [iff]: "2 \<le> sesKlife"
33    by blast
34
35text\<open>The authenticator only for one journey\<close>
36specification (authlife)
37  authlife_LB [iff]:    "authlife \<noteq> 0"
38    by blast
39
40abbreviation
41  CT :: "event list \<Rightarrow> nat" where
42  "CT == length "
43
44abbreviation
45  expiredK :: "[nat, event list] \<Rightarrow> bool" where
46  "expiredK T evs == sesKlife + T < CT evs"
47
48abbreviation
49  expiredA :: "[nat, event list] \<Rightarrow> bool" where
50  "expiredA T evs == authlife + T < CT evs"
51
52
53definition
54 (* A is the true creator of X if she has sent X and X never appeared on
55    the trace before this event. Recall that traces grow from head. *)
56  Issues :: "[agent, agent, msg, event list] \<Rightarrow> bool"
57             ("_ Issues _ with _ on _") where
58   "A Issues B with X on evs =
59      (\<exists>Y. Says A B Y \<in> set evs \<and> X \<in> parts {Y} \<and>
60        X \<notin> parts (spies (takeWhile (\<lambda>z. z  \<noteq> Says A B Y) (rev evs))))"
61
62definition
63 (* Yields the subtrace of a given trace from its beginning to a given event *)
64  before :: "[event, event list] \<Rightarrow> event list" ("before _ on _")
65  where "before ev on evs = takeWhile (\<lambda>z. z \<noteq> ev) (rev evs)"
66
67definition
68 (* States than an event really appears only once on a trace *)
69  Unique :: "[event, event list] \<Rightarrow> bool" ("Unique _ on _")
70  where "Unique ev on evs = (ev \<notin> set (tl (dropWhile (\<lambda>z. z \<noteq> ev) evs)))"
71
72
73inductive_set bankerberos :: "event list set"
74 where
75
76   Nil:  "[] \<in> bankerberos"
77
78 | Fake: "\<lbrakk> evsf \<in> bankerberos;  X \<in> synth (analz (spies evsf)) \<rbrakk>
79          \<Longrightarrow> Says Spy B X # evsf \<in> bankerberos"
80
81
82 | BK1:  "\<lbrakk> evs1 \<in> bankerberos \<rbrakk>
83          \<Longrightarrow> Says A Server \<lbrace>Agent A, Agent B\<rbrace> # evs1
84                \<in>  bankerberos"
85
86
87 | BK2:  "\<lbrakk> evs2 \<in> bankerberos;  Key K \<notin> used evs2; K \<in> symKeys;
88             Says A' Server \<lbrace>Agent A, Agent B\<rbrace> \<in> set evs2 \<rbrakk>
89          \<Longrightarrow> Says Server A
90                (Crypt (shrK A)
91                   \<lbrace>Number (CT evs2), Agent B, Key K,
92                    (Crypt (shrK B) \<lbrace>Number (CT evs2), Agent A, Key K\<rbrace>)\<rbrace>)
93                # evs2 \<in> bankerberos"
94
95
96 | BK3:  "\<lbrakk> evs3 \<in> bankerberos;
97             Says S A (Crypt (shrK A) \<lbrace>Number Tk, Agent B, Key K, Ticket\<rbrace>)
98               \<in> set evs3;
99             Says A Server \<lbrace>Agent A, Agent B\<rbrace> \<in> set evs3;
100             \<not> expiredK Tk evs3 \<rbrakk>
101          \<Longrightarrow> Says A B \<lbrace>Ticket, Crypt K \<lbrace>Agent A, Number (CT evs3)\<rbrace> \<rbrace>
102               # evs3 \<in> bankerberos"
103
104
105 | BK4:  "\<lbrakk> evs4 \<in> bankerberos;
106             Says A' B \<lbrace>(Crypt (shrK B) \<lbrace>Number Tk, Agent A, Key K\<rbrace>),
107                         (Crypt K \<lbrace>Agent A, Number Ta\<rbrace>) \<rbrace> \<in> set evs4;
108             \<not> expiredK Tk evs4;  \<not> expiredA Ta evs4 \<rbrakk>
109          \<Longrightarrow> Says B A (Crypt K (Number Ta)) # evs4
110                \<in> bankerberos"
111
112        (*Old session keys may become compromised*)
113 | Oops: "\<lbrakk> evso \<in> bankerberos;
114         Says Server A (Crypt (shrK A) \<lbrace>Number Tk, Agent B, Key K, Ticket\<rbrace>)
115               \<in> set evso;
116             expiredK Tk evso \<rbrakk>
117          \<Longrightarrow> Notes Spy \<lbrace>Number Tk, Key K\<rbrace> # evso \<in> bankerberos"
118
119
120declare Says_imp_knows_Spy [THEN parts.Inj, dest]
121declare parts.Body [dest]
122declare analz_into_parts [dest]
123declare Fake_parts_insert_in_Un [dest]
124
125text\<open>A "possibility property": there are traces that reach the end.\<close>
126lemma "\<lbrakk>Key K \<notin> used []; K \<in> symKeys\<rbrakk>
127       \<Longrightarrow> \<exists>Timestamp. \<exists>evs \<in> bankerberos.
128             Says B A (Crypt K (Number Timestamp))
129                  \<in> set evs"
130apply (cut_tac sesKlife_LB)
131apply (intro exI bexI)
132apply (rule_tac [2]
133           bankerberos.Nil [THEN bankerberos.BK1, THEN bankerberos.BK2,
134                             THEN bankerberos.BK3, THEN bankerberos.BK4])
135apply (possibility, simp_all (no_asm_simp) add: used_Cons)
136done
137
138subsection\<open>Lemmas for reasoning about predicate "Issues"\<close>
139
140lemma spies_Says_rev: "spies (evs @ [Says A B X]) = insert X (spies evs)"
141apply (induct_tac "evs")
142apply (rename_tac [2] a b)
143apply (induct_tac [2] "a", auto)
144done
145
146lemma spies_Gets_rev: "spies (evs @ [Gets A X]) = spies evs"
147apply (induct_tac "evs")
148apply (rename_tac [2] a b)
149apply (induct_tac [2] "a", auto)
150done
151
152lemma spies_Notes_rev: "spies (evs @ [Notes A X]) =
153          (if A\<in>bad then insert X (spies evs) else spies evs)"
154apply (induct_tac "evs")
155apply (rename_tac [2] a b)
156apply (induct_tac [2] "a", auto)
157done
158
159lemma spies_evs_rev: "spies evs = spies (rev evs)"
160apply (induct_tac "evs")
161apply (rename_tac [2] a b)
162apply (induct_tac [2] "a")
163apply (simp_all (no_asm_simp) add: spies_Says_rev spies_Gets_rev spies_Notes_rev)
164done
165
166lemmas parts_spies_evs_revD2 = spies_evs_rev [THEN equalityD2, THEN parts_mono]
167
168lemma spies_takeWhile: "spies (takeWhile P evs) \<subseteq> spies evs"
169apply (induct_tac "evs")
170apply (rename_tac [2] a b)
171apply (induct_tac [2] "a", auto)
172txt\<open>Resembles \<open>used_subset_append\<close> in theory Event.\<close>
173done
174
175lemmas parts_spies_takeWhile_mono = spies_takeWhile [THEN parts_mono]
176
177
178text\<open>Lemmas for reasoning about predicate "before"\<close>
179lemma used_Says_rev: "used (evs @ [Says A B X]) = parts {X} \<union> (used evs)"
180apply (induct_tac "evs")
181apply simp
182apply (rename_tac a b)
183apply (induct_tac "a")
184apply auto
185done
186
187lemma used_Notes_rev: "used (evs @ [Notes A X]) = parts {X} \<union> (used evs)"
188apply (induct_tac "evs")
189apply simp
190apply (rename_tac a b)
191apply (induct_tac "a")
192apply auto
193done
194
195lemma used_Gets_rev: "used (evs @ [Gets B X]) = used evs"
196apply (induct_tac "evs")
197apply simp
198apply (rename_tac a b)
199apply (induct_tac "a")
200apply auto
201done
202
203lemma used_evs_rev: "used evs = used (rev evs)"
204apply (induct_tac "evs")
205apply simp
206apply (rename_tac a b)
207apply (induct_tac "a")
208apply (simp add: used_Says_rev)
209apply (simp add: used_Gets_rev)
210apply (simp add: used_Notes_rev)
211done
212
213lemma used_takeWhile_used [rule_format]: 
214      "x \<in> used (takeWhile P X) \<longrightarrow> x \<in> used X"
215apply (induct_tac "X")
216apply simp
217apply (rename_tac a b)
218apply (induct_tac "a")
219apply (simp_all add: used_Nil)
220apply (blast dest!: initState_into_used)+
221done
222
223lemma set_evs_rev: "set evs = set (rev evs)"
224apply auto
225done
226
227lemma takeWhile_void [rule_format]:
228      "x \<notin> set evs \<longrightarrow> takeWhile (\<lambda>z. z \<noteq> x) evs = evs"
229apply auto
230done
231
232(**** Inductive proofs about bankerberos ****)
233
234text\<open>Forwarding Lemma for reasoning about the encrypted portion of message BK3\<close>
235lemma BK3_msg_in_parts_spies:
236     "Says S A (Crypt KA \<lbrace>Timestamp, B, K, X\<rbrace>) \<in> set evs
237      \<Longrightarrow> X \<in> parts (spies evs)"
238apply blast
239done
240
241lemma Oops_parts_spies:
242     "Says Server A (Crypt (shrK A) \<lbrace>Timestamp, B, K, X\<rbrace>) \<in> set evs
243      \<Longrightarrow> K \<in> parts (spies evs)"
244apply blast
245done
246
247text\<open>Spy never sees another agent's shared key! (unless it's bad at start)\<close>
248lemma Spy_see_shrK [simp]:
249     "evs \<in> bankerberos \<Longrightarrow> (Key (shrK A) \<in> parts (spies evs)) = (A \<in> bad)"
250apply (erule bankerberos.induct)
251apply (frule_tac [7] Oops_parts_spies)
252apply (frule_tac [5] BK3_msg_in_parts_spies, simp_all, blast+)
253done
254
255
256lemma Spy_analz_shrK [simp]:
257     "evs \<in> bankerberos \<Longrightarrow> (Key (shrK A) \<in> analz (spies evs)) = (A \<in> bad)"
258apply auto
259done
260
261lemma Spy_see_shrK_D [dest!]:
262     "\<lbrakk> Key (shrK A) \<in> parts (spies evs);
263                evs \<in> bankerberos \<rbrakk> \<Longrightarrow> A\<in>bad"
264apply (blast dest: Spy_see_shrK)
265done
266
267lemmas Spy_analz_shrK_D = analz_subset_parts [THEN subsetD, THEN Spy_see_shrK_D,  dest!]
268
269
270text\<open>Nobody can have used non-existent keys!\<close>
271lemma new_keys_not_used [simp]:
272    "\<lbrakk>Key K \<notin> used evs; K \<in> symKeys; evs \<in> bankerberos\<rbrakk>
273     \<Longrightarrow> K \<notin> keysFor (parts (spies evs))"
274apply (erule rev_mp)
275apply (erule bankerberos.induct)
276apply (frule_tac [7] Oops_parts_spies)
277apply (frule_tac [5] BK3_msg_in_parts_spies, simp_all)
278txt\<open>Fake\<close>
279apply (force dest!: keysFor_parts_insert)
280txt\<open>BK2, BK3, BK4\<close>
281apply (force dest!: analz_shrK_Decrypt)+
282done
283
284subsection\<open>Lemmas concerning the form of items passed in messages\<close>
285
286text\<open>Describes the form of K, X and K' when the Server sends this message.\<close>
287lemma Says_Server_message_form:
288     "\<lbrakk> Says Server A (Crypt K' \<lbrace>Number Tk, Agent B, Key K, Ticket\<rbrace>)
289         \<in> set evs; evs \<in> bankerberos \<rbrakk>
290      \<Longrightarrow> K' = shrK A \<and> K \<notin> range shrK \<and>
291          Ticket = (Crypt (shrK B) \<lbrace>Number Tk, Agent A, Key K\<rbrace>) \<and>
292          Key K \<notin> used(before
293                  Says Server A (Crypt K' \<lbrace>Number Tk, Agent B, Key K, Ticket\<rbrace>)
294                  on evs) \<and>
295          Tk = CT(before 
296                  Says Server A (Crypt K' \<lbrace>Number Tk, Agent B, Key K, Ticket\<rbrace>)
297                  on evs)"
298apply (unfold before_def)
299apply (erule rev_mp)
300apply (erule bankerberos.induct, simp_all add: takeWhile_tail)
301apply auto
302 apply (metis length_rev set_rev takeWhile_void used_evs_rev)+
303done
304
305
306text\<open>If the encrypted message appears then it originated with the Server
307  PROVIDED that A is NOT compromised!
308  This allows A to verify freshness of the session key.
309\<close>
310lemma Kab_authentic:
311     "\<lbrakk> Crypt (shrK A) \<lbrace>Number Tk, Agent B, Key K, X\<rbrace>
312           \<in> parts (spies evs);
313         A \<notin> bad;  evs \<in> bankerberos \<rbrakk>
314       \<Longrightarrow> Says Server A (Crypt (shrK A) \<lbrace>Number Tk, Agent B, Key K, X\<rbrace>)
315             \<in> set evs"
316apply (erule rev_mp)
317apply (erule bankerberos.induct)
318apply (frule_tac [7] Oops_parts_spies)
319apply (frule_tac [5] BK3_msg_in_parts_spies, simp_all, blast)
320done
321
322
323text\<open>If the TICKET appears then it originated with the Server\<close>
324text\<open>FRESHNESS OF THE SESSION KEY to B\<close>
325lemma ticket_authentic:
326     "\<lbrakk> Crypt (shrK B) \<lbrace>Number Tk, Agent A, Key K\<rbrace> \<in> parts (spies evs);
327         B \<notin> bad;  evs \<in> bankerberos \<rbrakk>
328       \<Longrightarrow> Says Server A
329            (Crypt (shrK A) \<lbrace>Number Tk, Agent B, Key K,
330                          Crypt (shrK B) \<lbrace>Number Tk, Agent A, Key K\<rbrace>\<rbrace>)
331           \<in> set evs"
332apply (erule rev_mp)
333apply (erule bankerberos.induct)
334apply (frule_tac [7] Oops_parts_spies)
335apply (frule_tac [5] BK3_msg_in_parts_spies, simp_all, blast)
336done
337
338
339text\<open>EITHER describes the form of X when the following message is sent,
340  OR     reduces it to the Fake case.
341  Use \<open>Says_Server_message_form\<close> if applicable.\<close>
342lemma Says_S_message_form:
343     "\<lbrakk> Says S A (Crypt (shrK A) \<lbrace>Number Tk, Agent B, Key K, X\<rbrace>)
344            \<in> set evs;
345         evs \<in> bankerberos \<rbrakk>
346 \<Longrightarrow> (K \<notin> range shrK \<and> X = (Crypt (shrK B) \<lbrace>Number Tk, Agent A, Key K\<rbrace>))
347          | X \<in> analz (spies evs)"
348apply (case_tac "A \<in> bad")
349apply (force dest!: Says_imp_spies [THEN analz.Inj])
350apply (frule Says_imp_spies [THEN parts.Inj])
351apply (blast dest!: Kab_authentic Says_Server_message_form)
352done
353
354
355
356(****
357 The following is to prove theorems of the form
358
359  Key K \<in> analz (insert (Key KAB) (spies evs)) \<Longrightarrow>
360  Key K \<in> analz (spies evs)
361
362 A more general formula must be proved inductively.
363
364****)
365
366text\<open>Session keys are not used to encrypt other session keys\<close>
367lemma analz_image_freshK [rule_format (no_asm)]:
368     "evs \<in> bankerberos \<Longrightarrow>
369   \<forall>K KK. KK \<subseteq> - (range shrK) \<longrightarrow>
370          (Key K \<in> analz (Key`KK \<union> (spies evs))) =
371          (K \<in> KK | Key K \<in> analz (spies evs))"
372apply (erule bankerberos.induct)
373apply (drule_tac [7] Says_Server_message_form)
374apply (erule_tac [5] Says_S_message_form [THEN disjE], analz_freshK, spy_analz, auto) 
375done
376
377
378lemma analz_insert_freshK:
379     "\<lbrakk> evs \<in> bankerberos;  KAB \<notin> range shrK \<rbrakk> \<Longrightarrow>
380      (Key K \<in> analz (insert (Key KAB) (spies evs))) =
381      (K = KAB | Key K \<in> analz (spies evs))"
382apply (simp only: analz_image_freshK analz_image_freshK_simps)
383done
384
385text\<open>The session key K uniquely identifies the message\<close>
386lemma unique_session_keys:
387     "\<lbrakk> Says Server A
388           (Crypt (shrK A) \<lbrace>Number Tk, Agent B, Key K, X\<rbrace>) \<in> set evs;
389         Says Server A'
390          (Crypt (shrK A') \<lbrace>Number Tk', Agent B', Key K, X'\<rbrace>) \<in> set evs;
391         evs \<in> bankerberos \<rbrakk> \<Longrightarrow> A=A' \<and> Tk=Tk' \<and> B=B' \<and> X = X'"
392apply (erule rev_mp)
393apply (erule rev_mp)
394apply (erule bankerberos.induct)
395apply (frule_tac [7] Oops_parts_spies)
396apply (frule_tac [5] BK3_msg_in_parts_spies, simp_all)
397txt\<open>BK2: it can't be a new key\<close>
398apply blast
399done
400
401lemma Server_Unique:
402     "\<lbrakk> Says Server A
403            (Crypt (shrK A) \<lbrace>Number Tk, Agent B, Key K, Ticket\<rbrace>) \<in> set evs;
404        evs \<in> bankerberos \<rbrakk> \<Longrightarrow> 
405   Unique Says Server A (Crypt (shrK A) \<lbrace>Number Tk, Agent B, Key K, Ticket\<rbrace>)
406   on evs"
407apply (erule rev_mp, erule bankerberos.induct, simp_all add: Unique_def)
408apply blast
409done
410
411
412subsection\<open>Non-temporal guarantees, explicitly relying on non-occurrence of
413oops events - refined below by temporal guarantees\<close>
414
415text\<open>Non temporal treatment of confidentiality\<close>
416
417text\<open>Lemma: the session key sent in msg BK2 would be lost by oops
418    if the spy could see it!\<close>
419lemma lemma_conf [rule_format (no_asm)]:
420     "\<lbrakk> A \<notin> bad;  B \<notin> bad;  evs \<in> bankerberos \<rbrakk>
421  \<Longrightarrow> Says Server A
422          (Crypt (shrK A) \<lbrace>Number Tk, Agent B, Key K,
423                            Crypt (shrK B) \<lbrace>Number Tk, Agent A, Key K\<rbrace>\<rbrace>)
424         \<in> set evs \<longrightarrow>
425      Key K \<in> analz (spies evs) \<longrightarrow> Notes Spy \<lbrace>Number Tk, Key K\<rbrace> \<in> set evs"
426apply (erule bankerberos.induct)
427apply (frule_tac [7] Says_Server_message_form)
428apply (frule_tac [5] Says_S_message_form [THEN disjE])
429apply (simp_all (no_asm_simp) add: analz_insert_eq analz_insert_freshK pushes)
430txt\<open>Fake\<close>
431apply spy_analz
432txt\<open>BK2\<close>
433apply (blast intro: parts_insertI)
434txt\<open>BK3\<close>
435apply (case_tac "Aa \<in> bad")
436 prefer 2 apply (blast dest: Kab_authentic unique_session_keys)
437apply (blast dest: Says_imp_spies [THEN analz.Inj] Crypt_Spy_analz_bad elim!: MPair_analz)
438txt\<open>Oops\<close>
439apply (blast dest: unique_session_keys)
440done
441
442
443text\<open>Confidentiality for the Server: Spy does not see the keys sent in msg BK2
444as long as they have not expired.\<close>
445lemma Confidentiality_S:
446     "\<lbrakk> Says Server A
447          (Crypt K' \<lbrace>Number Tk, Agent B, Key K, Ticket\<rbrace>) \<in> set evs;
448        Notes Spy \<lbrace>Number Tk, Key K\<rbrace> \<notin> set evs;
449         A \<notin> bad;  B \<notin> bad;  evs \<in> bankerberos
450      \<rbrakk> \<Longrightarrow> Key K \<notin> analz (spies evs)"
451apply (frule Says_Server_message_form, assumption)
452apply (blast intro: lemma_conf)
453done
454
455text\<open>Confidentiality for Alice\<close>
456lemma Confidentiality_A:
457     "\<lbrakk> Crypt (shrK A) \<lbrace>Number Tk, Agent B, Key K, X\<rbrace> \<in> parts (spies evs);
458        Notes Spy \<lbrace>Number Tk, Key K\<rbrace> \<notin> set evs;
459        A \<notin> bad;  B \<notin> bad;  evs \<in> bankerberos
460      \<rbrakk> \<Longrightarrow> Key K \<notin> analz (spies evs)"
461apply (blast dest!: Kab_authentic Confidentiality_S)
462done
463
464text\<open>Confidentiality for Bob\<close>
465lemma Confidentiality_B:
466     "\<lbrakk> Crypt (shrK B) \<lbrace>Number Tk, Agent A, Key K\<rbrace>
467          \<in> parts (spies evs);
468        Notes Spy \<lbrace>Number Tk, Key K\<rbrace> \<notin> set evs;
469        A \<notin> bad;  B \<notin> bad;  evs \<in> bankerberos
470      \<rbrakk> \<Longrightarrow> Key K \<notin> analz (spies evs)"
471apply (blast dest!: ticket_authentic Confidentiality_S)
472done
473
474text\<open>Non temporal treatment of authentication\<close>
475
476text\<open>Lemmas \<open>lemma_A\<close> and \<open>lemma_B\<close> in fact are common to both temporal and non-temporal treatments\<close>
477lemma lemma_A [rule_format]:
478     "\<lbrakk> A \<notin> bad; B \<notin> bad; evs \<in> bankerberos \<rbrakk>
479      \<Longrightarrow>
480         Key K \<notin> analz (spies evs) \<longrightarrow>
481         Says Server A (Crypt (shrK A) \<lbrace>Number Tk, Agent B, Key K, X\<rbrace>)
482         \<in> set evs \<longrightarrow>
483          Crypt K \<lbrace>Agent A, Number Ta\<rbrace> \<in> parts (spies evs) \<longrightarrow>
484         Says A B \<lbrace>X, Crypt K \<lbrace>Agent A, Number Ta\<rbrace>\<rbrace>
485             \<in> set evs"
486apply (erule bankerberos.induct)
487apply (frule_tac [7] Oops_parts_spies)
488apply (frule_tac [5] Says_S_message_form)
489apply (frule_tac [6] BK3_msg_in_parts_spies, analz_mono_contra)
490apply (simp_all (no_asm_simp) add: all_conj_distrib)
491txt\<open>Fake\<close>
492apply blast
493txt\<open>BK2\<close>
494apply (force dest: Crypt_imp_invKey_keysFor)
495txt\<open>BK3\<close>
496apply (blast dest: Kab_authentic unique_session_keys)
497done
498
499lemma lemma_B [rule_format]:
500     "\<lbrakk> B \<notin> bad;  evs \<in> bankerberos \<rbrakk>
501      \<Longrightarrow> Key K \<notin> analz (spies evs) \<longrightarrow>
502          Says Server A (Crypt (shrK A) \<lbrace>Number Tk, Agent B, Key K, X\<rbrace>)
503          \<in> set evs \<longrightarrow>
504          Crypt K (Number Ta) \<in> parts (spies evs) \<longrightarrow>
505          Says B A (Crypt K (Number Ta)) \<in> set evs"
506apply (erule bankerberos.induct)
507apply (frule_tac [7] Oops_parts_spies)
508apply (frule_tac [5] Says_S_message_form)
509apply (drule_tac [6] BK3_msg_in_parts_spies, analz_mono_contra)
510apply (simp_all (no_asm_simp) add: all_conj_distrib)
511txt\<open>Fake\<close>
512apply blast
513txt\<open>BK2\<close> 
514apply (force dest: Crypt_imp_invKey_keysFor)
515txt\<open>BK4\<close>
516apply (blast dest: ticket_authentic unique_session_keys
517                   Says_imp_spies [THEN analz.Inj] Crypt_Spy_analz_bad)
518done
519
520
521text\<open>The "r" suffix indicates theorems where the confidentiality assumptions are relaxed by the corresponding arguments.\<close>
522
523
524text\<open>Authentication of A to B\<close>
525lemma B_authenticates_A_r:
526     "\<lbrakk> Crypt K \<lbrace>Agent A, Number Ta\<rbrace> \<in> parts (spies evs);
527         Crypt (shrK B) \<lbrace>Number Tk, Agent A, Key K\<rbrace>  \<in> parts (spies evs);
528        Notes Spy \<lbrace>Number Tk, Key K\<rbrace> \<notin> set evs;
529         A \<notin> bad;  B \<notin> bad;  evs \<in> bankerberos \<rbrakk>
530      \<Longrightarrow> Says A B \<lbrace>Crypt (shrK B) \<lbrace>Number Tk, Agent A, Key K\<rbrace>,
531                     Crypt K \<lbrace>Agent A, Number Ta\<rbrace>\<rbrace> \<in> set evs"
532apply (blast dest!: ticket_authentic
533          intro!: lemma_A
534          elim!: Confidentiality_S [THEN [2] rev_notE])
535done
536
537
538text\<open>Authentication of B to A\<close>
539lemma A_authenticates_B_r:
540     "\<lbrakk> Crypt K (Number Ta) \<in> parts (spies evs);
541        Crypt (shrK A) \<lbrace>Number Tk, Agent B, Key K, X\<rbrace> \<in> parts (spies evs);
542        Notes Spy \<lbrace>Number Tk, Key K\<rbrace> \<notin> set evs;
543        A \<notin> bad;  B \<notin> bad;  evs \<in> bankerberos \<rbrakk>
544      \<Longrightarrow> Says B A (Crypt K (Number Ta)) \<in> set evs"
545apply (blast dest!: Kab_authentic
546          intro!: lemma_B elim!: Confidentiality_S [THEN [2] rev_notE])
547done
548
549lemma B_authenticates_A:
550     "\<lbrakk> Crypt K \<lbrace>Agent A, Number Ta\<rbrace> \<in> parts (spies evs);
551         Crypt (shrK B) \<lbrace>Number Tk, Agent A, Key K\<rbrace>  \<in> parts (spies evs);
552        Key K \<notin> analz (spies evs);
553         A \<notin> bad;  B \<notin> bad;  evs \<in> bankerberos \<rbrakk>
554      \<Longrightarrow> Says A B \<lbrace>Crypt (shrK B) \<lbrace>Number Tk, Agent A, Key K\<rbrace>,
555                     Crypt K \<lbrace>Agent A, Number Ta\<rbrace>\<rbrace> \<in> set evs"
556apply (blast dest!: ticket_authentic intro!: lemma_A)
557done
558
559lemma A_authenticates_B:
560     "\<lbrakk> Crypt K (Number Ta) \<in> parts (spies evs);
561        Crypt (shrK A) \<lbrace>Number Tk, Agent B, Key K, X\<rbrace> \<in> parts (spies evs);
562        Key K \<notin> analz (spies evs);
563        A \<notin> bad;  B \<notin> bad;  evs \<in> bankerberos \<rbrakk>
564      \<Longrightarrow> Says B A (Crypt K (Number Ta)) \<in> set evs"
565apply (blast dest!: Kab_authentic intro!: lemma_B)
566done
567
568subsection\<open>Temporal guarantees, relying on a temporal check that insures that
569no oops event occurred. These are available in the sense of goal availability\<close>
570
571
572text\<open>Temporal treatment of confidentiality\<close>
573
574text\<open>Lemma: the session key sent in msg BK2 would be EXPIRED
575    if the spy could see it!\<close>
576lemma lemma_conf_temporal [rule_format (no_asm)]:
577     "\<lbrakk> A \<notin> bad;  B \<notin> bad;  evs \<in> bankerberos \<rbrakk>
578  \<Longrightarrow> Says Server A
579          (Crypt (shrK A) \<lbrace>Number Tk, Agent B, Key K,
580                            Crypt (shrK B) \<lbrace>Number Tk, Agent A, Key K\<rbrace>\<rbrace>)
581         \<in> set evs \<longrightarrow>
582      Key K \<in> analz (spies evs) \<longrightarrow> expiredK Tk evs"
583apply (erule bankerberos.induct)
584apply (frule_tac [7] Says_Server_message_form)
585apply (frule_tac [5] Says_S_message_form [THEN disjE])
586apply (simp_all (no_asm_simp) add: less_SucI analz_insert_eq analz_insert_freshK pushes)
587txt\<open>Fake\<close>
588apply spy_analz
589txt\<open>BK2\<close>
590apply (blast intro: parts_insertI less_SucI)
591txt\<open>BK3\<close>
592apply (metis Crypt_Spy_analz_bad Kab_authentic Says_imp_analz_Spy 
593          Says_imp_parts_knows_Spy analz.Snd less_SucI unique_session_keys)
594txt\<open>Oops: PROOF FAILS if unsafe intro below\<close>
595apply (blast dest: unique_session_keys intro!: less_SucI)
596done
597
598
599text\<open>Confidentiality for the Server: Spy does not see the keys sent in msg BK2
600as long as they have not expired.\<close>
601lemma Confidentiality_S_temporal:
602     "\<lbrakk> Says Server A
603          (Crypt K' \<lbrace>Number T, Agent B, Key K, X\<rbrace>) \<in> set evs;
604         \<not> expiredK T evs;
605         A \<notin> bad;  B \<notin> bad;  evs \<in> bankerberos
606      \<rbrakk> \<Longrightarrow> Key K \<notin> analz (spies evs)"
607apply (frule Says_Server_message_form, assumption)
608apply (blast intro: lemma_conf_temporal)
609done
610
611text\<open>Confidentiality for Alice\<close>
612lemma Confidentiality_A_temporal:
613     "\<lbrakk> Crypt (shrK A) \<lbrace>Number T, Agent B, Key K, X\<rbrace> \<in> parts (spies evs);
614         \<not> expiredK T evs;
615         A \<notin> bad;  B \<notin> bad;  evs \<in> bankerberos
616      \<rbrakk> \<Longrightarrow> Key K \<notin> analz (spies evs)"
617apply (blast dest!: Kab_authentic Confidentiality_S_temporal)
618done
619
620text\<open>Confidentiality for Bob\<close>
621lemma Confidentiality_B_temporal:
622     "\<lbrakk> Crypt (shrK B) \<lbrace>Number Tk, Agent A, Key K\<rbrace>
623          \<in> parts (spies evs);
624        \<not> expiredK Tk evs;
625        A \<notin> bad;  B \<notin> bad;  evs \<in> bankerberos
626      \<rbrakk> \<Longrightarrow> Key K \<notin> analz (spies evs)"
627apply (blast dest!: ticket_authentic Confidentiality_S_temporal)
628done
629
630text\<open>Temporal treatment of authentication\<close>
631
632text\<open>Authentication of A to B\<close>
633lemma B_authenticates_A_temporal:
634     "\<lbrakk> Crypt K \<lbrace>Agent A, Number Ta\<rbrace> \<in> parts (spies evs);
635         Crypt (shrK B) \<lbrace>Number Tk, Agent A, Key K\<rbrace>
636         \<in> parts (spies evs);
637         \<not> expiredK Tk evs;
638         A \<notin> bad;  B \<notin> bad;  evs \<in> bankerberos \<rbrakk>
639      \<Longrightarrow> Says A B \<lbrace>Crypt (shrK B) \<lbrace>Number Tk, Agent A, Key K\<rbrace>,
640                     Crypt K \<lbrace>Agent A, Number Ta\<rbrace>\<rbrace> \<in> set evs"
641apply (blast dest!: ticket_authentic
642          intro!: lemma_A
643          elim!: Confidentiality_S_temporal [THEN [2] rev_notE])
644done
645
646text\<open>Authentication of B to A\<close>
647lemma A_authenticates_B_temporal:
648     "\<lbrakk> Crypt K (Number Ta) \<in> parts (spies evs);
649         Crypt (shrK A) \<lbrace>Number Tk, Agent B, Key K, X\<rbrace>
650         \<in> parts (spies evs);
651         \<not> expiredK Tk evs;
652         A \<notin> bad;  B \<notin> bad;  evs \<in> bankerberos \<rbrakk>
653      \<Longrightarrow> Says B A (Crypt K (Number Ta)) \<in> set evs"
654apply (blast dest!: Kab_authentic
655          intro!: lemma_B elim!: Confidentiality_S_temporal [THEN [2] rev_notE])
656done
657
658subsection\<open>Treatment of the key distribution goal using trace inspection. All
659guarantees are in non-temporal form, hence non available, though their temporal
660form is trivial to derive. These guarantees also convey a stronger form of 
661authentication - non-injective agreement on the session key\<close>
662
663
664lemma B_Issues_A:
665     "\<lbrakk> Says B A (Crypt K (Number Ta)) \<in> set evs;
666         Key K \<notin> analz (spies evs);
667         A \<notin> bad;  B \<notin> bad; evs \<in> bankerberos \<rbrakk>
668      \<Longrightarrow> B Issues A with (Crypt K (Number Ta)) on evs"
669apply (simp (no_asm) add: Issues_def)
670apply (rule exI)
671apply (rule conjI, assumption)
672apply (simp (no_asm))
673apply (erule rev_mp)
674apply (erule rev_mp)
675apply (erule bankerberos.induct, analz_mono_contra)
676apply (simp_all (no_asm_simp))
677txt\<open>fake\<close>
678apply blast
679txt\<open>K4 obviously is the non-trivial case\<close>
680apply (simp add: takeWhile_tail)
681apply (blast dest: ticket_authentic parts_spies_takeWhile_mono [THEN subsetD] parts_spies_evs_revD2 [THEN subsetD] intro: A_authenticates_B_temporal)
682done
683
684lemma A_authenticates_and_keydist_to_B:
685     "\<lbrakk> Crypt K (Number Ta) \<in> parts (spies evs);
686        Crypt (shrK A) \<lbrace>Number Tk, Agent B, Key K, X\<rbrace> \<in> parts (spies evs);
687         Key K \<notin> analz (spies evs);
688         A \<notin> bad;  B \<notin> bad; evs \<in> bankerberos \<rbrakk>
689      \<Longrightarrow> B Issues A with (Crypt K (Number Ta)) on evs"
690apply (blast dest!: A_authenticates_B B_Issues_A)
691done
692
693
694lemma A_Issues_B:
695     "\<lbrakk> Says A B \<lbrace>Ticket, Crypt K \<lbrace>Agent A, Number Ta\<rbrace>\<rbrace>
696           \<in> set evs;
697         Key K \<notin> analz (spies evs);
698         A \<notin> bad;  B \<notin> bad;  evs \<in> bankerberos \<rbrakk>
699   \<Longrightarrow> A Issues B with (Crypt K \<lbrace>Agent A, Number Ta\<rbrace>) on evs"
700apply (simp (no_asm) add: Issues_def)
701apply (rule exI)
702apply (rule conjI, assumption)
703apply (simp (no_asm))
704apply (erule rev_mp)
705apply (erule rev_mp)
706apply (erule bankerberos.induct, analz_mono_contra)
707apply (simp_all (no_asm_simp))
708txt\<open>fake\<close>
709apply blast
710txt\<open>K3 is the non trivial case\<close>
711apply (simp add: takeWhile_tail)
712apply auto (*Technically unnecessary, merely clarifies the subgoal as it is presemted in the book*)
713apply (blast dest: Kab_authentic Says_Server_message_form parts_spies_takeWhile_mono [THEN subsetD] parts_spies_evs_revD2 [THEN subsetD] 
714             intro!: B_authenticates_A)
715done
716
717
718lemma B_authenticates_and_keydist_to_A:
719     "\<lbrakk> Crypt K \<lbrace>Agent A, Number Ta\<rbrace> \<in> parts (spies evs);
720        Crypt (shrK B) \<lbrace>Number Tk, Agent A, Key K\<rbrace>  \<in> parts (spies evs);
721        Key K \<notin> analz (spies evs);
722        A \<notin> bad;  B \<notin> bad;  evs \<in> bankerberos \<rbrakk>
723   \<Longrightarrow> A Issues B with (Crypt K \<lbrace>Agent A, Number Ta\<rbrace>) on evs"
724apply (blast dest: B_authenticates_A A_Issues_B)
725done
726
727
728
729
730end
731