Skip to content

WIP: PHASE 2 of FixedRuntimeRep

sheaf requested to merge sheaf/ghc:frr-phase-2 into master

This MR attempts to migrate most of the remaining representation-polymorphism checks to allow rewriting.

Overview

  • Several inference functions such as tcInferRho now have counterparts that guarantee a syntactically fixed RuntimeRep (in this case, tcInferRhoFRR). These are nice, as we don't even need to put any coercions anywhere.

  • Added newOpenFlexiTyVarFRR which creates a new metavariable whose kind is a concrete metavariable. This is used in particular in matchActualFunTySigma.

  • To allow rewriting in patterns (in particular with UnliftedNewtypes), I had to adjust tcConPat to check both the argument types and the return type. This passes on the cast using the cpt_wrap field (which used to only be used for pattern synonyms and always carried idHsWrapper for real data constructors), which is then used in mkCoAlgCaseMatchResult.

  • Data constructor patterns can now have an additional cast. What I mean is that, given a datatype constructor MkD :: ... -> D x y z, when we use the MkD pattern, we check that the overall type D a b c has a syntactically fixed RuntimeRep, which might might require adding a cast. This means that use-sites of a MkD pattern will have a result type of the form D a b c |> co, and not just D a b c. To account for this, I changed many calls to splitTyConApp to splitCastedTyConApp, peeling off the additional cast. Note that we can't store the cast in the data constructor itself, because the data constructor return type might be representation-polymorphic; it's only at use sites that we know the relevant cast to use.

  • Added some assertions in matchCoercion, which were helpful in debugging the above.

  • Added an assertion in hsPatType to check that the type of a pattern always has a syntactically fixed RuntimeRep.

  • Added an assertion in dsHsWrapper to check that the "from" type of a WpFun wrapper has a syntactically fixed RuntimeRep. It would be nicer to check this when constructing the wrapper (in mkWpFun), but that isn't possible due to the Typed Template Haskell wrinkle outlined in Note [hasFixedRuntimeRep] in GHC.Tc.Utils.Concrete.

Checks still in PHASE 1

The only remaining uses of hasFixedRuntimeRep_syntactic are, currently:

  • in arrows (just because I haven't thought about it),
  • in monad/list comprehensions (ditto),
  • tcRecordField (ditto),
  • in hasFixedRuntimeRep_remainingValArgs, because we need to come up with a better story for eta-expansion rather than relying on simple_app, which is not robust as seen in #21377 (closed),
  • in tcPolyBinds because the check needs to be moved earlier as shown by #21238 (see this comment in particular).

Known bugs

I haven't completely ironed out the situation with splitTyConApp vs splitCastedTyConApp that resulted from data constructor patterns returning a type of the form D a b c |> co (i.e. an application of the parent TyCon BUT possibly wrapped in a cast).

There are also a few issues currently that aren't really to do with this patch:

Edited by sheaf

Merge request reports