Check for equality before deferring
authorSimon Peyton Jones <simonpj@microsoft.com>
Wed, 4 Mar 2015 13:18:57 +0000 (13:18 +0000)
committerSimon Peyton Jones <simonpj@microsoft.com>
Wed, 4 Mar 2015 13:19:35 +0000 (13:19 +0000)
commit3aa2519ec29156f57a862a033bc7a902b742a2e0
treeb75273a05019215e02862e774486e23998275f22
parentef2c7a7345a3c39c5290894e16edf187b97d3a96
Check for equality before deferring

This one was a bit of a surprise. In fixing Trac #7854, I moved
the checkAmbiguity tests to checkValidType. That meant it happened
even for monotypes, and that turned out to be very expensive in
T9872a, for reasons described in this (new) Note in TcUnify:

    Note [Check for equality before deferring]
    ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
    Particularly in ambiguity checks we can get equalities like (ty ~ ty).
    If ty involves a type function we may defer, which isn't very sensible.
    An egregious example of this was in test T9872a, which has a type signature
           Proxy :: Proxy (Solutions Cubes)
    Doing the ambiguity check on this signature generates the equality
       Solutions Cubes ~ Solutions Cubes
    and currently the constraint solver normalises both sides at vast cost.
    This little short-cut in 'defer' helps quite a bit.

I fixed the problem with a quick equality test, but it feels like an ad-hoc
solution; I think we might want to do something in the constraint solver too.

(The problem was there all along, just more hidden.)
compiler/typecheck/TcUnify.hs
compiler/typecheck/TcValidity.hs