(*  Title:      HOL/SPARK/Examples/RIPEMD-160/Round.thy
    Author:     Fabian Immler, TU Muenchen

Verification of the RIPEMD-160 hash function
*)

theory Round
imports RMD_Specification
begin

spark_open \<open>rmd/round\<close>

abbreviation from_chain :: "chain \<Rightarrow> RMD.chain" where
  "from_chain c \<equiv> (
    word_of_int (h0 c),
    word_of_int (h1 c),
    word_of_int (h2 c),
    word_of_int (h3 c),
    word_of_int (h4 c))"

abbreviation from_chain_pair :: "chain_pair \<Rightarrow> RMD.chain \<times> RMD.chain" where
  "from_chain_pair cc \<equiv> (
    from_chain (left cc),
    from_chain (right cc))"

abbreviation to_chain :: "RMD.chain \<Rightarrow> chain" where
  "to_chain c \<equiv>
    (let (h0, h1, h2, h3, h4) = c in
      (|h0 = uint h0,
        h1 = uint h1,
        h2 = uint h2,
        h3 = uint h3,
        h4 = uint h4|))"

abbreviation to_chain_pair :: "RMD.chain \<times> RMD.chain \<Rightarrow> chain_pair" where
  "to_chain_pair c == (let (c1, c2) = c in
    (| left = to_chain c1,
      right = to_chain c2 |))"

abbreviation steps' :: "chain_pair \<Rightarrow> int \<Rightarrow> block \<Rightarrow> chain_pair" where
  "steps' cc i b == to_chain_pair (steps
    (\<lambda>n. word_of_int (b (int n)))
    (from_chain_pair cc)
    (nat i))"

abbreviation round_spec :: "chain \<Rightarrow> block \<Rightarrow> chain" where
  "round_spec c b == to_chain (round (\<lambda>n. word_of_int (b (int n))) (from_chain c))"

spark_proof_functions
  steps = steps'
  round_spec = round_spec

lemma uint_word_of_int_id:
  assumes "0 <= (x::int)"
  assumes "x <= 4294967295"
  shows"uint(word_of_int x::word32) = x"
  using assms by (simp add: take_bit_int_eq_self)

lemma steps_step: "steps X cc (Suc i) = step_both X (steps X cc i) i"
  unfolding steps_def
  by (induct i) simp_all

lemma from_to_id: "from_chain_pair (to_chain_pair CC) = CC"
proof (cases CC)
  fix a::RMD.chain
  fix b c d e f::word32
  assume "CC = (a, b, c, d, e, f)"
  thus ?thesis by (cases a) simp
qed

lemma steps_to_steps':
  "F A (steps X cc i) B =
   F A (from_chain_pair (to_chain_pair (steps X cc i))) B"
  unfolding from_to_id ..

lemma steps'_step:
  assumes "0 <= i"
  shows
  "steps' cc (i + 1) X = to_chain_pair (
     step_both
       (\<lambda>n. word_of_int (X (int n)))
       (from_chain_pair (steps' cc i X))
       (nat i))"
proof -
  have "nat (i + 1) = Suc (nat i)" using assms by simp
  show ?thesis
    unfolding \<open>nat (i + 1) = Suc (nat i)\<close> steps_step steps_to_steps'
    ..
qed

lemma step_from_hyp:
  assumes
  step_hyp:
  "\<lparr>left =
      \<lparr>h0 = a, h1 = b, h2 = c, h3 = d, h4 = e\<rparr>,
    right =
      \<lparr>h0 = a', h1 = b', h2 = c', h3 = d', h4 = e'\<rparr>\<rparr> =
   steps'
     (\<lparr>left =
         \<lparr>h0 = a_0, h1 = b_0, h2 = c_0,
          h3 = d_0, h4 = e_0\<rparr>,
       right =
         \<lparr>h0 = a_0, h1 = b_0, h2 = c_0,
          h3 = d_0, h4 = e_0\<rparr>\<rparr>)
     j x"
  assumes "a <= 4294967295" (is "_ <= ?M")
  assumes                "b  <= ?M" and "c  <= ?M" and "d  <= ?M" and "e  <= ?M"
  assumes "a' <= ?M" and "b' <= ?M" and "c' <= ?M" and "d' <= ?M" and "e' <= ?M"
  assumes "0 <= a " and "0 <= b " and "0 <= c " and "0 <= d " and "0 <= e "
  assumes "0 <= a'" and "0 <= b'" and "0 <= c'" and "0 <= d'" and "0 <= e'"
  assumes "0 <= x (r_l_spec j)" and "x (r_l_spec j) <= ?M"
  assumes "0 <= x (r_r_spec j)" and "x (r_r_spec j) <= ?M"
  assumes "0 <= j" and "j <= 79"
  shows
  "\<lparr>left =
      \<lparr>h0 = e,
         h1 =
           (rotate_left (s_l_spec j)
             ((((a + f_spec j b c d) mod 4294967296 +
                x (r_l_spec j)) mod
               4294967296 +
               k_l_spec j) mod
              4294967296) +
            e) mod
           4294967296,
         h2 = b, h3 = rotate_left 10 c,
         h4 = d\<rparr>,
      right =
        \<lparr>h0 = e',
           h1 =
             (rotate_left (s_r_spec j)
               ((((a' + f_spec (79 - j) b' c' d') mod
                  4294967296 +
                  x (r_r_spec j)) mod
                 4294967296 +
                 k_r_spec j) mod
                4294967296) +
              e') mod
             4294967296,
           h2 = b', h3 = rotate_left 10 c',
           h4 = d'\<rparr>\<rparr> =
   steps'
    (\<lparr>left =
        \<lparr>h0 = a_0, h1 = b_0, h2 = c_0,
           h3 = d_0, h4 = e_0\<rparr>,
        right =
          \<lparr>h0 = a_0, h1 = b_0, h2 = c_0,
             h3 = d_0, h4 = e_0\<rparr>\<rparr>)
    (j + 1) x"
  using step_hyp
proof -
  let ?MM = 4294967296
  have AL: "uint(word_of_int e::word32) = e"
    by (rule uint_word_of_int_id[OF \<open>0 <= e\<close> \<open>e <= ?M\<close>])
  have CL: "uint(word_of_int b::word32) = b"
    by (rule uint_word_of_int_id[OF \<open>0 <= b\<close> \<open>b <= ?M\<close>])
  have DL: "True" ..
  have EL: "uint(word_of_int d::word32) = d"
    by (rule uint_word_of_int_id[OF \<open>0 <= d\<close> \<open>d <= ?M\<close>])
  have AR: "uint(word_of_int e'::word32) = e'"
    by (rule uint_word_of_int_id[OF \<open>0 <= e'\<close> \<open>e' <= ?M\<close>])
  have CR: "uint(word_of_int b'::word32) = b'"
    by (rule uint_word_of_int_id[OF \<open>0 <= b'\<close> \<open>b' <= ?M\<close>])
  have DR: "True" ..
  have ER: "uint(word_of_int d'::word32) = d'"
    by (rule uint_word_of_int_id[OF \<open>0 <= d'\<close> \<open>d' <= ?M\<close>])
  have BL:
    "(uint
      (word_rotl (s (nat j))
        ((word_of_int::int\<Rightarrow>word32)
          ((((a + f_spec j b c d) mod ?MM +
             x (r_l_spec j)) mod ?MM +
            k_l_spec j) mod ?MM))) +
        e) mod ?MM
    =
    uint
              (word_rotl (s (nat j))
                (word_of_int a +
                 f (nat j) (word_of_int b)
                  (word_of_int c) (word_of_int d) +
                 word_of_int (x (r_l_spec j)) +
                 K (nat j)) +
               word_of_int e)"
    (is "(uint (word_rotl _ (_ ((((_ + ?F) mod _ + ?X) mod _ + _) mod _))) + _) mod _ = _")
  proof -
    have "a mod ?MM = a" using \<open>0 <= a\<close> \<open>a <= ?M\<close>
      by simp
    have "?X mod ?MM = ?X" using \<open>0 <= ?X\<close> \<open>?X <= ?M\<close>
      by simp
    have "e mod ?MM = e" using \<open>0 <= e\<close> \<open>e <= ?M\<close>
      by simp
    have "(?MM::int) = 2 ^ LENGTH(32)" by simp
    show ?thesis
      unfolding
        word_add_def
        uint_word_of_int_id[OF \<open>0 <= a\<close> \<open>a <= ?M\<close>]
        uint_word_of_int_id[OF \<open>0 <= ?X\<close> \<open>?X <= ?M\<close>]
      using \<open>a mod ?MM = a\<close>
        \<open>e mod ?MM = e\<close>
        \<open>?X mod ?MM = ?X\<close>
      unfolding \<open>?MM = 2 ^ LENGTH(32)\<close>
      apply (simp only: flip: take_bit_eq_mod add: uint_word_of_int_eq)
      apply (metis (mono_tags, hide_lams) of_int_of_nat_eq ucast_id uint_word_of_int_eq unsigned_of_int)
      done
  qed

  have BR:
    "(uint
      (word_rotl (s' (nat j))
        ((word_of_int::int\<Rightarrow>word32)
          ((((a' + f_spec (79 - j) b' c' d') mod ?MM +
             x (r_r_spec j)) mod ?MM +
            k_r_spec j) mod ?MM))) +
        e') mod ?MM
    =
    uint
              (word_rotl (s' (nat j))
                (word_of_int a' +
                 f (79 - nat j) (word_of_int b')
                  (word_of_int c') (word_of_int d') +
                 word_of_int (x (r_r_spec j)) +
                 K' (nat j)) +
               word_of_int e')"
    (is "(uint (word_rotl _ (_ ((((_ + ?F) mod _ + ?X) mod _ + _) mod _))) + _) mod _ = _")
  proof -
    have "a' mod ?MM = a'" using \<open>0 <= a'\<close> \<open>a' <= ?M\<close>
      by simp
    have "?X mod ?MM = ?X" using \<open>0 <= ?X\<close> \<open>?X <= ?M\<close>
      by simp
    have "e' mod ?MM = e'" using \<open>0 <= e'\<close> \<open>e' <= ?M\<close>
      by simp
    have "(?MM::int) = 2 ^ LENGTH(32)" by simp
    have nat_transfer: "79 - nat j = nat (79 - j)"
      using nat_diff_distrib \<open>0 <= j\<close>  \<open>j <= 79\<close>
      by simp
    show ?thesis
      unfolding
        word_add_def
        uint_word_of_int_id[OF \<open>0 <= a'\<close> \<open>a' <= ?M\<close>]
        uint_word_of_int_id[OF \<open>0 <= ?X\<close> \<open>?X <= ?M\<close>]
        nat_transfer
      using \<open>a' mod ?MM = a'\<close>
        \<open>e' mod ?MM = e'\<close>
        \<open>?X mod ?MM = ?X\<close>
      unfolding \<open>?MM = 2 ^ LENGTH(32)\<close>
      apply (simp only: flip: take_bit_eq_mod add: uint_word_of_int_eq)
      apply (metis (mono_tags, hide_lams) of_nat_nat_take_bit_eq ucast_id unsigned_of_int)
      done
  qed

  show ?thesis
    unfolding steps'_step[OF \<open>0 <= j\<close>] step_hyp[symmetric]
      step_both_def step_r_def step_l_def
    using AL CL EL AR CR ER
    by (simp add: BL DL BR DR take_bit_int_eq_self_iff take_bit_int_eq_self)
qed

spark_vc procedure_round_61
proof -
  let ?M = "4294967295::int"
  have step_hyp:
  "\<lparr>left =
      \<lparr>h0 = ca, h1 = cb, h2 = cc,
         h3 = cd, h4 = ce\<rparr>,
      right =
        \<lparr>h0 = ca, h1 = cb, h2 = cc,
           h3 = cd, h4 = ce\<rparr>\<rparr> =
   steps'
    (\<lparr>left =
        \<lparr>h0 = ca, h1 = cb, h2 = cc,
           h3 = cd, h4 = ce\<rparr>,
        right =
          \<lparr>h0 = ca, h1 = cb, h2 = cc,
             h3 = cd, h4 = ce\<rparr>\<rparr>)
    0 x"
    unfolding steps_def
    using
      uint_word_of_int_id[OF \<open>0 <= ca\<close> \<open>ca <= ?M\<close>]
      uint_word_of_int_id[OF \<open>0 <= cb\<close> \<open>cb <= ?M\<close>]
      uint_word_of_int_id[OF \<open>0 <= cc\<close> \<open>cc <= ?M\<close>]
      uint_word_of_int_id[OF \<open>0 <= cd\<close> \<open>cd <= ?M\<close>]
      uint_word_of_int_id[OF \<open>0 <= ce\<close> \<open>ce <= ?M\<close>]
    by (simp add: take_bit_int_eq_self_iff take_bit_int_eq_self)
  let ?rotate_arg_l =
    "((((ca + f 0 cb cc cd) mod 4294967296 +
        x (r_l 0)) mod 4294967296 + k_l 0) mod 4294967296)"
  let ?rotate_arg_r =
    "((((ca + f 79 cb cc cd) mod 4294967296 +
        x (r_r 0)) mod 4294967296 + k_r 0) mod 4294967296)"
  note returns =
    \<open>wordops__rotate (s_l 0) ?rotate_arg_l =
     rotate_left (s_l 0) ?rotate_arg_l\<close>
    \<open>wordops__rotate (s_r 0) ?rotate_arg_r =
     rotate_left (s_r 0) ?rotate_arg_r\<close>
    \<open>wordops__rotate 10 cc = rotate_left 10 cc\<close>
    \<open>f 0 cb cc cd = f_spec 0 cb cc cd\<close>
    \<open>f 79 cb cc cd = f_spec 79 cb cc cd\<close>
    \<open>k_l 0 = k_l_spec 0\<close>
    \<open>k_r 0 = k_r_spec 0\<close>
    \<open>r_l 0 = r_l_spec 0\<close>
    \<open>r_r 0 = r_r_spec 0\<close>
    \<open>s_l 0 = s_l_spec 0\<close>
    \<open>s_r 0 = s_r_spec 0\<close>

  note x_borders = \<open>\<forall>i. 0 \<le> i \<and> i \<le> 15 \<longrightarrow> 0 \<le> x i \<and> x i \<le> ?M\<close>

  from \<open>0 <= r_l 0\<close> \<open>r_l 0 <= 15\<close> x_borders
  have "0 \<le> x (r_l 0)" by blast
  hence x_lower: "0 <= x (r_l_spec 0)" unfolding returns .

  from \<open>0 <= r_l 0\<close> \<open>r_l 0 <= 15\<close> x_borders
  have "x (r_l 0) <= ?M" by blast
  hence x_upper: "x (r_l_spec 0) <= ?M" unfolding returns .

  from \<open>0 <= r_r 0\<close> \<open>r_r 0 <= 15\<close> x_borders
  have "0 \<le> x (r_r 0)" by blast
  hence x_lower': "0 <= x (r_r_spec 0)" unfolding returns .

  from \<open>0 <= r_r 0\<close> \<open>r_r 0 <= 15\<close> x_borders
  have "x (r_r 0) <= ?M" by blast
  hence x_upper': "x (r_r_spec 0) <= ?M" unfolding returns .

  have "0 <= (0::int)" by simp
  have "0 <= (79::int)" by simp
  note step_from_hyp [OF
    step_hyp
    H2 H4 H6 H8 H10 H2 H4 H6 H8 H10 \<comment> \<open>upper bounds\<close>
    H1 H3 H5 H7 H9  H1 H3 H5 H7 H9  \<comment> \<open>lower bounds\<close>
  ]
  from this[OF x_lower x_upper x_lower' x_upper' \<open>0 <= 0\<close> \<open>0 <= 79\<close>]
    \<open>0 \<le> ca\<close> \<open>0 \<le> ce\<close> x_lower x_lower'
  show ?thesis unfolding returns(1) returns(2) unfolding returns
    by (simp del: mod_pos_pos_trivial mod_neg_neg_trivial)
