Repository navigation
perf: derive Repr, BEq and Hashable once per mutual block - #16339
Merged
Merged
Conversation
This PR makes `deriving Repr` on a mutual block generate the auxiliary functions once for the whole block instead of once per type, which removes quadratic elaboration cost on large mutual blocks. `mkReprInstanceHandler` now groups the requested types by mutual block, builds one aux-function block per group and emits an instance for each requested type. `mkInstanceCmds` names each instance after its own type, which leaves instance names of the other derive handlers unchanged since they pass a single type. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
|
The merge base of this PR does not coincide with branch |
This PR makes `deriving BEq` on a mutual block generate the auxiliary functions once for the whole block instead of once per type, which removes quadratic elaboration cost on large mutual blocks. `mkBEqInstanceHandler` now groups the requested types by mutual block and runs `mkBEqInstance` once per group, which emits an instance for each requested type. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
This PR makes `deriving Hashable` on a mutual block generate the auxiliary functions once for the whole block instead of once per type, which removes quadratic elaboration cost on large mutual blocks. `mkHashableHandler` now groups the requested types by mutual block, builds one aux-function block per group and emits an instance for each requested type. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Repr once per mutual blockRepr, BEq and Hashable once per mutual block
…own name `mkBEqInstance` now attaches `@[method_specs]` to the instance of every requested type instead of `ctx.instName`, so it no longer relies on a non-`partial` context covering a single type. The names are computed before the instances are added, since `mkInstName` picks names that are still free. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
The `Repr`, `BEq` and `Hashable` handlers now wrap a whole mutual-block group with `withoutExposeFromCtorsAll` instead of folding `withoutExposeFromCtors` over a separately bound continuation. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
The `Repr`, `BEq` and `Hashable` mutual-block tests now record the handler's trace with `#guard_msgs`, which shows the single generated block directly, instead of probing the environment for aux-function names. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
The benchmark derives `Repr`, `BEq` and `Hashable` on a mutual block with a 40-constructor hub (10 in the test suite), which is quadratic if a handler generates the block's auxiliary functions once per type. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Kha
marked this pull request as ready for review
November 7, 2026 20:13
Kha
enabled auto-merge
November 7, 2026 20:13
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
This PR makes
deriving Repr,BEqandHashableon a mutual block generate their auxiliary functions once for the whole block instead of once per type, removing quadratic elaboration cost on large mutual blocks.These handlers already receive all types of a mutual block in one call, but previously ran
mkContextfor each of them, and each run builds aux functions for every type in the block. They now group the requested types by mutual block (groupByMutualBlock), build one aux-function block per group, and emit an instance for each requested type.mkInstanceCmdsnames each instance after its own type; the other derive handlers pass a single type, so their instance names are unchanged. The@[no_expose]aux functions of a block derived together are now all named after the first type's instance.On a 76-type mutual block deriving one class on every type:
ReprBEqHashable