src/HOL/Word/Bit_Int.thy
changeset 54847 d6cf9a5b9be9
parent 54489 03ff4d1e6784
child 54848 a303daddebbf
equal deleted inserted replaced
54846:bf86b2002c96 54847:d6cf9a5b9be9
     7 *) 
     7 *) 
     8 
     8 
     9 header {* Bitwise Operations on Binary Integers *}
     9 header {* Bitwise Operations on Binary Integers *}
    10 
    10 
    11 theory Bit_Int
    11 theory Bit_Int
    12 imports Bit_Representation Bit_Bit
    12 imports Bit_Representation Bit_Operations
    13 begin
    13 begin
    14 
    14 
    15 subsection {* Logical operations *}
    15 subsection {* Logical operations *}
    16 
    16 
    17 text "bit-wise logical operations on the int type"
    17 text "bit-wise logical operations on the int type"
    23   "bitNOT = (\<lambda>x::int. - x - 1)"
    23   "bitNOT = (\<lambda>x::int. - x - 1)"
    24 
    24 
    25 function bitAND_int where
    25 function bitAND_int where
    26   "bitAND_int x y =
    26   "bitAND_int x y =
    27     (if x = 0 then 0 else if x = -1 then y else
    27     (if x = 0 then 0 else if x = -1 then y else
    28       (bin_rest x AND bin_rest y) BIT (bin_last x AND bin_last y))"
    28       (bin_rest x AND bin_rest y) BIT (bin_last x \<and> bin_last y))"
    29   by pat_completeness simp
    29   by pat_completeness simp
    30 
    30 
    31 termination
    31 termination
    32   by (relation "measure (nat o abs o fst)", simp_all add: bin_rest_def)
    32   by (relation "measure (nat o abs o fst)", simp_all add: bin_rest_def)
    33 
    33 
    44 end
    44 end
    45 
    45 
    46 subsubsection {* Basic simplification rules *}
    46 subsubsection {* Basic simplification rules *}
    47 
    47 
    48 lemma int_not_BIT [simp]:
    48 lemma int_not_BIT [simp]:
    49   "NOT (w BIT b) = (NOT w) BIT (NOT b)"
    49   "NOT (w BIT b) = (NOT w) BIT (\<not> b)"
    50   unfolding int_not_def Bit_def by (cases b, simp_all)
    50   unfolding int_not_def Bit_def by (cases b, simp_all)
    51 
    51 
    52 lemma int_not_simps [simp]:
    52 lemma int_not_simps [simp]:
    53   "NOT (0::int) = -1"
    53   "NOT (0::int) = -1"
    54   "NOT (1::int) = -2"
    54   "NOT (1::int) = -2"
    66 
    66 
    67 lemma int_and_m1 [simp]: "(-1::int) AND x = x"
    67 lemma int_and_m1 [simp]: "(-1::int) AND x = x"
    68   by (simp add: bitAND_int.simps)
    68   by (simp add: bitAND_int.simps)
    69 
    69 
    70 lemma int_and_Bits [simp]: 
    70 lemma int_and_Bits [simp]: 
    71   "(x BIT b) AND (y BIT c) = (x AND y) BIT (b AND c)" 
    71   "(x BIT b) AND (y BIT c) = (x AND y) BIT (b \<and> c)" 
    72   by (subst bitAND_int.simps, simp add: Bit_eq_0_iff Bit_eq_m1_iff)
    72   by (subst bitAND_int.simps, simp add: Bit_eq_0_iff Bit_eq_m1_iff)
    73 
    73 
    74 lemma int_or_zero [simp]: "(0::int) OR x = x"
    74 lemma int_or_zero [simp]: "(0::int) OR x = x"
    75   unfolding int_or_def by simp
    75   unfolding int_or_def by simp
    76 
    76 
    77 lemma int_or_minus1 [simp]: "(-1::int) OR x = -1"
    77 lemma int_or_minus1 [simp]: "(-1::int) OR x = -1"
    78   unfolding int_or_def by simp
    78   unfolding int_or_def by simp
    79 
    79 
    80 lemma int_or_Bits [simp]: 
    80 lemma int_or_Bits [simp]: 
    81   "(x BIT b) OR (y BIT c) = (x OR y) BIT (b OR c)"
    81   "(x BIT b) OR (y BIT c) = (x OR y) BIT (b \<or> c)"
    82   unfolding int_or_def bit_or_def by simp
    82   unfolding int_or_def by simp
    83 
    83 
    84 lemma int_xor_zero [simp]: "(0::int) XOR x = x"
    84 lemma int_xor_zero [simp]: "(0::int) XOR x = x"
    85   unfolding int_xor_def by simp
    85   unfolding int_xor_def by simp
    86 
    86 
    87 lemma int_xor_Bits [simp]: 
    87 lemma int_xor_Bits [simp]: 
    88   "(x BIT b) XOR (y BIT c) = (x XOR y) BIT (b XOR c)"
    88   "(x BIT b) XOR (y BIT c) = (x XOR y) BIT ((b \<or> c) \<and> \<not> (b \<and> c))"
    89   unfolding int_xor_def bit_xor_def by simp
    89   unfolding int_xor_def by auto
    90 
    90 
    91 subsubsection {* Binary destructors *}
    91 subsubsection {* Binary destructors *}
    92 
    92 
    93 lemma bin_rest_NOT [simp]: "bin_rest (NOT x) = NOT (bin_rest x)"
    93 lemma bin_rest_NOT [simp]: "bin_rest (NOT x) = NOT (bin_rest x)"
    94   by (cases x rule: bin_exhaust, simp)
    94   by (cases x rule: bin_exhaust, simp)
    95 
    95 
    96 lemma bin_last_NOT [simp]: "bin_last (NOT x) = NOT (bin_last x)"
    96 lemma bin_last_NOT [simp]: "bin_last (NOT x) \<longleftrightarrow> \<not> bin_last x"
    97   by (cases x rule: bin_exhaust, simp)
    97   by (cases x rule: bin_exhaust, simp)
    98 
    98 
    99 lemma bin_rest_AND [simp]: "bin_rest (x AND y) = bin_rest x AND bin_rest y"
    99 lemma bin_rest_AND [simp]: "bin_rest (x AND y) = bin_rest x AND bin_rest y"
   100   by (cases x rule: bin_exhaust, cases y rule: bin_exhaust, simp)
   100   by (cases x rule: bin_exhaust, cases y rule: bin_exhaust, simp)
   101 
   101 
   102 lemma bin_last_AND [simp]: "bin_last (x AND y) = bin_last x AND bin_last y"
   102 lemma bin_last_AND [simp]: "bin_last (x AND y) \<longleftrightarrow> bin_last x \<and> bin_last y"
   103   by (cases x rule: bin_exhaust, cases y rule: bin_exhaust, simp)
   103   by (cases x rule: bin_exhaust, cases y rule: bin_exhaust, simp)
   104 
   104 
   105 lemma bin_rest_OR [simp]: "bin_rest (x OR y) = bin_rest x OR bin_rest y"
   105 lemma bin_rest_OR [simp]: "bin_rest (x OR y) = bin_rest x OR bin_rest y"
   106   by (cases x rule: bin_exhaust, cases y rule: bin_exhaust, simp)
   106   by (cases x rule: bin_exhaust, cases y rule: bin_exhaust, simp)
   107 
   107 
   108 lemma bin_last_OR [simp]: "bin_last (x OR y) = bin_last x OR bin_last y"
   108 lemma bin_last_OR [simp]: "bin_last (x OR y) \<longleftrightarrow> bin_last x \<or> bin_last y"
   109   by (cases x rule: bin_exhaust, cases y rule: bin_exhaust, simp)
   109   by (cases x rule: bin_exhaust, cases y rule: bin_exhaust, simp)
   110 
   110 
   111 lemma bin_rest_XOR [simp]: "bin_rest (x XOR y) = bin_rest x XOR bin_rest y"
   111 lemma bin_rest_XOR [simp]: "bin_rest (x XOR y) = bin_rest x XOR bin_rest y"
   112   by (cases x rule: bin_exhaust, cases y rule: bin_exhaust, simp)
   112   by (cases x rule: bin_exhaust, cases y rule: bin_exhaust, simp)
   113 
   113 
   114 lemma bin_last_XOR [simp]: "bin_last (x XOR y) = bin_last x XOR bin_last y"
   114 lemma bin_last_XOR [simp]: "bin_last (x XOR y) \<longleftrightarrow> (bin_last x \<or> bin_last y) \<and> \<not> (bin_last x \<and> bin_last y)"
   115   by (cases x rule: bin_exhaust, cases y rule: bin_exhaust, simp)
   115   by (cases x rule: bin_exhaust, cases y rule: bin_exhaust, simp)
   116 
   116 
   117 lemma bin_nth_ops:
   117 lemma bin_nth_ops:
   118   "!!x y. bin_nth (x AND y) n = (bin_nth x n & bin_nth y n)" 
   118   "!!x y. bin_nth (x AND y) n = (bin_nth x n & bin_nth y n)" 
   119   "!!x y. bin_nth (x OR y) n = (bin_nth x n | bin_nth y n)"
   119   "!!x y. bin_nth (x OR y) n = (bin_nth x n | bin_nth y n)"
   223 
   223 
   224 text {* Cases for @{text "0"} and @{text "-1"} are already covered by
   224 text {* Cases for @{text "0"} and @{text "-1"} are already covered by
   225   other simp rules. *}
   225   other simp rules. *}
   226 
   226 
   227 lemma bin_rl_eqI: "\<lbrakk>bin_rest x = bin_rest y; bin_last x = bin_last y\<rbrakk> \<Longrightarrow> x = y"
   227 lemma bin_rl_eqI: "\<lbrakk>bin_rest x = bin_rest y; bin_last x = bin_last y\<rbrakk> \<Longrightarrow> x = y"
   228   by (metis bin_rl_simp)
   228   by (metis (mono_tags) BIT_eq_iff bin_ex_rl bin_last_BIT bin_rest_BIT)
   229 
   229 
   230 lemma bin_rest_neg_numeral_BitM [simp]:
   230 lemma bin_rest_neg_numeral_BitM [simp]:
   231   "bin_rest (- numeral (Num.BitM w)) = - numeral w"
   231   "bin_rest (- numeral (Num.BitM w)) = - numeral w"
   232   by (simp only: BIT_bin_simps [symmetric] bin_rest_BIT)
   232   by (simp only: BIT_bin_simps [symmetric] bin_rest_BIT)
   233 
   233 
   234 lemma bin_last_neg_numeral_BitM [simp]:
   234 lemma bin_last_neg_numeral_BitM [simp]:
   235   "bin_last (-  numeral (Num.BitM w)) = 1"
   235   "bin_last (- numeral (Num.BitM w))"
   236   by (simp only: BIT_bin_simps [symmetric] bin_last_BIT)
   236   by (simp only: BIT_bin_simps [symmetric] bin_last_BIT)
   237 
   237 
   238 text {* FIXME: The rule sets below are very large (24 rules for each
   238 text {* FIXME: The rule sets below are very large (24 rules for each
   239   operator). Is there a simpler way to do this? *}
   239   operator). Is there a simpler way to do this? *}
   240 
   240 
   241 lemma int_and_numerals [simp]:
   241 lemma int_and_numerals [simp]:
   242   "numeral (Num.Bit0 x) AND numeral (Num.Bit0 y) = (numeral x AND numeral y) BIT 0"
   242   "numeral (Num.Bit0 x) AND numeral (Num.Bit0 y) = (numeral x AND numeral y) BIT False"
   243   "numeral (Num.Bit0 x) AND numeral (Num.Bit1 y) = (numeral x AND numeral y) BIT 0"
   243   "numeral (Num.Bit0 x) AND numeral (Num.Bit1 y) = (numeral x AND numeral y) BIT False"
   244   "numeral (Num.Bit1 x) AND numeral (Num.Bit0 y) = (numeral x AND numeral y) BIT 0"
   244   "numeral (Num.Bit1 x) AND numeral (Num.Bit0 y) = (numeral x AND numeral y) BIT False"
   245   "numeral (Num.Bit1 x) AND numeral (Num.Bit1 y) = (numeral x AND numeral y) BIT 1"
   245   "numeral (Num.Bit1 x) AND numeral (Num.Bit1 y) = (numeral x AND numeral y) BIT True"
   246   "numeral (Num.Bit0 x) AND - numeral (Num.Bit0 y) = (numeral x AND - numeral y) BIT 0"
   246   "numeral (Num.Bit0 x) AND - numeral (Num.Bit0 y) = (numeral x AND - numeral y) BIT False"
   247   "numeral (Num.Bit0 x) AND - numeral (Num.Bit1 y) = (numeral x AND - numeral (y + Num.One)) BIT 0"
   247   "numeral (Num.Bit0 x) AND - numeral (Num.Bit1 y) = (numeral x AND - numeral (y + Num.One)) BIT False"
   248   "numeral (Num.Bit1 x) AND - numeral (Num.Bit0 y) = (numeral x AND - numeral y) BIT 0"
   248   "numeral (Num.Bit1 x) AND - numeral (Num.Bit0 y) = (numeral x AND - numeral y) BIT False"
   249   "numeral (Num.Bit1 x) AND - numeral (Num.Bit1 y) = (numeral x AND - numeral (y + Num.One)) BIT 1"
   249   "numeral (Num.Bit1 x) AND - numeral (Num.Bit1 y) = (numeral x AND - numeral (y + Num.One)) BIT True"
   250   "- numeral (Num.Bit0 x) AND numeral (Num.Bit0 y) = (- numeral x AND numeral y) BIT 0"
   250   "- numeral (Num.Bit0 x) AND numeral (Num.Bit0 y) = (- numeral x AND numeral y) BIT False"
   251   "- numeral (Num.Bit0 x) AND numeral (Num.Bit1 y) = (- numeral x AND numeral y) BIT 0"
   251   "- numeral (Num.Bit0 x) AND numeral (Num.Bit1 y) = (- numeral x AND numeral y) BIT False"
   252   "- numeral (Num.Bit1 x) AND numeral (Num.Bit0 y) = (- numeral (x + Num.One) AND numeral y) BIT 0"
   252   "- numeral (Num.Bit1 x) AND numeral (Num.Bit0 y) = (- numeral (x + Num.One) AND numeral y) BIT False"
   253   "- numeral (Num.Bit1 x) AND numeral (Num.Bit1 y) = (- numeral (x + Num.One) AND numeral y) BIT 1"
   253   "- numeral (Num.Bit1 x) AND numeral (Num.Bit1 y) = (- numeral (x + Num.One) AND numeral y) BIT True"
   254   "- numeral (Num.Bit0 x) AND - numeral (Num.Bit0 y) = (- numeral x AND - numeral y) BIT 0"
   254   "- numeral (Num.Bit0 x) AND - numeral (Num.Bit0 y) = (- numeral x AND - numeral y) BIT False"
   255   "- numeral (Num.Bit0 x) AND - numeral (Num.Bit1 y) = (- numeral x AND - numeral (y + Num.One)) BIT 0"
   255   "- numeral (Num.Bit0 x) AND - numeral (Num.Bit1 y) = (- numeral x AND - numeral (y + Num.One)) BIT False"
   256   "- numeral (Num.Bit1 x) AND - numeral (Num.Bit0 y) = (- numeral (x + Num.One) AND - numeral y) BIT 0"
   256   "- numeral (Num.Bit1 x) AND - numeral (Num.Bit0 y) = (- numeral (x + Num.One) AND - numeral y) BIT False"
   257   "- numeral (Num.Bit1 x) AND - numeral (Num.Bit1 y) = (- numeral (x + Num.One) AND - numeral (y + Num.One)) BIT 1"
   257   "- numeral (Num.Bit1 x) AND - numeral (Num.Bit1 y) = (- numeral (x + Num.One) AND - numeral (y + Num.One)) BIT True"
   258   "(1::int) AND numeral (Num.Bit0 y) = 0"
   258   "(1::int) AND numeral (Num.Bit0 y) = 0"
   259   "(1::int) AND numeral (Num.Bit1 y) = 1"
   259   "(1::int) AND numeral (Num.Bit1 y) = 1"
   260   "(1::int) AND - numeral (Num.Bit0 y) = 0"
   260   "(1::int) AND - numeral (Num.Bit0 y) = 0"
   261   "(1::int) AND - numeral (Num.Bit1 y) = 1"
   261   "(1::int) AND - numeral (Num.Bit1 y) = 1"
   262   "numeral (Num.Bit0 x) AND (1::int) = 0"
   262   "numeral (Num.Bit0 x) AND (1::int) = 0"
   264   "- numeral (Num.Bit0 x) AND (1::int) = 0"
   264   "- numeral (Num.Bit0 x) AND (1::int) = 0"
   265   "- numeral (Num.Bit1 x) AND (1::int) = 1"
   265   "- numeral (Num.Bit1 x) AND (1::int) = 1"
   266   by (rule bin_rl_eqI, simp, simp)+
   266   by (rule bin_rl_eqI, simp, simp)+
   267 
   267 
   268 lemma int_or_numerals [simp]:
   268 lemma int_or_numerals [simp]:
   269   "numeral (Num.Bit0 x) OR numeral (Num.Bit0 y) = (numeral x OR numeral y) BIT 0"
   269   "numeral (Num.Bit0 x) OR numeral (Num.Bit0 y) = (numeral x OR numeral y) BIT False"
   270   "numeral (Num.Bit0 x) OR numeral (Num.Bit1 y) = (numeral x OR numeral y) BIT 1"
   270   "numeral (Num.Bit0 x) OR numeral (Num.Bit1 y) = (numeral x OR numeral y) BIT True"
   271   "numeral (Num.Bit1 x) OR numeral (Num.Bit0 y) = (numeral x OR numeral y) BIT 1"
   271   "numeral (Num.Bit1 x) OR numeral (Num.Bit0 y) = (numeral x OR numeral y) BIT True"
   272   "numeral (Num.Bit1 x) OR numeral (Num.Bit1 y) = (numeral x OR numeral y) BIT 1"
   272   "numeral (Num.Bit1 x) OR numeral (Num.Bit1 y) = (numeral x OR numeral y) BIT True"
   273   "numeral (Num.Bit0 x) OR - numeral (Num.Bit0 y) = (numeral x OR - numeral y) BIT 0"
   273   "numeral (Num.Bit0 x) OR - numeral (Num.Bit0 y) = (numeral x OR - numeral y) BIT False"
   274   "numeral (Num.Bit0 x) OR - numeral (Num.Bit1 y) = (numeral x OR - numeral (y + Num.One)) BIT 1"
   274   "numeral (Num.Bit0 x) OR - numeral (Num.Bit1 y) = (numeral x OR - numeral (y + Num.One)) BIT True"
   275   "numeral (Num.Bit1 x) OR - numeral (Num.Bit0 y) = (numeral x OR - numeral y) BIT 1"
   275   "numeral (Num.Bit1 x) OR - numeral (Num.Bit0 y) = (numeral x OR - numeral y) BIT True"
   276   "numeral (Num.Bit1 x) OR - numeral (Num.Bit1 y) = (numeral x OR - numeral (y + Num.One)) BIT 1"
   276   "numeral (Num.Bit1 x) OR - numeral (Num.Bit1 y) = (numeral x OR - numeral (y + Num.One)) BIT True"
   277   "- numeral (Num.Bit0 x) OR numeral (Num.Bit0 y) = (- numeral x OR numeral y) BIT 0"
   277   "- numeral (Num.Bit0 x) OR numeral (Num.Bit0 y) = (- numeral x OR numeral y) BIT False"
   278   "- numeral (Num.Bit0 x) OR numeral (Num.Bit1 y) = (- numeral x OR numeral y) BIT 1"
   278   "- numeral (Num.Bit0 x) OR numeral (Num.Bit1 y) = (- numeral x OR numeral y) BIT True"
   279   "- numeral (Num.Bit1 x) OR numeral (Num.Bit0 y) = (- numeral (x + Num.One) OR numeral y) BIT 1"
   279   "- numeral (Num.Bit1 x) OR numeral (Num.Bit0 y) = (- numeral (x + Num.One) OR numeral y) BIT True"
   280   "- numeral (Num.Bit1 x) OR numeral (Num.Bit1 y) = (- numeral (x + Num.One) OR numeral y) BIT 1"
   280   "- numeral (Num.Bit1 x) OR numeral (Num.Bit1 y) = (- numeral (x + Num.One) OR numeral y) BIT True"
   281   "- numeral (Num.Bit0 x) OR - numeral (Num.Bit0 y) = (- numeral x OR - numeral y) BIT 0"
   281   "- numeral (Num.Bit0 x) OR - numeral (Num.Bit0 y) = (- numeral x OR - numeral y) BIT False"
   282   "- numeral (Num.Bit0 x) OR - numeral (Num.Bit1 y) = (- numeral x OR - numeral (y + Num.One)) BIT 1"
   282   "- numeral (Num.Bit0 x) OR - numeral (Num.Bit1 y) = (- numeral x OR - numeral (y + Num.One)) BIT True"
   283   "- numeral (Num.Bit1 x) OR - numeral (Num.Bit0 y) = (- numeral (x + Num.One) OR - numeral y) BIT 1"
   283   "- numeral (Num.Bit1 x) OR - numeral (Num.Bit0 y) = (- numeral (x + Num.One) OR - numeral y) BIT True"
   284   "- numeral (Num.Bit1 x) OR - numeral (Num.Bit1 y) = (- numeral (x + Num.One) OR - numeral (y + Num.One)) BIT 1"
   284   "- numeral (Num.Bit1 x) OR - numeral (Num.Bit1 y) = (- numeral (x + Num.One) OR - numeral (y + Num.One)) BIT True"
   285   "(1::int) OR numeral (Num.Bit0 y) = numeral (Num.Bit1 y)"
   285   "(1::int) OR numeral (Num.Bit0 y) = numeral (Num.Bit1 y)"
   286   "(1::int) OR numeral (Num.Bit1 y) = numeral (Num.Bit1 y)"
   286   "(1::int) OR numeral (Num.Bit1 y) = numeral (Num.Bit1 y)"
   287   "(1::int) OR - numeral (Num.Bit0 y) = - numeral (Num.BitM y)"
   287   "(1::int) OR - numeral (Num.Bit0 y) = - numeral (Num.BitM y)"
   288   "(1::int) OR - numeral (Num.Bit1 y) = - numeral (Num.Bit1 y)"
   288   "(1::int) OR - numeral (Num.Bit1 y) = - numeral (Num.Bit1 y)"
   289   "numeral (Num.Bit0 x) OR (1::int) = numeral (Num.Bit1 x)"
   289   "numeral (Num.Bit0 x) OR (1::int) = numeral (Num.Bit1 x)"
   291   "- numeral (Num.Bit0 x) OR (1::int) = - numeral (Num.BitM x)"
   291   "- numeral (Num.Bit0 x) OR (1::int) = - numeral (Num.BitM x)"
   292   "- numeral (Num.Bit1 x) OR (1::int) = - numeral (Num.Bit1 x)"
   292   "- numeral (Num.Bit1 x) OR (1::int) = - numeral (Num.Bit1 x)"
   293   by (rule bin_rl_eqI, simp, simp)+
   293   by (rule bin_rl_eqI, simp, simp)+
   294 
   294 
   295 lemma int_xor_numerals [simp]:
   295 lemma int_xor_numerals [simp]:
   296   "numeral (Num.Bit0 x) XOR numeral (Num.Bit0 y) = (numeral x XOR numeral y) BIT 0"
   296   "numeral (Num.Bit0 x) XOR numeral (Num.Bit0 y) = (numeral x XOR numeral y) BIT False"
   297   "numeral (Num.Bit0 x) XOR numeral (Num.Bit1 y) = (numeral x XOR numeral y) BIT 1"
   297   "numeral (Num.Bit0 x) XOR numeral (Num.Bit1 y) = (numeral x XOR numeral y) BIT True"
   298   "numeral (Num.Bit1 x) XOR numeral (Num.Bit0 y) = (numeral x XOR numeral y) BIT 1"
   298   "numeral (Num.Bit1 x) XOR numeral (Num.Bit0 y) = (numeral x XOR numeral y) BIT True"
   299   "numeral (Num.Bit1 x) XOR numeral (Num.Bit1 y) = (numeral x XOR numeral y) BIT 0"
   299   "numeral (Num.Bit1 x) XOR numeral (Num.Bit1 y) = (numeral x XOR numeral y) BIT False"
   300   "numeral (Num.Bit0 x) XOR - numeral (Num.Bit0 y) = (numeral x XOR - numeral y) BIT 0"
   300   "numeral (Num.Bit0 x) XOR - numeral (Num.Bit0 y) = (numeral x XOR - numeral y) BIT False"
   301   "numeral (Num.Bit0 x) XOR - numeral (Num.Bit1 y) = (numeral x XOR - numeral (y + Num.One)) BIT 1"
   301   "numeral (Num.Bit0 x) XOR - numeral (Num.Bit1 y) = (numeral x XOR - numeral (y + Num.One)) BIT True"
   302   "numeral (Num.Bit1 x) XOR - numeral (Num.Bit0 y) = (numeral x XOR - numeral y) BIT 1"
   302   "numeral (Num.Bit1 x) XOR - numeral (Num.Bit0 y) = (numeral x XOR - numeral y) BIT True"
   303   "numeral (Num.Bit1 x) XOR - numeral (Num.Bit1 y) = (numeral x XOR - numeral (y + Num.One)) BIT 0"
   303   "numeral (Num.Bit1 x) XOR - numeral (Num.Bit1 y) = (numeral x XOR - numeral (y + Num.One)) BIT False"
   304   "- numeral (Num.Bit0 x) XOR numeral (Num.Bit0 y) = (- numeral x XOR numeral y) BIT 0"
   304   "- numeral (Num.Bit0 x) XOR numeral (Num.Bit0 y) = (- numeral x XOR numeral y) BIT False"
   305   "- numeral (Num.Bit0 x) XOR numeral (Num.Bit1 y) = (- numeral x XOR numeral y) BIT 1"
   305   "- numeral (Num.Bit0 x) XOR numeral (Num.Bit1 y) = (- numeral x XOR numeral y) BIT True"
   306   "- numeral (Num.Bit1 x) XOR numeral (Num.Bit0 y) = (- numeral (x + Num.One) XOR numeral y) BIT 1"
   306   "- numeral (Num.Bit1 x) XOR numeral (Num.Bit0 y) = (- numeral (x + Num.One) XOR numeral y) BIT True"
   307   "- numeral (Num.Bit1 x) XOR numeral (Num.Bit1 y) = (- numeral (x + Num.One) XOR numeral y) BIT 0"
   307   "- numeral (Num.Bit1 x) XOR numeral (Num.Bit1 y) = (- numeral (x + Num.One) XOR numeral y) BIT False"
   308   "- numeral (Num.Bit0 x) XOR - numeral (Num.Bit0 y) = (- numeral x XOR - numeral y) BIT 0"
   308   "- numeral (Num.Bit0 x) XOR - numeral (Num.Bit0 y) = (- numeral x XOR - numeral y) BIT False"
   309   "- numeral (Num.Bit0 x) XOR - numeral (Num.Bit1 y) = (- numeral x XOR - numeral (y + Num.One)) BIT 1"
   309   "- numeral (Num.Bit0 x) XOR - numeral (Num.Bit1 y) = (- numeral x XOR - numeral (y + Num.One)) BIT True"
   310   "- numeral (Num.Bit1 x) XOR - numeral (Num.Bit0 y) = (- numeral (x + Num.One) XOR - numeral y) BIT 1"
   310   "- numeral (Num.Bit1 x) XOR - numeral (Num.Bit0 y) = (- numeral (x + Num.One) XOR - numeral y) BIT True"
   311   "- numeral (Num.Bit1 x) XOR - numeral (Num.Bit1 y) = (- numeral (x + Num.One) XOR - numeral (y + Num.One)) BIT 0"
   311   "- numeral (Num.Bit1 x) XOR - numeral (Num.Bit1 y) = (- numeral (x + Num.One) XOR - numeral (y + Num.One)) BIT False"
   312   "(1::int) XOR numeral (Num.Bit0 y) = numeral (Num.Bit1 y)"
   312   "(1::int) XOR numeral (Num.Bit0 y) = numeral (Num.Bit1 y)"
   313   "(1::int) XOR numeral (Num.Bit1 y) = numeral (Num.Bit0 y)"
   313   "(1::int) XOR numeral (Num.Bit1 y) = numeral (Num.Bit0 y)"
   314   "(1::int) XOR - numeral (Num.Bit0 y) = - numeral (Num.BitM y)"
   314   "(1::int) XOR - numeral (Num.Bit0 y) = - numeral (Num.BitM y)"
   315   "(1::int) XOR - numeral (Num.Bit1 y) = - numeral (Num.Bit0 (y + Num.One))"
   315   "(1::int) XOR - numeral (Num.Bit1 y) = - numeral (Num.Bit0 (y + Num.One))"
   316   "numeral (Num.Bit0 x) XOR (1::int) = numeral (Num.Bit1 x)"
   316   "numeral (Num.Bit0 x) XOR (1::int) = numeral (Num.Bit1 x)"
   330   apply (case_tac y rule: bin_exhaust)
   330   apply (case_tac y rule: bin_exhaust)
   331   apply clarsimp
   331   apply clarsimp
   332   apply (unfold Bit_def)
   332   apply (unfold Bit_def)
   333   apply clarsimp
   333   apply clarsimp
   334   apply (erule_tac x = "x" in allE)
   334   apply (erule_tac x = "x" in allE)
   335   apply (simp add: bitval_def split: bit.split)
   335   apply simp
   336   done
   336   done
   337 
   337 
   338 lemma le_int_or:
   338 lemma le_int_or:
   339   "bin_sign (y::int) = 0 ==> x <= x OR y"
   339   "bin_sign (y::int) = 0 ==> x <= x OR y"
   340   apply (induct y arbitrary: x rule: bin_induct)
   340   apply (induct y arbitrary: x rule: bin_induct)
   383 lemmas bin_trunc_or = bin_trunc_ao(2) [THEN bintr_bintr_i]
   383 lemmas bin_trunc_or = bin_trunc_ao(2) [THEN bintr_bintr_i]
   384 
   384 
   385 subsection {* Setting and clearing bits *}
   385 subsection {* Setting and clearing bits *}
   386 
   386 
   387 primrec
   387 primrec
   388   bin_sc :: "nat => bit => int => int"
   388   bin_sc :: "nat => bool => int => int"
   389 where
   389 where
   390   Z: "bin_sc 0 b w = bin_rest w BIT b"
   390   Z: "bin_sc 0 b w = bin_rest w BIT b"
   391   | Suc: "bin_sc (Suc n) b w = bin_sc n b (bin_rest w) BIT bin_last w"
   391   | Suc: "bin_sc (Suc n) b w = bin_sc n b (bin_rest w) BIT bin_last w"
   392 
   392 
   393 (** nth bit, set/clear **)
   393 (** nth bit, set/clear **)
   394 
   394 
   395 lemma bin_nth_sc [simp]: 
   395 lemma bin_nth_sc [simp]: 
   396   "bin_nth (bin_sc n b w) n = (b = 1)"
   396   "bin_nth (bin_sc n b w) n \<longleftrightarrow> b"
   397   by (induct n arbitrary: w) auto
   397   by (induct n arbitrary: w) auto
   398 
   398 
   399 lemma bin_sc_sc_same [simp]: 
   399 lemma bin_sc_sc_same [simp]: 
   400   "bin_sc n c (bin_sc n b w) = bin_sc n c w"
   400   "bin_sc n c (bin_sc n b w) = bin_sc n c w"
   401   by (induct n arbitrary: w) auto
   401   by (induct n arbitrary: w) auto
   407    apply (case_tac [!] m)
   407    apply (case_tac [!] m)
   408      apply auto
   408      apply auto
   409   done
   409   done
   410 
   410 
   411 lemma bin_nth_sc_gen: 
   411 lemma bin_nth_sc_gen: 
   412   "bin_nth (bin_sc n b w) m = (if m = n then b = 1 else bin_nth w m)"
   412   "bin_nth (bin_sc n b w) m = (if m = n then b else bin_nth w m)"
   413   by (induct n arbitrary: w m) (case_tac [!] m, auto)
   413   by (induct n arbitrary: w m) (case_tac [!] m, auto)
   414   
   414   
   415 lemma bin_sc_nth [simp]:
   415 lemma bin_sc_nth [simp]:
   416   "(bin_sc n (If (bin_nth w n) 1 0) w) = w"
   416   "(bin_sc n (bin_nth w n) w) = w"
   417   by (induct n arbitrary: w) auto
   417   by (induct n arbitrary: w) auto
   418 
   418 
   419 lemma bin_sign_sc [simp]:
   419 lemma bin_sign_sc [simp]:
   420   "bin_sign (bin_sc n b w) = bin_sign w"
   420   "bin_sign (bin_sc n b w) = bin_sign w"
   421   by (induct n arbitrary: w) auto
   421   by (induct n arbitrary: w) auto
   426    apply (case_tac [!] w rule: bin_exhaust)
   426    apply (case_tac [!] w rule: bin_exhaust)
   427    apply (case_tac [!] m, auto)
   427    apply (case_tac [!] m, auto)
   428   done
   428   done
   429 
   429 
   430 lemma bin_clr_le:
   430 lemma bin_clr_le:
   431   "bin_sc n 0 w <= w"
   431   "bin_sc n False w <= w"
   432   apply (induct n arbitrary: w)
   432   apply (induct n arbitrary: w)
   433    apply (case_tac [!] w rule: bin_exhaust)
   433    apply (case_tac [!] w rule: bin_exhaust)
   434    apply (auto simp: le_Bits)
   434    apply (auto simp: le_Bits)
   435   done
   435   done
   436 
   436 
   437 lemma bin_set_ge:
   437 lemma bin_set_ge:
   438   "bin_sc n 1 w >= w"
   438   "bin_sc n True w >= w"
   439   apply (induct n arbitrary: w)
   439   apply (induct n arbitrary: w)
   440    apply (case_tac [!] w rule: bin_exhaust)
   440    apply (case_tac [!] w rule: bin_exhaust)
   441    apply (auto simp: le_Bits)
   441    apply (auto simp: le_Bits)
   442   done
   442   done
   443 
   443 
   444 lemma bintr_bin_clr_le:
   444 lemma bintr_bin_clr_le:
   445   "bintrunc n (bin_sc m 0 w) <= bintrunc n w"
   445   "bintrunc n (bin_sc m False w) <= bintrunc n w"
   446   apply (induct n arbitrary: w m)
   446   apply (induct n arbitrary: w m)
   447    apply simp
   447    apply simp
   448   apply (case_tac w rule: bin_exhaust)
   448   apply (case_tac w rule: bin_exhaust)
   449   apply (case_tac m)
   449   apply (case_tac m)
   450    apply (auto simp: le_Bits)
   450    apply (auto simp: le_Bits)
   451   done
   451   done
   452 
   452 
   453 lemma bintr_bin_set_ge:
   453 lemma bintr_bin_set_ge:
   454   "bintrunc n (bin_sc m 1 w) >= bintrunc n w"
   454   "bintrunc n (bin_sc m True w) >= bintrunc n w"
   455   apply (induct n arbitrary: w m)
   455   apply (induct n arbitrary: w m)
   456    apply simp
   456    apply simp
   457   apply (case_tac w rule: bin_exhaust)
   457   apply (case_tac w rule: bin_exhaust)
   458   apply (case_tac m)
   458   apply (case_tac m)
   459    apply (auto simp: le_Bits)
   459    apply (auto simp: le_Bits)
   460   done
   460   done
   461 
   461 
   462 lemma bin_sc_FP [simp]: "bin_sc n 0 0 = 0"
   462 lemma bin_sc_FP [simp]: "bin_sc n False 0 = 0"
   463   by (induct n) auto
   463   by (induct n) auto
   464 
   464 
   465 lemma bin_sc_TM [simp]: "bin_sc n 1 -1 = -1"
   465 lemma bin_sc_TM [simp]: "bin_sc n True -1 = -1"
   466   by (induct n) auto
   466   by (induct n) auto
   467   
   467   
   468 lemmas bin_sc_simps = bin_sc.Z bin_sc.Suc bin_sc_TM bin_sc_FP
   468 lemmas bin_sc_simps = bin_sc.Z bin_sc.Suc bin_sc_TM bin_sc_FP
   469 
   469 
   470 lemma bin_sc_minus:
   470 lemma bin_sc_minus:
   609   "bin_split n b = (b div 2 ^ n, b mod 2 ^ n)"
   609   "bin_split n b = (b div 2 ^ n, b mod 2 ^ n)"
   610   apply (induct n arbitrary: b, simp)
   610   apply (induct n arbitrary: b, simp)
   611   apply (simp add: bin_rest_def zdiv_zmult2_eq)
   611   apply (simp add: bin_rest_def zdiv_zmult2_eq)
   612   apply (case_tac b rule: bin_exhaust)
   612   apply (case_tac b rule: bin_exhaust)
   613   apply simp
   613   apply simp
   614   apply (simp add: Bit_def mod_mult_mult1 p1mod22k bitval_def
   614   apply (simp add: Bit_def mod_mult_mult1 p1mod22k)
   615               split: bit.split)
       
   616   done
   615   done
   617 
   616 
   618 subsection {* Miscellaneous lemmas *}
   617 subsection {* Miscellaneous lemmas *}
   619 
   618 
   620 lemma nth_2p_bin: 
   619 lemma nth_2p_bin: 
   630 
   629 
   631 lemma ex_eq_or:
   630 lemma ex_eq_or:
   632   "(EX m. n = Suc m & (m = k | P m)) = (n = Suc k | (EX m. n = Suc m & P m))"
   631   "(EX m. n = Suc m & (m = k | P m)) = (n = Suc k | (EX m. n = Suc m & P m))"
   633   by auto
   632   by auto
   634 
   633 
   635 lemma power_BIT: "2 ^ (Suc n) - 1 = (2 ^ n - 1) BIT 1"
   634 lemma power_BIT: "2 ^ (Suc n) - 1 = (2 ^ n - 1) BIT True"
   636   unfolding Bit_B1
   635   unfolding Bit_B1
   637   by (induct n) simp_all
   636   by (induct n) simp_all
   638 
   637 
   639 lemma mod_BIT:
   638 lemma mod_BIT:
   640   "bin BIT bit mod 2 ^ Suc n = (bin mod 2 ^ n) BIT bit"
   639   "bin BIT bit mod 2 ^ Suc n = (bin mod 2 ^ n) BIT bit"
   643   then have "bin mod 2 ^ n \<le> 2 ^ n - 1" by simp
   642   then have "bin mod 2 ^ n \<le> 2 ^ n - 1" by simp
   644   then have "2 * (bin mod 2 ^ n) \<le> 2 * (2 ^ n - 1)"
   643   then have "2 * (bin mod 2 ^ n) \<le> 2 * (2 ^ n - 1)"
   645     by (rule mult_left_mono) simp
   644     by (rule mult_left_mono) simp
   646   then have "2 * (bin mod 2 ^ n) + 1 < 2 * 2 ^ n" by simp
   645   then have "2 * (bin mod 2 ^ n) + 1 < 2 * 2 ^ n" by simp
   647   then show ?thesis
   646   then show ?thesis
   648     by (auto simp add: Bit_def bitval_def mod_mult_mult1 mod_add_left_eq [of "2 * bin"]
   647     by (auto simp add: Bit_def mod_mult_mult1 mod_add_left_eq [of "2 * bin"]
   649       mod_pos_pos_trivial split add: bit.split)
   648       mod_pos_pos_trivial)
   650 qed
   649 qed
   651 
   650 
   652 lemma AND_mod:
   651 lemma AND_mod:
   653   fixes x :: int
   652   fixes x :: int
   654   shows "x AND 2 ^ n - 1 = x mod 2 ^ n"
   653   shows "x AND 2 ^ n - 1 = x mod 2 ^ n"
   663 next
   662 next
   664   case (3 bin bit)
   663   case (3 bin bit)
   665   show ?case
   664   show ?case
   666   proof (cases n)
   665   proof (cases n)
   667     case 0
   666     case 0
   668     then show ?thesis by (simp add: int_and_extra_simps)
   667     then show ?thesis by simp
   669   next
   668   next
   670     case (Suc m)
   669     case (Suc m)
   671     with 3 show ?thesis
   670     with 3 show ?thesis
   672       by (simp only: power_BIT mod_BIT int_and_Bits) simp
   671       by (simp only: power_BIT mod_BIT int_and_Bits) simp
   673   qed
   672   qed