File: .lake/packages/lean4/src/lean/Lean/Meta/Eqns.lean

full_name: Lean.Meta.recExt
code: /--
Environment extension for storing which declarations are recursive.
This information is populated by the `PreDefinition` module, but the simplifier
uses when unfolding declarations.
-/
builtin_initialize recExt : TagDeclarationExtension ← mkTagDeclarationExtension `recExt
goal: Lean.TagDeclarationExtension

full_name: Lean.Meta.initFn._@..lake.packages.lean4.src.lean.Lean.Meta.Eqns._hyg.4
code: /--
Environment extension for storing which declarations are recursive.
This information is populated by the `PreDefinition` module, but the simplifier
uses when unfolding declarations.
-/
builtin_initialize recExt : TagDeclarationExtension ← mkTagDeclarationExtension `recExt
goal: IO Lean.TagDeclarationExtension

full_name: Lean.Meta.markAsRecursive
code: /--
Marks the given declaration as recursive.
-/
def markAsRecursive (declName : Name) : CoreM Unit 
goal: Lean.CoreM Unit

full_name: Lean.Meta.isRecursiveDefinition
code: /--
Returns `true` if `declName` was defined using well-founded recursion, or structural recursion.
-/
def isRecursiveDefinition (declName : Name) : CoreM Bool 
goal: Lean.CoreM Bool

full_name: Lean.Meta.eqnThmSuffixBase
code: def eqnThmSuffixBase 
goal: String

full_name: Lean.Meta.eqnThmSuffixBasePrefix
code: def eqnThmSuffixBasePrefix 
goal: String

full_name: Lean.Meta.eqn1ThmSuffix
code: def eqn1ThmSuffix 
goal: String

full_name: Lean.Meta.isEqnReservedNameSuffix
code: /-- Returns `true` if `s` is of the form `eq_<idx>` -/
def isEqnReservedNameSuffix (s : String) : Bool 
goal: Bool

full_name: Lean.Meta.unfoldThmSuffix
code: def unfoldThmSuffix 
goal: String

full_name: Lean.Meta.isUnfoldReservedNameSuffix
code: /-- Returns `true` if `s == "eq_def"` -/
def isUnfoldReservedNameSuffix (s : String) : Bool 
goal: Bool

full_name: Lean.Meta.ensureEqnReservedNamesAvailable
code: /--
Throw an error if names for equation theorems for `declName` are not available.
-/
def ensureEqnReservedNamesAvailable (declName : Name) : CoreM Unit 
goal: Lean.CoreM Unit

full_name: Lean.Meta.initFn._@..lake.packages.lean4.src.lean.Lean.Meta.Eqns._hyg.163
code: /--
Ensures that `f.eq_def` and `f.eq_<idx>` are reserved names if `f` is a safe definition.
-/
builtin_initialize registerReservedNamePredicate fun env n =>
  match n with
  | .str p s =>
    (isEqnReservedNameSuffix s || isUnfoldReservedNameSuffix s)
    && env.isSafeDefinition p
    -- Remark: `f.match_<idx>.eq_<idx>` are private definitions and are not treated as reserved names
    -- Reason: `f.match_<idx>.splitter is generated at the same time, and can eliminate into type.
    -- Thus, it cannot be defined in different modules since it is not a theorem, and is used to generate code.
    && !isMatcherCore env p
  | _ => false
goal: IO Unit

full_name: Lean.Meta.GetEqnsFn
code: def GetEqnsFn 
goal: Type

full_name: Lean.Meta.initFn._@..lake.packages.lean4.src.lean.Lean.Meta.Eqns._hyg.236
code: private builtin_initialize getEqnsFnsRef : IO.Ref (List GetEqnsFn) ← IO.mkRef []
goal: IO (IO.Ref (List Lean.Meta.GetEqnsFn))

full_name: _private.«.lake».packages.lean4.src.lean.Lean.Meta.Eqns.0.Lean.Meta.getEqnsFnsRef
code: private builtin_initialize getEqnsFnsRef : IO.Ref (List GetEqnsFn) ← IO.mkRef []
goal: IO.Ref (List Lean.Meta.GetEqnsFn)

full_name: Lean.Meta.registerGetEqnsFn
code: /--
Registers a new function for retrieving equation theorems.
We generate equations theorems on demand, and they are generated by more than one module.
For example, the structural and well-founded recursion modules generate them.
Most recent getters are tried first.

A getter returns an `Option (Array Name)`. The result is `none` if the getter failed.
Otherwise, it is a sequence of theorem names where each one of them corresponds to
an alternative. Example: the definition

```
def f (xs : List Nat) : List Nat :=
  match xs with
  | [] => []
  | x::xs => (x+1)::f xs
