summaryrefslogtreecommitdiff
path: root/compiler/GHC/Tc/Utils
diff options
context:
space:
mode:
authorRichard Eisenberg <rae@richarde.dev>2020-01-15 22:49:51 +0000
committerMarge Bot <ben+marge-bot@smart-cactus.org>2021-09-29 09:40:14 -0400
commitb8d98827d73fd3e49867cab09f9440fc8c311bfe (patch)
tree51f28143cdf9898ae5b75d08ce4a7c71b05cc8ad /compiler/GHC/Tc/Utils
parent028abd5bf398db6d872a10342695e8e84e0827b3 (diff)
downloadhaskell-b8d98827d73fd3e49867cab09f9440fc8c311bfe.tar.gz
Compare FunTys as if they were TyConApps.
See Note [Equality on FunTys] in TyCoRep. Close #17675. Close #17655, about documentation improvements included in this patch. Close #19677, about a further mistake around FunTy. test cases: typecheck/should_compile/T19677
Diffstat (limited to 'compiler/GHC/Tc/Utils')
-rw-r--r--compiler/GHC/Tc/Utils/TcType.hs34
1 files changed, 12 insertions, 22 deletions
diff --git a/compiler/GHC/Tc/Utils/TcType.hs b/compiler/GHC/Tc/Utils/TcType.hs
index 367922e3e5..d878ccc75a 100644
--- a/compiler/GHC/Tc/Utils/TcType.hs
+++ b/compiler/GHC/Tc/Utils/TcType.hs
@@ -625,6 +625,10 @@ EQUAL TO, but we'd need to think carefully about
But in fact (GivenInv) is automatically true, so we're adhering to
it for now. See #18929.
+* If a tyvar tv has level n, then the levels of all variables free
+ in tv's kind are <= n. Consequence: if tv is untouchable, so are
+ all variables in tv's kind.
+
Note [WantedInv]
~~~~~~~~~~~~~~~~
Why is WantedInv important? Consider this implication, where
@@ -1591,6 +1595,7 @@ tc_eq_type :: Bool -- ^ True <=> do not expand type synonyms
-> Type -> Type
-> Bool
-- Flags False, False is the usual setting for tc_eq_type
+-- See Note [Computing equality on types] in Type
tc_eq_type keep_syns vis_only orig_ty1 orig_ty2
= go orig_env orig_ty1 orig_ty2
where
@@ -1620,10 +1625,14 @@ tc_eq_type keep_syns vis_only orig_ty1 orig_ty2
-- Make sure we handle all FunTy cases since falling through to the
-- AppTy case means that tcRepSplitAppTy_maybe may see an unzonked
-- kind variable, which causes things to blow up.
+ -- See Note [Equality on FunTys] in GHC.Core.TyCo.Rep: we must check
+ -- kinds here
go env (FunTy _ w1 arg1 res1) (FunTy _ w2 arg2 res2)
- = go env w1 w2 && go env arg1 arg2 && go env res1 res2
- go env ty (FunTy _ w arg res) = eqFunTy env w arg res ty
- go env (FunTy _ w arg res) ty = eqFunTy env w arg res ty
+ = kinds_eq && go env arg1 arg2 && go env res1 res2 && go env w1 w2
+ where
+ kinds_eq | vis_only = True
+ | otherwise = go env (typeKind arg1) (typeKind arg2) &&
+ go env (typeKind res1) (typeKind res2)
-- See Note [Equality on AppTys] in GHC.Core.Type
go env (AppTy s1 t1) ty2
@@ -1658,25 +1667,6 @@ tc_eq_type keep_syns vis_only orig_ty1 orig_ty2
orig_env = mkRnEnv2 $ mkInScopeSet $ tyCoVarsOfTypes [orig_ty1, orig_ty2]
- -- @eqFunTy w arg res ty@ is True when @ty@ equals @FunTy w arg res@. This is
- -- sometimes hard to know directly because @ty@ might have some casts
- -- obscuring the FunTy. And 'splitAppTy' is difficult because we can't
- -- always extract a RuntimeRep (see Note [xyz]) if the kind of the arg or
- -- res is unzonked. Thus this function, which handles this
- -- corner case.
- eqFunTy :: RnEnv2 -> Mult -> Type -> Type -> Type -> Bool
- -- Last arg is /not/ FunTy
- eqFunTy env w arg res ty@(AppTy{}) = get_args ty []
- where
- get_args :: Type -> [Type] -> Bool
- get_args (AppTy f x) args = get_args f (x:args)
- get_args (CastTy t _) args = get_args t args
- get_args (TyConApp tc tys) args
- | tc == funTyCon
- , [w', _, _, arg', res'] <- tys ++ args
- = go env w w' && go env arg arg' && go env res res'
- get_args _ _ = False
- eqFunTy _ _ _ _ _ = False
{-# INLINE tc_eq_type #-} -- See Note [Specialising tc_eq_type].
{- Note [Typechecker equality vs definitional equality]