Commit graph

8848 commits

Author SHA1 Message Date
Kyle Miller
08e149de15 fix: make omission syntax be a builtin syntax (part 2)
Re-enables `⋯` processing that was disabled during the move to a builtin.
Adds tests.
2024-02-28 09:23:17 +01:00
Leonardo de Moura
a23292f049
feat: add option tactic.skipAssignedInstances := true for backward compatibilty (#3526)
When using `set_option tactic.skipAssignedInstances false`, `simp` and
`rw` will synthesize instance implicit arguments even if they have
assigned by unification. If the synthesized argument does not match the
assigned one the rewrite is not performed. This option has been added
for backward compatibility.
2024-02-28 05:52:29 +00:00
Scott Morrison
7cce64ee70
feat: omega doesn't check for defeq atoms (#3525)
```
example (a : Nat) :
    (((a + (2 ^ 64 - 1)) % 2 ^ 64 + 1) * 8 - 1 - (a + (2 ^ 64 - 1)) % 2 ^ 64 * 8 + 1) = 8 := by
  omega
```
used to time out, and now is fast.

(We will probably make separate changes later so the defeq checks would
be fast in any case here.)
2024-02-28 05:41:29 +00:00
Leonardo de Moura
86ca8e32c6
feat: improve simp discharge trace messages (#3523) 2024-02-28 04:39:57 +00:00
Leonardo de Moura
aed29525ab
fix: simp trace issues (#3522) 2024-02-27 23:19:25 +00:00
Kyle Miller
6e24a08907
feat: improve error messages and docstring for decide tactic (#3422)
The `decide` tactic produces error messages that users find to be
obscure. Now:
1. If the `Decidable` instance reduces to `isFalse`, it reports that
`decide` failed because the proposition is false.
2. If the `Decidable` instance fails to reduce, it explains what
proposition it failed for, and it shows the reduced `Decidable` instance
rather than the `Decidable.decide` expression. That expression tends to
be less useful since it shows the unreduced `Decidable` argument (plus
it's a lot longer!)

Examples:
```lean
example : 1 ≠ 1 := by decide
/-
tactic 'decide' proved that the proposition
  1 ≠ 1
is false
-/

opaque unknownProp : Prop

open scoped Classical in
example : unknownProp := by decide
/-
tactic 'decide' failed for proposition
  unknownProp
since its 'Decidable' instance reduced to
  Classical.choice ⋯
rather than to the 'isTrue' constructor.
-/
```

When reporting the error, `decide` only shows the whnf of the
`Decidable` instance. In the future we could consider having it reduce
all decidable instances present in the term, which can help with
determining the cause of failure (this was explored in
8cede580690faa5ce18683f168838b08b372bacb).
2024-02-27 23:07:38 +00:00
Kyle Miller
321ef5b956
fix: make Lean.Internal.liftCoeM and Lean.Internal.coeM unfold (#3404)
The elaboration function `Lean.Meta.coerceMonadLift?` inserts these
coercion helper functions into a term and tries to unfolded them with
`expandCoe`, but because that function only unfolds up to
reducible-and-instance transparency, these functions were not being
unfolded. The fix here is to give them the `@[reducible]` attribute.
2024-02-27 22:17:46 +00:00
Joachim Breitner
9c00a59339
feat: use omega in default decreasing_trivial (#3503)
with this, more functions will be proven terminating automatically,
namely those where after `simp_wf`, lexicographic order handling,
possibly `subst_vars` the remaining goal can be solved by `omega`.

Note that `simp_wf` already does simplification of the goal, so
this adds `omega`, not `(try simp) <;> omega` here.

There are certainly cases where `(try simp) <;> omega` will solve more 
goals (e.g. due to the `subst_vars` in `decreasing_with`), and
`(try simp at *) <;> omega` even more. This PR errs on the side of
taking
smaller steps.

Just appending `<;> omega` to the existing
`simp (config := { arith := true, failIfUnchanged := false })` call
doesn’t work nicely, as that leaves forms like `Nat.sub` in the goal
that
`omega` does not seem to recognize.

This does *not* remove any of the existing ad-hoc `decreasing_trivial`
rules based on `apply` and `assumption`, to not regress over the status
quo (these rules may apply in cases where `omega` wouldn't “see”
everything, but `apply` due to defeq works).

Additionally, just extending makes bootstrapping easier; early in `Init`
where
`omega` does not work yet these other tactics can still be used.

(Using a single `omega`-based tactic was tried in #3478 but isn’t quite
possible yet, and will be postponed until we have better automation
including forward reasoning.)
2024-02-27 18:53:36 +00:00
Joachim Breitner
d7ee5ba1cb
feat: use omega in the get_elem tactic (#3515)
with this, hopefully more obvious array accesses will be handled
automatically.

Just like #3503, this PR does not investiate which of the exitsting
tactics in `get_elem_tactic_trivial` are subsumed now and could be
dropped without (too much) breakage.
2024-02-27 18:52:04 +00:00
Leonardo de Moura
855fbed024
fix: regression on match expressions with builtin literals (#3521) 2024-02-27 18:49:44 +00:00
Kyle Miller
6e408ee402
feat: apply app unexpanders for all prefixes of an application (#3375)
Before, app unexpanders would only be applied to entire applications.
However, some notations produce functions, and these functions can be
given additional arguments. The solution so far has been to write app
unexpanders so that they can take an arbitrary number of additional
arguments. However, as reported in [this Zulip
thread](https://leanprover.zulipchat.com/#narrow/stream/270676-lean4/topic/pretty.20printer.20bug/near/420662236),
this leads to misleading hover information in the Infoview. For example,
while `HAdd.hAdd f g 1` pretty prints as `(f + g) 1`, hovering over `f +
g` shows `f`. There is no way to fix the situation from within an app
unexpander; the expression position for `HAdd.hAdd f g` is absent, and
app unexpanders cannot register TermInfo.

This commit changes the app delaborator to try running app unexpanders
on every prefix of an application, from longest to shortest prefix. For
efficiency, it is careful to only try this when app delaborators do in
fact exist for the head constant, and it also ensures arguments are only
delaborated once. Then, in `(f + g) 1`, the `f + g` gets TermInfo
registered for that subexpression, making it properly hoverable.

The app delaborator is also refactored, and there are some bug fixes:
- app unexpanders only run when `pp.explicit` is false
- trailing parameters in under-applied applications are now only
considered up to reducible & instance transparency, which lets, for
example, optional arguments for `IO`-valued functions to be omitted.
(`IO` is a reader monad, so it's hiding a pi type)
- app unexpanders will no longer run for delaborators that use
`withOverApp`
- auto parameters now always pretty print, since we are not verifying
that the provided argument equals the result of evaluating the tactic

Furthermore, the `notation` command has been modified to generate an app
unexpander that relies on the app delaborator's new behavior.

The change to app unexpanders is reverse-compatible, but it's
recommended to update `@[app_unexpander]`s in downstream projects so
that they no longer handle overapplication themselves.
2024-02-27 07:04:17 +00:00
Leonardo de Moura
c5fd88f5e1
feat: set literal unexpander (#3513) 2024-02-27 03:02:41 +00:00
Leonardo de Moura
5e101cf983
feat: use attribute command to add and erase simprocs (#3511) 2024-02-26 23:41:49 +00:00
Leonardo de Moura
bb0695b017
fix: simp? should track unfolded let-decls (#3510)
closes #3501
2024-02-26 20:49:24 +00:00
Leonardo de Moura
4a14ea3a5c
fix: rewrite tactic should not try to synthesize instances that have been inferred by unification (#3509) 2024-02-26 20:18:07 +00:00
Leonardo de Moura
f0b4902f7a
fix: simp should not try to synthesize instance implicit arguments that have been inferred by unification (#3507) 2024-02-26 20:17:55 +00:00
Leonardo de Moura
17fb8664f8
fix: issue when matching Int literals (#3504) 2024-02-26 13:09:07 +00:00
Marc Huisinga
a929c0176d
fix: auto-completion bugs and performance (#3460)
This PR addresses several performance issues in the auto-completion
implementation. It also fixes a number of smaller bugs related to
auto-completion.

In a file with `import Mathlib`, the performance of various kinds of
completions has improved as follows:
- Completing `C`: 49000ms -> 1400ms
- Completing `Cat`: 14300ms -> 1000ms
- Completing `x.` for `x : Nat`: 3700ms -> 220ms
- Completing `.` for an expected type of `Nat`: 11000ms -> 180ms

The following bugs have been fixed as well:
- VS Code never used our custom completion order. Now, the server fuzzy
completion score decides the order that completions appear in.
- Dot auto-completion for private types did not work at all. It does
now.
- Completing `.<identifier>` (where the expected type is used to infer
the namespace) did not filter by the expected type and instead displayed
all matching constants in the respective namespace. Now, it uses the
expected type for filtering. Note that this is not perfect because
sub-namespaces are technically correct completions as well (e.g.
`.Foo.foobar`). Implementing this is future work.
- Completing `.` was often not possible at all. Now, as long as the `.`
is not used in a bracket (where it may be used for the anonymous lambda
feature, e.g. `(. + 1)`), it triggers the correct completion.
-  Fixes #3228.
- The auto-completion in `#check` commands would always try to complete
identifiers using the full declaration name (including namespaces) if it
could be resolved. Now it simply uses the identifier itself in case
users want to complete this identifier to another identifier.

## Details

Regarding completion performance, I have more ideas on how to improve it
further in the future.

Other changes:
- The feature that completions with a matching expected type are sorted
to the top of the server-side ordering was removed. This was never
enabled in VS Code because it would use its own completion item order
and when testing it I found it to be more confusing than useful.
- In the server-side ordering, we would always display keywords at the
top of the list. They are now displayed according to their fuzzy match
score as well.

The following approaches have been used to improve performance:
- Pretty-printing the type for every single completion made up a
significant amount of the time needed to compute the completions. We now
do not pretty-print the type for every single completion that is offered
to the user anymore. Instead, the language server now supports
`completionItem/resolve` requests to compute the type lazily when the
user selects a completion item.
- Note that we need to keep the amount of properties that we compute in
a resolve request to a minimum. When the server receives the resolve
request, the document state may have changed from the state it was in
when the initial auto-completion request was received. LSP doesn't tell
us when it will stop sending resolve requests, so we cannot keep this
state around, as we would have to keep it around forever.
LSP's solution for this dilemma is to have servers send all the state
they need to compute a response to a resolve request to the client as
part of the initial auto completion response (which then sends it back
as part of the resolve request), but this is clearly infeasible for all
real language servers where the amount of state needed to resolve a
request is massive.
This means that the only practical solution is to use the current state
to compute a response to the resolve request, which may yield an
incorrect result. This scenario can especially occur when using
LiveShare where the document is edited by another person while cycling
through available completions.
- Request handlers can now specify a "header caching handler" that is
called after elaborating the header of a file. Request handlers can use
this caching handler to compute caches for information stored in the
header. The auto-completion uses this to pre-compute non-blacklisted
imported declarations, which in turn allow us to iterate only over
non-blacklisted imported declarations where we would before iterate over
all declarations in the environment. This is significant because
blacklisted declarations make up about 4/5 of all declarations.
- Dot completion now looks up names modulo private prefixes to figure
out whether a declaration is in the namespace of the type to the left of
the dot instead of first stripping the private prefix from the name and
then comparing it. This has the benefit that we do not need to scan the
full name in most cases.

This PR also adds a couple of regression tests for fixed bugs, but *no
benchmarks*. We will add these in the future when we add proper support
for benchmarking server interaction sessions to our benchmarking
architecture.

All tests that were broken by producing different completion output
(empty `detail` field, added `sortText?` and `data?` fields) have been
manually checked by me to be still correct before replacing their
expected output.
2024-02-26 09:43:19 +00:00
Scott Morrison
3dd10654e1 chore: upstream Std.CodeAction.*
Remove tactic_code_action

rearrange

oops

.

add tests

import file

Update src/Lean/Elab/Tactic/GuardMsgs.lean

Co-authored-by: David Thrane Christiansen <david@davidchristiansen.dk>

Update src/Lean/Elab/Tactic/GuardMsgs.lean

Co-authored-by: David Thrane Christiansen <david@davidchristiansen.dk>

fix namespace

move GuardMsgs

cleanup
2024-02-25 11:44:42 -08:00
Leonardo de Moura
9e5e0e23b2 perf: mkSplitterProof 2024-02-24 16:08:07 -08:00
Leonardo de Moura
33bc46d1a7 fix: complete Fin match 2024-02-24 16:08:07 -08:00
Leonardo de Moura
056cb75ee0 fix: match literal pattern support
The equation lemmas were not using the standard representation for literals.
2024-02-24 16:08:07 -08:00
Leonardo de Moura
335fef4396 feat: add helper functions for recognizing builtin literals 2024-02-24 16:08:07 -08:00
Leonardo de Moura
5b15e1a9f3
fix: disable USize simprocs (#3488) 2024-02-24 02:37:39 +00:00
Leonardo de Moura
d179d6c8d7
perf: bitvector literals in match patterns (#3485) 2024-02-24 00:38:46 +00:00
Leonardo de Moura
51fe66b9eb test: toExpr tests 2024-02-23 15:16:12 -08:00
Leonardo de Moura
4d4b79757d chore: move BitVec to top level namespace
Motivation: `Nat`, `Int`, `Fin`, `UInt??` are already in the top level
namespace. We will eventually define `UInt??` and `Int??` using `BitVec`.
2024-02-23 15:15:57 -08:00
Joachim Breitner
87e7c666e2
refactor: drop sizeOf_get_lt, duplicate of sizeOf_get (#3481) 2024-02-23 18:43:28 +00:00
Scott Morrison
5a32473f66
feat: replace ToExpr Int (#3472)
The current `ToExpr Int` instance produces `@Int.ofNat (@OfNat.ofNat Nat
i ...)` for nonnegative `i` and `@Int.negSucc (@OfNat.ofNat Nat (-i+1)
...)` for negative `i`.

However it should be producing `@OfNat.ofNat Int i ...` for nonnegative
`i`, and `@Neg.neg ... (@OfNat.ofNat Int (-i) ...)` for negative `i`.
2024-02-23 02:30:05 +00:00
Siddharth
e17e0d36a7
feat: omega uses b^(e+1) = b^e*b when b constant (#3450)
This is very helpful when dealing with bitvectors, where a case analysis
on the bitwidth leaves one with hypotheses of the form `x<2^(Nat.succ
w)`.

Design decisions I am unsure about:
- Is creating a helper `succ?` the correct way to match on the exponent
`e+1`?
- I'm not certain why the prior call to `Int.ofNat_pow` also checked
that the exponent was a ground natural. I removed this, since we now
explicitly handle cases where the exponent is a term of the form `e+1`.

---------

Co-authored-by: Scott Morrison <scott.morrison@gmail.com>
Co-authored-by: Joe Hendrix <joe@lean-fro.org>
Co-authored-by: Alex Keizer <alex@keizer.dev>
2024-02-23 01:17:03 +00:00
Sebastian Ullrich
8193af33e3
fix: split libInit_shared out of libleanshared (#3421)
Avoids hitting the Windows limit on symbols per shared library soon
2024-02-22 19:16:32 +00:00
Leonardo de Moura
53146db620
fix: zetaDelta := false regression (#3459)
See new test. It is a mwe for an issue blocking Mathlib.
2024-02-22 19:10:02 +00:00
Joachim Breitner
5bbc54429f
fix: improve error message when termination argument is too dependent (#3414)
this may help users when they face #2260

fixes #2260
2024-02-22 16:39:26 +00:00
Scott Morrison
2b1a0371c6 feat: add bv_omega tactic 2024-02-22 06:23:13 -08:00
Leonardo de Moura
4d0c0e2328
fix: allow users to disable builtin simprocs in simp args (#3441) 2024-02-21 20:01:11 +00:00
Leonardo de Moura
e5d2cbceaa
fix: structural equation proof generator (#3444)
See new test.
2024-02-21 19:42:39 +00:00
Leonardo de Moura
ddd6342737
fix: support for Fin and BitVec literal normalization (#3443) 2024-02-21 19:05:47 +00:00
Joe Hendrix
75272cb157
feat: BitVec.ofNatLt and updates to use it (#3430)
This PR is an effort to improve reasoning at the Nat level about
bitvectors and reduce of Fin and Nat.

It slightly tightens some proofs, but is generally aimed at reducing
inconsistencies between definitions at the Nat and Fin types in favor of
more consistently using Nat operations.

This ports leanprover/std4#664 to Lean core.

Here was the rational I provided in the discussion for
leanprover/std4#664:

It's mostly about consistency. If we use the same types and style in
definitions and proofs, there is less surprise when unfolding or
otherwise using definitions. We use some Nat based operations that
haven't been extended to Fin such as the bitwise operations, and I don't
want to pay the overhead of introducing a Fin version of every Bitvector
operation.
So this basically means Nat is preferred.

One argument potentially in favor of Fin is that we could reuse results
proven there, but that doesn't really seem to be the case so far.

A second argument is that we want to simplify expression to use more
canonical forms and we currently can pretty-print those operations
better using ofNat than ofFin. We could define the notations using ofFin
of course though, but that's additional operators that will show up in
expressions.
2024-02-21 18:02:56 +00:00
Leonardo de Moura
d55bab41bb
feat: Int.toNat simproc (#3440) 2024-02-21 17:12:14 +00:00
David Thrane Christiansen
74e7886ce7
feat: custom error recovery in parser (#3413)
Adds a simple error-recovery mechanism to Lean's parser, similar to
those used in other combinator parsing libraries.

Lean itself isn't very amenable to error recovery with this mechanism,
as it requires global knowledge of the grammar in question to write
recovery rules that don't break backtracking or `<|>`. I only found a
few opportunities.

But for DSLs, this is really important. In particular, Verso parse
errors interacted very badly with Lean parse errors in a way that
required frequent "restart file" commands, but this mechanism allows me
to both recover from Verso parse errors and to have Lean skip the rest
of the file rather than repeatedly trying to parse it as Lean commands.
2024-02-21 14:29:54 +00:00
Scott Morrison
cc8adfb2a5
feat: support for Fin in omega (#3427) 2024-02-21 13:09:38 +00:00
Leonardo de Moura
a0089d4667 fix: match pattern missing test 2024-02-21 05:14:26 -08:00
Scott Morrison
f76bb2495b
feat: omega handles shift operators, and normalises ground term exponentials (#3433)
This is a preliminary to a BitVec frontend for `omega`.
2024-02-21 11:55:58 +00:00
Scott Morrison
959ad98861
fix: bug in omega's elimination selection (#3425)
Silly bug that was resulting in unnecessary inexact eliminations. I'm
surprised this hasn't already been biting users.
2024-02-21 01:46:08 +00:00
Joe Hendrix
29244f32f6
chore: upstream solve_by_elim (#3408)
This upstreams the solve_by_elim tactic from Std.

It is a key tactic needed by library_search.
2024-02-21 01:16:04 +00:00
Sebastian Ullrich
c9aea32d3e
chore: speedcenter: count max symbols in shared libraries (#3418) 2024-02-20 19:25:24 +00:00
Scott Morrison
28a02a8688 chore: upstream norm_cast attributes and tests 2024-02-20 07:00:47 -08:00
Scott Morrison
35e374350c
chore: upstream norm_cast tactic (#3322)
This is a quite substantial tactic.

It also includes the infamour `NatCast` typeclass (which I've equipped
with a module-doc). I wasn't at all sure where that should live, so it
is currently randomly in `Lean/Elan/Tactic/NatCast.lean`: presumably if
we're doing this it will go somewhere in `Init`.

---------

Co-authored-by: Leonardo de Moura <leomoura@amazon.com>
2024-02-19 17:49:17 -08:00
Leonardo de Moura
9e27e92eea
chore: set literal notation (#3348)
Co-authored-by: Sebastian Ullrich <sebasti@nullri.ch>
2024-02-19 23:22:36 +00:00
Leonardo de Moura
489f2da711
feat: add simproc for BitVec.signExtend (#3409) 2024-02-19 15:15:37 -08:00