```
should have two equational theorems associated with it
```
f [] = []
```
and
```
(x : Nat) → (xs : List Nat) → f (x :: xs) = (x+1) :: f xs
```
-/
def registerGetEqnsFn (f : GetEqnsFn) : IO Unit 
goal: IO Unit

full_name: _private.«.lake».packages.lean4.src.lean.Lean.Meta.Eqns.0.Lean.Meta.shouldGenerateEqnThms
code: /-- Returns `true` iff `declName` is a definition and its type is not a proposition. -/
private def shouldGenerateEqnThms (declName : Name) : MetaM Bool 
goal: Lean.MetaM Bool

full_name: Lean.Meta.instInhabitedEqnsExtState
code: structure EqnsExtState where
  map    : PHashMap Name (Array Name) := {}
  mapInv : PHashMap Name Name := {} -- TODO: delete?
  deriving Inhabited
goal: Inhabited Lean.Meta.EqnsExtState

full_name: Lean.Meta.EqnsExtState.mapInv
code: structure EqnsExtState where
  map    : PHashMap Name (Array Name) := {}
  mapInv : PHashMap Name Name := {} -- TODO: delete?
  deriving Inhabited
goal: Lean.PHashMap Lean.Name Lean.Name

full_name: Lean.Meta.EqnsExtState
code: structure EqnsExtState where
  map    : PHashMap Name (Array Name) := {}
  mapInv : PHashMap Name Name := {} -- TODO: delete?
  deriving Inhabited
goal: Type

full_name: Lean.Meta.EqnsExtState.map
code: structure EqnsExtState where
  map    : PHashMap Name (Array Name) := {}
  mapInv : PHashMap Name Name := {} -- TODO: delete?
  deriving Inhabited
goal: Lean.PHashMap Lean.Name (Array Lean.Name)

full_name: Lean.Meta.initFn._@..lake.packages.lean4.src.lean.Lean.Meta.Eqns._hyg.513
code: builtin_initialize eqnsExt : EnvExtension EqnsExtState ←
  registerEnvExtension (pure {})
goal: IO (Lean.EnvExtension Lean.Meta.EqnsExtState)

full_name: Lean.Meta.eqnsExt
code: builtin_initialize eqnsExt : EnvExtension EqnsExtState ←
  registerEnvExtension (pure {})
goal: Lean.EnvExtension Lean.Meta.EqnsExtState

full_name: _private.«.lake».packages.lean4.src.lean.Lean.Meta.Eqns.0.Lean.Meta.mkSimpleEqThm
code: /--
Simple equation theorem for nonrecursive definitions.
-/
private def mkSimpleEqThm (declName : Name) (suffix := Name.mkSimple unfoldThmSuffix) : MetaM (Option Name) 
goal: Lean.MetaM (Option Lean.Name)

full_name: Lean.Meta.isEqnThm?
code: /--
Returns `some declName` if `thmName` is an equational theorem for `declName`.
-/
def isEqnThm? (thmName : Name) : CoreM (Option Name) 
goal: Lean.CoreM (Option Lean.Name)

full_name: _private.«.lake».packages.lean4.src.lean.Lean.Meta.Eqns.0.Lean.Meta.registerEqnThms
code: /--
Stores in the `eqnsExt` environment extension that `eqThms` are the equational theorems for `declName`
-/
private def registerEqnThms (declName : Name) (eqThms : Array Name) : CoreM Unit 
goal: Lean.CoreM Unit

full_name: _private.«.lake».packages.lean4.src.lean.Lean.Meta.Eqns.0.Lean.Meta.alreadyGenerated?.loop
code: /--
Equation theorems are generated on demand, check whether they were generated in an imported file.
-/
private partial def alreadyGenerated? (declName : Name) : MetaM (Option (Array Name)) 
goal: Lean.MetaM (Array Lean.Name)

full_name: _private.«.lake».packages.lean4.src.lean.Lean.Meta.Eqns.0.Lean.Meta.alreadyGenerated?
code: /--
Equation theorems are generated on demand, check whether they were generated in an imported file.
-/
private partial def alreadyGenerated? (declName : Name) : MetaM (Option (Array Name)) 
goal: Lean.MetaM (Option (Array Lean.Name))

full_name: Lean.Meta.getEqnsFor?
code: /--
Returns equation theorems for the given declaration.
By default, we do not create equation theorems for nonrecursive definitions.
You can use `nonRec := true` to override this behavior, a dummy `rfl` proof is created on the fly.
-/
def getEqnsFor? (declName : Name) (nonRec := false) : MetaM (Option (Array Name)) 
goal: Lean.MetaM (Option (Array Lean.Name))

full_name: Lean.Meta.GetUnfoldEqnFn
code: def GetUnfoldEqnFn 
goal: Type

full_name: Lean.Meta.initFn._@..lake.packages.lean4.src.lean.Lean.Meta.Eqns._hyg.1506
code: private builtin_initialize getUnfoldEqnFnsRef : IO.Ref (List GetUnfoldEqnFn) ← IO.mkRef []
goal: IO (IO.Ref (List Lean.Meta.GetUnfoldEqnFn))

full_name: _private.«.lake».packages.lean4.src.lean.Lean.Meta.Eqns.0.Lean.Meta.getUnfoldEqnFnsRef
code: private builtin_initialize getUnfoldEqnFnsRef : IO.Ref (List GetUnfoldEqnFn) ← IO.mkRef []
goal: IO.Ref (List Lean.Meta.GetUnfoldEqnFn)

full_name: Lean.Meta.registerGetUnfoldEqnFn
code: /--
Registers a new function for retrieving a "unfold" equation theorem.

We generate this kind of equation theorem on demand, and it is generated by more than one module.
For example, the structural and well-founded recursion modules generate it.
Most recent getters are tried first.

A getter returns an `Option Name`. The result is `none` if the getter failed.
Otherwise, it is a theorem name. Example: the definition

```
def f (xs : List Nat) : List Nat :=
  match xs with
  | [] => []
  | x::xs => (x+1)::f xs
```
should have the theorem
```
(xs : Nat) →
  f xs =
    match xs with
    | [] => []
    | x::xs => (x+1)::f xs
```
-/
def registerGetUnfoldEqnFn (f : GetUnfoldEqnFn) : IO Unit 
goal: IO Unit

full_name: Lean.Meta.getUnfoldEqnFor?
code: /--
Returns an "unfold" theorem for the given declaration.
By default, we do not create unfold theorems for nonrecursive definitions.
You can use `nonRec := true` to override this behavior.
-/
def getUnfoldEqnFor? (declName : Name) (nonRec := false) : MetaM (Option Name) 
goal: Lean.MetaM (Option Lean.Name)

full_name: Lean.Meta.initFn._@..lake.packages.lean4.src.lean.Lean.Meta.Eqns._hyg.2141
code: builtin_initialize
  registerReservedNameAction fun name => do
    let .str p s := name | return false
    unless (← getEnv).isSafeDefinition p do return false
    if isEqnReservedNameSuffix s then
      return (← MetaM.run' <| getEqnsFor? p (nonRec := true)).isSome
    if isUnfoldReservedNameSuffix s then
      return (← MetaM.run' <| getUnfoldEqnFor? p (nonRec := true)).isSome
    return false
goal: IO Unit