Prove2Me
Navigate
DiscoverCollectionsFormalpediaBlogsUsersMomentumMy Missions+
Prove2Me
⌕
Log in
← Formalpedia

κ-improvement development, part 19: item-language primitives

Definition
IntMul_Kappa_K_Defs19

by xuanji · Oct 14, 2026 · Mathlib 0df444a (Lean v4.33.1)

complexity-theoryinteger-multiplicationkappa-improvement

Definitions (part 19): item-language programs and cost functions for the κ>0 machine primitives (fine-cost moves, uniform interchange, Lemma 12, Gaussian record passes, Proposition 14 and Lemma 13 pieces).

Source modules (in order): Solutions.KFNSel, Solutions.KFNRole, Solutions.KFNPhase, Solutions.KFNImpl, Solutions.KFNGStep, Solutions.KFNWrap, Solutions.KFNIL, Solutions.KFNPhSem, Solutions.KFNGate, Solutions.KFNNode, Solutions.KFNRec, Solutions.KFNStep, Solutions.KFNPad, Solutions.KFNPieces, Solutions.KFNTop, Solutions.KFNLayer, Solutions.KFMErr, Solutions.KFMErr3, Solutions.KFNP14, Solutions.KFNClosed, Solutions.KFMPhase, Solutions.KFMSetup.

The file was generated from the development by deleting all theorems not needed by the definitions; it keeps all definitions plus the lemmas the definitions themselves need (proof fields of structures, decreasing_by facts) and simple @[simp]/rfl lemmas.

Definition code
-- OpenAI-preprint / κ-improvement development (integer-multiplication-kappa), generated by skeleton subtraction.

import Definitions.Def_IntMul_Kappa_K_Defs18
import Definitions.Def_IntMul_HvdH_BApprox
import Definitions.Def_IntMul_HvdH_DiagApprox
import Definitions.Def_IntMul_HvdH_EApprox
import Definitions.Def_IntMul_HvdH_FPApprox
import Definitions.Def_IntMul_HvdH_JApprox
import Definitions.Def_IntMul_HvdH_SApprox

set_option autoImplicit false
set_option relaxedAutoImplicit false
set_option maxHeartbeats 1000000

section
-- Source module: Solutions.KFNSel
/-!
# KFN: selected-bit operators by record strides

A selected-bit operator on a record array only needs, for every selected bit `i`, its record
stride `st i`: bit `i` of record `j` is `j / st i % 2` (`fbit`), and setting the selected bits to
`y` moves to record `fset st j y = j + Σ_i (y_i - bit_i) st_i`.  `selOpF st n T xs` is the
selected-bit operator in these terms.

* `SLaws st n`: the strides are those of a genuine selected-bit structure on `n` records
  (`fset` stays below `n` and reads back `y`).
* `selOpF_mul`, `selOpF_one`, `selOpF_diagonal`: the operator calculus.
* `StrideSel Sb st`: a `SelBits` structure whose bits/sets are given by the strides;
  `selOp_eq_selOpF` and `slaws_of_strideSel`.
* `strideSel_layer`: the layer layout `[P] × [2^K]^D × [S]` has strides `stT K D S ρ i`
  (independent of `P`).
* `subOp g T` (`T` on the bits `g κ`, identity elsewhere) and **`selOpF_subOp`**:
  `selOpF st n (subOp g T) = selOpF (st ∘ g) n T`.  This one lemma gives reindexing
  (`g` an equivalence, `subOp_tens`), the child slots (`slotOp_eq_subOp`) and the pieces
  (`embed_eq_subOp`).
-/

set_option linter.unusedSimpArgs false
set_option linter.unusedVariables false
set_option linter.unusedSectionVars false

namespace NLogN.KFN

open AModel Matrix Finset

section Basic

variable {ι : Type*} [Fintype ι] [DecidableEq ι]

/-- Bit `i` of record `j`. -/
def fbit (st : ι → ℕ) (j : ℕ) : ι → Fin 2 := fun i => ⟨j / st i % 2, Nat.mod_lt _ (by norm_num)⟩

/-- The record with the selected bits set to `y`, as an integer. -/
def fsetZ (st : ι → ℕ) (j : ℕ) (y : ι → Fin 2) : ℤ :=
  (j : ℤ) + ∑ i, (((y i : ℕ) : ℤ) - ((fbit st j i : ℕ) : ℤ)) * (st i : ℤ)

/-- The record with the selected bits set to `y`. -/
def fset (st : ι → ℕ) (j : ℕ) (y : ι → Fin 2) : ℕ := (fsetZ st j y).toNat

/-- The strides describe a selected-bit structure on `n` records. -/
structure SLaws (st : ι → ℕ) (n : ℕ) : Prop where
  nonneg : ∀ j < n, ∀ y, 0 ≤ fsetZ st j y
  lt : ∀ j < n, ∀ y, fset st j y < n
  bit_set : ∀ j < n, ∀ y, fbit st (fset st j y) = y

variable {M : Type*} [AddCommMonoid M] [Module ℂ M]

/-- The selected-bit operator `T` on `n` records with strides `st`. -/
noncomputable def selOpF (st : ι → ℕ) (n : ℕ) (T : Matrix (ι → Fin 2) (ι → Fin 2) ℂ)
    (xs : List M) : List M :=
  (List.range n).map fun j => ∑ y, T (fbit st j) y • xs.getD (fset st j y) 0

end Basic

/-! ## The bridge to `SelBits` -/

section Bridge

variable {sh : Shape} {ι : Type*} [Fintype ι] [DecidableEq ι]

/-- A `SelBits` structure described by record strides. -/
def StrideSel (Sb : Butterfly.SelBits sh ι) (st : ι → ℕ) : Prop :=
  ∀ j < vol sh, Sb.bits (decode sh j) = fbit st j ∧
    ∀ y, ((encode sh (Sb.set (decode sh j) y) : ℕ) : ℤ) = fsetZ st j y

variable {M : Type*} [AddCommMonoid M] [Module ℂ M]

end Bridge

/-! ## The layer layout -/

section Layer

variable {P K D S ρ : ℕ}

end Layer

/-! ## Operators on a subfamily of the selected bits -/

section Sub

variable {ι κ : Type*} [Fintype ι] [DecidableEq ι] [Fintype κ] [DecidableEq κ]

/-- `T` on the selected bits `g κ`, identity on the others. -/
def subOp (g : κ → ι) (T : Matrix (κ → Fin 2) (κ → Fin 2) ℂ) : Matrix (ι → Fin 2) (ι → Fin 2) ℂ :=
  fun x y => if ∀ i, (∀ k, g k ≠ i) → x i = y i then T (x ∘ g) (y ∘ g) else 0

/-- Extension of bits on `g κ` by the bits of `x` elsewhere. -/
noncomputable def extB (g : κ → ι) (x : ι → Fin 2) (z : κ → Fin 2) : ι → Fin 2 := by
  classical
  exact fun i => if h : ∃ k, g k = i then z (Classical.choose h) else x i

variable {M : Type*} [AddCommMonoid M] [Module ℂ M]

end Sub

/-! ## Slots and pieces as subfamilies -/

end NLogN.KFN

end

section
-- Source module: Solutions.KFNRole
/-!
# KFN: the role streams of a network invocation

A network state on `W` roles is stored role-major: role `w` is a list `X w` of `n` records, and
record `j` of a role carries the group address `fbit st j : Addr m κ` (selected bits with record
strides `st`, `KFNSel`).  `roleOpF st n A X` is the action of a network operator
`A : ROp (Fin W) m κ` on these streams.

* `roleOpF_mul`, `roleOpF_one`: the operator calculus.
* `roleOpF_blockOp`, `roleOpF_wireOp`, `roleOpF_roleDiag`: block operators act per role.
* The steps of `P8Lift.RStep`: `roleOpF_gate` (a linear combination of whole roles),
  `roleOpF_perm` (role permutation), `roleOpF_phase`, `roleOpF_rowAdd`, `roleOpF_child`
  (`selOpF` on one role; a child acts with the restricted strides of its slot).
* **`roleOpF_net`**: the network acts as the sequence of its steps, and for an interface
  (`Prop8IfaceR.correct`) **`roleOpF_iface`**: running the steps of `J.net` one after the other
  computes `selOpF st n (tens Cm)` on every role.
-/

set_option linter.unusedSimpArgs false
set_option linter.unusedVariables false
set_option linter.unusedSectionVars false

namespace NLogN.KFN

open AModel Matrix Finset P8Lift Butterfly

section Role

variable {W m : ℕ} {κ : Type} [Fintype κ] [DecidableEq κ] {M : Type*} [AddCommMonoid M]
  [Module ℂ M]

/-- The action of a network operator on role streams. -/
noncomputable def roleOpF (st : Fin m × κ → ℕ) (n : ℕ) (A : ROp (Fin W) m κ)
    (X : Fin W → List M) : Fin W → List M := fun w =>
  (List.range n).map fun j =>
    ∑ q : Fin W × Addr m κ, A (w, fbit st j) q • (X q.1).getD (fset st j q.2) 0

/-! ## The steps -/

/-! ## The network -/

/-- Run the steps one after the other. -/
noncomputable def runSteps (st : Fin m × κ → ℕ) (n : ℕ) (T : Butterfly.Op κ) :
    List (RStep (Fin W) m) → (Fin W → List M) → (Fin W → List M)
  | [], X => X
  | s :: l, X => runSteps st n T l (roleOpF st n (s.den T) X)

end Role

end NLogN.KFN

