Skip to content
GitLab
Projects Groups Snippets
  • /
  • Help
    • Help
    • Support
    • Community forum
    • Submit feedback
  • Sign in / Register
  • GHC GHC
  • Project information
    • Project information
    • Activity
    • Labels
    • Members
  • Repository
    • Repository
    • Files
    • Commits
    • Branches
    • Tags
    • Contributors
    • Graph
    • Compare
    • Locked Files
  • Issues 5,260
    • Issues 5,260
    • List
    • Boards
    • Service Desk
    • Milestones
    • Iterations
  • Merge requests 567
    • Merge requests 567
  • CI/CD
    • CI/CD
    • Pipelines
    • Jobs
    • Schedules
    • Test Cases
  • Deployments
    • Deployments
    • Releases
  • Analytics
    • Analytics
    • Value stream
    • CI/CD
    • Code review
    • Insights
    • Issue
    • Repository
  • Wiki
    • Wiki
  • Snippets
    • Snippets
  • Activity
  • Graph
  • Create a new issue
  • Jobs
  • Commits
  • Issue Boards
Collapse sidebar
  • Glasgow Haskell CompilerGlasgow Haskell Compiler
  • GHCGHC
  • Issues
  • #18311
Closed
Open
Issue created Jun 08, 2020 by Simon Peyton Jones@simonpjDeveloper

Record update is over-restrictive

Consider

type family F a

type instance F Int = Int
type instance F Bool = Int

data T a = MkT { x :: F a, y :: a }

foo1 :: T Int -> T Bool
foo1 (MkT { x = x }) = MkT { x = x, y = True}

foo2 :: T Int -> T Bool
foo2 t = t { y = True }

foo1 typechecks fine, but foo2 complains

Foo.hs:16:10: error:
    • Couldn't match type ‘Int’ with ‘Bool’
      Expected type: T Bool
        Actual type: T Int
    • In the expression: t {y = True}
      In an equation for ‘foo2’: foo2 t = t {y = True}

This is bogus. foo2 should be fine -- precisely because foo1 is.

The offending code is in the RecordUpd case of GHc.Tc.Gen.Expr.tcExpr. See this comment

        -- STEP 4  Note [Type of a record update]
        -- Figure out types for the scrutinee and result
        -- Both are of form (T a b c), with fresh type variables, but with
        -- common variables where the scrutinee and result must have the same type
        -- These are variables that appear in *any* arg of *any* of the
        -- relevant constructors *except* in the updated fields

With the advent of type families "appearing in" a type is not the same as being fixed by it.

Not hard to fix; might even lead to less code!

To upload designs, you'll need to enable LFS and have an admin enable hashed storage. More information
Assignee
Assign to
Time tracking