qed

spark_vc procedure_round_62
proof -
  let ?M = "4294967295::int"
  let ?rotate_arg_l =
    "((((cla + f (loop__1__j + 1) clb clc cld) mod 4294967296 +
         x (r_l (loop__1__j + 1))) mod 4294967296 +
         k_l (loop__1__j + 1)) mod 4294967296)"
  let ?rotate_arg_r =
    "((((cra + f (79 - (loop__1__j + 1)) crb crc crd) mod
         4294967296 + x (r_r (loop__1__j + 1))) mod 4294967296 +
         k_r (loop__1__j + 1)) mod 4294967296)"

  have s: "78 - loop__1__j = (79 - (loop__1__j + 1))" by simp
  note returns =
    \<open>wordops__rotate (s_l (loop__1__j + 1)) ?rotate_arg_l =
     rotate_left (s_l (loop__1__j + 1)) ?rotate_arg_l\<close>
    \<open>wordops__rotate (s_r (loop__1__j + 1)) ?rotate_arg_r =
     rotate_left (s_r (loop__1__j + 1)) ?rotate_arg_r\<close>
    \<open>f (loop__1__j + 1) clb clc cld =
     f_spec (loop__1__j + 1) clb clc cld\<close>
    \<open>f (78 - loop__1__j) crb crc crd =
     f_spec (78 - loop__1__j) crb crc crd\<close>[simplified s]
    \<open>wordops__rotate 10 clc = rotate_left 10 clc\<close>
    \<open>wordops__rotate 10 crc = rotate_left 10 crc\<close>
    \<open>k_l (loop__1__j + 1) = k_l_spec (loop__1__j + 1)\<close>
    \<open>k_r (loop__1__j + 1) = k_r_spec (loop__1__j + 1)\<close>
    \<open>r_l (loop__1__j + 1) = r_l_spec (loop__1__j + 1)\<close>
    \<open>r_r (loop__1__j + 1) = r_r_spec (loop__1__j + 1)\<close>
    \<open>s_l (loop__1__j + 1) = s_l_spec (loop__1__j + 1)\<close>
    \<open>s_r (loop__1__j + 1) = s_r_spec (loop__1__j + 1)\<close>

  note x_borders = \<open>\<forall>i. 0 \<le> i \<and> i \<le> 15 \<longrightarrow> 0 \<le> x i \<and> x i \<le> ?M\<close>

  from \<open>0 <= r_l (loop__1__j + 1)\<close> \<open>r_l (loop__1__j + 1) <= 15\<close> x_borders
  have "0 \<le> x (r_l (loop__1__j + 1))" by blast
  hence x_lower: "0 <= x (r_l_spec (loop__1__j + 1))" unfolding returns .

  from \<open>0 <= r_l (loop__1__j + 1)\<close> \<open>r_l (loop__1__j + 1) <= 15\<close> x_borders
  have "x (r_l (loop__1__j + 1)) <= ?M" by blast
  hence x_upper: "x (r_l_spec (loop__1__j + 1)) <= ?M" unfolding returns .

  from \<open>0 <= r_r (loop__1__j + 1)\<close> \<open>r_r (loop__1__j + 1) <= 15\<close> x_borders
  have "0 \<le> x (r_r (loop__1__j + 1))" by blast
  hence x_lower': "0 <= x (r_r_spec (loop__1__j + 1))" unfolding returns .

  from \<open>0 <= r_r (loop__1__j + 1)\<close> \<open>r_r (loop__1__j + 1) <= 15\<close> x_borders
  have "x (r_r (loop__1__j + 1)) <= ?M" by blast
  hence x_upper': "x (r_r_spec (loop__1__j + 1)) <= ?M" unfolding returns .

  from \<open>0 <= loop__1__j\<close> have "0 <= loop__1__j + 1" by simp
  from \<open>loop__1__j <= 78\<close> have "loop__1__j + 1 <= 79" by simp

  have "loop__1__j + 1 + 1 = loop__1__j + 2" by simp

  note step_from_hyp[OF H1
    \<open>cla <= ?M\<close>
    \<open>clb <= ?M\<close>
    \<open>clc <= ?M\<close>
    \<open>cld <= ?M\<close>
    \<open>cle <= ?M\<close>
    \<open>cra <= ?M\<close>
    \<open>crb <= ?M\<close>
    \<open>crc <= ?M\<close>
    \<open>crd <= ?M\<close>
    \<open>cre <= ?M\<close>

    \<open>0 <= cla\<close>
    \<open>0 <= clb\<close>
    \<open>0 <= clc\<close>
    \<open>0 <= cld\<close>
    \<open>0 <= cle\<close>
    \<open>0 <= cra\<close>
    \<open>0 <= crb\<close>
    \<open>0 <= crc\<close>
    \<open>0 <= crd\<close>
    \<open>0 <= cre\<close>]
  from this[OF
    x_lower x_upper x_lower' x_upper'
    \<open>0 <= loop__1__j + 1\<close> \<open>loop__1__j + 1 <= 79\<close>]
    \<open>0 \<le> cla\<close> \<open>0 \<le> cle\<close> \<open>0 \<le> cra\<close> \<open>0 \<le> cre\<close> x_lower x_lower'
  show ?thesis unfolding \<open>loop__1__j + 1 + 1 = loop__1__j + 2\<close>
    unfolding returns(1) returns(2) unfolding returns
    by (simp del: mod_pos_pos_trivial mod_neg_neg_trivial)

qed

spark_vc procedure_round_76
proof -
  let ?M = "4294967295 :: int"
  let ?INIT_CHAIN =
     "\<lparr>h0 = ca_init, h1 = cb_init,
         h2 = cc_init, h3 = cd_init,
         h4 = ce_init\<rparr>"
  have steps_to_steps':
    "steps
       (\<lambda>n::nat. word_of_int (x (int n)))
       (from_chain ?INIT_CHAIN, from_chain ?INIT_CHAIN)
       80 =
    from_chain_pair (
      steps'
      (\<lparr>left = ?INIT_CHAIN, right = ?INIT_CHAIN\<rparr>)
      80
      x)"
    unfolding from_to_id by simp
  from
    \<open>0 \<le> ca_init\<close> \<open>ca_init \<le> ?M\<close>
    \<open>0 \<le> cb_init\<close> \<open>cb_init \<le> ?M\<close>
    \<open>0 \<le> cc_init\<close> \<open>cc_init \<le> ?M\<close>
    \<open>0 \<le> cd_init\<close> \<open>cd_init \<le> ?M\<close>
    \<open>0 \<le> ce_init\<close> \<open>ce_init \<le> ?M\<close>
    \<open>0 \<le> cla\<close> \<open>cla \<le> ?M\<close>
    \<open>0 \<le> clb\<close> \<open>clb \<le> ?M\<close>
    \<open>0 \<le> clc\<close> \<open>clc \<le> ?M\<close>
    \<open>0 \<le> cld\<close> \<open>cld \<le> ?M\<close>
    \<open>0 \<le> cle\<close> \<open>cle \<le> ?M\<close>
    \<open>0 \<le> cra\<close> \<open>cra \<le> ?M\<close>
    \<open>0 \<le> crb\<close> \<open>crb \<le> ?M\<close>
    \<open>0 \<le> crc\<close> \<open>crc \<le> ?M\<close>
    \<open>0 \<le> crd\<close> \<open>crd \<le> ?M\<close>
    \<open>0 \<le> cre\<close> \<open>cre \<le> ?M\<close>
  show ?thesis
    unfolding round_def
    unfolding steps_to_steps'
    unfolding H1[symmetric]
    by (simp add: uint_word_ariths(1) mod_simps
      uint_word_of_int_id take_bit_int_eq_self)
qed

spark_end

end


theory Validity
imports LLEarleyParsing Derivations
begin

context LocalLexing begin

definition wellformed_token :: "('a, 'b, 'c) token \<Rightarrow> bool"
where
  "wellformed_token t = is_terminal (terminal_of_token t)"

definition wellformed_tokens :: "('a, 'b, 'c) tokens \<Rightarrow> bool"
where
  "wellformed_tokens ts = list_all wellformed_token ts"

definition doc_tokens :: "('a, 'b, 'c) tokens \<Rightarrow> bool"
where
  "doc_tokens p = (wellformed_tokens p \<and> is_prefix (chars p) Doc)"

definition wellformed_item :: "('a, 'b) item \<Rightarrow> bool"
where
  "wellformed_item x = (
    item_rule x \<in> \<RR> \<and>
    item_origin x \<le> item_end x \<and>
    item_end x \<le> length Doc \<and>
    item_dot x \<le> length (item_rhs x))"

definition wellformed_items :: "('a, 'b)items \<Rightarrow> bool"
where
  "wellformed_items X = (\<forall> x \<in> X. wellformed_item x)"

lemma is_word_terminals: "wellformed_tokens p \<Longrightarrow> is_word (terminals p)"
by (simp add: is_word_def list_all_length terminals_def wellformed_token_def wellformed_tokens_def)

lemma is_word_subset: "is_word x \<Longrightarrow> set y \<subseteq> set x \<Longrightarrow> is_word y"
by (metis (mono_tags, hide_lams) in_set_conv_nth is_word_def list_all_length subsetCE)

lemma is_word_terminals_take: "wellformed_tokens p \<Longrightarrow> is_word(terminals (take n p))"
by (metis append_take_drop_id is_word_terminals list_all_append wellformed_tokens_def)

lemma is_word_terminals_drop: "wellformed_tokens p \<Longrightarrow> is_word(terminals (drop n p))"
by (metis append_take_drop_id is_word_terminals list_all_append wellformed_tokens_def)

(*list of tokens, valid with regard to an item*)
definition pvalid :: "('a, 'b, 'c) tokens \<Rightarrow> ('a, 'b) item \<Rightarrow> bool"
where
  "pvalid p x = (\<exists> u \<gamma>.
     wellformed_tokens p \<and>
     wellformed_item x \<and>
     u \<le> length p \<and>
     charslength p = item_end x \<and>
     charslength (take u p) = item_origin x \<and>
     is_derivation (terminals (take u p) @ [item_nonterminal x] @ \<gamma>) \<and>
     derives (item_\<alpha> x) (terminals (drop u p)))"

definition Gen :: "('a, 'b, 'c) tokens set \<Rightarrow> ('a, 'b) items"
where
  "Gen P = { x | x p. p \<in> P \<and> pvalid p x }"

lemma "wellformed_items (Gen P)"
  by (auto simp add: Gen_def pvalid_def wellformed_items_def)

lemma "wellformed_items (Init)"
  by (auto simp add: wellformed_items_def Init_def init_item_def wellformed_item_def)