end

section
-- Source module: Solutions.KFNPhase
/-!
# KFN: a linear-time phase pass on a blocked stream

`phL R0 t B u aE` multiplies the `B · (R0 · 2^t)` Gaussian entries on top of the data stack by
`i^{E}`, where the exponent of entry `q` is read from the table
`tblG (replicate R0 (u mod 4)) aE t` (built by `t` doublings, `KFG.dblP`) at position
`q mod (R0 · 2^t)`:
`E = u + Σ_{p<t} aE p · ⌊q / R0 / 2^p⌋ mod 2` (`getD_tblR`).

Steps: build the table (`R0` pushes and `t` doublings, `O(R0 2^t)`), then for each of the `B`
blocks one multiply loop (`KFG.mulB`, table `xA → xB`, results to `qO`) and one move of the table
back (`xB → xA`); finally drop the table and move the results back to the data stack.
Cost `O(B · R0 2^t · (w + 1) + (t + B) (Z + 1))` (`phL_fsp`).
-/

set_option linter.unusedSimpArgs false
set_option linter.unusedVariables false

namespace NLogN.KFN

open IntMul RS AModel KIL KFD KFB KFG Complex

/-- The counter of the block loop. -/
abbrev cO : Fin HS := 46

/-! ## Tables -/

/-- The table after `t` doublings of `T0`. -/
def tblG (T0 : List ℤ) (aE : ℕ → ℕ) : ℕ → List ℤ
  | 0 => T0
  | t + 1 => dblL ((aE t % 4 : ℕ) : ℤ) (tblG T0 aE t)

/-! ## Building the table -/

/-- `R0` copies of `v` on `xA`. -/
def initP (R0 : ℕ) (v : ℤ) : RS := .rep NLogN.KFB.c1 (.lit (R0 : ℤ)) (.push xA (.lit v))

/-- `t` doublings. -/
def cTblG (M t Z : ℕ) : ℕ := 120000 * M * 2 ^ t + t * (10000 * (Z + 2) + 20001) + 1

/-! ## The multiply loop with a nonempty result stack -/

/-! ## One block -/

/-- One block: multiply by the table, then move the table back. -/
def blkP : RS := .seq (.rep NLogN.KFB.c1 (.reg xN) mulB) (NLogN.mvK xB xA NLogN.KFB.c1 (.reg xN))

/-- Cost of one block of `M` entries. -/
def cBlk (w M Z : ℕ) : ℕ := M * (cMulB w + 5000) + 1000 * (Z + 2) + 5000

/-! ## All blocks -/

/-- `B` copies of the table. -/
def repT (B : ℕ) (T : List ℤ) : List ℤ := (List.replicate B T).flatten

/-! ## The phase pass -/

/-- **The phase pass** on the `B · R0 · 2^t` entries on top of the data stack. -/
def phL (R0 t B u : ℕ) (aE : ℕ → ℕ) : RS :=
  .seq (initP R0 ((u % 4 : ℕ) : ℤ))
  (.seq (.push xN (.lit (R0 : ℤ)))
  (.seq (tblP aE t)
  (.seq (.rep NLogN.KFN.cO (.lit (B : ℤ)) blkP)
  (.seq (NLogN.mvK xA xB NLogN.KFB.c1 (.reg xN))
  (.seq (.rep NLogN.KFB.c1 (.reg xN) (.pop xB))
  (.seq (.asg xN (.lit ((2 * (B * (R0 * 2 ^ t)) : ℕ) : ℤ)))
  (.seq (NLogN.mvK qO 0 NLogN.KFB.c1 (.reg xN)) (.pop xN))))))))

/-- Cost of the phase pass on `V = B · R0 · 2^t` entries. -/
def cPhL (w V t B Z : ℕ) : ℕ := V * (cMulB w + 300000 + 500 * w) + (t + B + 10) * (20000 * (Z + 2) + 30000)

/-- The rotated stream. -/
noncomputable def phOut (R0 t B u : ℕ) (aE : ℕ → ℕ) (zs : List GI) : List GI :=
  KFG.mulL (repT B (tblG (List.replicate R0 ((u % 4 : ℕ) : ℤ)) aE t)) zs

end NLogN.KFN

end

section
-- Source module: Solutions.KFNImpl
/-!
# KFN: implementations of selected-bit operators and of network steps

* `ClN f`: the clean scratch used by all KFN programs (`KFB.Cl`, `KFG.ClP`, `KFG.ClT`, and the
  block counter `cO`).
* `SImpl r st n T code e dw cost`: on a clean managed state whose data stack starts with a record
  array `zs` (scale `F`, width `w`) representing `xs` (`n` records of `r` entries), `code` leaves
  an array representing `selOpF st n T xs` at scale `F + e`, width `w + dw`, at fine cost
  `cost w`.  This is `KFH.LImpl` with the layout given by record strides (`lImpl_of_sImpl`).
* `RImpl r n st A code e dw cost`: the same for a network operator `A` acting on `W` role streams
  stored one after the other (`flatR X`), through `roleOpF`.
* `RImpl.comp`, `rImpl_list` (a list of steps implements `denListR`), and
  `sImpl_of_rImpl_roleDiag`: an implementation of `roleDiag T` is one of `T` on the
  concatenated streams (strides inside the role blocks, `selOpF_flatR`).
-/

set_option linter.unusedSimpArgs false
set_option linter.unusedVariables false
set_option linter.unusedSectionVars false

namespace NLogN.KFN

open IntMul RS AModel KIL KFD KFB KFG KFH Complex P8Lift Butterfly

/-! ## Clean scratch -/

/-- The clean scratch of the KFN programs. -/
structure ClN (f : Fin HS → List ℤ) : Prop where
  cl : KFB.Cl f
  p : KFG.ClP f
  t : KFG.ClT f
  o : f NLogN.KFN.cO = []

/-! ## Role streams stored one after the other -/

/-- The streams one after the other. -/
def flatR {α : Type*} {W : ℕ} (X : Fin W → List α) : List α := (List.finRange W).flatMap X

/-! ## Implementations -/

variable {Pp : ℕ} {I : List Sym} {iprog : Fin Pp → IStmt HS Pp}

