[GHC] #12430: TypeFamilyDependencies accepts invalid injectivity annotation
#12430: TypeFamilyDependencies accepts invalid injectivity annotation -------------------------------------+------------------------------------- Reporter: vagarenko | Owner: Type: bug | Status: new Priority: high | Milestone: Component: Compiler | Version: 8.0.1 (Type checker) | Keywords: | Operating System: Unknown/Multiple Architecture: | Type of failure: GHC accepts Unknown/Multiple | invalid program Test Case: | Blocked By: Blocking: | Related Tickets: Differential Rev(s): | Wiki Page: -------------------------------------+------------------------------------- Consider this code (depends on singletons-2.2): {{{#!hs {-# LANGUAGE TypeFamilies, DataKinds, PolyKinds, TypeOperators, KindSignatures, TypeInType, TypeFamilyDependencies, UndecidableInstances #-} module Bug where import Data.Kind (Type) import Data.Singletons.Prelude (Map, SndSym0) import GHC.TypeLits (Nat) data Payload = A | B newtype NewType a = NewType Int type NatList = [(Nat, Payload)] type StripNatList (natList :: NatList) = Map SndSym0 natList type family Family (natList :: NatList) = (r :: Type) | r -> natList where Family '[] = () Family xs = NewType (StripNatList xs) }}} Why GHC is okay with injectivity annotation for `Family`: `r -> natList`? These two types: {{{#!hs type Foo = Family '[ '(0, 'A), '(1, 'B)] type Bar = Family '[ '(0, 'A), '(0, 'B)] }}} are obviously map to the same type: {{{#!hs *Bug Data.Singletons.Prelude> :kind! Foo Foo :: * = NewType ('A :$$$ '['B]) *Bug Data.Singletons.Prelude> :kind! Bar Bar :: * = NewType ('A :$$$ '['B]) }}} ---- If inline `StripNatList` inside `Family` definition: {{{#!hs type family Family (natList :: NatList) = (r :: Type) | r -> natList where Family '[] = () Family xs = NewType (Map SndSym0 xs) }}} or change `StripNatList` definition to type family: {{{#!hs type family StripNatList (natList :: NatList) where StripNatList '[] = '[] StripNatList ('(n, x) ': xs) = x ': StripNatList xs }}} compilation expectedly fails with `Type family equation violates injectivity annotation.` ---- Moreover, if I remove `NewType` from `Family` and change result kind: {{{#!hs type family Family (natList :: NatList) = (r :: [Payload]) | r -> natList where Family xs = StripNatList xs }}} it fails with correct error regardless of `StripNatList` definition. -- Ticket URL: <http://ghc.haskell.org/trac/ghc/ticket/12430> GHC <http://www.haskell.org/ghc/> The Glasgow Haskell Compiler
#12430: TypeFamilyDependencies accepts invalid injectivity annotation -------------------------------------+------------------------------------- Reporter: vagarenko | Owner: Type: bug | Status: new Priority: high | Milestone: Component: Compiler (Type | Version: 8.0.1 checker) | Resolution: | Keywords: Operating System: Unknown/Multiple | Architecture: Type of failure: GHC accepts | Unknown/Multiple invalid program | Test Case: Blocked By: | Blocking: Related Tickets: | Differential Rev(s): Wiki Page: | -------------------------------------+------------------------------------- Comment (by goldfire): It looks like we're not being aggressive enough in unrolling type synonyms -- a legitimate bug. -- Ticket URL: <http://ghc.haskell.org/trac/ghc/ticket/12430#comment:1> GHC <http://www.haskell.org/ghc/> The Glasgow Haskell Compiler
#12430: TypeFamilyDependencies accepts invalid injectivity annotation -------------------------------------+------------------------------------- Reporter: vagarenko | Owner: (none) Type: bug | Status: new Priority: high | Milestone: Component: Compiler (Type | Version: 8.0.1 checker) | Resolution: | Keywords: Operating System: Unknown/Multiple | Architecture: Type of failure: GHC accepts | Unknown/Multiple invalid program | Test Case: Blocked By: | Blocking: Related Tickets: | Differential Rev(s): Wiki Page: | -------------------------------------+------------------------------------- Comment (by monoidal): Here's a simpler version: {{{ #!hs {-# LANGUAGE TypeFamilies, PolyKinds, KindSignatures, TypeFamilyDependencies, GADTs, ScopedTypeVariables #-} module Bug where import Data.Kind (Type) data Proxy a type C a = Int type family Family (x :: Type) = (y :: Type) | y -> x where Family x = Proxy (C x) }}} `Family` shouldn't be allowed to be injective, it's a constant function: `Family Int ~ Family Bool`. -- Ticket URL: <http://ghc.haskell.org/trac/ghc/ticket/12430#comment:2> GHC <http://www.haskell.org/ghc/> The Glasgow Haskell Compiler
#12430: TypeFamilyDependencies accepts invalid injectivity annotation -------------------------------------+------------------------------------- Reporter: vagarenko | Owner: (none) Type: bug | Status: new Priority: high | Milestone: Component: Compiler (Type | Version: 8.0.1 checker) | Keywords: Resolution: | InjectiveFamilies Operating System: Unknown/Multiple | Architecture: Type of failure: GHC accepts | Unknown/Multiple invalid program | Test Case: Blocked By: | Blocking: Related Tickets: | Differential Rev(s): Wiki Page: | -------------------------------------+------------------------------------- Changes (by RyanGlScott): * keywords: => InjectiveFamilies Comment: Even simpler: {{{#!hs {-# LANGUAGE TypeFamilyDependencies #-} module Bug where type C a = Int type family F x = y | y -> x where F x = C x }}} I'm on this. -- Ticket URL: <http://ghc.haskell.org/trac/ghc/ticket/12430#comment:3> GHC <http://www.haskell.org/ghc/> The Glasgow Haskell Compiler
#12430: TypeFamilyDependencies accepts invalid injectivity annotation -------------------------------------+------------------------------------- Reporter: vagarenko | Owner: (none) Type: bug | Status: patch Priority: high | Milestone: Component: Compiler (Type | Version: 8.0.1 checker) | Keywords: Resolution: | InjectiveFamilies Operating System: Unknown/Multiple | Architecture: Type of failure: GHC accepts | Unknown/Multiple invalid program | Test Case: Blocked By: | Blocking: Related Tickets: | Differential Rev(s): Phab:D5228 Wiki Page: | -------------------------------------+------------------------------------- Changes (by RyanGlScott): * status: new => patch * differential: => Phab:D5228 -- Ticket URL: <http://ghc.haskell.org/trac/ghc/ticket/12430#comment:4> GHC <http://www.haskell.org/ghc/> The Glasgow Haskell Compiler
#12430: TypeFamilyDependencies accepts invalid injectivity annotation -------------------------------------+------------------------------------- Reporter: vagarenko | Owner: (none) Type: bug | Status: patch Priority: high | Milestone: Component: Compiler (Type | Version: 8.0.1 checker) | Keywords: Resolution: | InjectiveFamilies Operating System: Unknown/Multiple | Architecture: Type of failure: GHC accepts | Unknown/Multiple invalid program | Test Case: Blocked By: | Blocking: Related Tickets: | Differential Rev(s): Phab:D5228 Wiki Page: | -------------------------------------+------------------------------------- Comment (by Ben Gamari <ben@…>): In [changeset:"26e81e90281685af37c8f2cf149c242b4039117a/ghc" 26e81e90/ghc]: {{{ #!CommitTicketReference repository="ghc" revision="26e81e90281685af37c8f2cf149c242b4039117a" Fix #12430 by expanding type synonyms in injTyVarsOfType We weren't expanding type synonyms when determining the injective type variables of a type, leading to certain non-injective families being mistakenly labeled as injective (#12430). Easily fixed with a tactical use of `coreView`. Test Plan: make test TEST=T12430 Reviewers: bgamari, goldfire Reviewed By: goldfire Subscribers: goldfire, rwbarton, carter GHC Trac Issues: #12430 Differential Revision: https://phabricator.haskell.org/D5228 }}} -- Ticket URL: <http://ghc.haskell.org/trac/ghc/ticket/12430#comment:5> GHC <http://www.haskell.org/ghc/> The Glasgow Haskell Compiler
#12430: TypeFamilyDependencies accepts invalid injectivity annotation -------------------------------------+------------------------------------- Reporter: vagarenko | Owner: (none) Type: bug | Status: closed Priority: high | Milestone: 8.8.1 Component: Compiler (Type | Version: 8.0.1 checker) | Keywords: Resolution: fixed | InjectiveFamilies Operating System: Unknown/Multiple | Architecture: Type of failure: GHC accepts | Unknown/Multiple invalid program | Test Case: Blocked By: | Blocking: Related Tickets: | Differential Rev(s): Phab:D5228 Wiki Page: | -------------------------------------+------------------------------------- Changes (by bgamari): * status: patch => closed * resolution: => fixed * milestone: => 8.8.1 -- Ticket URL: <http://ghc.haskell.org/trac/ghc/ticket/12430#comment:6> GHC <http://www.haskell.org/ghc/> The Glasgow Haskell Compiler
participants (1)
-
GHC