[GHC] #12423: Panic with DeriveAnyClass
GHC
ghc-devs at haskell.org
Thu Aug 25 14:18:10 UTC 2016
#12423: Panic with DeriveAnyClass
-------------------------------------+-------------------------------------
Reporter: knrafto | Owner:
Type: bug | Status: new
Priority: normal | Milestone:
Component: Compiler | Version: 8.0.1
Resolution: | Keywords:
| GenericDeriving
Operating System: Unknown/Multiple | Architecture:
| Unknown/Multiple
Type of failure: None/Unknown | Test Case:
Blocked By: | Blocking:
Related Tickets: #12144 | Differential Rev(s):
Wiki Page: |
-------------------------------------+-------------------------------------
Changes (by RyanGlScott):
* keywords: => GenericDeriving
* related: => #12144
Comment:
*sigh* I know what's happening here. The algorithm that GHC uses to infer
constraints for `* -> *`-kinded things is co-opted from the
`DeriveFunctor` algorithm, which doesn't know how to deal with argument
types like `Either a a` (since it expects that last type parameter `a` to
only ever be used as the very last type in a type application). If you
tried to derive a `Functor` instance for `data Foo a = Foo (Either a a)`,
it'd give a proper error, since GHC has
[http://git.haskell.org/ghc.git/blob/613d745523f181991f6f916bbe58082b7970f7e6:/compiler/typecheck/TcDeriv.hs#l1487
checks] specifically for derived `Functor` instances.
On the other hand, there aren't any checks like that for things that are
derived in general with `DeriveAnyClass`, so it falls through to
[http://git.haskell.org/ghc.git/blob/0676e68cf5fe8696f1f760fef0f35dba14db1104:/compiler/typecheck/TcGenDeriv.hs#l1665
some code] which throws a GHC panic. Urk.
There are two ways we can proceed here. One thing we can do is to put
these same checks for `Functor` in place for all `DeriveAnyClass`-derived
typeclasses. That would eliminate the GHC panic, but it would simply
replace one error message with another.
Another approach, which Simon suggests in
[https://mail.haskell.org/pipermail/ghc-devs/2016-June/012276.html this
ghc-devs thread], is to instead adopt a different strategy for inferring
constraints for `DeriveAnyClass`-derived things. Instead of using the
`DeriveFunctor` algorithm, we'd collect all of the constraints given by
the default signatures of the typeclass, and then simplify as needed.
It should be noted that even with the second approach, you still wouldn't
be able to derive an `Eq1` instance for `data Foo a = Foo (Either a a)`,
since you can't eta-reduce the last type variable. But you would be
allowed to derive more things with `DeriveAnyClass` than you could before.
A similar problem popped up in #12144, except that uses the last type
variable in a contravariant position (another thing which the
`DeriveFunctor` algorithm chokes on).
Even though this ticket is technically a duplicate of #12144, I'll keep
this one open, since it's of a somewhat different nature and provides
another nice test case.
--
Ticket URL: <http://ghc.haskell.org/trac/ghc/ticket/12423#comment:3>
GHC <http://www.haskell.org/ghc/>
The Glasgow Haskell Compiler
More information about the ghc-tickets
mailing list