Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
43 commits
Select commit Hold shift + click to select a range
9fde4c6
feat: certify recursive normalization candidates
johnchandlerburnham Jul 31, 2026
b283912
feat: certify annotated normalization binders
johnchandlerburnham Jul 31, 2026
a84aa19
feat: certify singleton normalization candidates
johnchandlerburnham Jul 31, 2026
c2b1c4f
feat: assemble candidate generation certificates
johnchandlerburnham Jul 31, 2026
a1d8943
feat: replay annotated recursive Pi induction
johnchandlerburnham Aug 1, 2026
6a77882
feat: certify non-identity inductive transactions
johnchandlerburnham Aug 1, 2026
bc37d43
feat: certify executable inductive candidates
johnchandlerburnham Aug 1, 2026
5e5bb76
feat: advance annotated Pi validation
johnchandlerburnham Aug 1, 2026
33b99f4
feat: certify annotated Pi constructors
johnchandlerburnham Aug 1, 2026
a3ff992
feat: certify annotated Pi producer
johnchandlerburnham Aug 1, 2026
9a865ea
feat: generalize candidate family validation
johnchandlerburnham Aug 1, 2026
a627362
feat: certify indexed family candidates
johnchandlerburnham Aug 2, 2026
f0d80f8
perf: short-circuit syntactic definitional equality
johnchandlerburnham Aug 2, 2026
6732659
proof: verify IndexedVec nil constructor candidate
johnchandlerburnham Aug 2, 2026
c40a471
proof: verify IndexedVec cons constructor candidate
johnchandlerburnham Aug 2, 2026
c739d41
fix: stabilize inductive candidate context provenance
johnchandlerburnham Aug 2, 2026
82f4a54
feat: certify IndexedVec outer candidate production
johnchandlerburnham Aug 2, 2026
d553930
feat: support exact identity candidate replay
johnchandlerburnham Aug 2, 2026
cf3d5a4
feat: certify IndexedVec semantic generation
johnchandlerburnham Aug 2, 2026
d35a2f6
docs: record IndexedVec semantic checkpoint
johnchandlerburnham Aug 2, 2026
c9e4ae2
feat: generalize candidate list production
johnchandlerburnham Aug 2, 2026
9ff6be1
docs: record source-indexed list checkpoint
johnchandlerburnham Aug 2, 2026
a7d101b
feat: generalize produced candidate packaging
johnchandlerburnham Aug 2, 2026
80f9dce
docs: record produced-package checkpoint
johnchandlerburnham Aug 2, 2026
f0caf16
feat: retain candidate semantic hierarchy
johnchandlerburnham Aug 2, 2026
ea14f31
docs: record semantic-hierarchy checkpoint
johnchandlerburnham Aug 2, 2026
e3cf22d
feat: assemble produced semantic hierarchy
johnchandlerburnham Aug 2, 2026
7e5f4f7
feat: harden semantic hierarchy ownership
johnchandlerburnham Aug 2, 2026
1093311
docs: record semantic ownership checkpoint
johnchandlerburnham Aug 2, 2026
2b1d802
feat: derive structural generation evidence
johnchandlerburnham Aug 2, 2026
0270843
docs: record structural generation evidence checkpoint
johnchandlerburnham Aug 2, 2026
a64fe98
feat: derive generation analyzer provenance
johnchandlerburnham Aug 2, 2026
4b66e50
docs: record generation analyzer provenance checkpoint
johnchandlerburnham Aug 2, 2026
5aa9ab6
feat: derive generation shape alignment
johnchandlerburnham Aug 3, 2026
fda0016
docs: record generation shape alignment checkpoint
johnchandlerburnham Aug 3, 2026
bbb45e0
feat: consolidate generation readiness
johnchandlerburnham Aug 3, 2026
c4fd62b
docs: record generation readiness checkpoint
johnchandlerburnham Aug 3, 2026
f82ee77
docs: refactor roadmap into discrete checkpoints
johnchandlerburnham Aug 3, 2026
7c79220
feat: consolidate staged semantic inputs
johnchandlerburnham Aug 3, 2026
21b7a72
docs: record L4L-01A checkpoint
johnchandlerburnham Aug 3, 2026
da45b53
feat: derive family validation staging
johnchandlerburnham Aug 3, 2026
ac41ba9
docs: record L4L-01B checkpoint
johnchandlerburnham Aug 3, 2026
4ef21e0
docs: add upstream reconciliation checkpoint
johnchandlerburnham Aug 3, 2026
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 3 additions & 1 deletion .gitignore
Original file line number Diff line number Diff line change
@@ -1,4 +1,6 @@
/.lake
/result
/.direnv
/plans
# Keep scratch plans local while versioning the authoritative execution ladder.
/plans/*
!/plans/roadmap.md
1,148 changes: 1,100 additions & 48 deletions Lean4Lean/Inductive/Add.lean

Large diffs are not rendered by default.

29 changes: 29 additions & 0 deletions Lean4Lean/Theory/Inductive.lean
Original file line number Diff line number Diff line change
Expand Up @@ -1450,6 +1450,17 @@ structure GenerationChecked.WF {source : VInductDecl}
gen.block.sourceType.toVConstant = some envT →
∀ ctor ∈ gen.block.ctorPairs, ctor.WF gen.block envT

/-- Consumer-facing semantic package for one generation-ready inductive
declaration. The executable transaction inspects only `generation`; `wf` is
the ordinary Theory certificate used by preservation and is never a
normalization oracle.

Verify can erase checker-specific candidate provenance to this boundary
before handing a normalized transaction to downstream consumers. -/
structure GenerationCertificate (source : VInductDecl) (env : VEnv) where
generation : GenerationChecked source
wf : generation.WF env

end VInductDecl

def VInductDecl.WF (env : VEnv) (decl : VInductDecl) : Prop :=
Expand Down Expand Up @@ -1488,6 +1499,24 @@ def VEnv.addInductGeneration {source : VInductDecl}
let env ← env.addConst (.str ty.name "rec") gen.recursor
return gen.generatedRules.foldl VEnv.addDefEq env

/-- Public proof-carrying wrapper around `addInductGeneration`.

The certificate's proof is erased and does not influence computation. This
entry point lets a verified producer expose a non-identity normalization
without exposing its checker trace or asking a consumer to remember a
separate preservation premise. -/
def VEnv.addInductCertified {source : VInductDecl}
(env : VEnv) (certificate : source.GenerationCertificate env) :
Option VEnv :=
env.addInductGeneration certificate.generation

@[simp] theorem VEnv.addInductCertified_eq_addInductGeneration
{source : VInductDecl} (env : VEnv)
(certificate : source.GenerationCertificate env) :
env.addInductCertified certificate =
env.addInductGeneration certificate.generation :=
rfl

/-- Exact intermediate states of a successful normalized inductive
transaction. Stable lookup, freshness, monotonicity, and preservation
consequences are derived from this one trace in the typing layer. -/
Expand Down
152 changes: 152 additions & 0 deletions Lean4Lean/Theory/InductiveFixtures.lean
Original file line number Diff line number Diff line change
Expand Up @@ -512,6 +512,158 @@ def accRecCollisionEnv : VEnv :=
example : accRecCollisionEnv.addInduct accDecl = none :=
VEnv.addInduct_eq_none_of_rec_present rfl ⟨_, rfl⟩

/-! ## AnnotatedPi: recursive Pi normalization below a constructor field

Lean retains `outParam` in the constructor's raw recursive-function domain,
while inductive analysis consumes it before recognizing the recursive target.
This fixture combines the annotation and recursive-Pi seams in one declaration
and keeps the raw binder syntax in generated artifacts. -/

inductive AnnotatedPi : Type where
| mk : ((p : outParam Prop) → AnnotatedPi) → AnnotatedPi

def outParamDefEq : VDefEq :=
vdefeq(@outParam ≡ fun (α : Sort u) => α)

def outParamConstEnv : VEnv :=
(VEnv.empty.addConst ``outParam (vconst(type_of% @outParam))).get
(by decide)

def outParamEnv : VEnv := outParamConstEnv.addDefEq outParamDefEq

theorem outParamConstant_wf :
(vconst(type_of% @outParam) : VConstant).WF VEnv.empty := by
exact ⟨_, VEnv.HasType.forallE
(VEnv.HasType.sort (by decide))
(VEnv.HasType.sort (by decide))⟩

theorem outParamConstEnv_ordered : outParamConstEnv.Ordered := by
apply VEnv.Ordered.const VEnv.Ordered.empty
(ci := vconst(type_of% @outParam))
· exact outParamConstant_wf
· rfl

theorem outParamEnv_ordered : outParamEnv.Ordered := by
apply VEnv.Ordered.defeq outParamConstEnv_ordered
constructor
· exact VEnv.HasType.const0 rfl
(outParamConstant_wf.mono
(VEnv.addConst_le (by rfl :
VEnv.empty.addConst ``outParam (vconst(type_of% @outParam)) =
some outParamConstEnv)))
· exact VEnv.HasType.lam
(VEnv.HasType.sort (by decide))
(VEnv.HasType.bvar .zero)

def annotatedPiRawType : VInductiveType where
name := ``AnnotatedPi
uvars := 0
type := vconst(type_of% @AnnotatedPi).type
ctors := [⟨vconst(type_of% @AnnotatedPi.mk), ``AnnotatedPi.mk⟩]

def annotatedPiRawDecl : VInductDecl := ⟨0, 0, [annotatedPiRawType]⟩

def annotatedPiViewCtor : VConstVal where
name := ``AnnotatedPi.mk
uvars := 0
type := .forallE
(.forallE (.sort .zero) (.const ``AnnotatedPi []))
(.const ``AnnotatedPi [])

def annotatedPiViewType : VInductiveType :=
{ annotatedPiRawType with ctors := [annotatedPiViewCtor] }

def annotatedPiViewDecl : VInductDecl := ⟨0, 0, [annotatedPiViewType]⟩

example : annotatedPiRawType.ctors[0].type =
.forallE
(.forallE
(.app (.const ``outParam [.succ .zero]) (.sort .zero))
(.const ``AnnotatedPi []))
(.const ``AnnotatedPi []) := rfl

example : annotatedPiViewDecl.checked?.isSome = true := rfl
example : normalizationShape annotatedPiRawDecl annotatedPiViewDecl = true :=
rfl

def annotatedPiNormalization : Normalization annotatedPiRawDecl where
view := annotatedPiViewDecl
shape_eq := rfl

def annotatedPiViewChecked : annotatedPiViewDecl.Checked :=
annotatedPiViewDecl.checked?.get (by decide)

def annotatedPiBlock : NormalizedChecked annotatedPiRawDecl :=
annotatedPiNormalization.check?.get (by decide)

def annotatedPiGenerationChecked : GenerationChecked annotatedPiRawDecl :=
annotatedPiBlock.generation?.get (by decide)

def annotatedPiRecArg : RecArg where
fieldIndex := 0
binders := [.sort .zero]
targetType := 0
indices := []

example : annotatedPiViewChecked.constructors[0].recursive =
[annotatedPiRecArg] := rfl

example : annotatedPiGenerationChecked.block.ctorPairs[0].rawFields 0 =
[.forallE
(.app (.const ``outParam [.succ .zero]) (.sort .zero))
(.const ``AnnotatedPi [])] := rfl

example : annotatedPiGenerationChecked.recursor =
vconst(type_of% @AnnotatedPi.rec) := rfl

example : annotatedPiGenerationChecked.generatedRules[0].rhs =
(vdefeq((motive : AnnotatedPi → Sort u)
(mk : (f : (p : outParam Prop) → AnnotatedPi) →
((p : Prop) → motive (f p)) → motive (@AnnotatedPi.mk f))
(f : (p : outParam Prop) → AnnotatedPi) =>
@AnnotatedPi.rec motive mk (@AnnotatedPi.mk f) ≡
mk f (fun p => @AnnotatedPi.rec motive mk (f p)))).rhs := rfl

/-- The normalized recursive-Pi view is semantically well formed without
using the annotation definition; the raw-to-view bridge is supplied later by
the exact checker candidate. -/
theorem annotatedPiViewDecl_wf : annotatedPiViewDecl.WF VEnv.empty := by
refine ⟨rfl, ?_⟩
intro ty hty
have hty' : ty = annotatedPiViewType :=
List.mem_singleton.1 (by simpa [annotatedPiViewDecl] using hty)
subst ty
refine ⟨by trivial, ?_⟩
intro c hc
have hc' : c = annotatedPiViewCtor :=
List.mem_singleton.1 (by simpa [annotatedPiViewType] using hc)
subst c
constructor
· change fieldsWF 0 ``AnnotatedPi 0 VEnv.empty (.succ .zero) [] [] 0
[.forallE (.sort .zero) (.const ``AnnotatedPi [])]
refine ⟨?_, ?_, trivial⟩
· right
left
refine ⟨annotatedPiRecArg, ?_, ?_, ?_⟩
· rfl
· simp [annotatedPiRecArg]
· exact ⟨⟨⟨_, VEnv.HasType.sort (by decide)⟩, trivial⟩, rfl⟩
· intro h
change false = true at h
contradiction
· change VEnv.empty.SpineWF 0
[.forallE (.sort .zero) (.const ``AnnotatedPi [])]
(.sort (.succ .zero)) [] (.sort (.succ .zero))
rfl

theorem annotatedPiViewChecked_wf :
annotatedPiViewChecked.WF outParamEnv := by
apply VInductDecl.Checked.WF.mono
((VEnv.addConst_le (by rfl :
VEnv.empty.addConst ``outParam (vconst(type_of% @outParam)) =
some outParamConstEnv)).trans VEnv.addDefEq_le)
exact annotatedPiViewChecked.wf_of_decl annotatedPiViewDecl_wf

/-! ## Explicit normalization boundary

Lean stores reducible aliases in inductive metadata even though
Expand Down
Loading
Loading