definition pvalid_left :: "('a, 'b, 'c) tokens \<Rightarrow> ('a, 'b)item \<Rightarrow> bool"
where
  "pvalid_left p x = (\<exists> u \<gamma>.
     wellformed_tokens p \<and>
     wellformed_item x \<and>
     u \<le> length p \<and>
     charslength p = item_end x \<and>
     charslength (take u p) = item_origin x \<and>
     is_leftderivation (terminals (take u p) @ [item_nonterminal x] @ \<gamma>) \<and>
     leftderives (item_\<alpha> x) (terminals (drop u p)))"

lemma pvalid_left: "pvalid p x = pvalid_left p x"
proof -
  have right_imp_left: "pvalid_left p x \<Longrightarrow> pvalid p x"
    by (meson CFG.leftderives_implies_derives CFG_axioms LocalLexing.pvalid_def
        LocalLexing.pvalid_left_def LocalLexing_axioms leftderivation_implies_derivation)
  have left_imp_right: "pvalid p x \<Longrightarrow> pvalid_left p x"
  proof -
    assume "pvalid p x"
    then obtain u \<gamma> where
      "wellformed_tokens p \<and>
       wellformed_item x \<and>
       u \<le> length p \<and>
       charslength p = item_end x \<and>
       charslength (take u p) = item_origin x \<and>
       is_derivation (terminals (take u p) @ [item_nonterminal x] @ \<gamma>) \<and>
       derives (item_\<alpha> x) (terminals (drop u p))" by (simp add: pvalid_def, blast)
    thus ?thesis
      apply (auto simp add: pvalid_left_def)
      apply (rule_tac x=u in exI)
      apply auto
      apply (simp add: is_leftderivation_def)
      apply (rule_tac derives_implies_leftderives_cons[where b=\<gamma>])
      apply (erule is_word_terminals_take)
      apply (simp add: is_derivation_def)
      by (metis derives_implies_leftderives is_word_terminals_drop)
  qed
  show ?thesis by (metis left_imp_right right_imp_left)
qed

lemma \<L>\<^sub>P_wellformed_tokens: "terminals p \<in> \<L>\<^sub>P \<Longrightarrow> wellformed_tokens p"
by (metis (mono_tags, lifting) \<L>\<^sub>P_is_word is_word_def length_map list_all_length
    nth_map terminals_def wellformed_token_def wellformed_tokens_def)

end

end


           (*-------------------------------------------*
            |        CSP-Prover on Isabelle2004         |
            |                  April 2006               |
            |                  March 2007  (modified)   |
            |                October 2009  (modified)   |
            |                                           |
            |        Yoshinao Isobe (AIST JAPAN)        |
            *-------------------------------------------*)

theory CSP_T_law_etc
imports CSP_T_law_aux
begin

(*------------------------*
         |~| --> !!
 *------------------------*)

lemma cspT_Int_choice_to_Rep:
  "(P |~| Q) =T[M,M] (!nat n:{0, (Suc 0)} .. (IF (n = 0) THEN P ELSE Q))"
