[GHC] #10675: GHC does not check the functional dependency consistency condition correctly

GHC ghc-devs at haskell.org
Thu Apr 13 11:06:14 UTC 2017


#10675: GHC does not check the functional dependency consistency condition
correctly
-------------------------------------+-------------------------------------
        Reporter:  simonpj           |                Owner:  (none)
            Type:  bug               |               Status:  new
        Priority:  normal            |            Milestone:
       Component:  Compiler          |              Version:  7.10.1
      Resolution:                    |             Keywords:
Operating System:  Unknown/Multiple  |         Architecture:
                                     |  Unknown/Multiple
 Type of failure:  None/Unknown      |            Test Case:
      Blocked By:                    |             Blocking:
 Related Tickets:                    |  Differential Rev(s):
       Wiki Page:                    |
-------------------------------------+-------------------------------------

Comment (by AntC):

 ''Should these two instance declarations be accepted?''

 Depends what you mean by "accepted". I think the case is suffering from
 GHC's delayed/lazy instance enforcement, as affects the complications of
 confluence around partially overlapping instances.

 The `C Char ...` instance clearly could never work -- its constraint needs
 an infinite regress on `C Char [[[[ ... ]]]] ...`. Is anybody saying that
 instance on its own should be rejected? If so, see counter-example/highly
 valuable exploit below.

 It's an interesting experiment trying to find valid calls for `f` [I'm
 using 7.10]. This works: `f (Just "quoi?")`. This doesn't: `f ("quoi")` --
 GHC complains `"Couldn't match expected type 'Maybe y0' with actual type
 '[Char]'"`.

 So GHC __is__  applying the fundep `a -> b` Consistency Condition as per
 '''Definition 6''' in the CHRs/Mark Jones 2000 paper. It is taking `[x]
 [Maybe y]` to infer that in `[x] [x]` we must have `x ~ Maybe y` -- as the
 O.P. is saying.

 I think we've no reason to reject this example. Or perhaps Iavor could
 explain what "loophole" this opens up? Can it result in type incoherence?

 Before we reject this example as bogus, @Richard, I think there are
 examples similar to it that might get caught in the crossfire. [That's the
 reason I arrived here, because I'm trying to understand how/why the
 FunDeps work for it.] The classic Type-level type equality test:

 {{{
 class TTypeEq (a :: *) (a' :: *) (b :: Bool) | a a' -> b
 instance TTypeEq a a True
 instance (b ~ False) => TTypeEq a a' b
 }}}

 Seems to break '''Definition 6'''. There's a substitution for the two
 instances that makes the determinants of the FunDep equal, namely `{a' ~
 a}`. And under that substitution, the dependents are not equal `{b vs
 False}`. FWIW, Hugs applies a stricter interpretation of '''Definition
 6''', with the consequence no such declaration of `TTypeEq` is accepted
 [explored in Oleg/Ralph's HList paper].

 Or if we include substitution `{b ~ True}`, that substitution invalidates
 the constraint on the `False` instance. Clearly GHC isn't evaluating the
 instance's constraints for consistency with its improvement of the class
 parameters.

 We can't write that second instance as:
 {{{
 instance TTypeEq a a' False
 }}}
 GHC complains `"Functional Dependencies conflict between instance
 declarations"`

 What would any proposed fix for this ticket do to a class like?
 {{{
 class TTypeEq2 x a a' b | a a' -> b
 instance TTypeEq2 Bool a a True
 instance TTypeEq2 Char a a True
 instance (b ~ False) Bool a a' b
 instance (b ~ False) Char a a' b
 }}}

--
Ticket URL: <http://ghc.haskell.org/trac/ghc/ticket/10675#comment:9>
GHC <http://www.haskell.org/ghc/>
The Glasgow Haskell Compiler


More information about the ghc-tickets mailing list