src/HOL/Auth/KerberosV.thy
changeset 61830 4f5ab843cf5b
parent 58889 5b7a9633cfa8
child 67443 3abf6a722518
equal deleted inserted replaced
61829:55c85d25e18c 61830:4f5ab843cf5b
     1 (*  Title:      HOL/Auth/KerberosV.thy
     1 (*  Title:      HOL/Auth/KerberosV.thy
     2     Author:     Giampaolo Bella, Catania University
     2     Author:     Giampaolo Bella, Catania University
     3 *)
     3 *)
     4 
     4 
     5 section{*The Kerberos Protocol, Version V*}
     5 section\<open>The Kerberos Protocol, Version V\<close>
     6 
     6 
     7 theory KerberosV imports Public begin
     7 theory KerberosV imports Public begin
     8 
     8 
     9 text{*The "u" prefix indicates theorems referring to an updated version of the protocol. The "r" suffix indicates theorems where the confidentiality assumptions are relaxed by the corresponding arguments.*}
     9 text\<open>The "u" prefix indicates theorems referring to an updated version of the protocol. The "r" suffix indicates theorems where the confidentiality assumptions are relaxed by the corresponding arguments.\<close>
    10 
    10 
    11 abbreviation
    11 abbreviation
    12   Kas :: agent where
    12   Kas :: agent where
    13   "Kas == Server"
    13   "Kas == Server"
    14 
    14 
    17   "Tgs == Friend 0"
    17   "Tgs == Friend 0"
    18 
    18 
    19 
    19 
    20 axiomatization where
    20 axiomatization where
    21   Tgs_not_bad [iff]: "Tgs \<notin> bad"
    21   Tgs_not_bad [iff]: "Tgs \<notin> bad"
    22    --{*Tgs is secure --- we already know that Kas is secure*}
    22    \<comment>\<open>Tgs is secure --- we already know that Kas is secure\<close>
    23 
    23 
    24 definition
    24 definition
    25  (* authKeys are those contained in an authTicket *)
    25  (* authKeys are those contained in an authTicket *)
    26     authKeys :: "event list => key set" where
    26     authKeys :: "event list => key set" where
    27     "authKeys evs = {authK. \<exists>A Peer Ta. 
    27     "authKeys evs = {authK. \<exists>A Peer Ta. 
   201 declare analz_into_parts [dest]
   201 declare analz_into_parts [dest]
   202 declare Fake_parts_insert_in_Un [dest]
   202 declare Fake_parts_insert_in_Un [dest]
   203 
   203 
   204 
   204 
   205 
   205 
   206 subsection{*Lemmas about lists, for reasoning about  Issues*}
   206 subsection\<open>Lemmas about lists, for reasoning about  Issues\<close>
   207 
   207 
   208 lemma spies_Says_rev: "spies (evs @ [Says A B X]) = insert X (spies evs)"
   208 lemma spies_Says_rev: "spies (evs @ [Says A B X]) = insert X (spies evs)"
   209 apply (induct_tac "evs")
   209 apply (induct_tac "evs")
   210 apply (rename_tac [2] a b)
   210 apply (rename_tac [2] a b)
   211 apply (induct_tac [2] "a", auto)
   211 apply (induct_tac [2] "a", auto)
   235 
   235 
   236 lemma spies_takeWhile: "spies (takeWhile P evs) <=  spies evs"
   236 lemma spies_takeWhile: "spies (takeWhile P evs) <=  spies evs"
   237 apply (induct_tac "evs")
   237 apply (induct_tac "evs")
   238 apply (rename_tac [2] a b)
   238 apply (rename_tac [2] a b)
   239 apply (induct_tac [2] "a", auto)
   239 apply (induct_tac [2] "a", auto)
   240 txt{* Resembles @{text"used_subset_append"} in theory Event.*}
   240 txt\<open>Resembles \<open>used_subset_append\<close> in theory Event.\<close>
   241 done
   241 done
   242 
   242 
   243 lemmas parts_spies_takeWhile_mono = spies_takeWhile [THEN parts_mono]
   243 lemmas parts_spies_takeWhile_mono = spies_takeWhile [THEN parts_mono]
   244 
   244 
   245 
   245 
   246 subsection{*Lemmas about @{term authKeys}*}
   246 subsection\<open>Lemmas about @{term authKeys}\<close>
   247 
   247 
   248 lemma authKeys_empty: "authKeys [] = {}"
   248 lemma authKeys_empty: "authKeys [] = {}"
   249   by (simp add: authKeys_def)
   249   by (simp add: authKeys_def)
   250 
   250 
   251 lemma authKeys_not_insert:
   251 lemma authKeys_not_insert:
   277 
   277 
   278 lemma authKeys_used: "K \<in> authKeys evs \<Longrightarrow> Key K \<in> used evs"
   278 lemma authKeys_used: "K \<in> authKeys evs \<Longrightarrow> Key K \<in> used evs"
   279   by (auto simp add: authKeys_def)
   279   by (auto simp add: authKeys_def)
   280 
   280 
   281 
   281 
   282 subsection{*Forwarding Lemmas*}
   282 subsection\<open>Forwarding Lemmas\<close>
   283 
   283 
   284 lemma Says_ticket_parts:
   284 lemma Says_ticket_parts:
   285      "Says S A \<lbrace>Crypt K \<lbrace>SesKey, B, TimeStamp\<rbrace>, Ticket\<rbrace>
   285      "Says S A \<lbrace>Crypt K \<lbrace>SesKey, B, TimeStamp\<rbrace>, Ticket\<rbrace>
   286                \<in> set evs \<Longrightarrow> Ticket \<in> parts (spies evs)"
   286                \<in> set evs \<Longrightarrow> Ticket \<in> parts (spies evs)"
   287 by blast
   287 by blast
   325      "\<lbrakk> Key (shrK A) \<in> parts (spies evs);  evs \<in> kerbV \<rbrakk> \<Longrightarrow> A:bad"
   325      "\<lbrakk> Key (shrK A) \<in> parts (spies evs);  evs \<in> kerbV \<rbrakk> \<Longrightarrow> A:bad"
   326 by (blast dest: Spy_see_shrK)
   326 by (blast dest: Spy_see_shrK)
   327 
   327 
   328 lemmas Spy_analz_shrK_D = analz_subset_parts [THEN subsetD, THEN Spy_see_shrK_D, dest!]
   328 lemmas Spy_analz_shrK_D = analz_subset_parts [THEN subsetD, THEN Spy_see_shrK_D, dest!]
   329 
   329 
   330 text{*Nobody can have used non-existent keys!*}
   330 text\<open>Nobody can have used non-existent keys!\<close>
   331 lemma new_keys_not_used [simp]:
   331 lemma new_keys_not_used [simp]:
   332     "\<lbrakk>Key K \<notin> used evs; K \<in> symKeys; evs \<in> kerbV\<rbrakk>
   332     "\<lbrakk>Key K \<notin> used evs; K \<in> symKeys; evs \<in> kerbV\<rbrakk>
   333      \<Longrightarrow> K \<notin> keysFor (parts (spies evs))"
   333      \<Longrightarrow> K \<notin> keysFor (parts (spies evs))"
   334 apply (erule rev_mp)
   334 apply (erule rev_mp)
   335 apply (erule kerbV.induct)
   335 apply (erule kerbV.induct)
   336 apply (frule_tac [7] Says_ticket_parts)
   336 apply (frule_tac [7] Says_ticket_parts)
   337 apply (frule_tac [5] Says_ticket_parts, simp_all)
   337 apply (frule_tac [5] Says_ticket_parts, simp_all)
   338 txt{*Fake*}
   338 txt\<open>Fake\<close>
   339 apply (force dest!: keysFor_parts_insert)
   339 apply (force dest!: keysFor_parts_insert)
   340 txt{*Others*}
   340 txt\<open>Others\<close>
   341 apply (force dest!: analz_shrK_Decrypt)+
   341 apply (force dest!: analz_shrK_Decrypt)+
   342 done
   342 done
   343 
   343 
   344 (*Earlier, all protocol proofs declared this theorem.
   344 (*Earlier, all protocol proofs declared this theorem.
   345   But few of them actually need it! (Another is Yahalom) *)
   345   But few of them actually need it! (Another is Yahalom) *)
   348   \<Longrightarrow> K \<notin> keysFor (analz (spies evs))"
   348   \<Longrightarrow> K \<notin> keysFor (analz (spies evs))"
   349 by (blast dest: new_keys_not_used intro: keysFor_mono [THEN subsetD])
   349 by (blast dest: new_keys_not_used intro: keysFor_mono [THEN subsetD])
   350 
   350 
   351 
   351 
   352 
   352 
   353 subsection{*Regularity Lemmas*}
   353 subsection\<open>Regularity Lemmas\<close>
   354 text{*These concern the form of items passed in messages*}
   354 text\<open>These concern the form of items passed in messages\<close>
   355 
   355 
   356 text{*Describes the form of all components sent by Kas*}
   356 text\<open>Describes the form of all components sent by Kas\<close>
   357 lemma Says_Kas_message_form:
   357 lemma Says_Kas_message_form:
   358      "\<lbrakk> Says Kas A \<lbrace>Crypt K \<lbrace>Key authK, Agent Peer, Ta\<rbrace>, authTicket\<rbrace>
   358      "\<lbrakk> Says Kas A \<lbrace>Crypt K \<lbrace>Key authK, Agent Peer, Ta\<rbrace>, authTicket\<rbrace>
   359            \<in> set evs;
   359            \<in> set evs;
   360          evs \<in> kerbV \<rbrakk>
   360          evs \<in> kerbV \<rbrakk>
   361       \<Longrightarrow> authK \<notin> range shrK \<and> authK \<in> authKeys evs \<and> authK \<in> symKeys \<and> 
   361       \<Longrightarrow> authK \<notin> range shrK \<and> authK \<in> authKeys evs \<and> authK \<in> symKeys \<and> 
   397             \<in> set evs"
   397             \<in> set evs"
   398 apply (erule rev_mp)
   398 apply (erule rev_mp)
   399 apply (erule kerbV.induct)
   399 apply (erule kerbV.induct)
   400 apply (frule_tac [7] Says_ticket_parts)
   400 apply (frule_tac [7] Says_ticket_parts)
   401 apply (frule_tac [5] Says_ticket_parts, simp_all)
   401 apply (frule_tac [5] Says_ticket_parts, simp_all)
   402 txt{*Fake, K4*}
   402 txt\<open>Fake, K4\<close>
   403 apply (blast+)
   403 apply (blast+)
   404 done
   404 done
   405 
   405 
   406 lemma authTicket_crypt_authK:
   406 lemma authTicket_crypt_authK:
   407      "\<lbrakk> Crypt (shrK Tgs) \<lbrace>Agent A, Agent Tgs, Key authK, Number Ta\<rbrace>
   407      "\<lbrakk> Crypt (shrK Tgs) \<lbrace>Agent A, Agent Tgs, Key authK, Number Ta\<rbrace>
   408            \<in> parts (spies evs);
   408            \<in> parts (spies evs);
   409          evs \<in> kerbV \<rbrakk>
   409          evs \<in> kerbV \<rbrakk>
   410       \<Longrightarrow> authK \<in> authKeys evs"
   410       \<Longrightarrow> authK \<in> authKeys evs"
   411 by (metis authKeysI authTicket_authentic)
   411 by (metis authKeysI authTicket_authentic)
   412 
   412 
   413 text{*Describes the form of servK, servTicket and authK sent by Tgs*}
   413 text\<open>Describes the form of servK, servTicket and authK sent by Tgs\<close>
   414 lemma Says_Tgs_message_form:
   414 lemma Says_Tgs_message_form:
   415      "\<lbrakk> Says Tgs A \<lbrace>Crypt authK \<lbrace>Key servK, Agent B, Ts\<rbrace>, servTicket\<rbrace>
   415      "\<lbrakk> Says Tgs A \<lbrace>Crypt authK \<lbrace>Key servK, Agent B, Ts\<rbrace>, servTicket\<rbrace>
   416            \<in> set evs;
   416            \<in> set evs;
   417          evs \<in> kerbV \<rbrakk>
   417          evs \<in> kerbV \<rbrakk>
   418    \<Longrightarrow> B \<noteq> Tgs \<and> 
   418    \<Longrightarrow> B \<noteq> Tgs \<and> 
   420        servTicket = (Crypt (shrK B) \<lbrace>Agent A, Agent B, Key servK, Ts\<rbrace>) \<and>
   420        servTicket = (Crypt (shrK B) \<lbrace>Agent A, Agent B, Key servK, Ts\<rbrace>) \<and>
   421        authK \<notin> range shrK \<and> authK \<in> authKeys evs \<and> authK \<in> symKeys"
   421        authK \<notin> range shrK \<and> authK \<in> authKeys evs \<and> authK \<in> symKeys"
   422 apply (erule rev_mp)
   422 apply (erule rev_mp)
   423 apply (erule kerbV.induct)
   423 apply (erule kerbV.induct)
   424 apply (simp_all add: authKeys_insert authKeys_not_insert authKeys_empty authKeys_simp, blast, auto)
   424 apply (simp_all add: authKeys_insert authKeys_not_insert authKeys_empty authKeys_simp, blast, auto)
   425 txt{*Three subcases of Message 4*}
   425 txt\<open>Three subcases of Message 4\<close>
   426 apply (blast dest!: authKeys_used Says_Kas_message_form)
   426 apply (blast dest!: authKeys_used Says_Kas_message_form)
   427 apply (blast dest!: SesKey_is_session_key)
   427 apply (blast dest!: SesKey_is_session_key)
   428 apply (blast dest: authTicket_crypt_authK)
   428 apply (blast dest: authTicket_crypt_authK)
   429 done
   429 done
   430 
   430 
   442 The new strategy always lets the simplifier solve cases K3 and K5, saving on
   442 The new strategy always lets the simplifier solve cases K3 and K5, saving on
   443 long dedicated analyses, which seemed unavoidable. For this reason, lemma 
   443 long dedicated analyses, which seemed unavoidable. For this reason, lemma 
   444 servK_notin_authKeysD is no longer needed.
   444 servK_notin_authKeysD is no longer needed.
   445 *)
   445 *)
   446 
   446 
   447 subsection{*Authenticity theorems: confirm origin of sensitive messages*}
   447 subsection\<open>Authenticity theorems: confirm origin of sensitive messages\<close>
   448 
   448 
   449 lemma authK_authentic:
   449 lemma authK_authentic:
   450      "\<lbrakk> Crypt (shrK A) \<lbrace>Key authK, Peer, Ta\<rbrace>
   450      "\<lbrakk> Crypt (shrK A) \<lbrace>Key authK, Peer, Ta\<rbrace>
   451            \<in> parts (spies evs);
   451            \<in> parts (spies evs);
   452          A \<notin> bad;  evs \<in> kerbV \<rbrakk>
   452          A \<notin> bad;  evs \<in> kerbV \<rbrakk>
   457 apply (frule_tac [7] Says_ticket_parts)
   457 apply (frule_tac [7] Says_ticket_parts)
   458 apply (frule_tac [5] Says_ticket_parts, simp_all)
   458 apply (frule_tac [5] Says_ticket_parts, simp_all)
   459 apply blast+
   459 apply blast+
   460 done
   460 done
   461 
   461 
   462 text{*If a certain encrypted message appears then it originated with Tgs*}
   462 text\<open>If a certain encrypted message appears then it originated with Tgs\<close>
   463 lemma servK_authentic:
   463 lemma servK_authentic:
   464      "\<lbrakk> Crypt authK \<lbrace>Key servK, Agent B, Ts\<rbrace>
   464      "\<lbrakk> Crypt authK \<lbrace>Key servK, Agent B, Ts\<rbrace>
   465            \<in> parts (spies evs);
   465            \<in> parts (spies evs);
   466          Key authK \<notin> analz (spies evs);
   466          Key authK \<notin> analz (spies evs);
   467          authK \<notin> range shrK;
   467          authK \<notin> range shrK;
   489 apply (erule kerbV.induct, analz_mono_contra)
   489 apply (erule kerbV.induct, analz_mono_contra)
   490 apply (frule_tac [7] Says_ticket_parts)
   490 apply (frule_tac [7] Says_ticket_parts)
   491 apply (frule_tac [5] Says_ticket_parts, simp_all, blast+)
   491 apply (frule_tac [5] Says_ticket_parts, simp_all, blast+)
   492 done
   492 done
   493 
   493 
   494 text{*Authenticity of servK for B*}
   494 text\<open>Authenticity of servK for B\<close>
   495 lemma servTicket_authentic_Tgs:
   495 lemma servTicket_authentic_Tgs:
   496      "\<lbrakk> Crypt (shrK B) \<lbrace>Agent A, Agent B, Key servK, Ts\<rbrace>
   496      "\<lbrakk> Crypt (shrK B) \<lbrace>Agent A, Agent B, Key servK, Ts\<rbrace>
   497            \<in> parts (spies evs);  B \<noteq> Tgs;  B \<notin> bad;
   497            \<in> parts (spies evs);  B \<noteq> Tgs;  B \<notin> bad;
   498          evs \<in> kerbV \<rbrakk>
   498          evs \<in> kerbV \<rbrakk>
   499  \<Longrightarrow> \<exists>authK.
   499  \<Longrightarrow> \<exists>authK.
   504 apply (erule kerbV.induct)
   504 apply (erule kerbV.induct)
   505 apply (frule_tac [7] Says_ticket_parts)
   505 apply (frule_tac [7] Says_ticket_parts)
   506 apply (frule_tac [5] Says_ticket_parts, simp_all, blast+)
   506 apply (frule_tac [5] Says_ticket_parts, simp_all, blast+)
   507 done
   507 done
   508 
   508 
   509 text{*Anticipated here from next subsection*}
   509 text\<open>Anticipated here from next subsection\<close>
   510 lemma K4_imp_K2:
   510 lemma K4_imp_K2:
   511 "\<lbrakk> Says Tgs A \<lbrace>Crypt authK \<lbrace>Key servK, Agent B, Number Ts\<rbrace>, servTicket\<rbrace>
   511 "\<lbrakk> Says Tgs A \<lbrace>Crypt authK \<lbrace>Key servK, Agent B, Number Ts\<rbrace>, servTicket\<rbrace>
   512       \<in> set evs;  evs \<in> kerbV\<rbrakk>
   512       \<in> set evs;  evs \<in> kerbV\<rbrakk>
   513    \<Longrightarrow> \<exists>Ta. Says Kas A
   513    \<Longrightarrow> \<exists>Ta. Says Kas A
   514         \<lbrace>Crypt (shrK A) \<lbrace>Key authK, Agent Tgs, Number Ta\<rbrace>,
   514         \<lbrace>Crypt (shrK A) \<lbrace>Key authK, Agent Tgs, Number Ta\<rbrace>,
   519 apply (frule_tac [7] Says_ticket_parts)
   519 apply (frule_tac [7] Says_ticket_parts)
   520 apply (frule_tac [5] Says_ticket_parts, simp_all, auto)
   520 apply (frule_tac [5] Says_ticket_parts, simp_all, auto)
   521 apply (metis MPair_analz Says_imp_analz_Spy analz_conj_parts authTicket_authentic)
   521 apply (metis MPair_analz Says_imp_analz_Spy analz_conj_parts authTicket_authentic)
   522 done
   522 done
   523 
   523 
   524 text{*Anticipated here from next subsection*}
   524 text\<open>Anticipated here from next subsection\<close>
   525 lemma u_K4_imp_K2:
   525 lemma u_K4_imp_K2:
   526 "\<lbrakk> Says Tgs A \<lbrace>Crypt authK \<lbrace>Key servK, Agent B, Number Ts\<rbrace>, servTicket\<rbrace>  \<in> set evs; evs \<in> kerbV\<rbrakk>
   526 "\<lbrakk> Says Tgs A \<lbrace>Crypt authK \<lbrace>Key servK, Agent B, Number Ts\<rbrace>, servTicket\<rbrace>  \<in> set evs; evs \<in> kerbV\<rbrakk>
   527    \<Longrightarrow> \<exists>Ta. Says Kas A \<lbrace>Crypt (shrK A) \<lbrace>Key authK, Agent Tgs, Number Ta\<rbrace>,
   527    \<Longrightarrow> \<exists>Ta. Says Kas A \<lbrace>Crypt (shrK A) \<lbrace>Key authK, Agent Tgs, Number Ta\<rbrace>,
   528              Crypt (shrK Tgs) \<lbrace>Agent A, Agent Tgs, Key authK, Number Ta\<rbrace> \<rbrace>
   528              Crypt (shrK Tgs) \<lbrace>Agent A, Agent Tgs, Key authK, Number Ta\<rbrace> \<rbrace>
   529              \<in> set evs
   529              \<in> set evs
   586 lemma u_NotexpiredSK_NotexpiredAK:
   586 lemma u_NotexpiredSK_NotexpiredAK:
   587      "\<lbrakk> \<not> expiredSK Ts evs; servKlife + Ts <= authKlife + Ta \<rbrakk>
   587      "\<lbrakk> \<not> expiredSK Ts evs; servKlife + Ts <= authKlife + Ta \<rbrakk>
   588       \<Longrightarrow> \<not> expiredAK Ta evs"
   588       \<Longrightarrow> \<not> expiredAK Ta evs"
   589 by (metis order_le_less_trans)
   589 by (metis order_le_less_trans)
   590 
   590 
   591 subsection{* Reliability: friendly agents send somthing if something else happened*}
   591 subsection\<open>Reliability: friendly agents send somthing if something else happened\<close>
   592 
   592 
   593 lemma K3_imp_K2:
   593 lemma K3_imp_K2:
   594      "\<lbrakk> Says A Tgs
   594      "\<lbrakk> Says A Tgs
   595              \<lbrace>authTicket, Crypt authK \<lbrace>Agent A, Number T2\<rbrace>, Agent B\<rbrace>
   595              \<lbrace>authTicket, Crypt authK \<lbrace>Agent A, Number T2\<rbrace>, Agent B\<rbrace>
   596            \<in> set evs;
   596            \<in> set evs;
   602 apply (frule_tac [7] Says_ticket_parts)
   602 apply (frule_tac [7] Says_ticket_parts)
   603 apply (frule_tac [5] Says_ticket_parts, simp_all, blast, blast)
   603 apply (frule_tac [5] Says_ticket_parts, simp_all, blast, blast)
   604 apply (blast dest: Says_imp_spies [THEN parts.Inj, THEN parts.Fst, THEN authK_authentic])
   604 apply (blast dest: Says_imp_spies [THEN parts.Inj, THEN parts.Fst, THEN authK_authentic])
   605 done
   605 done
   606 
   606 
   607 text{*Anticipated here from next subsection. An authK is encrypted by one and only one Shared key. A servK is encrypted by one and only one authK.*}
   607 text\<open>Anticipated here from next subsection. An authK is encrypted by one and only one Shared key. A servK is encrypted by one and only one authK.\<close>
   608 lemma Key_unique_SesKey:
   608 lemma Key_unique_SesKey:
   609      "\<lbrakk> Crypt K  \<lbrace>Key SesKey,  Agent B, T\<rbrace>
   609      "\<lbrakk> Crypt K  \<lbrace>Key SesKey,  Agent B, T\<rbrace>
   610            \<in> parts (spies evs);
   610            \<in> parts (spies evs);
   611          Crypt K' \<lbrace>Key SesKey,  Agent B', T'\<rbrace>
   611          Crypt K' \<lbrace>Key SesKey,  Agent B', T'\<rbrace>
   612            \<in> parts (spies evs);  Key SesKey \<notin> analz (spies evs);
   612            \<in> parts (spies evs);  Key SesKey \<notin> analz (spies evs);
   616 apply (erule rev_mp)
   616 apply (erule rev_mp)
   617 apply (erule rev_mp)
   617 apply (erule rev_mp)
   618 apply (erule kerbV.induct, analz_mono_contra)
   618 apply (erule kerbV.induct, analz_mono_contra)
   619 apply (frule_tac [7] Says_ticket_parts)
   619 apply (frule_tac [7] Says_ticket_parts)
   620 apply (frule_tac [5] Says_ticket_parts, simp_all)
   620 apply (frule_tac [5] Says_ticket_parts, simp_all)
   621 txt{*Fake, K2, K4*}
   621 txt\<open>Fake, K2, K4\<close>
   622 apply (blast+)
   622 apply (blast+)
   623 done
   623 done
   624 
   624 
   625 text{*This inevitably has an existential form in version V*}
   625 text\<open>This inevitably has an existential form in version V\<close>
   626 lemma Says_K5:
   626 lemma Says_K5:
   627      "\<lbrakk> Crypt servK \<lbrace>Agent A, Number T3\<rbrace> \<in> parts (spies evs);
   627      "\<lbrakk> Crypt servK \<lbrace>Agent A, Number T3\<rbrace> \<in> parts (spies evs);
   628          Says Tgs A \<lbrace>Crypt authK \<lbrace>Key servK, Agent B, Number Ts\<rbrace>,
   628          Says Tgs A \<lbrace>Crypt authK \<lbrace>Key servK, Agent B, Number Ts\<rbrace>,
   629                                      servTicket\<rbrace> \<in> set evs;
   629                                      servTicket\<rbrace> \<in> set evs;
   630          Key servK \<notin> analz (spies evs);
   630          Key servK \<notin> analz (spies evs);
   636 apply (erule kerbV.induct, analz_mono_contra)
   636 apply (erule kerbV.induct, analz_mono_contra)
   637 apply (frule_tac [5] Says_ticket_parts)
   637 apply (frule_tac [5] Says_ticket_parts)
   638 apply (frule_tac [7] Says_ticket_parts)
   638 apply (frule_tac [7] Says_ticket_parts)
   639 apply (simp_all (no_asm_simp) add: all_conj_distrib)
   639 apply (simp_all (no_asm_simp) add: all_conj_distrib)
   640 apply blast
   640 apply blast
   641 txt{*K3*}
   641 txt\<open>K3\<close>
   642 apply (blast dest: authK_authentic Says_Kas_message_form Says_Tgs_message_form)
   642 apply (blast dest: authK_authentic Says_Kas_message_form Says_Tgs_message_form)
   643 txt{*K4*}
   643 txt\<open>K4\<close>
   644 apply (force dest!: Crypt_imp_keysFor)
   644 apply (force dest!: Crypt_imp_keysFor)
   645 txt{*K5*}
   645 txt\<open>K5\<close>
   646 apply (blast dest: Key_unique_SesKey)
   646 apply (blast dest: Key_unique_SesKey)
   647 done
   647 done
   648 
   648 
   649 text{*Anticipated here from next subsection*}
   649 text\<open>Anticipated here from next subsection\<close>
   650 lemma unique_CryptKey:
   650 lemma unique_CryptKey:
   651      "\<lbrakk> Crypt (shrK B)  \<lbrace>Agent A,  Agent B,  Key SesKey, T\<rbrace>
   651      "\<lbrakk> Crypt (shrK B)  \<lbrace>Agent A,  Agent B,  Key SesKey, T\<rbrace>
   652            \<in> parts (spies evs);
   652            \<in> parts (spies evs);
   653          Crypt (shrK B') \<lbrace>Agent A', Agent B', Key SesKey, T'\<rbrace>
   653          Crypt (shrK B') \<lbrace>Agent A', Agent B', Key SesKey, T'\<rbrace>
   654            \<in> parts (spies evs);  Key SesKey \<notin> analz (spies evs);
   654            \<in> parts (spies evs);  Key SesKey \<notin> analz (spies evs);
   658 apply (erule rev_mp)
   658 apply (erule rev_mp)
   659 apply (erule rev_mp)
   659 apply (erule rev_mp)
   660 apply (erule kerbV.induct, analz_mono_contra)
   660 apply (erule kerbV.induct, analz_mono_contra)
   661 apply (frule_tac [7] Says_ticket_parts)
   661 apply (frule_tac [7] Says_ticket_parts)
   662 apply (frule_tac [5] Says_ticket_parts, simp_all)
   662 apply (frule_tac [5] Says_ticket_parts, simp_all)
   663 txt{*Fake, K2, K4*}
   663 txt\<open>Fake, K2, K4\<close>
   664 apply (blast+)
   664 apply (blast+)
   665 done
   665 done
   666 
   666 
   667 lemma Says_K6:
   667 lemma Says_K6:
   668      "\<lbrakk> Crypt servK (Number T3) \<in> parts (spies evs);
   668      "\<lbrakk> Crypt servK (Number T3) \<in> parts (spies evs);
   678 apply (erule kerbV.induct, analz_mono_contra)
   678 apply (erule kerbV.induct, analz_mono_contra)
   679 apply (frule_tac [7] Says_ticket_parts)
   679 apply (frule_tac [7] Says_ticket_parts)
   680 apply (frule_tac [5] Says_ticket_parts)
   680 apply (frule_tac [5] Says_ticket_parts)
   681 apply simp_all
   681 apply simp_all
   682 
   682 
   683 txt{*fake*}
   683 txt\<open>fake\<close>
   684 apply blast
   684 apply blast
   685 txt{*K4*}
   685 txt\<open>K4\<close>
   686 apply (force dest!: Crypt_imp_keysFor)
   686 apply (force dest!: Crypt_imp_keysFor)
   687 txt{*K6*}
   687 txt\<open>K6\<close>
   688 apply (metis MPair_parts Says_imp_parts_knows_Spy unique_CryptKey)
   688 apply (metis MPair_parts Says_imp_parts_knows_Spy unique_CryptKey)
   689 done
   689 done
   690 
   690 
   691 text{*Needs a unicity theorem, hence moved here*}
   691 text\<open>Needs a unicity theorem, hence moved here\<close>
   692 lemma servK_authentic_ter:
   692 lemma servK_authentic_ter:
   693  "\<lbrakk> Says Kas A
   693  "\<lbrakk> Says Kas A
   694        \<lbrace>Crypt (shrK A) \<lbrace>Key authK, Agent Tgs, Ta\<rbrace>, authTicket\<rbrace> \<in> set evs;
   694        \<lbrace>Crypt (shrK A) \<lbrace>Key authK, Agent Tgs, Ta\<rbrace>, authTicket\<rbrace> \<in> set evs;
   695      Crypt authK \<lbrace>Key servK, Agent B, Ts\<rbrace>
   695      Crypt authK \<lbrace>Key servK, Agent B, Ts\<rbrace>
   696        \<in> parts (spies evs);
   696        \<in> parts (spies evs);
   705 apply (erule rev_mp)
   705 apply (erule rev_mp)
   706 apply (erule rev_mp)
   706 apply (erule rev_mp)
   707 apply (erule kerbV.induct, analz_mono_contra)
   707 apply (erule kerbV.induct, analz_mono_contra)
   708 apply (frule_tac [7] Says_ticket_parts)
   708 apply (frule_tac [7] Says_ticket_parts)
   709 apply (frule_tac [5] Says_ticket_parts, simp_all, blast)
   709 apply (frule_tac [5] Says_ticket_parts, simp_all, blast)
   710 txt{*K2 and K4 remain*}
   710 txt\<open>K2 and K4 remain\<close>
   711 apply (blast dest!: servK_authentic Says_Tgs_message_form authKeys_used)
   711 apply (blast dest!: servK_authentic Says_Tgs_message_form authKeys_used)
   712 apply (blast dest!: unique_CryptKey)
   712 apply (blast dest!: unique_CryptKey)
   713 done
   713 done
   714 
   714 
   715 
   715 
   716 subsection{*Unicity Theorems*}
   716 subsection\<open>Unicity Theorems\<close>
   717 
   717 
   718 text{* The session key, if secure, uniquely identifies the Ticket
   718 text\<open>The session key, if secure, uniquely identifies the Ticket
   719    whether authTicket or servTicket. As a matter of fact, one can read
   719    whether authTicket or servTicket. As a matter of fact, one can read
   720    also Tgs in the place of B.                                     *}
   720    also Tgs in the place of B.\<close>
   721 
   721 
   722 
   722 
   723 lemma unique_authKeys:
   723 lemma unique_authKeys:
   724      "\<lbrakk> Says Kas A
   724      "\<lbrakk> Says Kas A
   725               \<lbrace>Crypt Ka \<lbrace>Key authK, Agent Tgs, Ta\<rbrace>, X\<rbrace> \<in> set evs;
   725               \<lbrace>Crypt Ka \<lbrace>Key authK, Agent Tgs, Ta\<rbrace>, X\<rbrace> \<in> set evs;
   732 apply (frule_tac [7] Says_ticket_parts)
   732 apply (frule_tac [7] Says_ticket_parts)
   733 apply (frule_tac [5] Says_ticket_parts, simp_all)
   733 apply (frule_tac [5] Says_ticket_parts, simp_all)
   734 apply blast+
   734 apply blast+
   735 done
   735 done
   736 
   736 
   737 text{* servK uniquely identifies the message from Tgs *}
   737 text\<open>servK uniquely identifies the message from Tgs\<close>
   738 lemma unique_servKeys:
   738 lemma unique_servKeys:
   739      "\<lbrakk> Says Tgs A
   739      "\<lbrakk> Says Tgs A
   740               \<lbrace>Crypt K \<lbrace>Key servK, Agent B, Ts\<rbrace>, X\<rbrace> \<in> set evs;
   740               \<lbrace>Crypt K \<lbrace>Key servK, Agent B, Ts\<rbrace>, X\<rbrace> \<in> set evs;
   741          Says Tgs A'
   741          Says Tgs A'
   742               \<lbrace>Crypt K' \<lbrace>Key servK, Agent B', Ts'\<rbrace>, X'\<rbrace> \<in> set evs;
   742               \<lbrace>Crypt K' \<lbrace>Key servK, Agent B', Ts'\<rbrace>, X'\<rbrace> \<in> set evs;
   747 apply (frule_tac [7] Says_ticket_parts)
   747 apply (frule_tac [7] Says_ticket_parts)
   748 apply (frule_tac [5] Says_ticket_parts, simp_all)
   748 apply (frule_tac [5] Says_ticket_parts, simp_all)
   749 apply blast+
   749 apply blast+
   750 done
   750 done
   751 
   751 
   752 subsection{*Lemmas About the Predicate @{term AKcryptSK}*}
   752 subsection\<open>Lemmas About the Predicate @{term AKcryptSK}\<close>
   753 
   753 
   754 lemma not_AKcryptSK_Nil [iff]: "\<not> AKcryptSK authK servK []"
   754 lemma not_AKcryptSK_Nil [iff]: "\<not> AKcryptSK authK servK []"
   755 apply (simp add: AKcryptSK_def)
   755 apply (simp add: AKcryptSK_def)
   756 done
   756 done
   757 
   757 
   797       \<Longrightarrow> \<not> AKcryptSK K authK evs"
   797       \<Longrightarrow> \<not> AKcryptSK K authK evs"
   798 apply (erule rev_mp)
   798 apply (erule rev_mp)
   799 apply (erule kerbV.induct)
   799 apply (erule kerbV.induct)
   800 apply (frule_tac [7] Says_ticket_parts)
   800 apply (frule_tac [7] Says_ticket_parts)
   801 apply (frule_tac [5] Says_ticket_parts, simp_all)
   801 apply (frule_tac [5] Says_ticket_parts, simp_all)
   802 txt{*Fake,K2,K4*}
   802 txt\<open>Fake,K2,K4\<close>
   803 apply (auto simp add: AKcryptSK_def)
   803 apply (auto simp add: AKcryptSK_def)
   804 done
   804 done
   805 
   805 
   806 text{*A secure serverkey cannot have been used to encrypt others*}
   806 text\<open>A secure serverkey cannot have been used to encrypt others\<close>
   807 lemma servK_not_AKcryptSK:
   807 lemma servK_not_AKcryptSK:
   808  "\<lbrakk> Crypt (shrK B) \<lbrace>Agent A, Agent B, Key SK, tt\<rbrace> \<in> parts (spies evs);
   808  "\<lbrakk> Crypt (shrK B) \<lbrace>Agent A, Agent B, Key SK, tt\<rbrace> \<in> parts (spies evs);
   809      Key SK \<notin> analz (spies evs);  SK \<in> symKeys;
   809      Key SK \<notin> analz (spies evs);  SK \<in> symKeys;
   810      B \<noteq> Tgs;  evs \<in> kerbV \<rbrakk>
   810      B \<noteq> Tgs;  evs \<in> kerbV \<rbrakk>
   811   \<Longrightarrow> \<not> AKcryptSK SK K evs"
   811   \<Longrightarrow> \<not> AKcryptSK SK K evs"
   812 apply (erule rev_mp)
   812 apply (erule rev_mp)
   813 apply (erule rev_mp)
   813 apply (erule rev_mp)
   814 apply (erule kerbV.induct, analz_mono_contra)
   814 apply (erule kerbV.induct, analz_mono_contra)
   815 apply (frule_tac [7] Says_ticket_parts)
   815 apply (frule_tac [7] Says_ticket_parts)
   816 apply (frule_tac [5] Says_ticket_parts, simp_all, blast)
   816 apply (frule_tac [5] Says_ticket_parts, simp_all, blast)
   817 txt{*K4*}
   817 txt\<open>K4\<close>
   818 apply (metis Auth_fresh_not_AKcryptSK MPair_parts Says_imp_parts_knows_Spy authKeys_used authTicket_crypt_authK unique_CryptKey)
   818 apply (metis Auth_fresh_not_AKcryptSK MPair_parts Says_imp_parts_knows_Spy authKeys_used authTicket_crypt_authK unique_CryptKey)
   819 done
   819 done
   820 
   820 
   821 text{*Long term keys are not issued as servKeys*}
   821 text\<open>Long term keys are not issued as servKeys\<close>
   822 lemma shrK_not_AKcryptSK:
   822 lemma shrK_not_AKcryptSK:
   823      "evs \<in> kerbV \<Longrightarrow> \<not> AKcryptSK K (shrK A) evs"
   823      "evs \<in> kerbV \<Longrightarrow> \<not> AKcryptSK K (shrK A) evs"
   824 apply (unfold AKcryptSK_def)
   824 apply (unfold AKcryptSK_def)
   825 apply (erule kerbV.induct)
   825 apply (erule kerbV.induct)
   826 apply (frule_tac [7] Says_ticket_parts)
   826 apply (frule_tac [7] Says_ticket_parts)
   827 apply (frule_tac [5] Says_ticket_parts, auto)
   827 apply (frule_tac [5] Says_ticket_parts, auto)
   828 done
   828 done
   829 
   829 
   830 text{*The Tgs message associates servK with authK and therefore not with any
   830 text\<open>The Tgs message associates servK with authK and therefore not with any
   831   other key authK.*}
   831   other key authK.\<close>
   832 lemma Says_Tgs_AKcryptSK:
   832 lemma Says_Tgs_AKcryptSK:
   833      "\<lbrakk> Says Tgs A \<lbrace>Crypt authK \<lbrace>Key servK, Agent B, tt\<rbrace>, X \<rbrace>
   833      "\<lbrakk> Says Tgs A \<lbrace>Crypt authK \<lbrace>Key servK, Agent B, tt\<rbrace>, X \<rbrace>
   834            \<in> set evs;
   834            \<in> set evs;
   835          authK' \<noteq> authK;  evs \<in> kerbV \<rbrakk>
   835          authK' \<noteq> authK;  evs \<in> kerbV \<rbrakk>
   836       \<Longrightarrow> \<not> AKcryptSK authK' servK evs"
   836       \<Longrightarrow> \<not> AKcryptSK authK' servK evs"
   842 apply (erule rev_mp)
   842 apply (erule rev_mp)
   843 apply (erule kerbV.induct)
   843 apply (erule kerbV.induct)
   844 apply (frule_tac [7] Says_ticket_parts)
   844 apply (frule_tac [7] Says_ticket_parts)
   845 apply (frule_tac [5] Says_ticket_parts)
   845 apply (frule_tac [5] Says_ticket_parts)
   846 apply (simp_all, safe)
   846 apply (simp_all, safe)
   847 txt{*K4 splits into subcases*}
   847 txt\<open>K4 splits into subcases\<close>
   848 prefer 4 apply (blast dest!: authK_not_AKcryptSK)
   848 prefer 4 apply (blast dest!: authK_not_AKcryptSK)
   849 txt{*servK is fresh and so could not have been used, by
   849 txt\<open>servK is fresh and so could not have been used, by
   850    @{text new_keys_not_used}*}
   850    \<open>new_keys_not_used\<close>\<close>
   851  prefer 2 
   851  prefer 2 
   852  apply (force dest!: Crypt_imp_invKey_keysFor simp add: AKcryptSK_def)
   852  apply (force dest!: Crypt_imp_invKey_keysFor simp add: AKcryptSK_def)
   853 txt{*Others by freshness*}
   853 txt\<open>Others by freshness\<close>
   854 apply (blast+)
   854 apply (blast+)
   855 done
   855 done
   856 
   856 
   857 lemma not_different_AKcryptSK:
   857 lemma not_different_AKcryptSK:
   858      "\<lbrakk> AKcryptSK authK servK evs;
   858      "\<lbrakk> AKcryptSK authK servK evs;
   860       \<Longrightarrow> \<not> AKcryptSK authK' servK evs  \<and> servK \<in> symKeys"
   860       \<Longrightarrow> \<not> AKcryptSK authK' servK evs  \<and> servK \<in> symKeys"
   861 apply (simp add: AKcryptSK_def)
   861 apply (simp add: AKcryptSK_def)
   862 apply (blast dest: unique_servKeys Says_Tgs_message_form)
   862 apply (blast dest: unique_servKeys Says_Tgs_message_form)
   863 done
   863 done
   864 
   864 
   865 text{*The only session keys that can be found with the help of session keys are
   865 text\<open>The only session keys that can be found with the help of session keys are
   866   those sent by Tgs in step K4.  *}
   866   those sent by Tgs in step K4.\<close>
   867 
   867 
   868 text{*We take some pains to express the property
   868 text\<open>We take some pains to express the property
   869   as a logical equivalence so that the simplifier can apply it.*}
   869   as a logical equivalence so that the simplifier can apply it.\<close>
   870 lemma Key_analz_image_Key_lemma:
   870 lemma Key_analz_image_Key_lemma:
   871      "P \<longrightarrow> (Key K \<in> analz (Key`KK Un H)) \<longrightarrow> (K:KK | Key K \<in> analz H)
   871      "P \<longrightarrow> (Key K \<in> analz (Key`KK Un H)) \<longrightarrow> (K:KK | Key K \<in> analz H)
   872       \<Longrightarrow>
   872       \<Longrightarrow>
   873       P \<longrightarrow> (Key K \<in> analz (Key`KK Un H)) = (K:KK | Key K \<in> analz H)"
   873       P \<longrightarrow> (Key K \<in> analz (Key`KK Un H)) = (K:KK | Key K \<in> analz H)"
   874 by (blast intro: analz_mono [THEN subsetD])
   874 by (blast intro: analz_mono [THEN subsetD])
   895 apply (simp add: AKcryptSK_def)
   895 apply (simp add: AKcryptSK_def)
   896 apply (blast dest: Says_Tgs_message_form)
   896 apply (blast dest: Says_Tgs_message_form)
   897 done
   897 done
   898 
   898 
   899 
   899 
   900 subsection{*Secrecy Theorems*}
   900 subsection\<open>Secrecy Theorems\<close>
   901 
   901 
   902 text{*For the Oops2 case of the next theorem*}
   902 text\<open>For the Oops2 case of the next theorem\<close>
   903 lemma Oops2_not_AKcryptSK:
   903 lemma Oops2_not_AKcryptSK:
   904      "\<lbrakk> evs \<in> kerbV;
   904      "\<lbrakk> evs \<in> kerbV;
   905          Says Tgs A \<lbrace>Crypt authK
   905          Says Tgs A \<lbrace>Crypt authK
   906                      \<lbrace>Key servK, Agent B, Number Ts\<rbrace>, servTicket\<rbrace>
   906                      \<lbrace>Key servK, Agent B, Number Ts\<rbrace>, servTicket\<rbrace>
   907            \<in> set evs \<rbrakk>
   907            \<in> set evs \<rbrakk>
   908       \<Longrightarrow> \<not> AKcryptSK servK SK evs"
   908       \<Longrightarrow> \<not> AKcryptSK servK SK evs"
   909 by (blast dest: AKcryptSKI AKcryptSK_not_AKcryptSK)
   909 by (blast dest: AKcryptSKI AKcryptSK_not_AKcryptSK)
   910    
   910    
   911 text{* Big simplification law for keys SK that are not crypted by keys in KK
   911 text\<open>Big simplification law for keys SK that are not crypted by keys in KK
   912  It helps prove three, otherwise hard, facts about keys. These facts are
   912  It helps prove three, otherwise hard, facts about keys. These facts are
   913  exploited as simplification laws for analz, and also "limit the damage"
   913  exploited as simplification laws for analz, and also "limit the damage"
   914  in case of loss of a key to the spy. See ESORICS98.*}
   914  in case of loss of a key to the spy. See ESORICS98.\<close>
   915 lemma Key_analz_image_Key [rule_format (no_asm)]:
   915 lemma Key_analz_image_Key [rule_format (no_asm)]:
   916      "evs \<in> kerbV \<Longrightarrow>
   916      "evs \<in> kerbV \<Longrightarrow>
   917       (\<forall>SK KK. SK \<in> symKeys & KK <= -(range shrK) \<longrightarrow>
   917       (\<forall>SK KK. SK \<in> symKeys & KK <= -(range shrK) \<longrightarrow>
   918        (\<forall>K \<in> KK. \<not> AKcryptSK K SK evs)   \<longrightarrow>
   918        (\<forall>K \<in> KK. \<not> AKcryptSK K SK evs)   \<longrightarrow>
   919        (Key SK \<in> analz (Key`KK Un (spies evs))) =
   919        (Key SK \<in> analz (Key`KK Un (spies evs))) =
   926 apply (drule_tac [7] Says_ticket_analz)
   926 apply (drule_tac [7] Says_ticket_analz)
   927 (*Used to apply Says_kas_message form, which is no longer available. 
   927 (*Used to apply Says_kas_message form, which is no longer available. 
   928   Instead\<dots>*)
   928   Instead\<dots>*)
   929 apply (drule_tac [5] Says_ticket_analz)
   929 apply (drule_tac [5] Says_ticket_analz)
   930 apply (safe del: impI intro!: Key_analz_image_Key_lemma [THEN impI])
   930 apply (safe del: impI intro!: Key_analz_image_Key_lemma [THEN impI])
   931 txt{*Case-splits for Oops1 and message 5: the negated case simplifies using
   931 txt\<open>Case-splits for Oops1 and message 5: the negated case simplifies using
   932  the induction hypothesis*}
   932  the induction hypothesis\<close>
   933 apply (case_tac [9] "AKcryptSK authK SK evsO1")
   933 apply (case_tac [9] "AKcryptSK authK SK evsO1")
   934 apply (case_tac [7] "AKcryptSK servK SK evs5")
   934 apply (case_tac [7] "AKcryptSK servK SK evs5")
   935 apply (simp_all del: image_insert
   935 apply (simp_all del: image_insert
   936           add: analz_image_freshK_simps AKcryptSK_Says shrK_not_AKcryptSK
   936           add: analz_image_freshK_simps AKcryptSK_Says shrK_not_AKcryptSK
   937                Oops2_not_AKcryptSK Auth_fresh_not_AKcryptSK
   937                Oops2_not_AKcryptSK Auth_fresh_not_AKcryptSK
   938                Serv_fresh_not_AKcryptSK Says_Tgs_AKcryptSK Spy_analz_shrK)
   938                Serv_fresh_not_AKcryptSK Says_Tgs_AKcryptSK Spy_analz_shrK)
   939 txt{*Fake*} 
   939 txt\<open>Fake\<close> 
   940 apply spy_analz
   940 apply spy_analz
   941 txt{*K2*}
   941 txt\<open>K2\<close>
   942 apply blast 
   942 apply blast 
   943 txt{*Cases K3 and K5 solved by the simplifier thanks to the ticket being in 
   943 txt\<open>Cases K3 and K5 solved by the simplifier thanks to the ticket being in 
   944 analz - this strategy is new wrt version IV*} 
   944 analz - this strategy is new wrt version IV\<close> 
   945 txt{*K4*}
   945 txt\<open>K4\<close>
   946 apply (blast dest!: authK_not_AKcryptSK)
   946 apply (blast dest!: authK_not_AKcryptSK)
   947 txt{*Oops1*}
   947 txt\<open>Oops1\<close>
   948 apply (metis AKcryptSK_analz_insert insert_Key_singleton)
   948 apply (metis AKcryptSK_analz_insert insert_Key_singleton)
   949 done
   949 done
   950 
   950 
   951 text{* First simplification law for analz: no session keys encrypt
   951 text\<open>First simplification law for analz: no session keys encrypt
   952 authentication keys or shared keys. *}
   952 authentication keys or shared keys.\<close>
   953 lemma analz_insert_freshK1:
   953 lemma analz_insert_freshK1:
   954      "\<lbrakk> evs \<in> kerbV;  K \<in> authKeys evs Un range shrK;
   954      "\<lbrakk> evs \<in> kerbV;  K \<in> authKeys evs Un range shrK;
   955         SesKey \<notin> range shrK \<rbrakk>
   955         SesKey \<notin> range shrK \<rbrakk>
   956       \<Longrightarrow> (Key K \<in> analz (insert (Key SesKey) (spies evs))) =
   956       \<Longrightarrow> (Key K \<in> analz (insert (Key SesKey) (spies evs))) =
   957           (K = SesKey | Key K \<in> analz (spies evs))"
   957           (K = SesKey | Key K \<in> analz (spies evs))"
   959 apply (simp del: image_insert
   959 apply (simp del: image_insert
   960             add: analz_image_freshK_simps add: Key_analz_image_Key)
   960             add: analz_image_freshK_simps add: Key_analz_image_Key)
   961 done
   961 done
   962 
   962 
   963 
   963 
   964 text{* Second simplification law for analz: no service keys encrypt any other keys.*}
   964 text\<open>Second simplification law for analz: no service keys encrypt any other keys.\<close>
   965 lemma analz_insert_freshK2:
   965 lemma analz_insert_freshK2:
   966      "\<lbrakk> evs \<in> kerbV;  servK \<notin> (authKeys evs); servK \<notin> range shrK;
   966      "\<lbrakk> evs \<in> kerbV;  servK \<notin> (authKeys evs); servK \<notin> range shrK;
   967         K \<in> symKeys \<rbrakk>
   967         K \<in> symKeys \<rbrakk>
   968       \<Longrightarrow> (Key K \<in> analz (insert (Key servK) (spies evs))) =
   968       \<Longrightarrow> (Key K \<in> analz (insert (Key servK) (spies evs))) =
   969           (K = servK | Key K \<in> analz (spies evs))"
   969           (K = servK | Key K \<in> analz (spies evs))"
   971 apply (simp del: image_insert
   971 apply (simp del: image_insert
   972             add: analz_image_freshK_simps add: Key_analz_image_Key)
   972             add: analz_image_freshK_simps add: Key_analz_image_Key)
   973 done
   973 done
   974 
   974 
   975 
   975 
   976 text{* Third simplification law for analz: only one authentication key encrypts a certain service key.*}
   976 text\<open>Third simplification law for analz: only one authentication key encrypts a certain service key.\<close>
   977 
   977 
   978 lemma analz_insert_freshK3:
   978 lemma analz_insert_freshK3:
   979  "\<lbrakk> AKcryptSK authK servK evs;
   979  "\<lbrakk> AKcryptSK authK servK evs;
   980     authK' \<noteq> authK; authK' \<notin> range shrK; evs \<in> kerbV \<rbrakk>
   980     authK' \<noteq> authK; authK' \<notin> range shrK; evs \<in> kerbV \<rbrakk>
   981         \<Longrightarrow> (Key servK \<in> analz (insert (Key authK') (spies evs))) =
   981         \<Longrightarrow> (Key servK \<in> analz (insert (Key authK') (spies evs))) =
   993                 (servK = authK' | Key servK \<in> analz (spies evs))"
   993                 (servK = authK' | Key servK \<in> analz (spies evs))"
   994 apply (frule AKcryptSKI, assumption)
   994 apply (frule AKcryptSKI, assumption)
   995 apply (simp add: analz_insert_freshK3)
   995 apply (simp add: analz_insert_freshK3)
   996 done
   996 done
   997 
   997 
   998 text{*a weakness of the protocol*}
   998 text\<open>a weakness of the protocol\<close>
   999 lemma authK_compromises_servK:
   999 lemma authK_compromises_servK:
  1000      "\<lbrakk> Says Tgs A \<lbrace>Crypt authK \<lbrace>Key servK, Agent B, Number Ts\<rbrace>, servTicket\<rbrace>
  1000      "\<lbrakk> Says Tgs A \<lbrace>Crypt authK \<lbrace>Key servK, Agent B, Number Ts\<rbrace>, servTicket\<rbrace>
  1001         \<in> set evs;  authK \<in> symKeys;
  1001         \<in> set evs;  authK \<in> symKeys;
  1002          Key authK \<in> analz (spies evs); evs \<in> kerbV \<rbrakk>
  1002          Key authK \<in> analz (spies evs); evs \<in> kerbV \<rbrakk>
  1003       \<Longrightarrow> Key servK \<in> analz (spies evs)"
  1003       \<Longrightarrow> Key servK \<in> analz (spies evs)"
  1004   by (metis Says_imp_analz_Spy analz.Fst analz_Decrypt')
  1004   by (metis Says_imp_analz_Spy analz.Fst analz_Decrypt')
  1005 
  1005 
  1006 
  1006 
  1007 text{*lemma @{text servK_notin_authKeysD} not needed in version V*}
  1007 text\<open>lemma \<open>servK_notin_authKeysD\<close> not needed in version V\<close>
  1008 
  1008 
  1009 text{*If Spy sees the Authentication Key sent in msg K2, then
  1009 text\<open>If Spy sees the Authentication Key sent in msg K2, then
  1010     the Key has expired.*}
  1010     the Key has expired.\<close>
  1011 lemma Confidentiality_Kas_lemma [rule_format]:
  1011 lemma Confidentiality_Kas_lemma [rule_format]:
  1012      "\<lbrakk> authK \<in> symKeys; A \<notin> bad;  evs \<in> kerbV \<rbrakk>
  1012      "\<lbrakk> authK \<in> symKeys; A \<notin> bad;  evs \<in> kerbV \<rbrakk>
  1013       \<Longrightarrow> Says Kas A
  1013       \<Longrightarrow> Says Kas A
  1014                \<lbrace>Crypt (shrK A) \<lbrace>Key authK, Agent Tgs, Number Ta\<rbrace>,
  1014                \<lbrace>Crypt (shrK A) \<lbrace>Key authK, Agent Tgs, Number Ta\<rbrace>,
  1015           Crypt (shrK Tgs) \<lbrace>Agent A, Agent Tgs, Key authK, Number Ta\<rbrace>\<rbrace>
  1015           Crypt (shrK Tgs) \<lbrace>Agent A, Agent Tgs, Key authK, Number Ta\<rbrace>\<rbrace>
  1021 apply (frule_tac [9] Oops_range_spies1)
  1021 apply (frule_tac [9] Oops_range_spies1)
  1022 apply (frule_tac [7] Says_ticket_analz)
  1022 apply (frule_tac [7] Says_ticket_analz)
  1023 apply (frule_tac [5] Says_ticket_analz)
  1023 apply (frule_tac [5] Says_ticket_analz)
  1024 apply (safe del: impI conjI impCE)
  1024 apply (safe del: impI conjI impCE)
  1025 apply (simp_all (no_asm_simp) add: Says_Kas_message_form less_SucI analz_insert_eq not_parts_not_analz analz_insert_freshK1 pushes)
  1025 apply (simp_all (no_asm_simp) add: Says_Kas_message_form less_SucI analz_insert_eq not_parts_not_analz analz_insert_freshK1 pushes)
  1026 txt{*Fake*}
  1026 txt\<open>Fake\<close>
  1027 apply spy_analz
  1027 apply spy_analz
  1028 txt{*K2*}
  1028 txt\<open>K2\<close>
  1029 apply blast
  1029 apply blast
  1030 txt{*K4*}
  1030 txt\<open>K4\<close>
  1031 apply blast
  1031 apply blast
  1032 txt{*Oops1*}
  1032 txt\<open>Oops1\<close>
  1033 apply (blast dest!: unique_authKeys intro: less_SucI)
  1033 apply (blast dest!: unique_authKeys intro: less_SucI)
  1034 txt{*Oops2*}
  1034 txt\<open>Oops2\<close>
  1035 apply (blast dest: Says_Tgs_message_form Says_Kas_message_form)
  1035 apply (blast dest: Says_Tgs_message_form Says_Kas_message_form)
  1036 done
  1036 done
  1037 
  1037 
  1038 lemma Confidentiality_Kas:
  1038 lemma Confidentiality_Kas:
  1039      "\<lbrakk> Says Kas A
  1039      "\<lbrakk> Says Kas A
  1043         A \<notin> bad;  evs \<in> kerbV \<rbrakk>
  1043         A \<notin> bad;  evs \<in> kerbV \<rbrakk>
  1044       \<Longrightarrow> Key authK \<notin> analz (spies evs)"
  1044       \<Longrightarrow> Key authK \<notin> analz (spies evs)"
  1045 apply (blast dest: Says_Kas_message_form Confidentiality_Kas_lemma)
  1045 apply (blast dest: Says_Kas_message_form Confidentiality_Kas_lemma)
  1046 done
  1046 done
  1047 
  1047 
  1048 text{*If Spy sees the Service Key sent in msg K4, then
  1048 text\<open>If Spy sees the Service Key sent in msg K4, then
  1049     the Key has expired.*}
  1049     the Key has expired.\<close>
  1050 
  1050 
  1051 lemma Confidentiality_lemma [rule_format]:
  1051 lemma Confidentiality_lemma [rule_format]:
  1052      "\<lbrakk> Says Tgs A
  1052      "\<lbrakk> Says Tgs A
  1053             \<lbrace>Crypt authK \<lbrace>Key servK, Agent B, Number Ts\<rbrace>,
  1053             \<lbrace>Crypt authK \<lbrace>Key servK, Agent B, Number Ts\<rbrace>,
  1054               Crypt (shrK B) \<lbrace>Agent A, Agent B, Key servK, Number Ts\<rbrace>\<rbrace>
  1054               Crypt (shrK B) \<lbrace>Agent A, Agent B, Key servK, Number Ts\<rbrace>\<rbrace>
  1060           expiredSK Ts evs"
  1060           expiredSK Ts evs"
  1061 apply (erule rev_mp)
  1061 apply (erule rev_mp)
  1062 apply (erule rev_mp)
  1062 apply (erule rev_mp)
  1063 apply (erule kerbV.induct)
  1063 apply (erule kerbV.induct)
  1064 apply (rule_tac [9] impI)+
  1064 apply (rule_tac [9] impI)+
  1065   --{*The Oops1 case is unusual: must simplify
  1065   \<comment>\<open>The Oops1 case is unusual: must simplify
  1066     @{term "Authkey \<notin> analz (spies (ev#evs))"}, not letting
  1066     @{term "Authkey \<notin> analz (spies (ev#evs))"}, not letting
  1067    @{text analz_mono_contra} weaken it to
  1067    \<open>analz_mono_contra\<close> weaken it to
  1068    @{term "Authkey \<notin> analz (spies evs)"},
  1068    @{term "Authkey \<notin> analz (spies evs)"},
  1069   for we then conclude @{term "authK \<noteq> authKa"}.*}
  1069   for we then conclude @{term "authK \<noteq> authKa"}.\<close>
  1070 apply analz_mono_contra
  1070 apply analz_mono_contra
  1071 apply (frule_tac [10] Oops_range_spies2)
  1071 apply (frule_tac [10] Oops_range_spies2)
  1072 apply (frule_tac [9] Oops_range_spies1)
  1072 apply (frule_tac [9] Oops_range_spies1)
  1073 apply (frule_tac [7] Says_ticket_analz)
  1073 apply (frule_tac [7] Says_ticket_analz)
  1074 apply (frule_tac [5] Says_ticket_analz)
  1074 apply (frule_tac [5] Says_ticket_analz)
  1075 apply (safe del: impI conjI impCE)
  1075 apply (safe del: impI conjI impCE)
  1076 apply (simp_all add: less_SucI new_keys_not_analzd Says_Kas_message_form Says_Tgs_message_form analz_insert_eq not_parts_not_analz analz_insert_freshK1 analz_insert_freshK2 analz_insert_freshK3_bis pushes)
  1076 apply (simp_all add: less_SucI new_keys_not_analzd Says_Kas_message_form Says_Tgs_message_form analz_insert_eq not_parts_not_analz analz_insert_freshK1 analz_insert_freshK2 analz_insert_freshK3_bis pushes)
  1077     txt{*Fake*}
  1077     txt\<open>Fake\<close>
  1078     apply spy_analz
  1078     apply spy_analz
  1079    txt{*K2*}
  1079    txt\<open>K2\<close>
  1080    apply (blast intro: parts_insertI less_SucI)
  1080    apply (blast intro: parts_insertI less_SucI)
  1081   txt{*K4*}
  1081   txt\<open>K4\<close>
  1082   apply (blast dest: authTicket_authentic Confidentiality_Kas)
  1082   apply (blast dest: authTicket_authentic Confidentiality_Kas)
  1083  txt{*Oops1*}
  1083  txt\<open>Oops1\<close>
  1084  apply (blast dest: Says_Kas_message_form Says_Tgs_message_form intro: less_SucI)
  1084  apply (blast dest: Says_Kas_message_form Says_Tgs_message_form intro: less_SucI)
  1085 txt{*Oops2*}
  1085 txt\<open>Oops2\<close>
  1086 apply (metis Suc_le_eq linorder_linear linorder_not_le msg.simps(2) unique_servKeys)
  1086 apply (metis Suc_le_eq linorder_linear linorder_not_le msg.simps(2) unique_servKeys)
  1087 done
  1087 done
  1088 
  1088 
  1089 
  1089 
  1090 text{* In the real world Tgs can't check wheter authK is secure! *}
  1090 text\<open>In the real world Tgs can't check wheter authK is secure!\<close>
  1091 lemma Confidentiality_Tgs:
  1091 lemma Confidentiality_Tgs:
  1092      "\<lbrakk> Says Tgs A
  1092      "\<lbrakk> Says Tgs A
  1093               \<lbrace>Crypt authK \<lbrace>Key servK, Agent B, Number Ts\<rbrace>, servTicket\<rbrace>
  1093               \<lbrace>Crypt authK \<lbrace>Key servK, Agent B, Number Ts\<rbrace>, servTicket\<rbrace>
  1094            \<in> set evs;
  1094            \<in> set evs;
  1095          Key authK \<notin> analz (spies evs);
  1095          Key authK \<notin> analz (spies evs);
  1096          \<not> expiredSK Ts evs;
  1096          \<not> expiredSK Ts evs;
  1097          A \<notin> bad;  B \<notin> bad; evs \<in> kerbV \<rbrakk>
  1097          A \<notin> bad;  B \<notin> bad; evs \<in> kerbV \<rbrakk>
  1098       \<Longrightarrow> Key servK \<notin> analz (spies evs)"
  1098       \<Longrightarrow> Key servK \<notin> analz (spies evs)"
  1099 by (blast dest: Says_Tgs_message_form Confidentiality_lemma)
  1099 by (blast dest: Says_Tgs_message_form Confidentiality_lemma)
  1100 
  1100 
  1101 text{* In the real world Tgs CAN check what Kas sends! *}
  1101 text\<open>In the real world Tgs CAN check what Kas sends!\<close>
  1102 lemma Confidentiality_Tgs_bis:
  1102 lemma Confidentiality_Tgs_bis:
  1103      "\<lbrakk> Says Kas A
  1103      "\<lbrakk> Says Kas A
  1104                \<lbrace>Crypt Ka \<lbrace>Key authK, Agent Tgs, Number Ta\<rbrace>, authTicket\<rbrace>
  1104                \<lbrace>Crypt Ka \<lbrace>Key authK, Agent Tgs, Number Ta\<rbrace>, authTicket\<rbrace>
  1105            \<in> set evs;
  1105            \<in> set evs;
  1106          Says Tgs A
  1106          Says Tgs A
  1109          \<not> expiredAK Ta evs; \<not> expiredSK Ts evs;
  1109          \<not> expiredAK Ta evs; \<not> expiredSK Ts evs;
  1110          A \<notin> bad;  B \<notin> bad; evs \<in> kerbV \<rbrakk>
  1110          A \<notin> bad;  B \<notin> bad; evs \<in> kerbV \<rbrakk>
  1111       \<Longrightarrow> Key servK \<notin> analz (spies evs)"
  1111       \<Longrightarrow> Key servK \<notin> analz (spies evs)"
  1112 by (blast dest!: Confidentiality_Kas Confidentiality_Tgs)
  1112 by (blast dest!: Confidentiality_Kas Confidentiality_Tgs)
  1113 
  1113 
  1114 text{*Most general form*}
  1114 text\<open>Most general form\<close>
  1115 lemmas Confidentiality_Tgs_ter = authTicket_authentic [THEN Confidentiality_Tgs_bis]
  1115 lemmas Confidentiality_Tgs_ter = authTicket_authentic [THEN Confidentiality_Tgs_bis]
  1116 
  1116 
  1117 lemmas Confidentiality_Auth_A = authK_authentic [THEN exE, THEN Confidentiality_Kas]
  1117 lemmas Confidentiality_Auth_A = authK_authentic [THEN exE, THEN Confidentiality_Kas]
  1118 
  1118 
  1119 text{*Needs a confidentiality guarantee, hence moved here.
  1119 text\<open>Needs a confidentiality guarantee, hence moved here.
  1120       Authenticity of servK for A*}
  1120       Authenticity of servK for A\<close>
  1121 lemma servK_authentic_bis_r:
  1121 lemma servK_authentic_bis_r:
  1122      "\<lbrakk> Crypt (shrK A) \<lbrace>Key authK, Agent Tgs, Number Ta\<rbrace>
  1122      "\<lbrakk> Crypt (shrK A) \<lbrace>Key authK, Agent Tgs, Number Ta\<rbrace>
  1123            \<in> parts (spies evs);
  1123            \<in> parts (spies evs);
  1124          Crypt authK \<lbrace>Key servK, Agent B, Number Ts\<rbrace>
  1124          Crypt authK \<lbrace>Key servK, Agent B, Number Ts\<rbrace>
  1125            \<in> parts (spies evs);
  1125            \<in> parts (spies evs);
  1166       \<Longrightarrow> Key servK \<notin> analz (spies evs)"
  1166       \<Longrightarrow> Key servK \<notin> analz (spies evs)"
  1167 by (blast dest: u_servTicket_authentic u_NotexpiredSK_NotexpiredAK Confidentiality_Tgs_bis)
  1167 by (blast dest: u_servTicket_authentic u_NotexpiredSK_NotexpiredAK Confidentiality_Tgs_bis)
  1168 
  1168 
  1169 
  1169 
  1170 
  1170 
  1171 subsection{*Parties authentication: each party verifies "the identity of
  1171 subsection\<open>Parties authentication: each party verifies "the identity of
  1172        another party who generated some data" (quoted from Neuman and Ts'o).*}
  1172        another party who generated some data" (quoted from Neuman and Ts'o).\<close>
  1173 
  1173 
  1174 text{*These guarantees don't assess whether two parties agree on
  1174 text\<open>These guarantees don't assess whether two parties agree on
  1175       the same session key: sending a message containing a key
  1175       the same session key: sending a message containing a key
  1176       doesn't a priori state knowledge of the key.*}
  1176       doesn't a priori state knowledge of the key.\<close>
  1177 
  1177 
  1178 
  1178 
  1179 text{*These didn't have existential form in version IV*}
  1179 text\<open>These didn't have existential form in version IV\<close>
  1180 lemma B_authenticates_A:
  1180 lemma B_authenticates_A:
  1181      "\<lbrakk> Crypt servK \<lbrace>Agent A, Number T3\<rbrace> \<in> parts (spies evs);
  1181      "\<lbrakk> Crypt servK \<lbrace>Agent A, Number T3\<rbrace> \<in> parts (spies evs);
  1182         Crypt (shrK B) \<lbrace>Agent A, Agent B, Key servK, Number Ts\<rbrace>
  1182         Crypt (shrK B) \<lbrace>Agent A, Agent B, Key servK, Number Ts\<rbrace>
  1183            \<in> parts (spies evs);
  1183            \<in> parts (spies evs);
  1184         Key servK \<notin> analz (spies evs);
  1184         Key servK \<notin> analz (spies evs);
  1185         A \<notin> bad; B \<notin> bad; B \<noteq> Tgs; evs \<in> kerbV \<rbrakk>
  1185         A \<notin> bad; B \<notin> bad; B \<noteq> Tgs; evs \<in> kerbV \<rbrakk>
  1186   \<Longrightarrow> \<exists> ST. Says A B \<lbrace>ST, Crypt servK \<lbrace>Agent A, Number T3\<rbrace> \<rbrace> \<in> set evs"
  1186   \<Longrightarrow> \<exists> ST. Says A B \<lbrace>ST, Crypt servK \<lbrace>Agent A, Number T3\<rbrace> \<rbrace> \<in> set evs"
  1187 by (blast dest: servTicket_authentic_Tgs intro: Says_K5)
  1187 by (blast dest: servTicket_authentic_Tgs intro: Says_K5)
  1188 
  1188 
  1189 text{*The second assumption tells B what kind of key servK is.*}
  1189 text\<open>The second assumption tells B what kind of key servK is.\<close>
  1190 lemma B_authenticates_A_r:
  1190 lemma B_authenticates_A_r:
  1191      "\<lbrakk> Crypt servK \<lbrace>Agent A, Number T3\<rbrace> \<in> parts (spies evs);
  1191      "\<lbrakk> Crypt servK \<lbrace>Agent A, Number T3\<rbrace> \<in> parts (spies evs);
  1192          Crypt (shrK B) \<lbrace>Agent A, Agent B, Key servK, Number Ts\<rbrace>
  1192          Crypt (shrK B) \<lbrace>Agent A, Agent B, Key servK, Number Ts\<rbrace>
  1193            \<in> parts (spies evs);
  1193            \<in> parts (spies evs);
  1194          Crypt authK \<lbrace>Key servK, Agent B, Number Ts\<rbrace>
  1194          Crypt authK \<lbrace>Key servK, Agent B, Number Ts\<rbrace>
  1198          \<not> expiredSK Ts evs; \<not> expiredAK Ta evs;
  1198          \<not> expiredSK Ts evs; \<not> expiredAK Ta evs;
  1199          B \<noteq> Tgs; A \<notin> bad;  B \<notin> bad;  evs \<in> kerbV \<rbrakk>
  1199          B \<noteq> Tgs; A \<notin> bad;  B \<notin> bad;  evs \<in> kerbV \<rbrakk>
  1200   \<Longrightarrow> \<exists> ST. Says A B \<lbrace>ST, Crypt servK \<lbrace>Agent A, Number T3\<rbrace> \<rbrace> \<in> set evs"
  1200   \<Longrightarrow> \<exists> ST. Says A B \<lbrace>ST, Crypt servK \<lbrace>Agent A, Number T3\<rbrace> \<rbrace> \<in> set evs"
  1201 by (blast intro: Says_K5 dest: Confidentiality_B servTicket_authentic_Tgs)
  1201 by (blast intro: Says_K5 dest: Confidentiality_B servTicket_authentic_Tgs)
  1202 
  1202 
  1203 text{* @{text u_B_authenticates_A} would be the same as @{text B_authenticates_A} because the
  1203 text\<open>\<open>u_B_authenticates_A\<close> would be the same as \<open>B_authenticates_A\<close> because the
  1204  servK confidentiality assumption is yet unrelaxed*}
  1204  servK confidentiality assumption is yet unrelaxed\<close>
  1205 
  1205 
  1206 lemma u_B_authenticates_A_r:
  1206 lemma u_B_authenticates_A_r:
  1207      "\<lbrakk> Crypt servK \<lbrace>Agent A, Number T3\<rbrace> \<in> parts (spies evs);
  1207      "\<lbrakk> Crypt servK \<lbrace>Agent A, Number T3\<rbrace> \<in> parts (spies evs);
  1208          Crypt (shrK B) \<lbrace>Agent A, Agent B, Key servK, Number Ts\<rbrace>
  1208          Crypt (shrK B) \<lbrace>Agent A, Agent B, Key servK, Number Ts\<rbrace>
  1209            \<in> parts (spies evs);
  1209            \<in> parts (spies evs);
  1241 apply (metis Confidentiality_Tgs K4_imp_K2 Says_K6 unique_authKeys) 
  1241 apply (metis Confidentiality_Tgs K4_imp_K2 Says_K6 unique_authKeys) 
  1242 done
  1242 done
  1243 
  1243 
  1244 
  1244 
  1245 
  1245 
  1246 subsection{*Parties' knowledge of session keys. 
  1246 subsection\<open>Parties' knowledge of session keys. 
  1247        An agent knows a session key if he used it to issue a cipher. These
  1247        An agent knows a session key if he used it to issue a cipher. These
  1248        guarantees can be interpreted both in terms of key distribution
  1248        guarantees can be interpreted both in terms of key distribution
  1249        and of non-injective agreement on the session key.*}
  1249        and of non-injective agreement on the session key.\<close>
  1250 
  1250 
  1251 lemma Kas_Issues_A:
  1251 lemma Kas_Issues_A:
  1252    "\<lbrakk> Says Kas A \<lbrace>Crypt (shrK A) \<lbrace>Key authK, Peer, Ta\<rbrace>, authTicket\<rbrace> \<in> set evs;
  1252    "\<lbrakk> Says Kas A \<lbrace>Crypt (shrK A) \<lbrace>Key authK, Peer, Ta\<rbrace>, authTicket\<rbrace> \<in> set evs;
  1253       evs \<in> kerbV \<rbrakk>
  1253       evs \<in> kerbV \<rbrakk>
  1254   \<Longrightarrow> Kas Issues A with (Crypt (shrK A) \<lbrace>Key authK, Peer, Ta\<rbrace>)
  1254   \<Longrightarrow> Kas Issues A with (Crypt (shrK A) \<lbrace>Key authK, Peer, Ta\<rbrace>)
  1260 apply (erule rev_mp)
  1260 apply (erule rev_mp)
  1261 apply (erule kerbV.induct)
  1261 apply (erule kerbV.induct)
  1262 apply (frule_tac [5] Says_ticket_parts)
  1262 apply (frule_tac [5] Says_ticket_parts)
  1263 apply (frule_tac [7] Says_ticket_parts)
  1263 apply (frule_tac [7] Says_ticket_parts)
  1264 apply (simp_all (no_asm_simp) add: all_conj_distrib)
  1264 apply (simp_all (no_asm_simp) add: all_conj_distrib)
  1265 txt{*K2*}
  1265 txt\<open>K2\<close>
  1266 apply (simp add: takeWhile_tail)
  1266 apply (simp add: takeWhile_tail)
  1267 apply (metis MPair_parts parts.Body parts_idem parts_spies_takeWhile_mono parts_trans spies_evs_rev usedI)
  1267 apply (metis MPair_parts parts.Body parts_idem parts_spies_takeWhile_mono parts_trans spies_evs_rev usedI)
  1268 done
  1268 done
  1269 
  1269 
  1270 lemma A_authenticates_and_keydist_to_Kas:
  1270 lemma A_authenticates_and_keydist_to_Kas:
  1317 apply (erule rev_mp)
  1317 apply (erule rev_mp)
  1318 apply (erule rev_mp)
  1318 apply (erule rev_mp)
  1319 apply (erule kerbV.induct, analz_mono_contra)
  1319 apply (erule kerbV.induct, analz_mono_contra)
  1320 apply (simp_all (no_asm_simp) add: all_conj_distrib)
  1320 apply (simp_all (no_asm_simp) add: all_conj_distrib)
  1321 apply blast
  1321 apply blast
  1322 txt{*K6 requires numerous lemmas*}
  1322 txt\<open>K6 requires numerous lemmas\<close>
  1323 apply (simp add: takeWhile_tail)
  1323 apply (simp add: takeWhile_tail)
  1324 apply (blast intro: Says_K6 dest: servTicket_authentic 
  1324 apply (blast intro: Says_K6 dest: servTicket_authentic 
  1325         parts_spies_takeWhile_mono [THEN subsetD] 
  1325         parts_spies_takeWhile_mono [THEN subsetD] 
  1326         parts_spies_evs_revD2 [THEN subsetD])
  1326         parts_spies_evs_revD2 [THEN subsetD])
  1327 done
  1327 done
  1362 txt{*cannot solve K6 unless B updates the timestamp - rather than bouncing T3*}
  1362 txt{*cannot solve K6 unless B updates the timestamp - rather than bouncing T3*}
  1363 oops
  1363 oops
  1364 *)
  1364 *)
  1365 
  1365 
  1366 
  1366 
  1367 text{*But can prove a less general fact conerning only authenticators!*}
  1367 text\<open>But can prove a less general fact conerning only authenticators!\<close>
  1368 lemma honest_never_says_newer_timestamp_in_auth:
  1368 lemma honest_never_says_newer_timestamp_in_auth:
  1369      "\<lbrakk> (CT evs) \<le> T; Number T \<in> parts {X}; A \<notin> bad; evs \<in> kerbV \<rbrakk> 
  1369      "\<lbrakk> (CT evs) \<le> T; Number T \<in> parts {X}; A \<notin> bad; evs \<in> kerbV \<rbrakk> 
  1370      \<Longrightarrow> Says A B \<lbrace>Y, X\<rbrace> \<notin> set evs"
  1370      \<Longrightarrow> Says A B \<lbrace>Y, X\<rbrace> \<notin> set evs"
  1371 apply (erule rev_mp)
  1371 apply (erule rev_mp)
  1372 apply (erule kerbV.induct)
  1372 apply (erule kerbV.induct)
  1392 apply (erule rev_mp)
  1392 apply (erule rev_mp)
  1393 apply (erule kerbV.induct, analz_mono_contra)
  1393 apply (erule kerbV.induct, analz_mono_contra)
  1394 apply (frule_tac [7] Says_ticket_parts)
  1394 apply (frule_tac [7] Says_ticket_parts)
  1395 apply (frule_tac [5] Says_ticket_parts)
  1395 apply (frule_tac [5] Says_ticket_parts)
  1396 apply (simp_all (no_asm_simp))
  1396 apply (simp_all (no_asm_simp))
  1397 txt{*K5*}
  1397 txt\<open>K5\<close>
  1398 apply auto
  1398 apply auto
  1399 apply (simp add: takeWhile_tail)
  1399 apply (simp add: takeWhile_tail)
  1400 txt{*Level 15: case study necessary because the assumption doesn't state
  1400 txt\<open>Level 15: case study necessary because the assumption doesn't state
  1401   the form of servTicket. The guarantee becomes stronger.*}
  1401   the form of servTicket. The guarantee becomes stronger.\<close>
  1402 prefer 2 apply (simp add: takeWhile_tail)
  1402 prefer 2 apply (simp add: takeWhile_tail)
  1403 (**This single command of version IV...
  1403 (**This single command of version IV...
  1404 apply (blast dest: Says_imp_spies [THEN analz.Inj, THEN analz_Decrypt']
  1404 apply (blast dest: Says_imp_spies [THEN analz.Inj, THEN analz_Decrypt']
  1405                    K3_imp_K2 K4_trustworthy'
  1405                    K3_imp_K2 K4_trustworthy'
  1406                    parts_spies_takeWhile_mono [THEN subsetD]
  1406                    parts_spies_takeWhile_mono [THEN subsetD]
  1413 apply (frule K3_imp_K2, assumption, assumption, erule exE, erule exE)
  1413 apply (frule K3_imp_K2, assumption, assumption, erule exE, erule exE)
  1414 apply (drule Says_imp_knows_Spy [THEN parts.Inj, THEN parts.Fst])
  1414 apply (drule Says_imp_knows_Spy [THEN parts.Inj, THEN parts.Fst])
  1415 apply (frule servK_authentic_ter, blast, assumption+)
  1415 apply (frule servK_authentic_ter, blast, assumption+)
  1416 apply (drule parts_spies_takeWhile_mono [THEN subsetD])
  1416 apply (drule parts_spies_takeWhile_mono [THEN subsetD])
  1417 apply (drule parts_spies_evs_revD2 [THEN subsetD])
  1417 apply (drule parts_spies_evs_revD2 [THEN subsetD])
  1418 txt{* @{term Says_K5} closes the proof in version IV because it is clear which 
  1418 txt\<open>@{term Says_K5} closes the proof in version IV because it is clear which 
  1419 servTicket an authenticator appears with in msg 5. In version V an authenticator can appear with any item that the spy could replace the servTicket with*}
  1419 servTicket an authenticator appears with in msg 5. In version V an authenticator can appear with any item that the spy could replace the servTicket with\<close>
  1420 apply (frule Says_K5, blast)
  1420 apply (frule Says_K5, blast)
  1421 txt{*We need to state that an honest agent wouldn't send the wrong timestamp
  1421 txt\<open>We need to state that an honest agent wouldn't send the wrong timestamp
  1422 within an authenticator, wathever it is paired with*}
  1422 within an authenticator, wathever it is paired with\<close>
  1423 apply (auto simp add: honest_never_says_current_timestamp_in_auth)
  1423 apply (auto simp add: honest_never_says_current_timestamp_in_auth)
  1424 done
  1424 done
  1425 
  1425 
  1426 lemma B_authenticates_and_keydist_to_A:
  1426 lemma B_authenticates_and_keydist_to_A:
  1427      "\<lbrakk> Crypt servK \<lbrace>Agent A, Number T3\<rbrace> \<in> parts (spies evs);
  1427      "\<lbrakk> Crypt servK \<lbrace>Agent A, Number T3\<rbrace> \<in> parts (spies evs);
  1432    \<Longrightarrow> A Issues B with (Crypt servK \<lbrace>Agent A, Number T3\<rbrace>) on evs"
  1432    \<Longrightarrow> A Issues B with (Crypt servK \<lbrace>Agent A, Number T3\<rbrace>) on evs"
  1433 by (blast dest: B_authenticates_A A_Issues_B)
  1433 by (blast dest: B_authenticates_A A_Issues_B)
  1434 
  1434 
  1435 
  1435 
  1436 
  1436 
  1437 subsection{*
  1437 subsection\<open>
  1438 Novel guarantees, never studied before. Because honest agents always say
  1438 Novel guarantees, never studied before. Because honest agents always say
  1439 the right timestamp in authenticators, we can prove unicity guarantees based 
  1439 the right timestamp in authenticators, we can prove unicity guarantees based 
  1440 exactly on timestamps. Classical unicity guarantees are based on nonces.
  1440 exactly on timestamps. Classical unicity guarantees are based on nonces.
  1441 Of course assuming the agent to be different from the Spy, rather than not in 
  1441 Of course assuming the agent to be different from the Spy, rather than not in 
  1442 bad, would suffice below. Similar guarantees must also hold of
  1442 bad, would suffice below. Similar guarantees must also hold of
  1443 Kerberos IV.*}
  1443 Kerberos IV.\<close>
  1444 
  1444 
  1445 text{*Notice that an honest agent can send the same timestamp on two
  1445 text\<open>Notice that an honest agent can send the same timestamp on two
  1446 different traces of the same length, but not on the same trace!*}
  1446 different traces of the same length, but not on the same trace!\<close>
  1447 
  1447 
  1448 lemma unique_timestamp_authenticator1:
  1448 lemma unique_timestamp_authenticator1:
  1449      "\<lbrakk> Says A Kas \<lbrace>Agent A, Agent Tgs, Number T1\<rbrace> \<in> set evs;
  1449      "\<lbrakk> Says A Kas \<lbrace>Agent A, Agent Tgs, Number T1\<rbrace> \<in> set evs;
  1450          Says A Kas' \<lbrace>Agent A, Agent Tgs', Number T1\<rbrace> \<in> set evs;
  1450          Says A Kas' \<lbrace>Agent A, Agent Tgs', Number T1\<rbrace> \<in> set evs;
  1451          A \<notin>bad; evs \<in> kerbV \<rbrakk>
  1451          A \<notin>bad; evs \<in> kerbV \<rbrakk>
  1473 apply (erule rev_mp, erule rev_mp)
  1473 apply (erule rev_mp, erule rev_mp)
  1474 apply (erule kerbV.induct)
  1474 apply (erule kerbV.induct)
  1475 apply (auto simp add: honest_never_says_current_timestamp_in_auth)
  1475 apply (auto simp add: honest_never_says_current_timestamp_in_auth)
  1476 done
  1476 done
  1477 
  1477 
  1478 text{*The second part of the message is treated as an authenticator by the last
  1478 text\<open>The second part of the message is treated as an authenticator by the last
  1479 simplification step, even if it is not an authenticator!*}
  1479 simplification step, even if it is not an authenticator!\<close>
  1480 lemma unique_timestamp_authticket:
  1480 lemma unique_timestamp_authticket:
  1481      "\<lbrakk> Says Kas A \<lbrace>X, Crypt (shrK Tgs) \<lbrace>Agent A, Agent Tgs, Key AK, T\<rbrace>\<rbrace> \<in> set evs;
  1481      "\<lbrakk> Says Kas A \<lbrace>X, Crypt (shrK Tgs) \<lbrace>Agent A, Agent Tgs, Key AK, T\<rbrace>\<rbrace> \<in> set evs;
  1482        Says Kas A' \<lbrace>X', Crypt (shrK Tgs') \<lbrace>Agent A', Agent Tgs', Key AK', T\<rbrace>\<rbrace> \<in> set evs;
  1482        Says Kas A' \<lbrace>X', Crypt (shrK Tgs') \<lbrace>Agent A', Agent Tgs', Key AK', T\<rbrace>\<rbrace> \<in> set evs;
  1483          evs \<in> kerbV \<rbrakk>
  1483          evs \<in> kerbV \<rbrakk>
  1484   \<Longrightarrow> A=A' \<and> X=X' \<and> Tgs=Tgs' \<and> AK=AK'"
  1484   \<Longrightarrow> A=A' \<and> X=X' \<and> Tgs=Tgs' \<and> AK=AK'"
  1485 apply (erule rev_mp, erule rev_mp)
  1485 apply (erule rev_mp, erule rev_mp)
  1486 apply (erule kerbV.induct)
  1486 apply (erule kerbV.induct)
  1487 apply (auto simp add: honest_never_says_current_timestamp_in_auth)
  1487 apply (auto simp add: honest_never_says_current_timestamp_in_auth)
  1488 done
  1488 done
  1489 
  1489 
  1490 text{*The second part of the message is treated as an authenticator by the last
  1490 text\<open>The second part of the message is treated as an authenticator by the last
  1491 simplification step, even if it is not an authenticator!*}
  1491 simplification step, even if it is not an authenticator!\<close>
  1492 lemma unique_timestamp_servticket:
  1492 lemma unique_timestamp_servticket:
  1493      "\<lbrakk> Says Tgs A \<lbrace>X, Crypt (shrK B) \<lbrace>Agent A, Agent B, Key SK, T\<rbrace>\<rbrace> \<in> set evs;
  1493      "\<lbrakk> Says Tgs A \<lbrace>X, Crypt (shrK B) \<lbrace>Agent A, Agent B, Key SK, T\<rbrace>\<rbrace> \<in> set evs;
  1494        Says Tgs A' \<lbrace>X', Crypt (shrK B') \<lbrace>Agent A', Agent B', Key SK', T\<rbrace>\<rbrace> \<in> set evs;
  1494        Says Tgs A' \<lbrace>X', Crypt (shrK B') \<lbrace>Agent A', Agent B', Key SK', T\<rbrace>\<rbrace> \<in> set evs;
  1495          evs \<in> kerbV \<rbrakk>
  1495          evs \<in> kerbV \<rbrakk>
  1496   \<Longrightarrow> A=A' \<and> X=X' \<and> B=B' \<and> SK=SK'"
  1496   \<Longrightarrow> A=A' \<and> X=X' \<and> B=B' \<and> SK=SK'"