apply (rule cspT_rw_right)
apply (subgoal_tac
 "(!nat n:{0, (Suc 0)} .. IF (n = 0) THEN P ELSE Q) =T[M,M]
  (!nat n:({0} Un {(Suc 0)}) .. IF (n = 0) THEN P ELSE Q)")
apply (assumption)
apply (rule cspT_decompo)
apply (fast)
apply (simp)
apply (rule cspT_rw_right)
apply (rule cspT_Rep_int_choice_union_Int)
apply (rule cspT_decompo)

apply (rule cspT_rw_right)
apply (rule cspT_Rep_int_choice_singleton)
apply (simp)
apply (rule cspT_rw_right)
apply (rule cspT_IF)
apply (simp)

apply (rule cspT_rw_right)
apply (rule cspT_Rep_int_choice_singleton)
apply (simp)
apply (rule cspT_rw_right)
apply (rule cspT_IF)
apply (simp)
done

(*** cspT_Rep_int_choice_set_input ***)

lemma cspT_Rep_int_choice_sum_set_input:
  "!! c:C .. (!set X:(Xsf c) .. (? :X -> (Pff c)))
   =T[M,M] !set X:(Union {(Xsf c) |c. c : sumset C}) ..
          (? a:X -> (!! c:{c:C. EX X. X:(Xsf c) & a:X}s .. (Pff c a)))"
apply (simp add: cspT_semantics)
apply (rule order_antisym)

(* <= *)
 apply (rule)
 apply (simp add: in_traces)
 apply (elim conjE exE bexE disjE)
 apply (simp_all)
  apply (force)

(* => *)
 apply (rule)
 apply (simp add: in_traces)
 apply (elim conjE exE bexE disjE)
 apply (simp_all)
  apply (rule_tac x="c" in bexI)
  apply (force)
  apply (simp)

  apply (simp)
  apply (rule_tac x="ca" in bexI)
  apply (simp)
  apply (simp)
  apply (fast)
  apply (simp)
done

(*** cspT_Rep_int_choice_set_input ***)

lemma cspT_Rep_int_choice_set_input:
  "!nat n:N .. (!set X:(Xsf n) .. (? :X -> (Pff n)))
   =T[M,M] !set X:(Union {(Xsf n) |n. n : N}) ..
          (? a:X -> (!nat n:{n:N. EX X. X:(Xsf n) & a:X} .. (Pff n a)))"
apply (simp add: Rep_int_choice_nat_def)
apply (rule cspT_rw_left)
apply (rule cspT_Rep_int_choice_sum_set_input)
apply (rule cspT_decompo)
apply (force)
apply (simp)
done

(*** cspT_Rep_int_choice_set_set_DIV ***)

lemma cspT_Rep_int_choice_set_set_DIV:
  "[| Xs ~= {} ; Ys ~= {} |] ==>
   !set X:Xs .. (!set Y:Ys .. (? a:(X Un Y) -> DIV))
   =T[M,M] !set Z:{X Un Y |X Y. X:Xs & Y:Ys} .. (? a:Z -> DIV)"
apply (simp add: cspT_semantics)
apply (rule order_antisym)

(* <= *)
 apply (rule)
 apply (simp add: in_traces)
 apply (elim conjE exE bexE disjE)
 apply (simp_all)
  apply (rule_tac x="X Un Xa" in exI)
  apply (simp)
  apply (rule_tac x="X" in exI)
  apply (rule_tac x="Xa" in exI)
  apply (simp)
  apply (rule_tac x="X Un Xa" in exI)
  apply (simp)
  apply (rule_tac x="X" in exI)
  apply (rule_tac x="Xa" in exI)
  apply (simp)

(* => *)
 apply (rule)
 apply (simp add: in_traces)
 apply (elim conjE exE bexE disjE)
 apply (simp_all)
 apply (force)
done

(*********************************************************
               (P [+] SKIP) |~| (Q [+] SKIP)
 *********************************************************)

(* p.289 *)

lemma cspT_Int_choice_Ext_choice_SKIP:
  "(P [+] SKIP) |~| (Q [+] SKIP) =T[M,M] (P [+] Q [+] SKIP)"
apply (simp add: cspT_semantics)
apply (rule order_antisym)

(* => *)
 apply (rule, simp add: in_traces)
 apply (force)

(* <= *)
 apply (rule, simp add: in_traces)
 apply (force)
done

(*********************************************************
               (P [+] DIV) |~| (Q [+] DIV)
 *********************************************************)

lemma cspT_Int_choice_Ext_choice_DIV:
  "(P [+] DIV) |~| (Q [+] DIV) =T[M,M] (P [+] Q [+] DIV)"
apply (simp add: cspT_semantics)
apply (rule order_antisym)

(* => *)
 apply (rule, simp add: in_traces)
 apply (force)

(* <= *)
 apply (rule, simp add: in_traces)
 apply (force)
done

(*********************************************************
             (P [+] SKIP) |~| (Q [+] DIV)
 *********************************************************)

lemma cspT_Int_choice_Ext_choice_SKIP_DIV:
  "(P [+] SKIP) |~| (Q [+] DIV) =T[M,M] (P [+] Q [+] SKIP)"
apply (simp add: cspT_semantics)
apply (rule order_antisym)
apply (rule, simp add: in_traces, force)+
done

(*********************************************************
             (P [+] DIV) |~| (Q [+] SKIP)
 *********************************************************)

lemma cspT_Int_choice_Ext_choice_DIV_SKIP:
  "(P [+] DIV) |~| (Q [+] SKIP) =T[M,M] (P [+] Q [+] SKIP)"
apply (simp add: cspT_semantics)
apply (rule order_antisym)
apply (rule, simp add: in_traces, force)+
done

(*********************************************************
         (P [+] SKIP or DIV) |~| (Q [+] DIV or SKIP)
 *********************************************************)

lemma cspT_Int_choice_Ext_choice_SKIP_or_DIV:
  "[| P2 = SKIP | P2 = DIV ; Q2 = SKIP | Q2 = DIV |] ==>
   (P1 [+] P2) |~| (Q1 [+] Q2) =T[M,M] (P1 [+] Q1 [+] (P2 |~| Q2))"
apply (elim disjE)
apply (simp)
apply (rule cspT_rw_right)
apply (rule cspT_decompo)
apply (rule cspT_reflex)
apply (rule cspT_idem)
apply (simp add: cspT_Int_choice_Ext_choice_SKIP)

apply (simp)
apply (rule cspT_rw_right)
apply (rule cspT_decompo)
apply (rule cspT_reflex)
apply (rule cspT_unit)
apply (simp add: cspT_Int_choice_Ext_choice_SKIP_DIV)

apply (simp)
apply (rule cspT_rw_right)
apply (rule cspT_decompo)
apply (rule cspT_reflex)
apply (rule cspT_unit)
apply (simp add: cspT_Int_choice_Ext_choice_DIV_SKIP)

apply (simp)
apply (rule cspT_rw_right)
apply (rule cspT_decompo)
apply (rule cspT_reflex)
apply (rule cspT_unit)
apply (simp add: cspT_Int_choice_Ext_choice_DIV)
done

(*********************************************************
                    (P [+] DIV) |~| P
 *********************************************************)

lemma cspT_Ext_choice_DIV_Int_choice_Id:
  "(P [+] DIV) |~| P =T[M,M] P"
apply (simp add: cspT_semantics)
apply (rule order_antisym)
 apply (rule, simp add: in_traces)
 apply (force)
 apply (rule, simp add: in_traces)
done

(* =================================================== *
 |             addition for CSP-Prover 5               |
 |                    (renaming)                       |
 * =================================================== *)

lemma cspT_Ext_pre_choice_Renaming_fun_step:
  "(? x:X -> Pf x)[[<rel> f]] =T[M,M]
   (? y:(f ` X) -> (! x:{x:X. y = f x} .. (Pf x[[<rel> f]])))"
apply (rule cspT_rw_left)
apply (rule cspT_step)

apply (rule cspT_decompo)
apply (simp add: fun_to_rel_def)
apply (force)

apply (rule cspT_decompo)
apply (simp add: fun_to_rel_def)
apply (force)
done

(* Act prefix event *)

lemma cspT_Act_prefix_Renaming_fun_step:
  "(a -> P)[[<rel> f]] =T[M,M] f(a) -> P[[<rel> f]]"
apply (rule cspT_rw_left)
apply (rule cspT_decompo)
apply (simp)
apply (rule cspT_step)

apply (rule cspT_rw_left)
apply (rule cspT_Ext_pre_choice_Renaming_fun_step)

apply (rule cspT_rw_right)
apply (rule cspT_step)

apply (rule cspT_decompo)
apply (simp)

apply (simp)
apply (subgoal_tac
  "{x. x = a & f a = f x}={a}")
apply (simp)
apply (rule cspT_rw_left)
apply (rule cspT_Rep_int_choice_const_com_rule)
apply (auto)
apply (rule cspT_rw_left)
apply (rule cspT_IF_split)
apply (auto)
done

lemmas cspT_Renaming_fun_step
     = cspT_Ext_pre_choice_Renaming_fun_step
       cspT_Act_prefix_Renaming_fun_step

(* -------- event -------- *)

lemma cspT_Act_prefix_Renaming1_event1_step_in:
  "(a -> P)[[a<-->b]] =T[M,M] b -> P[[a<-->b]]"
apply (simp add: Renaming_event_def Renaming_event_fun_def)
by (rule cspT_rw_left, rule cspT_Act_prefix_Renaming_fun_step, auto)

lemma cspT_Act_prefix_Renaming1_event2_step_in:
  "(a -> P)[[b<-->a]] =T[M,M] b -> P[[b<-->a]]"
by (simp add: cspT_Act_prefix_Renaming1_event1_step_in Renaming_commut)

lemma cspT_Act_prefix_Renaming1_event_step_notin:
  "[| a ~= c ; b ~= c |] ==> (c -> P)[[a<-->b]] =T[M,M] c -> P[[a<-->b]]"
apply (simp add: Renaming_event_def Renaming_event_fun_def)
by (rule cspT_rw_left, rule cspT_Act_prefix_Renaming_fun_step, auto)

lemmas cspT_Act_prefix_Renaming1_event_step =
       cspT_Act_prefix_Renaming1_event1_step_in
       cspT_Act_prefix_Renaming1_event2_step_in
       cspT_Act_prefix_Renaming1_event_step_notin

lemma cspT_Act_prefix_Renaming2_set_event_step_in:
  "a:A ==> (a -> P)[[A<<-b]] =T[M,M] b -> P[[A<<-b]]"
apply (simp add: Renaming_event_def Renaming_event_fun_def)
by (rule cspT_rw_left, rule cspT_Act_prefix_Renaming_fun_step, auto)

lemma cspT_Act_prefix_Renaming2_set_event_step_notin:
  "c~:A ==> (c -> P)[[A<<-b]] =T[M,M] c -> P[[A<<-b]]"
apply (simp add: Renaming_event_def Renaming_event_fun_def)
by (rule cspT_rw_left, rule cspT_Act_prefix_Renaming_fun_step, auto)

lemma cspT_Act_prefix_Renaming2_set_event_step:
  "(a -> P)[[A<<-b]] =T[M,M]
   IF (a:A) THEN (b -> P[[A<<-b]])
            ELSE (a -> P[[A<<-b]])"
apply (case_tac "a:A")
apply (rule cspT_rw_left)
apply (rule cspT_Act_prefix_Renaming2_set_event_step_in)
apply (simp)
apply (rule cspT_rw_right)
apply (rule cspT_IF_split)
apply (simp)
apply (rule cspT_rw_left)
apply (rule cspT_Act_prefix_Renaming2_set_event_step_notin)
apply (simp)
apply (rule cspT_rw_right)
apply (rule cspT_IF_split)
apply (simp)
done

lemmas cspT_Act_prefix_Renaming2_set_event_steps =
       cspT_Act_prefix_Renaming2_set_event_step_in
       cspT_Act_prefix_Renaming2_set_event_step_notin

(* sinlge *)

lemma cspT_Act_prefix_Renaming2_event_step_in:
  "(a -> P)[[a<--b]] =T[M,M] b -> P[[a<--b]]"
by (simp add: cspT_Act_prefix_Renaming2_set_event_step_in)

lemma cspT_Act_prefix_Renaming2_event_step_notin:
  "c~=a ==> (c -> P)[[a<--b]] =T[M,M] c -> P[[a<--b]]"
by (simp add: cspT_Act_prefix_Renaming2_set_event_step_notin)

lemmas cspT_Act_prefix_Renaming2_event_step =
       cspT_Act_prefix_Renaming2_event_step_in
       cspT_Act_prefix_Renaming2_event_step_notin

lemmas cspT_Act_prefix_Renaming_event_step =
       cspT_Act_prefix_Renaming1_event_step
       cspT_Act_prefix_Renaming2_event_step

(* -------- channel -------- *)

(* Act prefix channel *)

lemma cspT_Act_prefix_Renaming1_channel1_step_in:
  "[| inj f ; ALL x y. f x ~= g y |]
   ==> (f v -> P)[[f<==>g]] =T[M,M] g v -> P[[f<==>g]]"
apply (simp add: Renaming_channel_fun_def Renaming_channel_def)
by (rule cspT_rw_left, rule cspT_Act_prefix_Renaming_fun_step, auto)

lemma cspT_Act_prefix_Renaming1_channel2_step_in:
  "[| inj f ; ALL x y. f x ~= g y |]
   ==> (f v -> P)[[g<==>f]] =T[M,M] g v -> P[[g<==>f]]"
by (simp add: Renaming_commut cspT_Act_prefix_Renaming1_channel1_step_in)

lemma cspT_Act_prefix_Renaming1_channel_step_notin:
  "[| (ALL x. a ~= f x) | a ~: range f ;
      (ALL x. a ~= g x) | a ~: range g |]
   ==> (a -> P)[[f<==>g]] =T[M,M] a -> P[[f<==>g]]"
apply (simp add: Renaming_channel_fun_def Renaming_channel_def)
by (rule cspT_rw_left, rule cspT_Act_prefix_Renaming_fun_step, auto)

lemmas cspT_Act_prefix_Renaming1_channel_step =
       cspT_Act_prefix_Renaming1_channel1_step_in
       cspT_Act_prefix_Renaming1_channel2_step_in
       cspT_Act_prefix_Renaming1_channel_step_notin

lemma cspT_Act_prefix_Renaming2_channel_step_in:
  "[| inj f ; ALL x y. f x ~= g y |]
   ==> (f v -> P)[[f<==g]] =T[M,M] g v -> P[[f<==g]]"
apply (simp add: Renaming_channel_fun_def Renaming_channel_def)
by (rule cspT_rw_left, rule cspT_Act_prefix_Renaming_fun_step, auto)

lemma cspT_Act_prefix_Renaming2_channel_step_notin:
  "[| (ALL x. a ~= f x) | a ~: range f |]
   ==> (a -> P)[[f<==g]] =T[M,M] a -> P[[f<==g]]"
apply (simp add: Renaming_channel_fun_def Renaming_channel_def)
by (rule cspT_rw_left, rule cspT_Act_prefix_Renaming_fun_step, auto)

lemmas cspT_Act_prefix_Renaming2_channel_step =
       cspT_Act_prefix_Renaming2_channel_step_in
       cspT_Act_prefix_Renaming2_channel_step_notin

lemmas cspT_Act_prefix_Renaming_channel_step =
       cspT_Act_prefix_Renaming1_channel_step
       cspT_Act_prefix_Renaming2_channel_step

(* -------*)

lemmas cspT_Act_prefix_Renaming_step =
       cspT_Act_prefix_Renaming_fun_step
       cspT_Act_prefix_Renaming_event_step
       cspT_Act_prefix_Renaming_channel_step

(* --- Ext_pre_choice_Renaming_even --- *)

(* <--> *)

lemma cspT_Ext_pre_choice_Renaming1_event1_step:
  "a ~= b ==>
     (? x:X -> Pf x)[[a<-->b]] =T[M,M]
     (IF (a:X) THEN (b -> (Pf a)[[a<-->b]]) ELSE STOP) [+]
     (IF (b:X) THEN (a -> (Pf b)[[a<-->b]]) ELSE STOP) [+]
      (? x:(X - {a,b}) -> (Pf x)[[a<-->b]])"
apply (rule cspT_rw_left)
apply (simp add: Renaming_event_def)
apply (rule cspT_Renaming_fun_step)
apply (fold Renaming_event_def)

apply (case_tac "a:X")
 apply (case_tac "b:X")
  apply (simp)
  apply (rule cspT_rw_right)
  apply (rule cspT_decompo)
  apply (rule cspT_decompo)
  apply (rule cspT_IF_split)
  apply (rule cspT_IF_split)
  apply (rule cspT_reflex)
  apply (simp)

  apply (rule cspT_rw_right)
  apply (rule cspT_decompo)
  apply (rule cspT_decompo)
  apply (rule cspT_step)
  apply (rule cspT_step)
  apply (rule cspT_reflex)

  apply (rule cspT_rw_right)
  apply (rule cspT_decompo)
  apply (rule cspT_step)
  apply (rule cspT_reflex)

  apply (rule cspT_rw_right)
  apply (rule cspT_step)
  apply (simp)

  apply (rule cspT_decompo)
  apply (simp add: image_def Renaming_event_fun_def)
  apply (force)

  apply (simp)

   apply (case_tac "aa = a")
   apply (simp)
   apply ((rule cspT_rw_right, rule cspT_IF_split | rule cspT_decompo)| simp)+
   apply (simp add: image_def Renaming_event_fun_def)
   apply (rule cspT_rw_left)
   apply (rule cspT_Rep_int_choice_singleton)
   apply (simp)

   apply (case_tac "aa = b")
   apply (simp)
   apply ((rule cspT_rw_right, rule cspT_IF_split | rule cspT_decompo)| simp)+
   apply (simp add: image_def Renaming_event_fun_def)
   apply (subgoal_tac "{x. x ~= b & (x ~= b --> x = a)}={a}")
   apply (simp)
   apply (rule cspT_Rep_int_choice_singleton)
   apply (force)

   (* etc *)
   apply (simp)
   apply ((rule cspT_rw_right, rule cspT_IF_split | rule cspT_decompo)| simp)+
   apply (simp add: image_def Renaming_event_fun_def)
   apply (subgoal_tac
     "{x. x ~= b & (x ~= b --> x ~= a & (x ~= a --> x : X & aa = x))}={aa}")
   apply (simp)
   apply (rule cspT_Rep_int_choice_singleton)
   apply (force)

 (* b~:X *)
  apply (simp)
  apply (rule cspT_rw_right)
  apply (rule cspT_decompo)
  apply (rule cspT_decompo)
  apply (rule cspT_IF_split)
  apply (rule cspT_IF_split)
  apply (rule cspT_reflex)
  apply (simp)

  apply (rule cspT_rw_right)
  apply (rule cspT_decompo)
  apply (rule cspT_decompo)
  apply (rule cspT_step)
  apply (rule cspT_step)
  apply (rule cspT_reflex)

  apply (rule cspT_rw_right)
  apply (rule cspT_decompo)
  apply (rule cspT_step)
  apply (rule cspT_reflex)
  apply (simp)

  apply (rule cspT_rw_right)
  apply (rule cspT_step)
  apply (simp)

  apply (rule cspT_decompo)
  apply (simp add: image_def Renaming_event_fun_def)
  apply (force)

  apply (simp)

   apply (case_tac "aa = b")
   apply (simp)
   apply ((rule cspT_rw_right, rule cspT_IF_split | rule cspT_decompo)| simp)+
   apply (simp add: image_def Renaming_event_fun_def)
   apply (subgoal_tac "{x. x ~= b & (x ~= b --> x = a)}={a}")
   apply (simp)
   apply (rule cspT_Rep_int_choice_singleton)
   apply (force)

   apply (simp)
   apply ((rule cspT_rw_right, rule cspT_IF_split | rule cspT_decompo)| simp)+
   apply (simp add: image_def Renaming_event_fun_def)
   apply (subgoal_tac
   "{x. x ~= b & (x ~= b --> x ~= a & (x ~= a --> x : X & aa = x))} = {aa}")
   apply (simp)
   apply (rule cspT_Rep_int_choice_singleton)
   apply (force)

(* a~:X *)
 apply (case_tac "b:X")

  apply (simp)
  apply (rule cspT_rw_right)
  apply (rule cspT_decompo)
  apply (rule cspT_decompo)
  apply (rule cspT_IF_split)
  apply (rule cspT_IF_split)
  apply (rule cspT_reflex)
  apply (simp)

  apply (rule cspT_rw_right)
  apply (rule cspT_decompo)
  apply (rule cspT_decompo)
  apply (rule cspT_step)
  apply (rule cspT_step)
  apply (rule cspT_reflex)

  apply (rule cspT_rw_right)
  apply (rule cspT_decompo)
  apply (rule cspT_step)
  apply (rule cspT_reflex)
  apply (simp)

  apply (rule cspT_rw_right)
  apply (rule cspT_step)
  apply (simp)

  apply (rule cspT_decompo)
  apply (simp add: image_def Renaming_event_fun_def)
  apply (force)

  apply (simp)

   apply (case_tac "aa = a")
   apply (simp)
   apply ((rule cspT_rw_right, rule cspT_IF_split | rule cspT_decompo)| simp)+
   apply (simp add: image_def Renaming_event_fun_def)
   apply (rule cspT_Rep_int_choice_singleton)

   apply (simp)
   apply ((rule cspT_rw_right, rule cspT_IF_split | rule cspT_decompo)| simp)+
   apply (simp add: image_def Renaming_event_fun_def)
   apply (subgoal_tac
   "{x. x ~= b & (x ~= b --> x ~= a & (x ~= a --> x : X & aa = x))} = {aa}")
   apply (simp)
   apply (rule cspT_Rep_int_choice_singleton)
   apply (force)

 (* b~:X *)
  apply (simp)
  apply (rule cspT_rw_right)
  apply (rule cspT_decompo)
  apply (rule cspT_decompo)
  apply (rule cspT_IF_split)
  apply (rule cspT_IF_split)
  apply (rule cspT_reflex)
  apply (simp)

  apply (rule cspT_rw_right)
  apply (rule cspT_decompo)
  apply (rule cspT_decompo)
  apply (rule cspT_step)
  apply (rule cspT_step)
  apply (rule cspT_reflex)

  apply (rule cspT_rw_right)
  apply (rule cspT_decompo)
  apply (rule cspT_step)
  apply (rule cspT_reflex)
  apply (simp)

  apply (rule cspT_rw_right)
  apply (rule cspT_step)
  apply (simp)

  apply (rule cspT_decompo)
  apply (simp add: image_def Renaming_event_fun_def)
  apply (force)

   apply ((rule cspT_rw_right, rule cspT_IF_split | rule cspT_decompo)| simp)+
   apply (simp add: image_def Renaming_event_fun_def)
   apply (subgoal_tac
   "{x. x ~= b & (x ~= b --> x ~= a & (x ~= a --> x : X & aa = x))} = {aa}")
   apply (simp)
   apply (rule cspT_Rep_int_choice_singleton)
   apply (force)
done

lemma cspT_Ext_pre_choice_Renaming1_event2_step:
  "a = b ==>
     (? x:X -> Pf x)[[a<-->b]] =T[M,M]
     (IF (a:X) THEN (b -> (Pf a)[[a<-->b]]) ELSE STOP) [+]
     (IF (b:X) THEN (a -> (Pf b)[[a<-->b]]) ELSE STOP) [+]
      (? x:(X - {a,b}) -> (Pf x)[[a<-->b]])"
apply (simp)
apply (rule cspT_rw_left)
apply (simp add: Renaming_event_def)
apply (rule cspT_Renaming_fun_step)
apply (fold Renaming_event_def)

apply (rule cspT_rw_right)
apply (rule cspT_decompo)
apply (rule cspT_idem)
apply (rule cspT_reflex)

 apply (case_tac "b:X")
  apply (simp)
  apply (rule cspT_rw_right)
  apply (rule cspT_decompo)
  apply (rule cspT_IF_split)
  apply (rule cspT_reflex)
  apply (simp)

  apply (rule cspT_rw_right)
  apply (rule cspT_decompo)
  apply (rule cspT_step)
  apply (rule cspT_reflex)

  apply (rule cspT_rw_right)
  apply (rule cspT_step)
  apply (simp)

  apply (rule cspT_decompo)
  apply (simp add: image_def Renaming_event_fun_def)
  apply (force)

  apply (simp)

   apply (case_tac "aa = b")
   apply (simp)
   apply ((rule cspT_rw_right, rule cspT_IF_split | rule cspT_decompo)| simp)+
   apply (simp add: image_def Renaming_event_fun_def)
   apply (rule cspT_Rep_int_choice_singleton)

   apply (simp)
   apply ((rule cspT_rw_right, rule cspT_IF_split | rule cspT_decompo)| simp)+
   apply (simp add: image_def Renaming_event_fun_def)
   apply (subgoal_tac
     "{x. x ~= b & (x ~= b --> x ~= a & (x ~= a --> x : X & aa = x))}={aa}")
   apply (simp)
   apply (rule cspT_Rep_int_choice_singleton)
   apply (force)

 (* b~:X *)
  apply (simp)
  apply (rule cspT_rw_right)
  apply (rule cspT_decompo)
  apply (rule cspT_IF_split)
  apply (rule cspT_reflex)
  apply (simp)

  apply (rule cspT_rw_right)
  apply (rule cspT_decompo)
  apply (rule cspT_step)
  apply (rule cspT_reflex)

  apply (rule cspT_rw_right)
  apply (rule cspT_step)
  apply (simp)

  apply (rule cspT_decompo)
  apply (simp add: image_def Renaming_event_fun_def)
  apply (force)

   apply ((rule cspT_rw_right, rule cspT_IF_split | rule cspT_decompo)| simp)+
   apply (simp add: image_def Renaming_event_fun_def)
   apply (subgoal_tac
   "{x. x ~= b & (x ~= b --> x ~= a & (x ~= a --> x : X & aa = x))} = {aa}")
   apply (simp)
   apply (rule cspT_Rep_int_choice_singleton)
   apply (force)
done

lemma cspT_Ext_pre_choice_Renaming1_event_step:
  "(? x:X -> Pf x)[[a<-->b]] =T[M,M]
     (IF (a:X) THEN (b -> (Pf a)[[a<-->b]]) ELSE STOP) [+]
     (IF (b:X) THEN (a -> (Pf b)[[a<-->b]]) ELSE STOP) [+]
      (? x:(X - {a,b}) -> (Pf x)[[a<-->b]])"
apply (case_tac "a=b")
apply (rule cspT_Ext_pre_choice_Renaming1_event2_step)
apply (simp_all)
apply (rule cspT_Ext_pre_choice_Renaming1_event1_step)
apply (simp_all)
done

(* <<- *)

lemma cspT_Ext_pre_choice_Renaming2_set_event_step_in:
  "X Int A ~= {} ==>
     (? x:X -> Pf x)[[A<<-a]] =T[M,M]
      a -> (! x:(X Int A) .. (Pf x)[[A<<-a]])
     [+] ? x:(X-A) -> (Pf x)[[A<<-a]]"
apply (rule cspT_rw_left)
apply (simp add: Renaming_event_def)
apply (rule cspT_Renaming_fun_step)
apply (fold Renaming_event_def)
apply (simp add: image_def)

apply (rule cspT_rw_right)
apply (rule cspT_decompo)
apply (rule cspT_step)
apply (rule cspT_reflex)
apply (rule cspT_rw_right)
apply (rule cspT_step)

apply (rule cspT_decompo)
apply (simp add: Renaming_event_fun_def)
apply (blast)

apply (simp)

apply (case_tac "aa = a")
 apply (simp)
 apply (case_tac "a : X & a ~: A")
  apply (simp)
  apply (rule cspT_rw_right)
  apply (rule cspT_IF_split)
  apply (simp)
  apply (rule cspT_ref_eq)

  (* <= *)
  apply (rule cspT_Int_choice_right)
   apply (rule cspT_Rep_int_choice_right)
   apply (simp)
   apply (rule cspT_Rep_int_choice_left)
   apply (rule_tac x="aaa" in exI)
   apply (simp)
   apply (simp add: Renaming_event_fun_def)

   apply (rule cspT_Rep_int_choice_left)
   apply (rule_tac x="a" in exI)
   apply (simp)
   apply (simp add: Renaming_event_fun_def)

  (* => *)
   apply (rule cspT_Rep_int_choice_right)
   apply (simp)
   apply (elim conjE bexE)
   apply (simp add: Renaming_event_fun_def)
   apply (case_tac "aaa : A")

    apply (simp)
    apply (rule cspT_Int_choice_left1)
    apply (rule cspT_Rep_int_choice_left)
    apply (simp)
    apply (rule_tac x="aaa" in exI)
    apply (simp)

    apply (simp)
    apply (rule cspT_Int_choice_left2)
    apply (simp)

 (* ~(a : X & a ~: A) *)
  apply (simp (no_asm_simp))
  apply (rule cspT_rw_right)
  apply (rule cspT_IF_split)
  apply (simp)
  apply (rule cspT_rw_right)
  apply (rule cspT_IF_split)
  apply (simp)

  apply (rule cspT_decompo)
  apply (simp add: Renaming_event_fun_def)
  apply (fast)
  apply (simp)

(* aa ~= a *)
 apply (simp)
 apply (rule cspT_rw_right)
 apply (rule cspT_IF_split)
 apply (simp)
 apply (rule cspT_rw_right)
 apply (rule cspT_IF_split)
 apply (simp)
 apply (simp add: Renaming_event_fun_def)
 apply (subgoal_tac "{x. x ~: A & (x ~: A --> x : X & aa = x)}={aa}")
 apply (simp)
 apply (rule cspT_Rep_int_choice_singleton)
 apply (force)
done

lemma cspT_Ext_pre_choice_Renaming2_set_event_step_notin:
  "[| X Int A = {} |] ==>
     (? x:X -> Pf x)[[A<<-b]] =T[M,M] ? x:X -> (Pf x)[[A<<-b]]"
apply (simp add: Renaming_event_def)
apply (rule cspT_rw_left)
apply (rule cspT_Renaming_fun_step)
apply (fold Renaming_event_def)

apply (rule cspT_decompo)
apply (simp add: Image_def image_def)
apply (simp add: Renaming_event_fun_def)
apply (force)
apply (simp add: Renaming_event_fun_def)
apply (subgoal_tac
  "{x. (x : A --> x : X & a = b) & (x ~: A --> x : X & a = x)} = {a}")
apply (simp)
apply (rule cspT_Rep_int_choice_singleton)
apply (force)
done

lemma cspT_Ext_pre_choice_Renaming2_set_event_step:
  "(? x:X -> Pf x)[[A<<-a]] =T[M,M]
  IF (X Int A ~= {})
  THEN (a -> (! x:(X Int A) .. (Pf x)[[A<<-a]])
        [+] ? x:(X-A) -> (Pf x)[[A<<-a]])
  ELSE (? x:X -> (Pf x)[[A<<-a]])"
apply (case_tac "X Int A ~= {}")
apply (rule cspT_rw_left)
apply (rule cspT_Ext_pre_choice_Renaming2_set_event_step_in)
apply (simp)
apply (simp)
apply (rule cspT_rw_right)
apply (rule cspT_IF_split)
apply (simp)
apply (rule cspT_rw_left)
apply (rule cspT_Ext_pre_choice_Renaming2_set_event_step_notin)
apply (simp)
apply (rule cspT_rw_right)
apply (rule cspT_IF_split)
apply (simp)
done

(* <-- *)

lemma cspT_Ext_pre_choice_Renaming2_event_step:
  "(? x:X -> Pf x)[[a<--b]] =T[M,M]
  IF (a : X)
  THEN (b -> (Pf a)[[a<--b]]
        [+] ? x:(X-{a}) -> (Pf x)[[a<--b]])
  ELSE (? x:X -> (Pf x)[[a<--b]])"
apply (rule cspT_rw_left)
apply (rule cspT_Ext_pre_choice_Renaming2_set_event_step)
apply (case_tac "a:X")

 apply (rule cspT_decompo)
 apply (simp)
 apply (rule cspT_decompo)
 apply (rule cspT_decompo)
 apply (simp)
 apply (subgoal_tac "X Int {a} = {a}")
 apply (simp)
 apply (rule cspT_Rep_int_choice_singleton)
 apply (force)
 apply (simp)
 apply (simp)

 apply (simp)
 apply (rule cspT_rw_right)
 apply (rule cspT_IF_split)
 apply (simp)
 apply (rule cspT_rw_left)
 apply (rule cspT_IF_split)
 apply (simp)
done

lemmas cspT_Ext_pre_choice_Renaming_event_step =
       cspT_Ext_pre_choice_Renaming1_event_step
       cspT_Ext_pre_choice_Renaming2_set_event_step
       cspT_Ext_pre_choice_Renaming2_event_step

(* sending -- event -- *)

lemma cspT_Send_prefix_Renaming1_event1_step_in:
  "inj f ==> (f!v -> P)[[a<-->f v]] =T[M,M] a -> P[[a<-->f v]]"
apply (simp add: csp_prefix_ss_def)
apply (simp add: cspT_Act_prefix_Renaming_step)
done

lemma cspT_Send_prefix_Renaming1_event2_step_in:
  "inj f ==> (f!v -> P)[[f v<-->a]] =T[M,M] a -> P[[f v<-->a]]"
by (simp add: Renaming_commut cspT_Send_prefix_Renaming1_event1_step_in)

lemma cspT_Send_prefix_Renaming1_event_step_notin:
  "[| a ~= f v | f v ~= a ; b ~= f v | f v ~= b |]
   ==> (f!v -> P)[[a<-->b]] =T[M,M] f!v -> P[[a<-->b]]"
apply (simp add: csp_prefix_ss_def)
apply (simp add: cspT_Act_prefix_Renaming_step)
done

lemmas cspT_Send_prefix_Renaming1_event_step =
       cspT_Send_prefix_Renaming1_event1_step_in
       cspT_Send_prefix_Renaming1_event2_step_in
       cspT_Send_prefix_Renaming1_event_step_notin

(* <<- *)

lemma cspT_Send_prefix_Renaming2_set_event_step_in:
  "f v : A ==> (f!v -> P)[[A<<-a]] =T[M,M] a -> P[[A<<-a]]"
apply (simp add: csp_prefix_ss_def)
apply (simp add: cspT_Act_prefix_Renaming2_set_event_step_in)
done

lemma cspT_Send_prefix_Renaming2_set_event_step_notin:
  "f v ~: A
   ==> (f!v -> P)[[A<<-b]] =T[M,M] f!v -> P[[A<<-b]]"
apply (simp add: csp_prefix_ss_def)
apply (simp add: cspT_Act_prefix_Renaming2_set_event_step_notin)
done

lemma cspT_Send_prefix_Renaming2_set_event_step:
  "(f!v -> P)[[A<<-a]] =T[M,M]
   IF (f v : A) THEN (a -> P[[A<<-a]]) ELSE (f!v -> P[[A<<-a]])"
apply (case_tac "f v : A")
apply (rule cspT_rw_left)
apply (rule cspT_Send_prefix_Renaming2_set_event_step_in)
apply (simp)
apply (rule cspT_rw_right)
apply (rule cspT_IF_split)
apply (simp)
apply (rule cspT_rw_left)
apply (rule cspT_Send_prefix_Renaming2_set_event_step_notin)
apply (simp)
apply (rule cspT_rw_right)
apply (rule cspT_IF_split)
apply (simp)
done

(* <-- *)

lemma cspT_Send_prefix_Renaming2_event_step_in:
  "(f!v -> P)[[f v<--a]] =T[M,M] a -> P[[f v<--a]]"
by (simp add: cspT_Send_prefix_Renaming2_set_event_step_in)

lemma cspT_Send_prefix_Renaming2_event_step_notin:
  "[| a ~= f v | f v ~= a |]
   ==> (f!v -> P)[[a<--b]] =T[M,M] f!v -> P[[a<--b]]"
by (simp add: cspT_Send_prefix_Renaming2_set_event_step_notin)

lemmas cspT_Send_prefix_Renaming2_event_step =
       cspT_Send_prefix_Renaming2_event_step_in
       cspT_Send_prefix_Renaming2_event_step_notin

lemmas cspT_Send_prefix_Renaming_event_step =
       cspT_Send_prefix_Renaming1_event_step
       cspT_Send_prefix_Renaming2_event_step

(* sending -- channel -- *)

lemma cspT_Send_prefix_Renaming1_channel1_step_in:
  "[| inj f ; ALL x y. f x ~= g y |]
   ==> (f!v -> P)[[f<==>g]] =T[M,M] g!v -> P[[f<==>g]]"
apply (simp add: csp_prefix_ss_def)
apply (simp add: cspT_Act_prefix_Renaming_step)
done

lemma cspT_Send_prefix_Renaming1_channel2_step_in:
  "[| inj f ; ALL x y. f x ~= g y |]
   ==> (f!v -> P)[[g<==>f]] =T[M,M] g!v -> P[[g<==>f]]"
by (simp add: Renaming_commut cspT_Send_prefix_Renaming1_channel1_step_in)

lemma cspT_Send_prefix_Renaming1_channel_step_notin:
  "[| (ALL x. h v ~= f x) | h v ~: range f ;
      (ALL x. h v ~= g x) | h v ~: range g |]
    ==> (h!v -> P)[[f<==>g]] =T[M,M] h!v -> P[[f<==>g]]"
apply (simp add: csp_prefix_ss_def)
apply (simp add: cspT_Act_prefix_Renaming_step)
done

lemmas cspT_Send_prefix_Renaming1_channel_step =
       cspT_Send_prefix_Renaming1_channel1_step_in
       cspT_Send_prefix_Renaming1_channel2_step_in
       cspT_Send_prefix_Renaming1_channel_step_notin

lemma cspT_Send_prefix_Renaming2_channel_step_in:
  "[| inj f ; ALL x y. f x ~= g y |]
   ==> (f!v -> P)[[f<==g]] =T[M,M] g!v -> P[[f<==g]]"
apply (simp add: csp_prefix_ss_def)
apply (simp add: cspT_Act_prefix_Renaming_step)
done

lemma cspT_Send_prefix_Renaming2_channel_step_notin:
  "[| (ALL x. h v ~= f x) | h v ~: range f |]
    ==> (h!v -> P)[[f<==g]] =T[M,M] h!v -> P[[f<==g]]"
apply (simp add: csp_prefix_ss_def)
apply (simp add: cspT_Act_prefix_Renaming_step)
done

lemmas cspT_Send_prefix_Renaming2_channel_step =
       cspT_Send_prefix_Renaming2_channel_step_in
       cspT_Send_prefix_Renaming2_channel_step_notin

lemmas cspT_Send_prefix_Renaming_channel_step =
       cspT_Send_prefix_Renaming1_channel_step
       cspT_Send_prefix_Renaming2_channel_step

lemmas cspT_Send_prefix_Renaming_step =
       cspT_Send_prefix_Renaming_event_step
       cspT_Send_prefix_Renaming_channel_step

(* --- Rec_prefix_Renaming_even --- *)

(* <--> *)

lemma cspT_Rec_prefix_Renaming1_event1_step_in:
  "[| inj f ; v:X ; ALL x:X. a ~= f x |] ==>
     (f ? x:X -> Pf x)[[a<-->f v]] =T[M,M]
     (a -> (Pf v)[[a<-->f v]]) [+] f ? x:(X-{v}) -> (Pf x)[[a<-->f v]]"
apply (simp add: csp_prefix_ss_def)
apply (rule cspT_rw_left)
apply (simp add: Renaming_event_def)
apply (rule cspT_Renaming_fun_step)
apply (fold Renaming_event_def)

apply (rule cspT_rw_right)
apply (rule cspT_decompo)
apply (rule cspT_step)
apply (rule cspT_reflex)
apply (rule cspT_rw_right)
apply (rule cspT_step)

apply (rule cspT_decompo)
apply (simp add: inj_on_def)
apply (simp add: Image_def image_def)
apply (simp add: Renaming_event_fun_def)
apply (blast)

apply (simp)
apply (rule cspT_ref_eq)

(* <= *)
apply (case_tac "aa = a")

 (* aa = a *)
 apply (simp)
 apply (case_tac "a : f ` (X - {v})")
  apply (simp add: image_iff)

  (* a ~: f ` (X - {v})" *)
  apply (simp)
  apply (rule cspT_rw_right)
  apply (rule cspT_IF_split)
  apply (simp)
  apply (rule cspT_rw_right)
  apply (rule cspT_IF_split)
  apply (simp)
  apply (rule cspT_Rep_int_choice_left)
  apply (rule_tac x="f v" in exI)
  apply (simp add: Renaming_event_fun_def)

 (* aa ~= a *)
 apply (simp)

 apply (rule cspT_rw_right)
 apply (rule cspT_IF_split)
 apply (simp)
 apply (rule cspT_rw_right)
 apply (rule cspT_IF_split)
 apply (simp)

 apply (rule cspT_Rep_int_choice_left)
 apply (rule_tac x="aa" in exI)
 apply (simp)

 apply (simp add: image_iff)
 apply (erule bexE)
 apply (simp add: inj_on_def)
 apply (simp add: Renaming_event_fun_def)
 apply (force)

(* => *)
apply (simp add: Renaming_event_fun_def)
apply (case_tac "aa = a")

 (* aa = a *)
 apply (simp)
 apply (case_tac "a : f ` (X - {v})")

  apply (simp add: image_iff)

  (* a ~: f ` (X - {v})" *)
  apply (simp)
  apply (rule cspT_rw_left)
  apply (rule cspT_IF_split)
  apply (simp)
  apply (rule cspT_rw_left)
  apply (rule cspT_IF_split)
  apply (simp)
  apply (rule cspT_Rep_int_choice_right)
  apply (force)

 (* aa ~= a *)
 apply (simp)

 apply (rule cspT_rw_left)
 apply (rule cspT_IF_split)
 apply (simp)
 apply (rule cspT_rw_left)
 apply (rule cspT_IF_split)
 apply (simp)

 apply (rule cspT_Rep_int_choice_right)
 apply (auto)
done

lemma cspT_Rec_prefix_Renaming1_event2_step_in:
  "[| inj f ; v:X ; ALL x:X. a ~= f x |] ==>
     (f ? x:X -> Pf x)[[f v<-->a]] =T[M,M]
     (a -> (Pf v)[[f v<-->a]]) [+] f ? x:(X-{v}) -> (Pf x)[[f v<-->a]]"
apply (simp add: Renaming_commut)
apply (simp add: cspT_Rec_prefix_Renaming1_event1_step_in)
done

lemma cspT_Rec_prefix_Renaming1_event_step_notin:
  "[| (ALL x:X. a ~= f x) | a ~: f ` X ;
      (ALL x:X. b ~= f x) | b ~: f ` X |] ==>
     (f ? x:X -> Pf x)[[a<-->b]] =T[M,M] f ? x:X -> (Pf x)[[a<-->b]]"
apply (simp add: csp_prefix_ss_def)
apply (simp add: Renaming_event_def)
apply (rule cspT_rw_left)
apply (rule cspT_Renaming_fun_step)
apply (fold Renaming_event_def)

apply (rule cspT_decompo)
apply (simp add: Image_def image_def)
apply (simp add: Renaming_event_fun_def)
apply (force)
apply (subgoal_tac
  "{x : f ` X. aa = Renaming1_event_fun a b x} = {aa}")
apply (simp)
apply (rule cspT_Rep_int_choice_singleton)

apply (simp add: Renaming_event_fun_def)
apply (force)
done

lemmas cspT_Rec_prefix_Renaming1_event_step =
       cspT_Rec_prefix_Renaming1_event1_step_in
       cspT_Rec_prefix_Renaming1_event2_step_in
       cspT_Rec_prefix_Renaming1_event_step_notin

(* <<- *)

lemma cspT_Rec_prefix_Renaming2_set_event_step_in:
  "[| inj f ; EX x:X. f x : A |] ==>
     (f ? x:X -> Pf x)[[A<<-a]] =T[M,M]
      a -> (!<f> x:{x:X. f x : A} .. (Pf x)[[A<<-a]])
     [+] f ? x:(X-{x. f x : A}) -> (Pf x)[[A<<-a]]"
apply (simp add: csp_prefix_ss_def)
apply (rule cspT_rw_left)
apply (simp add: Renaming_event_def)
apply (rule cspT_Renaming_fun_step)
apply (fold Renaming_event_def)
apply (simp add: image_def)

apply (rule cspT_rw_right)
apply (rule cspT_decompo)
apply (rule cspT_step)
apply (rule cspT_reflex)
apply (rule cspT_rw_right)
apply (rule cspT_step)

apply (rule cspT_decompo)
apply (simp add: Renaming_event_fun_def)
apply (blast)

apply (simp)

apply (case_tac "aa = a")
 apply (simp)
 apply (case_tac "EX x:X - {x. f x : A}. a = f x")
  apply (simp add: image_iff)
  apply (rule cspT_rw_right)
  apply (rule cspT_IF_split)
  apply (elim conjE bexE)
  apply (simp)

  apply (rule cspT_ref_eq)

  (* <= *)
  apply (rule cspT_Int_choice_right)
   apply (rule cspT_Rep_int_choice_right)
   apply (simp)
   apply (simp)
   apply (rule cspT_Rep_int_choice_left)
   apply (rule_tac x="f aaa" in exI)
   apply (simp)
   apply (simp add: Renaming_event_fun_def)
   apply (fast)

   apply (rule cspT_Rep_int_choice_left)
   apply (rule_tac x="a" in exI)
   apply (simp)
   apply (rule conjI)
    apply (blast)
   apply (simp add: Renaming_event_fun_def)

  (* => *)
   apply (rule cspT_Rep_int_choice_right)
   apply (simp)
   apply (elim conjE bexE)
   apply (simp add: Renaming_event_fun_def)
   apply (case_tac "f xb : A")

    apply (simp)
    apply (rule cspT_Int_choice_left1)
    apply (rule cspT_Rep_int_choice_left)
    apply (simp)
    apply (rule_tac x="xb" in exI)
    apply (simp)

    apply (simp)
    apply (rule cspT_Int_choice_left2)
    apply (simp add: inj_on_def)
    apply (force)

 (* ~(EX x:X - {x. f x : A}. a = f x) *)
  apply (simp)
  apply (rule cspT_rw_right)
  apply (rule cspT_IF_split)
  apply (simp)
  apply (rule cspT_rw_right)
  apply (rule cspT_IF_split)
  apply (simp)

  apply (rule cspT_ref_eq)

  (* <= *)
   apply (rule cspT_Rep_int_choice_right)
   apply (simp)
   apply (simp)
   apply (rule cspT_Rep_int_choice_left)
   apply (rule_tac x="f aaa" in exI)
   apply (simp)
   apply (simp add: Renaming_event_fun_def)
   apply (fast)

  (* => *)
   apply (rule cspT_Rep_int_choice_right)
   apply (simp)
   apply (rule cspT_Rep_int_choice_left)
   apply (simp)
   apply (elim conjE bexE)
   apply (simp add: Renaming_event_fun_def)
   apply (case_tac "f xa : A")

    apply (simp)
    apply (rule_tac x="xa" in exI)
    apply (simp)
    apply (simp)

 (* aa ~= a *)
 apply (simp)

 apply (rule cspT_rw_right)
 apply (rule cspT_IF_split)
 apply (simp)
 apply (rule cspT_rw_right)
 apply (rule cspT_IF_split)
 apply (simp)
 apply (rule cspT_ref_eq)

  (* => *)
  apply (rule cspT_Rep_int_choice_left)
  apply (rule_tac x="aa" in exI)
  apply (simp)
  apply (erule bexE)
  apply (simp add: inj_on_def)
  apply (simp add: Renaming_event_fun_def)
  apply (force)

 (* <= *)
  apply (rule cspT_Rep_int_choice_right)
  apply (simp)
  apply (elim conjE bexE)
  apply (simp add: Renaming_event_fun_def)
   apply (case_tac "f xb : A")
   apply (simp)
   apply (simp add: inj_on_def)
   apply (force)
done

lemma cspT_Rec_prefix_Renaming2_set_event_step_notin:
  "[| (ALL x:X. f x ~: A) | A Int f ` X = {} |] ==>
     (f ? x:X -> Pf x)[[A<<-b]] =T[M,M] f ? x:X -> (Pf x)[[A<<-b]]"
apply (simp add: csp_prefix_ss_def)
apply (simp add: Renaming_event_def)
apply (rule cspT_rw_left)
apply (rule cspT_Renaming_fun_step)
apply (fold Renaming_event_def)

apply (rule cspT_decompo)
apply (simp add: Image_def image_def)
apply (simp add: Renaming_event_fun_def)
apply (force)
apply (subgoal_tac
  "{x : f ` X. a = Renaming2_event_fun A b x} = {a}")
apply (simp)
apply (rule cspT_Rep_int_choice_singleton)

apply (simp add: Renaming_event_fun_def)
apply (force)
done

lemma cspT_Rec_prefix_Renaming2_set_event_step:
  "inj f ==>
  (f ? x:X -> Pf x)[[A<<-a]] =T[M,M]
  IF (EX x:X. f x : A)
  THEN (a -> (!<f> x:{x:X. f x : A} .. (Pf x)[[A<<-a]])
       [+] f ? x:(X-{x. f x : A}) -> (Pf x)[[A<<-a]])
  ELSE (f ? x:X -> (Pf x)[[A<<-a]])"
apply (case_tac "EX x:X. f x : A")
apply (rule cspT_rw_left)
apply (rule cspT_Rec_prefix_Renaming2_set_event_step_in)
apply (simp)
apply (simp)
apply (rule cspT_rw_right)
apply (rule cspT_IF_split)
apply (simp)
apply (rule cspT_rw_left)
apply (rule cspT_Rec_prefix_Renaming2_set_event_step_notin)
apply (simp)
apply (rule cspT_rw_right)
apply (rule cspT_IF_split)
apply (simp)
done

(* <-- *)

lemma cspT_Rec_prefix_Renaming2_event_step_in:
  "[| inj f ; v:X |] ==>
     (f ? x:X -> Pf x)[[f v<--a]] =T[M,M]
     (a -> (Pf v)[[f v<--a]]) [+] f ? x:(X-{v}) -> (Pf x)[[f v<--a]]"
apply (rule cspT_rw_left)
apply (rule cspT_Rec_prefix_Renaming2_set_event_step_in)
apply (simp)
apply (simp)
apply (force)
apply (simp)

apply (rule cspT_decompo)
 apply (rule cspT_decompo)
 apply (simp)
 apply (subgoal_tac "{x : X. f x = f v}={v}")
 apply (simp)
 apply (rule cspT_rw_left)
 apply (rule cspT_Rep_int_choice_singleton)
 apply (simp)
 apply (simp)
 apply (simp add: inj_on_def)
 apply (force)

 apply (subgoal_tac "{x. f x = f v}={v}")
 apply (simp)
 apply (simp add: inj_on_def)
 apply (force)
done

lemma cspT_Rec_prefix_Renaming2_event_step_notin:
  "[| (ALL x:X. a ~= f x) | a ~: f ` X |] ==>
     (f ? x:X -> Pf x)[[a<--b]] =T[M,M] f ? x:X -> (Pf x)[[a<--b]]"
apply (rule cspT_rw_left)
apply (rule cspT_Rec_prefix_Renaming2_set_event_step_notin)
apply (simp)
apply (force)
apply (simp)
done

lemmas cspT_Rec_prefix_Renaming2_event_step =
       cspT_Rec_prefix_Renaming2_event_step_in
       cspT_Rec_prefix_Renaming2_event_step_notin

lemmas cspT_Rec_prefix_Renaming_event_step =
       cspT_Rec_prefix_Renaming1_event_step
       cspT_Rec_prefix_Renaming2_event_step

(* ------ *)

(* <==> *)

lemma cspT_Rec_prefix_Renaming1_channel1_step_in:
  "[| inj f ; inj g ; ALL x y. f x ~= g y |] ==>
     (f ? x:X -> Pf x)[[f<==>g]] =T[M,M] g ? x:X -> (Pf x)[[f<==>g]]"
apply (simp add: Renaming_channel_def)
apply (simp add: csp_prefix_ss_def)
apply (rule cspT_rw_left)
apply (rule cspT_Renaming_fun_step)
apply (rule cspT_decompo)
apply (simp add: Renaming_channel_fun_simp)
apply (simp add: image_iff)
apply (erule bexE)
apply (simp)
apply (subgoal_tac
  "{xa. (EX x:X. xa = f x) & g x = Renaming1_channel_fun f g xa} = {f x}")
apply (simp)
apply (rule cspT_rw_left)
apply (rule cspT_Rep_int_choice_singleton)
apply (simp)

apply (auto)
apply (simp add: Renaming_channel_fun_simp)
apply (simp add: inj_on_def)
apply (force)
apply (simp add: Renaming_channel_fun_simp)
done

lemma cspT_Rec_prefix_Renaming1_channel2_step_in:
  "[| inj f ; inj g ; ALL x y. f x ~= g y |] ==>
     (f ? x:X -> Pf x)[[g<==>f]] =T[M,M] g ? x:X -> (Pf x)[[g<==>f]]"
apply (simp add: Renaming_commut)
apply (simp add: cspT_Rec_prefix_Renaming1_channel1_step_in)
done

(*
lemma Renaming_channel_fun_h:
   "[| ALL x y. f x ~= g y ; ALL x y. f x ~= h y ; ALL x y. g x ~= h y |]
    ==> Renaming_channel_fun f g (h x) = h x"
by (auto simp add: Renaming_channel_fun_def)

lemma Renaming_channel_fun_map_h:
   "[| (ALL x y. f x ~= h y) ;
       (ALL x y. g x ~= h y) ;
       ALL x y. f x ~= g y |]
    ==> Renaming_channel_fun f g ` h ` X = h ` X"
apply (simp add: image_def)
apply (auto simp add: Renaming_channel_fun_h)
done
*)

lemma cspT_Rec_prefix_Renaming1_channel_step_notin:
  "[| inj h;
      (ALL x y. f x ~= h y) | range f Int range h = {} ;
      (ALL x y. g x ~= h y) | range g Int range h = {} ;
       ALL x y. f x ~= g y |] ==>
    (h ? x:X -> Pf x)[[f<==>g]] =T[M,M] h ? x:X -> (Pf x)[[f<==>g]]"
apply (subgoal_tac "(ALL x y. f x ~= h y) & (ALL x y. g x ~= h y)")
apply (simp add: Renaming_channel_def)
apply (simp add: csp_prefix_ss_def)
apply (rule cspT_rw_left)
apply (rule cspT_Renaming_fun_step)
apply (rule cspT_decompo)
apply (simp add: Renaming_channel_fun_simp)

apply (simp add: image_iff)
apply (erule bexE)
apply (simp)
apply (subgoal_tac
  "{xa. (EX x:X. xa = h x) & h x = Renaming1_channel_fun f g xa} = {h x}")
apply (simp)
apply (rule cspT_rw_left)
apply (rule cspT_Rep_int_choice_singleton)
apply (simp)

apply (auto)
apply (simp add: Renaming_channel_fun_simp)
apply (simp add: Renaming_channel_fun_simp)
apply (blast)+
done

lemmas cspT_Rec_prefix_Renaming1_channel_step =
       cspT_Rec_prefix_Renaming1_channel1_step_in
       cspT_Rec_prefix_Renaming1_channel2_step_in
       cspT_Rec_prefix_Renaming1_channel_step_notin

(* <== *)

lemma cspT_Rec_prefix_Renaming2_channel_step_in:
  "[| inj f ; inj g ; ALL x y. f x ~= g y |] ==>
     (f ? x:X -> Pf x)[[f<==g]] =T[M,M] g ? x:X -> (Pf x)[[f<==g]]"
apply (simp add: Renaming_channel_def)
apply (simp add: csp_prefix_ss_def)
apply (rule cspT_rw_left)
apply (rule cspT_Renaming_fun_step)
apply (rule cspT_decompo)
apply (simp add: Renaming_channel_fun_simp)
apply (simp add: image_iff)
apply (erule bexE)
apply (simp)
apply (subgoal_tac
  "{xa. (EX x:X. xa = f x) & g x = Renaming2_channel_fun f g xa} = {f x}")
apply (simp)
apply (rule cspT_rw_left)
apply (rule cspT_Rep_int_choice_singleton)
apply (simp)

apply (auto)
apply (simp add: Renaming_channel_fun_simp)
apply (simp add: inj_on_def)
apply (force)
apply (simp add: Renaming_channel_fun_simp)
done

lemma cspT_Rec_prefix_Renaming2_channel_step_notin:
  "[| inj h;
      (ALL x y. f x ~= h y) | range f Int range h = {} ;
       ALL x y. f x ~= g y |] ==>
    (h ? x:X -> Pf x)[[f<==g]] =T[M,M] h ? x:X -> (Pf x)[[f<==g]]"
apply (subgoal_tac "(ALL x y. f x ~= h y)")
apply (simp add: Renaming_channel_def)
apply (simp add: csp_prefix_ss_def)
apply (rule cspT_rw_left)
apply (rule cspT_Renaming_fun_step)
apply (rule cspT_decompo)
apply (simp add: Renaming_channel_fun_simp)

apply (simp add: image_iff)
apply (erule bexE)
apply (simp)
apply (subgoal_tac
  "{xa. (EX x:X. xa = h x) & h x = Renaming2_channel_fun f g xa} = {h x}")
apply (simp)
apply (rule cspT_rw_left)
apply (rule cspT_Rep_int_choice_singleton)
apply (simp)

apply (auto)
apply (simp add: Renaming_channel_fun_simp)
apply (simp add: Renaming_channel_fun_simp)
apply (blast)+
done

lemmas cspT_Rec_prefix_Renaming2_channel_step =
       cspT_Rec_prefix_Renaming2_channel_step_in
       cspT_Rec_prefix_Renaming2_channel_step_notin

lemmas cspT_Rec_prefix_Renaming_channel_step =
       cspT_Rec_prefix_Renaming1_channel_step
       cspT_Rec_prefix_Renaming2_channel_step

lemmas cspT_Rec_prefix_Renaming_step =
       cspT_Rec_prefix_Renaming_event_step
       cspT_Rec_prefix_Renaming_channel_step

(* Nondet Sending *)

(* <--> *)

lemma cspT_Nondet_send_prefix_Renaming1_event1_step_in:
  "[| inj f ; v:X ; ALL x. a ~= f x |] ==>
     (f !? x:X -> Pf x)[[a<-->f v]] =T[M,M]
     (a -> (Pf v)[[a<-->f v]]) |~| f !? x:(X-{v}) -> (Pf x)[[a<-->f v]]"
apply (simp add: csp_prefix_ss_def)
apply (rule cspT_rw_left)
apply (rule cspT_Dist)
apply (subgoal_tac "(f ` X) = {f v} Un (f ` (X - {v}))")
apply (simp del: Un_insert_left)
apply (rule cspT_rw_left)
apply (rule cspT_Rep_int_choice_com_union_Int)
apply (rule cspT_decompo)

 (* 1 *)
 apply (rule cspT_rw_left)
 apply (rule cspT_Rep_int_choice_singleton)
 apply (simp add: cspT_Act_prefix_Renaming_event_step)

 (* 2 *)
 apply (rule cspT_decompo)
 apply (simp)
 apply (rule cspT_rw_left)
 apply (rule cspT_Act_prefix_Renaming_event_step)
 apply (auto)
 apply (simp add: inj_on_def)
done

lemma cspT_Nondet_send_prefix_Renaming1_event2_step_in:
  "[| inj f ; v:X ; ALL x. a ~= f x |] ==>
     (f !? x:X -> Pf x)[[f v<-->a]] =T[M,M]
     (a -> (Pf v)[[f v<-->a]]) |~| f !? x:(X-{v}) -> (Pf x)[[f v<-->a]]"
apply (simp add: Renaming_commut)
apply (simp add: cspT_Nondet_send_prefix_Renaming1_event1_step_in)
done

lemma cspT_Nondet_send_prefix_Renaming1_event_step_notin:
  "[| (ALL x. a ~= f x) | a ~: range f ;
      (ALL x. b ~= f x) | b ~: range f |] ==>
   (f !? x:X -> Pf x)[[a<-->b]] =T[M,M] f !? x:X -> (Pf x)[[a<-->b]]"
apply (simp add: csp_prefix_ss_def)
apply (rule cspT_rw_left)
apply (rule cspT_Dist)
apply (rule cspT_decompo)
apply (simp)
 apply (rule cspT_rw_left)
 apply (rule cspT_Act_prefix_Renaming_event_step)
 apply (auto)
done

lemmas cspT_Nondet_send_prefix_Renaming1_event_step =
       cspT_Nondet_send_prefix_Renaming1_event1_step_in
       cspT_Nondet_send_prefix_Renaming1_event2_step_in
       cspT_Nondet_send_prefix_Renaming1_event_step_notin

(* <<- *)

lemma cspT_Nondet_send_prefix_Renaming2_set_event_step_in:
  "[| inj f ; EX x:X. f x : A |] ==>
     (f !? x:X -> Pf x)[[A<<-a]] =T[M,M]
      a -> (!<f> x:{x:X. f x : A} .. (Pf x)[[A<<-a]])
     |~| f !? x:(X-{x. f x : A}) -> (Pf x)[[A<<-a]]"
apply (simp add: csp_prefix_ss_def)
apply (rule cspT_rw_left)
apply (rule cspT_Dist)
apply (rule cspT_rw_left)
apply (rule cspT_decompo)
apply (simp)
apply (rule cspT_decompo)
apply (simp)
apply (rule cspT_step)

apply (rule cspT_rw_left)
apply (rule cspT_decompo)
apply (simp)
apply (rule cspT_step)

apply (subgoal_tac "(f ` X) = (f ` {x : X. f x : A}) Un (f ` (X - {x. f x : A}))") (* 1 *)
 apply (simp del: Un_insert_left)
 apply (rule cspT_rw_left)
 apply (rule cspT_Rep_int_choice_com_union_Int)
 apply (rule cspT_decompo)

 (* left *)
 apply (subgoal_tac
  "a -> (!<f> x:{x : X. f x : A} .. Pf x [[A<<-a]])
   =T[M,M] !<f> x:{x : X. f x : A} .. a -> Pf x [[A<<-a]]")  (* 2 *)

  apply (rule cspT_rw_right)
  apply (assumption)
  apply (simp add: Rep_int_choice_f_def)
  apply (rule cspT_decompo)
  apply (simp)
  apply (simp add: image_iff)
  apply (elim conjE exE bexE)
  apply (simp)

  apply (rule cspT_rw_right)
  apply (rule cspT_step)
  apply (rule cspT_decompo)
  apply (simp add: Renaming_event_def)
  apply (simp add: Renaming_event_fun_def)
  apply (simp add: fun_to_rel_def)
  apply (force)

  apply (rule cspT_ref_eq)

   (* <= *)
   apply (rule cspT_Rep_int_choice_left)
   apply (simp add: Renaming_event_def)
   apply (simp add: Renaming_event_fun_def)
   apply (simp add: fun_to_rel_def)
   (* => *)
   apply (rule cspT_Rep_int_choice_right)
   apply (simp)

 (* 2 *)
  apply (rule cspT_rw_right)
  apply (rule cspT_choice_delay)
  apply (simp)
  apply (subgoal_tac "~(ALL x. x : X --> f x ~: A)")
   apply (simp (no_asm_simp))
   apply (rule cspT_rw_right)
   apply (rule cspT_IF_split)
   apply (simp)
  apply (force)

 (* right *)
 apply (rule cspT_decompo)
 apply (simp)

 apply (rule cspT_rw_right)
 apply (rule cspT_step)
 apply (rule cspT_decompo)
  apply (simp add: Renaming_event_def)
  apply (simp add: Renaming_event_fun_def)
  apply (simp add: fun_to_rel_def)
  apply (force)

 apply (simp)
 apply (rule cspT_ref_eq)

  (* <= *)
  apply (rule cspT_Rep_int_choice_left)
  apply (simp add: Renaming_event_def)
  apply (simp add: Renaming_event_fun_def)
  apply (simp add: fun_to_rel_def)
  apply (force)

  (* => *)
  apply (rule cspT_Rep_int_choice_right)
  apply (simp)

(* 1 *)
apply (auto)
done

lemma cspT_Nondet_send_prefix_Renaming2_set_event_step_notin:
  "[| (ALL x:X. f x ~: A) | A Int f ` X = {} |] ==>
     (f !? x:X -> Pf x)[[A<<-a]] =T[M,M]
      f !? x:X -> (Pf x)[[A<<-a]]"
apply (simp add: csp_prefix_ss_def)
apply (rule cspT_rw_left)
apply (rule cspT_Dist)
apply (rule cspT_decompo)
apply (simp)

apply (rule cspT_rw_left)
apply (rule cspT_decompo)
apply (simp)
apply (rule cspT_step)

apply (rule cspT_rw_left)
apply (rule cspT_step)

apply (rule cspT_rw_right)
apply (rule cspT_step)

apply (rule cspT_decompo)
 apply (simp add: Renaming_event_def)
 apply (simp add: Renaming_event_fun_def)
 apply (simp add: fun_to_rel_def)
 apply (force)

apply (simp)
 apply (rule cspT_ref_eq)

  (* <= *)
  apply (rule cspT_Rep_int_choice_left)
  apply (simp add: Renaming_event_def)
  apply (simp add: Renaming_event_fun_def)
  apply (simp add: fun_to_rel_def)
  apply (force)

  (* => *)
  apply (rule cspT_Rep_int_choice_right)
  apply (simp)
done

lemma cspT_Nondet_send_prefix_Renaming2_set_event_step:
  "inj f ==>
  (f !? x:X -> Pf x)[[A<<-a]] =T[M,M]
   IF (EX x:X. f x : A)
   THEN (a -> (!<f> x:{x:X. f x : A} .. (Pf x)[[A<<-a]])
         |~| f !? x:(X-{x. f x : A}) -> (Pf x)[[A<<-a]])
   ELSE (f !? x:X -> (Pf x)[[A<<-a]])"
apply (case_tac "EX x:X. f x : A")
apply (rule cspT_rw_left)
apply (rule cspT_Nondet_send_prefix_Renaming2_set_event_step_in)
apply (simp)
apply (simp)
apply (rule cspT_rw_right)
apply (rule cspT_IF_split)
apply (simp)
apply (rule cspT_rw_left)
apply (rule cspT_Nondet_send_prefix_Renaming2_set_event_step_notin)
apply (simp)
apply (simp)
apply (rule cspT_rw_right)
apply (rule cspT_IF_split)
apply (simp)
done

(* <-- *)

lemma cspT_Nondet_send_prefix_Renaming2_event_step_in:
  "[| inj f ; v:X ; ALL x. a ~= f x |] ==>
     (f !? x:X -> Pf x)[[f v<--a]] =T[M,M]
     (a -> (Pf v)[[f v<--a]]) |~| f !? x:(X-{v}) -> (Pf x)[[f v<--a]]"
apply (rule cspT_rw_left)
apply (rule cspT_Nondet_send_prefix_Renaming2_set_event_step_in)
apply (simp)
apply (simp)
apply (force)
apply (simp)

apply (rule cspT_decompo)
 apply (rule cspT_decompo)
 apply (simp)
 apply (subgoal_tac "{x : X. f x = f v}={v}")
 apply (simp)
 apply (rule cspT_rw_left)
 apply (rule cspT_Rep_int_choice_singleton)
 apply (simp)
 apply (simp)
 apply (simp add: inj_on_def)
 apply (force)

 apply (subgoal_tac "{x. f x = f v}={v}")
 apply (simp)
 apply (simp add: inj_on_def)
 apply (force)
done

lemma cspT_Nondet_send_prefix_Renaming2_event_step_notin:
  "[| (ALL x. a ~= f x) | a ~: range f |] ==>
   (f !? x:X -> Pf x)[[a<--b]] =T[M,M] f !? x:X -> (Pf x)[[a<--b]]"
apply (rule cspT_rw_left)
apply (rule cspT_Nondet_send_prefix_Renaming2_set_event_step_notin)
apply (simp)
apply (force)
apply (simp)
done

lemmas cspT_Nondet_send_prefix_Renaming2_event_step =
       cspT_Nondet_send_prefix_Renaming2_event_step_in
       cspT_Nondet_send_prefix_Renaming2_event_step_notin

lemmas cspT_Nondet_send_prefix_Renaming_event_step =
       cspT_Nondet_send_prefix_Renaming1_event_step
       cspT_Nondet_send_prefix_Renaming2_event_step

(* <==> *)

lemma cspT_Nondet_send_prefix_Renaming1_channel1_step_in:
  "[| inj f ; inj g ; ALL x y. f x ~= g y |] ==>
   (f !? x:X -> Pf x)[[f<==>g]] =T[M,M] g !? x:X -> (Pf x)[[f<==>g]]"
apply (simp add: csp_prefix_ss_def)
apply (rule cspT_rw_left)
apply (rule cspT_Dist)
apply (rule cspT_ref_eq)

(* <= *)
 apply (rule cspT_Rep_int_choice_right)
 apply (simp add: image_iff)
 apply (erule bexE)
 apply (simp)

 apply (rule cspT_Rep_int_choice_left)
 apply (rule_tac x="f x" in exI)
 apply (simp)
 apply (rule cspT_rw_left)
 apply (rule cspT_Act_prefix_Renaming_channel_step)
 apply (simp_all)

(* => *)
 apply (rule cspT_Rep_int_choice_right)
 apply (simp add: image_iff)
 apply (erule bexE)
 apply (simp)

 apply (rule cspT_Rep_int_choice_left)
 apply (rule_tac x="g x" in exI)
 apply (simp)
 apply (rule cspT_rw_right)
 apply (rule cspT_Act_prefix_Renaming_channel_step)
 apply (simp_all)
done

lemma cspT_Nondet_send_prefix_Renaming1_channel2_step_in:
  "[| inj f ; inj g ; ALL x y. f x ~= g y |] ==>
   (f !? x:X -> Pf x)[[g<==>f]] =T[M,M] g !? x:X -> (Pf x)[[g<==>f]]"
apply (simp add: Renaming_commut)
apply (simp add: cspT_Nondet_send_prefix_Renaming1_channel1_step_in)
done

lemma cspT_Nondet_send_prefix_Renaming1_channel_step_notin:
  "[| (ALL x y. f x ~= h y) | (range f Int range h = {}) ;
      (ALL x y. g x ~= h y) | (range g Int range h = {}) |] ==>
   (h !? x:X -> Pf x)[[f<==>g]] =T[M,M] h !? x:X -> (Pf x)[[f<==>g]]"
apply (simp add: csp_prefix_ss_def)
apply (rule cspT_rw_left)
apply (rule cspT_Dist)
apply (rule cspT_decompo)
apply (simp)

apply (rule cspT_rw_left)
apply (rule cspT_Act_prefix_Renaming_channel_step)
apply (blast)
apply (blast)
apply (simp)
done

lemmas cspT_Nondet_send_prefix_Renaming1_channel_step =
       cspT_Nondet_send_prefix_Renaming1_channel1_step_in
       cspT_Nondet_send_prefix_Renaming1_channel2_step_in
       cspT_Nondet_send_prefix_Renaming1_channel_step_notin

(* <== *)

lemma cspT_Nondet_send_prefix_Renaming2_channel_step_in:
  "[| inj f ; inj g ; ALL x y. f x ~= g y |] ==>
   (f !? x:X -> Pf x)[[f<==g]] =T[M,M] g !? x:X -> (Pf x)[[f<==g]]"
apply (simp add: csp_prefix_ss_def)
apply (rule cspT_rw_left)
apply (rule cspT_Dist)
apply (rule cspT_ref_eq)

(* <= *)
 apply (rule cspT_Rep_int_choice_right)
 apply (simp add: image_iff)
 apply (erule bexE)
 apply (simp)

 apply (rule cspT_Rep_int_choice_left)
 apply (rule_tac x="f x" in exI)
 apply (simp)
 apply (rule cspT_rw_left)
 apply (rule cspT_Act_prefix_Renaming_channel_step)
 apply (simp_all)

(* => *)
 apply (rule cspT_Rep_int_choice_right)
 apply (simp add: image_iff)
 apply (erule bexE)
 apply (simp)

 apply (rule cspT_Rep_int_choice_left)
 apply (rule_tac x="g x" in exI)
 apply (simp)
 apply (rule cspT_rw_right)
 apply (rule cspT_Act_prefix_Renaming_channel_step)
 apply (simp_all)
done

lemma cspT_Nondet_send_prefix_Renaming2_channel_step_notin:
  "[| (ALL x y. f x ~= h y) | (range f Int range h = {}) |] ==>
   (h !? x:X -> Pf x)[[f<==g]] =T[M,M] h !? x:X -> (Pf x)[[f<==g]]"
apply (simp add: csp_prefix_ss_def)
apply (rule cspT_rw_left)
apply (rule cspT_Dist)
apply (rule cspT_decompo)
apply (simp)

apply (rule cspT_rw_left)
apply (rule cspT_Act_prefix_Renaming_channel_step)
apply (blast)
apply (simp)
done

lemmas cspT_Nondet_send_prefix_Renaming2_channel_step =
       cspT_Nondet_send_prefix_Renaming2_channel_step_in
       cspT_Nondet_send_prefix_Renaming2_channel_step_notin

lemmas cspT_Nondet_send_prefix_Renaming_channel_step =
       cspT_Nondet_send_prefix_Renaming1_channel_step
       cspT_Nondet_send_prefix_Renaming2_channel_step

lemmas cspT_Nondet_send_prefix_Renaming_step =
       cspT_Nondet_send_prefix_Renaming_event_step
       cspT_Nondet_send_prefix_Renaming_channel_step

(* ---------------- *
      in or notin
 * ---------------- *)

lemmas cspT_prefix_Renaming_in_step =
       cspT_Act_prefix_Renaming1_event1_step_in
       cspT_Act_prefix_Renaming1_event2_step_in
       cspT_Act_prefix_Renaming1_channel1_step_in
       cspT_Act_prefix_Renaming1_channel2_step_in
       cspT_Send_prefix_Renaming1_event1_step_in
       cspT_Send_prefix_Renaming1_event2_step_in
       cspT_Send_prefix_Renaming1_channel1_step_in
       cspT_Send_prefix_Renaming1_channel2_step_in
       cspT_Rec_prefix_Renaming1_event1_step_in
       cspT_Rec_prefix_Renaming1_event2_step_in
       cspT_Rec_prefix_Renaming1_channel1_step_in
       cspT_Rec_prefix_Renaming1_channel2_step_in
       cspT_Nondet_send_prefix_Renaming1_event1_step_in
       cspT_Nondet_send_prefix_Renaming1_event2_step_in
       cspT_Nondet_send_prefix_Renaming1_channel1_step_in
       cspT_Nondet_send_prefix_Renaming1_channel2_step_in
       cspT_Act_prefix_Renaming2_event_step_in
       cspT_Act_prefix_Renaming2_channel_step_in
       cspT_Send_prefix_Renaming2_event_step_in
       cspT_Send_prefix_Renaming2_channel_step_in
       cspT_Rec_prefix_Renaming2_event_step_in
       cspT_Rec_prefix_Renaming2_channel_step_in
       cspT_Nondet_send_prefix_Renaming2_event_step_in
       cspT_Nondet_send_prefix_Renaming2_channel_step_in

(* notin + <<- + ?X *)

lemmas cspT_prefix_Renaming_notin_step =
       cspT_Act_prefix_Renaming1_event_step_notin
       cspT_Act_prefix_Renaming1_channel_step_notin
       cspT_Send_prefix_Renaming1_event_step_notin
       cspT_Send_prefix_Renaming1_channel_step_notin
       cspT_Rec_prefix_Renaming1_event_step_notin
       cspT_Rec_prefix_Renaming1_channel_step_notin
       cspT_Nondet_send_prefix_Renaming1_event_step_notin
       cspT_Nondet_send_prefix_Renaming1_channel_step_notin
       cspT_Act_prefix_Renaming2_event_step_notin
       cspT_Act_prefix_Renaming2_channel_step_notin
       cspT_Send_prefix_Renaming2_event_step_notin
       cspT_Send_prefix_Renaming2_channel_step_notin
       cspT_Rec_prefix_Renaming2_event_step_notin
       cspT_Rec_prefix_Renaming2_channel_step_notin
       cspT_Nondet_send_prefix_Renaming2_event_step_notin
       cspT_Nondet_send_prefix_Renaming2_channel_step_notin

       cspT_Act_prefix_Renaming2_set_event_step
       cspT_Send_prefix_Renaming2_set_event_step
       cspT_Rec_prefix_Renaming2_set_event_step
       cspT_Nondet_send_prefix_Renaming2_set_event_step

       cspT_Ext_pre_choice_Renaming_event_step

(* ----------------------------------------------------------- *)

end