/-- `code` implements the selected-bit operator `T` (record strides `st`, `n` records). -/
def SImpl {ι : Type*} [Fintype ι] [DecidableEq ι] (r : ℕ) (st : ι → ℕ) (n : ℕ)
    (T : Matrix (ι → Fin 2) (ι → Fin 2) ℂ) (code : RS) (e dw : ℕ) (cost : ℕ → ℕ) : Prop :=
  ∀ (s : IState HS) (f : Fin HS → List ℤ) (zs : List GI) (l : List ℤ) (xs : List (Fin r → ℂ))
    (F w : ℕ), ClN f → f 0 = gflat zs ++ l → RecRep r F zs xs → xs.length = n → NLogN.KFB.GB w zs →
    ∃ zs', RecRep r (F + e) zs' (selOpF st n T xs) ∧ NLogN.KFB.GB (w + dw) zs' ∧
      FSp code (encK s f) (encK s (Function.update f 0 (gflat zs' ++ l))) (cost w)

section SImplLemmas

variable {ι : Type*} [Fintype ι] [DecidableEq ι] {r : ℕ} {st : ι → ℕ} {n : ℕ}

end SImplLemmas

section RImplDefs

variable {W m : ℕ} {κ : Type} [Fintype κ] [DecidableEq κ]

/-- `code` implements the network operator `A` on `W` role streams of `n` records each. -/
def RImpl (r n : ℕ) (st : Fin m × κ → ℕ) (A : ROp (Fin W) m κ) (code : RS) (e dw : ℕ)
    (cost : ℕ → ℕ) : Prop :=
  ∀ (s : IState HS) (f : Fin HS → List ℤ) (zs : List GI) (l : List ℤ)
    (X : Fin W → List (Fin r → ℂ)) (F w : ℕ), ClN f → f 0 = gflat zs ++ l →
    RecRep r F zs (flatR X) → (∀ v, (X v).length = n) → NLogN.KFB.GB w zs →
    ∃ zs', RecRep r (F + e) zs' (flatR (roleOpF st n A X)) ∧ NLogN.KFB.GB (w + dw) zs' ∧
      FSp code (encK s f) (encK s (Function.update f 0 (gflat zs' ++ l))) (cost w)

variable {r n : ℕ} {st : Fin m × κ → ℕ}

/-- Sequence of programs. -/
def seqL : List RS → RS
  | [] => .skip
  | c :: cs => .seq c (seqL cs)

/-- Cost of a list of steps. -/
def costL {α : Type*} (cost : α → ℕ → ℕ) (dw : α → ℕ) : List α → ℕ → ℕ
  | [], _ => 1
  | a :: l, w => cost a w + costL cost dw l (w + dw a)

end RImplDefs

/-! ## Operators acting inside the role blocks -/

section Blocks

variable {ι : Type*} [Fintype ι] [DecidableEq ι] {M : Type*} [AddCommMonoid M] [Module ℂ M]

end Blocks

section Diag

variable {W m : ℕ} {κ : Type} [Fintype κ] [DecidableEq κ] {r n : ℕ} {st : Fin m × κ → ℕ}

end Diag

end NLogN.KFN

end

section
-- Source module: Solutions.KFNGStep
/-!
# KFN: gates and role permutations on role streams of records

* `enc_of_rec` / `rec_of_enc`: role streams of records (`RecRep r F zs (flatR X)`) are the
  KFG stream encoding `Enc W (n r) (const F) zs (yR r X)`.
* Scale shifts: the gate programs depend only on scale differences (`gateP_shE`, …), so one
  program serves every scale `F`.
* Scale bookkeeping (`gateE_bnd`, `gateE_top`, `gateE_zero`, `gateE_lev`) and the width / cost
  bounds `gateW_le`, `cGate_le` (shifts of at most one bit per atom).
* **`rImpl_gate`**: a gate `gateMat W as` (atoms with `h ≤ 1`, targets never sources) followed by
  a leveling pass (`c = 0` atoms bringing every role to the common scale `F + gδ as`).
* **`rImpl_perm`**: a role permutation.
-/

set_option linter.unusedSimpArgs false
set_option linter.unusedVariables false
set_option linter.unusedSectionVars false

namespace NLogN.KFN

open IntMul RS AModel KIL KFD KFB KFG KFH Complex P8Lift Butterfly

/-! ## Streams of records as the KFG encoding -/

section EncBridge

variable {W r n F : ℕ}

/-- Entry `p` of role `v` (record `p / r`, coefficient `p mod r`). -/
noncomputable def yR (r : ℕ) (X : Fin W → List (Fin r → ℂ)) : ℕ → ℕ → ℂ := fun v p =>
  if h : v < W ∧ 0 < r then ((X ⟨v, h.1⟩).getD (p / r) 0) ⟨p % r, Nat.mod_lt _ h.2⟩ else 0

end EncBridge

/-! ## Gate programs depend only on scale differences -/

section Shift

/-- Shift all scales by `F`. -/
def shE (F : ℕ) (e : ℕ → ℕ) : ℕ → ℕ := fun t => e t + F

end Shift

/-! ## Scale bookkeeping -/

section Scales

/-- The leveling atoms: every role `t ≠ t0` gets `0 ·` role `t0`. -/
def levA (W t0 : ℕ) : List KFG.Atom :=
  ((List.range W).filter fun t => t ≠ t0).map fun t => ⟨t, t0, (0, 0), 0⟩

end Scales

/-! ## Width and cost of a gate pass -/

section Bounds

end Bounds

/-! ## The gate step -/

section GateStep

/-- The first atom with `h = 1`. -/
def h1Atom (as : List KFG.Atom) : Option KFG.Atom := as.find? fun a => a.h == 1

/-- The scale added by a gate step. -/
def gδ (as : List KFG.Atom) : ℕ := if (h1Atom as).isSome then 1 else 0

/-- The leveling atoms after a gate. -/
def levOf (W : ℕ) (as : List KFG.Atom) : List KFG.Atom :=
  match h1Atom as with
  | some a0 => levA W a0.t
  | none => []

/-- The program of a gate step: the atoms, then the leveling. -/
def gateC (W L : ℕ) (as : List KFG.Atom) : RS :=
  .seq (gateP as (fun _ => 0) L) (gateP (levOf W as) (gateE as (fun _ => 0)) L)

/-- Cost of a gate step. -/
def cGateC (W L Z A w : ℕ) : ℕ :=
  A * cAtom (w + 3 * A) 1 L W Z + W * cAtom (w + 3 * A + 3 * W) 1 L W Z + 2

variable {W m : ℕ} {κ : Type} [Fintype κ] [DecidableEq κ]

end GateStep

end NLogN.KFN

end

section
-- Source module: Solutions.KFNWrap
/-!
# KFN: running a stream program on one role

`wrapC W L w e code`: swap role `w` to the front (one pair pass), run `code` on the first
segment (the other roles stay below it on the data stack), bring the other roles to the new
scale `F + e` (leveling atoms `0 · role 0`), and swap back.

**`rImpl_onRole`**: if `code` implements a selected-bit operator `Tw` on single streams
(`SImpl`), the wrapper implements every network operator `A` that acts as `Tw` on role `w` and
as the identity on the other roles (`roleOpF_phase`, `roleOpF_rowAdd`, `roleOpF_child`).
-/

set_option linter.unusedSimpArgs false
set_option linter.unusedVariables false
set_option linter.unusedSectionVars false

namespace NLogN.KFN

open IntMul RS AModel KIL KFD KFB KFG KFH Complex P8Lift Butterfly

/-! ## Widths and costs with a general scale window -/

section Bounds2

end Bounds2

/-! ## Segments of the encoding -/

section Seg

end Seg

/-! ## The wrapper -/

section Wrap

/-- The swap bringing role `w` to the front (none for `w = 0`). -/
def swL (w : ℕ) : List (ℕ × ℕ) := if w = 0 then [] else [(0, w)]

/-- Run `code` (scale `+e`) on role `w`. -/
def wrapC (W L w e : ℕ) (code : RS) : RS :=
  .seq (swapsP L (NLogN.KFN.swL w)) (.seq code
    (.seq (gateP (levA W 0) (Function.update (fun _ => 0) 0 e) L) (swapsP L (NLogN.KFN.swL w))))

/-- Cost of the wrapper around a program of cost `cost`. -/
def cWrapR (W L Z e dw : ℕ) (cost : ℕ → ℕ) (w : ℕ) : ℕ :=
  cost w + (W + 2) * cAtom (w + dw + (e + 2) * W) e L W Z + 3

variable {W m : ℕ} {κ : Type} [Fintype κ] [DecidableEq κ]

end Wrap

end NLogN.KFN

end

section
-- Source module: Solutions.KFNIL
/-!
# KFN: implementations by item-language programs

The row additions of Lemma 13 are item-language programs (`IStmt HS 1` calling the Lemma 12
routines under a fixed `iprog`), whose code depends on the input width `w`.  This file gives the
`IStmt` versions of the implementation predicates, with **code families `ℕ → IStmt HS Pp`**
indexed by the input width, run under a fixed `I`, `iprog`:

* `SImplI I iprog r st n T code e dw cost`, `RImplI ...` (as `SImpl`, `RImpl`, with
  `IRuns I iprog (code w)` in place of `FSp code`);
* lifts of the register-program versions (`SImpl.toI`, `RImpl.toI`, via `FSp.irun`);
* `SImplI.comp`, `RImplI.comp`, `rImplI_list`, `sImplI_of_rImplI_roleDiag`, `rImplI_onRole`.
-/

set_option linter.unusedSimpArgs false
set_option linter.unusedVariables false
set_option linter.unusedSectionVars false

namespace NLogN.KFN

open IntMul RS AModel KIL KFD KFB KFG KFH Complex P8Lift Butterfly

variable {Pp : ℕ} {I : List Sym} {iprog : Fin Pp → IStmt HS Pp}

/-- `code w` implements the selected-bit operator `T` on inputs of width `w`. -/
def SImplI (I : List Sym) (iprog : Fin Pp → IStmt HS Pp) {ι : Type*} [Fintype ι] [DecidableEq ι]
    (r : ℕ) (st : ι → ℕ) (n : ℕ) (T : Matrix (ι → Fin 2) (ι → Fin 2) ℂ) (code : ℕ → IStmt HS Pp)
    (e dw : ℕ) (cost : ℕ → ℕ) : Prop :=
  ∀ (s : IState HS) (f : Fin HS → List ℤ) (zs : List GI) (l : List ℤ) (xs : List (Fin r → ℂ))
    (F w : ℕ), ClN f → f 0 = gflat zs ++ l → RecRep r F zs xs → xs.length = n → NLogN.KFB.GB w zs →
    ∃ zs', RecRep r (F + e) zs' (selOpF st n T xs) ∧ NLogN.KFB.GB (w + dw) zs' ∧
      IRuns I iprog (code w) (encK s f) (encK s (Function.update f 0 (gflat zs' ++ l))) (cost w)

section SImplILemmas

variable {ι : Type*} [Fintype ι] [DecidableEq ι] {r : ℕ} {st : ι → ℕ} {n : ℕ}

/-- Sequential composition of code families. -/
def seqI (c1 c2 : ℕ → IStmt HS Pp) (d1 : ℕ) : ℕ → IStmt HS Pp :=
  fun w => .seq (c1 w) (c2 (w + d1))

end SImplILemmas

section RImplIDefs

variable {W m : ℕ} {κ : Type} [Fintype κ] [DecidableEq κ]

/-- `code w` implements the network operator `A` on `W` role streams of `n` records each. -/
def RImplI (I : List Sym) (iprog : Fin Pp → IStmt HS Pp) (r n : ℕ) (st : Fin m × κ → ℕ)
    (A : ROp (Fin W) m κ) (code : ℕ → IStmt HS Pp) (e dw : ℕ) (cost : ℕ → ℕ) : Prop :=
  ∀ (s : IState HS) (f : Fin HS → List ℤ) (zs : List GI) (l : List ℤ)
    (X : Fin W → List (Fin r → ℂ)) (F w : ℕ), ClN f → f 0 = gflat zs ++ l →
    RecRep r F zs (flatR X) → (∀ v, (X v).length = n) → NLogN.KFB.GB w zs →
    ∃ zs', RecRep r (F + e) zs' (flatR (roleOpF st n A X)) ∧ NLogN.KFB.GB (w + dw) zs' ∧
      IRuns I iprog (code w) (encK s f) (encK s (Function.update f 0 (gflat zs' ++ l))) (cost w)

variable {r n : ℕ} {st : Fin m × κ → ℕ}

/-- Sequence of code families (the `a`-th one starts at the width left by the previous ones). -/
def seqLI {α : Type*} (code : α → ℕ → IStmt HS Pp) (dw : α → ℕ) : List α → ℕ → IStmt HS Pp
  | [] => fun _ => .skip
  | a :: l => seqI (code a) (seqLI code dw l) (dw a)

end RImplIDefs

section DiagI

variable {W m : ℕ} {κ : Type} [Fintype κ] [DecidableEq κ] {r n : ℕ} {st : Fin m × κ → ℕ}

end DiagI

section WrapI

/-- Run the code family `code` (scale `+e`) on role `w`. -/
def wrapCI (W L w e : ℕ) (code : ℕ → IStmt HS Pp) : ℕ → IStmt HS Pp := fun x =>
  .seq (fcode (swapsP L (NLogN.KFN.swL w))) (.seq (code x)
    (.seq (fcode (gateP (levA W 0) (Function.update (fun _ => 0) 0 e) L))
      (fcode (swapsP L (NLogN.KFN.swL w)))))

variable {W m : ℕ} {κ : Type} [Fintype κ] [DecidableEq κ]

end WrapI

end NLogN.KFN

end

section
-- Source module: Solutions.KFNPhSem
/-!
# KFN: the phase pass as a selected-bit operator

For selected bits `i : ι` at record strides `2^{pos i} · S` (`pos i < t`) on `B · 2^t · S`
records of `r` entries, the phase pass `phL (S r) t B u (aEof pos a')` implements the diagonal
`x ↦ i^{u + Σ_i a'_i x_i}` (**`sImpl_phase`**), exactly (no scale, no width change), at cost
`cPhL`, linear in the data.
-/

set_option linter.unusedSimpArgs false
set_option linter.unusedVariables false
set_option linter.unusedSectionVars false

namespace NLogN.KFN

open IntMul RS AModel KIL KFD KFB KFG KFH Complex P8Lift Butterfly

/-- The doubling exponents: `aE p = Σ_{pos i = p} a'_i`. -/
def aEof {ι : Type*} [Fintype ι] (pos : ι → ℕ) (a' : ι → ℕ) (p : ℕ) : ℕ :=
  ∑ i ∈ Finset.univ.filter (fun i => pos i = p), a' i

end NLogN.KFN

end

section
-- Source module: Solutions.KFNGate
/-!
# KFN: classification of the scalar gates of the complex network (task 1)

Every `RStep.gate G` of `P8Lift.complexIface.net` is one of the two kinds of fine IL gates of
KFG:

* a **dyadic atom gate** `G = gateMat W_c as` (`KFG.gateMat`: `1 + Σ_a (c_a/2^{h_a}) e_{t_a,s_a}`)
  for a list of atoms with `c_a ∈ {±1}`, `h_a ≤ 1`, every atom `Ok` and no target of the list a
  source of the list (`KFG.NoTS`), so `KFG.gate_iruns` applies; these are the side injections,
  scatters, copies and gathers of the schedule (2) of `NetComplexLemma5` and their inverses;
* the **sign gate** `fixG`, a diagonal `±1` matrix (one unit scaling `KFG.UAtom` with `u = -1`
  per physical `X` wire).

`GOK G`: `G = 1 + Σ_{x ∈ l} (ε_x / 2^{h_x}) e_{t_x, s_x}` with `ε_x = ±1`, `h_x ≤ 1`, targets
never sources.  `cxNamed_GOK`: every gate of `cxNamed` is `GOK`.  `GOK_atoms`: a `GOK` matrix
transported along `W ≃ Fin n` is `gateMat n as` for an `Ok`, `NoTS` atom list.
**`complexIface_gate_class`**: the classification of all gate steps of `complexIface`.
-/

set_option linter.unusedSimpArgs false
set_option linter.unusedVariables false
set_option linter.unusedSectionVars false
set_option synthInstance.maxSize 512

namespace NLogN.KFN

open Matrix Finset Complex

section Generic

variable {W : Type*} [Fintype W] [DecidableEq W]

/-- The matrix of an elementary dyadic list. -/
noncomputable def eMat (l : List (W × W × ℤ × ℕ)) : Matrix W W ℂ :=
  (l.map fun x => single x.1 x.2.1 ((x.2.2.1 : ℂ) / 2 ^ x.2.2.2)).sum

/-- A dyadic elementary gate whose targets are never sources. -/
def GOK (G : Matrix W W ℂ) : Prop :=
  ∃ l : List (W × W × ℤ × ℕ), G = 1 + eMat l ∧ (∀ x ∈ l, ∀ y ∈ l, x.1 ≠ y.2.1) ∧
    ∀ x ∈ l, (x.2.2.1 = 1 ∨ x.2.2.1 = -1) ∧ x.2.2.2 ≤ 1

/-- The atoms of a `GOK` list, transported along `e : W ≃ Fin n`. -/
def atomsOf {n : ℕ} (e : W ≃ Fin n) (l : List (W × W × ℤ × ℕ)) : List KFG.Atom :=
  l.map fun x => ⟨(e x.1).val, (e x.2.1).val, (x.2.2.1, 0), x.2.2.2⟩

end Generic

/-! ## The gates of the complex construction -/

section Complex

variable {h : ℕ} {T : Type*} [Fintype T] [DecidableEq T] {ind : T → Finset (Fin h)}

variable {Wt : Type*} [Fintype Wt] [DecidableEq Wt]

end Complex

/-! ## The step lists -/

section Steps

open P8Lift

variable {R : Type} [Fintype R] [DecidableEq R]

end Steps

/-! ## The classification for `complexIface` -/

end NLogN.KFN

end

section
-- Source module: Solutions.KFNNode
/-!
# KFN: one node of the recursive `C`-layer

A node runs the steps of an interface `J : Prop8IfaceR W m s` on `W` role streams of `n`
records; its bits are `Fin m × κ` (rows × the bits of a child), at record strides `st`.

* **`sImpl_node`**: implementations of the steps compose to an implementation of `tens Cm`
  on the `W · n` records (`rImpl_list`, `J.correct`, `sImpl_of_rImpl_roleDiag`).
* Step builders on power-of-two strides `st p = 2^{pos p} · S₀` (`n = B · 2^t · S₀`):
  `rImpl_phaseStep` (phase pass on one role), `rImpl_fixG` (a `±1` role diagonal as a list of
  phase steps), `rImpl_rowStep` (a row addition from any single-stream implementation),
  `rImpl_childStep` (forward child from an implementation of the child, the inverse child via
  `tens Cinv = (-i)^{|κ|} ZD · tens Cm · ZD`, `sImpl_cinv`).
-/

set_option linter.unusedSimpArgs false
set_option linter.unusedVariables false
set_option linter.unusedSectionVars false

namespace NLogN.KFN

open IntMul RS AModel KIL KFD KFB KFG KFH Complex P8Lift Butterfly

section Node

variable {Pp : ℕ} {Isym : List Sym} {iprog : Fin Pp → IStmt HS Pp}
variable {W m : ℕ} {κ : Type} [Fintype κ] [DecidableEq κ]

/-! ## Phase steps -/

/-- Code of a phase pass with exponents `u + Σ a'_i x_i` on strides `2^{pos i} S₀`. -/
def phC {ι : Type*} [Fintype ι] (pos : ι → ℕ) (S0 r t B u : ℕ) (a' : ι → ℕ) : RS :=
  phL (S0 * r) t B u (aEof pos a')

/-- The phase steps negating the roles of a list. -/
def negSteps (l : List (Fin W)) : List (RStep (Fin W) m) := l.map fun w => RStep.phase w 2 0 0

/-! ## Row additions and child calls -/

/-- The inverse child: `ZD`, then the forward child, then `(-i)^{|κ|} ZD`. -/
def cinvC (pos : κ → ℕ) (S0 r t B : ℕ) (code : ℕ → IStmt HS Pp) (dw : ℕ) : ℕ → IStmt HS Pp :=
  seqI (seqI (fun _ => fcode (phC pos S0 r t B 0 (fun _ => 2))) code 0)
    (fun _ => fcode (phC pos S0 r t B (3 * Fintype.card κ) (fun _ => 2))) (0 + dw)

end Node

end NLogN.KFN

end

section
-- Source module: Solutions.KFNRec
/-!
# KFN: the recursive `C`-layer — local step bounds

Parameters: an interface `J : Prop8IfaceR W m s` whose gates are atom lists (at most `A`
atoms) or `±1` role diagonals (`GClass`), records of `r` entries, a size bound `Z`, and a
monotone "log-size" cost profile `Ψ ≥ Z + 2`.  The row additions are an abstract hypothesis
(`RowHyp`, e.g. Lemma 13): cost `CR · n · (r (w+1) (e+1)^τ + Ψ w)` on `n` records whose rows have
`e` bits.

Unit of cost: `Xf r Ψ v = r (v + 1) + Ψ v` per record at width `v`.

This file: the recursion constants (`Eb` scale, `DWb` width, `Ob` offsets, `Whb` cumulative
widths, `cb` cost coefficients), the per-step cost bounds, and **`step_ok`**: every step of
`J.net` at level `k+1` has an implementation with the bounds, given the level-`k` claim `Lv`.
-/

set_option linter.unusedSimpArgs false
set_option linter.unusedVariables false
set_option linter.unusedSectionVars false

namespace NLogN.KFN

open IntMul RS AModel KIL KFD KFB KFG KFH Complex P8Lift Butterfly

/-! ## Constants of the recursion -/

/-- Scale bound: the leaf kernel has scale `1`; a node adds `≤ 1` per local step. -/
def Eb (L s : ℕ) : ℕ → ℕ
  | 0 => 1
  | k + 1 => L + s * Eb L s k

/-- Width increase of a local step. -/
def dwloc (W A : ℕ) : ℕ := 3 * A + 3 * W + 2 * W * W + 2 * W

/-- Width bound of a level. -/
def DWb (L s W A : ℕ) : ℕ → ℕ
  | 0 => 2
  | k + 1 => s * (DWb L s W A k + (Eb L s k + 2) * W) + L * dwloc W A

/-- Width offset of the cost arguments inside the steps of level `k+1`. -/
def Ob (L s W A k : ℕ) : ℕ :=
  DWb L s W A k + (Eb L s k + 2) * W + Eb L s k + dwloc W A + 10

/-- Cumulative width offset of a level. -/
def Whb (L s W A : ℕ) : ℕ → ℕ
  | 0 => 2
  | k + 1 => DWb L s W A (k + 1) + Ob L s W A k + Whb L s W A k

/-- The local cost constant. -/
def alN (W A : ℕ) : ℕ := 10000000 * (W + A + 10) ^ 3

/-- Cost coefficients (per record, per unit `Xf`). -/
noncomputable def cb (L s W A m : ℕ) (CR τ : ℝ) : ℕ → ℝ
  | 0 => 100000
  | k + 1 => (s / W : ℝ) * cb L s W A m CR τ k +
      ((s + L : ℕ) : ℝ) * ((alN W A : ℝ) + CR * ((m : ℝ) ^ k + 1) ^ τ) + 1

/-- Cost unit per record. -/
def Xf (r : ℕ) (Ψ : ℕ → ℕ) (v : ℕ) : ℕ := r * (v + 1) + Ψ v

/-! ## Classes and hypotheses -/

/-- The gates of an interface: atom lists (at most `A` atoms) or `±1` role diagonals. -/
def GClass {W m s : ℕ} (J : Prop8IfaceR W m s) (A : ℕ) : Prop :=
  ∀ G, RStep.gate G ∈ J.net →
    (∃ as : List KFG.Atom, as.length ≤ A ∧ (∀ a ∈ as, a.Ok W ∧ a.h ≤ 1) ∧ KFG.NoTS as ∧
        G = KFG.gateMat W as) ∨
      (∃ U : Finset (Fin W), G = Matrix.diagonal fun w => if w ∈ U then -1 else 1)

/-- Positions of the bits of a row family at stride `K` (descending): `pos i + K i = e`, with
the top chunk `[e - e % K, e - e % K + K)` below `t`. -/
def AffK (K t : ℕ) {N : ℕ} (pos : Fin N → ℕ) : Prop :=
  ∃ e, (∀ i, pos i + K * i.val = e) ∧ e - e % K + K ≤ t

/-- The same for `Fin m × Fin (m^k)` (row `a`, bit `b` at index `b + m^k a`). -/
def AffK2 (K t m k : ℕ) (pos : Fin m × Fin (m ^ k) → ℕ) : Prop :=
  ∃ e, (∀ p, pos p + K * (p.2.val + m ^ k * p.1.val) = e) ∧ e - e % K + K ≤ t

/-- **Row additions** (abstract; e.g. Lemma 13): on the stride-`K` layouts of the bits
`Fin m × Fin (m^k)` (`AffK2`), as produced by the layer layout of stride `K`. -/
def RowHyp {Pp : ℕ} (Isym : List Sym) (iprog : Fin Pp → IStmt HS Pp) (K m r Z : ℕ)
    (Ψ : ℕ → ℕ) (CR τ : ℝ) : Prop :=
  ∀ (k : ℕ) (pos : Fin m × Fin (m ^ k) → ℕ) (t S0 B : ℕ), Function.Injective pos →
    (∀ p, pos p < t) → AffK2 K t m k pos → 1 ≤ S0 → 1 ≤ B →
    zsz ((16 * (B * 2 ^ t * S0 * r) : ℕ) : ℤ) ≤ Z →
    ∀ (i j : Fin m) (hij : i ≠ j), ∃ (code : ℕ → IStmt HS Pp) (cost : ℕ → ℕ),
      SImplI Isym iprog r (fun p => 2 ^ pos p * S0) (B * 2 ^ t * S0)
        (Pm i j : Butterfly.Op (Fin m × Fin (m ^ k))) code 0 0 cost ∧
      ∀ w, (cost w : ℝ) ≤ CR * ((B * 2 ^ t * S0 : ℕ) : ℝ) *
        ((r : ℝ) * (w + 1) * ((m : ℝ) ^ k + 1) ^ τ + Ψ w)

/-- The level claim: `tens Cm` on `m^k` bits at power-of-two strides. -/
def Lv {Pp : ℕ} (Isym : List Sym) (iprog : Fin Pp → IStmt HS Pp) (K W m r Z : ℕ) (Ψ : ℕ → ℕ)
    (k Ek DWk Wk : ℕ) (ck : ℝ) : Prop :=
  ∀ (pos : Fin (m ^ k) → ℕ) (t S0 B : ℕ), Function.Injective pos → (∀ i, pos i < t) →
    AffK K t pos →
    1 ≤ S0 → 1 ≤ B → W ^ k ∣ B → zsz ((16 * (B * 2 ^ t * S0 * r) : ℕ) : ℤ) ≤ Z →
    ∃ (code : ℕ → IStmt HS Pp) (e dw : ℕ) (cost : ℕ → ℕ),
      SImplI Isym iprog r (fun i => 2 ^ pos i * S0) (B * 2 ^ t * S0) (Butterfly.tens Cm : Butterfly.Op (Fin (m ^ k)))
        code e dw cost ∧ e ≤ Ek ∧ dw ≤ DWk ∧
      ∀ w, (cost w : ℝ) ≤ ck * ((B * 2 ^ t * S0 : ℕ) : ℝ) * (Xf r Ψ (w + Wk) : ℝ)

/-! ## Local cost bounds -/

section LocalBounds

variable {r Z : ℕ} {Ψ : ℕ → ℕ}

end LocalBounds

end NLogN.KFN

end

section
-- Source module: Solutions.KFNStep
/-!
# KFN: the steps of a node at level `k+1`, with bounds

Node bits `Fin m × Fin (m^k)` at strides `2^{pos p} S₀`, `W` roles of `n = B · 2^t · S₀`
records each.  **`step_ok`**: every step of `J.net` has an implementation (`RImpl`) with

* scale `≤ 1` (local) or `≤ E_k` (child),
* width `≤ dwloc W A` (local) or `≤ DW_k + (E_k + 2) W` (child),
* cost `≤ [c_k n Xf(w + Ŵ_k)]_{child} + (alN + CR Γ) (W n) Xf(w + O)`.
-/

set_option linter.unusedSimpArgs false
set_option linter.unusedVariables false
set_option linter.unusedSectionVars false

namespace NLogN.KFN

open IntMul RS AModel KIL KFD KFB KFG KFH Complex P8Lift Butterfly

section Steps

variable {Pp : ℕ} {Isym : List Sym} {iprog : Fin Pp → IStmt HS Pp} {K : ℕ}
variable {W m s : ℕ} (J : Prop8IfaceR W m s) {A r Z : ℕ} {Ψ : ℕ → ℕ}

/-- The number of records of a role. -/
abbrev nR (t S0 B : ℕ) : ℕ := B * 2 ^ t * S0

/-- Code of a phase step (other steps: `skip`). -/
def phStepC (W n r : ℕ) {k : ℕ} (pos : Fin m × Fin (m ^ k) → ℕ) (S0 t B : ℕ) :
    RStep (Fin W) m → RS
  | .phase w0 k₀ k₁ a => wrapC W (n * r) w0.val 0
      (phC pos S0 r t B (k₀ + k₁ * Fintype.card (Fin (m ^ k))) (fun p => a p.1))
  | _ => .skip

end Steps

end NLogN.KFN

end

section
-- Source module: Solutions.KFNPad
/-!
# KFN: running a program on a zero-padded stream

`padC L0 Q code`: park the `L0` entries of the stream (stack `qP`), push `Q` zeros, unpark;
run `code`; park the first `L0` entries, drop the next `Q`, unpark.

**`sImpl_pad`**: if `code` implements `T` on `np ≥ n` records (strides `st`), the padded program
implements `T` on `n` records (the padding records are zero, and the selected-bit structure on
`n` records never reads them: `selOpF_pad`).
-/

set_option linter.unusedSimpArgs false
set_option linter.unusedVariables false
set_option linter.unusedSectionVars false

namespace NLogN.KFN

open IntMul RS AModel KIL KFD KFB KFG KFH Complex P8Lift Butterfly

section Lists

variable {ι : Type*} [Fintype ι] [DecidableEq ι] {M : Type*} [AddCommMonoid M] [Module ℂ M]

end Lists

/-! ## The padded program -/

/-- Pad by `Q` zero entries (the register part before the program). -/
def padPre (L0 Q : ℕ) : RS :=
  .seq (NLogN.mvK 0 qP NLogN.KFB.c1 (.lit (L0 : ℤ))) (.seq (zeroK 0 NLogN.KFB.c1 Q) (NLogN.mvK qP 0 NLogN.KFB.c1 (.lit (L0 : ℤ))))

/-- Unpad (the register part after the program). -/
def padPost (L0 Q : ℕ) : RS :=
  .seq (NLogN.mvK 0 qP NLogN.KFB.c1 (.lit (L0 : ℤ))) (.seq (dropK 0 NLogN.KFB.c1 Q) (NLogN.mvK qP 0 NLogN.KFB.c1 (.lit (L0 : ℤ))))

/-- Pad by `Q` zero entries, run `code`, unpad. -/
def padC {Pp : ℕ} (L0 Q : ℕ) (code : ℕ → IStmt HS Pp) : ℕ → IStmt HS Pp := fun w =>
  .seq (fcode (NLogN.KFN.padPre L0 Q)) (.seq (code w) (fcode (padPost L0 Q)))

/-- The cost of a move of `L0` entries of width `w`. -/
def cMv (L0 w : ℕ) : ℕ := zsz (L0 : ℤ) + 2 + cRep L0 + L0 * (250 * (w + 2))

/-- Cost of the padded program. -/
def cPadC (L0 Q Z w dw : ℕ) (cost : ℕ → ℕ) : ℕ :=
  2 * NLogN.KFN.cMv L0 w + cLp Q 8000 Z + cost w + 2 * NLogN.KFN.cMv L0 (w + dw) + cLp Q (2 * (w + dw) + 2) Z

end NLogN.KFN

end

section
-- Source module: Solutions.KFNPieces
/-!
# KFN: digit pieces

`pcs m k base R`: the pieces `(level j, offset o)` of the base-`m` digit decomposition of the
bit range `[base, base + R)`: `R / m^k` pieces of level `k`, then the remainder at the lower
levels.  Every bit of the range is covered by exactly one piece (`countP_pcs`); there are at most
`R / m^k + k m` pieces (`length_pcs`).

Operators: `subOp g (tens A) = tensF (indicator)` (`subOp_tens`); implementations of
`tensF Fₐ` compose to `tensF (∏ₐ Fₐ)` (`sImpl_tensF_list`); a family of indicators of a
partition multiplies to `A` (`prod_ind`).
-/

set_option linter.unusedSimpArgs false
set_option linter.unusedVariables false
set_option linter.unusedSectionVars false

namespace NLogN.KFN

open IntMul RS AModel KIL KFD KFB KFG KFH Complex P8Lift Butterfly

/-! ## The pieces -/

/-- Pieces `(level, offset)` of the range `[base, base + R)`. -/
def pcs (m : ℕ) : ℕ → ℕ → ℕ → List (ℕ × ℕ)
  | 0, base, R => (List.range R).map fun c => (0, base + c)
  | k + 1, base, R => (List.range (R / m ^ (k + 1))).map (fun c => (k + 1, base + c * m ^ (k + 1))) ++
      pcs m k (base + R / m ^ (k + 1) * m ^ (k + 1)) (R % m ^ (k + 1))

/-- Piece `p` covers bit `i`. -/
def covers (m : ℕ) (i : ℕ) (p : ℕ × ℕ) : Bool := decide (p.2 ≤ i ∧ i < p.2 + m ^ p.1)

/-! ## Operators -/

section Ops

variable {ι κ : Type*} [Fintype ι] [DecidableEq ι] [Fintype κ] [DecidableEq κ]

end Ops

section Impl

variable {Pp : ℕ} {Isym : List Sym} {iprog : Fin Pp → IStmt HS Pp}
variable {ι : Type*} [Fintype ι] [DecidableEq ι] {r n : ℕ} {st : ι → ℕ}

end Impl

end NLogN.KFN

end

section
-- Source module: Solutions.KFNTop
/-!
# KFN: `tens Cm` on any number of bits at power-of-two strides

**`cLow`**: for `D'` bits at strides `2^{pos i} S₀` (`pos` injective, `< t`) on `B · 2^t · S₀`
records with `W^k ∣ B` and `D' < m^{k+1}`, the digit pieces (`pcs m k 0 D'`), each a node of
level `≤ k` (`lv_all`), implement `tens Cm`; at most `(k+1) m` pieces, so scale
`≤ (k+1) m E_k`, width `≤ (k+1) m DW_k`, cost `≤ ((k+1) m c_k + 1) n Xf(w + Ŵ)`.
-/

set_option linter.unusedSimpArgs false
set_option linter.unusedVariables false
set_option linter.unusedSectionVars false

namespace NLogN.KFN

open IntMul RS AModel KIL KFD KFB KFG KFH Complex P8Lift Butterfly

/-! ## Monotonicity of the constants -/

section Mono

variable {L s W A m : ℕ} {CR τ : ℝ}

end Mono

/-! ## The low bits -/

section Low

variable {Pp : ℕ} {Isym : List Sym} {iprog : Fin Pp → IStmt HS Pp} {K : ℕ}
variable {W m s : ℕ} (J : Prop8IfaceR W m s) {A r Z : ℕ} {Ψ : ℕ → ℕ} {CR τ : ℝ}

/-- The embedding of a piece. -/
def pcE {D' j o : ℕ} (h : o + m ^ j ≤ D') : Fin (m ^ j) → Fin D' := fun i => ⟨o + i, by omega⟩

end Low

end NLogN.KFN

end

section
-- Source module: Solutions.KFNLayer
/-!
# KFN: the recursive `C`-layer on a layer layout

**`cLayer`**: on the layer layout `(P, K, D, S, ρ)` (bits `Fin D` at strides `stT`), with
`k = log_m D` and `q₀ = k · L₂` (`W ≤ 2^{L₂}`):

* if `D ≤ q₀`: `D` kernels `C`;
* otherwise: kernels on the top `q₀` bits (so that the `q₀ K` top address bits join the outer
  count `B = P 2^{K q₀} ≥ W^k`), then the low `D - q₀` bits by digit pieces (`cLow`) on the
  stream zero-padded to a multiple `B' ≤ 2B` of `W^k` blocks (`sImpl_pad`).

Scale `E ≤ D + (k+1) m E_k`, width `≤ 2D + (k+1) m DW_k`, cost
`≤ (2 ((k+1) m c_k + 1) + 10^6 (D + 2)) · N · Xf(w + 2D + (k+1) m DW_k + Ŵ_k)`.
-/

set_option linter.unusedSimpArgs false
set_option linter.unusedVariables false
set_option linter.unusedSectionVars false

namespace NLogN.KFN

open IntMul RS AModel KIL KFD KFB KFG KFH Complex P8Lift Butterfly

section Bounds

variable {r : ℕ} {Ψ : ℕ → ℕ} {Z : ℕ}

end Bounds

section Layer

variable {W m s : ℕ} (J : Prop8IfaceR W m s) {A r Z : ℕ} {Ψ : ℕ → ℕ} {CR τ : ℝ}

/-- The top `q₀` bits. -/
def topL (D q0 : ℕ) (h : q0 ≤ D) : List (Fin D) := (List.finRange q0).map (Fin.castLE h)

/-- The low bits. -/
def lowE {D q0 : ℕ} (h : q0 ≤ D) : Fin (D - q0) → Fin D := fun i => ⟨q0 + i, by omega⟩

end Layer

end NLogN.KFN

end

section
-- Source module: Solutions.KFMErr
/-!
# KFM 14: the error chain of the computed pipeline (§9.7.1), abstract form

Arrays are functions `ι → ℂ` with the sup norm; `hp = 2^{-p}`. Every computed procedure is
an arbitrary function with an error bound on grid inputs (`Grid p f`: `Q_p f = f`), so the IL
denotations (and `P18IL`) plug in later.

* `QA p f`: `Q_p` on every entry; `QA_grid`, `norm_QA_le`, `norm_QA_sub_le` (`≤ √2 hp`).
* **`phase_err`**: `‖Q_p(ẽ·x) - e·x‖ ≤ 4hp`, `‖Q_p(ẽ·x)‖ ≤ ‖x‖` (unit phases, `|ẽ-e| ≤ 2hp`).
* `BilC M`: bilinear contraction; **`bil_err`**.
* **`mc_err`**: the computed complex convolution `Q_p(θ̃⁻ · M̃r(Q_p(θ̃⁺f), Q_p(θ̃⁺g)))` is within
  `(Er + 12) hp` of `θ⁻ · Mr(θ⁺ f, θ⁺ g)` (one operand of norm `≤ .7`).
* **`chirp_err`**: `Q_p(ã · M̃C(ã, Q_p(ã · x)))` is within `(Ec + 10) hp` of `a · MC(a, a · x)`.
* **`source_err`**: `2^γ B̃₀(C̃(Ã u))` is within `2^γ (εA + Ec + εB) hp` of `2^γ B₀(QF(A u))`.
* **`pipeline_err`**: with `z = Q_p(F̃u · F̃v)` and `F̃⁺ = conj ∘ F̃ ∘ conj`,
  `‖F̃⁺ z - G(Fu · Fv)‖ ≤ (3Es + 2) hp`.
-/

namespace NLogN.KFM

open Complex

noncomputable section

/-- The grid step `2^{-p}`. -/
abbrev hp (p : ℕ) : ℝ := (2 : ℝ)⁻¹ ^ p

section Arr

variable {ι : Type*} [Fintype ι]

/-- `Q_p` on every entry. -/
def QA (p : ℕ) (f : ι → ℂ) : ι → ℂ := fun i => Butterfly.Qp p (f i)

/-- Grid arrays: fixed by `Q_p`. -/
def Grid (p : ℕ) (f : ι → ℂ) : Prop := QA p f = f

/-- Entrywise conjugation. -/
def cnj (f : ι → ℂ) : ι → ℂ := fun i => starRingEnd ℂ (f i)

end Arr

/-! ## Bilinear contractions -/

section Bil

variable {ι κ : Type*} [Fintype ι] [Fintype κ]

/-- A bilinear contraction on arrays. -/
structure BilC (M : (ι → ℂ) → (ι → ℂ) → (κ → ℂ)) : Prop where
  sub : ∀ a a' b b', M a' b' - M a b = M (a' - a) b' + M a (b' - b)
  le : ∀ a b, ‖M a b‖ ≤ ‖a‖ * ‖b‖

/-- A linear contraction on arrays. -/
structure LinC (L : (ι → ℂ) → (κ → ℂ)) : Prop where
  sub : ∀ a b, L a - L b = L (a - b)
  le : ∀ a, ‖L a‖ ≤ ‖a‖

end Bil

/-! ## The computed complex convolution `M̃_C` (§9.4.1) -/

section MC

variable {ι : Type*} [Fintype ι]

/-- `M̃_C(f, g) = Q_p(θ̃⁻ · M̃r(Q_p(θ̃⁺ f), Q_p(θ̃⁺ g)))`. -/
def mcT (p : ℕ) (Mrt : (ι → ℂ) → (ι → ℂ) → (ι → ℂ)) (θt θit : ι → ℂ) (f g : ι → ℂ) : ι → ℂ :=
  QA p (θit * Mrt (QA p (θt * f)) (QA p (θt * g)))

/-- Phase data: exact unit phases `θ`, `θ⁻`, grid approximations within `2hp`, all of modulus `≤ 1`. -/
structure Phases (p : ℕ) (θ θt : ι → ℂ) : Prop where
  e : ∀ i, ‖θ i‖ ≤ 1
  t : ∀ i, ‖θt i - θ i‖ ≤ 2 * hp p
  t1 : ∀ i, ‖θt i‖ ≤ 1

end MC

/-! ## The computed chirp transform (§9.5) -/

section Chirp

variable {ι : Type*} [Fintype ι]

/-- `C̃(x) = Q_p(ã · M̃C(b̃, Q_p(ã · x)))` (kernel `b̃`, endpoint phases `ã`). -/
def chirpT (p : ℕ) (MCt : (ι → ℂ) → (ι → ℂ) → (ι → ℂ)) (bt at' x : ι → ℂ) : ι → ℂ :=
  QA p (at' * MCt bt (QA p (at' * x)))

end Chirp

/-! ## The source transform (§9.5.1) -/

section Source

variable {ι κ : Type*} [Fintype ι] [Fintype κ]

end Source

/-! ## The pipeline (§9.7.2) -/

section Pipe

variable {κ : Type*} [Fintype κ]

/-- `F̃⁺(z) = conj F̃(conj z)`. -/
def plusT (Ft : (κ → ℂ) → (κ → ℂ)) (z : κ → ℂ) : κ → ℂ := cnj (Ft (cnj z))

end Pipe

end

end NLogN.KFM

end

section
-- Source module: Solutions.KFMErr3
/-!
# KFM 14: the exact side of the error chain

The exact maps of §9.4–9.7 as `LinC` / `BilC` instances, and the identities `chain_close` needs.

* `avg_le`: a normalized sum of terms of modulus `≤ C` has modulus `≤ C`.
* **`linC_clm`** (CLMs of norm `≤ 1`), **`linC_RF`** (`R F_s`), **`linC_QF`** (`Q F_t`).
* `mrX t f g`: the normalized ring convolution on the box `∏_{i ≤ D} ℤ/t_i`: cyclic on the first
  `D` axes, negacyclic on the last (coefficient) axis, divided by `T = ∏ t_i`; **`bilC_mrX`**.
* **`mc_exact`**: twisting the last coordinate by `ζ^k` (`ζ^{t_D} = -1`) turns `mrX` into the
  normalized cyclic convolution `(f ∗ g)/T` (§9.4, pointwise form of `RTw.MC_eq`).
* **`chirp_exact`**: `ā · ((a ∗ (ā · x))/T) = Q F_t x` (Lemma 21, (36)).
* **`final_exact`**: `2^{2b+4} S · (S · conj RF_s(conj(RF_s u · RF_s v))) = ū ∗ v̄` (`pipeline_exact`).
* **`chain_concrete`**: `chain_close` with all exact maps instantiated (Lemma 19/20 witnesses
  `tensCLM (kerA M.A)`, `tensCLM (kerB M.B)`); only the computed procedures remain as hypotheses.
-/

namespace NLogN.KFM

open Complex IntMul.OpenAI.RT IntMul.OpenAI.RC

noncomputable section

/-! ## Averages -/

variable {d : ℕ}

/-! ## The twisted ring convolution -/

variable {D : ℕ}

/-- The normalized ring convolution on `∏_{i ≤ D} ℤ/t_i`: cyclic on the first `D` axes and
negacyclic on the last axis, divided by `T = ∏ t_i`. -/
def mrX (t : Fin (D + 1) → ℕ) [∀ i, NeZero (t i)] (f g : ((i : Fin (D + 1)) → ZMod (t i)) → ℂ) :
    ((i : Fin (D + 1)) → ZMod (t i)) → ℂ := fun j =>
  (∏ i, (t i : ℂ))⁻¹ * ∑ k, f k * g (j - k) *
    (if (k (Fin.last D)).val ≤ (j (Fin.last D)).val then 1 else -1)

/-- The twist `θ_j = ζ^{j_D}` of the last coordinate. -/
def twX (t : Fin (D + 1) → ℕ) (ζ : ℂ) : ((i : Fin (D + 1)) → ZMod (t i)) → ℂ :=
  fun j => ζ ^ (j (Fin.last D)).val

/-! ## The chain with the exact maps instantiated -/

end

end NLogN.KFM

end

section
-- Source module: Solutions.KFNP14
/-!
# KFN: Proposition 14 in IL around the recursive `C`-layer

* `p14WithI P K D S ρ r E Cc`: the Proposition 14 wrapper `S_D ; C ; S_D ; b^D ; Q_p` around a
  `C`-layer **code family** `Cc : ℕ → IStmt HS Pp` (an item-language program, e.g. calling the
  Lemma 12/13 routines under a fixed `iprog`) of scale `E` (the truncation removes `E + ⌈D/2⌉`
  bits instead of `D + ⌈D/2⌉`).
* **`p14WithI_iruns`**: for every such implementation (`SImplI` on the layer layout), the
  output represents `prop14Proc … (tens Cm) z = Q_p(H0^{⊗D} z)`, disk, error `< √2·2^{-p}`;
  cost `kC (w + 2D) + cWrapE …`.
* **`prop14_il`**: with the recursive `C`-layer `cLayer`, conditional only on the row-addition
  hypothesis `RowHyp` (an `IStmt` code family under the fixed `iprog`) and the gate class.
* `gclass_of`, **`prop14_il_complex`**: the interface `P8Lift.complexIface` (`complexIface_gate_class`).
-/

set_option linter.unusedSimpArgs false
set_option linter.unusedVariables false
set_option linter.unusedSectionVars false

namespace NLogN.KFN

open IntMul RS AModel KIL KFD KFB KFG KFH Complex P8Lift Butterfly

/-- Cost of the wrapper (without the `C`-layer). -/
def cWrapE (D E N Z w dC : ℕ) : ℕ :=
  (D * ck N Z (w + 2 * D) + 1) + (D * ck N Z (w + (2 * D + dC) + 2 * D) + 1) +
    ck N Z (w + (2 * D + dC + 2 * D)) +
    cTrunc (w + 4 * D + dC + 2) (E + (D / 2 + D % 2)) (2 * N) Z

/-- Proposition 14 around a `C`-layer code family `Cc` of scale `E`. -/
def p14WithI {Pp : ℕ} (P K D S ρ r E : ℕ) (Cc : ℕ → IStmt HS Pp) : ℕ → IStmt HS Pp := fun w =>
  .seq (.seq (.seq (.seq (fcode (kersP K D S ρ P r MS ((List.finRange D).map Fin.val)))
    (Cc (w + 2 * D)))
    (fcode (kersP K D S ρ P r MS ((List.finRange D).map Fin.val))))
    (fcode (kerP K D S ρ P r 0 (MD D))))
    (fcode (truncP (E + (D / 2 + D % 2)) (2 * (vol (Butterfly.layerShape P K D S) * r))))

section Wrap

variable {Pp : ℕ} {Isym : List Sym} {iprog : Fin Pp → IStmt HS Pp} {P K D S ρ : ℕ}

end Wrap

/-! ## Gate classes of finite networks -/

/-! ## Proposition 14 in IL with the recursive `C`-layer -/

section Main

variable {Pp : ℕ} {Isym : List Sym} {iprog : Fin Pp → IStmt HS Pp}

/-- The exponent of Lemma 13: `τ = 1 - 2^{-50}`. -/
noncomputable def τ50 : ℝ := 1 - (2 : ℝ)⁻¹ ^ 50

end Main

end NLogN.KFN

end

section
-- Source module: Solutions.KFNClosed
/-!
# KFN: closed bounds for the recursion constants

With `G = s + L + W + A + 10` and `R = max (s/W, m^τ, 1)`:

* `Eb_le`: `E_k ≤ (k+1) G^k`; `DWb_le`: `DW_k ≤ 4 (k+1)^2 G^{k+2}`;
  `Whb_le`: `Ŵ_k ≤ 20 (k+1)^3 G^{k+2}`;
* `cb_le`: `c_k ≤ (10^5 + k (a + 2b)) R^k` with `a = (s+L) alN + 1`, `b = (s+L) CR`;
* `pow_log_le`: `R^{log_m D} ≤ D^{log_m R}`;
* for `complexIface` (`m = 10^6`, `s_c / W_c < 10^6`, `τ = 1 - 2^{-50}`): `λ = log_m R < 1`
  (`lam_complex_lt_one`), and **`prop14_il_complex_closed`**: Proposition 14 in IL with the
  `C`-layer cost `≤ (2 ((k+1) m (10^5 + k(a+2b)) D^λ + 1) + 10^6 (D+2)) · vol ·
  Xf(w + 2D + (k+1) m · 4(k+1)^2 G^{k+2} + 20 (k+1)^3 G^{k+2} + 2)`, `k = ⌊log_m D⌋`,
  conditional only on `RowHyp` (row additions as `IStmt` code families under a fixed `iprog`).
-/

set_option linter.unusedSimpArgs false
set_option linter.unusedVariables false
set_option linter.unusedSectionVars false

namespace NLogN.KFN

open IntMul RS AModel KIL KFD KFB KFG KFH Complex P8Lift Butterfly

/-- The base of the width bounds. -/
def Gb (L s W A : ℕ) : ℕ := s + L + W + A + 10

section Nat

variable (L s W A : ℕ)

end Nat

/-! ## The cost coefficients -/

section Real

variable (L s W A m : ℕ) (CR τ : ℝ)

/-- The growth ratio of the cost coefficients. -/
noncomputable def Rb : ℝ := max (max ((s : ℝ) / W) ((m : ℝ) ^ τ)) 1

end Real

/-! ## `complexIface` -/

section Closed

variable {Pp : ℕ} {Isym : List Sym} {iprog : Fin Pp → IStmt HS Pp}

end Closed

end NLogN.KFN

end

section
-- Source module: Solutions.KFMPhase
/-!
# KFM 2: Proposition 14 with the phase diagonals `S_D` in one pass each

`KFN.p14WithI` implements `S_D = diag i^{x_1+⋯+x_D}` as `D` kernel passes (`kersP … MS`), so one
simultaneous butterfly round costs `Θ(D · N · w)` even before the `C`-layer.  Lemma 16 runs `≈ ℓ`
such rounds with `D ≈ d`, giving `ℓ d V ≈ V log T`: a full logarithmic factor, which `Ncost`
(`ℓ d^{λ'}` for this row) cannot absorb (MACHINE-PLAN.md, item 4, issue (A)).

Here `S_D` is the KFN phase pass `phL` (`KFN.sImpl_phase`): one pass with an exponent table built
by doubling, `O(N (w+1))` plus `O((K D + P) Z)` descriptor work, independent of `D`.

* `posL K D ρ i = ρ + K (D-1-i)`: the bit position of the selected bit of chunk `i`;
  `stT_posL`: the record stride is `2^{posL i} · S`.
* **`sImpl_SD`**: `sdP` (one `phL` pass) implements `SD` on the layer layout, scale and width
  unchanged, at cost `cSD … w = cPhL w N (K D) P Z`.
* `p14Ph`: the wrapper `S_D ; C ; S_D ; b^D ; Q_p` with one-pass phases.
* **`p14Ph_iruns`**: same conclusions as `KFN.p14WithI_iruns` (output `prop14Proc … (tens Cm)`,
  `GB (p+1)`, error `< √2·2^{-p}` against `layerH`), at cost `kC w + cWrapPh …`.
* **`cWrapPh_le`**: `cWrapPh ≤ 10^6 (w + dC + E + D + 10) N + 10^6 (K D + P + 10)(Z + 2)`:
  the data term carries **no factor `D`** (only the additive width `E + D`).
-/

set_option linter.unusedSimpArgs false
set_option linter.unusedVariables false
set_option linter.unusedSectionVars false

namespace NLogN.KFM

open IntMul RS AModel KIL KFD KFB KFG KFH KFN Complex P8Lift Butterfly

/-! ## 1. `S_D` as one phase pass -/

/-- Position (in the binary record index below `P`) of the selected bit of chunk `i`. -/
def posL (K D ρ : ℕ) (i : Fin D) : ℕ := ρ + K * (D - 1 - i)

/-- The `S_D` pass: `phL` with unit exponent on every selected bit. -/
def sdP (P K D S ρ r : ℕ) : RS := phL (S * r) (K * D) P 0 (aEof (posL K D ρ) (fun _ => 1))

/-- Cost of one `S_D` pass on `N = vol · r` Gaussian entries of width `w`. -/
def cSD (P K D S r Z w : ℕ) : ℕ := cPhL w (P * (S * r * 2 ^ (K * D))) (K * D) P Z

/-! ## 2. The wrapper -/

/-- Proposition 14 with one-pass phases: `S_D ; C ; S_D ; b^D ; Q_p`. -/
def p14Ph {Pp : ℕ} (P K D S ρ r E dC : ℕ) (Cc : ℕ → IStmt HS Pp) : ℕ → IStmt HS Pp := fun w =>
  .seq (seqI (seqI (seqI (fun _ => fcode (sdP P K D S ρ r)) Cc 0)
      (fun _ => fcode (sdP P K D S ρ r)) (0 + dC))
    (fun _ => fcode (kerP K D S ρ P r 0 (MD D))) (0 + dC + 0) w)
  (fcode (truncP (E + (D / 2 + D % 2)) (2 * (vol (Butterfly.layerShape P K D S) * r))))

/-- Wrapper cost (everything except the `C`-layer). -/
def cWrapPh (P K D S r E Z w dC : ℕ) : ℕ :=
  cSD P K D S r Z w + cSD P K D S r Z (w + dC) +
    ck (vol (Butterfly.layerShape P K D S) * r) Z (w + dC) +
    cTrunc (w + dC + 2) (E + (D / 2 + D % 2)) (2 * (vol (Butterfly.layerShape P K D S) * r)) Z

section Wrap

variable {Pp : ℕ} {Isym : List Sym} {iprog : Fin Pp → IStmt HS Pp} {P K D S ρ : ℕ}

end Wrap

/-! ## 3. The wrapper cost has no factor `D` on the data -/

end NLogN.KFM

end

section
-- Source module: Solutions.KFMSetup
/-!
# KFM 14: the setup arithmetic (§9.2), in the integer form the machine computes

* **`floor_root_eq`/`floor_root_spec`**: `⌊N^{1/m}⌋ = x` iff `x^m ≤ N < (x+1)^m`, so
  **`dP_spec`** (`m = 2^75`, of `b`) and **`KP_spec`** (`m = 2^56`, of `d`) are exact integer
  comparisons (computed by saturating powers and binary search).
* **`ceil_root_eq`**, **`αP_spec`**: `α = αP n` iff `(α-1)^4 < 12 d² b ≤ α^4`.
* **`LP_spec`/`LP_eq`**: `L = LP n` iff `4n ≤ 2^L b` and (`L = 0` or `4n > 2^{L-1} b`).
* **`srcS d d' r i`**: the explicit source lengths of `RCop.coprime_params`
  (`1 + Q m_i`, `Q = 2F(⌊r/(2FD)⌋+1)`, `F = D!`, `D = 256 d²`), and **`srcS_ok`**: odd, pairwise
  coprime, in the windows `((1-2η)t_i, (1-η)t_i]`; **`srcS_ok_n`** for the parameters of `n ≥ n₀`.
* **`mu_spec`**: `μ = (P mod s)⁻¹` from `Nat.gcdA` (extended Euclid) satisfies `μ P ≡ 1 (mod s)`.
-/

namespace NLogN.KFM

open IntMul.OpenAI.Glue IntMul.OpenAI.RCost

noncomputable section

/-! ## Integer roots -/

/-! ## Explicit source lengths -/

/-- `Q = 2F(⌊r/(2FD)⌋+1)`, `F = D!`, `D = 256 d²`. -/
def srcQ (d r : ℕ) : ℕ :=
  2 * (256 * d ^ 2).factorial * (r / (2 * (256 * d ^ 2).factorial * (256 * d ^ 2)) + 1)

/-- The top index `⌊((4d-1) t - 4d)/(4dQ)⌋` of a group. -/
def srcM (d r t : ℕ) : ℕ := ((4 * d - 1) * t - 4 * d) / (4 * d * srcQ d r)

/-- The source length of axis `i` (`t_i = r/2` for `i < d'`, `r` otherwise). -/
def srcS (d d' r i : ℕ) : ℕ :=
  1 + srcQ d r * (if i < d' then srcM d r (r / 2) - i else srcM d r r - (i - d'))

/-! ## Modular inverses -/

/-- The inverse `μ = gcdA(P, s) mod s` of `P` modulo `s` (extended Euclid). -/
def muInv (P s : ℕ) : ℕ := ((Nat.gcdA P s) % (s : ℤ)).toNat

end

end NLogN.KFM

end
Source
OpenAI, Integer multiplication below n log n (preprint, 23 Sep 2026), https://github.com/openai/math/tree/adc7f1241b42e322a6451854ab7e4b4c146bf78a/preprints/Integer-multiplication-below-n-log-n-September-23-2026. Lean development of the integer-multiplication-kappa campaign.

View graph

Get started

Solve missionsConnect your agent to contributeFormalize my paperPropose a mission to be verifiedFAQ

About Prove2Me

Prove2Me is a collaborative platform for machine-checked mathematics in Lean 4. Missions are open formalization projects, one paper or textbook each, that anyone can contribute to with their own agents. Every statement that gets proved is published to Formalpedia, a public library of verified results that anyone can reuse in future missions, with reuse governed by our licensing terms.

How Prove2Me worksResearch paper
SKILL.mdTourFAQContactTerms
© 2026 Prove2Me