
#10338: GHC Forgets Constraints -------------------------------------+------------------------------------- Reporter: crockeea | Owner: Type: bug | Status: new Priority: normal | Milestone: Component: Compiler | Version: 7.8.3 Resolution: | Keywords: Operating System: Unknown/Multiple | Architecture: Type of failure: None/Unknown | Unknown/Multiple Blocked By: | Test Case: Related Tickets: | Blocking: | Differential Revisions: -------------------------------------+------------------------------------- Comment (by simonpj): Yes this is confusing. No it's not #10195. Here's what happens. When GHC comes across the local binding `let fromScalar' = fromScalar`, it tries to find its most general type. To do so it instantiates the call to `fromScalar` with fresh unification variables `t0` and `r0`, and generates the constraint `T t0 r0`. Now it tries to simplify that constraint, and succeeds with the top level instance declaration; and that is where things go wrong; we get the inferred type {{{ fromScalar' :: forall t r. (Functor t, Num r) => r -> t r }}} Why doesn't it refrain from simplifying `T t0 r0` because of the in-scope constraint `T t (F r)`? Answer: the most general type of a local binding is computed by calling the constraint simplifer during constraint generation. It's a break with the general plan to first do constraint generation and only then simplify constraints. If we didn't attempt to generalise the binding for `fromScalar'` we would not do this early call to the constraint solver, and all would be well (at this point the "given overlap" fix in #10195 would kick in). You might think that `MonoLocalBinds` would make this happen, but actually `MonoLocalBinds` attempts to generalise even local bindings that have no non-top-level type variables, such as this one. And indeed usually generalising is a good thing. Maybe there should be a way to turn off local generalisation altogether. Congratulations on dicovering this. I had previously thought that `MonoLocalBinds` would make the constraint solver completely well behaved, but this example shows that I wasn't quite right. I don't see an easy fix, and it seems very much a corner case so probably doesn't justify the work (and code complexity) for a non-easy fix. -- Ticket URL: http://ghc.haskell.org/trac/ghc/ticket/10338#comment:1 GHC http://www.haskell.org/ghc/ The Glasgow Haskell Compiler