You are an expert Lean4 and formal verification agent proving a Lean4 theorem. Your output **must** strictly adhere to the specified format.

### Input Information
You will receive the following components, relevant to the target theorem:
* <all_available_defs>: Definitions available from imported modules (either from the current Lean repository or from Mathlib)
* <all_available_lemmas>: Lemmas/theorems available that may assist the proof.
* <local_ctx>...</local_ctx>: The local file context (imports, namespaces, definitions, comments, etc.) from the top of the file up to—but not including—the target theorem or any previously defined local lemmas/theorems.
* <target_theorem>...</target_theorem>: The target theorem statement, ending with `:=`.

**Notes**
1. Definitions include their full bodies, but for definitions whose bodies contain proofs, the proof parts are replaced by `admit` (i.e., admit /- proof elided -/), while the rest of the definition is kept unchanged; lemmas include only their statements.
2. You may freely reference any definition or lemma contained in these tags without redefining them.
3. The tags for available definitions and lemmas (all_available_defs, all_available_lemmas) may be omitted if empty.

### Output Format & Requirements
Your output MUST contain a complete, syntactically correct Lean 4 proof for the target theorem.

**Strict Output Structure:**
<reasoning> 
...
</reasoning> 

<lean4_invented_lemmas>
-- each lemma is a full Lean 4 declaration with a complete proof
...
</lean4_invented_lemmas>

<lean4_proof>
-- Lean 4 proof body of the target theorem
...
</lean4_proof>

**Requirements:**
1. <reasoning> and <lean4_invented_lemmas> are OPTIONAL. Include them only if they aid proof construction.
2. <lean4_proof> MUST contain only the proof body (tactics/terms), starting by "by", NOT the theorem declaration.
3. <lean4_invented_lemmas> (if present) MUST contain syntactically correct lemma declarations that type checks AND complete proof bodies. Defining a lemma using `axiom` is NOT allowed.
4. <reasoning> contains high-level proof planning.
5. If you create a lemma under <lean4_invented_lemmas> whose name is namespaced (e.g., X.Y.Z), you MUST always refer to it using its fully qualified name. Do NOT rely on shortened names. For example, write rw [X.Y.Z], not rw [Z] for invented lemmas.
6. All Lean 4 code MUST be syntactically correct. No `sorry`, `admit`, or non-Lean text. Comments allowed using `--` or `/- ... -/`.
7. Follow the tags and structure EXACTLY. No extra text before, between, or after the sections.
8. Do NOT wrap invented lemmas in a `mutual` block unless they have genuine mutual recursion. Declare each lemma independently.

### Examples are provided here (example input are under "User Prompt", and example assistant response are under "Agent Response"):
Example 1 ------------------- 
User Prompt:
<all_available_defs>
structure BitVec (w : Nat) where
  /-- Construct a `BitVec w` from a number less than `2^w`.
  O(1), because we use `Fin` as the internal representation of a bitvector. -/
  ofFin ::

  /-- Interpret a bitvector as a number less than `2^w`.
  O(1), because we use `Fin` as the internal representation of a bitvector. -/
  toFin : Fin (hPow 2 w)
</all_available_defs>

<all_available_lemmas>
theorem List.getElem_append_left{α : Type u_1} {l₁ l₂ : List α} {i : Nat} (hn : i < l₁.length) : (l₁ ++ l₂)[i] = l₁[i]
theorem getElem_eq_testBit_toNat (x : BitVec w) (i : Nat) (h : i < w) :
  x[i] = x.toNat.testBit i := rfl
@[simp, grind =] theorem toNat_cons (b : Bool) (x : BitVec w) :
    (cons b x).toNat = (b.toNat <<< w) ||| x.toNat
@[simp, grind =] theorem getLsbD_of_ge (x : BitVec w) (i : Nat) (ge : w ≤ i) : getLsbD x i = false
theorem testBit_toNat (x : BitVec w) : x.toNat.testBit i = x.getLsbD i
</all_available_lemmas>

<local_ctx>
import Mathlib.Computability.NFA
import Mathlib.Data.FinEnum
import Mathlib.Data.Rel
import Mathlib.Data.Vector.Basic
import Blase.AutoStructs.ForLean

open Set
open Mathlib
open SetRel

-- this is better because card is defeq to n
instance (α : Type) : Inter (Language α) := ⟨Set.inter⟩
instance (α : Type) : Union (Language α) := ⟨Set.union⟩

/--
The set of `n`-tuples of bit vectors of an arbitrary width.
-/
structure BitVecs (n : Nat) where
  w : Nat
  bvs : List.Vector (BitVec w) n

def BitVecs.cast (bvs : BitVecs n) (h : n = n') : BitVecs n' :=
  { w := bvs.w, bvs := h ▸ bvs.bvs }

abbrev BitVecs.empty : BitVecs n := ⟨0, List.Vector.replicate n .nil⟩
abbrev BitVecs.singleton {w : Nat} (bv : BitVec w) : BitVecs 1 := ⟨w, bv ::ᵥ .nil⟩
abbrev BitVecs.pair {w : Nat} (bv1 bv2 : BitVec w) : BitVecs 2 := ⟨w, bv1 ::ᵥ bv2 ::ᵥ .nil⟩

/--
The set of `n`-tuples of bit vectors of an arbitrary width, encoded as a list of
bit vectors of width `n`. The width of the encoded bit vectors is the length of
the list.
-/
abbrev BitVecs' (n : Nat) := List (BitVec n)

@[simps]
def dec (bvs' : BitVecs' n) : BitVecs n where
  w := bvs'.length
  bvs := List.Vector.ofFn fun k => BitVec.ofFn fun i => bvs'[i].getLsbD k

@[simp]
</local_ctx>

<target_theorem>
lemma dec_snoc n (bvs' : BitVecs' n) (a : BitVec n) :
  dec (bvs' ++ [a]) =
    { w := bvs'.length + 1
      bvs := List.Vector.ofFn fun k =>
        BitVec.cons (a.getLsbD k) ((dec bvs').bvs.get k) } :=
</target_theorem>

Agent Response:
<reasoning> 
The goal is to understand what `dec` does after appending one more bitvector `a` to `bvs'`. By definition, `dec` builds a width `= length` and a vector of bitvectors whose `i`-th bit at position `k` is `bvs'[i].getLsbD k`. So for `bvs' ++ [a]`, we expect the width to increase by 1 and each resulting bitvector to be `BitVec.cons` of the new bit coming from `a`.

First, I use `ext` twice: once on the record to focus on the `bvs` field, and once on the resulting bitvector. This reduces everything to a pointwise statement:
for fixed `k` and `i` with `i < bvs'.length + 1`,
the bit `(bvs' ++ [a])[i].getLsbD k` should match the bit at index `i` of `BitVec.cons (a.getLsbD k) ((dec bvs').bvs.get k)`.

At this point I need a clean description of indexing into `BitVec.cons`: if we have `x : BitVec n`, then `(cons b x)[i]` should give `b` at the new “last” index `n` and `x[i]` otherwise. That motivates an auxiliary lemma `getElem_cons` expressing exactly this behavior, proved via the `testBit`/`toNat` characterization and a case split on `i < n`, `i = n`, `i > n`.

Using `getElem_cons`, the RHS becomes an `if` on whether `i = bvs'.length`. So I split into cases:
- If `i = bvs'.length`, then `(bvs' ++ [a])[i]` is the appended `a`, so both sides reduce to `a.getLsbD k`.
- If `i ≠ bvs'.length`, the bound `i < bvs'.length + 1` forces `i < bvs'.length`. Then `(bvs' ++ [a])[i] = bvs'[i]` by `List.getElem_append_left`, and the RHS takes the “else” branch and likewise gives the bit from `bvs'[i]`. In both subcases, `simp` (plus the definition of `dec`) finishes.

So the whole proof is: `ext` to bit level, unfold `dec` with `simp_all`, rewrite with `getElem_cons`, split on the boundary index `i = length bvs'`, and in the “< length” branch use `List.getElem_append_left` and bounds to line up both sides.
</reasoning> 

<lean4_invented_lemmas>
@[grind =]
theorem getElem_cons {b : Bool} {n} {x : BitVec n} {i : Nat} (h : i < n + 1) :
    (cons b x)[i] = if h : i = n then b else x[i] := by
  simp only [BitVec.getElem_eq_testBit_toNat, BitVec.toNat_cons, Nat.testBit_or]
  rw [Nat.testBit_shiftLeft]
  rcases Nat.lt_trichotomy i n with i_lt_n | i_eq_n | n_lt_i
  · have p1 : ¬(n ≤ i) := by omega
    have p2 : i ≠ n := by omega
    simp [p1, p2]
  · simp only [i_eq_n, ge_iff_le, Nat.le_refl, decide_true, Nat.sub_self, Nat.testBit_zero,
    Bool.true_and, BitVec.testBit_toNat, BitVec.getLsbD_of_ge, Bool.or_false]
    cases b <;> trivial
  · have p1 : i ≠ n := by omega
    have p2 : i - n ≠ 0 := by omega
    simp [p1, p2, Nat.testBit_bool_toNat]
</lean4_invented_lemmas>

<lean4_proof>
by
  ext k i hi <;> simp_all
  rw [getElem_cons]
  split
  next heq => simp_all
  next h =>
    have hlt : i < List.length bvs' := by simp at hi; omega
    rw [List.getElem_append_left hlt]
    simp
</lean4_proof>

### Your task:
<all_available_defs>
Vector in Init.Data.Vector.Basic
Fin in Init.Prelude
String in Init.Prelude
Unit in Init.Prelude
List in Init.Prelude
Field in Mathlib.Algebra.Field.Defs
Bool in Init.Prelude
DecidableEq in Init.Prelude
FinEnum in Mathlib.Data.FinEnum
Hashable in Init.Prelude
Sum.inl in Init.Core
Sum.inr in Init.Core
Nat in Init.Prelude
Repr in Init.Data.Repr
Sum in Init.Core
Sum.elim in Init.Data.Sum.Basic
id in Init.Prelude
Nat.max in Init.Data.Nat.Basic
Nat.min in Init.Data.Nat.Basic
Decidable in Init.Prelude

syntax "min" : MLIR.Pretty.uniform_op

macro_rules
  | `(mlir_op| $res:mlir_op_operand = const ($x)
      $[: $outer_type]? ) => do
      let outer_type ← outer_type.getDM `(mlir_type| _)
      `(mlir_op| $res:mlir_op_operand = "const"()
          {val = $x:num : $outer_type} : ($outer_type) -> ($outer_type) )

macro_rules
  | `(mlir_op| $res:mlir_op_operand = li ($x)
     $[: $outer_type]?  ) => do
      let outer_type ← outer_type.getDM `(mlir_type| _ )
      `(mlir_op| $res:mlir_op_operand = "li"()
          {imm = $x:num : $outer_type } : ($outer_type) -> ($outer_type))

macro_rules
| `(mlir_op| $res:mlir_op_operand = $op1:MLIR.Pretty.RV.opWithImmediate $reg1 , $x : $t)  => do
    let some opName := MLIR.EDSL.Pretty.extractOpName op1.raw
      | Macro.throwUnsupported
    `(mlir_op| $res:mlir_op_operand = $opName ($reg1) {imm = $x:num : $t} : ($t) -> ($t) )

macro_rules
| `(mlir_op| $res:mlir_op_operand = $op1:MLIR.Pretty.RV.opWithShamt $reg1 , $x  : $t )  => do
    let some opName := MLIR.EDSL.Pretty.extractOpName op1.raw
      | Macro.throwUnsupported
    `(mlir_op| $res:mlir_op_operand = $opName ($reg1) {shamt = $x:num : $t}  : ($t) -> ($t) )

def ls (b : Bool) : FSM Unit :=
  { α := Unit,
    initCarry := fun _ => b,
    nextStateCirc := fun () => Circuit.var true (inr ()),
    outputCirc := Circuit.var true (inl ())
  }

structure FSM (arity : Type) : Type 1 where
   
  ( α  : Type )
  [ i : FinEnum α ]
  [ h : Hashable α ]
  [ dec_eq : DecidableEq α ]
   
  ( initCarry : α → Bool )
   
  outputCirc : Circuit (α ⊕ arity)
  nextStateCirc : α → Circuit (α ⊕ arity)

inductive Circuit (α : Type u) : Type u
  | tru : Circuit α
  | fals : Circuit α
   
  | var : (positive: Bool) → α → Circuit α
  | and : Circuit α → Circuit α → Circuit α
  | or : Circuit α → Circuit α → Circuit α
  | xor : Circuit α → Circuit α → Circuit α
deriving Repr, DecidableEq

def Var (Γ : Context Ty) (ty : Ty) : Type := { v : VarName // Γ.hasType v ty }

inductive StateSpace (wcard tcard bcard ncard icard pcard : Nat)
| widthVar (v : Fin wcard)
| termVar (v : Fin tcard)
| predVar (v : Fin pcard)
| boolVar (v : Fin bcard)
deriving DecidableEq, Repr, Hashable

inductive Term
| ofNat (w : WidthExpr) (n : Nat) : Term
| var (v : Nat) (w : WidthExpr) : Term
| add (w : WidthExpr) (a b : Term) : Term
| zext (a : Term) (wnew : WidthExpr) : Term
| setWidth (a : Term) (wnew : WidthExpr) : Term
| sext (a : Term) (wnew : WidthExpr) : Term
| bor (w : WidthExpr) (a b : Term) : Term
| band (w : WidthExpr) (a b : Term) : Term
| bxor (w : WidthExpr) (a b : Term) : Term
| bnot (w : WidthExpr)  (a : Term) : Term
| boolVar (v : Nat) : Term
| boolConst (b : Bool) : Term
| shiftl (w : WidthExpr) (a : Term) (k : Nat) : Term
| bvOfBool (b : Term) : Term
| binWidthRel (k : WidthBinaryRelationKind) (wa wb : WidthExpr) : Term
| binRel (k : BinaryRelationKind) (w : WidthExpr)
    (a : Term) (b : Term) : Term
| or (p1 p2 : Term) : Term
| and (p1 p2 : Term) : Term
| pvar (v : Nat) : Term
| boolBinRel (k : BoolBinaryRelationKind)
    (a b : Term) : Term
deriving DecidableEq, Inhabited, Repr, Lean.ToExpr

def composeUnaryAux
    (p : FSM Unit)
    (q : FSM arity) :
    FSM arity :=
  p.compose
    arity
    _
    (λ _ => id)
    (λ _ => q)

def compose [FinEnum arity] [DecidableEq arity] [Hashable arity]
    (new_arity : Type)        
    (q_arity : arity → Type)  
    (vars : ∀ (a : arity), q_arity a → new_arity)
    
    
    (q : ∀ (a : arity), FSM (q_arity a)) : 
    FSM new_arity :=
  { α := p.α ⊕ (Σ a, (q a).α),
    i := by admit /- proof elided -/

structure NatFSM (wcard tcard bcard ncard icard pcard : Nat) (v : Nondep.WidthExpr) where
  toFsm : FSM (StateSpace wcard tcard bcard ncard icard pcard)

inductive WidthExpr where
| const : Nat → WidthExpr
| var : Nat → WidthExpr
| max : WidthExpr → WidthExpr → WidthExpr
| min : WidthExpr → WidthExpr → WidthExpr
| addK : WidthExpr → Nat → WidthExpr
| kadd : Nat → WidthExpr → WidthExpr
deriving Inhabited, Repr, Hashable, DecidableEq, Lean.ToExpr

def scanOr  : FSM Unit :=
  {
   α := Unit,
   initCarry := fun () => false,
   outputCirc := Circuit.var true (inl ()) ||| Circuit.var true (inr ()),
   nextStateCirc := fun () => Circuit.var true (inl ()) ||| Circuit.var true (inr ())
  }

abbrev WidthExpr.Env (wcard : Nat) : Type :=
  Fin wcard → Nat

structure HWidthEnv {wcard tcard : Nat}
    (fsmEnv : StateSpace wcard tcard bcard ncard icard pcard → BitStream)
    (wenv : Fin wcard → Nat) : Prop where
    heq_width : ∀ (v : Fin wcard),
      fsmEnv (StateSpace.widthVar v) = BitStream.ofNatUnary (wenv v)

structure HPredicateEnv {wcard tcard bcard ncard icard pcard : Nat}
    (fsmEnv : StateSpace wcard tcard bcard ncard icard pcard → BitStream)
    (penv : Fin pcard → Prop) : Prop where
    heq_width : ∀ (v : Fin pcard),
      fsmEnv (StateSpace.predVar v) = BitStream.ofProp (penv v)

def BitStream : Type := Nat → Bool

abbrev ofNatUnary (n : Nat) : BitStream :=
  fun i => decide (i < n)

structure HNatFSMToBitstream {wcard : Nat} {v : WidthExpr wcard} {tcard : Nat} {bcard : Nat} {pcard : Nat}
   (fsm : NatFSM wcard tcard bcard ncard icard pcard (.ofDep v)) : Prop where
  heq :
    ∀ (wenv : Fin wcard → Nat)
    (fsmEnv : StateSpace wcard tcard bcard ncard icard pcard → BitStream),
    (henv : HWidthEnv fsmEnv wenv) →
      fsm.toFsm.eval fsmEnv =
      BitStream.ofNatUnary (v.toNat wenv)

def WidthExpr.toNat (e : WidthExpr wcard) (env : WidthExpr.Env wcard) : Nat :=
  match e with
  | .const n => n
  | .var v => env v
  | .min v w => Nat.min (v.toNat env) (w.toNat env)
  | .max v w => Nat.max (v.toNat env) (w.toNat env)
  | .addK v k => v.toNat env + k
  | .kadd k v => k + v.toNat env

inductive WidthExpr (wcard : Nat) : Type
| const (n : Nat) :  WidthExpr wcard
| var : (v : Fin wcard) → WidthExpr wcard
| min : (v w : WidthExpr wcard) → WidthExpr wcard
| max : (v w : WidthExpr wcard) → WidthExpr wcard
| addK : (v : WidthExpr wcard) → (k : Nat) → WidthExpr wcard
| kadd : (k : Nat) → (v : WidthExpr wcard) → WidthExpr wcard

structure HPredFSMToBitStream {pcard : Nat}
  {tctx : Term.Ctx wcard tcard}
  {p : Term bcard ncard icard pcard tctx .prop}
  (fsm : TermFSM wcard tcard bcard ncard icard pcard
    (.ofDepTerm p)) : Prop where
  heq :
    ∀ {wenv : WidthExpr.Env wcard}
      (benv : Term.BoolEnv bcard)
      (nenv : Term.NatEnv ncard)
      (ienv : Term.IntEnv icard)
      (penv : Predicate.Env pcard) (tenv : tctx.Env wenv)
      (fsmEnv : StateSpace wcard tcard bcard ncard icard pcard → BitStream),
      (htenv : HTermEnv fsmEnv tenv benv) →
      (hpenv : HPredicateEnv fsmEnv penv) →
        p.toBV benv nenv ienv penv tenv  ↔ (fsm.toFsmZext.eval fsmEnv = .negOne)

def scanOr (s : BitStream) : BitStream := scanl false Bool.or s

abbrev scanl (init : Bool) (f : Bool → Bool → Bool) (s : BitStream) : BitStream :=
  fun n => match n with
    | 0 => f init (s 0)
    | n+1 => f (scanl init f s n) (s (n + 1))

def test1_after := [llvm|
{
^0(%arg19 : i32, %arg20 : i8):
  %0 = llvm.mlir.constant(1 : i32) : i32
  %1 = llvm.zext nneg %arg20 : i8 to i32
  %2 = llvm.lshr %arg19, %1 : i32
  %3 = llvm.and %2, %0 : i32
  "llvm.return"(%3) : (i32) -> ()
}
]

def sge_swap_or_max_logical_before := [llvm|
{
^0(%arg180 : i8, %arg181 : i8):
  %0 = llvm.mlir.constant(127 : i8) : i8
  %1 = llvm.mlir.constant(true) : i1
  %2 = llvm.icmp "sle" %arg181, %arg180 : i8
  %3 = llvm.icmp "eq" %arg180, %0 : i8
  %4 = "llvm.select"(%2, %1, %3) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i1, i1) -> i1
  "llvm.return"(%4) : (i1) -> ()
}
]

def negation_of_increment_via_or_with_no_common_bits_set_before := [llvm|
{
^0(%arg87 : i8, %arg88 : i8):
  %0 = llvm.mlir.constant(1 : i8) : i8
  %1 = llvm.shl %arg88, %0 : i8
  %2 = llvm.or %1, %0 : i8
  %3 = llvm.sub %arg87, %2 : i8
  "llvm.return"(%3) : (i8) -> ()
}
]

def foo_before := [llvm|
{
^0(%arg0 : i32):
  %0 = llvm.mlir.constant(0 : i32) : i32
  %1 = llvm.mlir.constant(7 : i32) : i32
  %2 = llvm.or %0, %1 : i32
  %3 = llvm.and %arg0, %2 : i32
  "llvm.return"(%3) : (i32) -> ()
}
]

def t3_c0_after := [llvm|
{
^0(%arg25 : i8, %arg26 : i8):
  %0 = llvm.mlir.constant(42 : i8) : i8
  %1 = llvm.add %arg25, %arg26 : i8
  %2 = llvm.sub %0, %1 : i8
  "llvm.return"(%2) : (i8) -> ()
}
]

@[simp, reducible]
instance : DialectDenote RV64 where
  denote o args _ := [o.denote args]ₕ

def or_shl_before := [llvm|
{
^0(%arg640 : i8, %arg641 : i8, %arg642 : i8, %arg643 : i8):
  %0 = llvm.shl %arg640, %arg643 : i8
  %1 = llvm.shl %arg641, %arg643 : i8
  %2 = llvm.or %0, %arg642 : i8
  %3 = llvm.or %2, %1 : i8
  "llvm.return"(%3) : (i8) -> ()
}
]

def icmp_equality_test_wrong_and_before := [llvm|
{
^0(%arg6 : i64, %arg7 : i64, %arg8 : i64):
  %0 = llvm.mlir.constant(true) : i1
  %1 = llvm.mlir.constant(false) : i1
  %2 = llvm.icmp "eq" %arg6, %arg8 : i64
  %3 = llvm.icmp "eq" %arg7, %arg8 : i64
  %4 = llvm.icmp "eq" %arg6, %arg7 : i64
  %5 = llvm.xor %3, %0 : i1
  %6 = "llvm.select"(%5, %1, %4) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i1, i1) -> i1
  %7 = "llvm.select"(%2, %3, %6) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i1, i1) -> i1
  "llvm.return"(%7) : (i1) -> ()
}
]

def test9_after := [llvm|
{
^0(%arg45 : i1):
  %0 = llvm.mlir.constant(false) : i1
  "llvm.return"(%0) : (i1) -> ()
}
]

def sub_from_constant_of_sub_from_constant_before := [llvm|
{
^0(%arg170 : i8):
  %0 = llvm.mlir.constant(42 : i8) : i8
  %1 = llvm.mlir.constant(11 : i8) : i8
  %2 = llvm.sub %0, %arg170 : i8
  %3 = llvm.sub %1, %2 : i8
  "llvm.return"(%3) : (i8) -> ()
}
]

def bools2_logical_commute0_and1_after := [llvm|
{
^0(%arg61 : i1, %arg62 : i1, %arg63 : i1):
  %0 = "llvm.select"(%arg63, %arg61, %arg62) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i1, i1) -> i1
  "llvm.return"(%0) : (i1) -> ()
}
]

def shl_nsw_nuw_add_nsw_before := [llvm|
{
^0(%arg13 : i32):
  %0 = llvm.mlir.constant(1 : i32) : i32
  %1 = llvm.mlir.constant(-1 : i32) : i32
  %2 = llvm.shl %0, %arg13 overflow<nsw,nuw> : i32
  %3 = llvm.add %2, %1 overflow<nsw> : i32
  "llvm.return"(%3) : (i32) -> ()
}
]

def liRiscv_24 := [LV| {
  ^entry ():
    %0 = "li"() {imm = -24 : !i64} : (!i64) -> (!i64)
    %1 = "builtin.unrealized_conversion_cast"(%0) : (!i64) -> (i64)
    llvm.return %1 : i64
  }]

def shrink_and_after := [llvm|
{
^0(%arg9 : i64):
  %0 = llvm.mlir.constant(42) : i64
  %1 = llvm.and %arg9, %0 : i64
  %2 = llvm.trunc %1 overflow<nsw,nuw> : i64 to i31
  "llvm.return"(%2) : (i31) -> ()
}
]

def ashrsgt_03_14_exact_after := [llvm|
{
^0(%arg55 : i4):
  %0 = llvm.mlir.constant(true) : i1
  "llvm.return"(%0) : (i1) -> ()
}
]

def select_icmp_eq_and_1_0_or_2_after := [llvm|
{
^0(%arg255 : i32, %arg256 : i32):
  %0 = llvm.mlir.constant(1 : i32) : i32
  %1 = llvm.mlir.constant(2 : i32) : i32
  %2 = llvm.shl %arg255, %0 : i32
  %3 = llvm.and %2, %1 : i32
  %4 = llvm.or %arg256, %3 : i32
  "llvm.return"(%4) : (i32) -> ()
}
]

def bitwise_and_logical_and_masked_icmp_allones_poison1_before := [llvm|
{
^0(%arg136 : i1, %arg137 : i32, %arg138 : i32):
  %0 = llvm.mlir.constant(false) : i1
  %1 = llvm.mlir.constant(7 : i32) : i32
  %2 = llvm.and %arg137, %arg138 : i32
  %3 = llvm.icmp "eq" %2, %arg138 : i32
  %4 = "llvm.select"(%3, %arg136, %0) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i1, i1) -> i1
  %5 = llvm.and %arg137, %1 : i32
  %6 = llvm.icmp "eq" %5, %1 : i32
  %7 = llvm.and %4, %6 : i1
  "llvm.return"(%7) : (i1) -> ()
}
]

def t1_sshr_before := [llvm|
{
^0(%arg28 : i32, %arg29 : i32):
  %0 = llvm.mlir.constant(-1 : i32) : i32
  %1 = llvm.shl %0, %arg29 : i32
  %2 = llvm.and %1, %arg28 : i32
  %3 = llvm.ashr exact %2, %arg29 : i32
  "llvm.return"(%3) : (i32) -> ()
}
]

def or_not_and_and_not_and_xor_commute3_after := [llvm|
{
^0(%arg280 : i32, %arg281 : i32, %arg282 : i32):
  %0 = llvm.mlir.constant(-1 : i32) : i32
  %1 = llvm.and %arg281, %arg282 : i32
  %2 = llvm.xor %1, %0 : i32
  %3 = llvm.or %arg280, %2 : i32
  %4 = llvm.xor %arg282, %arg281 : i32
  %5 = llvm.and %4, %arg280 : i32
  %6 = llvm.xor %5, %3 : i32
  "llvm.return"(%6) : (i32) -> ()
}
]

def n5_after := [llvm|
{
^0(%arg9 : i8, %arg10 : i8, %arg11 : i8):
  "llvm.return"(%arg11) : (i8) -> ()
}
]

def ashrslt_03_01_exact_before := [llvm|
{
^0(%arg20 : i4):
  %0 = llvm.mlir.constant(3 : i4) : i4
  %1 = llvm.mlir.constant(1 : i4) : i4
  %2 = llvm.ashr exact %arg20, %0 : i4
  %3 = llvm.icmp "slt" %2, %1 : i4
  "llvm.return"(%3) : (i1) -> ()
}
]

def alive_AddSub_1043_tgt := [sllvm| {
^bb0(%C1 : i64, %Z : i64, %RHS : i64):
  %v1 = llvm.not %C1 : i64
  %v2 = llvm.or %Z, %v1 : i64
  %v3 = llvm.and %Z, %C1 : i64
  %v4 = llvm.xor %v3, %C1 : i64
  %v5 = llvm.mlir.constant 1 : i64
  %v6 = llvm.add %v4, %v5 : i64
  %v7 = llvm.sub %RHS, %v2 : i64
  llvm.return %v7 : i64
}]

partial def reflectPredicateAux (exprToIx : ReflectMap) (e : Expr) (wExpected : Expr) : MetaM (ReflectResult Predicate) := do
  match_expr e with
  | Eq α a b =>
    match_expr α with
    | Nat =>
       
      
      if wExpected != a then
        throwError m!"Only Nat expressions allowed are '{wExpected} ≠ <concrete value>'. Found {indentD e}."
      let some natVal ← Lean.Meta.getNatValue? b
        | throwError m!"Expected '{wExpected} ≠ <concrete width>', found symbolic width {indentD b}."
      let out := Predicate.width .eq natVal
      return { exprToIx := exprToIx, e := out }

    | BitVec w =>
      let a ←  reflectTermUnchecked exprToIx w a
      let b ← reflectTermUnchecked a.exprToIx w b
      return { exprToIx := b.exprToIx, e := Predicate.binary .eq a.e b.e }
    | Bool =>
      
      
      
      
      let_expr true := b
        | throwError m!"only boolean conditionals allowed are 'bv.\{u,s}l\{t,e} bv = true'. Found {indentD e}."
      match_expr a with
      | BitVec.slt w a b =>
        let a ← reflectTermUnchecked exprToIx w a
        let b ← reflectTermUnchecked a.exprToIx w b
        return { exprToIx := b.exprToIx, e := Predicate.binary .slt a.e b.e }
      | BitVec.sle w a b =>
        let a ← reflectTermUnchecked exprToIx w a
        let b ← reflectTermUnchecked a.exprToIx w b
        return { exprToIx := b.exprToIx, e := Predicate.binary .sle a.e b.e }
      | BitVec.ult w a b =>
        let a ← reflectTermUnchecked exprToIx w a
        let b ← reflectTermUnchecked a.exprToIx w b
        return { exprToIx := b.exprToIx, e := Predicate.binary .ult a.e b.e }
      | BitVec.ule w a b =>
        let a ← reflectTermUnchecked exprToIx w a
        let b ← reflectTermUnchecked a.exprToIx w b
        return { exprToIx := b.exprToIx, e := Predicate.binary .ule a.e b.e }
      | _ =>
        throwError m!"unknown boolean conditional, expected 'bv.slt bv = true' or 'bv.sle bv = true'. Found {indentD e}"
    | _ =>
      throwError m!"unknown equality kind, expected 'bv = bv' or 'bv.slt bv = true' or 'bv.sle bv = true'. Found {indentD e}"
  | Ne α a b =>
     
    match_expr α with
    | Nat => do
      
      if wExpected != a then
        throwError m!"Only Nat expressions allowed are '{wExpected} ≠ <concrete value>'. Found {indentD e}."
      let some natVal ← Lean.Meta.getNatValue? b
        | throwError m!"Expected '{wExpected} ≠ <concrete width>', found symbolic width {indentD b}."
      let out := Predicate.width .neq natVal
      return { exprToIx := exprToIx, e := out }
    | BitVec w =>
      let a ← reflectTermUnchecked exprToIx w a
      let b ← reflectTermUnchecked a.exprToIx w b
      return { exprToIx := b.exprToIx, e := Predicate.binary .neq a.e b.e }
    | _ =>
      throwError m!"Expected typeclass to be 'BitVec w' / 'Nat', found '{indentD α}' in {e} when matching against 'Ne'"
  | LT.lt α _inst a b =>
    let_expr BitVec w := α | throwError m!"Expected typeclass to be BitVec w, found '{indentD α}' in {indentD e} when matching against 'LT.lt'"
    let a ← reflectTermUnchecked exprToIx w a
    let b ← reflectTermUnchecked a.exprToIx w b
    return { exprToIx := b.exprToIx, e := Predicate.binary .ult a.e b.e }
  | LE.le α _inst a b =>
    let_expr BitVec w := α | throwError m!"Expected typeclass to be BitVec w, found '{indentD α}' in {indentD e} when matching against 'LE.le'"
    let a ← reflectTermUnchecked exprToIx w a
    let b ← reflectTermUnchecked a.exprToIx w b
    return { exprToIx := b.exprToIx, e := Predicate.binary .ule a.e b.e }
  | Or p q =>
    let p ← reflectPredicateAux exprToIx p wExpected
    let q ← reflectPredicateAux p.exprToIx q wExpected
    let out := Predicate.lor p.e q.e
    return { q with e := out }
  | And p q =>
    let p ← reflectPredicateAux exprToIx p wExpected
    let q ← reflectPredicateAux p.exprToIx q wExpected
    let out := Predicate.land p.e q.e
    return { q with e := out }
  | _ =>
     throwError m!"expected predicate over bitvectors (no quantification), found:  {indentD e}"

def select_sub_icmp_bad_before := [llvm|
{
^0(%arg71 : i32, %arg72 : i32, %arg73 : i32):
  %0 = llvm.mlir.constant(0 : i32) : i32
  %1 = llvm.icmp "eq" %arg71, %0 : i32
  %2 = llvm.sub %arg71, %arg73 : i32
  %3 = "llvm.select"(%1, %2, %arg72) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i32, i32) -> i32
  "llvm.return"(%3) : (i32) -> ()
}
]

def slt_or_not_max_logical_before := [llvm|
{
^0(%arg60 : i8, %arg61 : i8):
  %0 = llvm.mlir.constant(127 : i8) : i8
  %1 = llvm.mlir.constant(true) : i1
  %2 = llvm.icmp "slt" %arg60, %arg61 : i8
  %3 = llvm.icmp "ne" %arg60, %0 : i8
  %4 = "llvm.select"(%2, %1, %3) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i1, i1) -> i1
  "llvm.return"(%4) : (i1) -> ()
}
]

BitVec.add in Init.Data.BitVec.BasicAux

abbrev Com (Γ) (ty) := _root_.Com ExOp Γ .pure ty

def positive_with_aggressive_icmp_before := [llvm|
{
^0(%arg56 : i32):
  %0 = llvm.mlir.constant(128 : i32) : i32
  %1 = llvm.mlir.constant(256 : i32) : i32
  %2 = llvm.mlir.constant(512 : i32) : i32
  %3 = llvm.icmp "ult" %arg56, %0 : i32
  %4 = llvm.add %arg56, %1 : i32
  %5 = llvm.icmp "ult" %4, %2 : i32
  %6 = llvm.and %3, %5 : i1
  "llvm.return"(%6) : (i1) -> ()
}
]

def test_shl_nsw__none_are_safe_before := [llvm|
{
^0(%arg66 : i32, %arg67 : i64):
  %0 = llvm.mlir.constant(-2 : i32) : i32
  %1 = llvm.mlir.constant(2 : i32) : i32
  %2 = llvm.mlir.constant(0 : i32) : i32
  %3 = llvm.and %arg66, %0 : i32
  %4 = llvm.shl %3, %1 overflow<nsw> : i32
  %5 = llvm.zext %4 : i32 to i64
  %6 = llvm.icmp "eq" %3, %2 : i32
  %7 = llvm.ashr %arg67, %5 : i64
  %8 = "llvm.select"(%6, %arg67, %7) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i64, i64) -> i64
  "llvm.return"(%8) : (i64) -> ()
}
]

def or_and_or_pat4_after := [llvm|
{
^0(%arg26 : i8, %arg27 : i8, %arg28 : i8, %arg29 : i8):
  %0 = llvm.mlir.constant(42 : i8) : i8
  %1 = llvm.udiv %0, %arg28 : i8
  %2 = llvm.or %arg29, %arg26 : i8
  %3 = llvm.and %2, %arg27 : i8
  %4 = llvm.or %1, %3 : i8
  "llvm.return"(%4) : (i8) -> ()
}
]

ShiftLeft in Init.Prelude

def mkInitCarryAssignCircuitAux {arity : Type _}
  [DecidableEq arity]
  [Fintype arity]
  [Hashable arity]
  (p : FSM arity) (s : p.α):
  Circuit (Vars p.α arity 0) :=
    Circuit.xor
      (Circuit.ofBool (p.initCarry s))
      (Circuit.var true <| Vars.stateN s 0)

@[simp_denote]
def slt_llvm_i64 := [LV| {
    ^entry (%a: i64, %b: i64):
    %0 = llvm.icmp.slt %a, %b : i64
    %1 = llvm.zext %0 : i1 to i64
    llvm.return %1 : i64
  }]

def and_zext_eq_odd_after := [llvm|
{
^0(%arg31 : i32):
  %0 = llvm.mlir.constant(3 : i32) : i32
  %1 = llvm.icmp "eq" %arg31, %0 : i32
  %2 = llvm.zext %1 : i1 to i32
  "llvm.return"(%2) : (i32) -> ()
}
]

def bitwise_and_bitwise_and_icmps_comm1_after := [llvm|
{
^0(%arg241 : i8, %arg242 : i8, %arg243 : i8):
  %0 = llvm.mlir.constant(42 : i8) : i8
  %1 = llvm.mlir.constant(1 : i8) : i8
  %2 = llvm.icmp "eq" %arg242, %0 : i8
  %3 = llvm.shl %1, %arg243 overflow<nuw> : i8
  %4 = llvm.or %3, %1 : i8
  %5 = llvm.and %arg241, %4 : i8
  %6 = llvm.icmp "eq" %5, %4 : i8
  %7 = llvm.and %2, %6 : i1
  "llvm.return"(%7) : (i1) -> ()
}
]

def CNFA.inter (m1 m2 : CNFA n) : CNFA n := product (fun b1 b2 => b1 && b2) m1 m2

def test20_after := [llvm|
{
^0(%arg2 : i33, %arg3 : i33):
  %0 = llvm.mlir.constant(0 : i33) : i33
  %1 = llvm.icmp "ne" %arg3, %0 : i33
  "llvm.return"(%1) : (i1) -> ()
}
]

def test57_after := [llvm|
{
^0(%arg126 : i64):
  %0 = llvm.mlir.constant(8 : i32) : i32
  %1 = llvm.trunc %arg126 : i64 to i32
  %2 = llvm.lshr %1, %0 : i32
  %3 = llvm.zext nneg %2 : i32 to i64
  "llvm.return"(%3) : (i64) -> ()
}
]

def test_and4_before := [llvm|
{
^0(%arg40 : i32, %arg41 : i32):
  %0 = llvm.mlir.constant(2147483647 : i32) : i32
  %1 = llvm.mlir.constant(0 : i32) : i32
  %2 = llvm.and %arg41, %0 : i32
  %3 = llvm.icmp "sge" %2, %arg40 : i32
  %4 = llvm.icmp "sge" %arg40, %1 : i32
  %5 = llvm.and %3, %4 : i1
  "llvm.return"(%5) : (i1) -> ()
}
]

def icmp_slt_0_and_icmp_sge_neg1_i64_fail_after := [llvm|
{
^0(%arg59 : i64):
  %0 = llvm.mlir.constant(-2) : i64
  %1 = llvm.mlir.constant(62) : i64
  %2 = llvm.mlir.constant(1) : i64
  %3 = llvm.mlir.constant(0) : i64
  %4 = llvm.icmp "sgt" %arg59, %0 : i64
  %5 = llvm.lshr %arg59, %1 : i64
  %6 = llvm.and %5, %2 : i64
  %7 = "llvm.select"(%4, %6, %3) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i64, i64) -> i64
  "llvm.return"(%7) : (i64) -> ()
}
]

def test_or_ne_a_b_after := [llvm|
{
^0(%arg15 : i1, %arg16 : i8, %arg17 : i8):
  "llvm.return"(%arg16) : (i8) -> ()
}
]

def do_not_add_annotation_to_existing_instr_before := [llvm|
{
^0(%arg15 : i32, %arg16 : i32):
  %0 = llvm.mlir.constant(0 : i32) : i32
  %1 = llvm.add %arg15, %arg16 : i32
  %2 = llvm.add %0, %1 : i32
  "llvm.return"(%2) : (i32) -> ()
}
]

def n3_constmask_samemask_after := [llvm|
{
^0(%arg0 : i32, %arg1 : i32):
  %0 = llvm.mlir.constant(65280 : i32) : i32
  %1 = llvm.or %arg0, %arg1 : i32
  %2 = llvm.and %1, %0 : i32
  "llvm.return"(%2) : (i32) -> ()
}
]

def not_or_or_and_no_and_commute2_after := [llvm|
{
^0(%arg109 : i32, %arg110 : i32, %arg111 : i32):
  %0 = llvm.mlir.constant(42 : i32) : i32
  %1 = llvm.mlir.constant(-1 : i32) : i32
  %2 = llvm.sdiv %0, %arg110 : i32
  %3 = llvm.xor %arg109, %1 : i32
  %4 = llvm.xor %2, %1 : i32
  %5 = llvm.and %arg111, %4 : i32
  %6 = llvm.or %5, %3 : i32
  "llvm.return"(%6) : (i32) -> ()
}
]

def mul_constant_partial_nuw_eq_before := [llvm|
{
^0(%arg104 : i32, %arg105 : i32):
  %0 = llvm.mlir.constant(44 : i32) : i32
  %1 = llvm.mul %arg104, %0 : i32
  %2 = llvm.mul %arg105, %0 overflow<nuw> : i32
  %3 = llvm.icmp "eq" %1, %2 : i32
  "llvm.return"(%3) : (i1) -> ()
}
]

def ashrslt_03_12_exact_after := [llvm|
{
^0(%arg9 : i4):
  %0 = llvm.mlir.constant(false) : i1
  "llvm.return"(%0) : (i1) -> ()
}
]

def test1_before := [llvm|
{
^0(%arg3 : i57, %arg4 : i57, %arg5 : i57):
  %0 = llvm.and %arg5, %arg3 : i57
  %1 = llvm.and %arg5, %arg4 : i57
  %2 = llvm.xor %0, %1 : i57
  "llvm.return"(%2) : (i57) -> ()
}
]

def ashr_ult_noexact_after := [llvm|
{
^0(%arg159 : i8):
  %0 = llvm.mlir.constant(80 : i8) : i8
  %1 = llvm.icmp "ult" %arg159, %0 : i8
  "llvm.return"(%1) : (i1) -> ()
}
]

def zext_nneg_sext_sle_op0_narrow_before := [llvm|
{
^0(%arg50 : i8, %arg51 : i16):
  %0 = llvm.zext nneg %arg50 : i8 to i32
  %1 = llvm.sext %arg51 : i16 to i32
  %2 = llvm.icmp "sle" %0, %1 : i32
  "llvm.return"(%2) : (i1) -> ()
}
]

def ashr_icmp2_after := [llvm|
{
^0(%arg26 : i64):
  %0 = llvm.mlir.constant(16) : i64
  %1 = llvm.icmp "slt" %arg26, %0 : i64
  "llvm.return"(%1) : (i1) -> ()
}
]

def select_replace_udiv_non_speculatable_before := [llvm|
{
^0(%arg1 : i32, %arg2 : i32):
  %0 = llvm.mlir.constant(0 : i32) : i32
  %1 = llvm.icmp "eq" %arg1, %0 : i32
  %2 = llvm.udiv %arg2, %arg1 : i32
  %3 = "llvm.select"(%1, %2, %arg2) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i32, i32) -> i32
  "llvm.return"(%3) : (i32) -> ()
}
]

inductive Op :  Type
  | add : Op
  | const : (val : ℤ) → Op
  | iterate (k : ℕ) : Op
  deriving DecidableEq

def lshrult_01_01_exact_after := [llvm|
{
^0(%arg148 : i4):
  %0 = llvm.mlir.constant(0 : i4) : i4
  %1 = llvm.icmp "eq" %arg148, %0 : i4
  "llvm.return"(%1) : (i1) -> ()
}
]

def and_slt_to_mask_before := [llvm|
{
^0(%arg5 : i8):
  %0 = llvm.mlir.constant(-124 : i8) : i8
  %1 = llvm.mlir.constant(2 : i8) : i8
  %2 = llvm.mlir.constant(0 : i8) : i8
  %3 = llvm.icmp "slt" %arg5, %0 : i8
  %4 = llvm.and %arg5, %1 : i8
  %5 = llvm.icmp "eq" %4, %2 : i8
  %6 = llvm.and %3, %5 : i1
  "llvm.return"(%6) : (i1) -> ()
}
]

def select_or_disjoint_or_before := [llvm|
{
^0(%arg14 : i32, %arg15 : i1):
  %0 = llvm.mlir.constant(0 : i32) : i32
  %1 = llvm.mlir.constant(4 : i32) : i32
  %2 = "llvm.select"(%arg15, %0, %1) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i32, i32) -> i32
  %3 = llvm.shl %arg14, %1 : i32
  %4 = llvm.or disjoint %2, %3 : i32
  %5 = llvm.add %4, %1 : i32
  "llvm.return"(%5) : (i32) -> ()
}
]

def simplify_neg_maxmin : RISCVPeepholeRewrite [Ty.riscv (.bv) ] where
  lhs := [LV| {
    ^entry (%x: !riscv.reg):
      %0 = neg %x : !riscv.reg
      %1 = max %x, %0 : !riscv.reg
      %2 = neg %1 : !riscv.reg
      ret %2 : !riscv.reg
  }]
  rhs := [LV| {
    ^entry (%x: !riscv.reg):
      %0 = neg %x : !riscv.reg
      %1 = min %x, %0 : !riscv.reg
      ret %1 : !riscv.reg
  }]

@[match_pattern] def poison : PoisonOr α := ⟨none⟩

def test1_after := [llvm|
{
^0(%arg3 : i16):
  %0 = llvm.mlir.constant(8 : i16) : i16
  %1 = llvm.mlir.constant(5 : i16) : i16
  %2 = llvm.lshr %arg3, %0 : i16
  %3 = llvm.mul %arg3, %1 : i16
  %4 = llvm.or %2, %3 : i16
  "llvm.return"(%4) : (i16) -> ()
}
]

def add_signbit_shl_after := [llvm|
{
^0(%arg17 : i32):
  %0 = llvm.mlir.constant(8 : i32) : i32
  %1 = llvm.mlir.constant(-16777216 : i32) : i32
  %2 = llvm.shl %arg17, %0 : i32
  %3 = llvm.add %2, %1 : i32
  "llvm.return"(%3) : (i32) -> ()
}
]

def shift_xor_multiuse_and_after := [llvm|
{
^0(%arg124 : i32, %arg125 : i32):
  %0 = llvm.mlir.constant(4096 : i32) : i32
  %1 = llvm.mlir.constant(0 : i32) : i32
  %2 = llvm.mlir.constant(-2049 : i32) : i32
  %3 = llvm.and %arg124, %0 : i32
  %4 = llvm.icmp "eq" %3, %1 : i32
  %5 = llvm.and %arg125, %2 : i32
  %6 = "llvm.select"(%4, %5, %arg125) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i32, i32) -> i32
  %7 = llvm.mul %6, %5 : i32
  "llvm.return"(%7) : (i32) -> ()
}
]

def t5_ugt_slt_0_after := [llvm|
{
^0(%arg63 : i32, %arg64 : i32, %arg65 : i32):
  %0 = llvm.mlir.constant(-16 : i32) : i32
  %1 = llvm.mlir.constant(127 : i32) : i32
  %2 = llvm.icmp "slt" %arg63, %0 : i32
  %3 = llvm.icmp "sgt" %arg63, %1 : i32
  %4 = "llvm.select"(%2, %arg64, %arg63) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i32, i32) -> i32
  %5 = "llvm.select"(%3, %arg65, %4) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i32, i32) -> i32
  "llvm.return"(%5) : (i32) -> ()
}
]

def demorgan_nor_use2ab_after := [llvm|
{
^0(%arg24 : i8, %arg25 : i8):
  %0 = llvm.mlir.constant(23 : i8) : i8
  %1 = llvm.mlir.constant(-1 : i8) : i8
  %2 = llvm.mlir.constant(17 : i8) : i8
  %3 = llvm.mul %arg25, %0 : i8
  %4 = llvm.xor %arg24, %1 : i8
  %5 = llvm.mul %4, %2 : i8
  %6 = llvm.xor %arg25, %1 : i8
  %7 = llvm.and %arg24, %6 : i8
  %8 = llvm.sdiv %7, %3 : i8
  %9 = llvm.sdiv %8, %5 : i8
  "llvm.return"(%9) : (i8) -> ()
}
]

def add_nsw_poison_constant_fold_after := [llvm|
{
^0(%arg2 : i1, %arg3 : i8):
  %0 = llvm.mlir.constant(64 : i8) : i8
  %1 = llvm.mlir.constant(-127 : i8) : i8
  %2 = llvm.add %arg3, %0 overflow<nsw> : i8
  %3 = "llvm.select"(%arg2, %2, %1) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i8, i8) -> i8
  "llvm.return"(%3) : (i8) -> ()
}
]

def and_zext_zext_before := [llvm|
{
^0(%arg58 : i8, %arg59 : i4):
  %0 = llvm.zext %arg58 : i8 to i16
  %1 = llvm.zext %arg59 : i4 to i16
  %2 = llvm.and %0, %1 : i16
  "llvm.return"(%2) : (i16) -> ()
}
]

def canonicalize_icmp_sgt_1 : LLVMPeepholeRewriteRefine 1 [Ty.llvm (.bitvec 64)] where
  lhs := [LV| {
    ^entry (%x: i64):
      %c = llvm.mlir.constant 1 : i64
      %1 = llvm.icmp.sgt %c, %x : i64
      llvm.return %1 : i1
  }]
  rhs := [LV| {
    ^entry (%x: i64):
      %c = llvm.mlir.constant 1 : i64
      %1 = llvm.icmp.slt %x, %c : i64
      llvm.return %1 : i1
  }]

def pr33078_4_after := [llvm|
{
^0(%arg2 : i3):
  %0 = llvm.mlir.constant(13 : i16) : i16
  %1 = llvm.sext %arg2 : i3 to i16
  %2 = llvm.lshr %1, %0 : i16
  %3 = llvm.trunc %2 overflow<nsw,nuw> : i16 to i8
  "llvm.return"(%3) : (i8) -> ()
}
]

Std.HashSet.ofList in Std.Data.HashSet.Basic

def slt_zero_before := [llvm|
{
^0(%arg30 : i4, %arg31 : i4):
  %0 = llvm.mlir.constant(0 : i4) : i4
  %1 = llvm.icmp "slt" %arg30, %0 : i4
  %2 = llvm.icmp "slt" %arg31, %0 : i4
  %3 = llvm.xor %1, %2 : i1
  "llvm.return"(%3) : (i1) -> ()
}
]

def ashrsgt_02_01_exact_before := [llvm|
{
^0(%arg84 : i4):
  %0 = llvm.mlir.constant(2 : i4) : i4
  %1 = llvm.mlir.constant(1 : i4) : i4
  %2 = llvm.ashr exact %arg84, %0 : i4
  %3 = llvm.icmp "sgt" %2, %1 : i4
  "llvm.return"(%3) : (i1) -> ()
}
]

def scalar_i32_udiv_and_negC_eq_X_is_constant3_after := [llvm|
{
^0(%arg7 : i32):
  %0 = llvm.mlir.constant(1544 : i32) : i32
  %1 = llvm.icmp "ult" %arg7, %0 : i32
  "llvm.return"(%1) : (i1) -> ()
}
]

def test21_after := [llvm|
{
^0(%arg174 : i32):
  %0 = llvm.mlir.constant(255 : i32) : i32
  %1 = llvm.and %arg174, %0 : i32
  "llvm.return"(%1) : (i32) -> ()
}
]

def main7e_logical_before := [llvm|
{
^0(%arg49 : i32, %arg50 : i32, %arg51 : i32, %arg52 : i32, %arg53 : i32):
  %0 = llvm.mlir.constant(false) : i1
  %1 = llvm.mlir.constant(0 : i32) : i32
  %2 = llvm.mlir.constant(1 : i32) : i32
  %3 = llvm.and %arg50, %arg52 : i32
  %4 = llvm.and %arg51, %arg53 : i32
  %5 = llvm.and %3, %arg49 : i32
  %6 = llvm.icmp "eq" %5, %3 : i32
  %7 = llvm.and %4, %arg49 : i32
  %8 = llvm.icmp "eq" %7, %4 : i32
  %9 = "llvm.select"(%6, %8, %0) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i1, i1) -> i1
  %10 = "llvm.select"(%9, %1, %2) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i32, i32) -> i32
  "llvm.return"(%10) : (i32) -> ()
}
]

def llvm02:=
  [LV|{
  ^bb0(%X : i64, %Y : i64 ):
    %1 = llvm.mlir.constant 9 : i64
    %2 = llvm.sub %X, %X : i64
    llvm.return %1 : i64
  }]

def worklistRun (final : S → Bool) (inits : Array S)
    (hinits : inits.toList.Nodup) (f : S → Array (BitVec n × S)) : CNFA n :=
  ⟨worklistRun' _ S final inits hinits f, worklistRun'_wf (BitVec n) S⟩

def xor_or_xor_common_op_commute8_after := [llvm|
{
^0(%arg59 : i32, %arg60 : i32, %arg61 : i32):
  %0 = llvm.mlir.constant(-1 : i32) : i32
  %1 = llvm.xor %arg59, %0 : i32
  %2 = llvm.and %arg60, %1 : i32
  %3 = llvm.xor %2, %arg61 : i32
  "llvm.return"(%3) : (i32) -> ()
}
]

inductive ExOp :  Type
  | add : ExOp
  | beq : ExOp
  | cst : ℕ → ExOp
  deriving DecidableEq

def test84_before := [llvm|
{
^0(%arg61 : i32):
  %0 = llvm.mlir.constant(-16777216 : i32) : i32
  %1 = llvm.mlir.constant(23 : i32) : i32
  %2 = llvm.add %arg61, %0 overflow<nsw> : i32
  %3 = llvm.lshr exact %2, %1 : i32
  %4 = llvm.trunc %3 : i32 to i8
  "llvm.return"(%4) : (i8) -> ()
}
]

def eq_umax3_after := [llvm|
{
^0(%arg56 : i32, %arg57 : i32):
  %0 = llvm.mlir.constant(3 : i32) : i32
  %1 = llvm.add %arg56, %0 : i32
  %2 = llvm.icmp "uge" %1, %arg57 : i32
  "llvm.return"(%2) : (i1) -> ()
}
]

def ptradd (p : SLLVM.Ptr) (x : LLVM.IntW 64) : SLLVM.Ptr := do
  let p ← p
  let x ← x
  return { p with offset := p.offset + x}

instance : HydrablePrettifyAsTheorem FpPredicate where
  prettifyAsTheorem := prettifyAsTheorem

def xor_logic_and_or2_after := [llvm|
{
^0(%arg15 : i1, %arg16 : i1, %arg17 : i1):
  %0 = llvm.mlir.constant(true) : i1
  %1 = llvm.xor %arg16, %0 : i1
  %2 = "llvm.select"(%arg15, %1, %arg17) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i1, i1) -> i1
  "llvm.return"(%2) : (i1) -> ()
}
]

def toHom (d : Diff Γ₁ Γ₂) : Hom Γ₁ Γ₂ :=
  fun _ v => ⟨v.val + d.val, d.property v.property⟩

def nomask_rhs_after := [llvm|
{
^0(%arg113 : i32):
  %0 = llvm.mlir.constant(1 : i32) : i32
  %1 = llvm.mlir.constant(0 : i32) : i32
  %2 = llvm.and %arg113, %0 : i32
  %3 = llvm.icmp "eq" %2, %1 : i32
  "llvm.return"(%3) : (i1) -> ()
}
]

def sle_swap_and_min_commute_after := [llvm|
{
^0(%arg210 : i8, %arg211 : i8):
  %0 = llvm.mlir.constant(-128 : i8) : i8
  %1 = llvm.icmp "eq" %arg210, %0 : i8
  "llvm.return"(%1) : (i1) -> ()
}
]

LawfulMonad in Init.Control.Lawful.Basic

def and_not_or_commute5_before := [llvm|
{
^0(%arg466 : i32, %arg467 : i32, %arg468 : i32):
  %0 = llvm.mlir.constant(42 : i32) : i32
  %1 = llvm.mlir.constant(-1 : i32) : i32
  %2 = llvm.sdiv %0, %arg466 : i32
  %3 = llvm.sdiv %0, %arg468 : i32
  %4 = llvm.and %2, %arg467 : i32
  %5 = llvm.xor %4, %1 : i32
  %6 = llvm.or %3, %5 : i32
  %7 = llvm.and %2, %3 : i32
  %8 = llvm.xor %7, %1 : i32
  %9 = llvm.or %8, %arg467 : i32
  %10 = llvm.and %6, %9 : i32
  "llvm.return"(%10) : (i32) -> ()
}
]

def ule_swap_or_not_min_logical_before := [llvm|
{
^0(%arg262 : i8, %arg263 : i8):
  %0 = llvm.mlir.constant(0 : i8) : i8
  %1 = llvm.mlir.constant(true) : i1
  %2 = llvm.icmp "uge" %arg263, %arg262 : i8
  %3 = llvm.icmp "ne" %arg262, %0 : i8
  %4 = "llvm.select"(%2, %1, %3) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i1, i1) -> i1
  "llvm.return"(%4) : (i1) -> ()
}
]

elab "[poly" qi:term "," ni:term "," hq:term " | " reg:mlir_region "]" : term => do
  let q : Q(Nat) ← elabTermEnsuringTypeQ qi q(Nat)
  let n : Q(Nat) ← elabTermEnsuringTypeQ ni q(Nat)
  let _factval ← elabTermEnsuringTypeQ hq q(Fact ($q > 1))

  SSA.elabIntoCom reg q(FHE $q $n)

def test15_before := [llvm|
{
^0(%arg44 : i8, %arg45 : i8):
  %0 = llvm.mlir.constant(33 : i8) : i8
  %1 = llvm.xor %arg45, %arg44 : i8
  %2 = llvm.xor %arg44, %0 : i8
  %3 = llvm.xor %2, %arg45 : i8
  %4 = llvm.and %1, %3 : i8
  %5 = llvm.mul %4, %3 : i8
  "llvm.return"(%5) : (i8) -> ()
}
]

def f_after := [llvm|
{
^0(%arg0 : i32):
  %0 = llvm.mlir.constant(false) : i1
  "llvm.return"(%0) : (i1) -> ()
}
]

Lean.Expr.eq? in Lean.Util.Recognizers

def Lets.repr (prec : Nat) : Lets d eff Γ t → Format
    | .nil => .align false ++ f!";"
    | .var body e => body.repr prec ++ (.align false ++ f!"{e.print}")

def nonexact_ashr_ne_noexactlog_before := [llvm|
{
^0(%arg133 : i8):
  %0 = llvm.mlir.constant(-90 : i8) : i8
  %1 = llvm.mlir.constant(-30 : i8) : i8
  %2 = llvm.ashr %0, %arg133 : i8
  %3 = llvm.icmp "ne" %2, %1 : i8
  "llvm.return"(%3) : (i1) -> ()
}
]

def samesign_after := [llvm|
{
^0(%arg131 : i32, %arg132 : i32):
  %0 = llvm.mlir.constant(-1 : i32) : i32
  %1 = llvm.xor %arg131, %arg132 : i32
  %2 = llvm.icmp "sgt" %1, %0 : i32
  "llvm.return"(%2) : (i1) -> ()
}
]

PartialOrder in Mathlib.Order.Defs.PartialOrder

Set.Mem in Mathlib.Data.Set.Defs

def icmp_x_slt_0_and_icmp_y_ne_neg2_i32_fail_after := [llvm|
{
^0(%arg42 : i32, %arg43 : i32):
  %0 = llvm.mlir.constant(-2 : i32) : i32
  %1 = llvm.mlir.constant(0 : i32) : i32
  %2 = llvm.icmp "ne" %arg42, %0 : i32
  %3 = llvm.icmp "slt" %arg43, %1 : i32
  %4 = llvm.and %3, %2 : i1
  %5 = llvm.zext %4 : i1 to i32
  "llvm.return"(%5) : (i32) -> ()
}
]

def test_mul__none_are_safe_after := [llvm|
{
^0(%arg0 : i32):
  %0 = llvm.mlir.constant(9 : i32) : i32
  %1 = llvm.mul %arg0, %0 : i32
  "llvm.return"(%1) : (i32) -> ()
}
]

def sra_negative_constant_lhs_i32_test : LLVMPeepholeRewriteRefine 32 [Ty.llvm (.bitvec 32)] where
  lhs := sra_negative_constant_lhs_llvm_i32
  rhs := sra_negative_constant_lhs_riscv_i32

def lshrugt_02_05_exact_before := [llvm|
{
^0(%arg200 : i4):
  %0 = llvm.mlir.constant(2 : i4) : i4
  %1 = llvm.mlir.constant(5 : i4) : i4
  %2 = llvm.lshr exact %arg200, %0 : i4
  %3 = llvm.icmp "ugt" %2, %1 : i4
  "llvm.return"(%3) : (i1) -> ()
}
]

def ashr_sgt_noexact_before := [llvm|
{
^0(%arg157 : i8):
  %0 = llvm.mlir.constant(3 : i8) : i8
  %1 = llvm.mlir.constant(10 : i8) : i8
  %2 = llvm.ashr %arg157, %0 : i8
  %3 = llvm.icmp "sgt" %2, %1 : i8
  "llvm.return"(%3) : (i1) -> ()
}
]

def factorize2_before := [llvm|
{
^0(%arg8 : i32):
  %0 = llvm.mlir.constant(3 : i32) : i32
  %1 = llvm.mlir.constant(2 : i32) : i32
  %2 = llvm.mul %0, %arg8 : i32
  %3 = llvm.mul %1, %arg8 : i32
  %4 = llvm.sub %2, %3 : i32
  "llvm.return"(%4) : (i32) -> ()
}
]

def test19_commutative1_after := [llvm|
{
^0(%arg72 : i32, %arg73 : i32):
  %0 = llvm.mlir.constant(1 : i32) : i32
  %1 = llvm.mlir.constant(-1 : i32) : i32
  %2 = llvm.shl %0, %arg72 overflow<nuw> : i32
  %3 = llvm.shl %0, %arg73 overflow<nuw> : i32
  %4 = llvm.and %2, %3 : i32
  %5 = llvm.add %2, %4 : i32
  %6 = llvm.add %5, %1 : i32
  %7 = llvm.and %arg73, %6 : i32
  "llvm.return"(%7) : (i32) -> ()
}
]

def ashr_shl_constants_after := [llvm|
{
^0(%arg25 : i32):
  %0 = llvm.mlir.constant(-33 : i32) : i32
  %1 = llvm.mlir.constant(3 : i32) : i32
  %2 = llvm.ashr %0, %arg25 : i32
  %3 = llvm.shl %2, %1 overflow<nsw> : i32
  "llvm.return"(%3) : (i32) -> ()
}
]

def or_and_or_pat1_before := [llvm|
{
^0(%arg38 : i8, %arg39 : i8, %arg40 : i8, %arg41 : i8):
  %0 = llvm.mlir.constant(42 : i8) : i8
  %1 = llvm.udiv %0, %arg40 : i8
  %2 = llvm.and %arg38, %arg39 : i8
  %3 = llvm.and %arg38, %arg41 : i8
  %4 = llvm.or %1, %3 : i8
  %5 = llvm.or %2, %4 : i8
  "llvm.return"(%5) : (i8) -> ()
}
]

def test13_after := [llvm|
{
^0(%arg27 : i18):
  %0 = llvm.mlir.constant(6 : i18) : i18
  %1 = llvm.mlir.constant(-512 : i18) : i18
  %2 = llvm.mul %arg27, %0 : i18
  %3 = llvm.and %2, %1 : i18
  "llvm.return"(%3) : (i18) -> ()
}
]

def not_logicalAnd_not_op1_after := [llvm|
{
^0(%arg58 : i1, %arg59 : i1):
  %0 = llvm.mlir.constant(true) : i1
  %1 = llvm.xor %arg58, %0 : i1
  %2 = "llvm.select"(%1, %0, %arg59) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i1, i1) -> i1
  "llvm.return"(%2) : (i1) -> ()
}
]

def ripple_nsw6_after := [llvm|
{
^0(%arg13 : i16, %arg14 : i16):
  %0 = llvm.mlir.constant(-21845 : i16) : i16
  %1 = llvm.mlir.constant(-10923 : i16) : i16
  %2 = llvm.or %arg14, %0 : i16
  %3 = llvm.or %arg13, %1 : i16
  %4 = llvm.add %3, %2 overflow<nsw> : i16
  "llvm.return"(%4) : (i16) -> ()
}
]

def icmp_ne_and_pow2_shl_pow2_after := [llvm|
{
^0(%arg63 : i32):
  %0 = llvm.mlir.constant(3 : i32) : i32
  %1 = llvm.icmp "eq" %arg63, %0 : i32
  %2 = llvm.zext %1 : i1 to i32
  "llvm.return"(%2) : (i32) -> ()
}
]

def ne_rem_zero_nonuw_after := [llvm|
{
^0(%arg142 : i8):
  %0 = llvm.mlir.constant(6 : i8) : i8
  %1 = llvm.icmp "ne" %arg142, %0 : i8
  "llvm.return"(%1) : (i1) -> ()
}
]

def fold_select_trunc_nuw_true_after := [llvm|
{
^0(%arg10 : i8, %arg11 : i8):
  %0 = llvm.mlir.constant(1 : i8) : i8
  %1 = llvm.trunc %arg10 overflow<nuw> : i8 to i1
  %2 = "llvm.select"(%1, %0, %arg11) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i8, i8) -> i8
  "llvm.return"(%2) : (i8) -> ()
}
]

def main7a_before := [llvm|
{
^0(%arg84 : i32, %arg85 : i32, %arg86 : i32):
  %0 = llvm.mlir.constant(0 : i32) : i32
  %1 = llvm.mlir.constant(1 : i32) : i32
  %2 = llvm.and %arg85, %arg84 : i32
  %3 = llvm.icmp "eq" %2, %arg85 : i32
  %4 = llvm.and %arg86, %arg84 : i32
  %5 = llvm.icmp "eq" %4, %arg86 : i32
  %6 = llvm.and %3, %5 : i1
  %7 = "llvm.select"(%6, %0, %1) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i32, i32) -> i32
  "llvm.return"(%7) : (i32) -> ()
}
]

def llvm_trunc_riscv_64_to_1 : LLVMPeepholeRewriteRefine 1 [Ty.llvm (.bitvec 64)] :=
  {lhs:= trunc_llvm_64_to_1, rhs:= trunc_riscv_to_1}

def sge_to_ult_before := [llvm|
{
^0(%arg17 : i8):
  %0 = llvm.mlir.constant(127 : i8) : i8
  %1 = llvm.mlir.constant(15 : i8) : i8
  %2 = llvm.xor %arg17, %0 : i8
  %3 = llvm.icmp "sge" %2, %1 : i8
  "llvm.return"(%3) : (i1) -> ()
}
]

@[simps]
def lift (M: NFA (BitVec n1) σ) (f : Fin n1 → Fin n2) : NFA (BitVec n2) σ where
  start := M.start
  accept := M.accept
  step q a := M.step q (a.transport f)

def ashrslt_03_02_exact_before := [llvm|
{
^0(%arg19 : i4):
  %0 = llvm.mlir.constant(3 : i4) : i4
  %1 = llvm.mlir.constant(2 : i4) : i4
  %2 = llvm.ashr exact %arg19, %0 : i4
  %3 = llvm.icmp "slt" %2, %1 : i4
  "llvm.return"(%3) : (i1) -> ()
}
]

def fold_sext_to_and_wrong10_before := [llvm|
{
^0(%arg0 : i8):
  %0 = llvm.mlir.constant(-256 : i32) : i32
  %1 = llvm.mlir.constant(1 : i32) : i32
  %2 = llvm.sext %arg0 : i8 to i32
  %3 = llvm.and %2, %0 : i32
  %4 = llvm.icmp "ne" %3, %1 : i32
  "llvm.return"(%4) : (i1) -> ()
}
]

def select_icmp_eq_and_1_0_lshr_fv_before := [llvm|
{
^0(%arg2 : i8, %arg3 : i8):
  %0 = llvm.mlir.constant(1 : i8) : i8
  %1 = llvm.mlir.constant(0 : i8) : i8
  %2 = llvm.mlir.constant(2 : i8) : i8
  %3 = llvm.and %arg2, %0 : i8
  %4 = llvm.icmp "eq" %3, %1 : i8
  %5 = llvm.lshr %arg3, %2 : i8
  %6 = "llvm.select"(%4, %arg3, %5) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i8, i8) -> i8
  "llvm.return"(%6) : (i8) -> ()
}
]

def test_xor_ne_before := [llvm|
{
^0(%arg64 : i8, %arg65 : i8, %arg66 : i8):
  %0 = llvm.mlir.constant(-1 : i8) : i8
  %1 = llvm.xor %arg66, %0 : i8
  %2 = llvm.xor %arg65, %0 : i8
  %3 = llvm.xor %2, %arg64 : i8
  %4 = llvm.icmp "ne" %1, %3 : i8
  "llvm.return"(%4) : (i1) -> ()
}
]

def sextinreg_after := [llvm|
{
^0(%arg14 : i32):
  %0 = llvm.mlir.constant(16 : i32) : i32
  %1 = llvm.shl %arg14, %0 : i32
  %2 = llvm.ashr exact %1, %0 : i32
  "llvm.return"(%2) : (i32) -> ()
}
]

def test44_before := [llvm|
{
^0(%arg144 : i8):
  %0 = llvm.mlir.constant(1234 : i16) : i16
  %1 = llvm.zext %arg144 : i8 to i16
  %2 = llvm.or %1, %0 : i16
  %3 = llvm.zext %2 : i16 to i64
  "llvm.return"(%3) : (i64) -> ()
}
]

def t0_ult_slt_65536_after := [llvm|
{
^0(%arg66 : i32, %arg67 : i32, %arg68 : i32):
  %0 = llvm.mlir.constant(0 : i32) : i32
  %1 = llvm.mlir.constant(65535 : i32) : i32
  %2 = llvm.icmp "slt" %arg66, %0 : i32
  %3 = llvm.icmp "sgt" %arg66, %1 : i32
  %4 = "llvm.select"(%2, %arg67, %arg66) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i32, i32) -> i32
  %5 = "llvm.select"(%3, %arg68, %4) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i32, i32) -> i32
  "llvm.return"(%5) : (i32) -> ()
}
]

def slt_to_ult_after := [llvm|
{
^0(%arg36 : i8, %arg37 : i8):
  %0 = llvm.icmp "ult" %arg36, %arg37 : i8
  "llvm.return"(%0) : (i1) -> ()
}
]

Std.Format.group in Init.Data.Format.Basic

@[simp_denote]
def sext_riscv_i1_to_32 := [LV| {
  ^entry (%arg: i1):
    %0 = "builtin.unrealized_conversion_cast"(%arg) : (i1) -> (!i64)
    %1 = slli %0, 63 : !i64
    %2 = srai %1, 63 : !i64
    %res = "builtin.unrealized_conversion_cast"(%2) : (!i64) -> (i32)
    llvm.return %res : i32
  }]

def lshr_lshr_after := [llvm|
{
^0(%arg47 : i232):
  %0 = llvm.mlir.constant(0 : i232) : i232
  "llvm.return"(%0) : (i232) -> ()
}
]

def ashr_mul_sign_bits_before := [llvm|
{
^0(%arg101 : i8, %arg102 : i8):
  %0 = llvm.mlir.constant(3 : i32) : i32
  %1 = llvm.sext %arg101 : i8 to i32
  %2 = llvm.sext %arg102 : i8 to i32
  %3 = llvm.mul %1, %2 : i32
  %4 = llvm.ashr %3, %0 : i32
  %5 = llvm.trunc %4 : i32 to i16
  "llvm.return"(%5) : (i16) -> ()
}
]

def mkTy : MLIR.AST.MLIRType φ → MLIR.AST.ExceptM DC DC.Ty
  | MLIR.AST.MLIRType.undefined s => do
    match s.splitOn "_" with
    | ["TokenStream"] =>
      return .tokenstream
    | ["TokenStream2"] =>
      return .tokenstream2
    | ["ValueStream", w] =>
      match w.toNat? with
      | some w' => return .valuestream w'
      | _ => throw .unsupportedType
    | ["ValueStream2", w] =>
      match w.toNat? with
      | some w' => return .valuestream2 w'
      | _ => throw .unsupportedType
    | ["ValueTokenStream", w] =>
    match w.toNat? with
      | some w' => return .valuetokenstream w'
      | _ => throw .unsupportedType
    | ["VariadicValueTokenStream", w] =>
    match w.toNat? with
      | some w' => return .variadicvaluetokenstream w'
      | _ => throw .unsupportedType
    | _ => throw .unsupportedType
  | _ => throw .unsupportedType

def liftExcept3 n : Fin n → Fin (n + 3) :=
  fun k => Fin.castLE (by admit /- proof elided -/
  ) k

def not? {w : Nat} (x : BitVec w) : IntW w := do
  .value (~~~x)

def nonexact_lshr_eq_before := [llvm|
{
^0(%arg154 : i8):
  %0 = llvm.mlir.constant(4 : i8) : i8
  %1 = llvm.mlir.constant(1 : i8) : i8
  %2 = llvm.lshr %0, %arg154 : i8
  %3 = llvm.icmp "eq" %2, %1 : i8
  "llvm.return"(%3) : (i1) -> ()
}
]

def add_and_or_after := [llvm|
{
^0(%arg15 : i32, %arg16 : i32):
  %0 = llvm.add %arg15, %arg16 : i32
  "llvm.return"(%0) : (i32) -> ()
}
]

def not_ashr_const_after := [llvm|
{
^0(%arg138 : i8):
  %0 = llvm.mlir.constant(41 : i8) : i8
  %1 = llvm.lshr %0, %arg138 : i8
  "llvm.return"(%1) : (i8) -> ()
}
]

def udiv_exact_eq_1_before := [llvm|
{
^0(%arg10 : i8, %arg11 : i8):
  %0 = llvm.mlir.constant(1 : i8) : i8
  %1 = llvm.udiv exact %arg10, %arg11 : i8
  %2 = llvm.icmp "ne" %1, %0 : i8
  "llvm.return"(%2) : (i1) -> ()
}
]

def scalar_after := [llvm|
{
^0(%arg43 : i4, %arg44 : i4, %arg45 : i4):
  %0 = llvm.xor %arg43, %arg44 : i4
  %1 = llvm.and %0, %arg45 : i4
  %2 = llvm.xor %1, %arg43 : i4
  "llvm.return"(%2) : (i4) -> ()
}
]

def test_and_ne_a_b_commuted_before := [llvm|
{
^0(%arg27 : i1, %arg28 : i8, %arg29 : i8):
  %0 = llvm.icmp "ne" %arg28, %arg29 : i8
  %1 = llvm.and %arg27, %0 : i1
  %2 = "llvm.select"(%1, %arg29, %arg28) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i8, i8) -> i8
  "llvm.return"(%2) : (i8) -> ()
}
]

def ashrsgt_02_07_after := [llvm|
{
^0(%arg294 : i4):
  %0 = llvm.mlir.constant(false) : i1
  "llvm.return"(%0) : (i1) -> ()
}
]

def icmp_and_ashr_multiuse_logical_after := [llvm|
{
^0(%arg4 : i32):
  %0 = llvm.mlir.constant(240 : i32) : i32
  %1 = llvm.mlir.constant(224 : i32) : i32
  %2 = llvm.mlir.constant(496 : i32) : i32
  %3 = llvm.mlir.constant(432 : i32) : i32
  %4 = llvm.and %arg4, %0 : i32
  %5 = llvm.icmp "ne" %4, %1 : i32
  %6 = llvm.and %arg4, %2 : i32
  %7 = llvm.icmp "ne" %6, %3 : i32
  %8 = llvm.and %5, %7 : i1
  "llvm.return"(%8) : (i1) -> ()
}
]

def set_bits_after := [llvm|
{
^0(%arg26 : i8, %arg27 : i1):
  %0 = llvm.mlir.constant(-6 : i8) : i8
  %1 = llvm.mlir.constant(5 : i8) : i8
  %2 = llvm.mlir.constant(0 : i8) : i8
  %3 = llvm.and %arg26, %0 : i8
  %4 = "llvm.select"(%arg27, %1, %2) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i8, i8) -> i8
  %5 = llvm.or disjoint %3, %4 : i8
  "llvm.return"(%5) : (i8) -> ()
}
]

def not_xor_to_or_not2_after := [llvm|
{
^0(%arg36 : i3, %arg37 : i3, %arg38 : i3):
  %0 = llvm.mlir.constant(-1 : i3) : i3
  %1 = llvm.or %arg38, %arg37 : i3
  %2 = llvm.and %arg36, %arg38 : i3
  %3 = llvm.xor %1, %0 : i3
  %4 = llvm.or %2, %3 : i3
  "llvm.return"(%4) : (i3) -> ()
}
]

def shl_add_nsw_after := [llvm|
{
^0(%arg10 : i8, %arg11 : i8):
  %0 = llvm.mlir.constant(-32 : i8) : i8
  %1 = llvm.mlir.constant(2 : i8) : i8
  %2 = llvm.or %arg10, %0 : i8
  %3 = llvm.and %arg11, %1 : i8
  %4 = llvm.shl %2, %3 overflow<nsw> : i8
  "llvm.return"(%4) : (i8) -> ()
}
]

def test_sge_xor_after := [llvm|
{
^0(%arg38 : i32, %arg39 : i32):
  %0 = llvm.xor %arg39, %arg38 : i32
  %1 = llvm.icmp "sle" %0, %arg38 : i32
  "llvm.return"(%1) : (i1) -> ()
}
]

instance : ToExpr Term where
  toExpr := Term.toExpr
  toTypeExpr := mkConst ``Term

def positive_samevar_shlnuwnsw_before := [llvm|
{
^0(%arg47 : i8, %arg48 : i8):
  %0 = llvm.lshr %arg47, %arg48 : i8
  %1 = llvm.shl %0, %arg48 overflow<nsw,nuw> : i8
  "llvm.return"(%1) : (i8) -> ()
}
]

def land_bor_right1_after := [llvm|
{
^0(%arg38 : i1, %arg39 : i1):
  "llvm.return"(%arg38) : (i1) -> ()
}
]

def matchArg [DecidableEq d.Op]
    (lets : Lets d Γ_in eff Γ_out) (matchLets : Lets d Δ_in .pure Δ_out) :
    {l : List d.Ty} → HVector (Var Γ_out) l → HVector (Var Δ_out) l →
    MatchVar Δ_in Γ_out
  | _, .nil, .nil => return
  | t::l, .cons vₗ vsₗ, .cons vᵣ vsᵣ => do
      matchVar (t := t) lets vₗ matchLets vᵣ
      matchArg lets matchLets vsₗ vsᵣ
  termination_by l => (sizeOf matchLets, l.length + 1)

def bitwise_and_bitwise_and_icmps_comm3_after := [llvm|
{
^0(%arg235 : i8, %arg236 : i8, %arg237 : i8):
  %0 = llvm.mlir.constant(42 : i8) : i8
  %1 = llvm.mlir.constant(1 : i8) : i8
  %2 = llvm.icmp "eq" %arg236, %0 : i8
  %3 = llvm.shl %1, %arg237 overflow<nuw> : i8
  %4 = llvm.or %3, %1 : i8
  %5 = llvm.and %arg235, %4 : i8
  %6 = llvm.icmp "eq" %5, %4 : i8
  %7 = llvm.and %6, %2 : i1
  "llvm.return"(%7) : (i1) -> ()
}
]

def or_trunc_lshr_more_before := [llvm|
{
^0(%arg1 : i8):
  %0 = llvm.mlir.constant(4 : i8) : i8
  %1 = llvm.mlir.constant(-4 : i6) : i6
  %2 = llvm.lshr %arg1, %0 : i8
  %3 = llvm.trunc %2 : i8 to i6
  %4 = llvm.or %3, %1 : i6
  "llvm.return"(%4) : (i6) -> ()
}
]

def ashrslt_01_01_exact_before := [llvm|
{
^0(%arg52 : i4):
  %0 = llvm.mlir.constant(1 : i4) : i4
  %1 = llvm.ashr exact %arg52, %0 : i4
  %2 = llvm.icmp "slt" %1, %0 : i4
  "llvm.return"(%2) : (i1) -> ()
}
]

def and_min_7_8_before := [llvm|
{
^0(%arg1 : i8):
  %0 = llvm.mlir.constant(-8 : i8) : i8
  %1 = llvm.icmp "ult" %arg1, %0 : i8
  %2 = "llvm.select"(%1, %arg1, %0) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i8, i8) -> i8
  %3 = llvm.and %2, %0 : i8
  "llvm.return"(%3) : (i8) -> ()
}
]

def PR23309_after := [llvm|
{
^0(%arg53 : i32, %arg54 : i32):
  %0 = llvm.sub %arg53, %arg54 : i32
  %1 = llvm.trunc %0 : i32 to i1
  "llvm.return"(%1) : (i1) -> ()
}
]

def lshrult_01_07_after := [llvm|
{
^0(%arg360 : i4):
  %0 = llvm.mlir.constant(-2 : i4) : i4
  %1 = llvm.icmp "ult" %arg360, %0 : i4
  "llvm.return"(%1) : (i1) -> ()
}
]

def no_shift_xor_multiuse_cmp_after := [llvm|
{
^0(%arg96 : i32, %arg97 : i32, %arg98 : i32, %arg99 : i32):
  %0 = llvm.mlir.constant(4096 : i32) : i32
  %1 = llvm.mlir.constant(0 : i32) : i32
  %2 = llvm.and %arg96, %0 : i32
  %3 = llvm.icmp "eq" %2, %1 : i32
  %4 = llvm.xor %2, %0 : i32
  %5 = llvm.or %arg97, %4 : i32
  %6 = "llvm.select"(%3, %arg99, %arg98) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i32, i32) -> i32
  %7 = llvm.mul %5, %6 : i32
  "llvm.return"(%7) : (i32) -> ()
}
]

def orn_and_cmp_1_logical_before := [llvm|
{
^0(%arg17 : i37, %arg18 : i37, %arg19 : i1):
  %0 = llvm.mlir.constant(false) : i1
  %1 = llvm.mlir.constant(true) : i1
  %2 = llvm.icmp "sgt" %arg17, %arg18 : i37
  %3 = llvm.icmp "sle" %arg17, %arg18 : i37
  %4 = "llvm.select"(%arg19, %2, %0) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i1, i1) -> i1
  %5 = "llvm.select"(%3, %1, %4) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i1, i1) -> i1
  "llvm.return"(%5) : (i1) -> ()
}
]

def udiv_mul_shl_nuw_before := [llvm|
{
^0(%arg166 : i5, %arg167 : i5, %arg168 : i5):
  %0 = llvm.mul %arg166, %arg167 overflow<nuw> : i5
  %1 = llvm.shl %arg166, %arg168 overflow<nuw> : i5
  %2 = llvm.udiv %0, %1 : i5
  "llvm.return"(%2) : (i5) -> ()
}
]

def test1_after := [llvm|
{
^0(%arg3 : i57, %arg4 : i57, %arg5 : i57):
  %0 = llvm.xor %arg3, %arg4 : i57
  %1 = llvm.and %arg5, %0 : i57
  "llvm.return"(%1) : (i57) -> ()
}
]

def test_add_zero_rhs_RHS := [mod_arith q, hq| {
  ^bb0(%x : !R):
    return %x : !R
}]

instance : HydrableReduceWidth ParsedFpExpr FpPredicate FpExpr where
  shrink := shrink

def test_before := [llvm|
{
^0(%arg0 : i32):
  %0 = llvm.mlir.constant(12 : i32) : i32
  %1 = llvm.mlir.constant(0 : i32) : i32
  %2 = llvm.shl %arg0, %0 : i32
  %3 = llvm.lshr %2, %0 : i32
  %4 = llvm.icmp "ne" %3, %1 : i32
  "llvm.return"(%4) : (i1) -> ()
}
]

def test7_after := [llvm|
{
^0(%arg93 : i32):
  %0 = llvm.mlir.constant(0 : i32) : i32
  "llvm.return"(%0) : (i32) -> ()
}
]

def lshrugt_01_10_exact_before := [llvm|
{
^0(%arg211 : i4):
  %0 = llvm.mlir.constant(1 : i4) : i4
  %1 = llvm.mlir.constant(-6 : i4) : i4
  %2 = llvm.lshr exact %arg211, %0 : i4
  %3 = llvm.icmp "ugt" %2, %1 : i4
  "llvm.return"(%3) : (i1) -> ()
}
]

def mul8_low_A0_B0_after := [llvm|
{
^0(%arg60 : i8, %arg61 : i8):
  %0 = llvm.mul %arg60, %arg61 : i8
  "llvm.return"(%0) : (i8) -> ()
}
]

def ashr_ugt_2_after := [llvm|
{
^0(%arg112 : i4):
  %0 = llvm.mlir.constant(5 : i4) : i4
  %1 = llvm.icmp "ugt" %arg112, %0 : i4
  "llvm.return"(%1) : (i1) -> ()
}
]

def no_reassoc_add_nuw_none_after := [llvm|
{
^0(%arg23 : i32):
  %0 = llvm.mlir.constant(68 : i32) : i32
  %1 = llvm.add %arg23, %0 : i32
  "llvm.return"(%1) : (i32) -> ()
}
]

def add_nsw_mul_nsw_after := [llvm|
{
^0(%arg33 : i16):
  %0 = llvm.mlir.constant(3 : i16) : i16
  %1 = llvm.mul %arg33, %0 overflow<nsw> : i16
  "llvm.return"(%1) : (i16) -> ()
}
]

def test11_before := [llvm|
{
^0(%arg11 : i32):
  %0 = llvm.mlir.constant(4 : i32) : i32
  %1 = llvm.mlir.constant(1 : i32) : i32
  %2 = llvm.udiv %0, %arg11 : i32
  %3 = llvm.icmp "ult" %2, %1 : i32
  "llvm.return"(%3) : (i1) -> ()
}
]

Std.Tactic.BVDecide.BVBinPred in Std.Tactic.BVDecide.Bitblast.BVExpr.Basic

def a_true_implies_b_true2_after := [llvm|
{
^0(%arg30 : i8, %arg31 : i1, %arg32 : i1):
  %0 = llvm.mlir.constant(20 : i8) : i8
  %1 = llvm.mlir.constant(false) : i1
  %2 = llvm.icmp "ugt" %arg30, %0 : i8
  %3 = "llvm.select"(%2, %arg31, %1) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i1, i1) -> i1
  "llvm.return"(%3) : (i1) -> ()
}
]

def zext_sext_eq_known_nonneg_before := [llvm|
{
^0(%arg20 : i8, %arg21 : i8):
  %0 = llvm.mlir.constant(1 : i8) : i8
  %1 = llvm.lshr %arg20, %0 : i8
  %2 = llvm.zext %1 : i8 to i32
  %3 = llvm.sext %arg21 : i8 to i32
  %4 = llvm.icmp "eq" %2, %3 : i32
  "llvm.return"(%4) : (i1) -> ()
}
]

instance (q : ℕ) [Fact (q > 1)] : DialectSignature (ModArith q) := ⟨Op.signature⟩

def llvm_const_lower_riscv_li12 : LLVMPeepholeRewriteRefine 64 [] :=
  {lhs := constLLVM12, rhs:= liRiscv12,
   correct := by admit /- proof elided -/

@[simp_denote]
def addi_riscv_i32 :=
  [LV| {
    ^entry (%arg: i32):
    %a = "builtin.unrealized_conversion_cast" (%arg) : (i32) -> (!i64)
    %0 = addiw %a, 1 : !i64
    %1 = "builtin.unrealized_conversion_cast" (%0) : (!i64) -> (i32)
    llvm.return %1 : i32
  }]

def ashrslt_01_07_exact_before := [llvm|
{
^0(%arg46 : i4):
  %0 = llvm.mlir.constant(1 : i4) : i4
  %1 = llvm.mlir.constant(7 : i4) : i4
  %2 = llvm.ashr exact %arg46, %0 : i4
  %3 = llvm.icmp "slt" %2, %1 : i4
  "llvm.return"(%3) : (i1) -> ()
}
]

def Body (Γ : Context Ty) (ty : Ty) : Type :=
  { body : UnTyped.Body Op VarName // Body.WellTyped Γ body ty }

def nonexact_ashr_ne_noexactlog_after := [llvm|
{
^0(%arg133 : i8):
  %0 = llvm.mlir.constant(true) : i1
  "llvm.return"(%0) : (i1) -> ()
}
]

def xor_with_or_disjoint_ab_before := [llvm|
{
^0(%arg26 : i32, %arg27 : i32):
  %0 = llvm.or disjoint %arg26, %arg27 : i32
  %1 = llvm.xor %arg26, %0 : i32
  "llvm.return"(%1) : (i32) -> ()
}
]

def test_ashr_exact__exact_is_safe_before := [llvm|
{
^0(%arg54 : i32, %arg55 : i64):
  %0 = llvm.mlir.constant(-2147483588 : i32) : i32
  %1 = llvm.mlir.constant(2 : i32) : i32
  %2 = llvm.mlir.constant(0 : i32) : i32
  %3 = llvm.and %arg54, %0 : i32
  %4 = llvm.ashr exact %3, %1 : i32
  %5 = llvm.zext %4 : i32 to i64
  %6 = llvm.icmp "eq" %3, %2 : i32
  %7 = llvm.ashr %arg55, %5 : i64
  %8 = "llvm.select"(%6, %arg55, %7) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i64, i64) -> i64
  "llvm.return"(%8) : (i64) -> ()
}
]

def sext_zext_nneg_ult_before := [llvm|
{
^0(%arg38 : i8, %arg39 : i8):
  %0 = llvm.sext %arg38 : i8 to i32
  %1 = llvm.zext nneg %arg39 : i8 to i32
  %2 = llvm.icmp "ult" %0, %1 : i32
  "llvm.return"(%2) : (i1) -> ()
}
]

def test15_before := [llvm|
{
^0(%arg44 : i8, %arg45 : i8):
  %0 = llvm.mlir.constant(33 : i8) : i8
  %1 = llvm.xor %arg45, %arg44 : i8
  %2 = llvm.xor %arg44, %0 : i8
  %3 = llvm.xor %2, %arg45 : i8
  %4 = llvm.and %1, %3 : i8
  %5 = llvm.mul %4, %3 : i8
  "llvm.return"(%5) : (i8) -> ()
}
]

def test14_before := [llvm|
{
^0(%arg85 : i64, %arg86 : i32):
  %0 = llvm.mlir.constant(1 : i32) : i32
  %1 = llvm.shl %0, %arg86 : i32
  %2 = llvm.zext %1 : i32 to i64
  %3 = llvm.urem %arg85, %2 : i64
  "llvm.return"(%3) : (i64) -> ()
}
]

def test36_after := [llvm|
{
^0(%arg244 : i32):
  %0 = llvm.mlir.constant(7 : i32) : i32
  %1 = llvm.mlir.constant(240 : i32) : i32
  %2 = llvm.add %arg244, %0 : i32
  %3 = llvm.and %2, %1 : i32
  %4 = llvm.zext nneg %3 : i32 to i64
  "llvm.return"(%4) : (i64) -> ()
}
]

def fake_sext_after := [llvm|
{
^0(%arg166 : i3):
  %0 = llvm.mlir.constant(2 : i3) : i3
  %1 = llvm.lshr %arg166, %0 : i3
  %2 = llvm.zext nneg %1 : i3 to i18
  "llvm.return"(%2) : (i18) -> ()
}
]

def mkPostcondIndHypNoCycleBreaking {n} (_circs : KInductionCircuits fsm n) :
    Circuit (Vars fsm.α arity (n + 2)) :=
  mkUnsatImpliesCircuit
    
    (castCircLe (mkOutEqZeroCircuitLeN fsm <| n))
    
    (mkOutEqZeroCircuitN fsm <| n+1)

def test18_after := [llvm|
{
^0(%arg34 : i32, %arg35 : i32):
  %0 = llvm.mlir.constant(1431655765 : i32) : i32
  %1 = llvm.or %arg34, %0 : i32
  %2 = llvm.sub %arg35, %1 : i32
  "llvm.return"(%2) : (i32) -> ()
}
]

RV64.ctz in RISCV.Instructions

def test19_after := [llvm|
{
^0(%arg76 : i32, %arg77 : i32):
  %0 = llvm.mlir.constant(1 : i32) : i32
  %1 = llvm.mlir.constant(-1 : i32) : i32
  %2 = llvm.shl %0, %arg76 overflow<nuw> : i32
  %3 = llvm.shl %0, %arg77 overflow<nuw> : i32
  %4 = llvm.and %2, %3 : i32
  %5 = llvm.add %4, %2 : i32
  %6 = llvm.add %5, %1 : i32
  %7 = llvm.and %arg77, %6 : i32
  "llvm.return"(%7) : (i32) -> ()
}
]

def syncPrim1 (s : Stream α) : Stream α := s

def not_add_before := [llvm|
{
^0(%arg124 : i32):
  %0 = llvm.mlir.constant(123 : i32) : i32
  %1 = llvm.mlir.constant(-1 : i32) : i32
  %2 = llvm.add %arg124, %0 : i32
  %3 = llvm.xor %2, %1 : i32
  "llvm.return"(%3) : (i32) -> ()
}
]

def test3_before := [llvm|
{
^0(%arg207 : i32):
  %0 = llvm.xor %arg207, %arg207 : i32
  "llvm.return"(%0) : (i32) -> ()
}
]

inductive AttrEntry where
  | mk: (key: String)
      -> (value: AttrValue)
      -> AttrEntry

def factorize5_after := [llvm|
{
^0(%arg1 : i32, %arg2 : i32):
  %0 = llvm.mul %arg2, %arg1 : i32
  "llvm.return"(%0) : (i32) -> ()
}
]

@[simp_denote]
def sub_riscv_i64 :=
  [LV| {
    ^entry (%arg0: i64, %arg1: i64):
    %a = "builtin.unrealized_conversion_cast" (%arg0) : (i64) -> (!i64)
    %b = "builtin.unrealized_conversion_cast" (%arg1) : (i64) -> (!i64)
    %0 = sub %a, %b : !i64
    %1 = "builtin.unrealized_conversion_cast" (%0) : (!i64) -> (i64)
    llvm.return %1 : i64
  }]

def lshr_add_and_shl_before := [llvm|
{
^0(%arg17 : i32, %arg18 : i32):
  %0 = llvm.mlir.constant(5 : i32) : i32
  %1 = llvm.mlir.constant(127 : i32) : i32
  %2 = llvm.lshr %arg17, %0 : i32
  %3 = llvm.and %2, %1 : i32
  %4 = llvm.add %arg18, %3 : i32
  %5 = llvm.shl %4, %0 : i32
  "llvm.return"(%5) : (i32) -> ()
}
]

def main4f_like_logical_before := [llvm|
{
^0(%arg115 : i32, %arg116 : i32, %arg117 : i32):
  %0 = llvm.mlir.constant(true) : i1
  %1 = llvm.mlir.constant(0 : i32) : i32
  %2 = llvm.mlir.constant(1 : i32) : i32
  %3 = llvm.and %arg115, %arg116 : i32
  %4 = llvm.icmp "ne" %3, %arg116 : i32
  %5 = llvm.and %arg115, %arg117 : i32
  %6 = llvm.icmp "ne" %5, %arg117 : i32
  %7 = "llvm.select"(%4, %0, %6) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i1, i1) -> i1
  %8 = "llvm.select"(%7, %1, %2) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i32, i32) -> i32
  "llvm.return"(%8) : (i32) -> ()
}
]

def eq_signed_to_small_unsigned_after := [llvm|
{
^0(%arg0 : i8):
  %0 = llvm.mlir.constant(17 : i8) : i8
  %1 = llvm.icmp "eq" %arg0, %0 : i8
  "llvm.return"(%1) : (i1) -> ()
}
]

def lshrult_02_03_exact_before := [llvm|
{
^0(%arg130 : i4):
  %0 = llvm.mlir.constant(2 : i4) : i4
  %1 = llvm.mlir.constant(3 : i4) : i4
  %2 = llvm.lshr exact %arg130, %0 : i4
  %3 = llvm.icmp "ult" %2, %1 : i4
  "llvm.return"(%3) : (i1) -> ()
}
]

structure Item where
 name : String
 tac : Syntax

def negate_xor_before := [llvm|
{
^0(%arg142 : i4):
  %0 = llvm.mlir.constant(5 : i4) : i4
  %1 = llvm.mlir.constant(0 : i4) : i4
  %2 = llvm.xor %arg142, %0 : i4
  %3 = llvm.sub %1, %2 : i4
  "llvm.return"(%3) : (i4) -> ()
}
]

def binopRows (opName : String)
  (f : (w : Nat) → Option (BitVec w) → Option (BitVec w) → Option (BitVec w)) : Array Row := Id.run do
  let mut rows := #[]
  for w in [1:MAXW+1] do
    for i in BitVec.inputsForWidth w do
      for j in BitVec.inputsForWidth w do
        let retv := f (w := w) i j
        let retv := BitVec.outputToString retv
        let row : Row := {
          opName := opName,
          bitwidth := toString w,
          v1 := BitVec.inputToString i,
          v2 := BitVec.inputToString j,
          retval := retv
        }
        rows := rows.push row
  rows

def test_eq_0_and_15_add_3_after := [llvm|
{
^0(%arg3 : i8):
  %0 = llvm.mlir.constant(15 : i8) : i8
  %1 = llvm.mlir.constant(13 : i8) : i8
  %2 = llvm.and %arg3, %0 : i8
  %3 = llvm.icmp "eq" %2, %1 : i8
  "llvm.return"(%3) : (i1) -> ()
}
]

def test25_after := [llvm|
{
^0(%arg271 : i32):
  %0 = llvm.mlir.constant(-50 : i32) : i32
  %1 = llvm.mlir.constant(50 : i32) : i32
  %2 = llvm.add %arg271, %0 : i32
  %3 = llvm.icmp "ult" %2, %1 : i32
  "llvm.return"(%3) : (i1) -> ()
}
]

def irc_constants_AMinusC1PlusC2_0_2 : LLVMPeepholeRewriteRefine 64 [Ty.llvm (.bitvec 64)] where
  lhs := [LV| {
    ^entry (%a: i64):
      %c1 = llvm.mlir.constant (0) : i64
      %c2 = llvm.mlir.constant (2) : i64
      %0 = llvm.sub %a, %c1 : i64
      %1 = llvm.add %0, %c2 : i64
      llvm.return %1 : i64
  }]
  rhs := [LV| {
    ^entry (%a: i64):
      %c1 = llvm.mlir.constant (0) : i64
      %c2 = llvm.mlir.constant (2) : i64
      %0 = llvm.sub %c2, %c1 : i64
      %1 = llvm.add %a, %0 : i64
      llvm.return %1 : i64
  }]

def negtest_near_pow2_cmpval_ashr_wrong_cmp_pred_after := [llvm|
{
^0(%arg2 : i8):
  %0 = llvm.mlir.constant(10 : i8) : i8
  %1 = llvm.icmp "eq" %arg2, %0 : i8
  "llvm.return"(%1) : (i1) -> ()
}
]

def not_xor_to_or_not2_after := [llvm|
{
^0(%arg36 : i3, %arg37 : i3, %arg38 : i3):
  %0 = llvm.mlir.constant(-1 : i3) : i3
  %1 = llvm.or %arg38, %arg37 : i3
  %2 = llvm.and %arg36, %arg38 : i3
  %3 = llvm.xor %1, %0 : i3
  %4 = llvm.or %2, %3 : i3
  "llvm.return"(%4) : (i3) -> ()
}
]

def bitwise_or_bitwise_or_icmps_comm1_after := [llvm|
{
^0(%arg193 : i8, %arg194 : i8, %arg195 : i8):
  %0 = llvm.mlir.constant(42 : i8) : i8
  %1 = llvm.mlir.constant(1 : i8) : i8
  %2 = llvm.icmp "eq" %arg194, %0 : i8
  %3 = llvm.shl %1, %arg195 overflow<nuw> : i8
  %4 = llvm.or %3, %1 : i8
  %5 = llvm.and %arg193, %4 : i8
  %6 = llvm.icmp "ne" %5, %4 : i8
  %7 = llvm.or %2, %6 : i1
  "llvm.return"(%7) : (i1) -> ()
}
]

def or_logic_or_logic_and_5_before := [llvm|
{
^0(%arg36 : i1, %arg37 : i1, %arg38 : i1):
  %0 = llvm.mlir.constant(true) : i1
  %1 = llvm.mlir.constant(false) : i1
  %2 = llvm.or %arg37, %arg36 : i1
  %3 = "llvm.select"(%arg36, %0, %arg38) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i1, i1) -> i1
  %4 = "llvm.select"(%2, %3, %1) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i1, i1) -> i1
  "llvm.return"(%4) : (i1) -> ()
}
]

Stream'.drop in Mathlib.Data.Stream.Defs

def slt_zero_ne_ne_b_before := [llvm|
{
^0(%arg2 : i32, %arg3 : i32):
  %0 = llvm.mlir.constant(31 : i32) : i32
  %1 = llvm.icmp "ne" %arg2, %arg3 : i32
  %2 = llvm.zext %1 : i1 to i32
  %3 = llvm.lshr %arg2, %0 : i32
  %4 = llvm.icmp "ne" %2, %3 : i32
  "llvm.return"(%4) : (i1) -> ()
}
]

private def pretty_select (w : Nat) :=
  [llvm(w)| {
    ^bb0(%arg0: i1, %arg1 : _):
      %0 = llvm.select %arg0, %arg1, %arg1
      llvm.return %0
  }]

def lshr_ne_msb_low_last_zero_before := [llvm|
{
^0(%arg174 : i8):
  %0 = llvm.mlir.constant(127 : i8) : i8
  %1 = llvm.mlir.constant(0 : i8) : i8
  %2 = llvm.lshr %0, %arg174 : i8
  %3 = llvm.icmp "ne" %2, %1 : i8
  "llvm.return"(%3) : (i1) -> ()
}
]

def xor_logic_and_logic_or4_after := [llvm|
{
^0(%arg45 : i1, %arg46 : i1, %arg47 : i1):
  %0 = llvm.mlir.constant(true) : i1
  %1 = llvm.xor %arg46, %0 : i1
  %2 = "llvm.select"(%arg45, %1, %arg47) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i1, i1) -> i1
  "llvm.return"(%2) : (i1) -> ()
}
]

def _root_.Int.testBit' (i : Int) (k : Nat) : Bool :=
  match i with
  | .ofNat n => n.testBit k
  | .negSucc n => !(n.testBit k)

def ule_and_min_commute_before := [llvm|
{
^0(%arg202 : i8, %arg203 : i8):
  %0 = llvm.mlir.constant(0 : i8) : i8
  %1 = llvm.icmp "ule" %arg202, %arg203 : i8
  %2 = llvm.icmp "eq" %arg202, %0 : i8
  %3 = llvm.and %2, %1 : i1
  "llvm.return"(%3) : (i1) -> ()
}
]

@[simp_denote]
def liRiscv0_1bit := [LV| {
  ^entry ():
    %0 = "li"() {imm = 0 : !i64} : (!i64) -> (!i64)
    %1 = "builtin.unrealized_conversion_cast"(%0) : (!i64) -> (i1)
    llvm.return %1 : i1
  }]

def pr40493_neg3_after := [llvm|
{
^0(%arg15 : i32):
  %0 = llvm.mlir.constant(2 : i32) : i32
  %1 = llvm.mlir.constant(4 : i32) : i32
  %2 = llvm.shl %arg15, %0 : i32
  %3 = llvm.and %2, %1 : i32
  "llvm.return"(%3) : (i32) -> ()
}
]

def sel_false_val_is_a_masked_lshr_of_true_val2_after := [llvm|
{
^0(%arg4 : i32, %arg5 : i64):
  %0 = llvm.mlir.constant(2 : i32) : i32
  %1 = llvm.mlir.constant(15 : i32) : i32
  %2 = llvm.lshr %arg4, %0 : i32
  %3 = llvm.and %2, %1 : i32
  %4 = llvm.zext nneg %3 : i32 to i64
  %5 = llvm.ashr %arg5, %4 : i64
  "llvm.return"(%5) : (i64) -> ()
}
]

def icmp_slt_0_and_icmp_ne_neg2_i32_fail_before := [llvm|
{
^0(%arg44 : i32):
  %0 = llvm.mlir.constant(-2 : i32) : i32
  %1 = llvm.mlir.constant(31 : i32) : i32
  %2 = llvm.icmp "ne" %arg44, %0 : i32
  %3 = llvm.zext %2 : i1 to i32
  %4 = llvm.lshr %arg44, %1 : i32
  %5 = llvm.and %4, %3 : i32
  "llvm.return"(%5) : (i32) -> ()
}
]

def fst {Γ : Ctxt _} (a : Γ.Var (.tokenstream2)) : Expr (DC) Γ .pure (.tokenstream)  :=
  Expr.mk
    (op := .fst)
    (ty_eq := rfl)
    (eff_le := by admit /- proof elided -/
    )
    (args := .cons a <| .nil)
    (regArgs := .nil)

@[simp_llvm]
def sub? {w : Nat} (x y : BitVec w) : IntW w :=
  .value <| x - y

def ripple_nsw2_before := [llvm|
{
^0(%arg21 : i16, %arg22 : i16):
  %0 = llvm.mlir.constant(1 : i16) : i16
  %1 = llvm.mlir.constant(-16385 : i16) : i16
  %2 = llvm.and %arg22, %0 : i16
  %3 = llvm.and %arg21, %1 : i16
  %4 = llvm.add %3, %2 : i16
  "llvm.return"(%4) : (i16) -> ()
}
]

def two_signed_truncation_checks_after := [llvm|
{
^0(%arg3 : i32):
  %0 = llvm.mlir.constant(128 : i32) : i32
  %1 = llvm.mlir.constant(256 : i32) : i32
  %2 = llvm.add %arg3, %0 : i32
  %3 = llvm.icmp "ult" %2, %1 : i32
  "llvm.return"(%3) : (i1) -> ()
}
]

def elabDefSignatureFor (dialect : Term) (alts : TSyntax ``matchAltsSig) : CommandElabM Unit := do
  let msg := (return m!"{exceptEmoji ·} Defining operation signature for {dialect} dialect")
  withTraceNode `LeanMLIR.Elab msg (collapsed := false) <| do
    let alts := getMatchAlts alts
    let alts ← do
      alts.mapM fun view => do
        trace[LeanMLIR.Elab] m!"Parsing match alternative with\n\
          \tpatterns: {view.patterns}\n\
          \tsignature: {view.rhs}"
        let rhs ← parseSignature view.rhs
        return { view with rhs }

    |

def llvm_add_lower_riscv_nuw_nsw_flag_32 : LLVMPeepholeRewriteRefine 32 [Ty.llvm (.bitvec 32), Ty.llvm (.bitvec 32)]
where
  lhs:= add_llvm_nsw_nuw_flags_32
  rhs:= add_riscv_32

def urem_c_i32_after := [llvm|
{
^0(%arg5 : i8):
  %0 = llvm.mlir.constant(10 : i8) : i8
  %1 = llvm.urem %0, %arg5 : i8
  %2 = llvm.zext nneg %1 : i8 to i32
  "llvm.return"(%2) : (i32) -> ()
}
]

def test45_after := [llvm|
{
^0(%arg201 : i32, %arg202 : i32):
  %0 = llvm.and %arg201, %arg202 : i32
  "llvm.return"(%0) : (i32) -> ()
}
]

def xor_or_after := [llvm|
{
^0(%arg159 : i8):
  %0 = llvm.mlir.constant(-8 : i8) : i8
  %1 = llvm.mlir.constant(39 : i8) : i8
  %2 = llvm.and %arg159, %0 : i8
  %3 = llvm.xor %2, %1 : i8
  "llvm.return"(%3) : (i8) -> ()
}
]

def src_is_notmask_x_xor_neg_x_inv_after := [llvm|
{
^0(%arg66 : i8, %arg67 : i8, %arg68 : i1):
  %0 = llvm.mlir.constant(123 : i8) : i8
  %1 = llvm.mlir.constant(-1 : i8) : i8
  %2 = llvm.mlir.constant(7 : i8) : i8
  %3 = llvm.xor %arg66, %0 : i8
  %4 = llvm.add %arg67, %1 : i8
  %5 = llvm.xor %arg67, %4 : i8
  %6 = "llvm.select"(%arg68, %5, %2) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i8, i8) -> i8
  %7 = llvm.icmp "ule" %3, %6 : i8
  "llvm.return"(%7) : (i1) -> ()
}
]

def narrow_sext_sub_after := [llvm|
{
^0(%arg40 : i16, %arg41 : i32):
  %0 = llvm.trunc %arg41 : i32 to i16
  %1 = llvm.sub %arg40, %0 : i16
  "llvm.return"(%1) : (i16) -> ()
}
]

def trunc_shl_shl_infloop_before := [llvm|
{
^0(%arg20 : i64):
  %0 = llvm.mlir.constant(1) : i64
  %1 = llvm.mlir.constant(2) : i64
  %2 = llvm.shl %arg20, %0 : i64
  %3 = llvm.shl %2, %1 : i64
  %4 = llvm.trunc %3 : i64 to i32
  "llvm.return"(%4) : (i32) -> ()
}
]

@[simp_denote]
def add_positive_low_bound_accept_riscv :=
  [LV| {
    ^entry (%arg: i32):
    %a =  "builtin.unrealized_conversion_cast" (%arg) : (i32) -> (!i64)
    %0 = addi %a, 2047 : !i64
    %1 = addiw %0, 1 : !i64
    %2 =  "builtin.unrealized_conversion_cast" (%1) : (!i64) -> (i32)
    llvm.return %2 :i32
  }]

def p0_after := [llvm|
{
^0(%arg16 : i8, %arg17 : i8):
  %0 = llvm.mlir.constant(-1 : i8) : i8
  %1 = llvm.lshr %0, %arg17 : i8
  %2 = llvm.icmp "ugt" %arg16, %1 : i8
  "llvm.return"(%2) : (i1) -> ()
}
]

def t2_before := [llvm|
{
^0(%arg11 : i8):
  %0 = llvm.mlir.constant(0 : i8) : i8
  %1 = llvm.sub %0, %arg11 overflow<nsw> : i8
  %2 = llvm.icmp "slt" %1, %arg11 : i8
  "llvm.return"(%2) : (i1) -> ()
}
]

def lshrugt_01_06_after := [llvm|
{
^0(%arg409 : i4):
  %0 = llvm.mlir.constant(-3 : i4) : i4
  %1 = llvm.icmp "ugt" %arg409, %0 : i4
  "llvm.return"(%1) : (i1) -> ()
}
]

def PR42691_8_logical_after := [llvm|
{
^0(%arg328 : i32):
  %0 = llvm.mlir.constant(2147483647 : i32) : i32
  %1 = llvm.mlir.constant(-2147483635 : i32) : i32
  %2 = llvm.add %arg328, %0 : i32
  %3 = llvm.icmp "ult" %2, %1 : i32
  "llvm.return"(%3) : (i1) -> ()
}
]

def test92_after := [llvm|
{
^0(%arg48 : i64):
  %0 = llvm.mlir.constant(32) : i64
  %1 = llvm.ashr %arg48, %0 : i64
  "llvm.return"(%1) : (i64) -> ()
}
]

def llvm_mul_lower_riscv_nsw_flag_32 : LLVMPeepholeRewriteRefine 32 [Ty.llvm (.bitvec 32), Ty.llvm (.bitvec 32)] where
  lhs := mul_llvm_nsw_32
  rhs := mul_riscv_32

def alive_AndOrXor_2063__X__C1__C2____X__C2__C1__C2_tgt :=
[sllvm| {
^bb0(%x : i64, %C1 : i64, %C : i64):
  %v1 = llvm.or %x, %C : i64
  %v2 = llvm.xor %x, %C1 : i64
  %v3 = llvm.not %C : i64
  %v4 = llvm.and %C1, %v3 : i64
  %v5 = llvm.xor %v1, %v4 : i64
  llvm.return %v5 : i64
}]

inductive Op
| fst
| snd
| pair (w : Nat)
| fstVal (w : Nat)
| sndVal (w : Nat)
| fstVal' (w : Nat)
| sndVal' (w : Nat)
| tokVal' (w : Nat)
| merge
| branch
| fork
| join
| select
| sink
| source
| pack (w : Nat)
| pack2 (w : Nat)
| unpack (w : Nat)
| unpack2 (w : Nat)
deriving Inhabited, DecidableEq, Repr, Lean.ToExpr

def test17_before := [llvm|
{
^0(%arg80 : i32):
  %0 = llvm.mlir.constant(1 : i32) : i32
  %1 = llvm.urem %0, %arg80 : i32
  "llvm.return"(%1) : (i32) -> ()
}
]

def test_after := [llvm|
{
^0(%arg0 : i26):
  "llvm.return"(%arg0) : (i26) -> ()
}
]

def or_not_and_commute5_after := [llvm|
{
^0(%arg522 : i32, %arg523 : i32, %arg524 : i32):
  %0 = llvm.mlir.constant(42 : i32) : i32
  %1 = llvm.mlir.constant(-1 : i32) : i32
  %2 = llvm.sdiv %0, %arg522 : i32
  %3 = llvm.sdiv %0, %arg524 : i32
  %4 = llvm.xor %arg523, %3 : i32
  %5 = llvm.xor %2, %1 : i32
  %6 = llvm.and %4, %5 : i32
  "llvm.return"(%6) : (i32) -> ()
}
]

def positive_samevar_shlnsw_after := [llvm|
{
^0(%arg52 : i8, %arg53 : i8):
  %0 = llvm.mlir.constant(-1 : i8) : i8
  %1 = llvm.shl %0, %arg53 overflow<nsw> : i8
  %2 = llvm.and %1, %arg52 : i8
  "llvm.return"(%2) : (i8) -> ()
}
]

def n9_wrong_x1_before := [llvm|
{
^0(%arg14 : i8, %arg15 : i8):
  %0 = llvm.mlir.constant(15 : i8) : i8
  %1 = llvm.mlir.constant(0 : i8) : i8
  %2 = llvm.mlir.constant(16 : i8) : i8
  %3 = llvm.mlir.constant(-16 : i8) : i8
  %4 = llvm.and %arg14, %0 : i8
  %5 = llvm.icmp "eq" %4, %1 : i8
  %6 = llvm.add %arg15, %2 : i8
  %7 = llvm.and %6, %3 : i8
  %8 = "llvm.select"(%5, %arg14, %7) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i8, i8) -> i8
  "llvm.return"(%8) : (i8) -> ()
}
]

def demorgan_nand_before := [llvm|
{
^0(%arg38 : i8, %arg39 : i8):
  %0 = llvm.mlir.constant(-1 : i8) : i8
  %1 = llvm.xor %arg38, %0 : i8
  %2 = llvm.and %1, %arg39 : i8
  %3 = llvm.xor %2, %0 : i8
  "llvm.return"(%3) : (i8) -> ()
}
]

def select {w : Nat} (c? : IntW 1) (x? y? : IntW w ) : IntW w := do
  let c ← c?
  if c = 1#1 then x? else y?

def ashr_eq_msb_low_second_zero_after := [llvm|
{
^0(%arg175 : i8):
  %0 = llvm.mlir.constant(6 : i8) : i8
  %1 = llvm.icmp "ugt" %arg175, %0 : i8
  "llvm.return"(%1) : (i1) -> ()
}
]

def ashrslt_03_01_exact_before := [llvm|
{
^0(%arg20 : i4):
  %0 = llvm.mlir.constant(3 : i4) : i4
  %1 = llvm.mlir.constant(1 : i4) : i4
  %2 = llvm.ashr exact %arg20, %0 : i4
  %3 = llvm.icmp "slt" %2, %1 : i4
  "llvm.return"(%3) : (i1) -> ()
}
]

def scalar_i32_shl_and_signbit_eq_nonzero_after := [llvm|
{
^0(%arg0 : i32, %arg1 : i32):
  %0 = llvm.mlir.constant(false) : i1
  "llvm.return"(%0) : (i1) -> ()
}
]

def n12_before := [llvm|
{
^0(%arg0 : i8):
  %0 = llvm.mlir.constant(6 : i8) : i8
  %1 = llvm.shl %arg0, %0 : i8
  %2 = llvm.ashr %1, %0 : i8
  "llvm.return"(%2) : (i8) -> ()
}
]

def ashrsgt_02_07_before := [llvm|
{
^0(%arg294 : i4):
  %0 = llvm.mlir.constant(2 : i4) : i4
  %1 = llvm.mlir.constant(7 : i4) : i4
  %2 = llvm.ashr %arg294, %0 : i4
  %3 = llvm.icmp "sgt" %2, %1 : i4
  "llvm.return"(%3) : (i1) -> ()
}
]

def and_match : List (Σ Γ, Σ ty, PeepholeRewrite LLVMPlusRiscV Γ ty) :=[
  mkRewrite (LLVMToRiscvPeepholeRewriteRefine.toPeepholeUNSOUND llvm_and_lower_riscv_1),
  mkRewrite (LLVMToRiscvPeepholeRewriteRefine.toPeepholeUNSOUND llvm_and_lower_riscv_8),
  mkRewrite (LLVMToRiscvPeepholeRewriteRefine.toPeepholeUNSOUND llvm_and_lower_riscv_16),
  mkRewrite (LLVMToRiscvPeepholeRewriteRefine.toPeepholeUNSOUND llvm_and_lower_riscv_32),
  mkRewrite (LLVMToRiscvPeepholeRewriteRefine.toPeepholeUNSOUND llvm_and_lower_riscv_64),
]

def sle_or_not_min_commute_before := [llvm|
{
^0(%arg284 : i8, %arg285 : i8):
  %0 = llvm.mlir.constant(-128 : i8) : i8
  %1 = llvm.icmp "sle" %arg284, %arg285 : i8
  %2 = llvm.icmp "ne" %arg284, %0 : i8
  %3 = llvm.or %2, %1 : i1
  "llvm.return"(%3) : (i1) -> ()
}
]

def or_not_and_commute5_before := [llvm|
{
^0(%arg522 : i32, %arg523 : i32, %arg524 : i32):
  %0 = llvm.mlir.constant(42 : i32) : i32
  %1 = llvm.mlir.constant(-1 : i32) : i32
  %2 = llvm.sdiv %0, %arg522 : i32
  %3 = llvm.sdiv %0, %arg524 : i32
  %4 = llvm.or %2, %arg523 : i32
  %5 = llvm.xor %4, %1 : i32
  %6 = llvm.and %3, %5 : i32
  %7 = llvm.or %2, %3 : i32
  %8 = llvm.xor %7, %1 : i32
  %9 = llvm.and %8, %arg523 : i32
  %10 = llvm.or %6, %9 : i32
  "llvm.return"(%10) : (i32) -> ()
}
]

def no_shift_xor_multiuse_or_before := [llvm|
{
^0(%arg134 : i32, %arg135 : i32):
  %0 = llvm.mlir.constant(4096 : i32) : i32
  %1 = llvm.mlir.constant(0 : i32) : i32
  %2 = llvm.and %arg134, %0 : i32
  %3 = llvm.icmp "ne" %1, %2 : i32
  %4 = llvm.or %arg135, %0 : i32
  %5 = "llvm.select"(%3, %arg135, %4) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i32, i32) -> i32
  %6 = llvm.mul %5, %4 : i32
  "llvm.return"(%6) : (i32) -> ()
}
]

def add_smin_simplify2_after := [llvm|
{
^0(%arg33 : i32):
  %0 = llvm.mlir.constant(-3 : i32) : i32
  %1 = llvm.add %arg33, %0 overflow<nsw> : i32
  "llvm.return"(%1) : (i32) -> ()
}
]

def test_sub_0_Y_ne_0_after := [llvm|
{
^0(%arg48 : i8):
  %0 = llvm.mlir.constant(0 : i8) : i8
  %1 = llvm.icmp "ne" %arg48, %0 : i8
  "llvm.return"(%1) : (i1) -> ()
}
]

def shl_add_nsw_before := [llvm|
{
^0(%arg25 : i32):
  %0 = llvm.mlir.constant(1 : i32) : i32
  %1 = llvm.mlir.constant(-1 : i32) : i32
  %2 = llvm.shl %0, %arg25 : i32
  %3 = llvm.add %2, %1 overflow<nsw> : i32
  "llvm.return"(%3) : (i32) -> ()
}
]

def test2_after := [llvm|
{
^0(%arg59 : i32):
  %0 = llvm.mlir.constant(39 : i32) : i32
  %1 = llvm.and %arg59, %0 : i32
  "llvm.return"(%1) : (i32) -> ()
}
]

def masked_or_allones_after := [llvm|
{
^0(%arg127 : i32):
  %0 = llvm.mlir.constant(7 : i32) : i32
  %1 = llvm.and %arg127, %0 : i32
  %2 = llvm.icmp "eq" %1, %0 : i32
  "llvm.return"(%2) : (i1) -> ()
}
]

def t2_before := [llvm|
{
^0(%arg8 : i64):
  %0 = llvm.mlir.constant(63) : i64
  %1 = llvm.mlir.constant(0) : i64
  %2 = llvm.ashr %arg8, %0 : i64
  %3 = llvm.sub %1, %2 : i64
  "llvm.return"(%3) : (i64) -> ()
}
]

def select_same_val_self : LLVMPeepholeRewriteRefine 64 [Ty.llvm (.bitvec 1), Ty.llvm (.bitvec 64) ] where
  lhs := [LV| {
    ^entry (%x: i64, %c: i1):
      %0 = llvm.select %c, %x, %x : i64
      llvm.return %0 : i64
  }]
  rhs := [LV| {
    ^entry (%x: i64, %c: i1):
      llvm.return %x : i64
  }]

def sge_smin3_after := [llvm|
{
^0(%arg75 : i32, %arg76 : i32):
  %0 = llvm.mlir.constant(3 : i32) : i32
  %1 = llvm.add %arg75, %0 : i32
  %2 = llvm.icmp "sge" %arg76, %1 : i32
  "llvm.return"(%2) : (i1) -> ()
}
]

def visitADD_BNegAPlusA : LLVMPeepholeRewriteRefine 64 [Ty.llvm (.bitvec 64), Ty.llvm (.bitvec 64)] where
  lhs := [LV| {
    ^entry (%a: i64, %b: i64):
      %0 = llvm.sub %b, %a : i64
      %1 = llvm.add %0, %a : i64
      llvm.return %1 : i64
  }]
  rhs := [LV| {
    ^entry (%a: i64, %b: i64):
      llvm.return %b : i64
  }]

Lean.Elab.Tactic.State in Lean.Elab.Term.TermElabM

def shift_trunc_wrong_cmp_after := [llvm|
{
^0(%arg0 : i32):
  %0 = llvm.mlir.constant(24 : i32) : i32
  %1 = llvm.mlir.constant(1 : i8) : i8
  %2 = llvm.lshr %arg0, %0 : i32
  %3 = llvm.trunc %2 overflow<nuw> : i32 to i8
  %4 = llvm.icmp "slt" %3, %1 : i8
  "llvm.return"(%4) : (i1) -> ()
}
]

def trunc_equality_nsw_zext_after := [llvm|
{
^0(%arg16 : i32, %arg17 : i8):
  %0 = llvm.zext %arg17 : i8 to i32
  %1 = llvm.icmp "ne" %arg16, %0 : i32
  "llvm.return"(%1) : (i1) -> ()
}
]

def n9_before := [llvm|
{
^0(%arg1 : i64):
  %0 = llvm.mlir.constant(62) : i64
  %1 = llvm.mlir.constant(0) : i64
  %2 = llvm.lshr %arg1, %0 : i64
  %3 = llvm.sub %1, %2 : i64
  "llvm.return"(%3) : (i64) -> ()
}
]

def lshrult_02_01_after := [llvm|
{
^0(%arg350 : i4):
  %0 = llvm.mlir.constant(4 : i4) : i4
  %1 = llvm.icmp "ult" %arg350, %0 : i4
  "llvm.return"(%1) : (i1) -> ()
}
]

def positive_biggershl_ashrexact_before := [llvm|
{
^0(%arg39 : i8):
  %0 = llvm.mlir.constant(3 : i8) : i8
  %1 = llvm.mlir.constant(6 : i8) : i8
  %2 = llvm.ashr exact %arg39, %0 : i8
  %3 = llvm.shl %2, %1 : i8
  "llvm.return"(%3) : (i8) -> ()
}
]

def test13_after := [llvm|
{
^0(%arg7 : i32):
  %0 = llvm.mlir.constant(1 : i32) : i32
  %1 = llvm.icmp "ugt" %arg7, %0 : i32
  "llvm.return"(%1) : (i1) -> ()
}
]

def constLLVM_23 : Com LLVMPlusRiscV ⟨[]⟩ .pure (.llvm (.bitvec 64)) := [LV| {
  ^entry ():
    %1 = llvm.mlir.constant (-23) : i64
    llvm.return %1 : i64
  }]

def min_of_max_swap_after := [llvm|
{
^0(%arg19 : i32):
  %0 = llvm.mlir.constant(-1 : i32) : i32
  "llvm.return"(%0) : (i32) -> ()
}
]

def andcond_before := [llvm|
{
^0(%arg169 : i1, %arg170 : i1, %arg171 : i8, %arg172 : i8, %arg173 : i8):
  %0 = llvm.mlir.constant(false) : i1
  %1 = "llvm.select"(%arg169, %arg170, %0) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i1, i1) -> i1
  %2 = "llvm.select"(%arg169, %arg171, %arg172) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i8, i8) -> i8
  %3 = "llvm.select"(%1, %arg173, %2) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i8, i8) -> i8
  "llvm.return"(%3) : (i8) -> ()
}
]

def slt_swap_and_not_max_logical_before := [llvm|
{
^0(%arg116 : i8, %arg117 : i8):
  %0 = llvm.mlir.constant(127 : i8) : i8
  %1 = llvm.mlir.constant(false) : i1
  %2 = llvm.icmp "sgt" %arg117, %arg116 : i8
  %3 = llvm.icmp "ne" %arg116, %0 : i8
  %4 = "llvm.select"(%2, %3, %1) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i1, i1) -> i1
  "llvm.return"(%4) : (i1) -> ()
}
]

def test3_before := [llvm|
{
^0(%arg307 : i1):
  %0 = llvm.mlir.constant(false) : i1
  %1 = llvm.and %arg307, %0 : i1
  "llvm.return"(%1) : (i1) -> ()
}
]

@[simp_denote]
def icmp_eq_llvm_32 : Com LLVMPlusRiscV ⟨[.llvm (.bitvec 32), .llvm (.bitvec 32)]⟩
  .pure (.llvm (.bitvec 1)) := [LV| {
  ^entry (%lhs: i32, %rhs: i32):
    %1 = llvm.icmp.eq %lhs, %rhs : i32
    llvm.return %1 : i1
  }]

def main5_like_logical_before := [llvm|
{
^0(%arg111 : i32, %arg112 : i32):
  %0 = llvm.mlir.constant(7 : i32) : i32
  %1 = llvm.mlir.constant(false) : i1
  %2 = llvm.mlir.constant(0 : i32) : i32
  %3 = llvm.mlir.constant(1 : i32) : i32
  %4 = llvm.and %arg111, %0 : i32
  %5 = llvm.icmp "eq" %4, %0 : i32
  %6 = llvm.and %arg112, %0 : i32
  %7 = llvm.icmp "eq" %6, %0 : i32
  %8 = "llvm.select"(%5, %7, %1) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i1, i1) -> i1
  %9 = "llvm.select"(%8, %2, %3) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i32, i32) -> i32
  "llvm.return"(%9) : (i32) -> ()
}
]

def test_invert_demorgan_and3_after := [llvm|
{
^0(%arg5 : i32, %arg6 : i32):
  %0 = llvm.mlir.constant(4095 : i32) : i32
  %1 = llvm.sub %arg5, %arg6 : i32
  %2 = llvm.and %1, %0 : i32
  %3 = llvm.icmp "eq" %2, %0 : i32
  "llvm.return"(%3) : (i1) -> ()
}
]

def or_consts_logical_after := [llvm|
{
^0(%arg160 : i32, %arg161 : i32, %arg162 : i32):
  %0 = llvm.mlir.constant(12 : i32) : i32
  %1 = llvm.and %arg160, %0 : i32
  %2 = llvm.icmp "eq" %1, %0 : i32
  "llvm.return"(%2) : (i1) -> ()
}
]

def shl_add_nuw_before := [llvm|
{
^0(%arg69 : i32):
  %0 = llvm.mlir.constant(5 : i32) : i32
  %1 = llvm.mlir.constant(6 : i32) : i32
  %2 = llvm.add %arg69, %0 overflow<nuw> : i32
  %3 = llvm.shl %1, %2 : i32
  "llvm.return"(%3) : (i32) -> ()
}
]

def ashr_ult_0_before := [llvm|
{
^0(%arg98 : i4):
  %0 = llvm.mlir.constant(1 : i4) : i4
  %1 = llvm.mlir.constant(0 : i4) : i4
  %2 = llvm.ashr %arg98, %0 : i4
  %3 = llvm.icmp "ult" %2, %1 : i4
  "llvm.return"(%3) : (i1) -> ()
}
]

List.Vector.replicate in Mathlib.Data.Vector.Defs

def mul_of_bool_no_lz_other_op_before := [llvm|
{
^0(%arg85 : i32, %arg86 : i8):
  %0 = llvm.mlir.constant(1 : i32) : i32
  %1 = llvm.mlir.constant(127 : i32) : i32
  %2 = llvm.and %arg85, %0 : i32
  %3 = llvm.sext %arg86 : i8 to i32
  %4 = llvm.mul %2, %3 overflow<nsw,nuw> : i32
  %5 = llvm.icmp "sgt" %4, %1 : i32
  "llvm.return"(%5) : (i1) -> ()
}
]

def xor_of_icmps_to_eq_before := [llvm|
{
^0(%arg21 : i8):
  %0 = llvm.mlir.constant(126 : i8) : i8
  %1 = llvm.mlir.constant(-128 : i8) : i8
  %2 = llvm.icmp "sgt" %arg21, %0 : i8
  %3 = llvm.icmp "slt" %arg21, %1 : i8
  %4 = llvm.xor %3, %2 : i1
  "llvm.return"(%4) : (i1) -> ()
}
]

def one_sdiv { w : Nat} {a : BitVec w} (ha0 : a ≠ 0) (ha1 : a ≠ 1)
    (hao : a ≠ allOnes w) :
    BitVec.sdiv (1#w) a = 0#w :=

def t20_before := [llvm|
{
^0(%arg145 : i8, %arg146 : i16):
  %0 = llvm.mlir.constant(-42 : i16) : i16
  %1 = llvm.shl %0, %arg146 : i16
  %2 = llvm.trunc %1 : i16 to i8
  %3 = llvm.sub %arg145, %2 : i8
  "llvm.return"(%3) : (i8) -> ()
}
]

def lshr_add_before := [llvm|
{
^0(%arg81 : i8, %arg82 : i8):
  %0 = llvm.mlir.constant(42 : i8) : i8
  %1 = llvm.mlir.constant(5 : i8) : i8
  %2 = llvm.srem %arg81, %0 : i8
  %3 = llvm.lshr %arg82, %1 : i8
  %4 = llvm.add %3, %2 : i8
  %5 = llvm.shl %4, %1 : i8
  "llvm.return"(%5) : (i8) -> ()
}
]

def lsb_mask_sign_zext_after := [llvm|
{
^0(%arg11 : i32):
  %0 = llvm.mlir.constant(0 : i32) : i32
  %1 = llvm.icmp "eq" %arg11, %0 : i32
  %2 = llvm.zext %1 : i1 to i32
  "llvm.return"(%2) : (i32) -> ()
}
]

def trunc_shl_33_i32_i64_before := [llvm|
{
^0(%arg33 : i64):
  %0 = llvm.mlir.constant(33) : i64
  %1 = llvm.shl %arg33, %0 : i64
  %2 = llvm.trunc %1 : i64 to i32
  "llvm.return"(%2) : (i32) -> ()
}
]

def eq_smax3_after := [llvm|
{
^0(%arg59 : i32, %arg60 : i32):
  %0 = llvm.mlir.constant(3 : i32) : i32
  %1 = llvm.add %arg59, %0 : i32
  %2 = llvm.icmp "sge" %1, %arg60 : i32
  "llvm.return"(%2) : (i1) -> ()
}
]

def lshrult_01_12_exact_before := [llvm|
{
^0(%arg137 : i4):
  %0 = llvm.mlir.constant(1 : i4) : i4
  %1 = llvm.mlir.constant(-4 : i4) : i4
  %2 = llvm.lshr exact %arg137, %0 : i4
  %3 = llvm.icmp "ult" %2, %1 : i4
  "llvm.return"(%3) : (i1) -> ()
}
]

def add_or_and_commutative_before := [llvm|
{
^0(%arg17 : i32, %arg18 : i32):
  %0 = llvm.or %arg17, %arg18 : i32
  %1 = llvm.and %arg18, %arg17 : i32
  %2 = llvm.add %0, %1 : i32
  "llvm.return"(%2) : (i32) -> ()
}
]

def test2_after := [llvm|
{
^0(%arg4 : i32, %arg5 : i32):
  %0 = llvm.mlir.constant(32 : i32) : i32
  %1 = llvm.xor %arg4, %arg5 : i32
  %2 = llvm.icmp "eq" %arg4, %arg5 : i32
  %3 = llvm.icmp "eq" %1, %0 : i32
  %4 = llvm.xor %2, %3 : i1
  "llvm.return"(%4) : (i1) -> ()
}
]

def test11_after := [llvm|
{
^0(%arg184 : i32, %arg185 : i32):
  %0 = llvm.and %arg185, %arg184 : i32
  "llvm.return"(%0) : (i32) -> ()
}
]

def add_umin_simplify2_before := [llvm|
{
^0(%arg53 : i32):
  %0 = llvm.mlir.constant(43 : i32) : i32
  %1 = llvm.mlir.constant(42 : i32) : i32
  %2 = llvm.add %arg53, %0 overflow<nuw> : i32
  %3 = llvm.icmp "ult" %2, %1 : i32
  %4 = "llvm.select"(%3, %2, %1) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i32, i32) -> i32
  "llvm.return"(%4) : (i32) -> ()
}
]

def and_xor_commute1_before := [llvm|
{
^0(%arg155 : i32, %arg156 : i32):
  %0 = llvm.mlir.constant(42 : i32) : i32
  %1 = llvm.udiv %0, %arg155 : i32
  %2 = llvm.udiv %0, %arg156 : i32
  %3 = llvm.and %2, %1 : i32
  %4 = llvm.xor %2, %3 : i32
  "llvm.return"(%4) : (i32) -> ()
}
]

def one_inst_com (w : ℕ) :
    Com InstCombine.LLVM [LLVM.Ty.bitvec w] .pure [LLVM.Ty.bitvec w] :=
  Com.var (not w 0) <|
  Com.ret ⟨0, rfl⟩

def binopNfa (op : Binop) (m1 m2 : CNFA n) : CNFA n :=
  match op with
  | .and => m1.inter m2
  | .or => m1.union m2
  | .impl => m1.neg.union m2
  | .equiv => (m1.neg.union m2).inter (m2.neg.union m1)

def t0_before := [llvm|
{
^0(%arg206 : i8):
  %0 = llvm.mlir.constant(-42 : i8) : i8
  %1 = llvm.sub %arg206, %0 : i8
  "llvm.return"(%1) : (i8) -> ()
}
]

def and_two_ranges_to_mask_and_range_no_add_on_one_range_before := [llvm|
{
^0(%arg249 : i16):
  %0 = llvm.mlir.constant(12 : i16) : i16
  %1 = llvm.mlir.constant(16 : i16) : i16
  %2 = llvm.mlir.constant(28 : i16) : i16
  %3 = llvm.icmp "uge" %arg249, %0 : i16
  %4 = llvm.icmp "ult" %arg249, %1 : i16
  %5 = llvm.icmp "uge" %arg249, %2 : i16
  %6 = llvm.or %4, %5 : i1
  %7 = llvm.and %3, %6 : i1
  "llvm.return"(%7) : (i1) -> ()
}
]

def test_add_nuw__nsw_is_safe_after := [llvm|
{
^0(%arg38 : i32):
  %0 = llvm.mlir.constant(-2147483648 : i32) : i32
  %1 = llvm.mlir.constant(1 : i32) : i32
  %2 = llvm.or %arg38, %0 : i32
  %3 = llvm.add %2, %1 overflow<nsw> : i32
  "llvm.return"(%3) : (i32) -> ()
}
]

def select_ashr_before := [llvm|
{
^0(%arg6 : i1, %arg7 : i128, %arg8 : i128):
  %0 = llvm.ashr %arg7, %arg8 : i128
  %1 = "llvm.select"(%arg6, %0, %arg7) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i128, i128) -> i128
  "llvm.return"(%1) : (i128) -> ()
}
]

def sdiv4_before := [llvm|
{
^0(%arg36 : i32):
  %0 = llvm.mlir.constant(3 : i32) : i32
  %1 = llvm.sdiv exact %arg36, %0 : i32
  %2 = llvm.mul %1, %0 : i32
  "llvm.return"(%2) : (i32) -> ()
}
]

def sub_select_sext_op_swapped_non_const_args_after := [llvm|
{
^0(%arg6 : i1, %arg7 : i6, %arg8 : i6):
  %0 = llvm.mlir.constant(-1 : i6) : i6
  %1 = llvm.mlir.constant(0 : i6) : i6
  %2 = llvm.xor %arg7, %0 : i6
  %3 = llvm.sub %1, %arg8 : i6
  %4 = "llvm.select"(%arg6, %2, %3) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i6, i6) -> i6
  "llvm.return"(%4) : (i6) -> ()
}
]

def test59_after := [llvm|
{
^0(%arg122 : i8, %arg123 : i8):
  %0 = llvm.mlir.constant(4 : i32) : i32
  %1 = llvm.mlir.constant(48 : i32) : i32
  %2 = llvm.mlir.constant(4 : i8) : i8
  %3 = llvm.zext %arg122 : i8 to i32
  %4 = llvm.shl %3, %0 overflow<nsw,nuw> : i32
  %5 = llvm.and %4, %1 : i32
  %6 = llvm.lshr %arg123, %2 : i8
  %7 = llvm.zext nneg %6 : i8 to i32
  %8 = llvm.or disjoint %5, %7 : i32
  %9 = llvm.zext nneg %8 : i32 to i64
  "llvm.return"(%9) : (i64) -> ()
}
]

def or_nand_xor_common_op_commute0_after := [llvm|
{
^0(%arg77 : i4, %arg78 : i4, %arg79 : i4):
  %0 = llvm.mlir.constant(-1 : i4) : i4
  %1 = llvm.and %arg77, %arg79 : i4
  %2 = llvm.and %1, %arg78 : i4
  %3 = llvm.xor %2, %0 : i4
  "llvm.return"(%3) : (i4) -> ()
}
]

def simplify_and_common_op_commute1_before := [llvm|
{
^0(%arg29 : i4, %arg30 : i4, %arg31 : i4):
  %0 = llvm.mlir.constant(-1 : i4) : i4
  %1 = llvm.or %arg30, %arg29 : i4
  %2 = llvm.or %1, %arg31 : i4
  %3 = llvm.xor %2, %0 : i4
  %4 = llvm.and %3, %arg29 : i4
  "llvm.return"(%4) : (i4) -> ()
}
]

def castCircLe {n m : Nat} (c : Circuit (Vars fsm.α arity n)) (hnm : n ≤ m := by admit /- proof elided -/
) :
    Circuit (Vars fsm.α arity m) :=
  c.map (fun v => v.castLe hnm)

def lshr_and_before := [llvm|
{
^0(%arg18 : i8):
  %0 = llvm.mlir.constant(48 : i8) : i8
  %1 = llvm.mlir.constant(1 : i8) : i8
  %2 = llvm.mlir.constant(64 : i8) : i8
  %3 = llvm.lshr %0, %arg18 : i8
  %4 = llvm.add %arg18, %1 : i8
  %5 = llvm.lshr %2, %4 : i8
  %6 = llvm.and %3, %5 : i8
  "llvm.return"(%6) : (i8) -> ()
}
]

def zext_sext_add_icmp_eq_minus1_after := [llvm|
{
^0(%arg84 : i1, %arg85 : i1):
  %0 = llvm.mlir.constant(true) : i1
  %1 = llvm.xor %arg84, %0 : i1
  %2 = llvm.and %arg85, %1 : i1
  "llvm.return"(%2) : (i1) -> ()
}
]

def masked_icmps_mask_notallzeros_bmask_mixed_negated_1_after := [llvm|
{
^0(%arg72 : i32):
  %0 = llvm.mlir.constant(15 : i32) : i32
  %1 = llvm.mlir.constant(9 : i32) : i32
  %2 = llvm.and %arg72, %0 : i32
  %3 = llvm.icmp "ne" %2, %1 : i32
  "llvm.return"(%3) : (i1) -> ()
}
]

def uge_swap_and_max_logical_before := [llvm|
{
^0(%arg228 : i8, %arg229 : i8):
  %0 = llvm.mlir.constant(-1 : i8) : i8
  %1 = llvm.mlir.constant(false) : i1
  %2 = llvm.icmp "ule" %arg229, %arg228 : i8
  %3 = llvm.icmp "eq" %arg228, %0 : i8
  %4 = "llvm.select"(%2, %3, %1) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i1, i1) -> i1
  "llvm.return"(%4) : (i1) -> ()
}
]

def pr51551_after := [llvm|
{
^0(%arg8 : i32, %arg9 : i32):
  %0 = llvm.mlir.constant(3 : i32) : i32
  %1 = llvm.mlir.constant(0 : i32) : i32
  %2 = llvm.and %arg8, %0 : i32
  %3 = llvm.icmp "eq" %2, %1 : i32
  "llvm.return"(%3) : (i1) -> ()
}
]

def add_nuw_nsw_or_and_before := [llvm|
{
^0(%arg7 : i32, %arg8 : i32):
  %0 = llvm.or %arg7, %arg8 : i32
  %1 = llvm.and %arg7, %arg8 : i32
  %2 = llvm.add %0, %1 overflow<nsw,nuw> : i32
  "llvm.return"(%2) : (i32) -> ()
}
]

def ashr_mul_times_5_div_4_exact_2_before := [llvm|
{
^0(%arg12 : i32):
  %0 = llvm.mlir.constant(5 : i32) : i32
  %1 = llvm.mlir.constant(2 : i32) : i32
  %2 = llvm.mul %arg12, %0 overflow<nsw> : i32
  %3 = llvm.ashr exact %2, %1 : i32
  "llvm.return"(%3) : (i32) -> ()
}
]

def test5_after := [llvm|
{
^0(%arg32 : i32):
  %0 = llvm.mlir.constant(30000 : i32) : i32
  %1 = llvm.urem %arg32, %0 : i32
  %2 = llvm.zext nneg %1 : i32 to i64
  "llvm.return"(%2) : (i64) -> ()
}
]

def test4_after := [llvm|
{
^0(%arg4 : i67, %arg5 : i67):
  %0 = llvm.mlir.constant(2 : i67) : i67
  %1 = llvm.and %arg4, %0 : i67
  "llvm.return"(%1) : (i67) -> ()
}
]

def PR42691_3_logical_after := [llvm|
{
^0(%arg338 : i32):
  %0 = llvm.mlir.constant(-2147483647 : i32) : i32
  %1 = llvm.icmp "ult" %arg338, %0 : i32
  "llvm.return"(%1) : (i1) -> ()
}
]

def ashr_and_or_disjoint_before := [llvm|
{
^0(%arg41 : i8, %arg42 : i8):
  %0 = llvm.mlir.constant(42 : i8) : i8
  %1 = llvm.mlir.constant(2 : i8) : i8
  %2 = llvm.mlir.constant(13 : i8) : i8
  %3 = llvm.srem %arg41, %0 : i8
  %4 = llvm.ashr %arg42, %1 : i8
  %5 = llvm.and %4, %2 : i8
  %6 = llvm.or disjoint %3, %5 : i8
  %7 = llvm.shl %6, %1 : i8
  "llvm.return"(%7) : (i8) -> ()
}
]

def or_xor_tree_1000_after := [llvm|
{
^0(%arg21 : i32, %arg22 : i32, %arg23 : i32):
  %0 = llvm.mlir.constant(42 : i32) : i32
  %1 = llvm.mul %arg21, %0 : i32
  %2 = llvm.mul %arg22, %0 : i32
  %3 = llvm.mul %arg23, %0 : i32
  %4 = llvm.xor %1, %2 : i32
  %5 = llvm.or %4, %3 : i32
  "llvm.return"(%5) : (i32) -> ()
}
]

def xor_or_xor_common_op_commute1_after := [llvm|
{
^0(%arg80 : i32, %arg81 : i32, %arg82 : i32):
  %0 = llvm.mlir.constant(-1 : i32) : i32
  %1 = llvm.xor %arg80, %0 : i32
  %2 = llvm.and %arg81, %1 : i32
  %3 = llvm.xor %2, %arg82 : i32
  "llvm.return"(%3) : (i32) -> ()
}
]

def scalar_i32_shl_ult_const_before := [llvm|
{
^0(%arg15 : i32):
  %0 = llvm.mlir.constant(11 : i32) : i32
  %1 = llvm.mlir.constant(131072 : i32) : i32
  %2 = llvm.shl %arg15, %0 : i32
  %3 = llvm.icmp "ult" %2, %1 : i32
  "llvm.return"(%3) : (i1) -> ()
}
]

def Expr.op : Expr Op T → Op
  | ⟨_, op, _, _⟩ => op

def or_to_nxor_multiuse_before := [llvm|
{
^0(%arg56 : i32, %arg57 : i32):
  %0 = llvm.mlir.constant(-1 : i32) : i32
  %1 = llvm.and %arg56, %arg57 : i32
  %2 = llvm.or %arg56, %arg57 : i32
  %3 = llvm.xor %2, %0 : i32
  %4 = llvm.or %1, %3 : i32
  %5 = llvm.mul %1, %3 : i32
  %6 = llvm.mul %5, %4 : i32
  "llvm.return"(%6) : (i32) -> ()
}
]

def add_mask_ashr28_i32_before := [llvm|
{
^0(%arg2 : i32):
  %0 = llvm.mlir.constant(28 : i32) : i32
  %1 = llvm.mlir.constant(8 : i32) : i32
  %2 = llvm.ashr %arg2, %0 : i32
  %3 = llvm.and %2, %1 : i32
  %4 = llvm.add %3, %2 : i32
  "llvm.return"(%4) : (i32) -> ()
}
]

def sge_and_max_logical_samesign_before := [llvm|
{
^0(%arg252 : i8, %arg253 : i8):
  %0 = llvm.mlir.constant(127 : i8) : i8
  %1 = llvm.mlir.constant(false) : i1
  %2 = llvm.icmp "sge" %arg252, %arg253 : i8
  %3 = llvm.icmp "eq" %arg252, %0 : i8
  %4 = "llvm.select"(%2, %3, %1) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i1, i1) -> i1
  "llvm.return"(%4) : (i1) -> ()
}
]

def sub_from_variable_of_sub_from_constant_before := [llvm|
{
^0(%arg167 : i8, %arg168 : i8):
  %0 = llvm.mlir.constant(42 : i8) : i8
  %1 = llvm.sub %0, %arg167 : i8
  %2 = llvm.sub %arg168, %1 : i8
  "llvm.return"(%2) : (i8) -> ()
}
]

def add_smin_simplify2_after := [llvm|
{
^0(%arg33 : i32):
  %0 = llvm.mlir.constant(-3 : i32) : i32
  %1 = llvm.add %arg33, %0 overflow<nsw> : i32
  "llvm.return"(%1) : (i32) -> ()
}
]

def scalar_i16_shl_and_negC_eq_before := [llvm|
{
^0(%arg33 : i16, %arg34 : i16):
  %0 = llvm.mlir.constant(-128 : i16) : i16
  %1 = llvm.mlir.constant(0 : i16) : i16
  %2 = llvm.shl %arg33, %arg34 : i16
  %3 = llvm.and %2, %0 : i16
  %4 = llvm.icmp "eq" %3, %1 : i16
  "llvm.return"(%4) : (i1) -> ()
}
]

def test7_after := [llvm|
{
^0(%arg0 : i47):
  %0 = llvm.mlir.constant(-70368744177664 : i47) : i47
  %1 = llvm.mlir.constant(70368040490200 : i47) : i47
  %2 = llvm.and %arg0, %0 : i47
  %3 = llvm.or disjoint %2, %1 : i47
  "llvm.return"(%3) : (i47) -> ()
}
]

def bools_multi_uses2_after := [llvm|
{
^0(%arg39 : i1, %arg40 : i1, %arg41 : i1):
  %0 = "llvm.select"(%arg41, %arg40, %arg39) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i1, i1) -> i1
  "llvm.return"(%0) : (i1) -> ()
}
]

Int.neg in Init.Data.Int.Basic

def State.empty (lets : Lets d Γstart .pure Γ) : State d lets where
  var2var := fun v => ⟨v, by admit /- proof elided -/
  ⟩
  expr2cache := fun α e => .none

def trunc_lshr_trunc_before := [llvm|
{
^0(%arg14 : i64):
  %0 = llvm.mlir.constant(8 : i32) : i32
  %1 = llvm.trunc %arg14 : i64 to i32
  %2 = llvm.lshr %1, %0 : i32
  %3 = llvm.trunc %2 : i32 to i8
  "llvm.return"(%3) : (i8) -> ()
}
]

def fstValPure (a : Γ.Var (MLIR2DCPlus.Ty.valuestream2 r)) : Expr (DCPlus) Γ .pure (.valuestream r) :=
    Expr.mk
    (op := .fstValPure r)
    (ty_eq := rfl)
    (eff_le := by admit /- proof elided -/
    )
    (args := .cons a <| .nil)
    (regArgs := .nil)

def lshrult_03_06_exact_after := [llvm|
{
^0(%arg111 : i4):
  %0 = llvm.mlir.constant(true) : i1
  "llvm.return"(%0) : (i1) -> ()
}
]

def test_invalid_simplify_select_1_before := [llvm|
{
^0(%arg206 : i8):
  %0 = llvm.mlir.constant(0 : i8) : i8
  %1 = llvm.mlir.constant(1 : i8) : i8
  %2 = llvm.icmp "eq" %arg206, %0 : i8
  %3 = llvm.sub %arg206, %1 : i8
  %4 = "llvm.select"(%2, %1, %3) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i8, i8) -> i8
  "llvm.return"(%4) : (i8) -> ()
}
]

def pr40493_before := [llvm|
{
^0(%arg18 : i32):
  %0 = llvm.mlir.constant(12 : i32) : i32
  %1 = llvm.mlir.constant(4 : i32) : i32
  %2 = llvm.mlir.constant(0 : i32) : i32
  %3 = llvm.mul %arg18, %0 : i32
  %4 = llvm.and %3, %1 : i32
  %5 = llvm.icmp "eq" %4, %2 : i32
  "llvm.return"(%5) : (i1) -> ()
}
]

def OrZextZext : LLVMPeepholeRewriteRefine 64 [Ty.llvm (.bitvec 32), Ty.llvm (.bitvec 32)] where
  lhs := [LV| {
    ^entry (%x: i32, %y: i32):
      %0 = llvm.zext %x : i32 to i64
      %1 = llvm.zext %y : i32 to i64
      %2 = llvm.or %0, %1 : i64
      llvm.return %2 : i64
  }]
  rhs := [LV| {
    ^entry (%x: i32, %y: i32):
      %0 = llvm.or %x, %y : i32
      %1 = llvm.zext %0 : i32 to i64
      llvm.return %1 : i64
  }]

def bad_add0_after := [llvm|
{
^0(%arg2 : i32, %arg3 : i32):
  %0 = llvm.mlir.constant(1 : i32) : i32
  %1 = llvm.shl %0, %arg2 overflow<nuw> : i32
  %2 = llvm.add %1, %arg3 : i32
  "llvm.return"(%2) : (i32) -> ()
}
]

def or_not_and_commute8_before := [llvm|
{
^0(%arg513 : i32, %arg514 : i32, %arg515 : i32):
  %0 = llvm.mlir.constant(42 : i32) : i32
  %1 = llvm.mlir.constant(-1 : i32) : i32
  %2 = llvm.sdiv %0, %arg513 : i32
  %3 = llvm.sdiv %0, %arg514 : i32
  %4 = llvm.or %2, %3 : i32
  %5 = llvm.xor %4, %1 : i32
  %6 = llvm.and %5, %arg515 : i32
  %7 = llvm.or %arg515, %2 : i32
  %8 = llvm.xor %7, %1 : i32
  %9 = llvm.and %3, %8 : i32
  %10 = llvm.or %6, %9 : i32
  "llvm.return"(%10) : (i32) -> ()
}
]

def trunc_lshr_sext_before := [llvm|
{
^0(%arg46 : i8):
  %0 = llvm.mlir.constant(6 : i32) : i32
  %1 = llvm.sext %arg46 : i8 to i32
  %2 = llvm.lshr %1, %0 : i32
  %3 = llvm.trunc %2 : i32 to i8
  "llvm.return"(%3) : (i8) -> ()
}
]

def CNFA.determinize_spec (m : CNFA n)
  {M : NFA' n} (hsim : m.Sim M) :
    m.determinize.Sim M.determinize :=

def alive_AndOrXor_2663_src  (w : Nat)   :=
[llvm( w )| {
^bb0(%a : _, %b : _):
  %v1 = llvm.icmp.ule %a, %b
  %v2 = llvm.icmp.ne %a, %b
  %v3 = llvm.xor %v1, %v2 : i1
  llvm.return %v3 : i1
}]

def logic_or_logic_and_6_before := [llvm|
{
^0(%arg72 : i1, %arg73 : i1, %arg74 : i1):
  %0 = llvm.mlir.constant(true) : i1
  %1 = llvm.mlir.constant(false) : i1
  %2 = "llvm.select"(%arg73, %0, %arg72) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i1, i1) -> i1
  %3 = "llvm.select"(%arg72, %0, %arg74) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i1, i1) -> i1
  %4 = "llvm.select"(%3, %2, %1) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i1, i1) -> i1
  "llvm.return"(%4) : (i1) -> ()
}
]

def masked_icmps_mask_notallzeros_bmask_mixed_negated_swapped_4_logical_after := [llvm|
{
^0(%arg17 : i32):
  %0 = llvm.mlir.constant(15 : i32) : i32
  %1 = llvm.mlir.constant(8 : i32) : i32
  %2 = llvm.and %arg17, %0 : i32
  %3 = llvm.icmp "ne" %2, %1 : i32
  "llvm.return"(%3) : (i1) -> ()
}
]

def ashr_eq_exact_after := [llvm|
{
^0(%arg173 : i8):
  %0 = llvm.mlir.constant(80 : i8) : i8
  %1 = llvm.icmp "eq" %arg173, %0 : i8
  "llvm.return"(%1) : (i1) -> ()
}
]

def splat_mul_known_lz_after := [llvm|
{
^0(%arg72 : i32):
  %0 = llvm.mlir.constant(true) : i1
  "llvm.return"(%0) : (i1) -> ()
}
]

def or_not_and_and_not_and_xor_commute5_before := [llvm|
{
^0(%arg274 : i32, %arg275 : i32, %arg276 : i32):
  %0 = llvm.mlir.constant(-1 : i32) : i32
  %1 = llvm.and %arg275, %arg276 : i32
  %2 = llvm.xor %1, %0 : i32
  %3 = llvm.or %2, %arg274 : i32
  %4 = llvm.xor %arg275, %arg276 : i32
  %5 = llvm.and %4, %arg274 : i32
  %6 = llvm.xor %5, %0 : i32
  %7 = llvm.and %6, %3 : i32
  "llvm.return"(%7) : (i32) -> ()
}
]

List.Perm in Init.Data.List.Basic

def lshrult_02_02_before := [llvm|
{
^0(%arg349 : i4):
  %0 = llvm.mlir.constant(2 : i4) : i4
  %1 = llvm.lshr %arg349, %0 : i4
  %2 = llvm.icmp "ult" %1, %0 : i4
  "llvm.return"(%2) : (i1) -> ()
}
]

def add_or_sub_comb_i128_commuted3_nuw_nsw_after := [llvm|
{
^0(%arg14 : i128):
  %0 = llvm.mul %arg14, %arg14 : i128
  "llvm.return"(%0) : (i128) -> ()
}
]

def mul8_low_A0_B0_before := [llvm|
{
^0(%arg60 : i8, %arg61 : i8):
  %0 = llvm.mlir.constant(15 : i8) : i8
  %1 = llvm.mlir.constant(4 : i8) : i8
  %2 = llvm.and %arg60, %0 : i8
  %3 = llvm.lshr %arg60, %1 : i8
  %4 = llvm.and %arg61, %0 : i8
  %5 = llvm.lshr %arg61, %1 : i8
  %6 = llvm.mul %5, %arg60 : i8
  %7 = llvm.mul %3, %arg61 : i8
  %8 = llvm.mul %4, %2 : i8
  %9 = llvm.add %6, %7 : i8
  %10 = llvm.shl %9, %1 : i8
  %11 = llvm.add %10, %8 : i8
  "llvm.return"(%11) : (i8) -> ()
}
]

def add_smin_simplify_before := [llvm|
{
^0(%arg34 : i32):
  %0 = llvm.mlir.constant(-3 : i32) : i32
  %1 = llvm.mlir.constant(2147483644 : i32) : i32
  %2 = llvm.add %arg34, %0 overflow<nsw> : i32
  %3 = llvm.icmp "slt" %2, %1 : i32
  %4 = "llvm.select"(%3, %2, %1) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i32, i32) -> i32
  "llvm.return"(%4) : (i32) -> ()
}
]

def or_not_and_commute1_after := [llvm|
{
^0(%arg534 : i32, %arg535 : i32, %arg536 : i32):
  %0 = llvm.mlir.constant(42 : i32) : i32
  %1 = llvm.mlir.constant(-1 : i32) : i32
  %2 = llvm.sdiv %0, %arg535 : i32
  %3 = llvm.xor %2, %arg536 : i32
  %4 = llvm.xor %arg534, %1 : i32
  %5 = llvm.and %3, %4 : i32
  "llvm.return"(%5) : (i32) -> ()
}
]

def n2_after := [llvm|
{
^0(%arg39 : i32, %arg40 : i32, %arg41 : i1):
  %0 = llvm.mlir.constant(true) : i1
  %1 = llvm.icmp "ne" %arg39, %arg40 : i32
  %2 = llvm.xor %arg41, %0 : i1
  %3 = "llvm.select"(%2, %0, %1) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i1, i1) -> i1
  "llvm.return"(%3) : (i1) -> ()
}
]

instance : TyDenote Ty where
  toType
    | .int => ℤ
    | .bool => Bool
    | .nat => Nat

def test_shl_nsw__none_are_safe_after := [llvm|
{
^0(%arg66 : i32, %arg67 : i64):
  %0 = llvm.mlir.constant(2 : i32) : i32
  %1 = llvm.mlir.constant(-8 : i32) : i32
  %2 = llvm.shl %arg66, %0 : i32
  %3 = llvm.and %2, %1 : i32
  %4 = llvm.zext nneg %3 : i32 to i64
  %5 = llvm.ashr %arg67, %4 : i64
  "llvm.return"(%5) : (i64) -> ()
}
]

def n2_after := [llvm|
{
^0(%arg19 : i1, %arg20 : i8, %arg21 : i8, %arg22 : i8, %arg23 : i8):
  %0 = llvm.mlir.constant(true) : i1
  %1 = llvm.icmp "eq" %arg20, %arg21 : i8
  %2 = llvm.xor %arg19, %0 : i1
  %3 = llvm.or %1, %2 : i1
  "llvm.return"(%3) : (i1) -> ()
}
]

def prettifyBVExpr (bvExpr : GenBVExpr w) (displayNames: Std.HashMap Nat HydraVariable) (widthVals: Std.HashMap Nat HydraVariable): String :=
    match bvExpr with
    | .var idx => displayNames[idx]!.name.toString
    | .const bv =>
       toString bv.toInt
    | .bin lhs BVBinOp.add (.bin  (GenBVExpr.const bv) BVBinOp.add (GenBVExpr.un BVUnOp.not rhs)) =>
      if bv.toInt == 1 then 
        s! "({prettifyBVExpr lhs displayNames widthVals} - {prettifyBVExpr rhs displayNames widthVals})"
      else
        s! "({prettifyBVExpr lhs displayNames widthVals} + ({prettifyBVExpr (GenBVExpr.const bv) displayNames widthVals} + {prettifyBVExpr (GenBVExpr.un BVUnOp.not rhs) displayNames widthVals}))"
    | .bin lhs op rhs =>
       s! "({prettifyBVExpr lhs displayNames widthVals} {prettifyBVBinOp op} {prettifyBVExpr rhs displayNames widthVals})"
    | .un op operand =>
       s! "({op.toString} {prettifyBVExpr operand displayNames widthVals})"
    | .shiftLeft lhs rhs =>
        s! "({prettifyBVExpr lhs displayNames widthVals} <<< {prettifyBVExpr rhs displayNames widthVals})"
    | .shiftRight lhs rhs =>
        s! "({prettifyBVExpr lhs displayNames widthVals} >>> {prettifyBVExpr rhs displayNames widthVals})"
    | .arithShiftRight lhs rhs =>
        s! "({prettifyBVExpr lhs displayNames widthVals} >>>a {prettifyBVExpr rhs displayNames widthVals})"
    | .signExtend v expr => s! "BitVec.signExtend {widthVals[v]!.name.toString} {prettifyBVExpr expr displayNames widthVals}"
    | .zeroExtend v expr => s! "BitVec.zeroExtend {widthVals[v]!.name.toString} {prettifyBVExpr expr displayNames widthVals}"
    | .truncate v expr =>   s! "BitVec.truncate {widthVals[v]!.name.toString} {prettifyBVExpr expr displayNames widthVals}"
    | _ => bvExpr.toString

def Factor.reflect {w : Nat} (xs : Env w) : Factor → BitVec w
| .var n => xs[n]?.getD (0#w)
| .and x y => x.reflect xs &&& y.reflect xs
| .or x y => x.reflect xs ||| y.reflect xs
| .xor x y => x.reflect xs ^^^ y.reflect xs
| .not x => ~~~ (x.reflect xs)

def intro_example_rhs := [LV| {
  ^entry (%arg: i64, %amount: i64):
    llvm.return %arg : i64
  }]

def branch (c : ValueStream (BitVec 1)) (x : TokenStream) : TokenStream × TokenStream  :=
  Stream.corec₂ (β := ValueStream (BitVec 1) × TokenStream) (c, x) fun ⟨c, x⟩ =>
    Id.run <| do
      match c 0 with
        | none => (none, none, (c.tail, x))
        | some x₀ =>
          if x₀.msb then
            (some (), none, (c.tail, x.tail))
          else
            (none, some (), (c.tail, x.tail))

def positive_trunc_base_before := [llvm|
{
^0(%arg39 : i32):
  %0 = llvm.mlir.constant(-1 : i16) : i16
  %1 = llvm.mlir.constant(128 : i16) : i16
  %2 = llvm.mlir.constant(256 : i16) : i16
  %3 = llvm.trunc %arg39 : i32 to i16
  %4 = llvm.icmp "sgt" %3, %0 : i16
  %5 = llvm.add %3, %1 : i16
  %6 = llvm.icmp "ult" %5, %2 : i16
  %7 = llvm.and %4, %6 : i1
  "llvm.return"(%7) : (i1) -> ()
}
]

def not_or_or_and_no_and_commute1_before := [llvm|
{
^0(%arg112 : i32, %arg113 : i32, %arg114 : i32):
  %0 = llvm.mlir.constant(-1 : i32) : i32
  %1 = llvm.and %arg112, %arg113 : i32
  %2 = llvm.xor %1, %0 : i32
  %3 = llvm.xor %arg112, %0 : i32
  %4 = llvm.or %3, %arg113 : i32
  %5 = llvm.or %4, %arg114 : i32
  %6 = llvm.and %5, %2 : i32
  "llvm.return"(%6) : (i32) -> ()
}
]

HPow in Init.Prelude

def getBitVecTypeWidth? (t : Expr) : MetaM (Option Expr) := do
  let t ← instantiateMVars t
  let t ← whnf t
  match_expr t with
  | BitVec w => return some (← whnf w)
  | _ => return none

instance {n} : ShiftRight (BitVec n) := ⟨fun x y => x >>> y.toNat⟩

def lshrult_03_07_before := [llvm|
{
^0(%arg328 : i4):
  %0 = llvm.mlir.constant(3 : i4) : i4
  %1 = llvm.mlir.constant(7 : i4) : i4
  %2 = llvm.lshr %arg328, %0 : i4
  %3 = llvm.icmp "ult" %2, %1 : i4
  "llvm.return"(%3) : (i1) -> ()
}
]

def ashrslt_02_01_exact_after := [llvm|
{
^0(%arg36 : i4):
  %0 = llvm.mlir.constant(4 : i4) : i4
  %1 = llvm.icmp "slt" %arg36, %0 : i4
  "llvm.return"(%1) : (i1) -> ()
}
]

def positive_biggerLshr_lshrexact_after := [llvm|
{
^0(%arg32 : i32):
  %0 = llvm.mlir.constant(5 : i32) : i32
  %1 = llvm.mlir.constant(4194303 : i32) : i32
  %2 = llvm.lshr exact %arg32, %0 : i32
  %3 = llvm.and %2, %1 : i32
  "llvm.return"(%3) : (i32) -> ()
}
]

def n12_after := [llvm|
{
^0(%arg0 : i8):
  %0 = llvm.mlir.constant(6 : i8) : i8
  %1 = llvm.shl %arg0, %0 : i8
  %2 = llvm.ashr exact %1, %0 : i8
  "llvm.return"(%2) : (i8) -> ()
}
]

def sgt_mulzero_before := [llvm|
{
^0(%arg144 : i8):
  %0 = llvm.mlir.constant(0 : i8) : i8
  %1 = llvm.mlir.constant(21 : i8) : i8
  %2 = llvm.mul %arg144, %0 overflow<nsw> : i8
  %3 = llvm.icmp "sgt" %2, %1 : i8
  "llvm.return"(%3) : (i1) -> ()
}
]

def ugt_swap_or_not_min_logical_after := [llvm|
{
^0(%arg4 : i8, %arg5 : i8):
  %0 = llvm.mlir.constant(0 : i8) : i8
  %1 = llvm.icmp "ne" %arg4, %0 : i8
  "llvm.return"(%1) : (i1) -> ()
}
]

def different_size_zext_zext_ugt_after := [llvm|
{
^0(%arg28 : i7, %arg29 : i4):
  %0 = llvm.zext %arg29 : i4 to i7
  %1 = llvm.icmp "ugt" %arg28, %0 : i7
  "llvm.return"(%1) : (i1) -> ()
}
]

def test9b_after := [llvm|
{
^0(%arg109 : i32, %arg110 : i32):
  %0 = llvm.or %arg109, %arg110 : i32
  "llvm.return"(%0) : (i32) -> ()
}
]

Algebra in Mathlib.Algebra.Algebra.Defs

def icmp_ne_zext_eq_one_before := [llvm|
{
^0(%arg38 : i32):
  %0 = llvm.mlir.constant(1 : i32) : i32
  %1 = llvm.icmp "eq" %arg38, %0 : i32
  %2 = llvm.zext %1 : i1 to i32
  %3 = llvm.icmp "ne" %2, %arg38 : i32
  "llvm.return"(%3) : (i1) -> ()
}
]

def and_not_or_or_not_or_xor_commute4_before := [llvm|
{
^0(%arg313 : i32, %arg314 : i32, %arg315 : i32):
  %0 = llvm.mlir.constant(42 : i32) : i32
  %1 = llvm.mlir.constant(-1 : i32) : i32
  %2 = llvm.sdiv %0, %arg313 : i32
  %3 = llvm.or %arg314, %arg315 : i32
  %4 = llvm.xor %3, %1 : i32
  %5 = llvm.and %2, %4 : i32
  %6 = llvm.xor %arg314, %arg315 : i32
  %7 = llvm.or %2, %6 : i32
  %8 = llvm.xor %7, %1 : i32
  %9 = llvm.or %5, %8 : i32
  "llvm.return"(%9) : (i32) -> ()
}
]

def ashrslt_01_14_after := [llvm|
{
^0(%arg255 : i4):
  %0 = llvm.mlir.constant(-4 : i4) : i4
  %1 = llvm.icmp "slt" %arg255, %0 : i4
  "llvm.return"(%1) : (i1) -> ()
}
]

def test18_after := [llvm|
{
^0(%arg282 : i32):
  %0 = llvm.mlir.constant(127 : i32) : i32
  %1 = llvm.icmp "ugt" %arg282, %0 : i32
  "llvm.return"(%1) : (i1) -> ()
}
]

def samesign_inverted_commute3_before := [llvm|
{
^0(%arg97 : i32, %arg98 : i32):
  %0 = llvm.mlir.constant(-1 : i32) : i32
  %1 = llvm.mlir.constant(0 : i32) : i32
  %2 = llvm.and %arg97, %arg98 : i32
  %3 = llvm.icmp "sgt" %2, %0 : i32
  %4 = llvm.or %arg98, %arg97 : i32
  %5 = llvm.icmp "slt" %4, %1 : i32
  %6 = llvm.and %5, %3 : i1
  "llvm.return"(%6) : (i1) -> ()
}
]

def ripple_nsw6_after := [llvm|
{
^0(%arg13 : i16, %arg14 : i16):
  %0 = llvm.mlir.constant(-21845 : i16) : i16
  %1 = llvm.mlir.constant(-10923 : i16) : i16
  %2 = llvm.or %arg14, %0 : i16
  %3 = llvm.or %arg13, %1 : i16
  %4 = llvm.add %3, %2 overflow<nsw> : i16
  "llvm.return"(%4) : (i16) -> ()
}
]

def CNFA.toNFA (m : CNFA n) : NFA (BitVec n) m.m.states where
  start := { s | s.val ∈ m.m.initials }
  accept := { s | s.val ∈ m.m.finals }
  step s₁ a := { s₂ | s₂.val ∈ m.m.tr s₁.val a }

def slt_swap_or_not_max_commute_logical_after := [llvm|
{
^0(%arg48 : i8, %arg49 : i8):
  %0 = llvm.mlir.constant(127 : i8) : i8
  %1 = llvm.icmp "ne" %arg48, %0 : i8
  "llvm.return"(%1) : (i1) -> ()
}
]

def trunc_sandwich_after := [llvm|
{
^0(%arg70 : i32):
  %0 = llvm.mlir.constant(30 : i32) : i32
  %1 = llvm.lshr %arg70, %0 : i32
  %2 = llvm.trunc %1 overflow<nsw,nuw> : i32 to i12
  "llvm.return"(%2) : (i12) -> ()
}
]

def ashrslt_01_00_before := [llvm|
{
^0(%arg269 : i4):
  %0 = llvm.mlir.constant(1 : i4) : i4
  %1 = llvm.mlir.constant(0 : i4) : i4
  %2 = llvm.ashr %arg269, %0 : i4
  %3 = llvm.icmp "slt" %2, %1 : i4
  "llvm.return"(%3) : (i1) -> ()
}
]

def test2_before := [llvm|
{
^0(%arg0 : i999, %arg1 : i999):
  %0 = llvm.mlir.constant(65280 : i999) : i999
  %1 = llvm.and %arg0, %0 : i999
  %2 = llvm.and %arg1, %0 : i999
  %3 = llvm.icmp "ne" %1, %2 : i999
  "llvm.return"(%3) : (i1) -> ()
}
]

def uge_umin2_before := [llvm|
{
^0(%arg50 : i32, %arg51 : i32):
  %0 = llvm.icmp "ult" %arg51, %arg50 : i32
  %1 = "llvm.select"(%0, %arg51, %arg50) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i32, i32) -> i32
  %2 = llvm.icmp "uge" %1, %arg50 : i32
  "llvm.return"(%2) : (i1) -> ()
}
]

def pr40493_neg1_before := [llvm|
{
^0(%arg17 : i32):
  %0 = llvm.mlir.constant(11 : i32) : i32
  %1 = llvm.mlir.constant(4 : i32) : i32
  %2 = llvm.mlir.constant(0 : i32) : i32
  %3 = llvm.mul %arg17, %0 : i32
  %4 = llvm.and %3, %1 : i32
  %5 = llvm.icmp "eq" %4, %2 : i32
  "llvm.return"(%5) : (i1) -> ()
}
]

DecidableEq in Init.Prelude

instance : GetElem? MemoryState BlockId Block (fun m i => i ∈ m.mem) where
  getElem mem id h := mem.mem[id]
  getElem? mem id  := mem.mem[id]?

def main11_logical_before := [llvm|
{
^0(%arg21 : i32):
  %0 = llvm.mlir.constant(64 : i32) : i32
  %1 = llvm.mlir.constant(0 : i32) : i32
  %2 = llvm.mlir.constant(0 : i8) : i8
  %3 = llvm.mlir.constant(true) : i1
  %4 = llvm.mlir.constant(2 : i32) : i32
  %5 = llvm.mlir.constant(1 : i32) : i32
  %6 = llvm.and %arg21, %0 : i32
  %7 = llvm.icmp "eq" %6, %1 : i32
  %8 = llvm.trunc %arg21 : i32 to i8
  %9 = llvm.icmp "sge" %8, %2 : i8
  %10 = "llvm.select"(%7, %3, %9) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i1, i1) -> i1
  %11 = "llvm.select"(%10, %4, %5) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i32, i32) -> i32
  "llvm.return"(%11) : (i32) -> ()
}
]

def t2_symmetry_after := [llvm|
{
^0(%arg37 : i8, %arg38 : i8):
  %0 = llvm.mlir.constant(-1 : i8) : i8
  %1 = llvm.xor %arg37, %0 : i8
  %2 = llvm.icmp "ule" %arg38, %1 : i8
  "llvm.return"(%2) : (i1) -> ()
}
]

def add_and_or_after := [llvm|
{
^0(%arg15 : i32, %arg16 : i32):
  %0 = llvm.add %arg15, %arg16 : i32
  "llvm.return"(%0) : (i32) -> ()
}
]

def llvm_sub_lower_riscv_no_flag_self: LLVMPeepholeRewriteRefine 64 [Ty.llvm (.bitvec 64)] where
  lhs := llvm_sub_self_ex
  rhs := sub_riscv_self_ex
  correct := by admit /- proof elided -/

def ne_umax4_after := [llvm|
{
^0(%arg38 : i32, %arg39 : i32):
  %0 = llvm.mlir.constant(3 : i32) : i32
  %1 = llvm.add %arg38, %0 : i32
  %2 = llvm.icmp "ult" %1, %arg39 : i32
  "llvm.return"(%2) : (i1) -> ()
}
]

def ne_umax2_after := [llvm|
{
^0(%arg42 : i32, %arg43 : i32):
  %0 = llvm.icmp "ult" %arg42, %arg43 : i32
  "llvm.return"(%0) : (i1) -> ()
}
]

def src_x_or_mask_ne_after := [llvm|
{
^0(%arg3 : i8, %arg4 : i8, %arg5 : i1):
  %0 = llvm.mlir.constant(-1 : i8) : i8
  %1 = llvm.mlir.constant(0 : i8) : i8
  %2 = llvm.lshr %0, %arg4 : i8
  %3 = "llvm.select"(%arg5, %2, %1) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i8, i8) -> i8
  %4 = llvm.icmp "ugt" %arg3, %3 : i8
  "llvm.return"(%4) : (i1) -> ()
}
]

def lshr_add_and_shl_after := [llvm|
{
^0(%arg17 : i32, %arg18 : i32):
  %0 = llvm.mlir.constant(5 : i32) : i32
  %1 = llvm.mlir.constant(4064 : i32) : i32
  %2 = llvm.shl %arg18, %0 : i32
  %3 = llvm.and %arg17, %1 : i32
  %4 = llvm.add %3, %2 : i32
  "llvm.return"(%4) : (i32) -> ()
}
]

def shl_add_lshr_flag_preservation_after := [llvm|
{
^0(%arg157 : i32, %arg158 : i32, %arg159 : i32):
  %0 = llvm.lshr exact %arg159, %arg158 : i32
  %1 = llvm.add %0, %arg157 overflow<nsw,nuw> : i32
  "llvm.return"(%1) : (i32) -> ()
}
]

def test2_before := [llvm|
{
^0(%arg0 : i167):
  %0 = llvm.mlir.constant(9 : i577) : i577
  %1 = llvm.mlir.constant(8 : i577) : i577
  %2 = llvm.zext %arg0 : i167 to i577
  %3 = llvm.lshr %2, %0 : i577
  %4 = llvm.shl %2, %1 : i577
  %5 = llvm.or %3, %4 : i577
  %6 = llvm.trunc %5 : i577 to i167
  "llvm.return"(%6) : (i167) -> ()
}
]

GetElem.getElem in Init.GetElem

def ashr_slt_exact_near_pow2_cmpval_after := [llvm|
{
^0(%arg5 : i8):
  %0 = llvm.mlir.constant(9 : i8) : i8
  %1 = llvm.icmp "slt" %arg5, %0 : i8
  "llvm.return"(%1) : (i1) -> ()
}
]

def test7_after := [llvm|
{
^0(%arg115 : i32, %arg116 : i32):
  %0 = llvm.mlir.constant(-1 : i32) : i32
  %1 = llvm.xor %arg116, %0 : i32
  %2 = llvm.or %arg115, %1 : i32
  "llvm.return"(%2) : (i32) -> ()
}
]

def bools2_logical_commute3_and1_after := [llvm|
{
^0(%arg24 : i1, %arg25 : i1, %arg26 : i1):
  %0 = "llvm.select"(%arg26, %arg24, %arg25) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i1, i1) -> i1
  "llvm.return"(%0) : (i1) -> ()
}
]

def sge_to_ult_before := [llvm|
{
^0(%arg17 : i8):
  %0 = llvm.mlir.constant(127 : i8) : i8
  %1 = llvm.mlir.constant(15 : i8) : i8
  %2 = llvm.xor %arg17, %0 : i8
  %3 = llvm.icmp "sge" %2, %1 : i8
  "llvm.return"(%3) : (i1) -> ()
}
]

List.flatten in Init.Prelude

def n11_wrong_pred3_after := [llvm|
{
^0(%arg20 : i8, %arg21 : i8):
  %0 = llvm.mlir.constant(0 : i8) : i8
  %1 = llvm.icmp "ne" %arg20, %0 : i8
  "llvm.return"(%1) : (i1) -> ()
}
]

def narrow_zext_ashr_keep_trunc_after := [llvm|
{
^0(%arg8 : i8, %arg9 : i8):
  %0 = llvm.mlir.constant(1 : i16) : i16
  %1 = llvm.sext %arg8 : i8 to i16
  %2 = llvm.sext %arg9 : i8 to i16
  %3 = llvm.add %1, %2 overflow<nsw> : i16
  %4 = llvm.lshr %3, %0 : i16
  %5 = llvm.trunc %4 : i16 to i8
  "llvm.return"(%5) : (i8) -> ()
}
]

def APlusBMinusA : LLVMPeepholeRewriteRefine 64 [Ty.llvm (.bitvec 64), Ty.llvm (.bitvec 64)] where
  lhs := [LV| {
    ^entry (%a: i64, %b: i64):
      %0 = llvm.sub %b, %a : i64
      %1 = llvm.add %a, %0 : i64
      llvm.return %1 : i64
  }]
  rhs := [LV| {
    ^entry (%a: i64, %b: i64):
      llvm.return %b : i64
  }]

def test2_before := [llvm|
{
^0(%arg120 : i32):
  %0 = llvm.mlir.constant(32 : i32) : i32
  %1 = llvm.mlir.constant(145 : i32) : i32
  %2 = llvm.mlir.constant(153 : i32) : i32
  %3 = llvm.and %arg120, %0 : i32
  %4 = llvm.add %3, %1 : i32
  %5 = llvm.xor %4, %2 : i32
  "llvm.return"(%5) : (i32) -> ()
}
]

def n12_after := [llvm|
{
^0(%arg0 : i8, %arg1 : i8):
  %0 = llvm.mlir.constant(0 : i8) : i8
  %1 = llvm.sub %0, %arg0 overflow<nsw> : i8
  %2 = llvm.icmp "slt" %arg1, %1 : i8
  "llvm.return"(%2) : (i1) -> ()
}
]

def lshr_and_xor_before := [llvm|
{
^0(%arg37 : i8, %arg38 : i8):
  %0 = llvm.mlir.constant(42 : i8) : i8
  %1 = llvm.mlir.constant(2 : i8) : i8
  %2 = llvm.mlir.constant(13 : i8) : i8
  %3 = llvm.srem %arg37, %0 : i8
  %4 = llvm.lshr %arg38, %1 : i8
  %5 = llvm.and %4, %2 : i8
  %6 = llvm.xor %5, %3 : i8
  %7 = llvm.shl %6, %1 : i8
  "llvm.return"(%7) : (i8) -> ()
}
]

instance instHandshakeTyDenote : TyDenote Ty where
toType := fun
| Ty.stream ty2 => CIRCTStream.Stream (TyDenote.toType ty2)
| Ty.stream2 ty2 => CIRCTStream.Stream (TyDenote.toType ty2) × CIRCTStream.Stream (TyDenote.toType ty2)
| Ty.stream2token ty2 => CIRCTStream.Stream (TyDenote.toType ty2) × CIRCTStream.Stream (TyDenote.toType (Ty2.bitvec 1))

def_denote for Handshake where
| .fst _ => fun s => [s.fst]ₕ
| .snd _ => fun s => [s.snd]ₕ
| .branch _ => fun s c => [HandshakeOp.branch s c]ₕ
| .merge _ => fun s₁ s₂ => [HandshakeOp.merge s₁ s₂]ₕ
| .altMerge _ => fun s₁ s₂ => [HandshakeOp.altMerge s₁ s₂]ₕ
| .fork _ => fun s => [HandshakeOp.fork s]ₕ
| .controlMerge _ => fun s₁ s₂ => [HandshakeOp.controlMerge s₁ s₂]ₕ
| .join _ => fun s₁ s₂ => [HandshakeOp.join s₁ s₂]ₕ
| .mux _ => fun s₁ s₂ c => [HandshakeOp.mux s₁ s₂ c]ₕ
| .sink _ => fun s => [HandshakeOp.sink s]ₕ
| .sync _ => fun s₁ s₂ => [HandshakeOp.sync s₁ s₂]ₕ
| .supp _ => fun s₁ s₂ => [HandshakeOp.supp s₁ s₂]ₕ
| .not => fun s₁ => [HandshakeOp.not s₁]ₕ

def sgt_swap_and_min_commute_logical_before := [llvm|
{
^0(%arg338 : i8, %arg339 : i8):
  %0 = llvm.mlir.constant(-128 : i8) : i8
  %1 = llvm.mlir.constant(false) : i1
  %2 = llvm.icmp "slt" %arg339, %arg338 : i8
  %3 = llvm.icmp "eq" %arg338, %0 : i8
  %4 = "llvm.select"(%3, %2, %1) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i1, i1) -> i1
  "llvm.return"(%4) : (i1) -> ()
}
]

def RawCNFA.newState (m : RawCNFA A) : State × RawCNFA A :=
  let old := m.stateMax
  let m := { m with stateMax := old + 1 }
  (old, m)

def test39_before := [llvm|
{
^0(%arg237 : i32):
  %0 = llvm.mlir.constant(7) : i64
  %1 = llvm.mlir.constant(240) : i64
  %2 = llvm.zext %arg237 : i32 to i64
  %3 = llvm.or %2, %0 : i64
  %4 = llvm.and %3, %1 : i64
  "llvm.return"(%4) : (i64) -> ()
}
]

def positive_biggerashr_shlnsw_ashrexact_after := [llvm|
{
^0(%arg35 : i8):
  %0 = llvm.mlir.constant(3 : i8) : i8
  %1 = llvm.ashr exact %arg35, %0 : i8
  "llvm.return"(%1) : (i8) -> ()
}
]

def not_invert_signbit_splat_mask2_before := [llvm|
{
^0(%arg81 : i8, %arg82 : i16):
  %0 = llvm.mlir.constant(6 : i8) : i8
  %1 = llvm.mlir.constant(-1 : i8) : i8
  %2 = llvm.ashr %arg81, %0 : i8
  %3 = llvm.xor %2, %1 : i8
  %4 = llvm.sext %3 : i8 to i16
  %5 = llvm.and %4, %arg82 : i16
  "llvm.return"(%5) : (i16) -> ()
}
]

def irc_constants_C1Minus2MinusC2_neg2_0 : LLVMPeepholeRewriteRefine 64 [Ty.llvm (.bitvec 64)] where
  lhs := [LV| {
    ^entry (%a: i64):
      %c1 = llvm.mlir.constant (-2) : i64
      %c2 = llvm.mlir.constant (0) : i64
      %0 = llvm.sub %c1, %a : i64
      %1 = llvm.sub %0, %c2 : i64
      llvm.return %1 : i64
  }]
  rhs := [LV| {
    ^entry (%a: i64):
      %c1 = llvm.mlir.constant (-2) : i64
      %c2 = llvm.mlir.constant (0) : i64
      %0 = llvm.sub %c1, %c2 : i64
      %1 = llvm.sub %0, %a : i64
      llvm.return %1 : i64
  }]

def ashrslt_03_15_exact_before := [llvm|
{
^0(%arg6 : i4):
  %0 = llvm.mlir.constant(3 : i4) : i4
  %1 = llvm.mlir.constant(-1 : i4) : i4
  %2 = llvm.ashr exact %arg6, %0 : i4
  %3 = llvm.icmp "slt" %2, %1 : i4
  "llvm.return"(%3) : (i1) -> ()
}
]

def Lets.denoteIntoSubtype (lets : Lets d Γ_in eff Γ_out) (Γv : Valuation Γ_in) :
    eff.toMonad d.m lets.ValidDenotation :=
  match lets with
    | .nil => return ⟨Γv, by admit /- proof elided -/
    ⟩
    | @Lets.var _ _ _ _ Γ_out eTy body e => do
        let ⟨Vout, h⟩ ← body.denoteIntoSubtype Γv
        let Ve ← e.denoteOpIntoSubtype Vout
        return ⟨Ve.val ++ Vout, by admit /- proof elided -/
        ⟩

class DialectHRefinement (d : Dialect) (d' : Dialect) [TyDenote d.Ty] [TyDenote d'.Ty] where
   
  MonadIsRefinedBy {α β} [inst : HRefinement α β] : HRefinement (d.m α) (d'.m β) := by admit /- proof elided -/

structure Signature (Ty : Type) where
  mkEffectful ::
  sig         : List Ty
  regSig      : RegionSignature Ty
  returnTypes : List Ty
  effectKind  : EffectKind := .pure

def lshrugt_03_14_exact_before := [llvm|
{
^0(%arg175 : i4):
  %0 = llvm.mlir.constant(3 : i4) : i4
  %1 = llvm.mlir.constant(-2 : i4) : i4
  %2 = llvm.lshr exact %arg175, %0 : i4
  %3 = llvm.icmp "ugt" %2, %1 : i4
  "llvm.return"(%3) : (i1) -> ()
}
]

def BitVec.transport (f : Fin n2 → Fin n1) (bv : BitVec n1) : BitVec n2 :=
  BitVec.ofFn fun i => bv.getLsbD (f i)

@[simp]
abbrev LLVMPlusRiscV : Dialect where
  Op := Op
  Ty := Ty

@[simp_denote]
def ori_riscv_i64 :=
  [LV| {
    ^entry (%arg: i64):
    %a = "builtin.unrealized_conversion_cast" (%arg) : (i64) -> (!i64)
    %0 = ori %a, 5 : !i64
    %1 = "builtin.unrealized_conversion_cast" (%0) : (!i64) -> (i64)
    llvm.return %1 : i64
  }]

def lshrugt_03_01_exact_before := [llvm|
{
^0(%arg188 : i4):
  %0 = llvm.mlir.constant(3 : i4) : i4
  %1 = llvm.mlir.constant(1 : i4) : i4
  %2 = llvm.lshr exact %arg188, %0 : i4
  %3 = llvm.icmp "ugt" %2, %1 : i4
  "llvm.return"(%3) : (i1) -> ()
}
]

def or_not_and_wrong_b_after := [llvm|
{
^0(%arg484 : i32, %arg485 : i32, %arg486 : i32, %arg487 : i32):
  %0 = llvm.mlir.constant(-1 : i32) : i32
  %1 = llvm.or %arg484, %arg485 : i32
  %2 = llvm.xor %1, %0 : i32
  %3 = llvm.and %arg486, %2 : i32
  %4 = llvm.or %arg484, %arg486 : i32
  %5 = llvm.xor %4, %0 : i32
  %6 = llvm.and %arg487, %5 : i32
  %7 = llvm.or %3, %6 : i32
  "llvm.return"(%7) : (i32) -> ()
}
]

def ashrsgt_01_05_after := [llvm|
{
^0(%arg312 : i4):
  %0 = llvm.mlir.constant(false) : i1
  "llvm.return"(%0) : (i1) -> ()
}
]

def test_srem_canonicalize_op0_before := [llvm|
{
^0(%arg8 : i32, %arg9 : i32):
  %0 = llvm.mlir.constant(0 : i32) : i32
  %1 = llvm.sub %0, %arg8 overflow<nsw> : i32
  %2 = llvm.srem %1, %arg9 : i32
  "llvm.return"(%2) : (i32) -> ()
}
]

def test9_after := [llvm|
{
^0(%arg18 : i64):
  %0 = llvm.mlir.constant(1) : i64
  %1 = llvm.and %arg18, %0 : i64
  "llvm.return"(%1) : (i64) -> ()
}
]

def test3_before := [llvm|
{
^0(%arg2 : i32, %arg3 : i32):
  %0 = llvm.mlir.constant(0 : i32) : i32
  %1 = llvm.mlir.constant(31 : i32) : i32
  %2 = llvm.sub %arg2, %arg3 overflow<nsw> : i32
  %3 = llvm.icmp "eq" %2, %0 : i32
  %4 = llvm.icmp "eq" %2, %1 : i32
  %5 = llvm.or %3, %4 : i1
  "llvm.return"(%5) : (i1) -> ()
}
]

def negative_trunc_not_arg_logical_after := [llvm|
{
^0(%arg20 : i32, %arg21 : i32):
  %0 = llvm.mlir.constant(128 : i32) : i32
  %1 = llvm.mlir.constant(0 : i32) : i32
  %2 = llvm.mlir.constant(256 : i32) : i32
  %3 = llvm.mlir.constant(false) : i1
  %4 = llvm.and %arg20, %0 : i32
  %5 = llvm.icmp "eq" %4, %1 : i32
  %6 = llvm.add %arg21, %0 : i32
  %7 = llvm.icmp "ult" %6, %2 : i32
  %8 = "llvm.select"(%5, %7, %3) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i1, i1) -> i1
  "llvm.return"(%8) : (i1) -> ()
}
]

def mul16_low_miss_shift_amount_before := [llvm|
{
^0(%arg4 : i16, %arg5 : i16):
  %0 = llvm.mlir.constant(127 : i16) : i16
  %1 = llvm.mlir.constant(8 : i16) : i16
  %2 = llvm.and %arg4, %0 : i16
  %3 = llvm.lshr %arg4, %1 : i16
  %4 = llvm.and %arg5, %0 : i16
  %5 = llvm.lshr %arg5, %1 : i16
  %6 = llvm.mul %5, %2 : i16
  %7 = llvm.mul %4, %3 : i16
  %8 = llvm.mul %4, %2 : i16
  %9 = llvm.add %6, %7 : i16
  %10 = llvm.shl %9, %1 : i16
  %11 = llvm.add %10, %8 : i16
  "llvm.return"(%11) : (i16) -> ()
}
]

def lshrult_02_12_after := [llvm|
{
^0(%arg339 : i4):
  %0 = llvm.mlir.constant(true) : i1
  "llvm.return"(%0) : (i1) -> ()
}
]

def test_mul__all_are_safe_after := [llvm|
{
^0(%arg12 : i32):
  %0 = llvm.mlir.constant(255 : i32) : i32
  %1 = llvm.mlir.constant(9 : i32) : i32
  %2 = llvm.and %arg12, %0 : i32
  %3 = llvm.mul %2, %1 overflow<nsw,nuw> : i32
  "llvm.return"(%3) : (i32) -> ()
}
]

instance : FinEnum Bool where
  card := 2
  equiv := {
    toFun := fun x => if x then 1 else 0,
    invFun := fun (x : Fin 2 ) => if x == 0 then false else true,
    left_inv := by admit /- proof elided -/

def not_or_or_and_not_and_and_commute3_before := [llvm|
{
^0(%arg187 : i32, %arg188 : i32, %arg189 : i32):
  %0 = llvm.mlir.constant(42 : i32) : i32
  %1 = llvm.mlir.constant(-1 : i32) : i32
  %2 = llvm.sdiv %0, %arg188 : i32
  %3 = llvm.and %2, %arg187 : i32
  %4 = llvm.and %3, %arg189 : i32
  %5 = llvm.xor %4, %1 : i32
  %6 = llvm.xor %arg187, %1 : i32
  %7 = llvm.or %2, %6 : i32
  %8 = llvm.or %7, %arg189 : i32
  %9 = llvm.and %8, %5 : i32
  "llvm.return"(%9) : (i32) -> ()
}
]

@[simp_denote]
def and_llvm_i64 := [LV| {
    ^entry (%a: i64, %b: i64):
    %0 = llvm.and %a, %b : i64
    llvm.return %0 : i64
  }]

def or_nosignbit_select_lshr_after := [llvm|
{
^0(%arg24 : i32, %arg25 : i1):
  %0 = llvm.mlir.constant(8 : i32) : i32
  %1 = llvm.mlir.constant(8388352 : i32) : i32
  %2 = llvm.lshr %arg24, %0 : i32
  %3 = llvm.or %2, %1 : i32
  %4 = "llvm.select"(%arg25, %3, %2) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i32, i32) -> i32
  "llvm.return"(%4) : (i32) -> ()
}
]

def t6_ugt_sgt_65536_after := [llvm|
{
^0(%arg48 : i32, %arg49 : i32, %arg50 : i32):
  %0 = llvm.mlir.constant(0 : i32) : i32
  %1 = llvm.mlir.constant(65535 : i32) : i32
  %2 = llvm.icmp "slt" %arg48, %0 : i32
  %3 = llvm.icmp "sgt" %arg48, %1 : i32
  %4 = "llvm.select"(%2, %arg49, %arg48) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i32, i32) -> i32
  %5 = "llvm.select"(%3, %arg50, %4) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i32, i32) -> i32
  "llvm.return"(%5) : (i32) -> ()
}
]

def lshrult_03_03_before := [llvm|
{
^0(%arg332 : i4):
  %0 = llvm.mlir.constant(3 : i4) : i4
  %1 = llvm.lshr %arg332, %0 : i4
  %2 = llvm.icmp "ult" %1, %0 : i4
  "llvm.return"(%2) : (i1) -> ()
}
]

BitVec.signExtend in Init.Data.BitVec.Basic

def and_add_bool_to_select_multi_use_after := [llvm|
{
^0(%arg0 : i1, %arg1 : i32):
  %0 = llvm.mlir.constant(-1 : i32) : i32
  %1 = llvm.mlir.constant(0 : i32) : i32
  %2 = llvm.add %arg1, %0 : i32
  %3 = "llvm.select"(%arg0, %1, %2) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i32, i32) -> i32
  "llvm.return"(%3) : (i32) -> ()
}
]

def sub_sel_op1_after := [llvm|
{
^0(%arg11 : i1):
  %0 = llvm.mlir.constant(true) : i1
  %1 = llvm.xor %arg11, %0 : i1
  %2 = llvm.zext %1 : i1 to i32
  "llvm.return"(%2) : (i32) -> ()
}
]

def src_x_and_nmask_ult_after := [llvm|
{
^0(%arg24 : i8, %arg25 : i8, %arg26 : i1):
  %0 = llvm.mlir.constant(-1 : i8) : i8
  %1 = llvm.mlir.constant(false) : i1
  %2 = llvm.shl %0, %arg25 overflow<nsw> : i8
  %3 = llvm.icmp "ugt" %2, %arg24 : i8
  %4 = "llvm.select"(%arg26, %3, %1) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i1, i1) -> i1
  "llvm.return"(%4) : (i1) -> ()
}
]

instance : AST.TransformReturn LLVM 0 := { mkReturn }

def fast_div_201_before := [llvm|
{
^0(%arg0 : i8):
  %0 = llvm.mlir.constant(71 : i16) : i16
  %1 = llvm.mlir.constant(8 : i16) : i16
  %2 = llvm.mlir.constant(1 : i8) : i8
  %3 = llvm.mlir.constant(7 : i8) : i8
  %4 = llvm.zext %arg0 : i8 to i16
  %5 = llvm.mul %4, %0 : i16
  %6 = llvm.lshr %5, %1 : i16
  %7 = llvm.trunc %6 : i16 to i8
  %8 = llvm.sub %arg0, %7 : i8
  %9 = llvm.lshr %8, %2 : i8
  %10 = llvm.add %7, %9 : i8
  %11 = llvm.lshr %10, %3 : i8
  "llvm.return"(%11) : (i8) -> ()
}
]

def max_of_min_swap_before := [llvm|
{
^0(%arg21 : i32):
  %0 = llvm.mlir.constant(-1 : i32) : i32
  %1 = llvm.mlir.constant(0 : i32) : i32
  %2 = llvm.xor %arg21, %0 : i32
  %3 = llvm.icmp "slt" %arg21, %1 : i32
  %4 = "llvm.select"(%3, %0, %2) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i32, i32) -> i32
  %5 = llvm.icmp "sgt" %4, %0 : i32
  %6 = "llvm.select"(%5, %4, %0) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i32, i32) -> i32
  "llvm.return"(%6) : (i32) -> ()
}
]

def lshr_mul_negative_nsw_before := [llvm|
{
^0(%arg29 : i64):
  %0 = llvm.mlir.constant(52) : i64
  %1 = llvm.mlir.constant(2) : i64
  %2 = llvm.mul %arg29, %0 overflow<nsw> : i64
  %3 = llvm.lshr %2, %1 : i64
  "llvm.return"(%3) : (i64) -> ()
}
]

def fold_sext_to_and_wrong9_before := [llvm|
{
^0(%arg1 : i8):
  %0 = llvm.mlir.constant(128 : i32) : i32
  %1 = llvm.mlir.constant(1 : i32) : i32
  %2 = llvm.sext %arg1 : i8 to i32
  %3 = llvm.and %2, %0 : i32
  %4 = llvm.icmp "ne" %3, %1 : i32
  "llvm.return"(%4) : (i1) -> ()
}
]

def getWidthRelations : GeneralizerStateM ParsedBVExpr GenBVPred (Option (BoolExpr GenBVPred)) := do
    let state ← get
    let parsedLogicalExprState :=  state.parsedLogicalExpr.state

    let processingWidth := state.processingWidth

    if parsedLogicalExprState.widthIdToVariable.size <= 1 then
      return none

    let relations := findRelationsBetweenWidths parsedLogicalExprState.widthIdToVariable processingWidth
    return some relations

def boolExprToSmtLib (pred : BoolExpr α) (f : α → SexprPBV.Predicate)
    (displayNames : Std.HashMap Nat HydraVariable) (widthVals : Std.HashMap Nat HydraVariable) : SexprPBV.Predicate :=
  match pred with
  | .literal litPred => f litPred
  | .not expr => SexprPBV.Predicate.not (boolExprToSmtLib expr f displayNames widthVals)
  | .gate gate lhs rhs =>
      
      
      
      match gate with
      | .beq => SexprPBV.Predicate.eq (boolExprToSmtLib lhs f displayNames widthVals) (boolExprToSmtLib rhs f displayNames widthVals)
      | .xor => SexprPBV.Predicate.xor (boolExprToSmtLib lhs f displayNames widthVals) (boolExprToSmtLib rhs f displayNames widthVals)
      | .and => SexprPBV.Predicate.and (boolExprToSmtLib lhs f displayNames widthVals) (boolExprToSmtLib rhs f displayNames widthVals)
      | .or  => SexprPBV.Predicate.or (boolExprToSmtLib lhs f displayNames widthVals) (boolExprToSmtLib rhs f displayNames widthVals)
  | .ite cond positive negative =>
      SexprPBV.Predicate.ite (boolExprToSmtLib cond f displayNames widthVals)
                            (boolExprToSmtLib positive f displayNames widthVals)
                            (boolExprToSmtLib negative f displayNames widthVals)
  | .const b => SexprPBV.Predicate.boolConstPred b

def ashr_pow2_ugt_after := [llvm|
{
^0(%arg67 : i8):
  %0 = llvm.mlir.constant(-128 : i8) : i8
  %1 = llvm.mlir.constant(-96 : i8) : i8
  %2 = llvm.ashr exact %0, %arg67 : i8
  %3 = llvm.icmp "ugt" %2, %1 : i8
  "llvm.return"(%3) : (i1) -> ()
}
]

instance : ToString FVarId where
  toString f := s! "{f.name}"

def not_or_or_not_after := [llvm|
{
^0(%arg552 : i32, %arg553 : i32, %arg554 : i32):
  %0 = llvm.mlir.constant(42 : i32) : i32
  %1 = llvm.mlir.constant(-1 : i32) : i32
  %2 = llvm.sdiv %0, %arg552 : i32
  %3 = llvm.and %arg553, %arg554 : i32
  %4 = llvm.xor %3, %1 : i32
  %5 = llvm.or %2, %4 : i32
  "llvm.return"(%5) : (i32) -> ()
}
]

def demorgan_nor_use2ac_after := [llvm|
{
^0(%arg22 : i8, %arg23 : i8):
  %0 = llvm.mlir.constant(-1 : i8) : i8
  %1 = llvm.mlir.constant(17 : i8) : i8
  %2 = llvm.mlir.constant(23 : i8) : i8
  %3 = llvm.xor %arg22, %0 : i8
  %4 = llvm.mul %3, %1 : i8
  %5 = llvm.or %arg23, %3 : i8
  %6 = llvm.mul %5, %2 : i8
  %7 = llvm.xor %5, %0 : i8
  %8 = llvm.sdiv %7, %6 : i8
  %9 = llvm.sdiv %8, %4 : i8
  "llvm.return"(%9) : (i8) -> ()
}
]

def select_constants_and_icmp_eq0_after := [llvm|
{
^0(%arg46 : i1, %arg47 : i1):
  %0 = llvm.xor %arg46, %arg47 : i1
  "llvm.return"(%0) : (i1) -> ()
}
]

def test15_before := [llvm|
{
^0(%arg40 : i32, %arg41 : i32):
  %0 = llvm.mlir.constant(-1431655767 : i32) : i32
  %1 = llvm.mlir.constant(1 : i32) : i32
  %2 = llvm.and %arg40, %0 : i32
  %3 = llvm.xor %2, %0 : i32
  %4 = llvm.add %arg41, %1 : i32
  %5 = llvm.add %4, %3 : i32
  "llvm.return"(%5) : (i32) -> ()
}
]

def lshr_add_xor_fail_before := [llvm|
{
^0(%arg90 : i8, %arg91 : i8):
  %0 = llvm.mlir.constant(1 : i8) : i8
  %1 = llvm.mlir.constant(123 : i8) : i8
  %2 = llvm.lshr %arg90, %0 : i8
  %3 = llvm.lshr %arg91, %0 : i8
  %4 = llvm.add %3, %1 : i8
  %5 = llvm.xor %2, %4 : i8
  "llvm.return"(%5) : (i8) -> ()
}
]

def pow2_or_zero_is_negative_commute_before := [llvm|
{
^0(%arg7 : i8):
  %0 = llvm.mlir.constant(42 : i8) : i8
  %1 = llvm.mlir.constant(0 : i8) : i8
  %2 = llvm.mul %0, %arg7 : i8
  %3 = llvm.sub %1, %2 : i8
  %4 = llvm.and %3, %2 : i8
  %5 = llvm.icmp "slt" %4, %1 : i8
  "llvm.return"(%5) : (i1) -> ()
}
]

def xvar' : MultiWidth.Nondep.Term := MultiWidth.Nondep.Term.var 0 xw'

def masked_and_notA_logical_after := [llvm|
{
^0(%arg124 : i32):
  %0 = llvm.mlir.constant(-79 : i32) : i32
  %1 = llvm.mlir.constant(0 : i32) : i32
  %2 = llvm.and %arg124, %0 : i32
  %3 = llvm.icmp "ne" %2, %1 : i32
  "llvm.return"(%3) : (i1) -> ()
}
]

@[simp]
def ofNat_eq_concrete (x : Nat) :
    (OfNat.ofNat x) = (ConcreteOrMVar.concrete x : ConcreteOrMVar Nat φ) := rfl

Lean.MacroM in Init.Prelude

def neg_slt_1_after := [llvm|
{
^0(%arg25 : i8):
  %0 = llvm.mlir.constant(-127 : i8) : i8
  %1 = llvm.icmp "ult" %arg25, %0 : i8
  "llvm.return"(%1) : (i1) -> ()
}
]

def shl_or_disjoint_lshr_comm_after := [llvm|
{
^0(%arg103 : i32, %arg104 : i32, %arg105 : i32):
  %0 = llvm.lshr %arg105, %arg104 : i32
  %1 = llvm.or disjoint %0, %arg103 : i32
  "llvm.return"(%1) : (i32) -> ()
}
]

def ule_swap_or_not_min_commute_logical_after := [llvm|
{
^0(%arg258 : i8, %arg259 : i8):
  %0 = llvm.mlir.constant(true) : i1
  "llvm.return"(%0) : (i1) -> ()
}
]

def both_after := [llvm|
{
^0(%arg17 : i8, %arg18 : i8):
  %0 = llvm.mlir.constant(-1 : i8) : i8
  %1 = llvm.shl %0, %arg17 overflow<nsw> : i8
  %2 = llvm.shl %0, %arg18 overflow<nsw> : i8
  %3 = llvm.icmp "ugt" %1, %2 : i8
  "llvm.return"(%3) : (i1) -> ()
}
]

def NFA.autWidthSA (n : Nat) (q : Fin (n+2)) : Language (BitVec 0) :=
  if q = Fin.last (n+1) then { w | w.length > n } else { w | w.length = q }

instance instTransformTy : MLIR.AST.TransformTy DCPlus 0 where
  mkTy := mkTy

def test3_logical_after := [llvm|
{
^0(%arg306 : i1):
  %0 = llvm.mlir.constant(false) : i1
  "llvm.return"(%0) : (i1) -> ()
}
]

def liRiscv_39 := [LV| {
  ^entry ():
    %0 = "li"() {imm = -39 : !i64} : (!i64) -> (!i64)
    %1 = "builtin.unrealized_conversion_cast"(%0) : (!i64) -> (i64)
    llvm.return %1 : i64
  }]

def shl_bad_sub2_i32_before := [llvm|
{
^0(%arg10 : i32):
  %0 = llvm.mlir.constant(31 : i32) : i32
  %1 = llvm.mlir.constant(1 : i32) : i32
  %2 = llvm.sub %arg10, %0 : i32
  %3 = llvm.shl %1, %2 : i32
  "llvm.return"(%3) : (i32) -> ()
}
]

def main_before := [llvm|
{
^0(%arg2 : i32):
  %0 = llvm.mlir.constant(-17 : i8) : i8
  %1 = llvm.mlir.constant(122 : i8) : i8
  %2 = llvm.mlir.constant(6 : i8) : i8
  %3 = llvm.mlir.constant(7 : i8) : i8
  %4 = llvm.mlir.constant(64 : i8) : i8
  %5 = llvm.trunc %arg2 : i32 to i8
  %6 = llvm.or %5, %0 : i8
  %7 = llvm.and %5, %1 : i8
  %8 = llvm.xor %7, %0 : i8
  %9 = llvm.shl %8, %2 : i8
  %10 = llvm.xor %9, %8 : i8
  %11 = llvm.xor %6, %10 : i8
  %12 = llvm.lshr %11, %3 : i8
  %13 = llvm.mul %12, %4 : i8
  %14 = llvm.zext %13 : i8 to i32
  "llvm.return"(%14) : (i32) -> ()
}
]

def ashrsgt_03_03_exact_before := [llvm|
{
^0(%arg66 : i4):
  %0 = llvm.mlir.constant(3 : i4) : i4
  %1 = llvm.ashr exact %arg66, %0 : i4
  %2 = llvm.icmp "sgt" %1, %0 : i4
  "llvm.return"(%2) : (i1) -> ()
}
]

def t0_before := [llvm|
{
^0(%arg18 : i32, %arg19 : i16):
  %0 = llvm.mlir.constant(32 : i16) : i16
  %1 = llvm.mlir.constant(-1 : i16) : i16
  %2 = llvm.sub %0, %arg19 : i16
  %3 = llvm.zext %2 : i16 to i32
  %4 = llvm.ashr %arg18, %3 : i32
  %5 = llvm.trunc %4 : i32 to i16
  %6 = llvm.add %arg19, %1 : i16
  %7 = llvm.ashr %5, %6 : i16
  "llvm.return"(%7) : (i16) -> ()
}
]

def select_t_cond : LLVMPeepholeRewriteRefine 64 [Ty.llvm (.bitvec 64), Ty.llvm (.bitvec 1)] where
  lhs := [LV| {
    ^entry (%c: i1, %t: i64):
      %0 = llvm.sext %c: i1 to i64
      %1 = llvm.select %c, %t, %0 : i64
      llvm.return %1 : i64
  }]
  rhs := [LV| {
    ^entry (%c: i1, %t: i64):
      %0 = llvm.sext %c: i1 to i64
      %1 = llvm.freeze %t : i64
      %2 = llvm.and %0, %1 : i64
      llvm.return %2 : i64
  }]

def logical_and_not_before := [llvm|
{
^0(%arg262 : i1, %arg263 : i1):
  %0 = llvm.mlir.constant(false) : i1
  %1 = "llvm.select"(%arg262, %0, %arg263) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i1, i1) -> i1
  "llvm.return"(%1) : (i1) -> ()
}
]

def irc_constants_AMinusC1PlusC2_neg1_0 : LLVMPeepholeRewriteRefine 64 [Ty.llvm (.bitvec 64)] where
  lhs := [LV| {
    ^entry (%a: i64):
      %c1 = llvm.mlir.constant (-1) : i64
      %c2 = llvm.mlir.constant (0) : i64
      %0 = llvm.sub %a, %c1 : i64
      %1 = llvm.add %0, %c2 : i64
      llvm.return %1 : i64
  }]
  rhs := [LV| {
    ^entry (%a: i64):
      %c1 = llvm.mlir.constant (-1) : i64
      %c2 = llvm.mlir.constant (0) : i64
      %0 = llvm.sub %c2, %c1 : i64
      %1 = llvm.add %a, %0 : i64
      llvm.return %1 : i64
  }]

def test_shl_nuw__nsw_is_safe_before := [llvm|
{
^0(%arg74 : i32):
  %0 = llvm.mlir.constant(-83886080 : i32) : i32
  %1 = llvm.mlir.constant(-83886079 : i32) : i32
  %2 = llvm.mlir.constant(2 : i32) : i32
  %3 = llvm.mlir.constant(-335544316 : i32) : i32
  %4 = llvm.or %arg74, %0 : i32
  %5 = llvm.icmp "eq" %4, %1 : i32
  %6 = llvm.shl %4, %2 overflow<nuw> : i32
  %7 = "llvm.select"(%5, %3, %6) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i32, i32) -> i32
  %8 = llvm.mul %7, %4 : i32
  %9 = llvm.mul %8, %6 : i32
  "llvm.return"(%9) : (i32) -> ()
}
]

def shl_xor_before := [llvm|
{
^0(%arg63 : i32, %arg64 : i32):
  %0 = llvm.mlir.constant(5 : i32) : i32
  %1 = llvm.mlir.constant(7 : i32) : i32
  %2 = llvm.shl %arg63, %0 : i32
  %3 = llvm.xor %2, %arg64 : i32
  %4 = llvm.shl %3, %1 : i32
  "llvm.return"(%4) : (i32) -> ()
}
]

def or_eq_with_one_bit_diff_constants1_logical_before := [llvm|
{
^0(%arg365 : i32):
  %0 = llvm.mlir.constant(50 : i32) : i32
  %1 = llvm.mlir.constant(51 : i32) : i32
  %2 = llvm.mlir.constant(true) : i1
  %3 = llvm.icmp "eq" %arg365, %0 : i32
  %4 = llvm.icmp "eq" %arg365, %1 : i32
  %5 = "llvm.select"(%3, %2, %4) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i1, i1) -> i1
  "llvm.return"(%5) : (i1) -> ()
}
]

def trunc_shl_33_i32_i64_after := [llvm|
{
^0(%arg33 : i64):
  %0 = llvm.mlir.constant(0 : i32) : i32
  "llvm.return"(%0) : (i32) -> ()
}
]

def p_commutative0_before := [llvm|
{
^0(%arg32 : i32, %arg33 : i32, %arg34 : i32):
  %0 = llvm.mlir.constant(-1 : i32) : i32
  %1 = llvm.and %arg34, %arg32 : i32
  %2 = llvm.xor %arg34, %0 : i32
  %3 = llvm.and %2, %arg33 : i32
  %4 = llvm.or %1, %3 : i32
  "llvm.return"(%4) : (i32) -> ()
}
]

def SyncEg1 := [handshake_com| {
  ^entry(%0: !Stream_BitVec_8, %1: !Stream_BitVec_8):
    %out = "handshake.sync" (%0, %1) : (!Stream_BitVec_8, !Stream_BitVec_8) -> (!Stream2_BitVec_8)
    %outf = "handshake.fst" (%out) : (!Stream2_BitVec_8) -> (!Stream_BitVec_8)
    "return" (%outf) : (!Stream_BitVec_8) -> ()
  }]

def neg_slt_0_before := [llvm|
{
^0(%arg26 : i8):
  %0 = llvm.mlir.constant(0 : i8) : i8
  %1 = llvm.sub %0, %arg26 : i8
  %2 = llvm.icmp "slt" %1, %0 : i8
  "llvm.return"(%2) : (i1) -> ()
}
]

instance : Coe String SSAVal where
  coe (s: String) := SSAVal.name s

def urem_i8_before := [llvm|
{
^0(%arg33 : i8, %arg34 : i8):
  %0 = llvm.zext %arg33 : i8 to i32
  %1 = llvm.zext %arg34 : i8 to i32
  %2 = llvm.urem %0, %1 : i32
  %3 = llvm.trunc %2 : i32 to i8
  "llvm.return"(%3) : (i8) -> ()
}
]

def function : Parser :=
  leading_parser argumentList >> arrow >> termParser

def test3_before := [llvm|
{
^0(%arg28 : i32, %arg29 : i32):
  %0 = llvm.mlir.constant(0 : i32) : i32
  %1 = llvm.udiv %arg28, %arg29 : i32
  %2 = llvm.icmp "ne" %1, %0 : i32
  "llvm.return"(%2) : (i1) -> ()
}
]

def lshrult_02_04_before := [llvm|
{
^0(%arg347 : i4):
  %0 = llvm.mlir.constant(2 : i4) : i4
  %1 = llvm.mlir.constant(4 : i4) : i4
  %2 = llvm.lshr %arg347, %0 : i4
  %3 = llvm.icmp "ult" %2, %1 : i4
  "llvm.return"(%3) : (i1) -> ()
}
]

def select_or_icmp_bad_before := [llvm|
{
^0(%arg149 : i32, %arg150 : i32, %arg151 : i32):
  %0 = llvm.mlir.constant(3 : i32) : i32
  %1 = llvm.icmp "eq" %arg149, %0 : i32
  %2 = llvm.or %arg149, %arg151 : i32
  %3 = "llvm.select"(%1, %2, %arg150) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i32, i32) -> i32
  "llvm.return"(%3) : (i32) -> ()
}
]

def trunc_shl_shl_var_after := [llvm|
{
^0(%arg14 : i64, %arg15 : i64):
  %0 = llvm.mlir.constant(2 : i32) : i32
  %1 = llvm.shl %arg14, %arg15 : i64
  %2 = llvm.trunc %1 : i64 to i32
  %3 = llvm.shl %2, %0 : i32
  "llvm.return"(%3) : (i32) -> ()
}
]

def test3_before := [llvm|
{
^0(%arg307 : i1):
  %0 = llvm.mlir.constant(false) : i1
  %1 = llvm.and %arg307, %0 : i1
  "llvm.return"(%1) : (i1) -> ()
}
]

Lean.Meta.Context in Lean.Meta.Basic

Except in Init.Prelude

def logic_or_logic_and_5_after := [llvm|
{
^0(%arg75 : i1, %arg76 : i1, %arg77 : i1):
  %0 = llvm.mlir.constant(false) : i1
  %1 = llvm.mlir.constant(true) : i1
  %2 = "llvm.select"(%arg77, %arg76, %0) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i1, i1) -> i1
  %3 = "llvm.select"(%arg75, %1, %2) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i1, i1) -> i1
  "llvm.return"(%3) : (i1) -> ()
}
]

def main7c_after := [llvm|
{
^0(%arg72 : i32, %arg73 : i32, %arg74 : i32):
  %0 = llvm.mlir.constant(42 : i32) : i32
  %1 = llvm.mul %arg74, %0 : i32
  %2 = llvm.or %arg73, %1 : i32
  %3 = llvm.and %arg72, %2 : i32
  %4 = llvm.icmp "ne" %3, %2 : i32
  %5 = llvm.zext %4 : i1 to i32
  "llvm.return"(%5) : (i32) -> ()
}
]

def one_side_fold_eq_after := [llvm|
{
^0(%arg25 : i32, %arg26 : i32, %arg27 : i32, %arg28 : i1):
  %0 = llvm.mlir.constant(true) : i1
  %1 = llvm.icmp "eq" %arg26, %arg25 : i32
  %2 = llvm.xor %arg28, %0 : i1
  %3 = "llvm.select"(%2, %0, %1) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i1, i1) -> i1
  "llvm.return"(%3) : (i1) -> ()
}
]

def test38_before := [llvm|
{
^0(%arg238 : i32):
  %0 = llvm.mlir.constant(7) : i64
  %1 = llvm.mlir.constant(240) : i64
  %2 = llvm.zext %arg238 : i32 to i64
  %3 = llvm.xor %2, %0 : i64
  %4 = llvm.and %3, %1 : i64
  "llvm.return"(%4) : (i64) -> ()
}
]

Int.cast in Init.Data.Int.Basic

def List.Vector.transport (v : Vector α m) (f : Fin n → Fin m) : Vector α n :=
  Vector.ofFn fun i => v.get (f i)

def sle_swap_and_min_logical_after := [llvm|
{
^0(%arg212 : i8, %arg213 : i8):
  %0 = llvm.mlir.constant(-128 : i8) : i8
  %1 = llvm.icmp "eq" %arg212, %0 : i8
  "llvm.return"(%1) : (i1) -> ()
}
]

def slt_zero_ult_i1_fail2_before := [llvm|
{
^0(%arg6 : i32, %arg7 : i1):
  %0 = llvm.mlir.constant(31 : i32) : i32
  %1 = llvm.zext %arg7 : i1 to i32
  %2 = llvm.ashr %arg6, %0 : i32
  %3 = llvm.icmp "ult" %1, %2 : i32
  "llvm.return"(%3) : (i1) -> ()
}
]

@[simp_denote]
def sext_llvm_i16_to_32 := [LV| {
  ^entry (%arg: i16):
    %0 = llvm.sext %arg: i16 to i32
    llvm.return %0: i32
  }]

def ashr_ugt_14_after := [llvm|
{
^0(%arg100 : i4):
  %0 = llvm.mlir.constant(-3 : i4) : i4
  %1 = llvm.icmp "ugt" %arg100, %0 : i4
  "llvm.return"(%1) : (i1) -> ()
}
]

def Holor.map (f : α → β) (h : Holor α ds) : Holor β ds :=
  f ∘ h

def t2_after := [llvm|
{
^0(%arg220 : i8, %arg221 : i8):
  %0 = llvm.mlir.constant(42 : i8) : i8
  %1 = llvm.shl %0, %arg221 : i8
  %2 = llvm.add %1, %arg220 : i8
  "llvm.return"(%2) : (i8) -> ()
}
]

BitVec.intMin in Init.Data.BitVec.Basic

def sle_swap_or_not_min_after := [llvm|
{
^0(%arg280 : i8, %arg281 : i8):
  %0 = llvm.mlir.constant(true) : i1
  "llvm.return"(%0) : (i1) -> ()
}
]

def scalar_i64_shl_ult_const_after := [llvm|
{
^0(%arg14 : i64):
  %0 = llvm.mlir.constant(549755813632) : i64
  %1 = llvm.mlir.constant(0) : i64
  %2 = llvm.and %arg14, %0 : i64
  %3 = llvm.icmp "eq" %2, %1 : i64
  "llvm.return"(%3) : (i1) -> ()
}
]

def liftOp n : Fin (n + 1) → Fin (n + 3) :=
  fun k =>
    if k = n then Fin.last (n+2) else k.castLE (by admit /- proof elided -/
    )

def and : FSM Bool :=
  { α := Empty,
    initCarry := Empty.elim,
    nextStateCirc := fun a => a.elim,
    outputCirc := Circuit.var true (inr true) &&& Circuit.var true (inr false),
  }

def test4_after := [llvm|
{
^0(%arg3 : i737):
  %0 = llvm.mlir.constant(-1 : i737) : i737
  "llvm.return"(%0) : (i737) -> ()
}
]

def trunc_shl_zext_64_before := [llvm|
{
^0(%arg0 : i64):
  %0 = llvm.mlir.constant(7 : i8) : i8
  %1 = llvm.trunc %arg0 : i64 to i8
  %2 = llvm.shl %1, %0 : i8
  %3 = llvm.zext %2 : i8 to i64
  "llvm.return"(%3) : (i64) -> ()
}
]

def constLLVM34 : Com LLVMPlusRiscV ⟨[]⟩ .pure (.llvm (.bitvec 64)) := [LV| {
  ^entry ():
    %1 = llvm.mlir.constant (34) : i64
    llvm.return %1 : i64
  }]

def max_of_min_swap_before := [llvm|
{
^0(%arg21 : i32):
  %0 = llvm.mlir.constant(-1 : i32) : i32
  %1 = llvm.mlir.constant(0 : i32) : i32
  %2 = llvm.xor %arg21, %0 : i32
  %3 = llvm.icmp "slt" %arg21, %1 : i32
  %4 = "llvm.select"(%3, %0, %2) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i32, i32) -> i32
  %5 = llvm.icmp "sgt" %4, %0 : i32
  %6 = "llvm.select"(%5, %4, %0) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i32, i32) -> i32
  "llvm.return"(%6) : (i32) -> ()
}
]

def ne_smax4_before := [llvm|
{
^0(%arg41 : i32, %arg42 : i32):
  %0 = llvm.mlir.constant(3 : i32) : i32
  %1 = llvm.add %arg41, %0 : i32
  %2 = llvm.icmp "sgt" %arg42, %1 : i32
  %3 = "llvm.select"(%2, %arg42, %1) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i32, i32) -> i32
  %4 = llvm.icmp "ne" %1, %3 : i32
  "llvm.return"(%4) : (i1) -> ()
}
]

def add_2_after := [llvm|
{
^0(%arg121 : i8, %arg122 : i1, %arg123 : i8, %arg124 : i8):
  %0 = llvm.mlir.constant(-124 : i8) : i8
  %1 = llvm.xor %arg124, %0 : i8
  %2 = "llvm.select"(%arg122, %arg123, %1) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i8, i8) -> i8
  %3 = llvm.sub %2, %arg121 : i8
  "llvm.return"(%3) : (i8) -> ()
}
]

def test14_after := [llvm|
{
^0(%arg0 : i32, %arg1 : i32):
  %0 = llvm.mlir.constant(8 : i32) : i32
  %1 = llvm.mlir.constant(0 : i32) : i32
  %2 = llvm.mlir.constant(128 : i32) : i32
  %3 = llvm.shl %arg0, %0 : i32
  %4 = llvm.sub %1, %arg1 : i32
  %5 = llvm.and %4, %2 : i32
  %6 = llvm.mul %5, %3 : i32
  "llvm.return"(%6) : (i32) -> ()
}
]

def main3d_after := [llvm|
{
^0(%arg143 : i32):
  %0 = llvm.mlir.constant(23 : i32) : i32
  %1 = llvm.mlir.constant(0 : i32) : i32
  %2 = llvm.and %arg143, %0 : i32
  %3 = llvm.icmp "eq" %2, %1 : i32
  %4 = llvm.zext %3 : i1 to i32
  "llvm.return"(%4) : (i32) -> ()
}
]

abbrev tctx : Term.Ctx (wcard := 1) (tcard := 1) := (Term.Ctx.empty (wcard := 1))
  
  |>.cons (WidthExpr.var ⟨0, by admit /- proof elided -/
  ⟩)

def n2_before := [llvm|
{
^0(%arg1 : i8, %arg2 : i8):
  %0 = llvm.mlir.constant(1 : i8) : i8
  %1 = llvm.shl %0, %arg2 : i8
  %2 = llvm.icmp "ult" %1, %arg1 : i8
  "llvm.return"(%2) : (i1) -> ()
}
]

def or_and_not_not_commute2_before := [llvm|
{
^0(%arg419 : i32, %arg420 : i32, %arg421 : i32):
  %0 = llvm.mlir.constant(-1 : i32) : i32
  %1 = llvm.or %arg420, %arg419 : i32
  %2 = llvm.xor %1, %0 : i32
  %3 = llvm.or %arg419, %arg421 : i32
  %4 = llvm.xor %3, %0 : i32
  %5 = llvm.and %4, %arg420 : i32
  %6 = llvm.or %5, %2 : i32
  "llvm.return"(%6) : (i32) -> ()
}
]

def sub_2_before := [llvm|
{
^0(%arg109 : i8, %arg110 : i1, %arg111 : i8, %arg112 : i8):
  %0 = llvm.mlir.constant(-1 : i8) : i8
  %1 = llvm.mlir.constant(123 : i8) : i8
  %2 = llvm.xor %arg111, %0 : i8
  %3 = llvm.xor %arg112, %1 : i8
  %4 = "llvm.select"(%arg110, %2, %3) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i8, i8) -> i8
  %5 = llvm.sub %arg109, %4 : i8
  %6 = llvm.xor %5, %0 : i8
  "llvm.return"(%6) : (i8) -> ()
}
]

def ashr_ugt_3_before := [llvm|
{
^0(%arg111 : i4):
  %0 = llvm.mlir.constant(1 : i4) : i4
  %1 = llvm.mlir.constant(3 : i4) : i4
  %2 = llvm.ashr %arg111, %0 : i4
  %3 = llvm.icmp "ugt" %2, %1 : i4
  "llvm.return"(%3) : (i1) -> ()
}
]

def alive_AddSub_1164_src  (w : Nat)   :=
[llvm( w )| {
^bb0(%a : _, %b : _):
  %v1 = llvm.mlir.constant 0
  %v2 = llvm.sub %v1, %a
  %v3 = llvm.add %v2, %b
  llvm.return %v3
}]

def shl_mask_before := [llvm|
{
^0(%arg6 : i32):
  %0 = llvm.mlir.constant(255 : i32) : i32
  %1 = llvm.mlir.constant(8 : i32) : i32
  %2 = llvm.and %arg6, %0 : i32
  %3 = llvm.shl %2, %1 : i32
  %4 = llvm.or %2, %3 : i32
  "llvm.return"(%4) : (i32) -> ()
}
]

def liftMaxSuccSucc2 (n m : Nat) : Fin (m + 1) → Fin (max n m + 3) :=
  fun k => if _ : k = Fin.last m then max n m + 1 else k.castLE (by admit /- proof elided -/
  )

def n1_after := [llvm|
{
^0(%arg3 : i8):
  %0 = llvm.mlir.constant(8 : i8) : i8
  %1 = llvm.icmp "ult" %arg3, %0 : i8
  "llvm.return"(%1) : (i1) -> ()
}
]

def t10_after := [llvm|
{
^0(%arg205 : i32, %arg206 : i32):
  %0 = llvm.mlir.constant(1 : i32) : i32
  %1 = llvm.shl %0, %arg206 overflow<nsw,nuw> : i32
  "llvm.return"(%1) : (i32) -> ()
}
]

def slt_i32_test : LLVMPeepholeRewriteRefine 32 [Ty.llvm (.bitvec 32), Ty.llvm (.bitvec 32)] where
  lhs := slt_llvm_i32
  rhs := slt_riscv_i32

def canonicalize_logic_first_and0_nsw_before := [llvm|
{
^0(%arg27 : i8):
  %0 = llvm.mlir.constant(48 : i8) : i8
  %1 = llvm.mlir.constant(-10 : i8) : i8
  %2 = llvm.add %arg27, %0 overflow<nsw> : i8
  %3 = llvm.and %2, %1 : i8
  "llvm.return"(%3) : (i8) -> ()
}
]

def irc_constants_C1Minus2MinusC2_0_1 : LLVMPeepholeRewriteRefine 64 [Ty.llvm (.bitvec 64)] where
  lhs := [LV| {
    ^entry (%a: i64):
      %c1 = llvm.mlir.constant (0) : i64
      %c2 = llvm.mlir.constant (1) : i64
      %0 = llvm.sub %c1, %a : i64
      %1 = llvm.sub %0, %c2 : i64
      llvm.return %1 : i64
  }]
  rhs := [LV| {
    ^entry (%a: i64):
      %c1 = llvm.mlir.constant (0) : i64
      %c2 = llvm.mlir.constant (1) : i64
      %0 = llvm.sub %c1, %c2 : i64
      %1 = llvm.sub %0, %a : i64
      llvm.return %1 : i64
  }]

instance : MLIR.AST.TransformExpr (Handshake) 0 where
  mkExpr := mkExpr

def scalar_i32_udiv_and_negC_eq_X_is_constant3_before := [llvm|
{
^0(%arg7 : i32):
  %0 = llvm.mlir.constant(12345 : i32) : i32
  %1 = llvm.mlir.constant(16376 : i32) : i32
  %2 = llvm.mlir.constant(0 : i32) : i32
  %3 = llvm.udiv %0, %arg7 : i32
  %4 = llvm.and %3, %1 : i32
  %5 = llvm.icmp "ne" %4, %2 : i32
  "llvm.return"(%5) : (i1) -> ()
}
]

def not_cond_before := [llvm|
{
^0(%arg24 : i1, %arg25 : i32, %arg26 : i32):
  %0 = llvm.mlir.constant(true) : i1
  %1 = llvm.xor %arg24, %0 : i1
  %2 = "llvm.select"(%1, %arg25, %arg26) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i32, i32) -> i32
  "llvm.return"(%2) : (i32) -> ()
}
]

def positive_sameconst_ashrexact_before := [llvm|
{
^0(%arg41 : i8):
  %0 = llvm.mlir.constant(3 : i8) : i8
  %1 = llvm.ashr exact %arg41, %0 : i8
  %2 = llvm.shl %1, %0 : i8
  "llvm.return"(%2) : (i8) -> ()
}
]

instance {n : Nat} : Cli.ParseableType (BitVec n) where
  name := s!"BitVec {n}"
  parse? str := do
   let intVal ← Cli.instParseableTypeInt.parse? str
   return BitVec.ofInt n intVal

def y : DCOp.ValueStream Int := ofList [some 1, some 2, none, none, some 3]

def fold_sext_to_and_wrong8_after := [llvm|
{
^0(%arg2 : i8):
  %0 = llvm.mlir.constant(true) : i1
  "llvm.return"(%0) : (i1) -> ()
}
]

def State.consOldExpr2Cache [DecidableEq d.Ty] [DecidableEq d.Op]
    {Γ : Ctxt d.Ty} {α}
    {lets : Lets d Γstart .pure Γ}
    (s : State d lets) (enew : Expr d Γ .pure α) (eold : Expr d Γ .pure α) (henew :
        ∀ (V : Γstart.Valuation), enew.denote (lets.denote V) = eold.denote (lets.denote V))
    (vold : HVector Γ.Var α)
    (hv : ∀ (V : Γstart.Valuation), eold.denoteOp (lets.denote V) =
      vold.map (lets.denote V)) :
    State d (Lets.var lets enew) where
  var2var := fun v => by admit /- proof elided -/
    | .none => .none
    | .some ⟨e', he'⟩ => .some ⟨e'.map fun _ v => v.appendInr, by admit /- proof elided -/
      ⟩

def add_smax_simplify2_after := [llvm|
{
^0(%arg24 : i8):
  %0 = llvm.mlir.constant(127 : i8) : i8
  %1 = llvm.add %arg24, %0 overflow<nsw> : i8
  "llvm.return"(%1) : (i8) -> ()
}
]

def lshrugt_03_13_after := [llvm|
{
^0(%arg370 : i4):
  %0 = llvm.mlir.constant(false) : i1
  "llvm.return"(%0) : (i1) -> ()
}
]

def cmpeq_xor_cst1_commuted_after := [llvm|
{
^0(%arg12 : i32, %arg13 : i32):
  %0 = llvm.mlir.constant(10 : i32) : i32
  %1 = llvm.mul %arg13, %arg13 : i32
  %2 = llvm.xor %arg12, %1 : i32
  %3 = llvm.icmp "eq" %2, %0 : i32
  "llvm.return"(%3) : (i1) -> ()
}
]

def select_constant_cmp : List (Σ Γ, LLVMPeepholeRewriteRefine 64  Γ) :=
  [⟨_, select_constant_cmp_true⟩,
  ⟨_, select_constant_cmp_false⟩]

def no_shift_xor_multiuse_cmp_with_and_after := [llvm|
{
^0(%arg88 : i32, %arg89 : i32, %arg90 : i32, %arg91 : i32):
  %0 = llvm.mlir.constant(4096 : i32) : i32
  %1 = llvm.mlir.constant(0 : i32) : i32
  %2 = llvm.mlir.constant(-4097 : i32) : i32
  %3 = llvm.and %arg88, %0 : i32
  %4 = llvm.icmp "eq" %3, %1 : i32
  %5 = llvm.and %arg89, %2 : i32
  %6 = "llvm.select"(%4, %5, %arg89) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i32, i32) -> i32
  %7 = "llvm.select"(%4, %arg91, %arg90) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i32, i32) -> i32
  %8 = llvm.mul %6, %7 : i32
  "llvm.return"(%8) : (i32) -> ()
}
]

def shl_and_and_fail_after := [llvm|
{
^0(%arg170 : i8, %arg171 : i8):
  %0 = llvm.mlir.constant(4 : i8) : i8
  %1 = llvm.mlir.constant(5 : i8) : i8
  %2 = llvm.mlir.constant(64 : i8) : i8
  %3 = llvm.shl %arg170, %0 : i8
  %4 = llvm.shl %arg171, %1 : i8
  %5 = llvm.and %4, %2 : i8
  %6 = llvm.and %3, %5 : i8
  "llvm.return"(%6) : (i8) -> ()
}
]

def hasAttr (attr : String) : Bool :=
  (op.getAttr? attr).isSome

def ugt_and_not_min_after := [llvm|
{
^0(%arg78 : i8, %arg79 : i8):
  %0 = llvm.icmp "ugt" %arg78, %arg79 : i8
  "llvm.return"(%0) : (i1) -> ()
}
]

noncomputable def complete (M : NFA' n) : NFA' n where
  σ := _
  M := M.M.complete

def add_select_sext_before := [llvm|
{
^0(%arg28 : i1):
  %0 = llvm.mlir.constant(64) : i64
  %1 = llvm.mlir.constant(1) : i64
  %2 = "llvm.select"(%arg28, %0, %1) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i64, i64) -> i64
  %3 = llvm.sext %arg28 : i1 to i64
  %4 = llvm.add %2, %3 : i64
  "llvm.return"(%4) : (i64) -> ()
}
]

WithBot.recBotCoe in Mathlib.Order.TypeTags

def zext_sext_add_icmp_i128_before := [llvm|
{
^0(%arg86 : i1, %arg87 : i1):
  %0 = llvm.mlir.constant(9223372036854775808 : i128) : i128
  %1 = llvm.zext %arg86 : i1 to i128
  %2 = llvm.sext %arg87 : i1 to i128
  %3 = llvm.add %1, %2 : i128
  %4 = llvm.icmp "sgt" %3, %0 : i128
  "llvm.return"(%4) : (i1) -> ()
}
]

def lshr_add_exact_after := [llvm|
{
^0(%arg6 : i8, %arg7 : i8):
  %0 = llvm.mlir.constant(-4 : i8) : i8
  %1 = llvm.mlir.constant(2 : i8) : i8
  %2 = llvm.and %arg6, %0 : i8
  %3 = llvm.and %arg7, %1 : i8
  %4 = llvm.lshr exact %2, %3 : i8
  "llvm.return"(%4) : (i8) -> ()
}
]

def uge_swap_and_max_commute_before := [llvm|
{
^0(%arg226 : i8, %arg227 : i8):
  %0 = llvm.mlir.constant(-1 : i8) : i8
  %1 = llvm.icmp "ule" %arg227, %arg226 : i8
  %2 = llvm.icmp "eq" %arg226, %0 : i8
  %3 = llvm.and %2, %1 : i1
  "llvm.return"(%3) : (i1) -> ()
}
]

def shl_nsw_add_negative_before := [llvm|
{
^0(%arg45 : i32):
  %0 = llvm.mlir.constant(-1 : i32) : i32
  %1 = llvm.mlir.constant(2 : i32) : i32
  %2 = llvm.add %arg45, %0 : i32
  %3 = llvm.shl %1, %2 overflow<nsw> : i32
  "llvm.return"(%3) : (i32) -> ()
}
]

def and_ne_with_one_bit_diff_constants2_logical_after := [llvm|
{
^0(%arg359 : i19):
  %0 = llvm.mlir.constant(-129 : i19) : i19
  %1 = llvm.mlir.constant(65 : i19) : i19
  %2 = llvm.and %arg359, %0 : i19
  %3 = llvm.icmp "ne" %2, %1 : i19
  "llvm.return"(%3) : (i1) -> ()
}
]

def t_1_10_before := [llvm|
{
^0(%arg13 : i8):
  %0 = llvm.mlir.constant(1 : i8) : i8
  %1 = llvm.mlir.constant(10 : i8) : i8
  %2 = llvm.icmp "ugt" %arg13, %0 : i8
  %3 = "llvm.select"(%2, %arg13, %0) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i8, i8) -> i8
  %4 = llvm.and %3, %1 : i8
  "llvm.return"(%4) : (i8) -> ()
}
]

def test_with_1_after := [llvm|
{
^0(%arg317 : i32):
  %0 = llvm.mlir.constant(0 : i32) : i32
  %1 = llvm.icmp "eq" %arg317, %0 : i32
  %2 = llvm.zext %1 : i1 to i32
  "llvm.return"(%2) : (i32) -> ()
}
]

def test_and4_after := [llvm|
{
^0(%arg40 : i32, %arg41 : i32):
  %0 = llvm.mlir.constant(2147483647 : i32) : i32
  %1 = llvm.and %arg41, %0 : i32
  %2 = llvm.icmp "ule" %arg40, %1 : i32
  "llvm.return"(%2) : (i1) -> ()
}
]

def masked_icmps_mask_notallzeros_bmask_mixed_swapped_5_before := [llvm|
{
^0(%arg38 : i32):
  %0 = llvm.mlir.constant(15 : i32) : i32
  %1 = llvm.mlir.constant(0 : i32) : i32
  %2 = llvm.mlir.constant(8 : i32) : i32
  %3 = llvm.and %arg38, %0 : i32
  %4 = llvm.icmp "ne" %3, %1 : i32
  %5 = llvm.and %arg38, %0 : i32
  %6 = llvm.icmp "eq" %5, %2 : i32
  %7 = llvm.and %6, %4 : i1
  "llvm.return"(%7) : (i1) -> ()
}
]

def alive_InstCombineShift__279_tgt  (w : Nat)  :=
[llvm( w )| {
^bb0(%X : _, %C : _):
  %v1 = llvm.lshr %X, %C
  %v2 = llvm.mlir.constant -1
  %v3 = llvm.shl %v2, %C
  %v4 = llvm.and %X, %v3
  llvm.return %v4
}]

@[simp] def ofBool (b : Bool) : Circuit α :=
  if b then tru else fals

def corec₂ {β} (s0 : β) (f : β → (Option α × Option γ × β)) : Stream α × Stream γ :=
  let f' := fun b =>
    let x := f b
    (x.fst, x.snd.fst)
  let g := (f · |>.snd.snd)
  let x := Stream'.corec f' g s0
  (
    fun i => (x i).fst,
    fun i => (x i).snd,
  )

def ashrsgt_02_00_after := [llvm|
{
^0(%arg301 : i4):
  %0 = llvm.mlir.constant(3 : i4) : i4
  %1 = llvm.icmp "sgt" %arg301, %0 : i4
  "llvm.return"(%1) : (i1) -> ()
}
]

@[simp_denote]
def sltiu_llvm_i64 := [LV| {
    ^entry (%a: i64):
    %0 = llvm.mlir.constant (3) : i64
    %1 = llvm.icmp.ult %a, %0 : i64
    %2 = llvm.zext %1 : i1 to i64
    llvm.return %2 : i64
  }]

def select_zext_or_eq_ult_add_after := [llvm|
{
^0(%arg14 : i32):
  %0 = llvm.mlir.constant(-3 : i32) : i32
  %1 = llvm.mlir.constant(3 : i32) : i32
  %2 = llvm.add %arg14, %0 : i32
  %3 = llvm.icmp "ult" %2, %1 : i32
  %4 = llvm.zext %3 : i1 to i32
  "llvm.return"(%4) : (i32) -> ()
}
]

def a_true_implies_b_false2_comm_after := [llvm|
{
^0(%arg18 : i8, %arg19 : i1, %arg20 : i1):
  %0 = llvm.mlir.constant(20 : i8) : i8
  %1 = llvm.mlir.constant(false) : i1
  %2 = llvm.icmp "ugt" %arg18, %0 : i8
  %3 = "llvm.select"(%2, %arg20, %1) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i1, i1) -> i1
  "llvm.return"(%3) : (i1) -> ()
}
]

def p_after := [llvm|
{
^0(%arg60 : i32, %arg61 : i32, %arg62 : i32):
  %0 = llvm.mlir.constant(-1 : i32) : i32
  %1 = llvm.and %arg60, %arg62 : i32
  %2 = llvm.xor %arg62, %0 : i32
  %3 = llvm.and %arg61, %2 : i32
  %4 = llvm.or disjoint %1, %3 : i32
  "llvm.return"(%4) : (i32) -> ()
}
]

def ugt_swap_and_not_min_logical_before := [llvm|
{
^0(%arg68 : i8, %arg69 : i8):
  %0 = llvm.mlir.constant(0 : i8) : i8
  %1 = llvm.mlir.constant(false) : i1
  %2 = llvm.icmp "ult" %arg69, %arg68 : i8
  %3 = llvm.icmp "ne" %arg68, %0 : i8
  %4 = "llvm.select"(%2, %3, %1) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i1, i1) -> i1
  "llvm.return"(%4) : (i1) -> ()
}
]

def xor_ashr_not_fail_invalid_xor_constant_before := [llvm|
{
^0(%arg15 : i8, %arg16 : i8, %arg17 : i8):
  %0 = llvm.mlir.constant(-2 : i8) : i8
  %1 = llvm.ashr %arg15, %arg17 : i8
  %2 = llvm.ashr %arg16, %arg17 : i8
  %3 = llvm.xor %2, %0 : i8
  %4 = llvm.xor %1, %3 : i8
  "llvm.return"(%4) : (i8) -> ()
}
]

def bools_logical_commute1_before := [llvm|
{
^0(%arg96 : i1, %arg97 : i1, %arg98 : i1):
  %0 = llvm.mlir.constant(true) : i1
  %1 = llvm.mlir.constant(false) : i1
  %2 = llvm.xor %arg98, %0 : i1
  %3 = "llvm.select"(%arg96, %2, %1) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i1, i1) -> i1
  %4 = "llvm.select"(%arg98, %arg97, %1) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i1, i1) -> i1
  %5 = "llvm.select"(%3, %0, %4) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i1, i1) -> i1
  "llvm.return"(%5) : (i1) -> ()
}
]

def test_shl__all_are_safe_before := [llvm|
{
^0(%arg84 : i32, %arg85 : i64):
  %0 = llvm.mlir.constant(15 : i32) : i32
  %1 = llvm.mlir.constant(2 : i32) : i32
  %2 = llvm.mlir.constant(0 : i32) : i32
  %3 = llvm.and %arg84, %0 : i32
  %4 = llvm.shl %3, %1 : i32
  %5 = llvm.zext %4 : i32 to i64
  %6 = llvm.icmp "eq" %3, %2 : i32
  %7 = llvm.ashr %arg85, %5 : i64
  %8 = "llvm.select"(%6, %arg85, %7) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i64, i64) -> i64
  "llvm.return"(%8) : (i64) -> ()
}
]

def logical_and_bitwise_and_icmps_before := [llvm|
{
^0(%arg220 : i8, %arg221 : i8, %arg222 : i8):
  %0 = llvm.mlir.constant(42 : i8) : i8
  %1 = llvm.mlir.constant(1 : i8) : i8
  %2 = llvm.mlir.constant(0 : i8) : i8
  %3 = llvm.mlir.constant(false) : i1
  %4 = llvm.icmp "eq" %arg221, %0 : i8
  %5 = llvm.and %arg220, %1 : i8
  %6 = llvm.shl %1, %arg222 : i8
  %7 = llvm.and %arg220, %6 : i8
  %8 = llvm.icmp "ne" %5, %2 : i8
  %9 = llvm.icmp "ne" %7, %2 : i8
  %10 = llvm.and %4, %8 : i1
  %11 = "llvm.select"(%10, %9, %3) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i1, i1) -> i1
  "llvm.return"(%11) : (i1) -> ()
}
]

def zext_zext_sle_op0_narrow_before := [llvm|
{
^0(%arg78 : i8, %arg79 : i16):
  %0 = llvm.zext %arg78 : i8 to i32
  %1 = llvm.zext %arg79 : i16 to i32
  %2 = llvm.icmp "sle" %0, %1 : i32
  "llvm.return"(%2) : (i1) -> ()
}
]

def alive_AddSub_1574_src :=
[sllvm| {
^bb0(%X : i64, %C : i64, %C2 : i64):
  %v1 = llvm.add %X, %C2 : i64
  %v2 = llvm.sub %C, %v1 : i64
  llvm.return %v2 : i64
}]

abbrev Expr (Γ) (ty) := _root_.Expr ExOp Γ .pure ty

def shrink_and_before := [llvm|
{
^0(%arg9 : i64):
  %0 = llvm.mlir.constant(42) : i64
  %1 = llvm.and %arg9, %0 : i64
  %2 = llvm.trunc %1 : i64 to i31
  "llvm.return"(%2) : (i31) -> ()
}
]

def main4e_like_before := [llvm|
{
^0(%arg128 : i32, %arg129 : i32, %arg130 : i32):
  %0 = llvm.mlir.constant(0 : i32) : i32
  %1 = llvm.mlir.constant(1 : i32) : i32
  %2 = llvm.and %arg128, %arg129 : i32
  %3 = llvm.icmp "eq" %2, %arg129 : i32
  %4 = llvm.and %arg128, %arg130 : i32
  %5 = llvm.icmp "eq" %4, %arg130 : i32
  %6 = llvm.and %3, %5 : i1
  %7 = "llvm.select"(%6, %0, %1) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i32, i32) -> i32
  "llvm.return"(%7) : (i32) -> ()
}
]

def scalar_i8_lshr_and_signbit_eq_before := [llvm|
{
^0(%arg35 : i8, %arg36 : i8):
  %0 = llvm.mlir.constant(-128 : i8) : i8
  %1 = llvm.mlir.constant(0 : i8) : i8
  %2 = llvm.lshr %arg35, %arg36 : i8
  %3 = llvm.and %2, %0 : i8
  %4 = llvm.icmp "eq" %3, %1 : i8
  "llvm.return"(%4) : (i1) -> ()
}
]

def lshr_neg_slt_zero_before := [llvm|
{
^0(%arg52 : i8):
  %0 = llvm.mlir.constant(-17 : i8) : i8
  %1 = llvm.mlir.constant(0 : i8) : i8
  %2 = llvm.lshr %0, %arg52 : i8
  %3 = llvm.icmp "slt" %2, %1 : i8
  "llvm.return"(%3) : (i1) -> ()
}
]

def commutativity_constant_14_vary_before := [llvm|
{
^0(%arg12 : i4, %arg13 : i4):
  %0 = llvm.mlir.constant(-2 : i4) : i4
  %1 = llvm.mlir.constant(1 : i4) : i4
  %2 = llvm.xor %arg12, %0 : i4
  %3 = llvm.and %2, %1 : i4
  %4 = llvm.xor %arg12, %3 : i4
  "llvm.return"(%4) : (i4) -> ()
}
]

def iso_binary (a b : Stream' (BitVec 1)) : Stream' (Vector (BitVec 1) 2) :=
    fun n =>
      {toArray := [a n, b n].toArray, size_toArray := by admit /- proof elided -/

def select_icmp_eq_and_4096_0_xor_4096_before := [llvm|
{
^0(%arg221 : i32, %arg222 : i32):
  %0 = llvm.mlir.constant(4096 : i32) : i32
  %1 = llvm.mlir.constant(0 : i32) : i32
  %2 = llvm.and %arg221, %0 : i32
  %3 = llvm.icmp "eq" %2, %1 : i32
  %4 = llvm.xor %arg222, %0 : i32
  %5 = "llvm.select"(%3, %arg222, %4) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i32, i32) -> i32
  "llvm.return"(%5) : (i32) -> ()
}
]

def sub_undemanded_low_bits_before := [llvm|
{
^0(%arg0 : i32):
  %0 = llvm.mlir.constant(15 : i32) : i32
  %1 = llvm.mlir.constant(1616 : i32) : i32
  %2 = llvm.mlir.constant(4 : i32) : i32
  %3 = llvm.or %arg0, %0 : i32
  %4 = llvm.sub %3, %1 : i32
  %5 = llvm.lshr %4, %2 : i32
  "llvm.return"(%5) : (i32) -> ()
}
]

def neg_not_signbit1_after := [llvm|
{
^0(%arg5 : i8):
  %0 = llvm.mlir.constant(-1 : i8) : i8
  %1 = llvm.icmp "sgt" %arg5, %0 : i8
  %2 = llvm.zext %1 : i1 to i32
  "llvm.return"(%2) : (i32) -> ()
}
]

def lshrult_01_15_before := [llvm|
{
^0(%arg352 : i4):
  %0 = llvm.mlir.constant(1 : i4) : i4
  %1 = llvm.mlir.constant(-1 : i4) : i4
  %2 = llvm.lshr %arg352, %0 : i4
  %3 = llvm.icmp "ult" %2, %1 : i4
  "llvm.return"(%3) : (i1) -> ()
}
]

def sel_zext_constants_before := [llvm|
{
^0(%arg96 : i1):
  %0 = llvm.mlir.constant(-1 : i8) : i8
  %1 = llvm.mlir.constant(42 : i8) : i8
  %2 = "llvm.select"(%arg96, %0, %1) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i8, i8) -> i8
  %3 = llvm.zext %2 : i8 to i16
  "llvm.return"(%3) : (i16) -> ()
}
]

def irc_constants_C2MinusAPlusC1_neg2_2 : LLVMPeepholeRewriteRefine 64 [Ty.llvm (.bitvec 64)] where
  lhs := [LV| {
    ^entry (%a: i64):
      %c1 = llvm.mlir.constant (-2) : i64
      %c2 = llvm.mlir.constant (2) : i64
      %0 = llvm.add %a, %c1 : i64
      %1 = llvm.sub %c2, %0 : i64
      llvm.return %1 : i64
  }]
  rhs := [LV| {
    ^entry (%a: i64):
      %c1 = llvm.mlir.constant (-2) : i64
      %c2 = llvm.mlir.constant (2) : i64
      %0 = llvm.sub %c2, %c1 : i64
      %1 = llvm.sub %0, %a : i64
      llvm.return %1 : i64
  }]

def lshrugt_02_15_exact_after := [llvm|
{
^0(%arg190 : i4):
  %0 = llvm.mlir.constant(false) : i1
  "llvm.return"(%0) : (i1) -> ()
}
]

def State.cseCom {α}
  {lets : Lets d Γstart .pure Γ}
  (s : State d lets)
  (com: Com d Γ .pure α) :
  { com' : Com d Γ .pure α
    // ∀ (V : Ctxt.Valuation Γstart), com.denote (lets.denote V) = com'.denote (lets.denote V) } :=
  match com with
  | .rets vs =>
      let ⟨vs', hvs'⟩ := s.vars2vars vs
      ⟨.rets vs', by admit /- proof elided -/
        ⟩
  | .var e body =>
      let ⟨⟨e', he'⟩, v'?⟩ := s.cseExpr e
      match v'? with
      | .none =>  
        let s' := s.consNewExpr2Cache (e := e')
         
        let ⟨body', hbody'⟩ := s'.cseCom body
        ⟨.var e' body',  by admit /- proof elided -/
            ⟩
      | .some ⟨v', hv'⟩ =>
        let s' := s.consOldExpr2Cache (enew := e') (eold := e) (henew := by admit /- proof elided -/
        )
          (vold := v') (hv := by admit /- proof elided -/
          )
          
        let ⟨body', hbody'⟩ := s'.cseCom body
        
        ⟨.var e body' 
        , by admit /- proof elided -/
        ⟩

def icmp_power2_and_icmp_shifted_mask_2147483648_2147483647_after := [llvm|
{
^0(%arg43 : i32):
  %0 = llvm.mlir.constant(2147483647 : i32) : i32
  %1 = llvm.icmp "ult" %arg43, %0 : i32
  "llvm.return"(%1) : (i1) -> ()
}
]

def mulh_to_lshr_512 : RISCVPeepholeRewrite [Ty.riscv (.bv)] where
  lhs := [LV| {
    ^entry (%x: !riscv.reg):
      %c = li (512) : !riscv.reg
      %0 = mulh %c, %x : !riscv.reg
      ret %0 : !riscv.reg
  }]
  rhs := [LV| {
    ^entry (%x: !riscv.reg):
      %c = li (55) : !riscv.reg
      %0 = sra %x, %c : !riscv.reg
      ret %0 : !riscv.reg
  }]

def bitwise_and_logical_and_icmps_before := [llvm|
{
^0(%arg232 : i8, %arg233 : i8, %arg234 : i8):
  %0 = llvm.mlir.constant(42 : i8) : i8
  %1 = llvm.mlir.constant(1 : i8) : i8
  %2 = llvm.mlir.constant(0 : i8) : i8
  %3 = llvm.mlir.constant(false) : i1
  %4 = llvm.icmp "eq" %arg233, %0 : i8
  %5 = llvm.and %arg232, %1 : i8
  %6 = llvm.shl %1, %arg234 : i8
  %7 = llvm.and %arg232, %6 : i8
  %8 = llvm.icmp "ne" %5, %2 : i8
  %9 = llvm.icmp "ne" %7, %2 : i8
  %10 = "llvm.select"(%4, %8, %3) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i1, i1) -> i1
  %11 = llvm.and %10, %9 : i1
  "llvm.return"(%11) : (i1) -> ()
}
]

Std.HashMap in Std.Data.HashMap.Basic

def clear_to_set_decomposebittest_before := [llvm|
{
^0(%arg13 : i8):
  %0 = llvm.mlir.constant(-1 : i8) : i8
  %1 = llvm.mlir.constant(-125 : i8) : i8
  %2 = llvm.mlir.constant(3 : i8) : i8
  %3 = llvm.icmp "sgt" %arg13, %0 : i8
  %4 = "llvm.select"(%3, %1, %2) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i8, i8) -> i8
  "llvm.return"(%4) : (i8) -> ()
}
]

def smear_set_bit_different_dest_type_wider_dst_after := [llvm|
{
^0(%arg0 : i32):
  %0 = llvm.mlir.constant(24 : i32) : i32
  %1 = llvm.mlir.constant(31 : i32) : i32
  %2 = llvm.shl %arg0, %0 : i32
  %3 = llvm.ashr %2, %1 : i32
  %4 = llvm.sext %3 : i32 to i64
  "llvm.return"(%4) : (i64) -> ()
}
]

def zext_sub_const_before := [llvm|
{
^0(%arg33 : i1):
  %0 = llvm.mlir.constant(42) : i64
  %1 = llvm.zext %arg33 : i1 to i64
  %2 = llvm.sub %0, %1 : i64
  "llvm.return"(%2) : (i64) -> ()
}
]

def test15c_before := [llvm|
{
^0(%arg25 : i32):
  %0 = llvm.mlir.constant(16 : i32) : i32
  %1 = llvm.mlir.constant(0 : i32) : i32
  %2 = llvm.and %arg25, %0 : i32
  %3 = llvm.icmp "eq" %2, %0 : i32
  %4 = "llvm.select"(%3, %0, %1) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i32, i32) -> i32
  "llvm.return"(%4) : (i32) -> ()
}
]

def ult_swap_or_not_max_logical_before := [llvm|
{
^0(%arg36 : i8, %arg37 : i8):
  %0 = llvm.mlir.constant(-1 : i8) : i8
  %1 = llvm.mlir.constant(true) : i1
  %2 = llvm.icmp "ugt" %arg37, %arg36 : i8
  %3 = llvm.icmp "ne" %arg36, %0 : i8
  %4 = "llvm.select"(%2, %1, %3) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i1, i1) -> i1
  "llvm.return"(%4) : (i1) -> ()
}
]

def positive_samevar_shlnsw_before := [llvm|
{
^0(%arg52 : i8, %arg53 : i8):
  %0 = llvm.lshr %arg52, %arg53 : i8
  %1 = llvm.shl %0, %arg53 overflow<nsw> : i8
  "llvm.return"(%1) : (i8) -> ()
}
]

class DecidableNFA [Fintype σ] [Fintype α] [DecidableEq σ] [DecidableEq α] (m : NFA α σ) where
  decidable_start : Decidable (q ∈ m.start)
  decidable_accept : Decidable (q ∈ m.accept)
  decidable_step : Decidable (s' ∈ m.step s a)

def eq_smin4_after := [llvm|
{
^0(%arg81 : i32, %arg82 : i32):
  %0 = llvm.mlir.constant(3 : i32) : i32
  %1 = llvm.add %arg81, %0 : i32
  %2 = llvm.icmp "sle" %1, %arg82 : i32
  "llvm.return"(%2) : (i1) -> ()
}
]

def c_after := [llvm|
{
^0(%arg0 : i32):
  %0 = llvm.mlir.constant(715827882 : i32) : i32
  "llvm.return"(%0) : (i32) -> ()
}
]

def or_to_nxor1_after := [llvm|
{
^0(%arg93 : i32, %arg94 : i32):
  %0 = llvm.mlir.constant(-1 : i32) : i32
  %1 = llvm.xor %arg93, %arg94 : i32
  %2 = llvm.xor %1, %0 : i32
  "llvm.return"(%2) : (i32) -> ()
}
]

def and_xor_commute4_before := [llvm|
{
^0(%arg149 : i32, %arg150 : i32):
  %0 = llvm.mlir.constant(42 : i32) : i32
  %1 = llvm.udiv %0, %arg149 : i32
  %2 = llvm.udiv %0, %arg150 : i32
  %3 = llvm.and %1, %2 : i32
  %4 = llvm.xor %2, %3 : i32
  "llvm.return"(%4) : (i32) -> ()
}
]

def Complete' (M : NFA α σ) : Prop := ∀ q a, M.step q a ≠ ∅

def scalar_i64_shl_and_signbit_eq_after := [llvm|
{
^0(%arg29 : i64, %arg30 : i64):
  %0 = llvm.mlir.constant(-1) : i64
  %1 = llvm.shl %arg29, %arg30 : i64
  %2 = llvm.icmp "sgt" %1, %0 : i64
  "llvm.return"(%2) : (i1) -> ()
}
]

def n13_overshift_after := [llvm|
{
^0(%arg7 : i32, %arg8 : i64, %arg9 : i32):
  %0 = llvm.mlir.constant(32 : i32) : i32
  %1 = llvm.mlir.constant(0 : i32) : i32
  %2 = llvm.sub %0, %arg9 : i32
  %3 = llvm.lshr %arg7, %2 : i32
  %4 = llvm.add %arg9, %0 : i32
  %5 = llvm.zext nneg %4 : i32 to i64
  %6 = llvm.shl %arg8, %5 : i64
  %7 = llvm.trunc %6 : i64 to i32
  %8 = llvm.and %3, %7 : i32
  %9 = llvm.icmp "ne" %8, %1 : i32
  "llvm.return"(%9) : (i1) -> ()
}
]

def constLLVM33 : Com LLVMPlusRiscV ⟨[]⟩ .pure (.llvm (.bitvec 64)) := [LV| {
  ^entry ():
    %1 = llvm.mlir.constant (33) : i64
    llvm.return %1 : i64
  }]

@[simp_llvm]
def sdiv? {w : Nat} (x y : BitVec w) : IntW w :=
  if y == 0 || (w != 1 && x == (BitVec.intMin w) && y == -1) then
    .poison
  else
    .value (x.sdiv y)

@[reducible]
def tests : List ConcreteCliTest := llvmTests!

def test14a_after := [llvm|
{
^0(%arg25 : i79):
  %0 = llvm.mlir.constant(77 : i79) : i79
  %1 = llvm.and %arg25, %0 : i79
  "llvm.return"(%1) : (i79) -> ()
}
]

def and_or1_commuted_before := [llvm|
{
^0(%arg197 : i1, %arg198 : i1, %arg199 : i1):
  %0 = llvm.mlir.constant(true) : i1
  %1 = llvm.xor %arg197, %0 : i1
  %2 = llvm.or %arg199, %1 : i1
  %3 = "llvm.select"(%2, %arg197, %arg198) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i1, i1) -> i1
  "llvm.return"(%3) : (i1) -> ()
}
]

def test_sext2_before := [llvm|
{
^0(%arg47 : i1, %arg48 : i1):
  %0 = llvm.mlir.constant(-1 : i32) : i32
  %1 = llvm.sext %arg47 : i1 to i32
  %2 = "llvm.select"(%arg48, %0, %1) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i32, i32) -> i32
  "llvm.return"(%2) : (i32) -> ()
}
]

def eq_shift_in_zeros_before := [llvm|
{
^0(%arg84 : i32, %arg85 : i32):
  %0 = llvm.mlir.constant(8 : i32) : i32
  %1 = llvm.mlir.constant(16 : i32) : i32
  %2 = llvm.lshr %arg84, %0 : i32
  %3 = llvm.trunc %2 : i32 to i8
  %4 = llvm.lshr %arg84, %1 : i32
  %5 = llvm.trunc %4 : i32 to i24
  %6 = llvm.lshr %arg85, %0 : i32
  %7 = llvm.trunc %6 : i32 to i8
  %8 = llvm.lshr %arg85, %1 : i32
  %9 = llvm.trunc %8 : i32 to i24
  %10 = llvm.icmp "eq" %3, %7 : i8
  %11 = llvm.icmp "eq" %5, %9 : i24
  %12 = llvm.and %11, %10 : i1
  "llvm.return"(%12) : (i1) -> ()
}
]

def shl_add_lshr_after := [llvm|
{
^0(%arg154 : i32, %arg155 : i32, %arg156 : i32):
  %0 = llvm.lshr %arg156, %arg155 : i32
  %1 = llvm.add %0, %arg154 overflow<nuw> : i32
  "llvm.return"(%1) : (i32) -> ()
}
]

def zext_true_val_must_be_one_before := [llvm|
{
^0(%arg5 : i1):
  %0 = llvm.mlir.constant(42 : i32) : i32
  %1 = llvm.zext %arg5 : i1 to i32
  %2 = "llvm.select"(%arg5, %1, %0) <{"fastmathFlags" = #llvm.fastmath<none>}> : (i1, i32, i32) -> i32
  "llvm.return"(%2) : (i32) -> ()
}
]

def not_match_inconsistent_values_before := [llvm|
{
^0(%arg12 : i64):
  %0 = llvm.mlir.constant(299) : i64
  %1 = llvm.mlir.constant(29) : i64
  %2 = llvm.mlir.constant(64) : i64
  %3 = llvm.urem %arg12, %0 : i64
  %4 = llvm.udiv %arg12, %1 : i64
  %5 = llvm.urem %4, %2 : i64
  %6 = llvm.mul %5, %0 : i64
  %7 = llvm.add %3, %6 : i64
  "llvm.return"(%7) : (i64) -> ()
}
]

def or_xor_xor_normal_variant4_after := [llvm|
{
^0(%arg11 : i64, %arg12 : i64):
  %0 = llvm.xor %arg12, %arg11 : i64
  "llvm.return"(%0) : (i64) -> ()
}
]

def llvm_zext_lower_riscv_16_to_32 : LLVMPeepholeRewriteRefine 32 [Ty.llvm (.bitvec 16)] :=
  {lhs:= zext_llvm_16_to_32, rhs:= zext_riscv_16_to_32}

def ofList (vals : List (Option α)) : Stream α :=
  fun i => (vals[i]?).join

def not_signbit_after := [llvm|
{
^0(%arg22 : i8):
  %0 = llvm.mlir.constant(-1 : i8) : i8
  %1 = llvm.icmp "sgt" %arg22, %0 : i8
  %2 = llvm.zext %1 : i1 to i8
  "llvm.return"(%2) : (i8) -> ()
}
]

def or_nontrivial_mask2_before := [llvm|
{
^0(%arg11 : i16):
  %0 = llvm.mlir.constant(127 : i8) : i8
  %1 = llvm.mlir.constant(-4096 : i16) : i16
  %2 = llvm.mlir.constant(20480 : i16) : i16
  %3 = llvm.trunc %arg11 : i16 to i8
  %4 = llvm.icmp "ne" %3, %0 : i8
  %5 = llvm.and %arg11, %1 : i16
  %6 = llvm.icmp "ne" %5, %2 : i16
  %7 = llvm.or %4, %6 : i1
  "llvm.return"(%7) : (i1) -> ()
}
]

abbrev BitVecs.pair {w : Nat} (bv1 bv2 : BitVec w) : BitVecs 2 := ⟨w, bv1 ::ᵥ bv2 ::ᵥ .nil⟩

def t9_before := [llvm|
{
^0(%arg192 : i8, %arg193 : i8):
  %0 = llvm.mlir.constant(0 : i8) : i8
  %1 = llvm.sub %arg193, %arg192 : i8
  %2 = llvm.sub %0, %1 : i8
  "llvm.return"(%2) : (i8) -> ()
}
]

@[simp_denote]
def llvm_urem: Com  LLVMPlusRiscV ⟨[.llvm (.bitvec 64), .llvm (.bitvec 64)]⟩
  .pure (.llvm (.bitvec 64)) := [LV| {
  ^entry (%x: i64, %y: i64 ):
    %1 = llvm.urem    %x, %y : i64
    llvm.return %1 : i64
  }]

abbrev State := Nat

Sum.inr in Init.Core
</all_available_defs>

<all_available_lemmas>
decide_eq_true_iff in Init.PropLemmas
iff_true in Init.SimpLemmas
inf_of_le_left in Mathlib.Order.Lattice
le_refl in Mathlib.Order.Defs.PartialOrder
left_eq_inf in Mathlib.Order.Lattice
not_iff in Mathlib.Logic.Basic
not_le in Mathlib.Order.Defs.LinearOrder
not_lt in Mathlib.Order.Defs.LinearOrder

theorem scanOr_eq_decide (s : BitStream) (n : Nat) :
    s.scanOr n = decide (∃ (i : Nat), i ≤ n ∧ s i = true)

theorem scanOr_true_iff (s : BitStream) (n : Nat)
    : s.scanOr n = true ↔ ∃ (i : Nat), (i ≤ n) ∧ s i = true

theorem scanOr_false_iff (s : BitStream) (n : Nat) : s.scanOr n = false ↔ ∀ (i : Nat), (hi : i ≤ n) → s i = false

@[simp]
theorem scanOr_succ (s : BitStream) : scanOr s (n+1) = ((s.scanOr n) || s (n + 1))

theorem and_add_bool_to_select_multi_use_thm.extracted_1._1 : ∀ (x : BitVec 32) (x_1 : BitVec 1),
  x_1 = 1#1 → (-1#32 + zeroExtend 32 x_1 &&& x) + (-1#32 + zeroExtend 32 x_1) = 0#32

theorem sdiv400_yes_proof : sdiv400_yes_before ⊑ sdiv400_yes_after

theorem a_false_implies_b_true2_proof : a_false_implies_b_true2_before ⊑ a_false_implies_b_true2_after

theorem rev8_mul_and_lshr_thm (e : IntW 8) :
  trunc 8
      (lshr
        (mul
          (LLVM.or (LLVM.and (mul (zext 64 e) (const? 64 2050) { «nsw» := true, «nuw» := true }) (const? 64 139536))
            (LLVM.and (mul (zext 64 e) (const? 64 32800) { «nsw» := true, «nuw» := true }) (const? 64 558144)))
          (const? 64 65793) { «nsw» := true, «nuw» := true })
        (const? 64 16)) ⊑
    trunc 8
      (lshr
        (mul
          (LLVM.or (LLVM.and (mul (zext 64 e) (const? 64 2050) { «nsw» := true, «nuw» := true }) (const? 64 139536))
            (LLVM.and (mul (zext 64 e) (const? 64 32800) { «nsw» := true, «nuw» := true }) (const? 64 558144))
            { «disjoint» := true })
          (const? 64 65793) { «nsw» := true, «nuw» := true })
        (const? 64 16))

theorem icmp_equality_test_proof : icmp_equality_test_before ⊑ icmp_equality_test_after

@[simp] theorem appendList_eq : Γ ++ tys = Γ ++ ⟨tys⟩

theorem ne_smax2_proof : ne_smax2_before ⊑ ne_smax2_after

theorem select_icmp_ne_0_and_8_and_not_1073741824_proof : select_icmp_ne_0_and_8_and_not_1073741824_before ⊑ select_icmp_ne_0_and_8_and_not_1073741824_after

theorem icmp_ne_sext_slt_allones_nofold_proof : icmp_ne_sext_slt_allones_nofold_before ⊑ icmp_ne_sext_slt_allones_nofold_after

@[simp] theorem Lets.addComToEnd_rets {lets : Lets d Γ_in eff Γ_out} :
    addComToEnd lets (.rets v : Com d Γ_out eff t) = lets

@[simp]
lemma RawCNFA.lift_processState_spec {m : CNFA n₁} {f : Fin n₁ → Fin n₂} :
    s' ∈ (lift.processState m.m f trs s₀).getD (s, b) ∅ ↔
      s' ∈ trs.getD (s, b) ∅ ∨ s = s₀ ∧ s' ∈ m.m.tr s (b.transport f)

theorem lshr_add_xor_fail_thm (e e_1 : IntW 8) :
  LLVM.xor (lshr e_1 (const? 8 1)) (add (lshr e (const? 8 1)) (const? 8 123)) ⊑
    LLVM.xor (lshr e_1 (const? 8 1))
      (add (lshr e (const? 8 1)) (const? 8 123) { «nsw» := false, «nuw» := true })

theorem nonexact_ashr_ne_proof : nonexact_ashr_ne_before ⊑ nonexact_ashr_ne_after

theorem f_var1_commutative_and_proof : f_var1_commutative_and_before ⊑ f_var1_commutative_and_after

theorem n0_proof : n0_before ⊑ n0_after

theorem logic_and_logic_or_3_thm.extracted_1._4 : ∀ (x x_1 : BitVec 1), ¬x_1 = 1#1 → x = 1#1 → 0#1 = 1#1 → False

theorem neg_mask_proof : neg_mask_before ⊑ neg_mask_after

theorem e_2023 :
     - 1 * (f ^^^ ( ~~~d ||| (e ||| f))) + 2 * ( ~~~(d ||| e) |||  ~~~(d ^^^ (e ^^^ f))) + 3 * (e ^^^ (d &&& ( ~~~e ||| f))) - 11 *  ~~~( ~~~d &&& ( ~~~e &&& f)) - 3 * (e &&&  ~~~(d ^^^ f)) - 2 * ((d &&& f) ^^^ (e ||| f)) - 7 * ((d ||| e) &&& (e ^^^ f)) - 6 * (f ^^^  ~~~( ~~~d ||| ( ~~~e &&& f))) - 2 * (e ^^^  ~~~( ~~~d ||| (e ^^^ f))) + 7 * ( ~~~(d ||| e) ||| (d ^^^ (e ^^^ f))) - 1 * ((d &&& e) ^^^ (d ^^^ ( ~~~e ||| f))) + 11 *  ~~~(d ||| e) + 1 * ( ~~~(d |||  ~~~e) |||  ~~~(e ^^^ f)) + 1 * (e ^^^  ~~~( ~~~d &&& (e ||| f))) - 6 * (d ||| ( ~~~e ||| f)) + 2 *  ~~~f + 2 * ( ~~~d &&& (e ||| f)) - 1 * ( ~~~d ||| (e &&& f)) + 1 * (f ^^^ ( ~~~d &&& ( ~~~e ||| f))) - 3 * (d ^^^ f) - 7 * (d &&& (e ||| f)) - 1 * (d ||| (e ||| f)) - 1 * (e ^^^ (d ||| (e ||| f))) + 3 * (e ^^^ ( ~~~d &&& (e ||| f))) + 1 * (e ^^^  ~~~(d &&& (e ||| f))) + 4 * (e ^^^ ( ~~~d ||| (e ||| f))) - 9 *  ~~~(d ||| (e ||| f)) + 13 *  ~~~(d ||| ( ~~~e ||| f)) + 15 *  ~~~( ~~~d ||| (e ||| f)) + 36 *  ~~~( ~~~d ||| ( ~~~e ||| f)) - 8 * ( ~~~d &&& ( ~~~e &&& f)) + 25 * ( ~~~d &&& (e &&& f)) + 29 * (d &&& ( ~~~e &&& f)) + 18 * (d &&& (e &&& f)) = 1 * ( ~~~d ||| (e ||| f))

theorem t0_ult_slt_65536_thm (e e_1 e_2 : IntW 32) :
  select (icmp IntPred.ult e_2 (const? 32 65536)) e_2
      (select (icmp IntPred.slt e_2 (const? 32 65536)) e_1 e) ⊑
    select (icmp IntPred.sgt e_2 (const? 32 65535)) e
      (select (icmp IntPred.slt e_2 (const? 32 0)) e_1 e_2)

theorem mul64_low_proof : mul64_low_before ⊑ mul64_low_after

theorem test_imply_not2_thm.extracted_1._4 : ∀ (x : BitVec 1) (x_1 : BitVec 32),
  ofBool (x_1 == 0#32) = 1#1 → ¬ofBool (x_1 != 0#32) = 1#1 → x ||

theorem select_of_symmetric_selects_thm.extracted_1._3 : ∀ (x : BitVec 32) (x_1 x_2 : BitVec 1),
  x_2 = 1#1 → ¬x_1 = 1#1 → ¬x_1 ^^^ x_2 = 1#1 → False

theorem test_thm.extracted_1._1_1_1 : ∀ (x x_1 : BitVec 16),
  True ∧ (signExtend 32 x_1).saddOverflow (signExtend 32 x) = true → False

@[simp] lemma BitVec.lk11 : (1#2 : BitVec 2)[1] = false

theorem not_or_or_and_not_and_and_commute2_proof : not_or_or_and_not_and_and_commute2_before ⊑ not_or_or_and_not_and_and_commute2_after

@[simp]
lemma swapLastTwo_eq2 : swapLastTwo (n := n) n = Fin.last (n+1)

theorem t9_ashr_exact_flag_preservation_thm.extracted_1._2 : ∀ (x x_1 : BitVec 32),
  ¬(True ∧ x_1 >>> (32#32 - x) <<< (32#32 - x) ≠ x_1 ∨
        32#32 - x ≥ ↑32 ∨
          True ∧
              x_1.sshiftRight' (32#32 - x) >>> (x + BitVec.ofInt 32 (-2)) <<< (x + BitVec.ofInt 32 (-2)) ≠
                x_1.sshiftRight' (32#32 - x) ∨
            x + BitVec.ofInt 32 (-2) ≥ ↑32) →
    ¬(True ∧ x_1 >>> 30#32 <<< 30#32 ≠ x_1 ∨ 30#32 ≥ ↑32) →
      (x_1.sshiftRight' (32#32 - x)).sshiftRight' (x + BitVec.ofInt 32 (-2)) = x_1.sshiftRight' 30#32

theorem negation_of_increment_via_or_with_no_common_bits_set_proof : negation_of_increment_via_or_with_no_common_bits_set_before ⊑ negation_of_increment_via_or_with_no_common_bits_set_after

theorem ashrslt_01_09_exact_proof : ashrslt_01_09_exact_before ⊑ ashrslt_01_09_exact_after

theorem main7g_logical_thm.extracted_1._2 : ∀ (x x_1 x_2 : BitVec 32),
  ¬ofBool (x_2 &&& x_1 == x_2 &&& x_1 &&& x) = 1#1 →
    ofBool (x_2 &&& x_1 != x_2 &&& x_1 &&& x) = 1#1 → ¬0#1 = 1#1 → 1#32 = zeroExtend 32 1#1

theorem add_constant_equal_with_the_top_bit_of_demandedbits_insertpt_proof : add_constant_equal_with_the_top_bit_of_demandedbits_insertpt_before ⊑ add_constant_equal_with_the_top_bit_of_demandedbits_insertpt_after

theorem test_simplify_decrement_invalid_ne_proof : test_simplify_decrement_invalid_ne_before ⊑ test_simplify_decrement_invalid_ne_after

theorem sub_select_not_sext_proof : sub_select_not_sext_before ⊑ sub_select_not_sext_after

theorem negtest_near_pow2_cmpval_would_overflow_into_signbit_thm (e : IntW 8) :
  icmp IntPred.ult (ashr e (const? 8 2) { «exact» := true }) (const? 8 33) ⊑
    icmp IntPred.sgt e (const? 8 (-1))

theorem e_2092 :
     - 7 * (f ^^^ ( ~~~d &&& (e ||| f))) + 2 * (e ^^^ (d &&& ( ~~~e ||| f))) - 11 *  ~~~(d ^^^ (e &&& f)) + 5 * ( ~~~(d &&&  ~~~e) &&&  ~~~(e ^^^ f)) + 2 * (e |||  ~~~(d |||  ~~~f)) - 3 * ( ~~~(d ||| e) ||| (e ^^^ f)) + 1 * ((d |||  ~~~e) &&& (e ^^^ f)) + 5 * (f ||| (d ^^^ e)) - 7 * ((e &&& f) ^^^  ~~~( ~~~d &&& (e ^^^ f))) - 1 * (e ^^^  ~~~( ~~~d &&& (e &&& f))) + 4 * (e ^^^ (d &&& f)) - 6 *  ~~~( ~~~d &&& ( ~~~e ||| f)) - 3 * ((e &&& f) ||| ( ~~~d &&& (e ||| f))) - 1 *  ~~~( ~~~d &&& (e ||| f)) + 1 * ( ~~~(d ^^^ e) &&&  ~~~(d ^^^ f)) + 4 * ((d ||| e) &&& (e ^^^ f)) + 1 * ( ~~~d ||| (e &&& f)) + 4 * (f ^^^ ( ~~~d ||| (e &&& f))) + 1 * (f &&&  ~~~(d &&&  ~~~e)) - 1 * ((d &&& e) ^^^ (e ||| f)) + 3 * (d ||| ( ~~~e ||| f)) + 7 * ((d &&& f) ^^^  ~~~(d ^^^ ( ~~~e &&& f))) - 3 *  ~~~(e &&& f) + 2 * ( ~~~e ||| (d ^^^ f)) + 3 * (e ^^^  ~~~( ~~~d &&& (e ||| f))) - 7 * (f ^^^ (d ||| (e ||| f))) - 11 * (e ||| (d &&&  ~~~f)) - 2 * (f ^^^  ~~~(d ||| (e &&& f))) + 4 * ((d ^^^ e) &&&  ~~~(d ^^^ f)) - 11 * ((d &&& f) |||  ~~~(e ||| f)) - 1 *  ~~~f - 2 * (e ^^^  ~~~(d &&& (e &&& f))) - 2 * (d ^^^ (e &&& f)) + 2 * (f ^^^  ~~~(d &&&  ~~~e)) + 19 *  ~~~(d ||| (e ||| f)) + 22 *  ~~~(d ||| ( ~~~e ||| f)) + 42 *  ~~~( ~~~d ||| (e ||| f)) + 26 *  ~~~( ~~~d ||| ( ~~~e ||| f)) + 14 * ( ~~~d &&& ( ~~~e &&& f)) - 15 * ( ~~~d &&& (e &&& f)) + 12 * (d &&& ( ~~~e &&& f)) + 34 * (d &&& (e &&& f)) = 5 * ( ~~~f |||  ~~~(d ^^^ e))

theorem select_icmp_x_and_8_ne_0_y_or_8_thm.extracted_1._2 : ∀ (x : BitVec 64) (x_1 : BitVec 32),
  ofBool (x_1 &&& 8#32 == 0#32) = 1#1 →
    ¬(True ∧ (x_1 &&& 8#32 ^^^ 8#32).msb = true) → x ||

theorem mul_add_to_mul_7_proof : mul_add_to_mul_7_before ⊑ mul_add_to_mul_7_after

theorem udiv_i32_multiuse_thm (e e_1 : IntW 8) :
  mul (LLVM.udiv (zext 32 e_1) (zext 32 e)) (add (zext 32 e_1) (zext 32 e)) ⊑
    mul (LLVM.udiv (zext 32 e_1) (zext 32 e)) (add (zext 32 e_1) (zext 32 e) { «nsw» := true, «nuw» := true })
      { «nsw» := true, «nuw» := true }

theorem lsb_mask_sign_sext_thm.extracted_1._1 : ∀ (x : BitVec 32),
  ¬31#32 ≥ ↑32 → (x + -1#32 &&& (x ^^^ -1#32)).sshiftRight' 31#32 = signExtend 32 (ofBool (x == 0#32))

theorem e_1661 :
    7 * ((a ||| b) &&& (b ^^^ c)) + 5 * ( ~~~(a |||  ~~~b) ||| (a ^^^ (b ^^^ c))) + 2 * (c ||| (a &&&  ~~~b)) + 4 * ((a &&&  ~~~b) |||  ~~~(a ^^^ (b ^^^ c))) - 3 * (b ^^^ ( ~~~a ||| (b &&& c))) - 7 *  ~~~(a &&& (b ||| c)) - 1 * ((a &&& b) ^^^  ~~~(a ^^^ ( ~~~b ||| c))) + 1 *  ~~~(a &&&  ~~~a) - 5 *  ~~~(a ^^^ b) + 3 * ( ~~~(a ^^^ b) &&& (a ^^^ c)) - 6 * (c ||| (a ^^^ b)) + 5 * ( ~~~(a &&& b) &&&  ~~~(a ^^^ (b ^^^ c))) - 5 * ((a &&& b) ||| (b ^^^ c)) - 11 * (c &&& (a |||  ~~~b)) - 2 * (b ^^^ (a ||| ( ~~~b &&& c))) + 11 * ((b &&& c) ^^^  ~~~(a &&& (b ^^^ c))) + 11 * (b |||  ~~~(a ||| c)) - 1 * (b ^^^  ~~~( ~~~a ||| ( ~~~b &&& c))) - 17 *  ~~~(a ||| (b ||| c)) - 6 *  ~~~( ~~~a ||| (b ||| c)) - 12 *  ~~~( ~~~a ||| ( ~~~b ||| c)) + 17 * ( ~~~a &&& ( ~~~b &&& c)) - 12 * ( ~~~a &&& (b &&& c)) + 8 * (a &&& (b &&& c)) =  - 6 * (a &&& ( ~~~b &&& c)) + 13 *  ~~~(a ||| ( ~~~b ||| c))

theorem select_2_thm.extracted_1._7 : ∀ (x x_1 : BitVec 8) (x_2 : BitVec 1),
  ¬x_2 = 1#1 → x ^^^ 45#8 ^^^ -1#8 = x ^^^ BitVec.ofInt 8 (-46)

theorem exact_lshr_ne_proof : exact_lshr_ne_before ⊑ exact_lshr_ne_after

lemma bv_to_set_ext : bv_to_set bv₁ = bv_to_set bv₂ ↔ bv₁ = bv₂

theorem uge_sext_thm.extracted_1._1 : ∀ (x : BitVec 8) (x_1 : BitVec 1),
  ofBool (x ≤ᵤ signExtend 8 x_1) = ofBool (x == 0#8) ||

theorem test_sub_nuw_nsw__none_are_safe_thm (e : IntW 32) :
  select (icmp IntPred.eq e (const? 32 1)) (const? 32 2147483647)
      (sub (const? 32 (-2147483648)) e { «nsw» := true, «nuw» := true }) ⊑
    sub (const? 32 (-2147483648)) e

theorem bv_Select_1105 :
    ∀ (e e_1 : LLVM.IntW w), LLVM.select (LLVM.const? 1 0) e_1 e ⊑ e

theorem test30_proof : test30_before ⊑ test30_after

theorem lt_signed_to_small_unsigned_proof : lt_signed_to_small_unsigned_before ⊑ lt_signed_to_small_unsigned_after

theorem main7g_logical_thm.extracted_1._6 : ∀ (x x_1 x_2 x_3 : BitVec 32),
  ¬ofBool (x_3 &&& x_2 == x_3 &&& x_2 &&& x_1) = 1#1 →
    ofBool (x_3 &&& x_2 != x_3 &&& x_2 &&& x_1) = 1#1 → ¬0#1 = 1#1 → 1#32 = zeroExtend 32 1#1

theorem not_ashr_bitwidth_mask_thm (e e_1 : IntW 8) :
  LLVM.and (LLVM.xor (ashr e_1 (const? 8 7)) (const? 8 (-1))) e ⊑
    select (icmp IntPred.slt e_1 (const? 8 0)) (const? 8 0) e

theorem and_not_or_or_not_or_xor_thm (e e_1 e_2 : IntW 32) :
  LLVM.or (LLVM.and (LLVM.xor (LLVM.or e_2 e_1) (const? 32 (-1))) e)
      (LLVM.xor (LLVM.or (LLVM.xor e_2 e_1) e) (const? 32 (-1))) ⊑
    LLVM.xor (LLVM.and (LLVM.or e_2 e_1) (LLVM.or (LLVM.xor e_2 e_1) e)) (const? 32 (-1))

theorem logic_or_logic_and_2_thm (e e_1 e_2 : IntW 1) :
  select (select e_2 (const? 1 1) e_1) (select e_1 (const? 1 1) e) (const? 1 0) ⊑
    select e_1 (const? 1 1) (select e_2 e (const? 1 0))

theorem t2_thm.extracted_1._1 : ∀ (x x_1 : BitVec 8), ¬x ≥ ↑8 → x_1 - BitVec.ofInt 8 (-42) <<< x = 42#8 <<< x + x_1

theorem main7a_logical_thm.extracted_1._10 : ∀ (x x_1 x_2 : BitVec 32),
  ¬ofBool (x_2 &&& x_1 == x_2) = 1#1 → ofBool (x_2 &&& x_1 != x_2) = 1#1 → ¬0#1 = 1#1 → 1#32 = zeroExtend 32 1#1

theorem ashrslt_01_12_exact_proof : ashrslt_01_12_exact_before ⊑ ashrslt_01_12_exact_after

theorem test_invalid_simplify_select_1_thm (e : IntW 8) :
  select (icmp IntPred.eq e (const? 8 0)) (const? 8 1) (sub e (const? 8 1)) ⊑
    select (icmp IntPred.eq e (const? 8 0)) (const? 8 1) (add e (const? 8 (-1)))

theorem shl_and_lshr_comm_proof : shl_and_lshr_comm_before ⊑ shl_and_lshr_comm_after

theorem band_land_left1_thm (e e_1 : IntW 1) : select (LLVM.and e_1 e) e_1 (const? 1 0) ⊑ LLVM.and e_1 e

theorem sext_sub_thm.extracted_1._1 : ∀ (x : BitVec 1) (x_1 : BitVec 8), x_1 - signExtend 8 x = x_1 + zeroExtend 8 x

theorem e_787 :
    4 *  ~~~(z ^^^ t) + 1 *  ~~~t + 6 *  ~~~(z |||  ~~~t) - 1 * (z &&&  ~~~t) - 4 * (z &&& t) = 6 *  ~~~z - 1 *  ~~~(z ||| t)

theorem positive_with_aggressive_icmp_thm (e : IntW 32) :
  LLVM.and (icmp IntPred.ult e (const? 32 128)) (icmp IntPred.ult (add e (const? 32 256)) (const? 32 512)) ⊑
    icmp IntPred.ult e (const? 32 128)

theorem bv_AddSub_1624 :
    ∀ (e e_1 : LLVM.IntW w), LLVM.sub (LLVM.or e e_1) (LLVM.xor e e_1) ⊑ LLVM.and e e_1

theorem not_and_and_or_no_or_commute3_proof : not_and_and_or_no_or_commute3_before ⊑ not_and_and_or_no_or_commute3_after

theorem xor_or_xor_common_op_commute5_thm.extracted_1._1 : ∀ (x x_1 x_2 : BitVec 32),
  (x_2 ||| x_1) ^^^ (x_2 ^^^ x) = x_1 &&& (x_2 ^^^ -1#32) ^^^ x

theorem e_1307 :
     - 6 *  ~~~(z ^^^ t) - 2 *  ~~~(z &&&  ~~~t) - 7 * t - 3 *  ~~~z + 1 * (z |||  ~~~t) + 1 *  ~~~t + 2 * (z ||| t) + 9 *  ~~~(z ||| t) + 12 * (z &&& t) =  - 10 *  ~~~(z |||  ~~~t) + 4 * (z &&&  ~~~t)

theorem test1_thm.extracted_1._1 : ∀ (x : BitVec 32),
  ¬(1#32 ≥ ↑32 ∨
        True ∧ (x.sshiftRight' 1#32 &&& 1431655765#32 ^^^ -1#32).saddOverflow 1#32 = true ∨
          True ∧ x.saddOverflow ((x.sshiftRight' 1#32 &&& 1431655765#32 ^^^ -1#32) + 1#32) = true) →
    1#32 ≥ ↑32 ∨ True ∧ x.ssubOverflow (x >>> 1#32 &&& 1431655765#32) = true → False

theorem zext_sext_ugt_known_nonneg_thm.extracted_1._1 : ∀ (x x_1 : BitVec 8),
  ofBool (signExtend 32 x <ᵤ zeroExtend 32 (x_1 &&& 127#8)) = ofBool (x <ᵤ x_1 &&& 127#8)

theorem xor_or_xor_common_op_commute5_proof : xor_or_xor_common_op_commute5_before ⊑ xor_or_xor_common_op_commute5_after

theorem pr51551_neg2_proof : pr51551_neg2_before ⊑ pr51551_neg2_after

theorem tryFactorization_add_nuw_mul_nuw_mul_nuw_var_proof : tryFactorization_add_nuw_mul_nuw_mul_nuw_var_before ⊑ tryFactorization_add_nuw_mul_nuw_mul_nuw_var_after

theorem xor_or_xor_common_op_commute2_thm (e e_1 e_2 : IntW 32) :
  LLVM.xor (LLVM.xor e_2 e_1) (LLVM.or e_1 e) ⊑ LLVM.xor (LLVM.and e (LLVM.xor e_1 (const? 32 (-1)))) e_2

theorem n14_trunc_of_lshr_thm.extracted_1._1 : ∀ (x x_1 : BitVec 32) (x_2 : BitVec 64),
  ¬(zeroExtend 64 (32#32 - x_1) ≥ ↑64 ∨ x_1 + -1#32 ≥ ↑32) →
    x_1 + -1#32 ≥ ↑32 ∨ True ∧ (32#32 - x_1).msb = true ∨ zeroExtend 64 (32#32 - x_1) ≥ ↑64 → False

theorem negate_select_of_op_vs_negated_op_nsw_xyyx_thm.extracted_1._2 : ∀ (x x_1 : BitVec 8) (x_2 : BitVec 1)
  (x_3 : BitVec 8), ¬x_2 = 1#1 → ¬(True ∧ x.ssubOverflow x_1 = true) → x_3 - (x - x_1) = x_1 - x + x_3

theorem test10_logical_proof : test10_logical_before ⊑ test10_logical_after

theorem same_source_shifted_signbit_thm (e : IntW 32) : sext 32 (trunc 8 (lshr e (const? 32 24))) ⊑ ashr e (const? 32 24)

theorem icmp_ne_and_pow2_minus1_shl_pow2_thm.extracted_1._1 : ∀ (x : BitVec 32),
  ¬x ≥ ↑32 → zeroExtend 32 (ofBool (2#32 <<< x &&& 15#32 != 0#32)) = zeroExtend 32 (ofBool (x <ᵤ 3#32))

theorem test15j_proof : test15j_before ⊑ test15j_after

theorem PR2844_logical_thm.extracted_1._2 : ∀ (x : BitVec 32),
  ofBool (x == 0#32) = 1#1 →
    ¬True → 0#32 = zeroExtend 32 (ofBool (x != 0#32) &&& ofBool (BitVec.ofInt 32 (-638208502) <ₛ x))

theorem ashr_ult_6_proof : ashr_ult_6_before ⊑ ashr_ult_6_after

theorem not_cmp_constant_proof : not_cmp_constant_before ⊑ not_cmp_constant_after

@[simp]
theorem mkUnsatImpliesCircuit_eq_false_iff
    (env : α → Bool)
    (lhs rhs : Circuit α) :
    (mkUnsatImpliesCircuit lhs rhs).eval env = false ↔
    (Circuit.eval lhs env = false → Circuit.eval rhs env = false)

theorem lshrult_03_13_thm.extracted_1._1 : ∀ (x : BitVec 4),
  ¬3#4 ≥ ↑4 → ofBool (x >>> 3#4 <ᵤ BitVec.ofInt 4 (-3)) = 1#1

theorem bor_land_left2_proof : bor_land_left2_before ⊑ bor_land_left2_after

theorem const_sub_sub_const_proof : const_sub_sub_const_before ⊑ const_sub_sub_const_after

theorem is_ascii_alphabetic_proof : is_ascii_alphabetic_before ⊑ is_ascii_alphabetic_after

theorem ashrslt_02_07_proof : ashrslt_02_07_before ⊑ ashrslt_02_07_after

theorem t0_ult_slt_128_proof : t0_ult_slt_128_before ⊑ t0_ult_slt_128_after

theorem lshrugt_02_13_exact_proof : lshrugt_02_13_exact_before ⊑ lshrugt_02_13_exact_after

theorem lshr_and_and_thm (e e_1 : IntW 8) :
  shl (LLVM.and (LLVM.and (lshr e_1 (const? 8 2)) (const? 8 13)) (LLVM.srem e (const? 8 42))) (const? 8 2) ⊑
    LLVM.and (LLVM.and e_1 (const? 8 52)) (shl (LLVM.srem e (const? 8 42)) (const? 8 2))

theorem t0_ult_slt_128_thm.extracted_1._13 : ∀ (x x_1 x_2 : BitVec 32),
  ¬ofBool (x_2 + 16#32 <ᵤ 144#32) = 1#1 →
    ofBool (x_2 <ₛ 128#32) = 1#1 →
      ¬ofBool (127#32 <ₛ x_2) = 1#1 → ¬ofBool (x_2 <ₛ BitVec.ofInt 32 (-16)) = 1#1 → x_1 = x_2

theorem ule_or_min_proof : ule_or_min_before ⊑ ule_or_min_after

theorem test_nuw_nsw_and_signed_pred_proof : test_nuw_nsw_and_signed_pred_before ⊑ test_nuw_nsw_and_signed_pred_after

theorem lshrult_03_04_exact_proof : lshrult_03_04_exact_before ⊑ lshrult_03_04_exact_after

theorem test_ne_11_and_15_add_10_proof : test_ne_11_and_15_add_10_before ⊑ test_ne_11_and_15_add_10_after

theorem not_not_false_thm.extracted_1._1 : ∀ (x : BitVec 1), ¬x ^^^ 1#1 = 1#1 → x = 1#1 → 0#1 = 1#1 ^^^ 1#1

theorem ashrslt_02_10_exact_proof : ashrslt_02_10_exact_before ⊑ ashrslt_02_10_exact_after

theorem test_thm (e : IntW 32) :
  icmp IntPred.ne (lshr (shl e (const? 32 12)) (const? 32 12)) (const? 32 0) ⊑
    icmp IntPred.ne (LLVM.and e (const? 32 1048575)) (const? 32 0)

theorem logical_and_logical_and_icmps_comm1_thm.extracted_1._7 : ∀ (x x_1 x_2 : BitVec 8),
  ¬x_1 ≥ ↑8 →
    ¬(ofBool (x_2 &&& 1#8 <<< x_1 != 0#8) = 1#1 ∧ ofBool (x == 42#8) = 1#1) →
      True ∧ 1#8 <<< x_1 >>> x_1 ≠ 1#8 ∨ x_1 ≥ ↑8 → False

theorem t0_thm.extracted_1._29 : ∀ (x x_1 x_2 x_3 : BitVec 8) (x_4 : BitVec 1),
  ¬x_4 ^^^ 1#1 = 1#1 → x_4 = 1#1 → ofBool (x_3 == x_2) = 1#1 → ofBool (x_3 != x_2) = 1#1 → x_1 = x

theorem positive_trunc_signbit_logical_thm (e : IntW 32) :
  select (icmp IntPred.sgt (trunc 8 e) (const? 8 (-1)))
      (icmp IntPred.ult (add e (const? 32 128)) (const? 32 256)) (const? 1 0) ⊑
    icmp IntPred.ult e (const? 32 128)

theorem masked_icmps_mask_notallzeros_bmask_mixed_negated_swapped_7_proof : masked_icmps_mask_notallzeros_bmask_mixed_negated_swapped_7_before ⊑ masked_icmps_mask_notallzeros_bmask_mixed_negated_swapped_7_after

theorem add_smax_simplify2_proof : add_smax_simplify2_before ⊑ add_smax_simplify2_after

theorem main7c_logical_thm.extracted_1._4 : ∀ (x x_1 : BitVec 32),
  ¬ofBool (x_1 == x_1 &&& x) = 1#1 → ¬ofBool (x_1 != x_1 &&& x) = 1#1 → ¬0#1 = 1#1 → False

theorem ult_or_not_max_commute_logical_thm.extracted_1._1 : ∀ (x : BitVec 8),
  ofBool (x != -1#8) = 1#1 → 1#1 = ofBool (x != -1#8)

theorem select_xor_icmp_bad_6_thm.extracted_1._2 : ∀ (x x_1 : BitVec 32),
  ¬ofBool (x_1 != 1#32) = 1#1 → ofBool (x_1 == 1#32) = 1#1 → x_1 ^^^ x = x ^^^ 1#32

theorem select_1_thm.extracted_1._19 : ∀ (x x_1 : BitVec 8) (x_2 : BitVec 1) (x_3 x_4 : BitVec 8) (x_5 : BitVec 1),
  ¬x_5 = 1#1 → x_2 = 1#1 → x_1 ^^^ -1#8 ^^^ -1#8 = x_1

theorem test6_proof : test6_before ⊑ test6_after

theorem gt_signed_to_large_negative_thm.extracted_1._1 : ∀ (x : BitVec 8),
  ofBool (BitVec.ofInt 32 (-1024) <ₛ signExtend 32 x) = 1#1

theorem icmp_eq_and_pow2_shl_pow2_proof : icmp_eq_and_pow2_shl_pow2_before ⊑ icmp_eq_and_pow2_shl_pow2_after

theorem ashr_C1_add_A_C2_i32_proof : ashr_C1_add_A_C2_i32_before ⊑ ashr_C1_add_A_C2_i32_after

theorem ne_umax2_proof : ne_umax2_before ⊑ ne_umax2_after

theorem test21_proof : test21_before ⊑ test21_after

theorem cv2_thm.extracted_1._1 : ∀ (x x_1 : BitVec 8), ¬x_1 ≥ ↑8 → ofBool ((-1#8) >>> x_1 &&& x ≤ᵤ x) = 1#1

theorem ashrsgt_02_14_exact_thm (e : IntW 4) :
  icmp IntPred.sgt (ashr e (const? 4 2) { «exact» := true }) (const? 4 (-2)) ⊑
    icmp IntPred.ne e (const? 4 (-8))

theorem sle_swap_or_min_commute_thm.extracted_1._1 : ∀ (x x_1 : BitVec 8),
  ofBool (x_1 == BitVec.ofInt 8 (-128)) ||

theorem band_land_right1_thm.extracted_1._1 : ∀ (x x_1 : BitVec 1), x_1 = 1#1 → x_1 &&& x = x

theorem masked_icmps_mask_notallzeros_bmask_mixed_negated_1_logical_proof : masked_icmps_mask_notallzeros_bmask_mixed_negated_1_logical_before ⊑ masked_icmps_mask_notallzeros_bmask_mixed_negated_1_logical_after

theorem test4c_proof : test4c_before ⊑ test4c_after

theorem shl_add_log_may_cause_poison_pr62175_with_nsw_proof : shl_add_log_may_cause_poison_pr62175_with_nsw_before ⊑ shl_add_log_may_cause_poison_pr62175_with_nsw_after

theorem lshrult_01_07_exact_proof : lshrult_01_07_exact_before ⊑ lshrult_01_07_exact_after

theorem eq_21_thm (e e_1 : IntW 32) :
  LLVM.and (icmp IntPred.eq (trunc 8 (lshr e_1 (const? 32 16))) (trunc 8 (lshr e (const? 32 16))))
      (icmp IntPred.eq (trunc 8 (lshr e_1 (const? 32 8))) (trunc 8 (lshr e (const? 32 8)))) ⊑
    icmp IntPred.eq (trunc 16 (lshr e_1 (const? 32 8))) (trunc 16 (lshr e (const? 32 8)))

theorem test1_thm.extracted_1._2 : ∀ (x : BitVec 32),
  ¬(1#32 ≥ ↑32 ∨
        True ∧ (x.sshiftRight' 1#32 &&& 1431655765#32 ^^^ -1#32).saddOverflow 1#32 = true ∨
          True ∧ x.saddOverflow ((x.sshiftRight' 1#32 &&& 1431655765#32 ^^^ -1#32) + 1#32) = true) →
    ¬(1#32 ≥ ↑32 ∨ True ∧ x.ssubOverflow (x >>> 1#32 &&& 1431655765#32) = true) →
      x + ((x.sshiftRight' 1#32 &&& 1431655765#32 ^^^ -1#32) + 1#32) = x - (x >>> 1#32 &&& 1431655765#32)

theorem t1_sub_from_falseval_thm.extracted_1._1 : ∀ (x : BitVec 1) (x_1 : BitVec 8), ¬x = 1#1 → x_1 - x_1 = 0#8

theorem invert_icmp_proof : invert_icmp_before ⊑ invert_icmp_after

theorem e_840 :
    2 * (z |||  ~~~t) + 2 *  ~~~(z &&& t) - 2 *  ~~~(z |||  ~~~t) - 4 * (z &&&  ~~~t) - 7 * (z &&& t) = 9 *  ~~~(z ||| t) - 5 *  ~~~(z ^^^ t)

theorem lshrugt_03_12_exact_thm (e : IntW 4) :
  icmp IntPred.ugt (lshr e (const? 4 3) { «exact» := true }) (const? 4 (-4)) ⊑ const? 1 0

theorem and_or1_commuted_thm.extracted_1._4 : ∀ (x x_1 x_2 : BitVec 1),
  x_2 ||

theorem Tensor2d'.map_functorial (g : β → γ) (f : α → β) (t : Tensor2d' α) :
  t.map (g ∘ f) = (t.map f).map g

theorem ashrsgt_01_15_exact_proof : ashrsgt_01_15_exact_before ⊑ ashrsgt_01_15_exact_after

theorem ult_and_max_thm.extracted_1._1 : ∀ (x x_1 : BitVec 8), ofBool (x_1 <ᵤ x) &&& ofBool (x_1 == -1#8) = 0#1

theorem e_1534 :
     - 7 * (b ^^^ (a &&& (b ^^^ c))) + 7 * (a ^^^ ( ~~~b &&& c)) + 5 * ((a ^^^ b) ||| (a ^^^ c)) - 5 * (b ^^^  ~~~(a |||  ~~~c)) + 1 *  ~~~( ~~~a &&& ( ~~~b &&& c)) + 4 * ( ~~~(a |||  ~~~b) ||| (a ^^^ (b ^^^ c))) - 1 *  ~~~(a ||| (b ||| c)) + 2 *  ~~~(a ||| ( ~~~b ||| c)) - 17 *  ~~~( ~~~a ||| (b ||| c)) - 8 *  ~~~( ~~~a ||| ( ~~~b ||| c)) - 11 * ( ~~~a &&& ( ~~~b &&& c)) - 3 * ( ~~~a &&& (b &&& c)) =  - 1 * (a &&& ( ~~~b &&& c))

theorem and_or_not_not_commute4_proof : and_or_not_not_commute4_before ⊑ and_or_not_not_commute4_after

theorem demorgan_and_apint3_thm (e e_1 : IntW 65) :
  LLVM.and (LLVM.xor e_1 (const? 65 (-1))) (LLVM.xor (const? 65 (-1)) e) ⊑
    LLVM.xor (LLVM.or e_1 e) (const? 65 (-1))

theorem udiv_i32_multiuse_thm.extracted_1._1 : ∀ (x x_1 : BitVec 8),
  ¬zeroExtend 32 x = 0 →
    zeroExtend 32 x = 0 ∨
        True ∧ (zeroExtend 32 x_1).saddOverflow (zeroExtend 32 x) = true ∨
          True ∧ (zeroExtend 32 x_1).uaddOverflow (zeroExtend 32 x) = true ∨
            True ∧ (zeroExtend 32 x_1 / zeroExtend 32 x).smulOverflow (zeroExtend 32 x_1 + zeroExtend 32 x) = true ∨
              True ∧ (zeroExtend 32 x_1 / zeroExtend 32 x).umulOverflow (zeroExtend 32 x_1 + zeroExtend 32 x) = true →
      False

theorem pb_thm (e : IntW 65) :
  icmp IntPred.eq e (ashr (shl e (const? 65 1)) (const? 65 1) { «exact» := true }) ⊑
    icmp IntPred.sgt (add e (const? 65 9223372036854775808)) (const? 65 (-1))

theorem demorgan_nor_use2ac_thm (e e_1 : IntW 8) :
  LLVM.sdiv
      (LLVM.sdiv (LLVM.xor (LLVM.or (LLVM.xor e_1 (const? 8 (-1))) e) (const? 8 (-1)))
        (mul (LLVM.or (LLVM.xor e_1 (const? 8 (-1))) e) (const? 8 23)))
      (mul (LLVM.xor e_1 (const? 8 (-1))) (const? 8 17)) ⊑
    LLVM.sdiv
      (LLVM.sdiv (LLVM.xor (LLVM.or e (LLVM.xor e_1 (const? 8 (-1)))) (const? 8 (-1)))
        (mul (LLVM.or e (LLVM.xor e_1 (const? 8 (-1)))) (const? 8 23)))
      (mul (LLVM.xor e_1 (const? 8 (-1))) (const? 8 17))

theorem ashrslt_02_12_thm (e : IntW 4) : icmp IntPred.slt (ashr e (const? 4 2)) (const? 4 (-4)) ⊑ const? 1 0

theorem t0_ult_slt_65536_proof : t0_ult_slt_65536_before ⊑ t0_ult_slt_65536_after

theorem e_690 :
    1 *  ~~~(x &&&  ~~~x) + 7 * (x ^^^ y) - 5 *  ~~~(x &&&  ~~~y) + 1 * x + 1 *  ~~~x - 1 *  ~~~(x ^^^ y) + 7 * (x ||| y) + 4 *  ~~~(x ||| y) - 11 *  ~~~(x |||  ~~~y) - 3 * (x &&& y) = 16 * (x &&&  ~~~y)

theorem masked_icmps_mask_notallzeros_bmask_mixed_negated_swapped_1_logical_thm (e : IntW 32) :
  select (icmp IntPred.ne (LLVM.and e (const? 32 7)) (const? 32 1)) (const? 1 1)
      (icmp IntPred.eq (LLVM.and e (const? 32 12)) (const? 32 0)) ⊑
    icmp IntPred.ne (LLVM.and e (const? 32 15)) (const? 32 9)

@[simp]
theorem Factor.numVars_term : (Factor.var n).numVars = n + 1

theorem shl_sub_lshr_reverse_no_nsw_proof : shl_sub_lshr_reverse_no_nsw_before ⊑ shl_sub_lshr_reverse_no_nsw_after

theorem and_ne_with_one_bit_diff_constants2_proof : and_ne_with_one_bit_diff_constants2_before ⊑ and_ne_with_one_bit_diff_constants2_after

theorem test3_thm.extracted_1._1 : ∀ (x : BitVec 64), zeroExtend 64 (truncate 8 x) = x &&& 255#64

theorem AvoidCollision_signExtend_not {x : BitVec w} (h : 0 < w) :
    (~~~x).signExtend v = ~~~(x.signExtend v)

theorem test82_thm (e : IntW 64) :
  zext 64 (shl (lshr (trunc 32 e) (const? 32 8)) (const? 32 9)) ⊑
    zext 64 (LLVM.and (shl (trunc 32 e) (const? 32 1)) (const? 32 (-512)))

theorem ult_swap_and_max_commute_proof : ult_swap_and_max_commute_before ⊑ ult_swap_and_max_commute_after

theorem e_2100 :
    2 *  ~~~(d &&& ( ~~~e &&& f)) + 1 * (e ^^^ ( ~~~d ||| (e ^^^ f))) - 2 * (e ^^^  ~~~(d &&& (e ||| f))) - 1 *  ~~~(d |||  ~~~e) - 1 * (d &&& ( ~~~e ||| f)) - 5 *  ~~~(e |||  ~~~f) + 5 * ( ~~~d &&& (e ^^^ f)) + 3 * ((d &&&  ~~~e) ||| (d ^^^ (e ^^^ f))) - 2 * ( ~~~(d |||  ~~~e) |||  ~~~(e ^^^ f)) - 11 * ( ~~~(d |||  ~~~e) ||| (e ^^^ f)) + 7 * (e ||| (d &&& f)) - 2 *  ~~~(d ||| (e ^^^ f)) + 11 * (f ^^^  ~~~(d &&& ( ~~~e &&& f))) + 11 *  ~~~(d &&& ( ~~~e ||| f)) + 7 * (f ^^^  ~~~( ~~~d ||| ( ~~~e &&& f))) - 2 * ( ~~~(d &&&  ~~~e) &&& (e ^^^ f)) - 1 * (e &&&  ~~~f) + 1 * (d ||| (e ||| f)) - 3 * (d ^^^ (e ||| f)) - 6 * (e ^^^ (d &&& (e ||| f))) - 6 * (f ^^^  ~~~(d ||| (e &&& f))) - 1 * (f ^^^ (d &&&  ~~~e)) - 1 *  ~~~( ~~~d ||| (e &&& f)) + 1 *  ~~~( ~~~d &&& (e ||| f)) + 1 * ( ~~~d ||| (e ^^^ f)) + 2 * (d |||  ~~~f) + 5 * d - 3 * (f ^^^  ~~~(d &&& ( ~~~e ||| f))) - 3 *  ~~~(d ^^^ f) - 1 * (f &&& (d |||  ~~~e)) + 5 * ( ~~~f &&&  ~~~(d ^^^ e)) - 11 * ( ~~~d ||| ( ~~~e ||| f)) + 2 * (e |||  ~~~(d ||| f)) + 1 * (e &&&  ~~~(d &&& f)) + 11 * ((d |||  ~~~e) &&&  ~~~(d ^^^ (e ^^^ f))) + 4 * ((d &&& e) ^^^ (e ||| f)) + 5 *  ~~~( ~~~d &&& ( ~~~e ||| f)) - 18 *  ~~~(d ||| (e ||| f)) - 7 *  ~~~(d ||| ( ~~~e ||| f)) - 17 *  ~~~( ~~~d ||| (e ||| f)) - 54 *  ~~~( ~~~d ||| ( ~~~e ||| f)) + 6 * ( ~~~d &&& (e &&& f)) - 13 * (d &&& ( ~~~e &&& f)) =  - 1 * (d ||| (e ^^^ f)) - 1 * ((d ||| e) &&&  ~~~(d ^^^ (e ^^^ f)))

theorem denote_multiRewritePeepholeAt (fuel : ℕ)
  (prs : List (Σ Γ, Σ ty, PeepholeRewrite d Γ ty)) (ix : ℕ) (target : Com d Γ₂ eff t₂) :
    (multiRewritePeepholeAt fuel prs ix target).denote = target.denote

theorem test_imply_not2_thm.extracted_1._6 : ∀ (x : BitVec 1) (x_1 : BitVec 32),
  ¬ofBool (x_1 == 0#32) = 1#1 → ¬ofBool (x_1 != 0#32) = 1#1 → 0#1 ||

theorem e_773 :
     - 3 * (z |||  ~~~t) + 3 *  ~~~z - 11 * z - 3 *  ~~~(z |||  ~~~t) + 14 * (z &&&  ~~~t) =  - 14 * (z &&& t)

theorem and_signbit_select_lshr_proof : and_signbit_select_lshr_before ⊑ and_signbit_select_lshr_after

theorem main12_logical_thm.extracted_1._2 : ∀ (x : BitVec 32),
  ofBool (truncate 16 x <ₛ 0#16) = 1#1 → ofBool (x &&& 32896#32 == 0#32) = 1#1 → ¬True → 2#32 = 1#32

theorem e_643 :
    4 * (x |||  ~~~y) + 1 * (x ||| y) - 1 *  ~~~(x &&&  ~~~y) - 11 *  ~~~(x ^^^ y) + 5 * x + 1 * y + 10 *  ~~~(x ||| y) - 6 *  ~~~(x |||  ~~~y) - 15 * (x &&&  ~~~y) + 3 * (x &&& y) =  - 7 * (x ^^^ y) + 2 *  ~~~(x &&&  ~~~x)

theorem ne_nsw_rem_nz_thm (e : IntW 8) :
  icmp IntPred.ne (mul e (const? 8 5) { «nsw» := true, «nuw» := false }) (const? 8 (-126)) ⊑ const? 1 1

theorem t0_thm (e e_1 e_2 : IntW 8) : sub (sub e_2 e_1) e ⊑ sub e_2 (add e_1 e)

theorem foo_thm.extracted_1._1 : ∀ (x x_1 : BitVec 64),
  zeroExtend 64 (truncate 32 x_1 &&& truncate 32 x) = x_1 &&& x &&& 4294967295#64

theorem e_940 :
     - 6 *  ~~~(z &&& t) - 2 * (z ^^^ t) + 2 * z + 6 *  ~~~(z ||| t) + 6 * (z &&&  ~~~t) - 2 * (z &&& t) =  - 8 *  ~~~(z |||  ~~~t)

theorem bitwise_and_logical_and_masked_icmp_allzeros_poison1_thm.extracted_1._4 : ∀ (x : BitVec 1)
  (x_1 x_2 : BitVec 32),
  ofBool (x_2 &&& x_1 == 0#32) = 1#1 →
    ¬ofBool (x_2 &&& (x_1 ||| 7#32) == 0#32) = 1#1 → x &&& ofBool (x_2 &&& 7#32 == 0#32) = 0#1

theorem zext_nneg_redundant_and_thm.extracted_1._1 : ∀ (x : BitVec 8),
  ¬(True ∧ x.msb = true) → zeroExtend 32 x &&& 127#32 = zeroExtend 32 x

theorem trunc_unsigned_nsw_zext_thm.extracted_1._1 : ∀ (x : BitVec 8) (x_1 : BitVec 32),
  ¬(True ∧ signExtend 32 (truncate 16 x_1) ≠ x_1) →
    ofBool (truncate 16 x_1 <ᵤ zeroExtend 16 x) = ofBool (x_1 <ᵤ zeroExtend 32 x)

theorem land_lor_right2_thm.extracted_1._2 : ∀ (x x_1 : BitVec 1), x_1 = 1#1 → 1#1 = x_1

theorem e_1864 :
    7 * (c &&&  ~~~(a &&& b)) + 3 * (c ^^^  ~~~(a &&& (b ||| c))) - 2 * ((a &&& c) ^^^  ~~~(a ^^^ (b &&& c))) - 1 * ( ~~~(a &&&  ~~~b) &&&  ~~~(a ^^^ (b ^^^ c))) - 11 * ( ~~~(a &&&  ~~~b) &&& (a ^^^ (b ^^^ c))) - 7 * ((a &&& b) |||  ~~~(b ||| c)) + 7 * ( ~~~(a |||  ~~~b) ||| (a ^^^ (b ^^^ c))) + 3 * (a &&&  ~~~c) + 3 *  ~~~(b &&& c) - 3 *  ~~~c + 4 * ( ~~~c &&& (a ^^^ b)) - 6 * (b ^^^ (a &&& (b ||| c))) + 5 * (b ^^^ ( ~~~a ||| ( ~~~b &&& c))) - 11 * ((a &&&  ~~~b) |||  ~~~(a ^^^ (b ^^^ c))) - 2 * (c ^^^ ( ~~~a ||| (b &&& c))) + 1 *  ~~~( ~~~a &&& (b ^^^ c)) + 2 * (b |||  ~~~(a ||| c)) - 7 * ((a &&& c) ^^^  ~~~(b &&&  ~~~c)) - 1 * ((a |||  ~~~b) &&& (a ^^^ (b ^^^ c))) - 1 * (b ||| c) - 6 * (a &&&  ~~~b) - 3 *  ~~~(a ||| ( ~~~b &&& c)) + 1 *  ~~~( ~~~a ||| (b ^^^ c)) - 11 * ((a &&& b) ^^^ (a ^^^ (b &&& c))) + 1 * (b ^^^ (a ||| ( ~~~b &&& c))) - 11 * (b ^^^ (a &&& (b ^^^ c))) - 5 * ( ~~~a &&& (b ^^^ c)) - 6 * (b ^^^  ~~~(a |||  ~~~c)) + 5 * ((b &&&  ~~~c) |||  ~~~( ~~~a ||| ( ~~~b &&& c))) + 7 *  ~~~(a &&& (b ||| c)) - 7 * (c &&&  ~~~(a ^^^ b)) - 1 * (c ^^^  ~~~(a &&& b)) + 4 * (b ^^^ (a ||| ( ~~~b ||| c))) + 11 * (b ^^^  ~~~( ~~~a &&& (b &&& c))) - 1 * ((b &&& c) ||| ( ~~~a &&& (b ||| c))) + 1 * ( ~~~(a &&& b) &&& (b ^^^ c)) - 1 * ( ~~~(a ||| b) ||| (b ^^^ c)) - 2 *  ~~~(a ||| (b &&& c)) + 5 * ( ~~~b &&&  ~~~(a ^^^ c)) + 1 *  ~~~(a ||| (b ||| c)) + 27 *  ~~~(a ||| ( ~~~b ||| c)) - 1 *  ~~~( ~~~a ||| (b ||| c)) + 20 *  ~~~( ~~~a ||| ( ~~~b ||| c)) + 18 * ( ~~~a &&& (b &&& c)) + 10 * (a &&& ( ~~~b &&& c)) + 40 * (a &&& (b &&& c)) = 7 * (b &&& (a |||  ~~~c)) + 2 *  ~~~(a &&& c)

theorem trunc_shl_ashr_infloop_thm (e : IntW 64) :
  trunc 32 (shl (ashr e (const? 64 3)) (const? 64 2)) ⊑
    LLVM.and (trunc 32 (lshr e (const? 64 1))) (const? 32 (-4))

theorem zext_or_masked_bit_test_thm (e e_1 e_2 : IntW 32) :
  zext 32
      (LLVM.or (icmp IntPred.ne (LLVM.and (shl (const? 32 1) e_2) e_1) (const? 32 0))
        (icmp IntPred.eq e e_2)) ⊑
    zext 32
      (LLVM.or
        (icmp IntPred.ne (LLVM.and (shl (const? 32 1) e_2 { «nsw» := false, «nuw» := true }) e_1) (const? 32 0))
        (icmp IntPred.eq e e_2))

theorem no_reassoc_add_none_nuw_thm (e : IntW 32) :
  add (add e (const? 32 4) { «nsw» := false, «nuw» := true }) (const? 32 64) ⊑ add e (const? 32 68)

theorem test4_apint_proof : test4_apint_before ⊑ test4_apint_after

theorem PR60818_ne_proof : PR60818_ne_before ⊑ PR60818_ne_after

theorem lshrult_01_09_proof : lshrult_01_09_before ⊑ lshrult_01_09_after

theorem test_srem_canonicalize_op0_thm (e e_1 : IntW 32) :
  LLVM.srem (sub (const? 32 0) e_1 { «nsw» := true, «nuw» := false }) e ⊑
    sub (const? 32 0) (LLVM.srem e_1 e) { «nsw» := true, «nuw» := false }

theorem ne_smax2_thm.extracted_1._2 : ∀ (x x_1 : BitVec 32),
  ¬ofBool (x <ₛ x_1) = 1#1 → ofBool (x != x) = ofBool (x <ₛ x_1)

theorem substitute_constant_and_eq_eq_commute_proof : substitute_constant_and_eq_eq_commute_before ⊑ substitute_constant_and_eq_eq_commute_after

theorem select_icmp_ne_0_and_1073741824_or_8_thm.extracted_1._1 : ∀ (x : BitVec 8) (x_1 : BitVec 32),
  ofBool (0#32 != x_1 &&& 1073741824#32) = 1#1 → ofBool (x_1 &&& 1073741824#32 == 0#32) = 1#1 → x = x ||

theorem sdiv_i1_is_op0_thm (e e_1 : IntW 1) : LLVM.sdiv e_1 e ⊑ e_1

theorem lor_land_right2_thm.extracted_1._1 : ∀ (x : BitVec 1), ¬x = 1#1 → 0#1 = x

theorem not_or_or_and_no_and_commute1_proof : not_or_or_and_no_and_commute1_before ⊑ not_or_or_and_no_and_commute1_after

theorem masked_icmps_mask_notallzeros_bmask_mixed_negated_0_logical_thm.extracted_1._2 : ∀ (x : BitVec 32),
  ¬ofBool (x &&& 12#32 == 0#32) = 1#1 →
    ofBool (x &&& 3#32 != 1#32) = ofBool (x &&& 12#32 == 0#32) ||

theorem t5_ugt_slt_0_thm.extracted_1._10 : ∀ (x x_1 x_2 : BitVec 32),
  ¬ofBool (65535#32 <ᵤ x_2) = 1#1 → ofBool (65535#32 <ₛ x_2) = 1#1 → x_2 = x

theorem flip_add_of_shift_neg_proof : flip_add_of_shift_neg_before ⊑ flip_add_of_shift_neg_after

theorem lshr_and_and_proof : lshr_and_and_before ⊑ lshr_and_and_after

theorem logical_and_logical_and_icmps_comm2_proof : logical_and_logical_and_icmps_comm2_before ⊑ logical_and_logical_and_icmps_comm2_after

theorem e_820 :
    5 * z + 1 *  ~~~(z &&&  ~~~z) + 5 *  ~~~t - 1 *  ~~~(z ||| t) - 5 * (z &&&  ~~~t) = 5 * (z |||  ~~~t) + 1 * (z ||| t)

theorem test_ashr__exact_is_safe_thm.extracted_1._1 : ∀ (x : BitVec 64) (x_1 : BitVec 32),
  ofBool (x_1 &&& BitVec.ofInt 32 (-2147483588) == 0#32) = 1#1 →
    2#32 ≥ ↑32 ∨
        True ∧ (x_1.sshiftRight' 2#32 &&& BitVec.ofInt 32 (-536870897)).msb = true ∨
          zeroExtend 64 (x_1.sshiftRight' 2#32 &&& BitVec.ofInt 32 (-536870897)) ≥ ↑64 →
      False

theorem select_of_symmetric_selects_negative1_thm.extracted_1._1 : ∀ (x : BitVec 32) (x_1 : BitVec 1),
  ¬(x_1 = 1#1 ∨ x_1 = 1#1) → x_1 = 1#1 → False

theorem sext_negate_proof : sext_negate_before ⊑ sext_negate_after

theorem test_negative_nsw_and_unsigned_pred_proof : test_negative_nsw_and_unsigned_pred_before ⊑ test_negative_nsw_and_unsigned_pred_after

theorem select_icmp_eq_0_and_1_xor_1_thm.extracted_1._1 : ∀ (x : BitVec 32) (x_1 : BitVec 64),
  ofBool (x_1 &&& 1#64 == 0#64) = 1#1 → x = x ^^^ truncate 32 x_1 &&& 1#32

theorem e_386 :
    2 *  ~~~(x &&& y) + 4 * (x ^^^ y) + 2 * (x |||  ~~~y) - 11 *  ~~~y - 1 *  ~~~(x &&&  ~~~y) + 8 *  ~~~(x ||| y) - 16 *  ~~~(x |||  ~~~y) - 12 * (x &&& y) =  - 3 * (x &&&  ~~~y) - 11 * y

theorem eq_basic_thm.extracted_1._1 : ∀ (x x_1 : BitVec 8),
  ofBool (x_1 == 0#8) ||

theorem main12_thm.extracted_1._1 : ∀ (x : BitVec 32),
  ofBool (truncate 16 x <ₛ 0#16) ||

theorem eq_21_comm_eq2_thm.extracted_1._1 : ∀ (x x_1 : BitVec 32),
  ¬(16#32 ≥ ↑32 ∨ 16#32 ≥ ↑32 ∨ 8#32 ≥ ↑32 ∨ 8#32 ≥ ↑32) → 8#32 ≥ ↑32 ∨ 8#32 ≥ ↑32 → False

theorem lshrugt_02_09_proof : lshrugt_02_09_before ⊑ lshrugt_02_09_after

theorem append_valid {Γ₁ Γ₂ Γ₃  : Ctxt Ty} {d₁ d₂ : Nat} :
  Diff.Valid Γ₁ Γ₂ d₁ →  Diff.Valid Γ₂ Γ₃ d₂ → Diff.Valid Γ₁ Γ₃ (d₁ + d₂)

theorem scalar_i32_signbit_lshr_and_slt_thm (e e_1 : IntW 32) :
  icmp IntPred.slt (LLVM.and (lshr (const? 32 (-2147483648)) e_1) e) (const? 32 0) ⊑
    icmp IntPred.slt (LLVM.and (lshr (const? 32 (-2147483648)) e_1 { «exact» := true }) e) (const? 32 0)

theorem lshr_pow2_ugt1_thm.extracted_1._1 : ∀ (x : BitVec 8),
  ¬x ≥ ↑8 → ofBool (1#8 <ᵤ BitVec.ofInt 8 (-128) >>> x) = ofBool (x <ᵤ 7#8)

theorem sdiv_icmp1_thm (e : IntW 64) :
  icmp IntPred.eq (LLVM.sdiv e (const? 64 5) { «exact» := true }) (const? 64 0) ⊑
    icmp IntPred.eq e (const? 64 0)

theorem scalar_i32_lshr_and_negC_slt_thm.extracted_1._1 : ∀ (x x_1 : BitVec 32),
  ¬x ≥ ↑32 → ofBool (x_1 >>> x &&& BitVec.ofInt 32 (-8) <ₛ 0#32) = ofBool (x_1 >>> x <ₛ 0#32)

theorem eq_21_comm_and_proof : eq_21_comm_and_before ⊑ eq_21_comm_and_after

theorem test15_thm.extracted_1._1 : ∀ (x x_1 : BitVec 32),
  x_1 &&& (x ^^^ -1#32) ^^^ (x_1 ^^^ -1#32) &&& x = x_1 ^^^ x

theorem allOnes_sub_eq_xor (x :BitVec w) : (allOnes w) - x = x ^^^ (allOnes w)

theorem different_size_zext_zext_sgt_thm (e : IntW 4) (e_1 : IntW 7) :
  icmp IntPred.sgt (zext 25 e_1) (zext 25 e) ⊑ icmp IntPred.ugt e_1 (zext 7 e)

theorem ashrslt_03_06_proof : ashrslt_03_06_before ⊑ ashrslt_03_06_after

theorem ashrsgt_01_04_exact_thm.extracted_1._1 : ∀ (x : BitVec 4),
  ¬(True ∧ x >>> 1#4 <<< 1#4 ≠ x ∨ 1#4 ≥ ↑4) → ofBool (4#4 <ₛ x.sshiftRight' 1#4) = 0#1

theorem e_1086 :
     - 6 *  ~~~(z ^^^ t) - 11 *  ~~~z - 6 * t + 7 *  ~~~(z &&&  ~~~z) - 1 * (z |||  ~~~t) + 11 *  ~~~(z ||| t) + 10 *  ~~~(z |||  ~~~t) - 6 * (z &&&  ~~~t) =  - 6 * (z &&& t)

theorem test2_thm.extracted_1._1 : ∀ (x x_1 : BitVec 32),
  ofBool (x_1 ^^^ x == 0#32) ^^^ ofBool (x_1 ^^^ x == 32#32) = ofBool (x_1 == x) ^^^ ofBool (x_1 ^^^ x == 32#32)

theorem test1_proof : test1_before ⊑ test1_after

theorem e_17 :
     - 11 *  ~~~(x &&& y) + 14 *  ~~~(x ||| y) + 9 *  ~~~(x |||  ~~~y) + 16 * (x &&&  ~~~y) =  - 2 *  ~~~x + 5 *  ~~~y

theorem select_xor_icmp2_thm.extracted_1._6 : ∀ (x x_1 x_2 : BitVec 32),
  ¬ofBool (x_2 != 0#32) = 1#1 → ¬ofBool (x_2 == 0#32) = 1#1 → x_2 ^^^ x = x_1

theorem test28_thm (e : IntW 32) :
  icmp IntPred.eq (LLVM.srem e (const? 32 (-2147483648))) (const? 32 0) ⊑
    icmp IntPred.eq (LLVM.and e (const? 32 2147483647)) (const? 32 0)

theorem nonesUntilSome_spec (x : Stream α) (not_stuck : x ≠ stuck α) :
    (dropLeadingNones x not_stuck).head.isSome
    ∧ ∀ j < nonesUntilSome x not_stuck, x.get j = none

theorem t0_thm.extracted_1._20 : ∀ (x x_1 : BitVec 8) (x_2 : BitVec 1),
  x_2 ^^^ 1#1 = 1#1 → ¬x_2 = 1#1 → ¬True → 0#1 = 1#1 → x_1 = x

theorem not_xor_eq_and_sub_or_sub_one :
    ~~~ (x ^^^ y) = (x &&& y) - (x ||| y) - 1

theorem t1_const_shl_lshr_ne_thm.extracted_1._2 : ∀ (x x_1 : BitVec 32),
  ¬(1#32 ≥ ↑32 ∨ 1#32 ≥ ↑32) →
    ¬2#32 ≥ ↑32 → ofBool (x_1 >>> 1#32 &&& x <<< 1#32 != 0#32) = ofBool (x_1 >>> 2#32 &&& x != 0#32)

theorem main4e_like_logical_thm.extracted_1._7 : ∀ (x x_1 x_2 : BitVec 32),
  ofBool (x_2 &&& x_1 == x_1) = 1#1 →
    ¬ofBool (x_2 &&& x_1 != x_1) = 1#1 →
      ofBool (x_2 &&& x == x) = 1#1 → 0#32 = zeroExtend 32 (ofBool (x_2 &&& x != x))

theorem e_2175 :
     - 3 * ( ~~~(d ^^^ e) &&&  ~~~(d ^^^ f)) + 7 * (d ||| ( ~~~e &&& f)) + 2 * ((d &&& e) |||  ~~~(e |||  ~~~f)) + 1 *  ~~~(d &&& f) + 3 * (e ^^^ ( ~~~d ||| (e &&& f))) - 3 * (e ^^^  ~~~(d ||| (e &&& f))) - 7 * ( ~~~(d &&& e) &&& (e ^^^ f)) + 1 * ((d &&& f) ^^^  ~~~(d ^^^ (e &&& f))) - 7 * (e |||  ~~~f) + 11 *  ~~~(d ||| ( ~~~e &&& f)) - 1 * (d ||| (e &&& f)) - 3 * ( ~~~(d ||| e) ||| (e ^^^ f)) + 1 * ((e &&&  ~~~f) ^^^ (d ||| (e ^^^ f))) - 5 * (e ^^^  ~~~( ~~~d ||| (e &&& f))) + 1 * (f ^^^ ( ~~~d ||| ( ~~~e ||| f))) - 3 * (f ^^^  ~~~( ~~~d ||| ( ~~~e &&& f))) + 7 * ((e &&&  ~~~f) |||  ~~~(d ||| ( ~~~e &&& f))) - 11 * (e ||| (d &&&  ~~~f)) + 5 * ((d ||| e) &&& (e ^^^ f)) + 3 *  ~~~( ~~~d ||| (e &&& f)) + 1 * (e |||  ~~~(d |||  ~~~f)) + 1 * ( ~~~e |||  ~~~(d ^^^ f)) - 2 * (e ^^^ f) - 3 *  ~~~(d ^^^ ( ~~~e ||| f)) - 1 * (f ^^^ (d ||| (e ||| f))) + 2 * (e ^^^ (d &&& ( ~~~e ||| f))) + 3 * (e &&& (d |||  ~~~f)) + 2 * (f ^^^ ( ~~~d ||| ( ~~~e &&& f))) - 6 * ((d &&& e) ^^^  ~~~(d ^^^ ( ~~~e ||| f))) - 2 *  ~~~(d ||| (e &&& f)) + 2 * ((d |||  ~~~e) &&&  ~~~(e ^^^ f)) - 7 * (f ^^^  ~~~(d &&& (e &&& f))) - 2 * (e |||  ~~~(d ^^^ f)) - 1 * ((d &&& f) ^^^ (e ||| f)) + 1 * (e ^^^ ( ~~~d ||| ( ~~~e &&& f))) + 11 *  ~~~(e |||  ~~~f) - 5 * ( ~~~(d |||  ~~~e) ||| (e ^^^ f)) - 2 * (e ^^^  ~~~( ~~~d ||| ( ~~~e &&& f))) + 5 * (e ^^^ ( ~~~d &&& (e ^^^ f))) - 2 * (e ^^^ ( ~~~d &&& ( ~~~e ||| f))) + 11 * (f ^^^  ~~~(d &&& (e ||| f))) + 4 * ( ~~~d ||| (e ^^^ f)) - 5 *  ~~~(d ||| (e ||| f)) + 16 *  ~~~(d ||| ( ~~~e ||| f)) + 17 *  ~~~( ~~~d ||| (e ||| f)) + 21 *  ~~~( ~~~d ||| ( ~~~e ||| f)) - 10 * ( ~~~d &&& ( ~~~e &&& f)) + 20 * ( ~~~d &&& (e &&& f)) - 1 * (d &&& ( ~~~e &&& f)) + 19 * (d &&& (e &&& f)) = 11 * ((d &&& e) |||  ~~~(d ^^^ (e ^^^ f)))

theorem icmp_select_implied_cond_relational_thm.extracted_1._2 : ∀ (x x_1 : BitVec 8),
  ofBool (10#8 <ᵤ x_1) = 1#1 → ofBool (10#8 <ᵤ x_1) = 1#1

theorem e_581 :
     - 3 * (x ||| y) - 6 * y + 11 *  ~~~(x &&&  ~~~x) - 1 * (x ^^^ y) + 4 *  ~~~x - 1 *  ~~~(x &&& y) + 1 * (x |||  ~~~y) - 4 *  ~~~(x |||  ~~~y) - 3 * (x &&& y) = 8 *  ~~~(x ||| y) + 7 *  ~~~y

theorem ule_and_min_commute_proof : ule_and_min_commute_before ⊑ ule_and_min_commute_after

theorem lshrugt_01_01_exact_thm (e : IntW 4) :
  icmp IntPred.ugt (lshr e (const? 4 1) { «exact» := true }) (const? 4 1) ⊑
    icmp IntPred.ugt e (const? 4 2)

theorem p0_thm (e e_1 : IntW 8) :
  icmp IntPred.ne (LLVM.and (LLVM.xor (shl (const? 8 (-1)) e_1) (const? 8 (-1))) e) e ⊑
    icmp IntPred.ne (lshr e e_1) (const? 8 0)

theorem smear_set_bit_different_dest_type_wider_dst_proof : smear_set_bit_different_dest_type_wider_dst_before ⊑ smear_set_bit_different_dest_type_wider_dst_after

theorem sub_ashr_and_i32_nuw_nsw_thm.extracted_1._1 : ∀ (x x_1 : BitVec 32),
  ¬(True ∧ x_1.ssubOverflow x = true ∨ True ∧ x_1.usubOverflow x = true ∨ 31#32 ≥ ↑32) →
    ofBool (x_1 <ₛ x) = 1#1 → (x_1 - x).sshiftRight' 31#32 &&& x = x

theorem t7_ugt_sgt_neg1_thm.extracted_1._15 : ∀ (x x_1 x_2 : BitVec 32),
  ¬ofBool (65535#32 <ᵤ x_2) = 1#1 → ¬ofBool (65535#32 <ₛ x_2) = 1#1 → ofBool (x_2 <ₛ 0#32) = 1#1 → x_2 = x

theorem not_and_and_or_no_or_commute2_and_proof : not_and_and_or_no_or_commute2_and_before ⊑ not_and_and_or_no_or_commute2_and_after

theorem negative2_thm.extracted_1._1 : ∀ (x x_1 : BitVec 32),
  ofBool (x_1 <ₛ x) &&& ofBool (0#32 ≤ₛ x_1) = ofBool (x_1 <ₛ x) &&& ofBool (-1#32 <ₛ x_1)

theorem ne_smax1_proof : ne_smax1_before ⊑ ne_smax1_after

theorem main7e_logical_thm.extracted_1._9 : ∀ (x x_1 x_2 x_3 x_4 : BitVec 32),
  ofBool (x_4 &&& x_3 &&& x_2 == x_4 &&& x_3) = 1#1 →
    ofBool (x_4 &&& x_3 &&& x_2 != x_4 &&& x_3) = 1#1 →
      ofBool (x_1 &&& x &&& x_2 == x_1 &&& x) = 1#1 → 0#32 = zeroExtend 32 1#1

theorem test_negative_nuw_and_signed_pred_proof : test_negative_nuw_and_signed_pred_before ⊑ test_negative_nuw_and_signed_pred_after

theorem masked_icmps_mask_notallzeros_bmask_mixed_negated_swapped_7_thm (e : IntW 32) :
  LLVM.or (icmp IntPred.ne (LLVM.and e (const? 32 15)) (const? 32 8))
      (icmp IntPred.eq (LLVM.and e (const? 32 7)) (const? 32 0)) ⊑
    const? 1 1

theorem p0_thm.extracted_1._1 : ∀ (x : BitVec 8), ofBool (x &&& 3#8 == x) = ofBool (x <ᵤ 4#8)

theorem main7b_logical_thm.extracted_1._12 : ∀ (x x_1 x_2 : BitVec 32),
  ¬ofBool (x_2 == x_1 &&& x_2) = 1#1 →
    ¬ofBool (x_2 != x_1 &&& x_2) = 1#1 → ¬0#1 = 1#1 → 1#32 = zeroExtend 32 (ofBool (x != x_1 &&& x))

theorem test2_thm (e e_1 : IntW 39) :
  LLVM.or
      (LLVM.and (add e_1 (LLVM.and e (const? 39 (-274877906944)))) (LLVM.xor (const? 39 274877906943) (const? 39 (-1))))
      (LLVM.and e_1 (const? 39 274877906943)) ⊑
    add e_1 (LLVM.and e (const? 39 (-274877906944)))

theorem lshr_add_or_fail_thm (e e_1 : IntW 8) :
  LLVM.or (lshr e_1 (const? 8 1)) (add (lshr e (const? 8 1)) (const? 8 123)) ⊑
    LLVM.or (lshr e_1 (const? 8 1))
      (add (lshr e (const? 8 1)) (const? 8 123) { «nsw» := false, «nuw» := true })

theorem shl_shl_constants_div_proof : shl_shl_constants_div_before ⊑ shl_shl_constants_div_after

theorem scalar_i8_shl_and_negC_eq_proof : scalar_i8_shl_and_negC_eq_before ⊑ scalar_i8_shl_and_negC_eq_after

theorem xor_signbit_shl_proof : xor_signbit_shl_before ⊑ xor_signbit_shl_after

theorem bitwise_or_logical_or_icmps_comm3_thm (e e_1 e_2 : IntW 8) :
  LLVM.or (icmp IntPred.eq (LLVM.and e_2 (shl (const? 8 1) e_1)) (const? 8 0))
      (select (icmp IntPred.eq (LLVM.and e_2 (const? 8 1)) (const? 8 0)) (const? 1 1)
        (icmp IntPred.eq e (const? 8 42))) ⊑
    select
      (icmp IntPred.ne
        (LLVM.and e_2 (LLVM.or (shl (const? 8 1) e_1 { «nsw» := false, «nuw» := true }) (const? 8 1)))
        (LLVM.or (shl (const? 8 1) e_1 { «nsw» := false, «nuw» := true }) (const? 8 1)))
      (const? 1 1) (icmp IntPred.eq e (const? 8 42))

theorem icmp_eq_and_pow2_minus1_shl1_thm.extracted_1._1 : ∀ (x : BitVec 32),
  ¬x ≥ ↑32 → zeroExtend 32 (ofBool (1#32 <<< x &&& 15#32 == 0#32)) = zeroExtend 32 (ofBool (3#32 <ᵤ x))

theorem e_844 :
     - 1 * t - 1 *  ~~~(z ||| t) + 3 *  ~~~(z |||  ~~~t) + 1 * (z &&&  ~~~t) + 1 * (z &&& t) = 2 * (z ^^^ t) - 1 *  ~~~t

theorem shl_bad_sub_i64_thm.extracted_1._1 : ∀ (x : BitVec 64),
  ¬67#64 - x ≥ ↑64 → True ∧ 1#64 <<< (67#64 - x) >>> (67#64 - x) ≠ 1#64 ∨ 67#64 - x ≥ ↑64 → False

theorem test_shl__nsw_is_safe_proof : test_shl__nsw_is_safe_before ⊑ test_shl__nsw_is_safe_after

theorem or_signbit_shl_thm.extracted_1._1 : ∀ (x : BitVec 32),
  ¬8#32 ≥ ↑32 → (x ||| BitVec.ofInt 32 (-65536)) <<< 8#32 = x <<< 8#32 ||

theorem main5c_like_logical_thm.extracted_1._10 : ∀ (x x_1 : BitVec 32),
  ¬ofBool (x_1 &&& 7#32 != 7#32) = 1#1 →
    ofBool (x_1 &&& 7#32 == 7#32) = 1#1 →
      ¬ofBool (x &&& 7#32 != 7#32) = 1#1 → 1#32 = zeroExtend 32 (ofBool (x &&& 7#32 == 7#32))

theorem ashrslt_03_09_exact_thm (e : IntW 4) :
  icmp IntPred.slt (ashr e (const? 4 3) { «exact» := true }) (const? 4 (-7)) ⊑ const? 1 0

theorem e_837 :
     - 6 * (z ||| t) - 6 *  ~~~z + 3 *  ~~~(z ||| t) + 12 *  ~~~(z |||  ~~~t) + 3 * (z &&&  ~~~t) =  - 3 *  ~~~t - 6 * (z &&& t)

theorem not_and_and_or_no_or_commute1_and_proof : not_and_and_or_no_or_commute1_and_before ⊑ not_and_and_or_no_or_commute1_and_after

theorem test43_thm (e e_1 e_2 : IntW 32) :
  LLVM.and (LLVM.or e_2 (mul e_1 e)) (LLVM.xor (LLVM.xor e_2 (const? 32 (-1))) (mul e_1 e)) ⊑
    LLVM.and (mul e_1 e) e_2

theorem shl_nsw_add_nuw_thm.extracted_1._2 : ∀ (x : BitVec 32),
  ¬(True ∧ x.uaddOverflow 1#32 = true ∨
        True ∧ ((-1#32) <<< (x + 1#32)).sshiftRight' (x + 1#32) ≠ -1#32 ∨ x + 1#32 ≥ ↑32) →
    ¬(True ∧ (BitVec.ofInt 32 (-2) <<< x).sshiftRight' x ≠ BitVec.ofInt 32 (-2) ∨ x ≥ ↑32) →
      (-1#32) <<< (x + 1#32) = BitVec.ofInt 32 (-2) <<< x

theorem logical_or_logical_or_icmps_comm1_thm.extracted_1._5 : ∀ (x x_1 x_2 : BitVec 8),
  ¬x_1 ≥ ↑8 →
    ¬(ofBool (x_2 &&& 1#8 <<< x_1 == 0#8) = 1#1 ∨ ofBool (x == 42#8) = 1#1) →
      ¬(True ∧ 1#8 <<< x_1 >>> x_1 ≠ 1#8 ∨ x_1 ≥ ↑8) →
        ofBool (x_2 &&& 1#8 <<< x_1 == 0#8) = 1#1 → True → ofBool (x_2 &&& 1#8 == 0#8) = 1#1

theorem main7e_logical_thm.extracted_1._5 : ∀ (x x_1 x_2 x_3 : BitVec 32),
  ¬ofBool (x_3 &&& x_2 &&& x_1 == x_3 &&& x_2) = 1#1 →
    ofBool (x_3 &&& x_2 &&& x_1 != x_3 &&& x_2) = 1#1 → 0#1 = 1#1 → 0#32 = zeroExtend 32 1#1

theorem abs_diff_signed_slt_swap_wrong_pred1_proof : abs_diff_signed_slt_swap_wrong_pred1_before ⊑ abs_diff_signed_slt_swap_wrong_pred1_after

theorem test_implied_true_proof : test_implied_true_before ⊑ test_implied_true_after

theorem ashr_sle_noexact_thm.extracted_1._1 : ∀ (x : BitVec 8),
  ¬3#8 ≥ ↑8 → ofBool (x.sshiftRight' 3#8 ≤ₛ 10#8) = ofBool (x <ₛ 88#8)

theorem multiuse_add_proof : multiuse_add_before ⊑ multiuse_add_after

theorem n10_lshr_ashr_proof : n10_lshr_ashr_before ⊑ n10_lshr_ashr_after

theorem sgt_smin3_thm (e e_1 : IntW 32) :
  icmp IntPred.slt (add e_1 (const? 32 3))
      (select (icmp IntPred.slt (add e_1 (const? 32 3)) e) (add e_1 (const? 32 3)) e) ⊑
    const? 1 0

theorem main13_logical_proof : main13_logical_before ⊑ main13_logical_after

theorem and_zext_eq_even_commuted_thm.extracted_1._1 : ∀ (x : BitVec 32),
  zeroExtend 32 (ofBool (x == 2#32)) &&& x = 0#32

theorem trunc_shl_lshr_infloop_thm (e : IntW 64) :
  trunc 32 (shl (lshr e (const? 64 1)) (const? 64 2)) ⊑
    LLVM.and (shl (trunc 32 e) (const? 32 1)) (const? 32 (-4))

theorem src_fv_ne_thm.extracted_1._3 : ∀ (x x_1 : BitVec 8) (x_2 : BitVec 1),
  ¬x_2 = 1#1 → ofBool (0#8 ||| x != 0#8) = ofBool (x != 0#8) ||

theorem lor_lor_left1_proof : lor_lor_left1_before ⊑ lor_lor_left1_after

theorem ashr_ugt_14_proof : ashr_ugt_14_before ⊑ ashr_ugt_14_after

theorem icmp_slt_0_or_icmp_sgt_0_i64_fail0_proof : icmp_slt_0_or_icmp_sgt_0_i64_fail0_before ⊑ icmp_slt_0_or_icmp_sgt_0_i64_fail0_after

@[simp] theorem ofBitVec_or {w : Nat} {x y : BitVec w} : ofBitVecSext (x ||| y) = (ofBitVecSext x) ||

theorem test4_proof : test4_before ⊑ test4_after

theorem ashr_1_thm (e e_1 e_2 : IntW 8) (e_3 : IntW 1) :
  LLVM.xor (ashr (select e_3 (LLVM.xor e_2 (const? 8 (-1))) (LLVM.xor e_1 (const? 8 123))) e) (const? 8 (-1)) ⊑
    ashr (select e_3 e_2 (LLVM.xor e_1 (const? 8 (-124)))) e

theorem signed_sign_bit_extract_proof : signed_sign_bit_extract_before ⊑ signed_sign_bit_extract_after

theorem test4_proof : test4_before ⊑ test4_after

theorem select_icmp_ne_0_and_4096_and_not_4096_proof : select_icmp_ne_0_and_4096_and_not_4096_before ⊑ select_icmp_ne_0_and_4096_and_not_4096_after

theorem test2_proof : test2_before ⊑ test2_after

theorem logical_or_logical_or_icmps_comm1_thm.extracted_1._3 : ∀ (x x_1 x_2 : BitVec 8),
  ¬x_1 ≥ ↑8 →
    ofBool (x_2 &&& 1#8 <<< x_1 == 0#8) = 1#1 ∨ ofBool (x == 42#8) = 1#1 →
      ¬(True ∧ 1#8 <<< x_1 >>> x_1 ≠ 1#8 ∨ x_1 ≥ ↑8) →
        ¬ofBool (x_2 &&& 1#8 <<< x_1 == 0#8) = 1#1 → ¬ofBool (x == 42#8) = 1#1 → 1#1 = ofBool (x_2 &&& 1#8 == 0#8)

theorem main13_logical_thm.extracted_1._2 : ∀ (x : BitVec 32),
  ofBool (truncate 16 x <ₛ 0#16) = 1#1 →
    ¬ofBool (x &&& 32896#32 == 32896#32) = 1#1 → ofBool (truncate 8 x <ₛ 0#8) = 1#1 → 2#32 = 1#32

theorem sgt_3_impliesT_sgt_2_proof : sgt_3_impliesT_sgt_2_before ⊑ sgt_3_impliesT_sgt_2_after

theorem lor_lor_left2_proof : lor_lor_left2_before ⊑ lor_lor_left2_after

theorem not_signbit_splat_mask1_proof : not_signbit_splat_mask1_before ⊑ not_signbit_splat_mask1_after

theorem add_signbit_select_shl_proof : add_signbit_select_shl_before ⊑ add_signbit_select_shl_after

theorem AndZextAnd_thm.extracted_1._2 : ∀ (x : BitVec 3),
  ¬(True ∧ (x &&& 2#3).msb = true) → zeroExtend 5 (x &&& 3#3) &&& 14#5 = zeroExtend 5 (x &&& 2#3)

theorem substitute_constant_or_ne_swap_sle_logical_proof : substitute_constant_or_ne_swap_sle_logical_before ⊑ substitute_constant_or_ne_swap_sle_logical_after

theorem src_is_mask_zext_fail_not_mask_thm (e : IntW 8) (e_1 : IntW 16) :
  icmp IntPred.eq (LLVM.and (LLVM.xor e_1 (const? 16 123)) (zext 16 (lshr (const? 8 (-2)) e)))
      (LLVM.xor e_1 (const? 16 123)) ⊑
    icmp IntPred.eq (LLVM.or (LLVM.xor e_1 (const? 16 (-124))) (zext 16 (lshr (const? 8 (-2)) e)))
      (const? 16 (-1))

theorem n0_thm (e : IntW 8) :
  icmp IntPred.eq (LLVM.and e (const? 8 4)) e ⊑
    icmp IntPred.eq (LLVM.and e (const? 8 (-5))) (const? 8 0)

theorem positive_samevar_shlnsw_thm.extracted_1._2 : ∀ (x x_1 : BitVec 8),
  ¬(x ≥ ↑8 ∨ True ∧ (x_1 >>> x <<< x).sshiftRight' x ≠ x_1 >>> x ∨ x ≥ ↑8) →
    ¬(True ∧ ((-1#8) <<< x).sshiftRight' x ≠ -1#8 ∨ x ≥ ↑8) → x_1 >>> x <<< x = (-1#8) <<< x &&& x_1

theorem missed_const_prop_2002h12h05_thm.extracted_1._1 : ∀ (x : BitVec 32),
  0#32 - x + (x + (0#32 - 1#32 + 1#32)) = 0#32

theorem negate_sdiv_proof : negate_sdiv_before ⊑ negate_sdiv_after

theorem PR44545_proof : PR44545_before ⊑ PR44545_after

theorem e_592 :
     - 1 * (x |||  ~~~y) + 1 * (x ||| y) - 5 *  ~~~(x &&& y) + 1 *  ~~~(x &&&  ~~~y) + 2 *  ~~~y + 7 * (x ^^^ y) + 14 *  ~~~(x ||| y) + 7 *  ~~~(x |||  ~~~y) + 8 * (x &&&  ~~~y) + 11 * (x &&& y) = 1 * x + 11 *  ~~~(x &&&  ~~~x)

theorem ashr_eq_both_equal_thm.extracted_1._1 : ∀ (x : BitVec 8),
  ¬x ≥ ↑8 → ofBool ((BitVec.ofInt 8 (-128)).sshiftRight' x == BitVec.ofInt 8 (-128)) = ofBool (x == 0#8)

theorem ugt_swap_and_min_commute_logical_proof : ugt_swap_and_min_commute_logical_before ⊑ ugt_swap_and_min_commute_logical_after

theorem scalar_i32_shl_and_negC_eq_nonzero_proof : scalar_i32_shl_and_negC_eq_nonzero_before ⊑ scalar_i32_shl_and_negC_eq_nonzero_after

theorem trunc_shl_15_i16_i64_thm.extracted_1._1 : ∀ (x : BitVec 64), ¬15#64 ≥ ↑64 → 15#16 ≥ ↑16 → False

theorem scalar_i32_signbit_lshr_and_eq_X_is_constant2_thm.extracted_1._1 : ∀ (x : BitVec 32),
  ¬x ≥ ↑32 → ofBool (BitVec.ofInt 32 (-2147483648) >>> x &&& 1#32 == 0#32) = ofBool (x != 31#32)

theorem and_two_ranges_to_mask_and_range_different_sizes_proof : and_two_ranges_to_mask_and_range_different_sizes_before ⊑ and_two_ranges_to_mask_and_range_different_sizes_after

theorem shl_nsw_nuw_uge_Csle0_thm (e e_1 : IntW 8) :
  icmp IntPred.uge (shl e_1 e { «nsw» := true, «nuw» := true }) (const? 8 (-120)) ⊑
    icmp IntPred.ugt e_1 (const? 8 (-121))

theorem test5_proof : test5_before ⊑ test5_after

theorem sle_smin4_thm.extracted_1._2 : ∀ (x x_1 : BitVec 32),
  ¬ofBool (x <ₛ x_1 + 3#32) = 1#1 → ofBool (x_1 + 3#32 ≤ₛ x_1 + 3#32) = 1#1

@[simp]
lemma fals_or (c : Circuit α) :
  Circuit.fals ||

theorem masked_and_notallzeroes_logical_proof : masked_and_notallzeroes_logical_before ⊑ masked_and_notallzeroes_logical_after

theorem logical_and_not_cond_reuse_thm.extracted_1._3 : ∀ (x x_1 : BitVec 1), x_1 = 1#1 → x_1 ^^^ 1#1 = 1#1 → x = 1#1

theorem e_1810 :
     - 1 * (c ^^^  ~~~(a &&&  ~~~b)) + 4 * ((a &&& c) ^^^  ~~~(a ^^^ ( ~~~b &&& c))) + 11 * ( ~~~(a ||| b) |||  ~~~(b ^^^ c)) + 7 * (c ^^^  ~~~(a &&& (b &&& c))) + 2 * (a ||| ( ~~~b &&& c)) - 2 * (b |||  ~~~(a ^^^ c)) + 4 * ((a &&& b) |||  ~~~(b |||  ~~~c)) - 2 * (a &&& c) + 2 *  ~~~(a ^^^ (b ||| c)) + 2 * (b ^^^ ( ~~~a &&& (b ^^^ c))) + 3 * (b &&& (a ||| c)) + 1 * (b ^^^  ~~~(a &&& (b &&& c))) - 5 * ( ~~~(a ||| b) ||| (a ^^^ (b ^^^ c))) - 11 * ((a |||  ~~~b) &&&  ~~~(a ^^^ (b ^^^ c))) + 1 * (b ^^^ ( ~~~a ||| ( ~~~b ||| c))) - 1 * ((a ||| b) &&&  ~~~(b ^^^ c)) + 5 *  ~~~(a &&&  ~~~b) - 6 * (a ||| (b &&& c)) + 4 * (c |||  ~~~(a ||| b)) + 3 *  ~~~(a ||| ( ~~~b &&& c)) - 11 *  ~~~(a &&&  ~~~c) - 3 * ((b &&& c) ||| ( ~~~a &&& (b ||| c))) - 1 * ((a &&& c) |||  ~~~(b ||| c)) + 2 * (c ^^^ (a ||| (b &&& c))) + 1 * ((b &&&  ~~~c) |||  ~~~(a ||| ( ~~~b &&& c))) - 1 * ((a &&& b) ^^^ (a ^^^ (b &&& c))) + 1 * ((b &&& c) ^^^  ~~~(a &&& (b ^^^ c))) - 11 * (a ||| (b ||| c)) + 11 * (b |||  ~~~(a |||  ~~~c)) + 1 * (b ^^^ (a &&&  ~~~c)) + 7 * ( ~~~(a ^^^ b) ||| (a ^^^ c)) + 7 * ((a |||  ~~~b) &&& (b ^^^ c)) - 2 * (c ^^^ (a &&& (b ||| c))) - 18 *  ~~~(a ||| (b ||| c)) - 3 *  ~~~(a ||| ( ~~~b ||| c)) - 9 *  ~~~( ~~~a ||| (b ||| c)) - 22 *  ~~~( ~~~a ||| ( ~~~b ||| c)) - 28 * ( ~~~a &&& ( ~~~b &&& c)) - 15 * ( ~~~a &&& (b &&& c)) + 25 * (a &&& ( ~~~b &&& c)) - 22 * (a &&& (b &&& c)) =  - 1 * ((b &&&  ~~~c) |||  ~~~( ~~~a ||| ( ~~~b &&& c))) - 2 *  ~~~(a ||| (b &&& c))

theorem e_195 :
     - 1 *  ~~~(x ^^^ y) + 2 * (x ||| y) - 1 *  ~~~(x &&&  ~~~x) + 2 *  ~~~(x &&&  ~~~y) - 13 *  ~~~(x |||  ~~~y) - 13 * (x &&& y) =  - 11 * y + 1 * (x ^^^ y)

theorem test7_thm.extracted_1._2 : ∀ (x : BitVec 32),
  ¬1#32 ≥ ↑32 →
    ¬(1#32 ≥ ↑32 ∨ True ∧ (x >>> 1#32).uaddOverflow 2147483647#32 = true) →
      zeroExtend 64 (x >>> 1#32) + 2147483647#64 = zeroExtend 64 (x >>> 1#32 + 2147483647#32)

theorem scalar1_proof : scalar1_before ⊑ scalar1_after

theorem e_1697 :
    4 * ( ~~~b ||| (a ^^^ c)) + 2 * (a &&& ( ~~~b ||| c)) - 2 *  ~~~(a ^^^ (b &&& c)) - 1 * (c ^^^ (a &&& b)) - 7 *  ~~~( ~~~a ||| (b ^^^ c)) + 1 * ((b &&& c) ||| ( ~~~a &&& (b ||| c))) - 2 * (c ^^^  ~~~( ~~~a &&& ( ~~~b &&& c))) + 2 *  ~~~(a ||| c) - 2 * ( ~~~(a ^^^ b) |||  ~~~(a ^^^ c)) + 3 * (a &&& c) - 2 * (c ^^^  ~~~( ~~~a &&& (b &&& c))) + 5 * (b ^^^  ~~~(a &&& c)) - 5 * (b ||| (a &&& c)) + 1 * (c |||  ~~~(a ^^^ b)) + 11 * (c ^^^ (a ||| ( ~~~b &&& c))) + 11 * (c ^^^  ~~~( ~~~a ||| ( ~~~b &&& c))) - 2 * (a &&& b) - 7 * ((a &&& b) ^^^  ~~~(a ^^^ (b &&& c))) - 3 * ((a &&& b) ^^^ (a ^^^ ( ~~~b ||| c))) + 3 * (b ^^^ (a ||| (b &&& c))) - 11 *  ~~~(a &&& ( ~~~b ||| c)) - 2 * ((a &&& c) ||| (b &&&  ~~~c)) + 17 *  ~~~(a ||| (b ||| c)) + 27 *  ~~~(a ||| ( ~~~b ||| c)) + 7 *  ~~~( ~~~a ||| ( ~~~b ||| c)) + 6 * ( ~~~a &&& ( ~~~b &&& c)) - 6 * ( ~~~a &&& (b &&& c)) - 14 * (a &&& ( ~~~b &&& c)) + 11 * (a &&& (b &&& c)) = 25 *  ~~~( ~~~a ||| (b ||| c))

theorem ugt_umax1_thm.extracted_1._1 : ∀ (x x_1 : BitVec 32),
  ofBool (x <ᵤ x_1) = 1#1 → ofBool (x_1 <ᵤ x_1) = ofBool (x_1 <ᵤ x)

theorem sdiv_shl_pair3_thm.extracted_1._2 : ∀ (x x_1 x_2 : BitVec 32),
  ¬(True ∧ (x_2 <<< x_1).sshiftRight' x_1 ≠ x_2 ∨
        x_1 ≥ ↑32 ∨
          True ∧ (x_2 <<< x).sshiftRight' x ≠ x_2 ∨
            x ≥ ↑32 ∨ (x_2 <<< x == 0 || 32 != 1 && x_2 <<< x_1 == intMin 32 && x_2 <<< x == -1) = true) →
    ¬(True ∧ 1#32 <<< x_1 >>> x_1 ≠ 1#32 ∨ x_1 ≥ ↑32 ∨ x ≥ ↑32) → (x_2 <<< x_1).sdiv (x_2 <<< x) = 1#32 <<< x_1 >>> x

theorem liftEffect_eq_pure_cast {m : Type → Type} [Pure m]
    {eff : EffectKind} (eff_eq : eff = .pure) (eff_le : eff ≤ .impure) :
    liftEffect eff_le = fun (x : eff.toMonad m α) =>
      Pure.pure (cast (by rw [eff_eq]; rfl) x)

theorem e_235 :
    1 *  ~~~(x ^^^ y) - 5 *  ~~~(x &&&  ~~~y) - 1 *  ~~~(x &&& y) + 3 *  ~~~y + 5 *  ~~~(x |||  ~~~y) - 2 * (x &&&  ~~~y) + 3 * (x &&& y) =  - 2 *  ~~~(x ||| y) - 1 * y

theorem ult_rem_zero_thm (e : IntW 8) :
  icmp IntPred.ult (mul e (const? 8 7) { «nsw» := false, «nuw» := true }) (const? 8 21) ⊑
    icmp IntPred.ult e (const? 8 3)

theorem and_or2_thm.extracted_1._3 : ∀ (x x_1 : BitVec 1), ¬(x_1 ^^^ 1#1) &&& x = 1#1 → ¬x = 1#1 → x = 0#1

theorem trunc_shl_nsw_nuw_31_i32_i64_thm (e : IntW 64) :
  trunc 32 (shl e (const? 64 31) { «nsw» := true, «nuw» := true }) ⊑ shl (trunc 32 e) (const? 32 31)

theorem test18_thm (e : IntW 32) :
  icmp IntPred.ne (LLVM.and e (const? 32 (-128))) (const? 32 0) ⊑ icmp IntPred.ugt e (const? 32 127)

theorem bitwise_and_bitwise_and_icmps_thm (e e_1 e_2 : IntW 8) :
  LLVM.and
      (LLVM.and (icmp IntPred.eq e_2 (const? 8 42))
        (icmp IntPred.ne (LLVM.and e_1 (const? 8 1)) (const? 8 0)))
      (icmp IntPred.ne (LLVM.and e_1 (shl (const? 8 1) e)) (const? 8 0)) ⊑
    LLVM.and (icmp IntPred.eq e_2 (const? 8 42))
      (icmp IntPred.eq (LLVM.and e_1 (LLVM.or (shl (const? 8 1) e { «nsw» := false, «nuw» := true }) (const? 8 1)))
        (LLVM.or (shl (const? 8 1) e { «nsw» := false, «nuw» := true }) (const? 8 1)))

theorem logical_or_bitwise_or_icmps_comm3_thm (e e_1 e_2 : IntW 8) :
  select (icmp IntPred.eq (LLVM.and e_2 (shl (const? 8 1) e_1)) (const? 8 0)) (const? 1 1)
      (LLVM.or (icmp IntPred.eq (LLVM.and e_2 (const? 8 1)) (const? 8 0)) (icmp IntPred.eq e (const? 8 42))) ⊑
    select (icmp IntPred.eq (LLVM.and e_2 (shl (const? 8 1) e_1 { «nsw» := false, «nuw» := true })) (const? 8 0))
      (const? 1 1)
      (LLVM.or (icmp IntPred.eq (LLVM.and e_2 (const? 8 1)) (const? 8 0))
        (icmp IntPred.eq e (const? 8 42)))

theorem uge_or_max_commute_thm.extracted_1._1 : ∀ (x x_1 : BitVec 8),
  ofBool (x_1 == -1#8) ||

theorem sub_select_not_sext_proof : sub_select_not_sext_before ⊑ sub_select_not_sext_after

theorem ashrslt_03_05_proof : ashrslt_03_05_before ⊑ ashrslt_03_05_after

theorem ashrslt_02_07_proof : ashrslt_02_07_before ⊑ ashrslt_02_07_after

theorem test_shl_nsw__nuw_is_safe_thm (e : IntW 64) (e_1 : IntW 32) :
  select (icmp IntPred.eq (LLVM.and e_1 (const? 32 1073741822)) (const? 32 0)) e
      (ashr e (zext 64 (shl (LLVM.and e_1 (const? 32 1073741822)) (const? 32 2) { «nsw» := true, «nuw» := false }))) ⊑
    ashr e (zext 64 (LLVM.and (shl e_1 (const? 32 2)) (const? 32 (-8))) { «nneg» := true })

theorem test6_thm.extracted_1._2 : ∀ (x : BitVec 1023),
  ¬ofBool (x &&& 64#1023 != 0#1023) = 1#1 → 0#1023 = x &&& 64#1023

theorem or_eq_with_diff_one_logical_proof : or_eq_with_diff_one_logical_before ⊑ or_eq_with_diff_one_logical_after

theorem xor_signbit_shl_proof : xor_signbit_shl_before ⊑ xor_signbit_shl_after

theorem ult_and_not_max_commute_thm.extracted_1._1 : ∀ (x x_1 : BitVec 8),
  ofBool (x_1 != -1#8) &&& ofBool (x_1 <ᵤ x) = ofBool (x_1 <ᵤ x)

theorem zext_nneg_proof : zext_nneg_before ⊑ zext_nneg_after

theorem lshrult_01_08_exact_thm (e : IntW 4) :
  icmp IntPred.ult (lshr e (const? 4 1) { «exact» := true }) (const? 4 (-8)) ⊑ const? 1 1

theorem ashr_sge_exact_thm.extracted_1._1 : ∀ (x : BitVec 8),
  ¬(True ∧ x >>> 3#8 <<< 3#8 ≠ x ∨ 3#8 ≥ ↑8) → ofBool (10#8 ≤ₛ x.sshiftRight' 3#8) = ofBool (72#8 <ₛ x)

theorem trunc_shl_33_i32_i64_thm.extracted_1._1 : ∀ (x : BitVec 64), ¬33#64 ≥ ↑64 → truncate 32 (x <<< 33#64) = 0#32

theorem e_345 :
    1 *  ~~~y + 1 * y + 11 *  ~~~(x ^^^ y) + 7 *  ~~~(x &&& y) + 2 * (x ^^^ y) - 19 *  ~~~(x ||| y) - 10 *  ~~~(x |||  ~~~y) - 10 * (x &&&  ~~~y) = 12 * (x &&& y)

theorem getLsb_geX(x : BitVec w) (hi : i ≥ w) :
    BitVec.getLsbD x i = false

theorem lshrugt_03_13_exact_thm (e : IntW 4) :
  icmp IntPred.ugt (lshr e (const? 4 3) { «exact» := true }) (const? 4 (-3)) ⊑ const? 1 0

theorem mullo_thm (e e_1 : IntW 64) :
  LLVM.or
      (shl
        (add
          (LLVM.and
            (add
              (lshr
                (mul (LLVM.and e_1 (const? 64 4294967295)) (LLVM.and e (const? 64 4294967295))
                  { «nsw» := false, «nuw» := true })
                (const? 64 32))
              (mul (LLVM.and e_1 (const? 64 4294967295)) (lshr e (const? 64 32)) { «nsw» := false, «nuw» := true }))
            (const? 64 4294967295))
          (mul (lshr e_1 (const? 64 32)) (LLVM.and e (const? 64 4294967295)) { «nsw» := false, «nuw» := true }))
        (const? 64 32))
      (LLVM.and
        (mul (LLVM.and e_1 (const? 64 4294967295)) (LLVM.and e (const? 64 4294967295))
          { «nsw» := false, «nuw» := true })
        (const? 64 4294967295)) ⊑
    LLVM.or
      (shl
        (add
          (add
            (lshr
              (mul (LLVM.and e_1 (const? 64 4294967295)) (LLVM.and e (const? 64 4294967295))
                { «nsw» := false, «nuw» := true })
              (const? 64 32))
            (mul e_1 (lshr e (const? 64 32))))
          (mul (lshr e_1 (const? 64 32)) e))
        (const? 64 32))
      (LLVM.and
        (mul (LLVM.and e_1 (const? 64 4294967295)) (LLVM.and e (const? 64 4294967295))
          { «nsw» := false, «nuw» := true })
        (const? 64 4294967295))
      { «disjoint» := true }

theorem icmp_equality_test_proof : icmp_equality_test_before ⊑ icmp_equality_test_after

theorem or_xor_common_op_commute7_thm (e e_1 e_2 : IntW 8) :
  LLVM.or (LLVM.xor e_2 e_1) (LLVM.or e e_1) ⊑ LLVM.or (LLVM.or e e_1) e_2

theorem test19_thm.extracted_1._1 : ∀ (x : BitVec 10),
  ¬(2#3 ≥ ↑3 ∨ 2#3 ≥ ↑3) → True ∧ (0#3).ssubOverflow (truncate 3 x &&& 1#3) = true → False

theorem test86_thm.extracted_1._2 : ∀ (x : BitVec 16),
  ¬4#32 ≥ ↑32 → ¬4#16 ≥ ↑16 → truncate 16 ((signExtend 32 x).sshiftRight' 4#32) = x.sshiftRight' 4#16

theorem bools_logical_thm.extracted_1._2 : ∀ (x : BitVec 1), ¬x ^^^ 1#1 = 1#1 → ¬x = 1#1 → 0#1 = 1#1 → False

theorem a_thm.extracted_1._2 : ∀ (x x_1 : BitVec 1),
  x_1 = 1#1 →
    ¬(True ∧ (2#32).saddOverflow (signExtend 32 x) = true) →
      zeroExtend 32 x_1 + 1#32 + (0#32 - zeroExtend 32 x) = 2#32 + signExtend 32 x

theorem e_626 :
     - 5 * x - 7 *  ~~~x + 1 *  ~~~(x &&&  ~~~y) - 1 * y - 1 *  ~~~(x ^^^ y) + 1 *  ~~~(x &&& y) + 1 * (x |||  ~~~y) + 5 *  ~~~(x ||| y) + 3 * (x &&&  ~~~y) + 5 * (x &&& y) =  - 6 *  ~~~(x |||  ~~~y)

theorem eq_21_logical_proof : eq_21_logical_before ⊑ eq_21_logical_after

theorem sgt_x_impliesF_eq_smin_todo_thm.extracted_1._1 : ∀ (x x_1 : BitVec 8),
  ofBool (x <ₛ x_1) = 1#1 → ofBool (x_1 ≤ₛ x) = 1#1 → False

theorem logic_and_logic_or_6_thm.extracted_1._2 : ∀ (x x_1 : BitVec 1), ¬x_1 = 1#1 → 0#1 = 1#1 → 1#1 = 0#1

theorem gt_unsigned_to_small_unsigned_proof : gt_unsigned_to_small_unsigned_before ⊑ gt_unsigned_to_small_unsigned_after

theorem t0_proof : t0_before ⊑ t0_after

@[simp] theorem Com.rec'_var (e : Expr d Γ eff u) (body : Com d _ _ t) :
    (Com.var e body).rec' (motive:=motive) rets var
    = var e body (body.rec' (motive:=motive) rets var)

theorem e_298 :
    1 * y - 7 * (x ^^^ y) + 1 *  ~~~(x &&& y) + 11 *  ~~~y - 12 *  ~~~(x ||| y) - 5 * (x &&&  ~~~y) - 1 * (x &&& y) =  - 5 *  ~~~(x |||  ~~~y)

theorem alive_AddSub_1539_2  (w : Nat)   : alive_AddSub_1539_2_src w  ⊑ alive_AddSub_1539_2_tgt w

theorem add_nextStateCirc_eval :
    (add.nextStateCirc ()).eval =
      fun x => x (inr true) && x (inr false) |

theorem alive_AndOrXor_2581__BAB___A__B : alive_AndOrXor_2581__BAB___A__B_src ⊑ alive_AndOrXor_2581__BAB___A__B_tgt

theorem n0_thm.extracted_1._2 : ∀ (x x_1 x_2 : BitVec 8),
  ¬x_2 ≥ ↑8 →
    ¬(True ∧ ((-1#8) <<< x_2).sshiftRight' x_2 ≠ -1#8 ∨ x_2 ≥ ↑8) →
      ofBool (((-1#8) <<< x_2 ^^^ -1#8) &&& x_1 != x) = ofBool (x_1 &&& ((-1#8) <<< x_2 ^^^ -1#8) != x)

theorem e_1424 :
    1 * t + 4 *  ~~~z + 4 *  ~~~t - 1 *  ~~~(z &&&  ~~~z) - 1 *  ~~~(z ^^^ t) - 7 * (z |||  ~~~t) - 1 * (z ^^^ t) - 4 *  ~~~(z |||  ~~~t) + 4 * (z &&&  ~~~t) + 8 * (z &&& t) =  - 1 *  ~~~(z &&& t)

theorem or_and_not_not_commute6_thm.extracted_1._2 : ∀ (x x_1 x_2 : BitVec 32),
  ¬((x_2 == 0 || 32 != 1 && 42#32 == intMin 32 && x_2 == -1) = true ∨
        (x_2 == 0 || 32 != 1 && 42#32 == intMin 32 && x_2 == -1) = true) →
    ¬(x_2 == 0 || 32 != 1 && 42#32 == intMin 32 && x_2 == -1) = true →
      (42#32).sdiv x_2 &&& ((x_1 ||| x) ^^^ -1#32) ||

theorem e_2211 :
    4 * (e |||  ~~~(d ^^^ f)) + 5 * (f ^^^  ~~~(d &&& (e ||| f))) + 7 * (e &&& f) - 2 * (e ||| (d &&&  ~~~f)) - 7 * ((d &&& f) ^^^ (d ^^^ ( ~~~e &&& f))) + 4 * (e ^^^  ~~~(d |||  ~~~f)) - 6 * ((d |||  ~~~e) &&& (d ^^^ (e ^^^ f))) - 7 * ((d &&& e) ^^^ (d ^^^ ( ~~~e ||| f))) - 11 * ( ~~~d ||| (e ^^^ f)) + 3 * (e ^^^ (d &&& (e ||| f))) - 1 * (f &&& (d ||| e)) - 6 * ((d |||  ~~~e) &&&  ~~~(e ^^^ f)) - 7 * (d &&& f) + 4 * ( ~~~d &&& (e ^^^ f)) - 1 * ( ~~~(d &&&  ~~~e) &&& (d ^^^ (e ^^^ f))) + 2 * (f ^^^  ~~~(d |||  ~~~e)) - 7 *  ~~~(d &&& ( ~~~e &&& f)) + 4 * ((d &&&  ~~~e) ||| (d ^^^ (e ^^^ f))) + 2 * (f ^^^ ( ~~~d ||| (e ||| f))) - 1 * ( ~~~e ||| (d ^^^ f)) - 2 * (e ^^^ f) + 1 *  ~~~( ~~~d &&& (e &&& f)) + 11 * ( ~~~e &&& (d ^^^ f)) + 2 * ((d &&& e) |||  ~~~(e ||| f)) - 2 * ((d ^^^ e) |||  ~~~(d ^^^ f)) + 5 * (d &&& e) + 1 *  ~~~( ~~~d &&& ( ~~~e ||| f)) + 4 *  ~~~(d ||| (e &&& f)) + 3 * (e ^^^  ~~~(d &&& ( ~~~e &&& f))) - 1 * ( ~~~e &&&  ~~~(d ^^^ f)) + 2 * (e ^^^ (d &&& (e ^^^ f))) - 5 * (d ||| e) - 2 * (d ||| ( ~~~e ||| f)) - 2 * (e |||  ~~~(d |||  ~~~f)) + 1 * (e ^^^ (d &&& f)) - 3 * ( ~~~(d &&& e) &&&  ~~~(e ^^^ f)) - 3 * (e ^^^  ~~~( ~~~d ||| ( ~~~e &&& f))) - 5 * ((e &&&  ~~~f) |||  ~~~( ~~~d ||| ( ~~~e &&& f))) + 3 * (d &&&  ~~~f) + 2 * ((d ||| e) &&&  ~~~(e ^^^ f)) + 5 *  ~~~( ~~~d ||| (e ^^^ f)) - 6 *  ~~~(e ||| f) + 1 * ((d &&& e) ||| (e ^^^ f)) - 5 * d - 1 * ((e &&& f) ^^^  ~~~(d &&& (e ^^^ f))) + 3 * (e ^^^  ~~~(d ||| (e ^^^ f))) + 23 *  ~~~(d ||| (e ||| f)) + 11 *  ~~~(d ||| ( ~~~e ||| f)) + 22 *  ~~~( ~~~d ||| ( ~~~e ||| f)) + 24 * ( ~~~d &&& ( ~~~e &&& f)) + 38 * ( ~~~d &&& (e &&& f)) + 20 * (d &&& ( ~~~e &&& f)) + 21 * (d &&& (e &&& f)) = 11 * ( ~~~(d |||  ~~~e) ||| (d ^^^ (e ^^^ f))) - 35 *  ~~~( ~~~d ||| (e ||| f))

theorem test_sub__nuw_is_safe_thm.extracted_1._3 : ∀ (x : BitVec 32),
  ¬ofBool (x &&& 2147483647#32 == 1073741824#32) = 1#1 →
    True ∧ (BitVec.ofInt 32 (-2147483648)).usubOverflow (x &&& 2147483647#32) = true → False

@[bv_multi_width_normalize] theorem ofBool_eq_ofBool_iff (x y : Bool) :
  BitVec.ofBool x = BitVec.ofBool y ↔ (x = y)

theorem ashrsgt_01_11_thm.extracted_1._1 : ∀ (x : BitVec 4),
  ¬1#4 ≥ ↑4 → ofBool (BitVec.ofInt 4 (-5) <ₛ x.sshiftRight' 1#4) = 1#1

theorem substitute_constant_and_eq_ugt_swap_logical_proof : substitute_constant_and_eq_ugt_swap_logical_before ⊑ substitute_constant_and_eq_ugt_swap_logical_after

theorem poo_thm (e e_1 e_2 e_3 : IntW 32) :
  LLVM.or (LLVM.and (select (icmp IntPred.slt e_3 e_2) (const? 32 (-1)) (const? 32 0)) e_1)
      (LLVM.and (select (icmp IntPred.slt e_3 e_2) (const? 32 0) (const? 32 (-1))) e) ⊑
    select (icmp IntPred.slt e_3 e_2) e_1 e

theorem main7b_logical_thm.extracted_1._1 : ∀ (x x_1 : BitVec 32),
  ¬ofBool (x_1 == x &&& x_1) = 1#1 → ofBool (x_1 != x &&& x_1) = 1#1 → 0#1 = 1#1 → 0#32 = zeroExtend 32 1#1

theorem main14_logical_thm.extracted_1._4 : ∀ (x : BitVec 32),
  ¬ofBool (0#16 ≤ₛ truncate 16 x) = 1#1 → ¬ofBool (x &&& 32896#32 == 0#32) = 1#1 → 0#1 = 1#1 → 2#32 = 1#32

theorem demorgan_nor_use2bc_thm.extracted_1._1 : ∀ (x x_1 : BitVec 8),
  ¬(((x_1 ^^^ -1#8 ||| x) * 23#8 == 0 ||
            8 != 1 && (x_1 ^^^ -1#8 ||| x) ^^^ -1#8 == intMin 8 && (x_1 ^^^ -1#8 ||| x) * 23#8 == -1) =
          true ∨
        (x * 23#8 == 0 ||
            8 != 1 && ((x_1 ^^^ -1#8 ||| x) ^^^ -1#8).sdiv ((x_1 ^^^ -1#8 ||| x) * 23#8) == intMin 8 &&
              x * 23#8 == -1) =
          true) →
    ((x ||| x_1 ^^^ -1#8) * 23#8 == 0 ||
            8 != 1 && (x ||| x_1 ^^^ -1#8) ^^^ -1#8 == intMin 8 && (x ||| x_1 ^^^ -1#8) * 23#8 == -1) =
          true ∨
        (x * 23#8 == 0 ||
            8 != 1 && ((x ||| x_1 ^^^ -1#8) ^^^ -1#8).sdiv ((x ||| x_1 ^^^ -1#8) * 23#8) == intMin 8 &&
              x * 23#8 == -1) =
          true →
      False

theorem t0_scalar_proof : t0_scalar_before ⊑ t0_scalar_after

theorem test_and3_logical_thm.extracted_1._1 : ∀ (x x_1 : BitVec 32),
  ofBool (x <ₛ x_1 &&& 2147483647#32) = 1#1 → ofBool (0#32 ≤ₛ x) = ofBool (x <ᵤ x_1 &&& 2147483647#32)

theorem or_ranges_separated_proof : or_ranges_separated_before ⊑ or_ranges_separated_after

theorem test42_thm.extracted_1._1 : ∀ (x : BitVec 32), zeroExtend 32 (truncate 8 x) = x &&& 255#32

theorem shl_nsw_nuw_add_proof : shl_nsw_nuw_add_before ⊑ shl_nsw_nuw_add_after

theorem invert_both_cmp_operands_add_thm (e e_1 : IntW 32) :
  icmp IntPred.sgt (add e_1 (LLVM.xor e (const? 32 (-1)))) (const? 32 0) ⊑
    icmp IntPred.slt (sub e e_1) (const? 32 (-1))

theorem lshrugt_01_12_thm (e : IntW 4) : icmp IntPred.ugt (lshr e (const? 4 1)) (const? 4 (-4)) ⊑ const? 1 0

theorem lshrult_01_07_exact_thm (e : IntW 4) :
  icmp IntPred.ult (lshr e (const? 4 1) { «exact» := true }) (const? 4 7) ⊑
    icmp IntPred.ne e (const? 4 (-2))

theorem add_assoc_3 (hq : q >= t) (hp : p < u) (hr : r < u) :
  (bw t (addMax (bw u (addMax (bw p a) (bw r b))) (bw s c)))  =
  (bw t (addMax (bw p a) (bw q (addMax (bw r b) (bw s c)))))

@[simp]
theorem eval_repeatN (b : Bool) (n : Nat) (env : Unit → BitStream) :
  (repeatN b n).eval env = fun i =>
    if i < n then b else (env () (i - n))

theorem lshrult_01_10_exact_proof : lshrult_01_10_exact_before ⊑ lshrult_01_10_exact_after

theorem different_size_zext_zext_ne_commute_thm.extracted_1._1 : ∀ (x : BitVec 4) (x_1 : BitVec 7),
  ofBool (zeroExtend 25 x_1 != zeroExtend 25 x) = ofBool (x_1 != zeroExtend 7 x)

theorem multiuse_add_proof : multiuse_add_before ⊑ multiuse_add_after

theorem e_1272 :
    11 *  ~~~t + 2 *  ~~~(z ^^^ t) + 5 *  ~~~(z &&&  ~~~t) - 1 * (z ||| t) - 1 *  ~~~(z &&&  ~~~z) - 17 *  ~~~(z ||| t) - 4 *  ~~~(z |||  ~~~t) - 10 * (z &&&  ~~~t) - 5 * (z &&& t) =  - 1 * (z ^^^ t)

theorem multiuse_add_thm.extracted_1._1 : ∀ (x : BitVec 1), x = 1#1 → 64#64 + zeroExtend 64 x + 1#64 = 66#64

theorem main5c_like_logical_thm.extracted_1._12 : ∀ (x x_1 : BitVec 32),
  ¬ofBool (x_1 &&& 7#32 != 7#32) = 1#1 →
    ¬ofBool (x_1 &&& 7#32 == 7#32) = 1#1 → ¬ofBool (x &&& 7#32 != 7#32) = 1#1 → 1#32 = zeroExtend 32 0#1

theorem e_1526 :
     - 1 * (b ^^^ (a &&& c)) - 2 * (a &&& c) + 3 * ( ~~~c &&& (a ^^^ b)) + 11 * (a &&&  ~~~c) + 2 * (c &&& (a ^^^ b)) + 5 * (b ^^^  ~~~(a |||  ~~~c)) - 7 *  ~~~(a ||| ( ~~~b ||| c)) - 14 *  ~~~( ~~~a ||| (b ||| c)) - 5 * ( ~~~a &&& ( ~~~b &&& c)) + 1 * (a &&& ( ~~~b &&& c)) - 3 * (a &&& (b &&& c)) = 1 * ( ~~~a &&& (b &&& c)) + 15 *  ~~~( ~~~a ||| ( ~~~b ||| c))

theorem main13_logical_thm.extracted_1._4 : ∀ (x : BitVec 32),
  ¬ofBool (truncate 16 x <ₛ 0#16) = 1#1 → ¬ofBool (x &&& 32896#32 == 32896#32) = 1#1 → 0#1 = 1#1 → 2#32 = 1#32

theorem e_1493 :
    1 * (z |||  ~~~t) + 1 *  ~~~(z &&&  ~~~t) + 2 * (z ||| t) - 1 * (z ^^^ t) - 5 *  ~~~(z ^^^ t) + 2 * z - 6 *  ~~~t - 1 *  ~~~(z &&& t) + 3 *  ~~~z + 8 *  ~~~(z ||| t) + 4 * (z &&&  ~~~t) = 1 *  ~~~(z &&&  ~~~z) + 3 *  ~~~(z |||  ~~~t)

theorem or_ranges_adjacent_proof : or_ranges_adjacent_before ⊑ or_ranges_adjacent_after

theorem trunc_sel_equal_sext_proof : trunc_sel_equal_sext_before ⊑ trunc_sel_equal_sext_after

theorem or_xor_commute4_proof : or_xor_commute4_before ⊑ or_xor_commute4_after

theorem main12_logical_thm.extracted_1._2 : ∀ (x : BitVec 32),
  ofBool (truncate 16 x <ₛ 0#16) = 1#1 → ofBool (x &&& 32896#32 == 0#32) = 1#1 → ¬True → 2#32 = 1#32

theorem src_is_mask_select_thm.extracted_1._2 : ∀ (x x_1 : BitVec 8) (x_2 : BitVec 1),
  x_2 = 1#1 →
    ofBool ((x_1 ^^^ x_1 + -1#8) &&& (x ^^^ 123#8) != x ^^^ 123#8) = ofBool (x_1 ^^^ x_1 + -1#8 <ᵤ x ^^^ 123#8)

theorem rev8_mul_and_lshr_proof : rev8_mul_and_lshr_before ⊑ rev8_mul_and_lshr_after

theorem test9_thm.extracted_1._2 : ∀ (x : BitVec 77),
  ¬(True ∧ (x &&& 562949953421310#77 &&& 1#77 != 0) = true) →
    (x &&& 562949953421310#77) + 1#77 = x &&& 562949953421310#77 ||

theorem eq_smax4_proof : eq_smax4_before ⊑ eq_smax4_after

theorem ashrsgt_03_15_thm.extracted_1._1 : ∀ (x : BitVec 4),
  ¬3#4 ≥ ↑4 → ofBool (-1#4 <ₛ x.sshiftRight' 3#4) = ofBool (-1#4 <ₛ x)

theorem demorgan_nand_apint1_proof : demorgan_nand_apint1_before ⊑ demorgan_nand_apint1_after

theorem scalar_i32_shl_and_negC_ne_thm.extracted_1._1 : ∀ (x x_1 : BitVec 32),
  ¬x ≥ ↑32 → ofBool (x_1 <<< x &&& BitVec.ofInt 32 (-262144) != 0#32) = ofBool (262143#32 <ᵤ x_1 <<< x)

theorem both_thm (e e_1 : IntW 8) :
  icmp IntPred.ult (LLVM.xor (shl (const? 8 (-1)) e_1) (const? 8 (-1)))
      (LLVM.xor (shl (const? 8 (-1)) e) (const? 8 (-1))) ⊑
    icmp IntPred.ugt (shl (const? 8 (-1)) e_1 { «nsw» := true, «nuw» := false })
      (shl (const? 8 (-1)) e { «nsw» := true, «nuw» := false })

theorem icmp_slt_sext_ne_zero_nofold_proof : icmp_slt_sext_ne_zero_nofold_before ⊑ icmp_slt_sext_ne_zero_nofold_after

theorem n2_proof : n2_before ⊑ n2_after

theorem test_shift_and_cmp_changed1_proof : test_shift_and_cmp_changed1_before ⊑ test_shift_and_cmp_changed1_after

theorem eq_10_thm.extracted_1._1 : ∀ (x x_1 : BitVec 32),
  ¬(8#32 ≥ ↑32 ∨ 8#32 ≥ ↑32) →
    ofBool (truncate 8 x_1 == truncate 8 x) &&& ofBool (truncate 8 (x_1 >>> 8#32) == truncate 8 (x >>> 8#32)) =
      ofBool (truncate 16 x_1 == truncate 16 x)

theorem e_1768 :
    7 * (b ^^^ (a &&& c)) + 7 * (a ^^^ (b &&& c)) - 1 * (b &&& c) - 1 * (c ^^^ ( ~~~a &&& (b ||| c))) - 6 * ( ~~~(a ||| b) |||  ~~~(a ^^^ (b ^^^ c))) + 11 *  ~~~(a ||| (b ^^^ c)) - 2 * (a ||| ( ~~~b &&& c)) + 1 * (b |||  ~~~c) + 4 *  ~~~(a &&& ( ~~~b ||| c)) - 6 * ((a &&& c) ^^^  ~~~(a ^^^ ( ~~~b &&& c))) + 2 * (b ^^^  ~~~( ~~~a ||| ( ~~~b &&& c))) - 1 * (a |||  ~~~b) - 2 * (a ^^^ ( ~~~b &&& c)) - 3 * (b ^^^  ~~~(a ||| (b &&& c))) + 3 * ((b &&&  ~~~c) ^^^ (a ||| (b ^^^ c))) - 7 * (a ^^^ ( ~~~b ||| c)) + 5 * (b ^^^  ~~~(a &&& (b ^^^ c))) - 3 * (a &&&  ~~~c) + 1 * (c ^^^ ( ~~~a ||| (b &&& c))) - 7 * ((a ||| b) &&&  ~~~(a ^^^ (b ^^^ c))) - 11 *  ~~~(a &&& (b ||| c)) - 11 * (a &&& b) + 2 * ((a &&& b) ^^^ (b |||  ~~~c)) - 11 * ((a &&& b) |||  ~~~(a ^^^ (b ^^^ c))) - 6 *  ~~~(a |||  ~~~b) + 1 *  ~~~c - 1 * ((b &&& c) ||| (a &&& (b ||| c))) + 2 * (c |||  ~~~(a ^^^ b)) + 29 *  ~~~(a ||| (b ||| c)) + 6 *  ~~~(a ||| ( ~~~b ||| c)) + 9 *  ~~~( ~~~a ||| (b ||| c)) + 27 *  ~~~( ~~~a ||| ( ~~~b ||| c)) + 29 * ( ~~~a &&& ( ~~~b &&& c)) + 34 * ( ~~~a &&& (b &&& c)) + 20 * (a &&& ( ~~~b &&& c)) + 33 * (a &&& (b &&& c)) = 11 * (b ^^^  ~~~( ~~~a &&& (b &&& c)))

theorem or_lshr_thm (e e_1 e_2 e_3 : IntW 8) :
  LLVM.or (lshr e_3 e_2) (LLVM.or (lshr e_1 e_2) e) ⊑ LLVM.or (lshr (LLVM.or e_1 e_3) e_2) e

theorem pr51551_demand3bits_thm.extracted_1._1 : ∀ (x x_1 : BitVec 32),
  ¬(True ∧ (x_1 &&& BitVec.ofInt 32 (-7) ||| 1#32).smulOverflow x = true) →
    (x_1 &&& BitVec.ofInt 32 (-7) ||| 1#32) * x &&& 7#32 = x &&& 7#32

theorem or3 (w : Nat) (a : BitVec w) : (a ≠ a + 1#w) ∨ (1#w + 1#w = 0#w) ∨ (1#w = 0#w)

theorem test_proof : test_before ⊑ test_after

theorem ashrslt_03_14_exact_thm (e : IntW 4) :
  icmp IntPred.slt (ashr e (const? 4 3) { «exact» := true }) (const? 4 (-2)) ⊑ const? 1 0

theorem e_941 :
    7 * (z |||  ~~~t) + 1 *  ~~~(z ^^^ t) - 9 *  ~~~(z ||| t) - 1 *  ~~~(z |||  ~~~t) - 14 * (z &&&  ~~~t) - 15 * (z &&& t) =  - 7 *  ~~~(z &&&  ~~~z) + 6 *  ~~~z

theorem t_2_63_or_proof : t_2_63_or_before ⊑ t_2_63_or_after

theorem e_227 :
    1 * (x |||  ~~~y) - 1 * y + 1 * (x ^^^ y) + 2 *  ~~~(x &&&  ~~~x) - 2 *  ~~~(x |||  ~~~y) + 3 * (x &&&  ~~~y) - 2 * (x &&& y) =  - 4 *  ~~~(x ||| y) + 7 *  ~~~y

theorem test4_proof : test4_before ⊑ test4_after

theorem a_proof : a_before ⊑ a_after

theorem and_zext_zext_thm (e : IntW 4) (e_1 : IntW 8) :
  LLVM.and (zext 16 e_1) (zext 16 e) ⊑ zext 16 (LLVM.and e_1 (zext 8 e)) { «nneg» := true }

theorem scalar_i8_shl_ult_const_3_proof : scalar_i8_shl_ult_const_3_before ⊑ scalar_i8_shl_ult_const_3_after

theorem alive_AddSub_1295  (w : Nat)   : alive_AddSub_1295_src w  ⊑ alive_AddSub_1295_tgt w

theorem ashrslt_01_13_exact_thm (e : IntW 4) :
  icmp IntPred.slt (ashr e (const? 4 1) { «exact» := true }) (const? 4 (-3)) ⊑
    icmp IntPred.slt e (const? 4 (-6))

theorem lowmask_xor_zext_commute_thm (e : IntW 8) (e_1 : IntW 32) :
  LLVM.and (LLVM.xor (mul e_1 e_1) (zext 32 e)) (const? 32 255) ⊑ zext 32 (LLVM.xor e (trunc 8 (mul e_1 e_1)))

theorem ashr_x_by_const_cmp_sge_x_proof : ashr_x_by_const_cmp_sge_x_before ⊑ ashr_x_by_const_cmp_sge_x_after

theorem neg_or_lshr_i32_thm.extracted_1._1 : ∀ (x : BitVec 32),
  ¬31#32 ≥ ↑32 → (0#32 - x ||| x) >>> 31#32 = zeroExtend 32 (ofBool (x != 0#32))

theorem bools_logical_commute1_thm.extracted_1._11 : ∀ (x x_1 x_2 : BitVec 1),
  x_2 = 1#1 → ¬x_1 = 1#1 → ¬x_1 ^^^ 1#1 = 1#1 → 0#1 = x_2

theorem xor_logic_and_logic_or2_thm.extracted_1._4 : ∀ (x x_1 x_2 : BitVec 1), ¬x_2 = 1#1 → x = 1#1 → 0#1 ^^^ 1#1 = x

theorem ashrsgt_01_14_exact_thm.extracted_1._1 : ∀ (x : BitVec 4),
  ¬(True ∧ x >>> 1#4 <<< 1#4 ≠ x ∨ 1#4 ≥ ↑4) →
    ofBool (BitVec.ofInt 4 (-2) <ₛ x.sshiftRight' 1#4) = ofBool (BitVec.ofInt 4 (-4) <ₛ x)

theorem e_2419 :
     - 3 * ((d ||| e) &&&  ~~~(e ^^^ f)) + 3 * ( ~~~d ||| (e ^^^ f)) + 3 * (f &&&  ~~~(d ^^^ e)) + 1 * (f ^^^ ( ~~~d ||| ( ~~~e ||| f))) + 2 * ((d &&& f) ^^^  ~~~(e &&&  ~~~f)) - 2 *  ~~~(d ^^^ f) + 7 * (e ^^^ (d ||| (e ^^^ f))) - 7 *  ~~~d - 11 * ((d ||| e) &&& (d ^^^ (e ^^^ f))) + 4 * (e ^^^  ~~~(d ||| (e &&& f))) + 5 * ( ~~~d ||| ( ~~~e ||| f)) - 6 * (e ||| (d &&& f)) - 2 * (e ^^^  ~~~( ~~~d ||| (e ^^^ f))) - 1 * ((d &&& e) ^^^ (d ^^^ (e &&& f))) + 1 *  ~~~( ~~~d ||| (e &&& f)) + 11 * ((d ^^^ e) |||  ~~~(d ^^^ f)) + 1 * (f &&&  ~~~(d &&&  ~~~e)) + 1 * ((d ||| e) &&& (e ^^^ f)) - 1 * (e ^^^ (d &&& f)) - 1 * (f ^^^ (d &&&  ~~~e)) + 5 * (e &&&  ~~~(d &&& f)) + 11 * ( ~~~(d |||  ~~~e) |||  ~~~(e ^^^ f)) + 2 * (f ^^^ (d ||| e)) + 1 * (e ^^^ ( ~~~d ||| (e ^^^ f))) - 7 * ((d &&& e) |||  ~~~(e ||| f)) + 3 * ( ~~~d &&& (e ^^^ f)) - 11 * (f ^^^  ~~~(d ||| e)) - 1 * ( ~~~(d &&& e) &&&  ~~~(d ^^^ (e ^^^ f))) - 7 * ((d &&& f) |||  ~~~(e ||| f)) + 1 * ((e &&&  ~~~f) ^^^ ( ~~~d ||| (e ^^^ f))) - 5 * (d &&& e) + 3 *  ~~~(d ^^^ (e ||| f)) - 6 * (e ^^^  ~~~(d &&& f)) - 11 * (e &&&  ~~~(d ^^^ f)) - 7 * (f &&& (d ^^^ e)) - 3 * (d &&& f) - 2 * (e ||| (d &&&  ~~~f)) - 11 * (e ^^^  ~~~(d &&& (e &&& f))) - 2 * (e &&& f) - 7 *  ~~~(d &&&  ~~~e) + 2 * (e ^^^  ~~~( ~~~d &&& ( ~~~e ||| f))) + 2 * ( ~~~(d ^^^ e) &&&  ~~~(d ^^^ f)) - 3 * (d &&& (e ||| f)) - 1 * (d &&& ( ~~~e ||| f)) - 11 * (f ^^^ ( ~~~d ||| ( ~~~e &&& f))) + 4 * (f ^^^  ~~~(d |||  ~~~e)) + 1 * ((e &&&  ~~~f) |||  ~~~(d ||| ( ~~~e &&& f))) - 1 * ((d &&& e) |||  ~~~(e |||  ~~~f)) + 1 * (f ^^^ (d |||  ~~~e)) - 7 * (e ^^^  ~~~( ~~~d &&& ( ~~~e &&& f))) - 5 *  ~~~(e ^^^ f) + 2 * (f ||| (d &&&  ~~~e)) - 1 *  ~~~(e ||| f) + 5 * (e ^^^ ( ~~~d &&& (e ^^^ f))) - 2 * (e ^^^  ~~~(d ||| ( ~~~e &&& f))) + 1 * ((d &&& e) ||| (e ^^^ f)) - 1 * ( ~~~f |||  ~~~(d ^^^ e)) + 4 * ( ~~~(d |||  ~~~e) ||| (e ^^^ f)) + 2 * ((d &&& e) ||| (d ^^^ (e ^^^ f))) + 2 * (e ^^^  ~~~(d ||| f)) + 2 * ((d &&& f) ^^^ (d ^^^ (e &&& f))) - 2 * (f ^^^  ~~~(d &&& ( ~~~e &&& f))) - 5 * (e &&&  ~~~f) - 1 * (e ^^^  ~~~(d &&& (e ^^^ f))) + 4 * (f ^^^  ~~~(d &&& e)) - 5 *  ~~~(e |||  ~~~f) + 30 *  ~~~(d ||| (e ||| f)) + 10 *  ~~~(d ||| ( ~~~e ||| f)) + 16 *  ~~~( ~~~d ||| (e ||| f)) + 8 *  ~~~( ~~~d ||| ( ~~~e ||| f)) - 17 * ( ~~~d &&& ( ~~~e &&& f)) - 20 * ( ~~~d &&& (e &&& f)) + 23 * (d &&& ( ~~~e &&& f)) + 50 * (d &&& (e &&& f)) =  - 7 * ((d &&& e) ^^^ (d ^^^ ( ~~~e ||| f)))

theorem e_2309 :
     - 5 * ( ~~~(d &&& e) &&& (e ^^^ f)) + 3 * (f ^^^  ~~~(d &&& (e &&& f))) - 2 * ( ~~~e |||  ~~~(d ^^^ f)) + 5 * (f ^^^  ~~~( ~~~d &&& (e ||| f))) + 5 * (e ^^^  ~~~(d &&& f)) - 6 * (e ^^^ ( ~~~d &&& (e ^^^ f))) + 3 *  ~~~(d ||| (e ^^^ f)) - 1 * ((d &&& f) ^^^  ~~~(e &&&  ~~~f)) + 3 * (e ^^^ (d ||| (e ||| f))) - 3 * ((d &&& e) |||  ~~~(e ^^^ f)) - 7 * (f ^^^ (d ||| (e ||| f))) - 7 * ( ~~~f |||  ~~~(d ^^^ e)) - 5 * (e ||| (d &&&  ~~~f)) + 3 * (e &&& (d |||  ~~~f)) - 2 * (e ^^^  ~~~( ~~~d ||| (e &&& f))) - 1 * (f ^^^  ~~~(d ||| ( ~~~e &&& f))) - 3 * ((d ||| e) &&&  ~~~(d ^^^ (e ^^^ f))) - 1 * ((d ^^^ e) ||| (d ^^^ f)) + 7 *  ~~~(d ^^^ (e ||| f)) - 2 * ((e &&&  ~~~f) |||  ~~~( ~~~d ||| ( ~~~e &&& f))) - 3 * (e ^^^ ( ~~~d &&& (e ||| f))) + 11 * (f ^^^  ~~~(d &&& e)) - 1 * ( ~~~d &&& (e ^^^ f)) + 2 * (f ^^^ (d |||  ~~~e)) + 3 * d - 1 *  ~~~(d &&& f) + 4 *  ~~~(e &&&  ~~~f) + 3 * (d ^^^ e) + 7 *  ~~~( ~~~d ||| (e &&& f)) + 2 * (e ^^^ (d &&& (e ^^^ f))) - 6 * (d &&&  ~~~e) - 1 *  ~~~d + 1 * ( ~~~(d &&& e) &&&  ~~~(d ^^^ (e ^^^ f))) + 1 * (f ^^^ (d &&&  ~~~e)) + 1 * ((e &&&  ~~~f) |||  ~~~(d ||| ( ~~~e &&& f))) + 1 * (e ^^^  ~~~( ~~~d &&& ( ~~~e &&& f))) + 5 * (e ^^^ ( ~~~d ||| ( ~~~e ||| f))) - 7 * (d ||| f) + 2 *  ~~~(d |||  ~~~e) + 3 * (e ^^^  ~~~(d &&& (e ^^^ f))) + 1 *  ~~~(e ^^^ f) + 1 * (e ^^^  ~~~(d &&& (e ||| f))) - 2 * ((d &&& e) |||  ~~~(d ^^^ (e ^^^ f))) - 11 * (f ^^^ ( ~~~d &&& (e ||| f))) - 6 * (e &&&  ~~~f) + 1 * (d ^^^ ( ~~~e &&& f)) + 4 * ((d &&& f) ^^^ (d ^^^ ( ~~~e &&& f))) + 11 * (e |||  ~~~(d ^^^ f)) - 5 * ( ~~~(d ^^^ e) &&&  ~~~(d ^^^ f)) - 1 * (f ^^^  ~~~(d ||| (e &&& f))) - 7 * ((d |||  ~~~e) &&& (d ^^^ (e ^^^ f))) - 2 * ((d &&& e) ^^^  ~~~(d ^^^ ( ~~~e ||| f))) - 1 * (d ^^^ ( ~~~e ||| f)) + 11 * (e ^^^ ( ~~~d ||| (e &&& f))) + 1 * (e ^^^  ~~~(d ||| ( ~~~e &&& f))) - 51 *  ~~~(d ||| (e ||| f)) + 26 *  ~~~(d ||| ( ~~~e ||| f)) - 9 *  ~~~( ~~~d ||| (e ||| f)) - 12 *  ~~~( ~~~d ||| ( ~~~e ||| f)) + 7 * ( ~~~d &&& ( ~~~e &&& f)) - 1 * ( ~~~d &&& (e &&& f)) - 2 * (d &&& ( ~~~e &&& f)) + 17 * (d &&& (e &&& f)) = 1 * (e ^^^ (d &&&  ~~~f)) + 6 * (f ^^^  ~~~(d |||  ~~~e))

theorem test11_thm.extracted_1._2 : ∀ (x x_1 : BitVec 32),
  ¬zeroExtend 128 x &&& 31#128 ≥ ↑128 →
    ¬(True ∧ (x &&& 31#32).msb = true ∨
          True ∧
              (zeroExtend 64 x_1 <<< zeroExtend 64 (x &&& 31#32)).sshiftRight' (zeroExtend 64 (x &&& 31#32)) ≠
                zeroExtend 64 x_1 ∨
            True ∧
                zeroExtend 64 x_1 <<< zeroExtend 64 (x &&& 31#32) >>> zeroExtend 64 (x &&& 31#32) ≠ zeroExtend 64 x_1 ∨
              zeroExtend 64 (x &&& 31#32) ≥ ↑64) →
      truncate 64 (zeroExtend 128 x_1 <<< (zeroExtend 128 x &&& 31#128)) =
        zeroExtend 64 x_1 <<< zeroExtend 64 (x &&& 31#32)

theorem zext_sext_add_icmp_slt_minus1_thm (e e_1 : IntW 1) :
  icmp IntPred.slt (add (zext 8 e_1) (sext 8 e)) (const? 8 (-1)) ⊑ const? 1 0

theorem icmp_select_const_proof : icmp_select_const_before ⊑ icmp_select_const_after

theorem main14_thm.extracted_1._1 : ∀ (x : BitVec 32),
  ofBool (0#16 ≤ₛ truncate 16 x) &&& ofBool (0#8 ≤ₛ truncate 8 x) = 1#1 →
    ¬ofBool (x &&& 32896#32 == 0#32) = 1#1 → 2#32 = 1#32

theorem and_or_not_not_wrong_a_thm.extracted_1._1 : ∀ (x x_1 x_2 x_3 : BitVec 32),
  (x_3 &&& x_2 ^^^ -1#32 ||| x_1) &&& (x_1 &&& x ^^^ -1#32) = x_1 &&& x ^^^ (x_1 ||| x_3 &&& x_2 ^^^ -1#32)

theorem ne_21_comm_ne2_thm.extracted_1._2 : ∀ (x x_1 : BitVec 32),
  ¬(16#32 ≥ ↑32 ∨ 16#32 ≥ ↑32 ∨ 8#32 ≥ ↑32 ∨ 8#32 ≥ ↑32) →
    ¬(8#32 ≥ ↑32 ∨ 8#32 ≥ ↑32) →
      ofBool (truncate 8 (x_1 >>> 16#32) != truncate 8 (x >>> 16#32)) ||

theorem narrow_sext_sub_thm.extracted_1._1 : ∀ (x : BitVec 32) (x_1 : BitVec 16),
  truncate 16 (signExtend 32 x_1 - x) = x_1 - truncate 16 x

theorem or_and_shifts1_thm.extracted_1._2 : ∀ (x : BitVec 32),
  ¬(3#32 ≥ ↑32 ∨ 5#32 ≥ ↑32) →
    ¬(3#32 ≥ ↑32 ∨ 5#32 ≥ ↑32 ∨ True ∧ (x <<< 3#32 &&& 8#32 &&& (x <<< 5#32 &&& 32#32) != 0) = true) →
      x <<< 3#32 &&& 15#32 ||

theorem e_419 :
    4 * (x ||| y) - 1 *  ~~~y + 2 *  ~~~(x &&& y) + 3 *  ~~~(x &&&  ~~~y) - 4 *  ~~~(x ||| y) - 14 *  ~~~(x |||  ~~~y) - 10 * (x &&&  ~~~y) - 7 * (x &&& y) =  - 5 * (x ^^^ y)

lemma CNFA.autUnsignedCmp_spec {cmp} : (CNFA.autUnsignedCmp cmp).Sim (NFA'.autUnsignedCmp cmp)

theorem sge_swap_or_max_commute_proof : sge_swap_or_max_commute_before ⊑ sge_swap_or_max_commute_after

theorem e_1392 :
    7 * (z |||  ~~~t) - 11 * z + 2 *  ~~~t + 3 * (z ^^^ t) - 3 *  ~~~(z &&& t) + 1 *  ~~~(z &&&  ~~~z) - 2 * t + 12 *  ~~~(z |||  ~~~t) + 1 * (z &&&  ~~~t) + 5 * (z &&& t) =  - 4 *  ~~~(z ||| t) + 11 *  ~~~z

theorem or_lshr_thm.extracted_1._1 : ∀ (x x_1 x_2 x_3 : BitVec 8), ¬(x_2 ≥ ↑8 ∨ x_2 ≥ ↑8) → x_2 ≥ ↑8 → False

theorem test6_thm.extracted_1._1 : ∀ (x : BitVec 8), x ^^^ 17#8 ^^^ 17#8 = x

@[simp]
theorem eval_castCircLe_eq {n m : Nat} (c : Circuit (Vars fsm.α arity n))
    (hnm : n ≤ m)
    {env : Vars fsm.α arity m → Bool} :
    (castCircLe c hnm).eval env = c.eval
      (fun x => env (x.castLe hnm))

theorem srem_common_dividend_defined_cond_proof : srem_common_dividend_defined_cond_before ⊑ srem_common_dividend_defined_cond_after

theorem bools2_logical_commute0_and2_thm.extracted_1._8 : ∀ (x x_1 x_2 : BitVec 1), ¬x_2 = 1#1 → 0#1 = 1#1 → 1#1 = x

theorem sgt_swap_and_min_proof : sgt_swap_and_min_before ⊑ sgt_swap_and_min_after

theorem sge_swap_or_not_max_commute_logical_thm.extracted_1._1 : ∀ (x x_1 : BitVec 8),
  ¬ofBool (x_1 != 127#8) = 1#1 → ofBool (x ≤ₛ x_1) = 1#1

theorem narrow_sext_mul_proof : narrow_sext_mul_before ⊑ narrow_sext_mul_after

theorem ofBitVec_xor_congr (h1 : ofBitVecSext x ≈ʷ a) (h2 : ofBitVecSext y ≈ʷ b) : ofBitVecSext (x ^^^ y) ≈ʷ a ^^^ b

theorem xor_or2_proof : xor_or2_before ⊑ xor_or2_after

theorem zext_sext_add_icmp_eq_minus1_proof : zext_sext_add_icmp_eq_minus1_before ⊑ zext_sext_add_icmp_eq_minus1_after

theorem select_zext_or_eq_ult_add_thm.extracted_1._2 : ∀ (x : BitVec 32),
  ¬ofBool (x + BitVec.ofInt 32 (-3) <ᵤ 2#32) = 1#1 →
    zeroExtend 32 (ofBool (x == 5#32)) = zeroExtend 32 (ofBool (x + BitVec.ofInt 32 (-3) <ᵤ 3#32))

theorem shift_xor_multiuse_xor_proof : shift_xor_multiuse_xor_before ⊑ shift_xor_multiuse_xor_after

theorem same_source_matching_signbits_proof : same_source_matching_signbits_before ⊑ same_source_matching_signbits_after

theorem masked_or_allzeroes_thm.extracted_1._1 : ∀ (x : BitVec 32),
  ofBool (x &&& 7#32 == 0#32) ||

theorem logic_and_logic_or_7_thm.extracted_1._1 : ∀ (x : BitVec 1), ¬x = 1#1 → 0#1 = 1#1 → False

theorem main7b_logical_thm.extracted_1._9 : ∀ (x x_1 x_2 : BitVec 32),
  ¬ofBool (x_2 == x_1 &&& x_2) = 1#1 → ofBool (x_2 != x_1 &&& x_2) = 1#1 → 0#1 = 1#1 → 0#32 = zeroExtend 32 1#1

@[bv_multi_width_normalize] theorem BitVec.nat_mul_eq_ofNat_mul (x : BitVec w) (n : Nat) :
  n * x = BitVec.ofNat w n * x

theorem lshrult_03_00_exact_thm.extracted_1._1 : ∀ (x : BitVec 4),
  ¬(True ∧ x >>> 3#4 <<< 3#4 ≠ x ∨ 3#4 ≥ ↑4) → ofBool (x >>> 3#4 <ᵤ 0#4) = 0#1

theorem sge_and_max_proof : sge_and_max_before ⊑ sge_and_max_after

theorem ne_smin2_thm.extracted_1._1 : ∀ (x x_1 : BitVec 32),
  ofBool (x_1 <ₛ x) = 1#1 → ofBool (x_1 != x) = ofBool (x_1 <ₛ x)

theorem lshrult_01_11_proof : lshrult_01_11_before ⊑ lshrult_01_11_after

theorem e_1451 :
     - 6 * (z |||  ~~~t) - 11 *  ~~~z - 1 *  ~~~(z &&&  ~~~t) - 7 * (z ||| t) - 6 *  ~~~(z &&& t) + 2 *  ~~~t + 22 *  ~~~(z ||| t) + 14 *  ~~~(z |||  ~~~t) + 6 * (z &&&  ~~~t) + 14 * (z &&& t) =  - 11 * (z ^^^ t)

theorem lshrugt_03_11_exact_proof : lshrugt_03_11_exact_before ⊑ lshrugt_03_11_exact_after

theorem uge_umin3_proof : uge_umin3_before ⊑ uge_umin3_after

theorem ne_10_thm.extracted_1._1 : ∀ (x x_1 : BitVec 32),
  ¬(8#32 ≥ ↑32 ∨ 8#32 ≥ ↑32) →
    ofBool (truncate 8 x_1 != truncate 8 x) ||

@[simp, grind=] theorem getElem_ofList (i : Nat) (h : _) : (ofList ts)[i]'h = ts[i]'h

@[simp]
theorem Expr.regArgs_mk {Γ : Ctxt d.Ty} {ty eff op}
    (ty_eq : ty = DialectSignature.returnTypes op)
    (eff_le : DialectSignature.effectKind op ≤ eff)
    (args : HVector (Var Γ) (DialectSignature.sig op)) (regArgs) :
    (Expr.mk op ty_eq eff_le args regArgs).regArgs = regArgs

theorem e_1553 :
     - 6 *  ~~~(a ^^^ c) - 1 * (b ^^^  ~~~( ~~~a &&& ( ~~~b ||| c))) - 5 * (b ^^^  ~~~(a &&& ( ~~~b &&& c))) - 1 * (b ||| (a ^^^ c)) - 1 *  ~~~( ~~~a &&& ( ~~~b ||| c)) + 5 * ( ~~~a &&& (b ||| c)) - 5 * ((a &&& c) ||| (b &&&  ~~~c)) + 12 *  ~~~(a ||| (b ||| c)) + 8 *  ~~~(a ||| ( ~~~b ||| c)) + 8 *  ~~~( ~~~a ||| (b ||| c)) + 8 *  ~~~( ~~~a ||| ( ~~~b ||| c)) - 3 * ( ~~~a &&& (b &&& c)) + 13 * (a &&& ( ~~~b &&& c)) + 14 * (a &&& (b &&& c)) =  - 2 * ( ~~~a &&& ( ~~~b &&& c)) + 1 *  ~~~(a ^^^ b)

theorem n0_thm.extracted_1._1 : ∀ (x : BitVec 8), ofBool (x ≤ᵤ x &&& 4#8) = ofBool (x &&& BitVec.ofInt 8 (-5) == 0#8)

theorem lt_signed_to_small_signed_thm (e : IntW 8) :
  icmp IntPred.slt (sext 32 e) (const? 32 17) ⊑ icmp IntPred.slt e (const? 8 17)

theorem hoist_ashr_ahead_of_sext_2_thm (e : IntW 8) : ashr (sext 32 e) (const? 32 8) ⊑ sext 32 (ashr e (const? 8 7))

theorem neg_test_icmp_non_equality_thm (e : IntW 32) :
  select (icmp IntPred.slt (LLVM.and e (const? 32 1073741823)) (const? 32 0)) (const? 32 0) (shl e (const? 32 2)) ⊑
    shl e (const? 32 2)

theorem ne_rem_zero_nonuw_proof : ne_rem_zero_nonuw_before ⊑ ne_rem_zero_nonuw_after

theorem shl_or_thm.extracted_1._2 : ∀ (x x_1 : BitVec 16),
  ¬((42#16 == 0 || 16 != 1 && x_1 == intMin 16 && 42#16 == -1) = true ∨ 5#16 ≥ ↑16 ∨ 7#16 ≥ ↑16) →
    ¬(12#16 ≥ ↑16 ∨
          (42#16 == 0 || 16 != 1 && x_1 == intMin 16 && 42#16 == -1) = true ∨
            True ∧ (x_1.srem 42#16 <<< 7#16).sshiftRight' 7#16 ≠ x_1.srem 42#16 ∨ 7#16 ≥ ↑16) →
      (x_1.srem 42#16 ||| x <<< 5#16) <<< 7#16 = x <<< 12#16 ||

theorem must_drop_poison_proof : must_drop_poison_before ⊑ must_drop_poison_after

theorem trunc_sel_equal_sext_thm.extracted_1._4 : ∀ (x : BitVec 32) (x_1 : BitVec 1),
  ¬x_1 = 1#1 → signExtend 32 42#16 = 42#32

@[simp] theorem HVector.denote_nil
    (T : HVector (fun (t : Ctxt d.Ty × List d.Ty) => Com d t.1 .impure t.2) []) :
    HVector.denote T = HVector.nil

@[simp] theorem denote_mk {lets : Lets d Γ_in eff Γ_out} {com : Com d Γ_out eff ty} :
    denote ⟨lets, com⟩ = fun V => (lets.denote V) >>= com.denote

theorem lshr_eq_msb_low_last_zero_proof : lshr_eq_msb_low_last_zero_before ⊑ lshr_eq_msb_low_last_zero_after

theorem sub_sext_mask1_trunc_lshr_thm.extracted_1._1 : ∀ (x : BitVec 64),
  ¬15#64 ≥ ↑64 →
    48#64 ≥ ↑64 ∨
        63#64 ≥ ↑64 ∨
          True ∧ signExtend 64 (truncate 8 ((x <<< 48#64).sshiftRight' 63#64)) ≠ (x <<< 48#64).sshiftRight' 63#64 ∨
            True ∧ (truncate 8 ((x <<< 48#64).sshiftRight' 63#64)).saddOverflow 10#8 = true →
      False

theorem ashrslt_02_05_proof : ashrslt_02_05_before ⊑ ashrslt_02_05_after

theorem select_icmp_ne_0_and_8_xor_1073741824_thm.extracted_1._2 : ∀ (x : BitVec 32) (x_1 : BitVec 8),
  ¬ofBool (0#8 != x_1 &&& 8#8) = 1#1 → ¬ofBool (x_1 &&& 8#8 == 0#8) = 1#1 → x ^^^ 1073741824#32 = x

theorem and_xor_commute3_thm (e e_1 : IntW 32) :
  LLVM.xor (LLVM.and (LLVM.udiv (const? 32 42) e_1) (LLVM.udiv (const? 32 42) e)) (LLVM.udiv (const? 32 42) e_1) ⊑
    LLVM.and (LLVM.udiv (const? 32 42) e_1) (LLVM.xor (LLVM.udiv (const? 32 42) e) (const? 32 (-1)))

theorem ashrsgt_01_06_proof : ashrsgt_01_06_before ⊑ ashrsgt_01_06_after

theorem and_zext_commuted_proof : and_zext_commuted_before ⊑ and_zext_commuted_after

theorem e_553 :
    11 *  ~~~(x &&&  ~~~x) + 1 * y + 2 * x + 5 *  ~~~(x &&&  ~~~y) + 1 * (x |||  ~~~y) - 4 *  ~~~(x ||| y) - 6 *  ~~~(x |||  ~~~y) - 1 * (x &&&  ~~~y) - 20 * (x &&& y) = 11 *  ~~~(x &&& y) + 2 *  ~~~y

theorem test_with_3_thm.extracted_1._1 : ∀ (x : BitVec 32),
  ¬x ≥ ↑32 → 3#32 <<< x &&& 1#32 = zeroExtend 32 (ofBool (x == 0#32))

theorem and_two_ranges_to_mask_and_range_not_pow2_diff_thm (e : IntW 8) :
  LLVM.and (icmp IntPred.ugt (add e (const? 8 (-97))) (const? 8 25))
      (icmp IntPred.ugt (add e (const? 8 (-64))) (const? 8 25)) ⊑
    LLVM.and (icmp IntPred.ult (add e (const? 8 (-123))) (const? 8 (-26)))
      (icmp IntPred.ult (add e (const? 8 (-90))) (const? 8 (-26)))

theorem e_1387 :
     - 2 *  ~~~z - 6 * t + 1 *  ~~~(z &&& t) - 1 * (z ||| t) - 7 *  ~~~(z &&&  ~~~t) + 4 * z - 1 * (z ^^^ t) + 12 *  ~~~(z ||| t) + 19 *  ~~~(z |||  ~~~t) + 14 * (z &&& t) = 1 *  ~~~(z ^^^ t) + 3 *  ~~~(z &&&  ~~~z)

theorem uadd_sat_canon_nuw_thm.extracted_1._1 : ∀ (x x_1 : BitVec 32),
  ¬(True ∧ x_1.uaddOverflow x = true) → ofBool (x_1 + x <ᵤ x_1) = 1#1 → -1#32 = x_1 + x

theorem rewrite_n (stream_d : DCOp.TokenStream) :
    DCOp.sink ((DCOp.fork stream_d).fst) = DCOp.sink stream_d

theorem bv_AndOrXor_1288_A__B__B__C__A___A__B__C :
    ∀ (e e_1 e_2 : LLVM.IntW w),
      LLVM.and (LLVM.xor e e_2) (LLVM.xor (LLVM.xor e_2 e_1) e) ⊑
        LLVM.and (LLVM.xor e e_2) (LLVM.xor e_1 (LLVM.const? w (-1)))

theorem or_ashr_not_commuted_thm (e e_1 e_2 : IntW 8) :
  LLVM.or (LLVM.xor (ashr e_2 e_1) (const? 8 (-1))) (ashr e e_1) ⊑
    ashr (LLVM.or e (LLVM.xor e_2 (const? 8 (-1)))) e_1

theorem zext_nneg_redundant_and_proof : zext_nneg_redundant_and_before ⊑ zext_nneg_redundant_and_after

theorem test_sub__all_are_safe_thm.extracted_1._3 : ∀ (x : BitVec 32),
  ¬ofBool (x &&& 255#32 == 6#32) = 1#1 →
    True ∧ (BitVec.ofInt 32 (-254)).ssubOverflow (x &&& 255#32) = true ∨
        True ∧ (BitVec.ofInt 32 (-254)).usubOverflow (x &&& 255#32) = true →
      False

theorem icmp_equality_test_wrong_and_thm.extracted_1._1 : ∀ (x x_1 x_2 : BitVec 64),
  ¬ofBool (x_2 == x_1) = 1#1 → ofBool (x == x_1) ^^^ 1#1 = 1#1 → ofBool (x == x_1) = 1#1 → 0#1 = ofBool (x_2 == x)

theorem e_604 :
     - 1 *  ~~~y - 1 * y + 3 * (x ^^^ y) - 7 *  ~~~(x &&& y) - 2 * x - 1 *  ~~~(x ^^^ y) + 1 * (x ||| y) - 1 * (x |||  ~~~y) + 6 *  ~~~(x ||| y) + 3 * (x &&&  ~~~y) =  - 4 *  ~~~(x &&&  ~~~x)

theorem main12_logical_thm (e : IntW 32) :
  select
      (select (icmp IntPred.slt (trunc 16 e) (const? 16 0)) (const? 1 1)
        (icmp IntPred.slt (trunc 8 e) (const? 8 0)))
      (const? 32 2) (const? 32 1) ⊑
    select (icmp IntPred.eq (LLVM.and e (const? 32 32896)) (const? 32 0)) (const? 32 1) (const? 32 2)

theorem and_xor_common_op_thm.extracted_1._1 : ∀ (x x_1 : BitVec 32),
  ¬(x_1 = 0 ∨ x_1 = 0 ∨ x = 0) → x_1 = 0 ∨ x = 0 → False

theorem main14_logical_thm.extracted_1._1 : ∀ (x : BitVec 32),
  ofBool (0#16 ≤ₛ truncate 16 x) = 1#1 →
    ofBool (x &&& 32896#32 == 0#32) = 1#1 → ¬ofBool (0#8 ≤ₛ truncate 8 x) = 1#1 → 1#32 = 2#32

theorem is_ascii_alphabetic_inverted_thm.extracted_1._1 : ∀ (x : BitVec 32),
  ¬(True ∧ x.saddOverflow (BitVec.ofInt 32 (-91)) = true) →
    ofBool (x + BitVec.ofInt 32 (-91) <ᵤ BitVec.ofInt 32 (-26)) = 1#1 →
      ¬(True ∧ x.saddOverflow (BitVec.ofInt 32 (-123)) = true) →
        ofBool (x + BitVec.ofInt 32 (-123) <ᵤ BitVec.ofInt 32 (-26)) =
          ofBool ((x &&& BitVec.ofInt 32 (-33)) + BitVec.ofInt 32 (-91) <ᵤ BitVec.ofInt 32 (-26))

theorem generic (p q r : Nat) (hpq : p ≤ q) (hpr : p ≤ r) (hqr : q ≤ r) : 
    ∀ (x : BitVec p) (y : BitVec q),
  (signExtend r y = signExtend r x) ↔ (y = signExtend q x)

theorem exact_ashr_ne_both_equal_thm.extracted_1._1 : ∀ (x : BitVec 8),
  ¬(True ∧ BitVec.ofInt 8 (-128) >>> x <<< x ≠ BitVec.ofInt 8 (-128) ∨ x ≥ ↑8) →
    ofBool ((BitVec.ofInt 8 (-128)).sshiftRight' x != BitVec.ofInt 8 (-128)) = ofBool (x != 0#8)

theorem Std.HashMap.fold_induction [BEq α] [LawfulBEq α] [DecidableEq α] [Hashable α]
  {f : γ → α → β → γ} {m : HashMap α β} {motive : γ → (α → Option β) → Prop} :
    motive b (λ _ ↦ none) →
    (∀ b x y m, m x = none → motive b m → motive (f b x y) (Function.update m x y)) →
    motive (m.fold f b) m.toPFun

theorem test51_thm.extracted_1._1 : ∀ (x : BitVec 64) (x_1 : BitVec 1),
  x_1 = 1#1 → True ∧ (truncate 32 x &&& BitVec.ofInt 32 (-2) &&& zeroExtend 32 (x_1 ^^^ 1#1) != 0) = true → False

theorem masked_icmps_mask_notallzeros_bmask_mixed_swapped_5_proof : masked_icmps_mask_notallzeros_bmask_mixed_swapped_5_before ⊑ masked_icmps_mask_notallzeros_bmask_mixed_swapped_5_after

theorem test19_proof : test19_before ⊑ test19_after

theorem test3_proof : test3_before ⊑ test3_after

theorem udiv_mul_shl_nuw_exact_commute1_thm.extracted_1._1 : ∀ (x x_1 x_2 : BitVec 5),
  ¬(True ∧ x_2.umulOverflow x_1 = true ∨
        True ∧ x_1 <<< x >>> x ≠ x_1 ∨ x ≥ ↑5 ∨ True ∧ (x_2 * x_1).umod (x_1 <<< x) ≠ 0 ∨ x_1 <<< x = 0) →
    True ∧ x_2 >>> x <<< x ≠ x_2 ∨ x ≥ ↑5 → False

theorem test_const_shr_exact_and_1_ne_0_proof : test_const_shr_exact_and_1_ne_0_before ⊑ test_const_shr_exact_and_1_ne_0_after

theorem masked_icmps_mask_notallzeros_bmask_mixed_swapped_5_thm.extracted_1._1 : ∀ (x : BitVec 32),
  ofBool (x &&& 15#32 == 8#32) &&& ofBool (x &&& 15#32 != 0#32) = ofBool (x &&& 15#32 == 8#32)

theorem n1_thm.extracted_1._1 : ∀ (x x_1 : BitVec 8), ¬x_1 ≥ ↑8 → True ∧ 1#8 <<< x_1 >>> x_1 ≠ 1#8 ∨ x_1 ≥ ↑8 → False

theorem masked_icmps_mask_notallzeros_bmask_mixed_negated_swapped_1b_logical_thm.extracted_1._1 : ∀ (x : BitVec 32),
  ofBool (x &&& 3#32 != 1#32) = 1#1 → 1#1 = ofBool (x &&& 3#32 != 1#32) ||

theorem test_thm (e e_1 : IntW 32) :
  LLVM.or (icmp IntPred.slt e_1 e) (icmp IntPred.eq e_1 e) ⊑ icmp IntPred.sle e_1 e

theorem t10_constants_proof : t10_constants_before ⊑ t10_constants_after

theorem sext_sub_const_thm.extracted_1._1 : ∀ (x : BitVec 1), x = 1#1 → 42#64 - signExtend 64 x = 43#64

theorem icmp_eq_and_pow2_shl_pow2_negative2_thm.extracted_1._1 : ∀ (x : BitVec 32),
  ¬x ≥ ↑32 → zeroExtend 32 (ofBool (2#32 <<< x &&& 14#32 == 0#32)) = zeroExtend 32 (ofBool (2#32 <ᵤ x))

theorem and_ashr_not_commuted_proof : and_ashr_not_commuted_before ⊑ and_ashr_not_commuted_after

theorem test_thm (e e_1 : IntW 8) :
  icmp IntPred.sgt (zext 32 e_1) (zext 32 e) ⊑ icmp IntPred.ugt e_1 e

theorem ofBitVec_add_congr (h1 : ofBitVecSext x ≈ʷ a) (h2 : ofBitVecSext y ≈ʷ b) : ofBitVecSext (x + y) ≈ʷ a + b

theorem ashrslt_01_11_thm.extracted_1._1 : ∀ (x : BitVec 4),
  ¬1#4 ≥ ↑4 → ofBool (x.sshiftRight' 1#4 <ₛ BitVec.ofInt 4 (-5)) = 0#1

theorem t9_c0_c2_thm (e : IntW 8) : sub (sub (const? 8 42) e) (const? 8 24) ⊑ sub (const? 8 18) e

@[simp, simp_denote] theorem not_nil_isRefinedBy_cons : ¬((nil : HVector A _) ⊑ (y ::ₕ ys))

theorem or_consts_thm.extracted_1._1 : ∀ (x : BitVec 32),
  ofBool (4#32 &&& x != 0#32) &&& ofBool (8#32 &&& x != 0#32) = ofBool (x &&& 12#32 == 12#32)

lemma CNFA.recognizes_functional {m : CNFA n} :
    m.recognizes L₁ → m.recognizes L₂ → L₁ = L₂

theorem main7a_logical_thm.extracted_1._6 : ∀ (x x_1 x_2 : BitVec 32),
  ofBool (x_2 &&& x_1 == x_2) = 1#1 →
    ofBool (x_2 &&& x_1 != x_2) = 1#1 → ¬ofBool (x &&& x_1 == x) = 1#1 → 1#32 = zeroExtend 32 1#1

theorem test_proof : test_before ⊑ test_after

theorem icmp_ult_x_y_thm.extracted_1._1 : ∀ (x x_1 : BitVec 8), ofBool (x_1 &&& x <ᵤ x_1) = ofBool (x_1 &&& x != x_1)

theorem e_1948 :
     - 2 * (b &&&  ~~~(a &&& c)) + 4 * ((a &&& b) |||  ~~~(b |||  ~~~c)) + 2 * (a ||| b) - 1 * (b ^^^ (a ||| ( ~~~b ||| c))) + 3 *  ~~~(a &&&  ~~~c) + 5 * ( ~~~b &&&  ~~~(a ^^^ c)) + 2 *  ~~~(a ^^^ (b &&& c)) + 7 * (a &&& (b ||| c)) + 1 * ( ~~~(a &&&  ~~~b) &&&  ~~~(b ^^^ c)) - 3 *  ~~~(a ^^^ ( ~~~b ||| c)) + 4 * ((b &&&  ~~~c) |||  ~~~( ~~~a ||| ( ~~~b &&& c))) - 5 * (b ^^^ ( ~~~a ||| ( ~~~b ||| c))) - 2 * (c |||  ~~~(a ^^^ b)) - 5 * (c &&& (a ||| b)) + 1 * (b ^^^  ~~~(a &&&  ~~~c)) - 1 * ((b &&& c) ||| ( ~~~a &&& (b ||| c))) - 1 * ((a |||  ~~~b) &&& (a ^^^ (b ^^^ c))) + 11 * (b ^^^  ~~~(a ||| c)) - 5 * (b ||| (a ^^^ c)) + 1 * a - 2 * ((a &&& c) ^^^  ~~~(a ^^^ ( ~~~b &&& c))) - 1 * (a ||| (b &&& c)) - 1 * (b ^^^ (a ||| ( ~~~b &&& c))) + 2 * (a ||| (b ||| c)) + 11 *  ~~~(a |||  ~~~c) - 6 * ( ~~~(a ||| b) |||  ~~~(a ^^^ (b ^^^ c))) - 11 * (a ||| ( ~~~b ||| c)) - 6 * ( ~~~(a |||  ~~~b) |||  ~~~(a ^^^ (b ^^^ c))) + 11 * (b ^^^  ~~~(a |||  ~~~c)) - 2 * ( ~~~b |||  ~~~(a ^^^ c)) - 3 * ( ~~~a ||| ( ~~~b ||| c)) - 5 * (c ^^^ ( ~~~a ||| (b ||| c))) + 2 * (b ^^^  ~~~(a &&& (b ^^^ c))) + 2 * ( ~~~a &&& (b ^^^ c)) - 1 * ( ~~~(a ^^^ b) &&& (a ^^^ c)) + 3 * ( ~~~(a |||  ~~~b) ||| (a ^^^ (b ^^^ c))) - 2 * ((a ||| b) &&& (a ^^^ (b ^^^ c))) - 3 * (a ^^^ (b ||| c)) - 11 * ((a &&& b) |||  ~~~(a ^^^ (b ^^^ c))) - 1 * (a &&& c) + 7 * (b |||  ~~~(a ||| c)) - 2 * ((a &&& c) ^^^  ~~~(a ^^^ (b &&& c))) - 2 * (b ^^^ (a ||| (b &&& c))) + 7 * ( ~~~(a &&&  ~~~b) &&& (b ^^^ c)) + 3 * (b ^^^ (a |||  ~~~c)) + 27 *  ~~~(a ||| (b ||| c)) + 3 *  ~~~(a ||| ( ~~~b ||| c)) + 29 *  ~~~( ~~~a ||| (b ||| c)) + 2 *  ~~~( ~~~a ||| ( ~~~b ||| c)) - 4 * ( ~~~a &&& ( ~~~b &&& c)) + 16 * ( ~~~a &&& (b &&& c)) + 34 * (a &&& ( ~~~b &&& c)) - 8 * (a &&& (b &&& c)) = 6 *  ~~~c

theorem fold_add_udiv_urem_without_noundef_thm.extracted_1._2 : ∀ (x : BitVec 32),
  ¬(10#32 = 0 ∨ 4#32 ≥ ↑32 ∨ 10#32 = 0) →
    ¬(10#32 = 0 ∨ 4#32 ≥ ↑32 ∨ 10#32 = 0 ∨ True ∧ ((x / 10#32) <<< 4#32 &&& x % 10#32 != 0) = true) →
      (x / 10#32) <<< 4#32 + x % 10#32 = (x / 10#32) <<< 4#32 ||

theorem sub_1_proof : sub_1_before ⊑ sub_1_after

theorem ashr_ult_10_proof : ashr_ult_10_before ⊑ ashr_ult_10_after

theorem select_add_icmp_bad_thm.extracted_1._1 : ∀ (x x_1 : BitVec 32),
  ofBool (x_1 == 1#32) = 1#1 → x_1 + x = x + 1#32

theorem sle_smax4_thm (e e_1 : IntW 32) :
  icmp IntPred.sge (add e_1 (const? 32 3))
      (select (icmp IntPred.sgt e (add e_1 (const? 32 3))) e (add e_1 (const? 32 3))) ⊑
    icmp IntPred.sle e (add e_1 (const? 32 3))

theorem ashr_and_icmp_sge_neg1_i64_thm.extracted_1._1 : ∀ (x : BitVec 64),
  ¬63#64 ≥ ↑64 → x.sshiftRight' 63#64 &&& zeroExtend 64 (ofBool (-1#64 ≤ₛ x)) = zeroExtend 64 (ofBool (x == -1#64))

theorem test7_thm.extracted_1._1 : ∀ (x : BitVec 32), x &&& (x ^^^ -1#32) = 0#32

theorem slt_swap_or_not_max_commute_proof : slt_swap_or_not_max_commute_before ⊑ slt_swap_or_not_max_commute_after

theorem widget_thm (e : IntW 32) :
  mul
      (add (mul (const? 32 20) (sub (const? 32 2) (zext 32 (icmp IntPred.eq e (const? 32 0)))))
        (LLVM.xor (zext 32 (icmp IntPred.eq e (const? 32 0))) (const? 32 1)))
      (sub (const? 32 2) (zext 32 (icmp IntPred.eq e (const? 32 0)))) ⊑
    shl
      (LLVM.or (shl (const? 32 20) (zext 32 (icmp IntPred.ne e (const? 32 0))) { «nsw» := true, «nuw» := true })
        (zext 32 (icmp IntPred.ne e (const? 32 0))) { «disjoint» := true })
      (zext 32 (icmp IntPred.ne e (const? 32 0))) { «nsw» := true, «nuw» := true }

theorem reused_mul_nuw_xy_z_selectnonzero_ugt_thm.extracted_1._5 : ∀ (x x_1 x_2 : BitVec 8),
  ofBool (x_2 != 0#8) = 1#1 →
    ¬(True ∧ x_1.umulOverflow x_2 = true ∨ True ∧ x.umulOverflow x_2 = true) →
      ofBool (x_2 == 0#8) = 1#1 → ofBool (x * x_2 <ᵤ x_1 * x_2) = 1#1

theorem n0_thm (e : IntW 8) :
  icmp IntPred.ult (LLVM.and e (const? 8 4)) e ⊑
    icmp IntPred.ne (LLVM.and e (const? 8 (-5))) (const? 8 0)

theorem ule_or_min_logical_proof : ule_or_min_logical_before ⊑ ule_or_min_logical_after

theorem and_orn_cmp_3_proof : and_orn_cmp_3_before ⊑ and_orn_cmp_3_after

theorem sextinreg2_thm.extracted_1._2 : ∀ (x : BitVec 32),
  ¬(24#32 ≥ ↑32 ∨ True ∧ x <<< 24#32 >>> 24#32 <<< 24#32 ≠ x <<< 24#32 ∨ 24#32 ≥ ↑32) →
    (x &&& 255#32 ^^^ 128#32) + BitVec.ofInt 32 (-128) = (x <<< 24#32).sshiftRight' 24#32

theorem n5_thm.extracted_1._4 : ∀ (x : BitVec 32),
  ¬ofBool (x &&& 2#32 == 0#32) = 1#1 → ¬1#32 ≥ ↑32 → 1#32 = x >>> 1#32 &&& 1#32

theorem test15a_proof : test15a_before ⊑ test15a_after

theorem sub_2_thm.extracted_1._4 : ∀ (x x_1 : BitVec 8) (x_2 : BitVec 1) (x_3 : BitVec 8),
  ¬x_2 = 1#1 → x_3 - (x ^^^ 123#8) ^^^ -1#8 = BitVec.ofInt 8 (-2) - ((x ^^^ BitVec.ofInt 8 (-124)) + x_3)

theorem e_80 :
     - 5 *  ~~~(x &&&  ~~~x) - 7 *  ~~~(x ^^^ y) + 4 *  ~~~(x |||  ~~~y) + 5 * (x &&&  ~~~y) + 11 * (x &&& y) =  - 1 *  ~~~(x &&&  ~~~y) - 11 *  ~~~(x ||| y)

theorem gt_signed_to_small_signed_thm.extracted_1._1 : ∀ (x : BitVec 8),
  ofBool (17#32 <ₛ signExtend 32 x) = ofBool (17#8 <ₛ x)

theorem lor_band_right2_thm (e e_1 : IntW 1) : LLVM.and e_1 (select e (const? 1 1) e_1) ⊑ e_1

theorem land_lor_right1_thm.extracted_1._3 : ∀ (x x_1 : BitVec 1), x_1 = 1#1 → 1#1 = x_1

theorem i_thm (e : IntW 8) :
  LLVM.sdiv (LLVM.sdiv e (const? 8 (-3))) (const? 8 (-3)) ⊑ LLVM.sdiv e (const? 8 9)

theorem icmp_eq_mul_nuw_nonequal_proof : icmp_eq_mul_nuw_nonequal_before ⊑ icmp_eq_mul_nuw_nonequal_after

theorem select_1_thm.extracted_1._6 : ∀ (x : BitVec 8) (x_1 : BitVec 1) (x_2 x_3 : BitVec 8) (x_4 : BitVec 1),
  x_4 = 1#1 → x_3 ^^^ (x_2 ^^^ 45#8) ^^^ -1#8 = x_2 ^^^ x_3 ^^^ BitVec.ofInt 8 (-46)

theorem t11_no_shift_thm.extracted_1._1 : ∀ (x : BitVec 64) (x_1 x_2 : BitVec 32),
  ¬(64#32 - x_1 ≥ ↑32 ∨ zeroExtend 64 (x_1 + BitVec.ofInt 32 (-64)) ≥ ↑64) →
    ofBool (x_2 <<< (64#32 - x_1) &&& truncate 32 (x >>> zeroExtend 64 (x_1 + BitVec.ofInt 32 (-64))) != 0#32) =
      ofBool (x &&& zeroExtend 64 x_2 != 0#64)

theorem n10_wrong_low_bit_mask_thm (e : IntW 8) :
  select (icmp IntPred.eq (LLVM.and e (const? 8 31)) (const? 8 0)) e
      (LLVM.and (add e (const? 8 16)) (const? 8 (-16))) ⊑
    select (icmp IntPred.eq (LLVM.and e (const? 8 31)) (const? 8 0)) e
      (add (LLVM.and e (const? 8 (-16))) (const? 8 16))

theorem udiv_exact_ne_30_no_of_proof : udiv_exact_ne_30_no_of_before ⊑ udiv_exact_ne_30_no_of_after

theorem bar_proof : bar_before ⊑ bar_after

theorem masked_and_notA_slightly_optimized_proof : masked_and_notA_slightly_optimized_before ⊑ masked_and_notA_slightly_optimized_after

theorem test_thm.extracted_1._2 : ∀ (x : BitVec 32),
  ¬(17#32 ≥ ↑32 ∨ 17#32 ≥ ↑32) → ¬31#32 ≥ ↑32 → (x.sshiftRight' 17#32).sshiftRight' 17#32 = x.sshiftRight' 31#32

theorem logical_and_not_cond_reuse_thm.extracted_1._4 : ∀ (x x_1 : BitVec 1),
  ¬x_1 = 1#1 → x_1 ^^^ 1#1 = 1#1 → x_1 ^^^ 1#1 = 1#1

theorem e_962 :
     - 1 *  ~~~(z &&& t) + 7 *  ~~~(z ^^^ t) + 5 * (z ^^^ t) - 4 *  ~~~(z ||| t) - 4 * (z &&&  ~~~t) - 5 * (z &&& t) = 2 *  ~~~(z &&&  ~~~t) + 2 *  ~~~(z |||  ~~~t)

theorem e_2246 :
    4 * (e ^^^ ( ~~~d ||| ( ~~~e &&& f))) - 2 * (e ^^^ ( ~~~d &&& (e ||| f))) - 3 * e + 1 *  ~~~( ~~~d &&& (e &&& f)) + 5 * (e |||  ~~~(d ||| f)) + 4 * (f ^^^  ~~~(d &&& (e &&& f))) + 3 * (d ||| e) + 11 *  ~~~(d ^^^ (e ^^^ f)) + 2 * (e ^^^ (d ||| ( ~~~e &&& f))) + 1 * (d ||| (e ^^^ f)) + 1 *  ~~~(d ||| ( ~~~e &&& f)) + 7 * (d ^^^ ( ~~~e ||| f)) - 11 * (f ^^^ (d &&&  ~~~e)) - 7 * ((d &&& e) ^^^  ~~~(d ^^^ ( ~~~e ||| f))) - 1 *  ~~~( ~~~d &&& ( ~~~e &&& f)) + 5 * (e &&& (d ^^^ f)) - 2 *  ~~~(d &&& (e ||| f)) + 7 * (e ^^^  ~~~( ~~~d &&& (e ||| f))) + 5 * (f ^^^  ~~~(d ||| ( ~~~e &&& f))) + 4 * (e &&& (d |||  ~~~f)) + 1 * (f ||| (d ^^^ e)) + 2 * ( ~~~f |||  ~~~(d ^^^ e)) + 3 *  ~~~(e &&& f) + 1 * ((e &&&  ~~~f) |||  ~~~( ~~~d ||| ( ~~~e &&& f))) + 2 * (d &&&  ~~~f) - 3 * (e ^^^ ( ~~~d &&& (e ^^^ f))) - 1 * (f |||  ~~~(d ^^^ e)) + 1 * ( ~~~e |||  ~~~(d ^^^ f)) + 1 * (e ||| (d ^^^ f)) - 2 * ((d &&&  ~~~e) ||| (d ^^^ (e ^^^ f))) - 3 * ((d &&&  ~~~e) ||| (e ^^^ f)) + 1 * (f &&&  ~~~(d &&&  ~~~e)) - 5 * ( ~~~(d ^^^ e) ||| (d ^^^ f)) + 11 * ((d &&& e) ^^^ (e |||  ~~~f)) - 1 * ( ~~~(d ||| e) ||| (e ^^^ f)) + 7 * (f ^^^  ~~~(d |||  ~~~e)) - 3 * (f ^^^ (d &&& e)) - 2 * ( ~~~(d ||| e) |||  ~~~(d ^^^ (e ^^^ f))) + 1 * (d ||| ( ~~~e &&& f)) + 11 * (d &&& f) - 2 * (d ||| f) + 2 * (f &&& (d ^^^ e)) - 11 * (f ^^^  ~~~( ~~~d ||| ( ~~~e &&& f))) - 6 * (d ^^^ e) + 3 * (e ^^^  ~~~(d &&&  ~~~f)) + 11 * (f ^^^ (d ||| ( ~~~e &&& f))) + 3 *  ~~~(d ^^^ ( ~~~e ||| f)) - 7 * ((d &&& f) ^^^  ~~~(e &&&  ~~~f)) + 11 * ((d |||  ~~~e) &&& (e ^^^ f)) - 47 *  ~~~(d ||| (e ||| f)) - 39 *  ~~~(d ||| ( ~~~e ||| f)) + 2 *  ~~~( ~~~d ||| (e ||| f)) - 36 *  ~~~( ~~~d ||| ( ~~~e ||| f)) + 4 * ( ~~~d &&& ( ~~~e &&& f)) - 12 * ( ~~~d &&& (e &&& f)) - 39 * (d &&& ( ~~~e &&& f)) - 27 * (d &&& (e &&& f)) =  - 1 * (f ^^^  ~~~(d ||| (e &&& f)))

theorem sub_shl_same_amount_partial_nuw2_proof : sub_shl_same_amount_partial_nuw2_before ⊑ sub_shl_same_amount_partial_nuw2_after

theorem and_or_not_not_commute7_proof : and_or_not_not_commute7_before ⊑ and_or_not_not_commute7_after

private theorem not_not_xor_not (a b : Bool) : ! ((!a).xor (!b)) = (a == b)

theorem ashrsgt_01_06_exact_proof : ashrsgt_01_06_exact_before ⊑ ashrsgt_01_06_exact_after

theorem intMin_not_gt_zero : ¬ (intMin w >ₛ (0#w))

theorem or_not_xor_common_op_commute3_thm (e e_1 e_2 : IntW 8) :
  LLVM.or (LLVM.or (sub (const? 8 0) e_2) (LLVM.xor e_1 (const? 8 (-1)))) (LLVM.xor e_1 e) ⊑
    LLVM.or (LLVM.xor (LLVM.and e_1 e) (const? 8 (-1))) (sub (const? 8 0) e_2)

theorem test46_thm.extracted_1._1 : ∀ (x : BitVec 64),
  ¬8#32 ≥ ↑32 → 8#32 ≥ ↑32 ∨ True ∧ (truncate 32 x <<< 8#32 &&& 10752#32).msb = true → False

theorem e_1535 :
     - 3 * ((a &&& b) ^^^  ~~~(a ^^^ ( ~~~b ||| c))) - 2 * (c ^^^ (a &&&  ~~~b)) + 2 *  ~~~(a ||| b) + 1 * (b ^^^  ~~~(a &&& ( ~~~b ||| c))) + 2 *  ~~~(a |||  ~~~b) + 3 * (c &&& (a ^^^ b)) - 3 * ((a &&& c) ^^^  ~~~(a ^^^ ( ~~~b &&& c))) - 2 *  ~~~(a ||| (b ||| c)) + 2 *  ~~~(a ||| ( ~~~b ||| c)) + 5 *  ~~~( ~~~a ||| (b ||| c)) + 3 *  ~~~( ~~~a ||| ( ~~~b ||| c)) + 4 * (a &&& (b &&& c)) =  - 2 *  ~~~(a ||| c) + 1 * ( ~~~a &&& ( ~~~b &&& c))

theorem lshrugt_02_02_thm.extracted_1._1 : ∀ (x : BitVec 4),
  ¬2#4 ≥ ↑4 → ofBool (2#4 <ᵤ x >>> 2#4) = ofBool (BitVec.ofInt 4 (-5) <ᵤ x)

theorem PR75692_1_thm (e : IntW 32) :
  LLVM.or (LLVM.xor e (const? 32 4)) (LLVM.xor e (const? 32 (-5))) ⊑ const? 32 (-1)

theorem test_eq1_thm.extracted_1._1 : ∀ (x : BitVec 16) (x_1 : BitVec 32),
  ¬(True ∧ signExtend 32 (truncate 8 x_1) ≠ x_1 ∨ True ∧ signExtend 16 (truncate 8 x) ≠ x) →
    ofBool (truncate 8 x_1 == truncate 8 x) = ofBool (x_1 == signExtend 32 x)

theorem ashr_ult_14_proof : ashr_ult_14_before ⊑ ashr_ult_14_after

theorem main_thm.extracted_1._1 : ∀ (x : BitVec 32),
  ¬(6#8 ≥ ↑8 ∨ 7#8 ≥ ↑8) → 5#8 ≥ ↑8 ∨ True ∧ ((truncate 8 x ^^^ -1#8) <<< 5#8 &&& 64#8).msb = true → False

@[deprecated "liftEffect_eq_pure_cast_of" (since := "")]
theorem liftEffect_pure [Pure m] {e} (hle : e ≤ pure) :
    liftEffect hle (α := α) (m := m) = cast (by rw [eq_of_le_pure hle])

theorem test7_proof : test7_before ⊑ test7_after

theorem ashrsgt_01_00_thm.extracted_1._1 : ∀ (x : BitVec 4),
  ¬1#4 ≥ ↑4 → ofBool (0#4 <ₛ x.sshiftRight' 1#4) = ofBool (1#4 <ₛ x)

theorem ule_swap_or_not_min_logical_proof : ule_swap_or_not_min_logical_before ⊑ ule_swap_or_not_min_logical_after

theorem lshrult_02_05_exact_proof : lshrult_02_05_exact_before ⊑ lshrult_02_05_exact_after

theorem select_icmp_eq_0_and_1_or_1_proof : select_icmp_eq_0_and_1_or_1_before ⊑ select_icmp_eq_0_and_1_or_1_after

theorem sle_smax2_thm.extracted_1._1 : ∀ (x x_1 : BitVec 32),
  ¬ofBool (x <ₛ x_1) = 1#1 → ofBool (x ≤ₛ x) = ofBool (x_1 ≤ₛ x)

theorem lshrugt_01_04_thm.extracted_1._1 : ∀ (x : BitVec 4),
  ¬1#4 ≥ ↑4 → ofBool (4#4 <ᵤ x >>> 1#4) = ofBool (BitVec.ofInt 4 (-7) <ᵤ x)

theorem or_to_nxor3_proof : or_to_nxor3_before ⊑ or_to_nxor3_after

theorem lshr_ne_msb_low_last_zero_proof : lshr_ne_msb_low_last_zero_before ⊑ lshr_ne_msb_low_last_zero_after

@[simp]
theorem map_tru (f : α → β) :
    Circuit.tru.map f = Circuit.tru

theorem slt_swap_and_max_thm (e e_1 : IntW 8) :
  LLVM.and (icmp IntPred.sgt e_1 e) (icmp IntPred.eq e (const? 8 127)) ⊑ const? 1 0

theorem exact_lshr_eq_both_equal_proof : exact_lshr_eq_both_equal_before ⊑ exact_lshr_eq_both_equal_after

theorem test15b_thm.extracted_1._2 : ∀ (x : BitVec 32),
  ¬ofBool (x &&& 32#32 == 0#32) = 1#1 → 0#32 = x &&& 32#32 ^^^ 32#32

theorem ashrslt_03_12_exact_proof : ashrslt_03_12_exact_before ⊑ ashrslt_03_12_exact_after

theorem e_1084 :
     - 6 * t + 1 *  ~~~(z &&& t) + 1 * z - 6 *  ~~~(z ^^^ t) - 1 * (z ||| t) + 5 *  ~~~(z ||| t) + 6 *  ~~~(z |||  ~~~t) - 1 * (z &&&  ~~~t) =  - 12 * (z &&& t)

theorem scalar_i32_lshr_and_signbit_eq_thm (e e_1 : IntW 32) :
  icmp IntPred.eq (LLVM.and (lshr e_1 e) (const? 32 (-2147483648))) (const? 32 0) ⊑
    icmp IntPred.sgt (lshr e_1 e) (const? 32 (-1))

theorem land_land_left1_thm.extracted_1._2 : ∀ (x x_1 : BitVec 1), x_1 = 1#1 → x = 1#1 → x_1 = x

theorem n12_thm (e e_1 : IntW 8) :
  icmp IntPred.sgt (sub (const? 8 0) e_1 { «nsw» := true, «nuw» := false }) e ⊑
    icmp IntPred.slt e (sub (const? 8 0) e_1 { «nsw» := true, «nuw» := false })

theorem and_nosignbit_select_ashr_thm.extracted_1._1 : ∀ (x : BitVec 32) (x_1 : BitVec 1),
  x_1 = 1#1 → ¬8#32 ≥ ↑32 → (x &&& 2147418112#32).sshiftRight' 8#32 = x.sshiftRight' 8#32 &&& 8388352#32

theorem not_logicalAnd_not_op1_thm.extracted_1._5 : ∀ (x x_1 : BitVec 1),
  ¬x_1 = 1#1 → x_1 ^^^ 1#1 = 1#1 → 0#1 ^^^ 1#1 = 1#1

theorem lt_unsigned_to_small_negative_thm (e : IntW 8) : icmp IntPred.slt (zext 32 e) (const? 32 (-17)) ⊑ const? 1 0

theorem positive_biggerShl_proof : positive_biggerShl_before ⊑ positive_biggerShl_after

theorem not_or_or_and_not_and_and_commute1_proof : not_or_or_and_not_and_and_commute1_before ⊑ not_or_or_and_not_and_and_commute1_after

theorem lshrugt_01_07_proof : lshrugt_01_07_before ⊑ lshrugt_01_07_after

theorem p2_scalar_shifted_urem_by_const_thm.extracted_1._1 : ∀ (x x_1 : BitVec 32),
  ¬(x ≥ ↑32 ∨ 3#32 = 0) → True ∧ (x_1 &&& 1#32) <<< x >>> x ≠ x_1 &&& 1#32 ∨ x ≥ ↑32 ∨ 3#32 = 0 → False

@[simp]
theorem instantiate_mvar_zero' :
    (mvar (φ := 1) ⟨0, by simp⟩).instantiate (Subtype.mk [w] (by simp)) = w

theorem main13_logical_thm.extracted_1._3 : ∀ (x : BitVec 32),
  ¬ofBool (truncate 16 x <ₛ 0#16) = 1#1 → ofBool (x &&& 32896#32 == 32896#32) = 1#1 → ¬0#1 = 1#1 → 1#32 = 2#32

theorem scalar1_thm.extracted_1._1 : ∀ (x x_1 : BitVec 4),
  True ∧ (x_1 &&& BitVec.ofInt 4 (-2) &&& (x &&& 1#4) != 0) = true → False

theorem fold_add_udiv_urem_thm.extracted_1._2 : ∀ (x : BitVec 32),
  ¬(10#32 = 0 ∨ 4#32 ≥ ↑32 ∨ 10#32 = 0) →
    ¬(10#32 = 0 ∨ True ∧ (x / 10#32).umulOverflow 6#32 = true) →
      (x / 10#32) <<< 4#32 + x % 10#32 = x / 10#32 * 6#32 + x

theorem e_1480 :
     - 3 *  ~~~z + 2 *  ~~~(z &&&  ~~~z) + 7 * (z |||  ~~~t) + 3 *  ~~~(z &&&  ~~~t) - 2 * z - 7 *  ~~~(z &&& t) - 5 *  ~~~t + 2 *  ~~~(z ||| t) + 6 *  ~~~(z |||  ~~~t) + 5 * (z &&&  ~~~t) - 10 * (z &&& t) =  - 1 *  ~~~(z ^^^ t) + 1 * t

theorem factorize_thm (e : IntW 32) : LLVM.and (LLVM.or e (const? 32 1)) (LLVM.or e (const? 32 2)) ⊑ e

theorem uge_swap_and_max_commute_logical_thm.extracted_1._1 : ∀ (x : BitVec 8),
  ¬ofBool (x == -1#8) = 1#1 → 0#1 = ofBool (x == -1#8)

theorem foo2_thm.extracted_1._1 : ∀ (x x_1 : BitVec 32),
  ¬ofBool (2#32 <ₛ x_1) = 1#1 → ¬(True ∧ x_1.ssubOverflow x = true) → x_1 - x = x_1 + (0#32 - x)

theorem foo_thm.extracted_1._2 : ∀ (x x_1 : BitVec 8),
  ¬(7#8 ≥ ↑8 ∨ 7#8 ≥ ↑8 ∨ 5#8 ≥ ↑8 ∨ 7#8 ≥ ↑8) →
    ¬(7#8 ≥ ↑8 ∨
          2#8 ≥ ↑8 ∨
            True ∧ (40#8).ssubOverflow (x &&& 84#8) = true ∨
              True ∧ (x &&& 33#8 &&& (40#8 - (x &&& 84#8) &&& 84#8) != 0) = true ∨
                7#8 ≥ ↑8 ∨
                  True ∧
                    ((x &&& 33#8 ||| 40#8 - (x &&& 84#8) &&& 84#8) &&& (x_1 <<< 7#8 ^^^ x &&& BitVec.ofInt 8 (-118)) !=
                        0) =
                      true) →
      (x_1 <<< 7#8 ^^^ x &&& BitVec.ofInt 8 (-118)) >>> 7#8 <<< 5#8 ^^^
          (x &&& 33#8 ||| BitVec.ofInt 8 (-88) - (x &&& 84#8) &&& 84#8 |||
            x_1 <<< 7#8 ^^^ x &&& BitVec.ofInt 8 (-118)) =
        (x_1 <<< 7#8 ^^^ x &&& BitVec.ofInt 8 (-118)) >>> 2#8 &&& 32#8 ^^^
          (x &&& 33#8 ||| 40#8 - (x &&& 84#8) &&& 84#8 ||| x_1 <<< 7#8 ^^^ x &&& BitVec.ofInt 8 (-118))

theorem xor_ashr_not_proof : xor_ashr_not_before ⊑ xor_ashr_not_after

theorem lshr_pow2_ult_proof : lshr_pow2_ult_before ⊑ lshr_pow2_ult_after

theorem e_492 :
     - 3 * y - 3 * (x ^^^ y) - 2 * (x |||  ~~~y) - 1 *  ~~~(x &&&  ~~~x) - 2 * x + 4 *  ~~~(x ||| y) + 8 *  ~~~(x |||  ~~~y) + 8 * (x &&&  ~~~y) + 8 * (x &&& y) = 1 *  ~~~x

theorem test35_with_trunc_thm.extracted_1._2 : ∀ (x : BitVec 64),
  ¬ofBool (0#32 ≤ₛ truncate 32 x) = 1#1 → ofBool (x &&& 2147483648#64 == 0#64) = 1#1 → 100#32 = 60#32

theorem main5_like_thm (e e_1 : IntW 32) :
  select
      (LLVM.and (icmp IntPred.eq (LLVM.and e_1 (const? 32 7)) (const? 32 7))
        (icmp IntPred.eq (LLVM.and e (const? 32 7)) (const? 32 7)))
      (const? 32 0) (const? 32 1) ⊑
    zext 32 (icmp IntPred.ne (LLVM.and (LLVM.and e_1 e) (const? 32 7)) (const? 32 7))

theorem test87_proof : test87_before ⊑ test87_after

theorem e_935 :
     - 2 *  ~~~(z ^^^ t) + 2 *  ~~~t + 2 *  ~~~(z &&& t) - 4 *  ~~~(z ||| t) - 4 *  ~~~(z |||  ~~~t) - 6 * (z &&&  ~~~t) =  - 2 *  ~~~(z &&&  ~~~z)

theorem max_sub_uge_c32_thm.extracted_1._2 : ∀ (x : BitVec 32),
  ¬ofBool (x ≤ᵤ 2#32) = 1#1 → ofBool (x <ᵤ 3#32) = 1#1 → 0#32 = x + BitVec.ofInt 32 (-2)

theorem or_xor_and_commuted2_proof : or_xor_and_commuted2_before ⊑ or_xor_and_commuted2_after

theorem eq_smax2_proof : eq_smax2_before ⊑ eq_smax2_after

theorem udiv_exact_ne_0_thm.extracted_1._1 : ∀ (x x_1 : BitVec 8),
  ¬(True ∧ x_1.umod x ≠ 0 ∨ x = 0) → ofBool (x_1 / x != 0#8) = ofBool (x_1 != 0#8)

theorem ashr_ugt_6_thm.extracted_1._1 : ∀ (x : BitVec 4),
  ¬1#4 ≥ ↑4 → ofBool (6#4 <ᵤ x.sshiftRight' 1#4) = ofBool (x <ₛ 0#4)

theorem uaddo_commute8_thm (e e_1 e_2 : IntW 32) :
  select (icmp IntPred.ult (LLVM.xor e_2 (const? 32 (-1))) e_1) (add e_2 e_1) e ⊑
    select (icmp IntPred.ugt e_1 (LLVM.xor e_2 (const? 32 (-1)))) (add e_2 e_1) e

theorem exact_lshr_eq_opposite_msb_thm.extracted_1._1 : ∀ (x : BitVec 8),
  ¬(True ∧ BitVec.ofInt 8 (-128) >>> x <<< x ≠ BitVec.ofInt 8 (-128) ∨ x ≥ ↑8) →
    ofBool (BitVec.ofInt 8 (-128) >>> x == 1#8) = ofBool (x == 7#8)

theorem testi128i128_thm.extracted_1._1 : ∀ (x : BitVec 128),
  ¬127#128 ≥ ↑128 → ofBool (-1#128 <ₛ x) = 1#1 → x.sshiftRight' 127#128 ^^^ 27#128 = 27#128

theorem icmp_slt_0_and_icmp_ne_neg2_i32_fail_proof : icmp_slt_0_and_icmp_ne_neg2_i32_fail_before ⊑ icmp_slt_0_and_icmp_ne_neg2_i32_fail_after

theorem bools_multi_uses2_logical_thm.extracted_1._31 : ∀ (x x_1 x_2 : BitVec 1),
  ¬x_2 ^^^ 1#1 = 1#1 → x_2 = 1#1 → 0#1 = 1#1 → ¬x = 1#1 → ¬True → 0#1 + x = 0#1

theorem t0_thm (e : IntW 64) :
  sub (const? 32 0) (trunc 32 (lshr e (const? 64 63))) ⊑
    trunc 32 (ashr e (const? 64 63)) { «nsw» := true, «nuw» := false }

theorem test_and_ne_a_b_thm.extracted_1._2 : ∀ (x x_1 : BitVec 8) (x_2 : BitVec 1),
  ¬x_2 &&& ofBool (x_1 != x) = 1#1 → x_2 = 1#1 → x = x_1

theorem mkCarryAssignCircuitNAux_eval_eq_ {arity : Type _}
    [DecidableEq arity]
    [Fintype arity]
    [Hashable arity]
    (p : FSM arity) (s : p.α) (n : Nat)
    {env : Vars p.α arity (n + 1) → Bool}
    {env' : p.α ⊕ arity → Bool}
    (hEnvState : ∀ (s : p.α), env (Vars.stateN s n) = env' (Sum.inl s))
    (hEnvInput : ∀ (i : arity), env (Vars.inputN i n) = env' (Sum.inr i)) :
    ((mkCarryAssignCircuitNAux p s n).eval env) = ((p.nextStateCirc s).eval env')

theorem slt_swap_and_not_max_commute_thm.extracted_1._1 : ∀ (x x_1 : BitVec 8),
  ofBool (x_1 != 127#8) &&& ofBool (x_1 <ₛ x) = ofBool (x_1 <ₛ x)

theorem icmp_eq_zext_eq_non_boolean_proof : icmp_eq_zext_eq_non_boolean_before ⊑ icmp_eq_zext_eq_non_boolean_after

theorem mul_constant_nuw_eq_proof : mul_constant_nuw_eq_before ⊑ mul_constant_nuw_eq_after

theorem icmp_ugt_32_thm.extracted_1._1 : ∀ (x : BitVec 64),
  ¬(True ∧ x <<< 32#64 >>> 32#64 ≠ x ∨ 32#64 ≥ ↑64) → ofBool (4294967295#64 <ᵤ x <<< 32#64) = ofBool (x != 0#64)

theorem test19_commutative0_thm (e e_1 : IntW 32) :
  urem e_1 (add (LLVM.and (shl (const? 32 1) e_1) (shl (const? 32 1) e)) (shl (const? 32 1) e)) ⊑
    LLVM.and e_1
      (add
        (add
          (LLVM.and (shl (const? 32 1) e_1 { «nsw» := false, «nuw» := true })
            (shl (const? 32 1) e { «nsw» := false, «nuw» := true }))
          (shl (const? 32 1) e { «nsw» := false, «nuw» := true }))
        (const? 32 (-1)))

theorem t3_exact_proof : t3_exact_before ⊑ t3_exact_after

@[simp]
lemma or_fals (c : Circuit α) :
  c ||

theorem eq_smax3_proof : eq_smax3_before ⊑ eq_smax3_after

theorem icmp_eq_and_pow2_minus1_shl_pow2_thm (e : IntW 32) :
  zext 32 (icmp IntPred.eq (LLVM.and (shl (const? 32 2) e) (const? 32 15)) (const? 32 0)) ⊑
    zext 32 (icmp IntPred.ugt e (const? 32 2))

theorem select_icmp_ne_0_and_1073741824_and_not_8_proof : select_icmp_ne_0_and_1073741824_and_not_8_before ⊑ select_icmp_ne_0_and_1073741824_and_not_8_after

theorem positive_with_icmp_proof : positive_with_icmp_before ⊑ positive_with_icmp_after

theorem lshr_neg_sgt_minus_1_thm.extracted_1._1 : ∀ (x : BitVec 8),
  ¬x ≥ ↑8 → ofBool (-1#8 <ₛ BitVec.ofInt 8 (-17) >>> x) = ofBool (x != 0#8)

theorem select_shl_icmp_bad_proof : select_shl_icmp_bad_before ⊑ select_shl_icmp_bad_after

theorem ashrslt_02_03_exact_thm (e : IntW 4) :
  icmp IntPred.slt (ashr e (const? 4 2) { «exact» := true }) (const? 4 3) ⊑ const? 1 1

theorem exact_lshr_ne_both_equal_thm (e : IntW 8) :
  icmp IntPred.ne (lshr (const? 8 126) e { «exact» := true }) (const? 8 126) ⊑
    icmp IntPred.ne e (const? 8 0)

theorem AvoidCollision_toInt_signExtend_of_le {x : BitVec w} (h : w ≤ v) :
    (x.signExtend v).toInt = x.toInt

@[simp] theorem head_corec : head (corec b f) = (f b).fst

theorem add_const_sub_const_thm (e : IntW 32) : sub (add e (const? 32 8)) (const? 32 2) ⊑ add e (const? 32 6)

theorem ne_21_logical_thm.extracted_1._2 : ∀ (x x_1 : BitVec 32),
  ¬(16#32 ≥ ↑32 ∨ 16#32 ≥ ↑32) →
    ofBool (truncate 8 (x_1 >>> 16#32) != truncate 8 (x >>> 16#32)) = 1#1 →
      ¬(8#32 ≥ ↑32 ∨ 8#32 ≥ ↑32) → 1#1 = ofBool (truncate 16 (x_1 >>> 8#32) != truncate 16 (x >>> 8#32))

@[simp] theorem size_var : (var e body : Com d Γ eff t).size = body.size + 1

theorem and_logic_and_logic_or_2_thm.extracted_1._1 : ∀ (x x_1 : BitVec 1),
  x_1 &&& x = 1#1 → x_1 = 1#1 → ¬x = 1#1 → False

theorem or_ugt_proof : or_ugt_before ⊑ or_ugt_after

theorem udiv_shl_pair2_thm.extracted_1._2 : ∀ (x x_1 x_2 : BitVec 32),
  ¬(True ∧ (x_2 <<< x_1).sshiftRight' x_1 ≠ x_2 ∨
        True ∧ x_2 <<< x_1 >>> x_1 ≠ x_2 ∨ x_1 ≥ ↑32 ∨ True ∧ x_2 <<< x >>> x ≠ x_2 ∨ x ≥ ↑32 ∨ x_2 <<< x = 0) →
    ¬(True ∧ (1#32 <<< x_1).sshiftRight' x_1 ≠ 1#32 ∨ True ∧ 1#32 <<< x_1 >>> x_1 ≠ 1#32 ∨ x_1 ≥ ↑32 ∨ x ≥ ↑32) →
      x_2 <<< x_1 / x_2 <<< x = 1#32 <<< x_1 >>> x

theorem uge_swap_or_not_max_proof : uge_swap_or_not_max_before ⊑ uge_swap_or_not_max_after

theorem trunc_sel_larger_zext_thm.extracted_1._3 : ∀ (x : BitVec 32) (x_1 : BitVec 1),
  x_1 = 1#1 → ¬(True ∧ (x &&& 65535#32).msb = true) → zeroExtend 64 (truncate 16 x) = zeroExtend 64 (x &&& 65535#32)

theorem select_lshr_icmp_bad_proof : select_lshr_icmp_bad_before ⊑ select_lshr_icmp_bad_after

theorem bools_multi_uses2_thm.extracted_1._1 : ∀ (x x_1 x_2 : BitVec 1),
  x_2 = 1#1 → ((x_2 ^^^ 1#1) &&& x_1 ||| x_2 &&& x) &&& ((x_2 ^^^ 1#1) &&& x_1) + (x_2 &&& x) = x

theorem src_is_mask_zext_fail_not_mask_proof : src_is_mask_zext_fail_not_mask_before ⊑ src_is_mask_zext_fail_not_mask_after

theorem masked_icmps_mask_notallzeros_bmask_mixed_negated_swapped_1_proof : masked_icmps_mask_notallzeros_bmask_mixed_negated_swapped_1_before ⊑ masked_icmps_mask_notallzeros_bmask_mixed_negated_swapped_1_after

theorem n7_wrong_pred2_proof : n7_wrong_pred2_before ⊑ n7_wrong_pred2_after

theorem e_969 :
    2 *  ~~~t + 1 *  ~~~(z &&&  ~~~z) - 6 * (z ||| t) - 4 *  ~~~(z ||| t) + 4 *  ~~~(z |||  ~~~t) + 2 * (z &&&  ~~~t) + 4 * (z &&& t) =  - 1 * (z ^^^ t) - 1 *  ~~~(z ^^^ t)

theorem gt_signed_to_large_signed_thm (e : IntW 8) : icmp IntPred.sgt (sext 32 e) (const? 32 1024) ⊑ const? 1 0

theorem uadd_sat_flipped_wrong_bounds4_thm (e : IntW 32) :
  select (icmp IntPred.uge e (const? 32 (-8))) (const? 32 (-1)) (add e (const? 32 9)) ⊑
    select (icmp IntPred.ugt e (const? 32 (-9))) (const? 32 (-1)) (add e (const? 32 9))

theorem test26_proof : test26_before ⊑ test26_after

theorem test_sub__nsw_is_safe_thm (e : IntW 32) :
  select (icmp IntPred.eq (LLVM.or e (const? 32 (-2147483648))) (const? 32 (-2147483647))) (const? 32 (-1))
      (sub (const? 32 (-2147483648)) (LLVM.or e (const? 32 (-2147483648)))) ⊑
    sub (const? 32 (-2147483648)) (LLVM.or e (const? 32 (-2147483648))) { «nsw» := true, «nuw» := false }

theorem and_or_not_not_thm.extracted_1._1 : ∀ (x x_1 x_2 : BitVec 32),
  (x_2 &&& x_1 ^^^ -1#32 ||| x) &&& (x &&& x_2 ^^^ -1#32) = (x_1 ||| x) &&& x_2 ^^^ -1#32

theorem positive_with_icmp_logical_proof : positive_with_icmp_logical_before ⊑ positive_with_icmp_logical_after

theorem test_invert_demorgan_or2_thm (e e_1 e_2 : IntW 64) :
  LLVM.xor
      (LLVM.or (LLVM.or (icmp IntPred.ugt e_2 (const? 64 23)) (icmp IntPred.ugt e_1 (const? 64 59)))
        (icmp IntPred.ugt e (const? 64 59)))
      (const? 1 1) ⊑
    LLVM.and (LLVM.and (icmp IntPred.ult e_2 (const? 64 24)) (icmp IntPred.ult e_1 (const? 64 60)))
      (icmp IntPred.ult e (const? 64 60))

theorem lshr_shl_eq_amt_multi_use_thm.extracted_1._1 : ∀ (x : BitVec 43),
  ¬(23#43 ≥ ↑43 ∨ 23#43 ≥ ↑43 ∨ 23#43 ≥ ↑43) → 23#43 ≥ ↑43 → False

theorem test_imply_not2_thm.extracted_1._5 : ∀ (x : BitVec 1) (x_1 : BitVec 32),
  ¬ofBool (x_1 == 0#32) = 1#1 → ofBool (x_1 != 0#32) = 1#1 → 0#1 ||

theorem t9_proof : t9_before ⊑ t9_after

@[bv_multi_width_normalize] theorem BitVec.le_eq_ule {x y : BitVec w} :
    (x ≤ y) = ((x.ule y) = true)

theorem test1_thm.extracted_1._1 : ∀ (x : BitVec 23), x - x = 0#23

theorem test_invert_demorgan_logical_or_thm.extracted_1._6 : ∀ (x x_1 : BitVec 64),
  ¬ofBool (x_1 == 27#64) = 1#1 →
    ¬ofBool (x_1 != 27#64) = 1#1 →
      (ofBool (x_1 == 0#64) ||| ofBool (x == 0#64)) ^^^ 1#1 = ofBool (x_1 != 0#64) &&& 0#1

theorem udiv_illegal_type_c_thm.extracted_1._2 : ∀ (x : BitVec 9),
  ¬10#32 = 0 → ¬(10#9 = 0 ∨ True ∧ (x / 10#9).msb = true) → zeroExtend 32 x / 10#32 = zeroExtend 32 (x / 10#9)

theorem fold_add_udiv_urem_to_mul_thm.extracted_1._1 : ∀ (x : BitVec 32),
  ¬(7#32 = 0 ∨ 7#32 = 0) → x / 7#32 * 21#32 + x % 7#32 * 3#32 = x * 3#32

theorem nomask_rhs_thm.extracted_1._1 : ∀ (x : BitVec 32),
  ofBool (x &&& 1#32 == 0#32) ||

theorem ashr_bitwidth_mask_proof : ashr_bitwidth_mask_before ⊑ ashr_bitwidth_mask_after

theorem test_ne_0_and_15_add_3_proof : test_ne_0_and_15_add_3_before ⊑ test_ne_0_and_15_add_3_after

theorem sge_or_not_max_logical_proof : sge_or_not_max_logical_before ⊑ sge_or_not_max_logical_after

theorem icmp_ne_zext_eq_non_boolean_proof : icmp_ne_zext_eq_non_boolean_before ⊑ icmp_ne_zext_eq_non_boolean_after

theorem com_Γ : com.1 = (Γn 1)

theorem e_1234 :
     - 2 * t - 11 *  ~~~z - 2 * (z ||| t) + 5 *  ~~~(z &&&  ~~~t) + 2 *  ~~~(z ^^^ t) - 7 *  ~~~(z &&&  ~~~z) + 11 *  ~~~(z ||| t) + 17 *  ~~~(z |||  ~~~t) + 4 * (z &&& t) =  - 9 * (z &&&  ~~~t)

theorem sub_from_constant_of_sub_from_constant_proof : sub_from_constant_of_sub_from_constant_before ⊑ sub_from_constant_of_sub_from_constant_after

theorem rem_euclid_1_thm.extracted_1._1 : ∀ (x : BitVec 32),
  ¬(8#32 == 0 || 32 != 1 && x == intMin 32 && 8#32 == -1) = true →
    ofBool (x.srem 8#32 <ₛ 0#32) = 1#1 → x.srem 8#32 + 8#32 = x &&& 7#32

theorem exact_lshr_ne_opposite_msb_proof : exact_lshr_ne_opposite_msb_before ⊑ exact_lshr_ne_opposite_msb_after

theorem alive_275   : alive_275_src ⊑ alive_275_tgt

theorem lshrugt_03_02_exact_thm.extracted_1._1 : ∀ (x : BitVec 4),
  ¬(True ∧ x >>> 3#4 <<< 3#4 ≠ x ∨ 3#4 ≥ ↑4) → ofBool (2#4 <ᵤ x >>> 3#4) = 0#1

theorem test16_thm.extracted_1._1 : ∀ (x : BitVec 84),
  ¬4#84 ≥ ↑84 → ofBool (x.sshiftRight' 4#84 &&& 1#84 != 0#84) = ofBool (x &&& 16#84 != 0#84)

theorem removeNone_eq_of_equiv {α : Type} {x y : Stream α} (h_sim : x ~ y) :
    x.removeNone = y.removeNone

theorem select_icmp_x_and_8_ne_0_y_xor_8_thm (e : IntW 64) (e_1 : IntW 32) :
  select (icmp IntPred.eq (LLVM.and e_1 (const? 32 8)) (const? 32 0)) (LLVM.xor e (const? 64 8)) e ⊑
    LLVM.xor e (zext 64 (LLVM.xor (LLVM.and e_1 (const? 32 8)) (const? 32 8)) { «nneg» := true })

@[simp] theorem not_eq :    (~~~x) i = !(x i)

@[simp] theorem lookup_matchVar_nil (m : MatchVarResult lets v .nil w ma) :
    m.val.lookup ⟨_, w⟩ = some v

theorem foo_thm.extracted_1._1 : ∀ (x x_1 : BitVec 64),
  zeroExtend 64 (truncate 32 x_1 &&& truncate 32 x) = x_1 &&& x &&& 4294967295#64

theorem PR42691_4_logical_proof : PR42691_4_logical_before ⊑ PR42691_4_logical_after

theorem and_ashr_not_proof : and_ashr_not_before ⊑ and_ashr_not_after

theorem foo1_and_thm.extracted_1._1 : ∀ (x x_1 x_2 : BitVec 32),
  ¬(x_2 ≥ ↑32 ∨ x ≥ ↑32) →
    True ∧ 1#32 <<< x_2 >>> x_2 ≠ 1#32 ∨
        x_2 ≥ ↑32 ∨
          True ∧ 1#32 <<< x >>> x ≠ 1#32 ∨
            x ≥ ↑32 ∨ True ∧ 1#32 <<< x_2 >>> x_2 ≠ 1#32 ∨ x_2 ≥ ↑32 ∨ True ∧ 1#32 <<< x >>> x ≠ 1#32 ∨ x ≥ ↑32 →
      False

theorem a_or_b_const_thm.extracted_1._1 : ∀ (x x_1 x_2 : BitVec 32),
  ofBool (x_2 == x_1) &&& ofBool (x != x_1) ||

theorem positive_biggerlshr_shlnuwnsw_proof : positive_biggerlshr_shlnuwnsw_before ⊑ positive_biggerlshr_shlnuwnsw_after

theorem test_zext4_thm.extracted_1._4 : ∀ (x x_1 : BitVec 1),
  ¬x_1 = 1#1 → x_1 ^^^ 1#1 = 1#1 → 1#32 = zeroExtend 32 1#1

@[simp] lemma eval_simplify : ∀ (c : Circuit α) (f : α → Bool),
    eval (simplify c) f = eval c f

theorem ashrsgt_02_07_exact_thm (e : IntW 4) :
  icmp IntPred.sgt (ashr e (const? 4 2) { «exact» := true }) (const? 4 7) ⊑ const? 1 0

theorem main7c_logical_thm.extracted_1._7 : ∀ (x x_1 x_2 : BitVec 32),
  ofBool (x_2 == x_2 &&& x_1) = 1#1 →
    ¬ofBool (x_2 != x_2 &&& x_1) = 1#1 →
      ofBool (x == x &&& x_1) = 1#1 → 0#32 = zeroExtend 32 (ofBool (x != x &&& x_1))

theorem ugt_rem_nz_thm.extracted_1._1 : ∀ (x : BitVec 8),
  ¬(True ∧ x.umulOverflow 5#8 = true) → ofBool (21#8 <ᵤ x * 5#8) = ofBool (4#8 <ᵤ x)

theorem shl_trunc_bigger_shl_thm (e : IntW 32) :
  shl (trunc 8 (shl e (const? 32 4))) (const? 8 2) ⊑ shl (trunc 8 e) (const? 8 6)

theorem test29_proof : test29_before ⊑ test29_after

theorem e_1709 :
     - 2 * (b |||  ~~~(a ^^^ c)) - 7 * (b |||  ~~~(a |||  ~~~c)) - 11 *  ~~~( ~~~a ||| ( ~~~b &&& c)) + 4 * (b ^^^ (a ||| (b &&& c))) + 1 * ((a &&& b) ^^^ (a ^^^ (b &&& c))) - 1 * ((a &&&  ~~~b) ||| (b ^^^ c)) + 1 * ( ~~~(a ^^^ b) &&&  ~~~(a ^^^ c)) - 5 * (c ||| (a &&& b)) + 3 * (a &&& b) + 1 * (c ^^^  ~~~(a &&& ( ~~~b ||| c))) + 1 * ((a ^^^ b) ||| (a ^^^ c)) - 7 * (a |||  ~~~c) + 3 * (b ^^^  ~~~( ~~~a &&& ( ~~~b &&& c))) + 1 * (a ^^^ ( ~~~b &&& c)) + 11 * (c ^^^ (a &&& b)) + 1 * ( ~~~a ||| (b ||| c)) - 3 * (c ^^^ (a ||| ( ~~~b &&& c))) + 11 * (c ^^^  ~~~( ~~~a ||| ( ~~~b &&& c))) + 2 * ((a ||| b) &&& (a ^^^ (b ^^^ c))) - 2 * (b ^^^  ~~~(a ||| (b &&& c))) + 3 * (b &&& c) - 1 * (b ^^^ ( ~~~a &&& (b ^^^ c))) - 1 * (b ^^^  ~~~( ~~~a ||| ( ~~~b &&& c))) + 7 * (b ^^^  ~~~(a &&&  ~~~c)) - 2 *  ~~~(a ||| (b ||| c)) + 9 *  ~~~(a ||| ( ~~~b ||| c)) + 3 *  ~~~( ~~~a ||| ( ~~~b ||| c)) - 23 * ( ~~~a &&& ( ~~~b &&& c)) - 25 * (a &&& ( ~~~b &&& c)) + 15 * (a &&& (b &&& c)) = 14 * ( ~~~a &&& (b &&& c)) - 7 * (c &&&  ~~~(a &&&  ~~~b))

theorem factorize4_thm.extracted_1._1 : ∀ (x x_1 : BitVec 32), ¬1#32 ≥ ↑32 → x_1 <<< 1#32 * x - x * x_1 = x_1 * x

theorem test1_thm.extracted_1._2 : ∀ (x : BitVec 8) (x_1 : BitVec 32),
  ¬zeroExtend 32 x ≥ ↑32 →
    ¬(True ∧ x.msb = true ∨ zeroExtend 32 x ≥ ↑32) →
      x_1.sshiftRight' (zeroExtend 32 x) &&& 1#32 = x_1 >>> zeroExtend 32 x &&& 1#32

theorem p_proof : p_before ⊑ p_after

@[simp]
lemma eval_scanOr_zero (x : Unit → BitStream) : scanOr.eval x 0 = (x () 0)

theorem ashr_ult_12_thm (e : IntW 4) :
  icmp IntPred.ult (ashr e (const? 4 1)) (const? 4 (-4)) ⊑ icmp IntPred.sgt e (const? 4 (-1))

@[simp]
lemma List.Vector.ofFn_0 {f : Fin 0 → α} : ofFn f = .nil

omit [LawfulBEq A] [Fintype S] [DecidableEq S] in
lemma processOneElem_visited (st : worklist.St A S) :
    let st' := processOneElem _ _  final s st (a, sa')
    st'.visited = st.visited

theorem eq_21_thm.extracted_1._1 : ∀ (x x_1 : BitVec 32),
  ¬(16#32 ≥ ↑32 ∨ 16#32 ≥ ↑32 ∨ 8#32 ≥ ↑32 ∨ 8#32 ≥ ↑32) → 8#32 ≥ ↑32 ∨ 8#32 ≥ ↑32 → False

theorem pow2_or_zero_is_negative_commute_thm (e : IntW 8) :
  icmp IntPred.slt (LLVM.and (sub (const? 8 0) (mul (const? 8 42) e)) (mul (const? 8 42) e)) (const? 8 0) ⊑
    icmp IntPred.eq (mul e (const? 8 42)) (const? 8 (-128))

theorem shl_xor_lshr_comm_thm.extracted_1._2 : ∀ (x x_1 x_2 : BitVec 32),
  ¬(True ∧ x_1 <<< x >>> x ≠ x_1 ∨ x ≥ ↑32 ∨ x ≥ ↑32) → ¬x ≥ ↑32 → (x_2 ^^^ x_1 <<< x) >>> x = x_2 >>> x ^^^ x_1

theorem ashrslt_03_07_exact_proof : ashrslt_03_07_exact_before ⊑ ashrslt_03_07_exact_after

theorem sub_eq_xor_sub_mul_not_and :
    x - y = (x ^^^ y) - 2 * (~~~ x &&& y)

theorem bitwise_and_logical_and_masked_icmp_allones_poison2_thm.extracted_1._3 : ∀ (x : BitVec 32) (x_1 : BitVec 1)
  (x_2 : BitVec 32),
  ¬ofBool (x_2 &&& 8#32 == 8#32) = 1#1 →
    ofBool (x_2 &&& 8#32 != 0#32) = 1#1 → 0#1 &&& ofBool (x_2 &&& x == x) = x_1 &&& ofBool (x_2 &&& x == x)

theorem sub_ashr_and_i16_thm (e e_1 : IntW 16) :
  LLVM.and (ashr (sub e_1 e { «nsw» := true, «nuw» := false }) (const? 16 15)) e ⊑
    select (icmp IntPred.slt e_1 e) e (const? 16 0)

theorem eq_mul_constants_with_tz_thm (e e_1 : IntW 32) :
  icmp IntPred.ne (mul e_1 (const? 32 12)) (mul e (const? 32 12)) ⊑
    icmp IntPred.ne (LLVM.and (LLVM.xor e_1 e) (const? 32 1073741823)) (const? 32 0)

theorem sle_and_min_commute_proof : sle_and_min_commute_before ⊑ sle_and_min_commute_after

theorem e_331 :
     - 6 *  ~~~x + 2 * (x |||  ~~~y) - 3 * x + 2 * (x ||| y) - 10 *  ~~~(x ||| y) - 10 *  ~~~(x |||  ~~~y) - 4 * (x &&&  ~~~y) - 15 * (x &&& y) =  - 3 *  ~~~(x &&&  ~~~x) - 11 *  ~~~(x &&&  ~~~y)

theorem t0_proof : t0_before ⊑ t0_after

theorem test5_thm.extracted_1._1 : ∀ (x : BitVec 16), truncate 16 (signExtend 32 x &&& 15#32) = x &&& 15#16

theorem main7g_logical_thm.extracted_1._4 : ∀ (x x_1 x_2 : BitVec 32),
  ¬ofBool (x_2 &&& x_1 == x_2 &&& x_1 &&& x) = 1#1 →
    ¬ofBool (x_2 &&& x_1 != x_2 &&& x_1 &&& x) = 1#1 → ¬0#1 = 1#1 → False

theorem zext_sext_add_icmp_slt_minus1_proof : zext_sext_add_icmp_slt_minus1_before ⊑ zext_sext_add_icmp_slt_minus1_after

theorem positive_biggerlshr_shlnuw_lshrexact_thm.extracted_1._1 : ∀ (x : BitVec 8),
  ¬(True ∧ x >>> 6#8 <<< 6#8 ≠ x ∨ 6#8 ≥ ↑8 ∨ True ∧ x >>> 6#8 <<< 3#8 >>> 3#8 ≠ x >>> 6#8 ∨ 3#8 ≥ ↑8) →
    True ∧ x >>> 3#8 <<< 3#8 ≠ x ∨ 3#8 ≥ ↑8 → False

theorem zext_sext_add_icmp_slt_0_proof : zext_sext_add_icmp_slt_0_before ⊑ zext_sext_add_icmp_slt_0_after

theorem main7b_proof : main7b_before ⊑ main7b_after

theorem logical_or_not_thm.extracted_1._3 : ∀ (x x_1 : BitVec 1), ¬x_1 = 1#1 → ¬x_1 ^^^ 1#1 = 1#1 → 1#1 = x

theorem main5c_like_logical_proof : main5c_like_logical_before ⊑ main5c_like_logical_after

theorem add_five (x : BitVec w) : (x + x) + (x + x) + x = x + x + x + x + x

theorem ashr_ne_both_equal_proof : ashr_ne_both_equal_before ⊑ ashr_ne_both_equal_after

theorem e_563 :
    2 * (x ^^^ y) + 2 *  ~~~y + 7 * y - 1 *  ~~~x - 7 *  ~~~(x &&& y) + 1 * (x |||  ~~~y) - 1 *  ~~~(x &&&  ~~~y) + 6 *  ~~~(x ||| y) + 2 * (x &&&  ~~~y) = 7 * (x &&& y)

theorem a_true_implies_b_false2_comm_thm.extracted_1._2 : ∀ (x : BitVec 1) (x_1 : BitVec 8),
  ofBool (x_1 == 10#8) = 1#1 → ¬ofBool (20#8 <ᵤ x_1) = 1#1 → x &&& ofBool (20#8 <ᵤ x_1) = 0#1

theorem add_nosignbit_select_shl_proof : add_nosignbit_select_shl_before ⊑ add_nosignbit_select_shl_after

theorem sext_shl_trunc_smaller_thm.extracted_1._1 : ∀ (x : BitVec 32) (x_1 : BitVec 16),
  ¬x ≥ ↑32 → truncate 5 (signExtend 32 x_1 <<< x) = truncate 5 (zeroExtend 32 x_1 <<< x)

theorem lowmask_xor_zext_commute_thm.extracted_1._1 : ∀ (x : BitVec 8) (x_1 : BitVec 32),
  (x_1 * x_1 ^^^ zeroExtend 32 x) &&& 255#32 = zeroExtend 32 (x ^^^ truncate 8 (x_1 * x_1))

theorem e_803 :
    4 *  ~~~(z &&& t) + 5 *  ~~~(z ^^^ t) + 4 * z - 9 *  ~~~(z ||| t) - 8 * (z &&&  ~~~t) = 4 *  ~~~(z |||  ~~~t) + 9 * (z &&& t)

theorem lshrult_01_08_thm.extracted_1._1 : ∀ (x : BitVec 4),
  ¬1#4 ≥ ↑4 → ofBool (x >>> 1#4 <ᵤ BitVec.ofInt 4 (-8)) = 1#1

@[simp]
lemma reduce_spec (M : NFA α σ) : M.reduce.accepts = M.accepts

theorem add_select_sext_thm.extracted_1._2 : ∀ (x : BitVec 1), ¬x = 1#1 → 1#64 + signExtend 64 x = 1#64

@[simp] theorem Com.outContext_rets (vs : HVector Γ.Var t) : (rets vs : Com d Γ eff t).outContext = Γ

theorem shl_lshr_eq_amt_multi_use_thm.extracted_1._2 : ∀ (x : BitVec 44),
  ¬(33#44 ≥ ↑44 ∨ 33#44 ≥ ↑44 ∨ 33#44 ≥ ↑44) →
    ¬(33#44 ≥ ↑44 ∨ True ∧ (x <<< 33#44 &&& (x &&& 2047#44) != 0) = true) →
      x <<< 33#44 + x <<< 33#44 >>> 33#44 = x <<< 33#44 ||

@[grind ., simp, aesop 50% unsafe]
lemma wf_addTrans [LawfulBEq A] (m : RawCNFA A) (hwf : m.WF) s a s' (hin : s ∈ m.states) (hin' : s' ∈ m.states) :
    (m.addTrans a s s').WF

theorem add_or_sub_comb_i8_negative_y_add_thm (e e_1 : IntW 8) :
  add (LLVM.or (sub (const? 8 0) e_1) e_1) e ⊑ add (LLVM.or e_1 (sub (const? 8 0) e_1)) e

theorem ashr_ugt_6_thm (e : IntW 4) :
  icmp IntPred.ugt (ashr e (const? 4 1)) (const? 4 6) ⊑ icmp IntPred.slt e (const? 4 0)

theorem test_shl_nuw_nsw__nuw_is_safe_proof : test_shl_nuw_nsw__nuw_is_safe_before ⊑ test_shl_nuw_nsw__nuw_is_safe_after

theorem ashr_ugt_4_proof : ashr_ugt_4_before ⊑ ashr_ugt_4_after

theorem test12_proof : test12_before ⊑ test12_after

theorem shl_nsw_nuw_uge_Csle0_thm.extracted_1._1 : ∀ (x x_1 : BitVec 8),
  ¬(True ∧ (x_1 <<< x).sshiftRight' x ≠ x_1 ∨ True ∧ x_1 <<< x >>> x ≠ x_1 ∨ x ≥ ↑8) →
    ofBool (BitVec.ofInt 8 (-120) ≤ᵤ x_1 <<< x) = ofBool (BitVec.ofInt 8 (-121) <ᵤ x_1)

theorem fold_ne_rhs_thm.extracted_1._1 : ∀ (x x_1 : BitVec 8),
  ¬x ≥ ↑8 → ofBool ((x_1 ^^^ 123#8) &&& (-1#8) <<< x != 0#8) = ofBool ((x_1 ^^^ 123#8) >>> x != 0#8)

theorem select_icmp_eq_pow2_thm.extracted_1._2 : ∀ (x : BitVec 8),
  ¬ofBool (x &&& 4#8 == 0#8) = 1#1 → x ^^^ 4#8 = x &&& BitVec.ofInt 8 (-5)

theorem shl_lshr_demand6_thm.extracted_1._2 : ∀ (x : BitVec 16),
  ¬(x ≥ ↑16 ∨ 4#16 ≥ ↑16) →
    ¬x ≥ ↑16 → BitVec.ofInt 16 (-32624) <<< x >>> 4#16 &&& 4094#16 = 2057#16 <<< x &&& 4094#16

theorem icmp_eq_and_pow2_lshr_pow2_case2_thm.extracted_1._1 : ∀ (x : BitVec 32),
  ¬x ≥ ↑32 → zeroExtend 32 (ofBool (4#32 >>> x &&& 8#32 == 0#32)) = 1#32

theorem bswap_and_mask_1_proof : bswap_and_mask_1_before ⊑ bswap_and_mask_1_after

theorem shl_fold_or_disjoint_cnt_proof : shl_fold_or_disjoint_cnt_before ⊑ shl_fold_or_disjoint_cnt_after

theorem lshr_or_or_no_const_thm.extracted_1._1 : ∀ (x x_1 x_2 x_3 : BitVec 8),
  ¬(x_2 ≥ ↑8 ∨ x_2 ≥ ↑8) → x_2 ≥ ↑8 → False

theorem t0_thm.extracted_1._16 : ∀ (x x_1 x_2 : BitVec 8) (x_3 : BitVec 1),
  ¬x_3 ^^^ 1#1 = 1#1 → ¬x_3 = 1#1 → ¬ofBool (x_2 == x_1) = 1#1 → ¬0#1 = 1#1 → False

theorem or_not_and_and_not_and_xor_proof : or_not_and_and_not_and_xor_before ⊑ or_not_and_and_not_and_xor_after

theorem lowbitmask_casted_shift_thm.extracted_1._1 : ∀ (x : BitVec 8), ¬1#8 ≥ ↑8 → 1#32 ≥ ↑32 → False

theorem shiftl1 {v : Nat} (x : BitVec v) :
    x <<< 5 = x <<< 3 <<< 2

theorem test_proof : test_before ⊑ test_after

theorem test16_proof : test16_before ⊑ test16_after

theorem com_ty : com.2.2.1 = [.bitvec 32]

theorem lshrugt_01_01_exact_thm.extracted_1._1 : ∀ (x : BitVec 4),
  ¬(True ∧ x >>> 1#4 <<< 1#4 ≠ x ∨ 1#4 ≥ ↑4) → ofBool (1#4 <ᵤ x >>> 1#4) = ofBool (2#4 <ᵤ x)

theorem ashr_lshr_inv_proof : ashr_lshr_inv_before ⊑ ashr_lshr_inv_after

theorem shl_xor_xor_good_mask_proof : shl_xor_xor_good_mask_before ⊑ shl_xor_xor_good_mask_after

theorem bv_AndOrXor_1230__A__B___A__B :
    ∀ (e e_1 : LLVM.IntW w),
      LLVM.and (LLVM.xor e (LLVM.const? w (-1))) (LLVM.xor e_1 (LLVM.const? w (-1))) ⊑
        LLVM.xor (LLVM.or e e_1) (LLVM.const? w (-1))

theorem not_sext_thm.extracted_1._2 : ∀ (x : BitVec 1), ¬x = 1#1 → -1#999 = signExtend 999 (x ^^^ 1#1)

theorem bools2_logical_commute1_thm.extracted_1._9 : ∀ (x x_1 : BitVec 1),
  ¬x_1 = 1#1 → ¬x ^^^ 1#1 = 1#1 → ¬x = 1#1 → 0#1 = 1#1 → False

theorem logical_and_bitwise_and_icmps_thm (e e_1 e_2 : IntW 8) :
  select
      (LLVM.and (icmp IntPred.eq e_2 (const? 8 42))
        (icmp IntPred.ne (LLVM.and e_1 (const? 8 1)) (const? 8 0)))
      (icmp IntPred.ne (LLVM.and e_1 (shl (const? 8 1) e)) (const? 8 0)) (const? 1 0) ⊑
    select
      (LLVM.and (icmp IntPred.eq e_2 (const? 8 42))
        (icmp IntPred.ne (LLVM.and e_1 (const? 8 1)) (const? 8 0)))
      (icmp IntPred.ne (LLVM.and e_1 (shl (const? 8 1) e { «nsw» := false, «nuw» := true })) (const? 8 0))
      (const? 1 0)

theorem shl_add_nsw_proof : shl_add_nsw_before ⊑ shl_add_nsw_after

theorem match_andAsRem_lshrAsDiv_shlAsMul_thm.extracted_1._1 : ∀ (x : BitVec 64),
  ¬(6#64 ≥ ↑64 ∨ 9#64 = 0 ∨ 6#64 ≥ ↑64) → 576#64 = 0 → False

theorem exact_lshr_eq_thm (e : IntW 8) :
  icmp IntPred.eq (lshr (const? 8 4) e { «exact» := true }) (const? 8 1) ⊑
    icmp IntPred.eq e (const? 8 2)

theorem main3f_like_logical_thm.extracted_1._4 : ∀ (x x_1 : BitVec 32),
  ofBool (x_1 &&& x != 0#32) = 1#1 → ¬ofBool (x_1 &&& x == 0#32) = 1#1 → ¬True → 0#32 = zeroExtend 32 0#1

theorem substitute_constant_or_ne_uge_commute_thm (e e_1 : IntW 8) :
  LLVM.or (icmp IntPred.uge e_1 e) (icmp IntPred.ne e_1 (const? 8 42)) ⊑
    LLVM.or (icmp IntPred.ne e_1 (const? 8 42)) (icmp IntPred.ult e (const? 8 43))

theorem same_source_not_matching_signbits_thm (e : IntW 32) :
  sext 32 (trunc 8 (shl (const? 32 (-1)) (LLVM.and e (const? 32 8)) { «nsw» := true, «nuw» := false })) ⊑
    ashr (shl (const? 32 (-16777216)) (LLVM.and e (const? 32 8))) (const? 32 24) { «exact» := true }

theorem scalar_proof : scalar_before ⊑ scalar_after

theorem zext_sext_add_icmp_slt_1_proof : zext_sext_add_icmp_slt_1_before ⊑ zext_sext_add_icmp_slt_1_after

theorem positive_with_aggressive_icmp_logical_proof : positive_with_aggressive_icmp_logical_before ⊑ positive_with_aggressive_icmp_logical_after

theorem ult_and_max_commute_proof : ult_and_max_commute_before ⊑ ult_and_max_commute_after

theorem udiv_x_by_const_cmp_x_thm.extracted_1._1 : ∀ (x : BitVec 32),
  ¬123#32 = 0 → ofBool (x / 123#32 <ₛ x) = ofBool (0#32 <ₛ x)

theorem main4c_logical_proof : main4c_logical_before ⊑ main4c_logical_after

theorem udiv_shl_pair1_thm.extracted_1._1 : ∀ (x x_1 x_2 : BitVec 32),
  ¬(True ∧ x_2 <<< x_1 >>> x_1 ≠ x_2 ∨ x_1 ≥ ↑32 ∨ True ∧ x_2 <<< x >>> x ≠ x_2 ∨ x ≥ ↑32 ∨ x_2 <<< x = 0) →
    True ∧ 1#32 <<< x_1 >>> x_1 ≠ 1#32 ∨ x_1 ≥ ↑32 ∨ x ≥ ↑32 → False

theorem e_2074 :
    1 * (e ^^^ (d ||| (e ||| f))) + 1 *  ~~~(d ^^^ ( ~~~e ||| f)) - 6 * (f ^^^ (d &&& e)) - 1 * (f &&& (d |||  ~~~e)) + 2 * (f ^^^ (d |||  ~~~e)) - 5 * ((d &&& e) |||  ~~~(e ||| f)) - 11 * ( ~~~e ||| (d ^^^ f)) + 11 *  ~~~(d ||| (e &&& f)) - 5 * (d ^^^ ( ~~~e &&& f)) + 1 * (e ^^^ (d ||| f)) + 1 * (e ^^^ (d &&& (e ||| f))) - 2 * ((d &&& f) ^^^  ~~~(e &&&  ~~~f)) - 5 * (d &&&  ~~~e) + 4 * (f ^^^ (d ||| (e &&& f))) + 4 * (d ||| ( ~~~e ||| f)) + 4 * ((d &&&  ~~~e) |||  ~~~(d ^^^ (e ^^^ f))) - 6 * ((d ||| e) &&& (e ^^^ f)) + 7 *  ~~~(d &&& ( ~~~e &&& f)) + 3 * ( ~~~f &&&  ~~~(d ^^^ e)) + 5 * (f &&& (d ^^^ e)) + 11 * (d &&& (e ^^^ f)) + 3 * (f ^^^  ~~~(d &&& (e &&& f))) + 5 * (e ^^^ ( ~~~d &&& (e ||| f))) - 11 * (f ^^^  ~~~(d &&&  ~~~e)) - 1 * (e ^^^  ~~~(d &&& (e &&& f))) + 2 * (f ^^^ ( ~~~d ||| ( ~~~e ||| f))) - 1 * ((d ||| e) &&& (d ^^^ (e ^^^ f))) + 1 * (e ^^^  ~~~( ~~~d ||| ( ~~~e &&& f))) - 2 * (e &&& (d ||| f)) - 3 * ((d &&& f) ^^^  ~~~(d ^^^ ( ~~~e &&& f))) - 1 * (f ^^^  ~~~(d &&& ( ~~~e ||| f))) - 5 * ((d ^^^ e) |||  ~~~(d ^^^ f)) + 3 *  ~~~(d ||| (e ||| f)) + 1 *  ~~~(d ||| ( ~~~e ||| f)) + 5 *  ~~~( ~~~d ||| (e ||| f)) + 5 *  ~~~( ~~~d ||| ( ~~~e ||| f)) - 7 * ( ~~~d &&& ( ~~~e &&& f)) + 6 * ( ~~~d &&& (e &&& f)) + 20 * (d &&& ( ~~~e &&& f)) + 4 * (d &&& (e &&& f)) = 1 * (e ^^^ (d &&& f))

theorem ashrslt_02_03_proof : ashrslt_02_03_before ⊑ ashrslt_02_03_after

theorem e_2430 :
    1 * e + 1 * ( ~~~(d |||  ~~~e) |||  ~~~(d ^^^ (e ^^^ f))) - 5 * ((d ^^^ e) |||  ~~~(d ^^^ f)) - 6 * (d ||| (e ^^^ f)) + 1 * (e |||  ~~~(d |||  ~~~f)) - 6 * ((e &&& f) ||| ( ~~~d &&& (e ||| f))) - 2 * (e ||| (d &&&  ~~~f)) + 4 * (f ^^^ (d &&& ( ~~~e ||| f))) - 2 * ((d &&& e) ||| (d ^^^ (e ^^^ f))) + 2 * ( ~~~(d &&&  ~~~e) &&&  ~~~(d ^^^ (e ^^^ f))) + 4 * ((d |||  ~~~e) &&&  ~~~(e ^^^ f)) + 4 * (e ^^^ ( ~~~d &&& (e ||| f))) + 2 * ((d &&& e) ^^^  ~~~(d ^^^ (e &&& f))) + 1 * ( ~~~d ||| ( ~~~e ||| f)) + 2 * (f ^^^ ( ~~~d ||| (e &&& f))) - 11 *  ~~~(d &&& (e &&& f)) + 1 * ((d &&& e) |||  ~~~(e ^^^ f)) + 7 * (d ^^^ f) + 11 *  ~~~( ~~~d &&& ( ~~~e ||| f)) + 4 * ((e &&&  ~~~f) ^^^ (d ||| (e ^^^ f))) - 3 * (f ^^^ (d ||| ( ~~~e &&& f))) - 6 * (f ^^^  ~~~(d &&& (e &&& f))) + 5 * ((d &&& f) ^^^ (d ^^^ ( ~~~e &&& f))) - 5 * (e ^^^  ~~~( ~~~d ||| (e &&& f))) + 5 * (f &&&  ~~~(d &&& e)) + 1 * ((d &&& f) ^^^  ~~~(e &&&  ~~~f)) - 7 *  ~~~d + 3 * (d ^^^ (e ^^^ f)) + 2 *  ~~~( ~~~d &&& ( ~~~e &&& f)) - 5 * (f ^^^ (d &&& (e ||| f))) + 5 *  ~~~(d &&& f) + 2 * (f ^^^  ~~~(d &&& (e ||| f))) - 2 * (f ^^^  ~~~(d ||| (e &&& f))) + 3 * (e ^^^ f) - 2 * (e ^^^  ~~~( ~~~d ||| (e ^^^ f))) - 2 *  ~~~( ~~~d &&& (e ||| f)) - 1 *  ~~~( ~~~d &&& (e &&& f)) + 11 * (e ||| f) - 3 * (e &&& (d ||| f)) - 2 * ((e &&&  ~~~f) |||  ~~~(d ||| ( ~~~e &&& f))) - 1 * (e |||  ~~~(d ||| f)) - 3 *  ~~~(d ||| f) - 3 * (f ^^^  ~~~(d ||| e)) + 1 * ( ~~~d ||| ( ~~~e &&& f)) - 1 * (e &&&  ~~~(d &&& f)) - 11 * (e ^^^  ~~~( ~~~d &&& (e ||| f))) + 5 * ( ~~~d ||| (e ^^^ f)) + 11 * ((d &&& e) ^^^  ~~~(d ^^^ ( ~~~e ||| f))) - 2 *  ~~~e + 11 * (d ^^^ e) + 2 * ( ~~~(d &&& e) &&&  ~~~(d ^^^ (e ^^^ f))) + 1 * (e &&& (d ^^^ f)) - 7 * ( ~~~(d ^^^ e) ||| (d ^^^ f)) - 3 *  ~~~(d ^^^ ( ~~~e ||| f)) + 7 * ((d &&& e) ^^^ (d ^^^ (e &&& f))) + 11 * ( ~~~(d &&&  ~~~e) &&&  ~~~(e ^^^ f)) - 2 *  ~~~( ~~~d ||| ( ~~~e &&& f)) + 1 * ( ~~~(d |||  ~~~e) ||| (e ^^^ f)) - 1 *  ~~~(d ^^^ (e ^^^ f)) + 1 *  ~~~(e &&& f) + 2 *  ~~~(d ||| e) + 5 * ( ~~~(d ^^^ e) &&&  ~~~(d ^^^ f)) + 1 * (f ^^^  ~~~( ~~~d &&& (e &&& f))) - 1 * (f |||  ~~~(d |||  ~~~e)) - 1 * ((d &&& f) |||  ~~~(e ||| f)) + 4 * (d |||  ~~~f) - 6 * (d ||| (e ||| f)) + 10 *  ~~~(d ||| (e ||| f)) + 3 *  ~~~(d ||| ( ~~~e ||| f)) - 8 *  ~~~( ~~~d ||| (e ||| f)) - 10 *  ~~~( ~~~d ||| ( ~~~e ||| f)) - 5 * ( ~~~d &&& ( ~~~e &&& f)) + 9 * ( ~~~d &&& (e &&& f)) - 30 * (d &&& ( ~~~e &&& f)) - 1 * (d &&& (e &&& f)) = 7 * (e ^^^ ( ~~~d &&& (e ^^^ f)))

theorem Array.push_incl {a : Array α} {x : α} (y : α) : x ∈ a → x ∈ a.push y

theorem no_shift_xor_multiuse_cmp_xor_thm.extracted_1._1 : ∀ (x x_1 x_2 : BitVec 32),
  ofBool (0#32 != x_2 &&& 4096#32) = 1#1 → ofBool (x_2 &&& 4096#32 == 0#32) = 1#1 → False

theorem n3_constmask_samemask_thm.extracted_1._1 : ∀ (x x_1 : BitVec 32),
  x_1 &&& 65280#32 ^^^ x &&& 65280#32 = (x_1 ^^^ x) &&& 65280#32

theorem lshr_and_thm (e e_1 : IntW 8) :
  shl (LLVM.and (lshr e_1 (const? 8 6)) (LLVM.srem e (const? 8 42))) (const? 8 6) ⊑
    LLVM.and e_1 (shl (LLVM.srem e (const? 8 42)) (const? 8 6))

theorem e_2085 :
     - 7 *  ~~~(d ||| ( ~~~e &&& f)) - 3 * (f ^^^  ~~~(d ||| (e &&& f))) - 1 * (e ^^^  ~~~(d ||| (e &&& f))) + 1 * (f ^^^  ~~~( ~~~d ||| ( ~~~e &&& f))) - 2 * (d &&&  ~~~e) + 1 * (e ^^^ (d &&&  ~~~f)) + 5 * ((d ||| e) &&& (d ^^^ (e ^^^ f))) - 5 *  ~~~(d ^^^ ( ~~~e ||| f)) + 4 * (e ^^^ (d ||| (e ^^^ f))) - 1 * (d &&& ( ~~~e ||| f)) - 11 *  ~~~(e |||  ~~~f) - 2 * (e ^^^  ~~~( ~~~d &&& ( ~~~e ||| f))) - 2 * ((d &&& e) |||  ~~~(e ||| f)) + 1 * (f ^^^  ~~~(d |||  ~~~e)) - 3 * ((d ||| e) &&& (e ^^^ f)) + 2 *  ~~~e + 7 *  ~~~( ~~~d &&& ( ~~~e &&& f)) - 6 * (d ||| e) + 2 *  ~~~(d &&& (e ||| f)) - 6 * ((d &&& e) ||| (e ^^^ f)) + 2 * (e ^^^ (d ||| ( ~~~e ||| f))) - 2 * (f ^^^  ~~~(d &&&  ~~~e)) + 3 * (e ^^^  ~~~(d &&& (e &&& f))) - 3 * (f &&&  ~~~(d ^^^ e)) + 2 * ( ~~~(d &&&  ~~~e) &&&  ~~~(d ^^^ (e ^^^ f))) - 6 * ((d &&& f) ^^^ (e ||| f)) - 1 * (e ^^^ ( ~~~d ||| ( ~~~e &&& f))) - 1 * d - 5 * ((d &&& f) ^^^  ~~~(e &&&  ~~~f)) - 7 * (d ||| (e &&& f)) - 1 * (f ^^^ (d ||| (e ||| f))) - 1 * (e ^^^ ( ~~~d ||| (e ||| f))) + 3 * (e ||| (d &&&  ~~~f)) - 1 *  ~~~(d ||| (e ||| f)) + 13 *  ~~~(d ||| ( ~~~e ||| f)) + 2 *  ~~~( ~~~d ||| (e ||| f)) + 18 *  ~~~( ~~~d ||| ( ~~~e ||| f)) + 14 * ( ~~~d &&& ( ~~~e &&& f)) + 17 * ( ~~~d &&& (e &&& f)) + 31 * (d &&& ( ~~~e &&& f)) + 16 * (d &&& (e &&& f)) =  - 5 * ((d &&& e) ^^^  ~~~(d ^^^ (e &&& f)))

theorem test_sub__all_are_safe_thm.extracted_1._1 : ∀ (x : BitVec 32),
  ofBool (x &&& 255#32 == 6#32) = 1#1 →
    True ∧ (BitVec.ofInt 32 (-254)).ssubOverflow (x &&& 255#32) = true ∨
        True ∧ (BitVec.ofInt 32 (-254)).usubOverflow (x &&& 255#32) = true →
      False

theorem e_1217 :
    7 *  ~~~z + 4 *  ~~~(z ^^^ t) - 2 *  ~~~(z &&& t) - 5 * z - 5 *  ~~~(z &&&  ~~~z) - 4 *  ~~~(z ||| t) + 1 *  ~~~(z |||  ~~~t) + 13 * (z &&&  ~~~t) + 6 * (z &&& t) = 1 * (z ^^^ t)

theorem logic_or_logic_and_8_proof : logic_or_logic_and_8_before ⊑ logic_or_logic_and_8_after

theorem lshrugt_01_04_exact_thm.extracted_1._1 : ∀ (x : BitVec 4),
  ¬(True ∧ x >>> 1#4 <<< 1#4 ≠ x ∨ 1#4 ≥ ↑4) → ofBool (4#4 <ᵤ x >>> 1#4) = ofBool (BitVec.ofInt 4 (-8) <ᵤ x)

theorem zext_sext_add_icmp_slt_2_thm (e e_1 : IntW 1) :
  icmp IntPred.slt (add (zext 8 e_1) (sext 8 e)) (const? 8 2) ⊑ const? 1 1

theorem shl_sub_i32_proof : shl_sub_i32_before ⊑ shl_sub_i32_after

theorem exact_lshr_eq_noexactdiv_proof : exact_lshr_eq_noexactdiv_before ⊑ exact_lshr_eq_noexactdiv_after
</all_available_lemmas>

<local_ctx>
import Blase.Fast.FiniteStateMachine

import Blase.Vars

import Blase.MultiWidth.Defs

import Blase.KInduction.KInduction

import Lean

namespace MultiWidth

def NatFSM.fsmUnaryIndexUle (a : NatFSM wcard tcard bcard ncard icard pcard v) :
    FSM (StateSpace wcard tcard bcard ncard icard pcard) :=
  composeUnaryAux (FSM.ls true) a.toFsm

def fsmUnaryNeqUpto (a : NatFSM wcard tcard bcard ncard icard pcard (.ofDep v))
    (b : NatFSM wcard tcard bcard ncard icard pcard (.ofDep w)) : FSM (StateSpace wcard tcard bcard ncard icard pcard) :=
  composeUnaryAux FSM.scanOr (a.fsmUnaryIndexUle ^^^ b.fsmUnaryIndexUle)
</local_ctx>

<target_theorem>
@[simp]
theorem eval_fsmUnaryNeqUpto_eq_decide
    (a : NatFSM wcard tcard bcard ncard icard pcard (.ofDep v))
    (b : NatFSM wcard tcard bcard ncard icard pcard (.ofDep w))
    {wenv : WidthExpr.Env wcard}
    {fsmEnv : StateSpace wcard tcard bcard ncard icard pcard → BitStream}
    (henv : HWidthEnv fsmEnv wenv)
    (ha : HNatFSMToBitstream a) (hb : HNatFSMToBitstream b) :
    ((fsmUnaryNeqUpto a b).eval fsmEnv) i =
    (decide (min i (v.toNat wenv) ≠ min i (w.toNat wenv))) :=
</target_theorem>

