{-# LANGUAGE FlexibleContexts #-}
{-# LANGUAGE DisambiguateRecordFields #-}
{-# OPTIONS_GHC -Wno-incomplete-uni-patterns #-}
{-# OPTIONS_GHC -Wno-incomplete-record-updates #-}
module GHC.Tc.Utils.Instantiate (
topSkolemise,
topInstantiate,
instantiateSigma,
instCall, instDFunType, instStupidTheta, instTyVarsWith,
newWanted, newWanteds,
tcInstType, tcInstTypeBndrs,
tcSkolemiseInvisibleBndrs,
tcInstSkolTyVars, tcInstSkolTyVarsX,
tcSkolDFunType, tcSuperSkolTyVars, tcInstSuperSkolTyVarsX,
freshenTyVarBndrs, freshenCoVarBndrsX,
tcInstInvisibleTyBindersN, tcInstInvisibleTyBinders, tcInstInvisibleTyBinder,
newOverloadedLit, mkOverLit,
newClsInst,
tcGetInsts, tcGetInstEnvs, getOverlapFlag,
tcExtendLocalInstEnv,
instCallConstraints, newMethodFromName,
tcSyntaxName,
tyCoVarsOfWC,
tyCoVarsOfCt, tyCoVarsOfCts,
) where
import GHC.Prelude
import GHC.Driver.Session
import GHC.Driver.Env
import GHC.Builtin.Types ( heqDataCon, eqDataCon, integerTyConName )
import GHC.Builtin.Names
import GHC.Hs
import GHC.Hs.Syn.Type ( hsLitType )
import GHC.Core.InstEnv
import GHC.Core.Predicate
import GHC.Core ( Expr(..), isOrphan )
import GHC.Core.Type
import GHC.Core.Multiplicity
import GHC.Core.TyCo.Rep
import GHC.Core.TyCo.Ppr ( debugPprType )
import GHC.Core.Class( Class )
import GHC.Core.DataCon
import {-# SOURCE #-} GHC.Tc.Gen.Expr( tcCheckPolyExpr, tcSyntaxOp )
import {-# SOURCE #-} GHC.Tc.Utils.Unify( unifyType, unifyKind )
import GHC.Tc.Utils.Zonk
import GHC.Tc.Utils.Monad
import GHC.Tc.Types.Constraint
import GHC.Tc.Types.Origin
import GHC.Tc.Utils.Env
import GHC.Tc.Types.Evidence
import GHC.Tc.Instance.FunDeps
import GHC.Tc.Utils.Concrete ( hasFixedRuntimeRep_syntactic )
import GHC.Tc.Utils.TcMType
import GHC.Tc.Utils.TcType
import GHC.Tc.Errors.Types
import GHC.Types.Id.Make( mkDictFunId )
import GHC.Types.Basic ( TypeOrKind(..), Arity )
import GHC.Types.Error
import GHC.Types.SourceText
import GHC.Types.SrcLoc as SrcLoc
import GHC.Types.Var.Env
import GHC.Types.Var.Set
import GHC.Types.Id
import GHC.Types.Name
import GHC.Types.Var
import qualified GHC.LanguageExtensions as LangExt
import GHC.Utils.Misc
import GHC.Utils.Panic
import GHC.Utils.Panic.Plain
import GHC.Utils.Outputable
import GHC.Unit.State
import GHC.Unit.External
import Data.List ( mapAccumL )
import qualified Data.List.NonEmpty as NE
import Control.Monad( when, unless )
import Data.Function ( on )
newMethodFromName
:: CtOrigin
-> Name
-> [TcRhoType]
-> TcM (HsExpr GhcTc)
newMethodFromName :: CtOrigin -> Name -> [Type] -> TcM (HsExpr GhcTc)
newMethodFromName CtOrigin
origin Name
name [Type]
ty_args
= do { DFunId
id <- Name -> TcM DFunId
tcLookupId Name
name
; let ty :: Type
ty = (() :: Constraint) => Type -> [Type] -> Type
Type -> [Type] -> Type
piResultTys (DFunId -> Type
idType DFunId
id) [Type]
ty_args
([Type]
theta, Type
_caller_knows_this) = Type -> ([Type], Type)
tcSplitPhiTy Type
ty
; HsWrapper
wrap <- Bool -> TcM HsWrapper -> TcM HsWrapper
forall a. HasCallStack => Bool -> a -> a
assert (Bool -> Bool
not (Type -> Bool
isForAllTy Type
ty) Bool -> Bool -> Bool
&& [Type] -> Bool
forall a. [a] -> Bool
isSingleton [Type]
theta) (TcM HsWrapper -> TcM HsWrapper) -> TcM HsWrapper -> TcM HsWrapper
forall a b. (a -> b) -> a -> b
$
CtOrigin -> [Type] -> [Type] -> TcM HsWrapper
instCall CtOrigin
origin [Type]
ty_args [Type]
theta
; HsExpr GhcTc -> TcM (HsExpr GhcTc)
forall a. a -> IOEnv (Env TcGblEnv TcLclEnv) a
forall (m :: * -> *) a. Monad m => a -> m a
return (HsWrapper -> HsExpr GhcTc -> HsExpr GhcTc
mkHsWrap HsWrapper
wrap (XVar GhcTc -> LIdP GhcTc -> HsExpr GhcTc
forall p. XVar p -> LIdP p -> HsExpr p
HsVar XVar GhcTc
NoExtField
noExtField (DFunId -> LocatedAn NameAnn DFunId
forall a an. a -> LocatedAn an a
noLocA DFunId
id))) }
topSkolemise :: SkolemInfo
-> TcSigmaType
-> TcM ( HsWrapper
, [(Name,TyVar)]
, [EvVar]
, TcRhoType )
topSkolemise :: SkolemInfo
-> Type -> TcM (HsWrapper, [(Name, DFunId)], [DFunId], Type)
topSkolemise SkolemInfo
skolem_info Type
ty
= TCvSubst
-> HsWrapper
-> [(Name, DFunId)]
-> [DFunId]
-> Type
-> TcM (HsWrapper, [(Name, DFunId)], [DFunId], Type)
go TCvSubst
init_subst HsWrapper
idHsWrapper [] [] Type
ty
where
init_subst :: TCvSubst
init_subst = InScopeSet -> TCvSubst
mkEmptyTCvSubst (VarSet -> InScopeSet
mkInScopeSet (Type -> VarSet
tyCoVarsOfType Type
ty))
go :: TCvSubst
-> HsWrapper
-> [(Name, DFunId)]
-> [DFunId]
-> Type
-> TcM (HsWrapper, [(Name, DFunId)], [DFunId], Type)
go TCvSubst
subst HsWrapper
wrap [(Name, DFunId)]
tv_prs [DFunId]
ev_vars Type
ty
| ([DFunId]
tvs, [Type]
theta, Type
inner_ty) <- Type -> ([DFunId], [Type], Type)
tcSplitSigmaTy Type
ty
, Bool -> Bool
not ([DFunId] -> Bool
forall a. [a] -> Bool
forall (t :: * -> *) a. Foldable t => t a -> Bool
null [DFunId]
tvs Bool -> Bool -> Bool
&& [Type] -> Bool
forall a. [a] -> Bool
forall (t :: * -> *) a. Foldable t => t a -> Bool
null [Type]
theta)
= do { (TCvSubst
subst', [DFunId]
tvs1) <- SkolemInfo -> TCvSubst -> [DFunId] -> TcM (TCvSubst, [DFunId])
tcInstSkolTyVarsX SkolemInfo
skolem_info TCvSubst
subst [DFunId]
tvs
; [DFunId]
ev_vars1 <- [Type] -> TcM [DFunId]
newEvVars ((() :: Constraint) => TCvSubst -> [Type] -> [Type]
TCvSubst -> [Type] -> [Type]
substTheta TCvSubst
subst' [Type]
theta)
; TCvSubst
-> HsWrapper
-> [(Name, DFunId)]
-> [DFunId]
-> Type
-> TcM (HsWrapper, [(Name, DFunId)], [DFunId], Type)
go TCvSubst
subst'
(HsWrapper
wrap HsWrapper -> HsWrapper -> HsWrapper
<.> [DFunId] -> HsWrapper
mkWpTyLams [DFunId]
tvs1 HsWrapper -> HsWrapper -> HsWrapper
<.> [DFunId] -> HsWrapper
mkWpLams [DFunId]
ev_vars1)
([(Name, DFunId)]
tv_prs [(Name, DFunId)] -> [(Name, DFunId)] -> [(Name, DFunId)]
forall a. [a] -> [a] -> [a]
++ ((DFunId -> Name) -> [DFunId] -> [Name]
forall a b. (a -> b) -> [a] -> [b]
map DFunId -> Name
tyVarName [DFunId]
tvs [Name] -> [DFunId] -> [(Name, DFunId)]
forall a b. [a] -> [b] -> [(a, b)]
`zip` [DFunId]
tvs1))
([DFunId]
ev_vars [DFunId] -> [DFunId] -> [DFunId]
forall a. [a] -> [a] -> [a]
++ [DFunId]
ev_vars1)
Type
inner_ty }
| Bool
otherwise
= (HsWrapper, [(Name, DFunId)], [DFunId], Type)
-> TcM (HsWrapper, [(Name, DFunId)], [DFunId], Type)
forall a. a -> IOEnv (Env TcGblEnv TcLclEnv) a
forall (m :: * -> *) a. Monad m => a -> m a
return (HsWrapper
wrap, [(Name, DFunId)]
tv_prs, [DFunId]
ev_vars, (() :: Constraint) => TCvSubst -> Type -> Type
TCvSubst -> Type -> Type
substTy TCvSubst
subst Type
ty)
topInstantiate ::CtOrigin -> TcSigmaType -> TcM (HsWrapper, TcRhoType)
topInstantiate :: CtOrigin -> Type -> TcM (HsWrapper, Type)
topInstantiate CtOrigin
orig Type
sigma
| ([DFunId]
tvs, Type
body1) <- (ArgFlag -> Bool) -> Type -> ([DFunId], Type)
tcSplitSomeForAllTyVars ArgFlag -> Bool
isInvisibleArgFlag Type
sigma
, ([Type]
theta, Type
body2) <- Type -> ([Type], Type)
tcSplitPhiTy Type
body1
, Bool -> Bool
not ([DFunId] -> Bool
forall a. [a] -> Bool
forall (t :: * -> *) a. Foldable t => t a -> Bool
null [DFunId]
tvs Bool -> Bool -> Bool
&& [Type] -> Bool
forall a. [a] -> Bool
forall (t :: * -> *) a. Foldable t => t a -> Bool
null [Type]
theta)
= do { ([DFunId]
_, HsWrapper
wrap1, Type
body3) <- CtOrigin
-> [DFunId] -> [Type] -> Type -> TcM ([DFunId], HsWrapper, Type)
instantiateSigma CtOrigin
orig [DFunId]
tvs [Type]
theta Type
body2
; (HsWrapper
wrap2, Type
body4) <- CtOrigin -> Type -> TcM (HsWrapper, Type)
topInstantiate CtOrigin
orig Type
body3
; (HsWrapper, Type) -> TcM (HsWrapper, Type)
forall a. a -> IOEnv (Env TcGblEnv TcLclEnv) a
forall (m :: * -> *) a. Monad m => a -> m a
return (HsWrapper
wrap2 HsWrapper -> HsWrapper -> HsWrapper
<.> HsWrapper
wrap1, Type
body4) }
| Bool
otherwise = (HsWrapper, Type) -> TcM (HsWrapper, Type)
forall a. a -> IOEnv (Env TcGblEnv TcLclEnv) a
forall (m :: * -> *) a. Monad m => a -> m a
return (HsWrapper
idHsWrapper, Type
sigma)
instantiateSigma :: CtOrigin -> [TyVar] -> TcThetaType -> TcSigmaType
-> TcM ([TcTyVar], HsWrapper, TcSigmaType)
instantiateSigma :: CtOrigin
-> [DFunId] -> [Type] -> Type -> TcM ([DFunId], HsWrapper, Type)
instantiateSigma CtOrigin
orig [DFunId]
tvs [Type]
theta Type
body_ty
= do { (TCvSubst
subst, [DFunId]
inst_tvs) <- (TCvSubst
-> DFunId -> IOEnv (Env TcGblEnv TcLclEnv) (TCvSubst, DFunId))
-> TCvSubst -> [DFunId] -> TcM (TCvSubst, [DFunId])
forall (m :: * -> *) acc x y.
Monad m =>
(acc -> x -> m (acc, y)) -> acc -> [x] -> m (acc, [y])
mapAccumLM TCvSubst
-> DFunId -> IOEnv (Env TcGblEnv TcLclEnv) (TCvSubst, DFunId)
newMetaTyVarX TCvSubst
empty_subst [DFunId]
tvs
; let inst_theta :: [Type]
inst_theta = (() :: Constraint) => TCvSubst -> [Type] -> [Type]
TCvSubst -> [Type] -> [Type]
substTheta TCvSubst
subst [Type]
theta
inst_body :: Type
inst_body = (() :: Constraint) => TCvSubst -> Type -> Type
TCvSubst -> Type -> Type
substTy TCvSubst
subst Type
body_ty
inst_tv_tys :: [Type]
inst_tv_tys = [DFunId] -> [Type]
mkTyVarTys [DFunId]
inst_tvs
; HsWrapper
wrap <- CtOrigin -> [Type] -> [Type] -> TcM HsWrapper
instCall CtOrigin
orig [Type]
inst_tv_tys [Type]
inst_theta
; String -> SDoc -> TcRn ()
traceTc String
"Instantiating"
([SDoc] -> SDoc
vcat [ String -> SDoc
text String
"origin" SDoc -> SDoc -> SDoc
<+> CtOrigin -> SDoc
pprCtOrigin CtOrigin
orig
, String -> SDoc
text String
"tvs" SDoc -> SDoc -> SDoc
<+> [DFunId] -> SDoc
forall a. Outputable a => a -> SDoc
ppr [DFunId]
tvs
, String -> SDoc
text String
"theta" SDoc -> SDoc -> SDoc
<+> [Type] -> SDoc
forall a. Outputable a => a -> SDoc
ppr [Type]
theta
, String -> SDoc
text String
"type" SDoc -> SDoc -> SDoc
<+> Type -> SDoc
debugPprType Type
body_ty
, String -> SDoc
text String
"with" SDoc -> SDoc -> SDoc
<+> [SDoc] -> SDoc
vcat ((Type -> SDoc) -> [Type] -> [SDoc]
forall a b. (a -> b) -> [a] -> [b]
map Type -> SDoc
debugPprType [Type]
inst_tv_tys)
, String -> SDoc
text String
"theta:" SDoc -> SDoc -> SDoc
<+> [Type] -> SDoc
forall a. Outputable a => a -> SDoc
ppr [Type]
inst_theta ])
; ([DFunId], HsWrapper, Type) -> TcM ([DFunId], HsWrapper, Type)
forall a. a -> IOEnv (Env TcGblEnv TcLclEnv) a
forall (m :: * -> *) a. Monad m => a -> m a
return ([DFunId]
inst_tvs, HsWrapper
wrap, Type
inst_body) }
where
free_tvs :: VarSet
free_tvs = Type -> VarSet
tyCoVarsOfType Type
body_ty VarSet -> VarSet -> VarSet
`unionVarSet` [Type] -> VarSet
tyCoVarsOfTypes [Type]
theta
in_scope :: InScopeSet
in_scope = VarSet -> InScopeSet
mkInScopeSet (VarSet
free_tvs VarSet -> [DFunId] -> VarSet
`delVarSetList` [DFunId]
tvs)
empty_subst :: TCvSubst
empty_subst = InScopeSet -> TCvSubst
mkEmptyTCvSubst InScopeSet
in_scope
instTyVarsWith :: CtOrigin -> [TyVar] -> [TcType] -> TcM TCvSubst
instTyVarsWith :: CtOrigin -> [DFunId] -> [Type] -> TcM TCvSubst
instTyVarsWith CtOrigin
orig [DFunId]
tvs [Type]
tys
= TCvSubst -> [DFunId] -> [Type] -> TcM TCvSubst
go TCvSubst
emptyTCvSubst [DFunId]
tvs [Type]
tys
where
go :: TCvSubst -> [DFunId] -> [Type] -> TcM TCvSubst
go TCvSubst
subst [] []
= TCvSubst -> TcM TCvSubst
forall a. a -> IOEnv (Env TcGblEnv TcLclEnv) a
forall (m :: * -> *) a. Monad m => a -> m a
return TCvSubst
subst
go TCvSubst
subst (DFunId
tv:[DFunId]
tvs) (Type
ty:[Type]
tys)
| Type
tv_kind (() :: Constraint) => Type -> Type -> Bool
Type -> Type -> Bool
`tcEqType` Type
ty_kind
= TCvSubst -> [DFunId] -> [Type] -> TcM TCvSubst
go (TCvSubst -> DFunId -> Type -> TCvSubst
extendTvSubstAndInScope TCvSubst
subst DFunId
tv Type
ty) [DFunId]
tvs [Type]
tys
| Bool
otherwise
= do { Coercion
co <- CtOrigin -> TypeOrKind -> Role -> Type -> Type -> TcM Coercion
emitWantedEq CtOrigin
orig TypeOrKind
KindLevel Role
Nominal Type
ty_kind Type
tv_kind
; TCvSubst -> [DFunId] -> [Type] -> TcM TCvSubst
go (TCvSubst -> DFunId -> Type -> TCvSubst
extendTvSubstAndInScope TCvSubst
subst DFunId
tv (Type
ty Type -> Coercion -> Type
`mkCastTy` Coercion
co)) [DFunId]
tvs [Type]
tys }
where
tv_kind :: Type
tv_kind = (() :: Constraint) => TCvSubst -> Type -> Type
TCvSubst -> Type -> Type
substTy TCvSubst
subst (DFunId -> Type
tyVarKind DFunId
tv)
ty_kind :: Type
ty_kind = (() :: Constraint) => Type -> Type
Type -> Type
tcTypeKind Type
ty
go TCvSubst
_ [DFunId]
_ [Type]
_ = String -> SDoc -> TcM TCvSubst
forall a. HasCallStack => String -> SDoc -> a
pprPanic String
"instTysWith" ([DFunId] -> SDoc
forall a. Outputable a => a -> SDoc
ppr [DFunId]
tvs SDoc -> SDoc -> SDoc
$$ [Type] -> SDoc
forall a. Outputable a => a -> SDoc
ppr [Type]
tys)
instCall :: CtOrigin -> [TcType] -> TcThetaType -> TcM HsWrapper
instCall :: CtOrigin -> [Type] -> [Type] -> TcM HsWrapper
instCall CtOrigin
orig [Type]
tys [Type]
theta
= do { HsWrapper
dict_app <- CtOrigin -> [Type] -> TcM HsWrapper
instCallConstraints CtOrigin
orig [Type]
theta
; HsWrapper -> TcM HsWrapper
forall a. a -> IOEnv (Env TcGblEnv TcLclEnv) a
forall (m :: * -> *) a. Monad m => a -> m a
return (HsWrapper
dict_app HsWrapper -> HsWrapper -> HsWrapper
<.> [Type] -> HsWrapper
mkWpTyApps [Type]
tys) }
instCallConstraints :: CtOrigin -> TcThetaType -> TcM HsWrapper
instCallConstraints :: CtOrigin -> [Type] -> TcM HsWrapper
instCallConstraints CtOrigin
orig [Type]
preds
| [Type] -> Bool
forall a. [a] -> Bool
forall (t :: * -> *) a. Foldable t => t a -> Bool
null [Type]
preds
= HsWrapper -> TcM HsWrapper
forall a. a -> IOEnv (Env TcGblEnv TcLclEnv) a
forall (m :: * -> *) a. Monad m => a -> m a
return HsWrapper
idHsWrapper
| Bool
otherwise
= do { [EvTerm]
evs <- (Type -> IOEnv (Env TcGblEnv TcLclEnv) EvTerm)
-> [Type] -> IOEnv (Env TcGblEnv TcLclEnv) [EvTerm]
forall (t :: * -> *) (m :: * -> *) a b.
(Traversable t, Monad m) =>
(a -> m b) -> t a -> m (t b)
forall (m :: * -> *) a b. Monad m => (a -> m b) -> [a] -> m [b]
mapM Type -> IOEnv (Env TcGblEnv TcLclEnv) EvTerm
go [Type]
preds
; String -> SDoc -> TcRn ()
traceTc String
"instCallConstraints" ([EvTerm] -> SDoc
forall a. Outputable a => a -> SDoc
ppr [EvTerm]
evs)
; HsWrapper -> TcM HsWrapper
forall a. a -> IOEnv (Env TcGblEnv TcLclEnv) a
forall (m :: * -> *) a. Monad m => a -> m a
return ([EvTerm] -> HsWrapper
mkWpEvApps [EvTerm]
evs) }
where
go :: TcPredType -> TcM EvTerm
go :: Type -> IOEnv (Env TcGblEnv TcLclEnv) EvTerm
go Type
pred
| Just (Role
Nominal, Type
ty1, Type
ty2) <- Type -> Maybe (Role, Type, Type)
getEqPredTys_maybe Type
pred
= do { Coercion
co <- Maybe TypedThing -> Type -> Type -> TcM Coercion
unifyType Maybe TypedThing
forall a. Maybe a
Nothing Type
ty1 Type
ty2
; EvTerm -> IOEnv (Env TcGblEnv TcLclEnv) EvTerm
forall a. a -> IOEnv (Env TcGblEnv TcLclEnv) a
forall (m :: * -> *) a. Monad m => a -> m a
return (Coercion -> EvTerm
evCoercion Coercion
co) }
| Just (TyCon
tc, args :: [Type]
args@[Type
_, Type
_, Type
ty1, Type
ty2]) <- (() :: Constraint) => Type -> Maybe (TyCon, [Type])
Type -> Maybe (TyCon, [Type])
splitTyConApp_maybe Type
pred
, TyCon
tc TyCon -> Unique -> Bool
forall a. Uniquable a => a -> Unique -> Bool
`hasKey` Unique
heqTyConKey
= do { Coercion
co <- Maybe TypedThing -> Type -> Type -> TcM Coercion
unifyType Maybe TypedThing
forall a. Maybe a
Nothing Type
ty1 Type
ty2
; EvTerm -> IOEnv (Env TcGblEnv TcLclEnv) EvTerm
forall a. a -> IOEnv (Env TcGblEnv TcLclEnv) a
forall (m :: * -> *) a. Monad m => a -> m a
return (DFunId -> [Type] -> [EvExpr] -> EvTerm
evDFunApp (DataCon -> DFunId
dataConWrapId DataCon
heqDataCon) [Type]
args [Coercion -> EvExpr
forall b. Coercion -> Expr b
Coercion Coercion
co]) }
| Bool
otherwise
= CtOrigin -> Type -> IOEnv (Env TcGblEnv TcLclEnv) EvTerm
emitWanted CtOrigin
orig Type
pred
instDFunType :: DFunId -> [DFunInstType]
-> TcM ( [TcType]
, TcThetaType )
instDFunType :: DFunId -> [DFunInstType] -> TcM ([Type], [Type])
instDFunType DFunId
dfun_id [DFunInstType]
dfun_inst_tys
= do { (TCvSubst
subst, [Type]
inst_tys) <- TCvSubst -> [DFunId] -> [DFunInstType] -> TcM (TCvSubst, [Type])
go TCvSubst
empty_subst [DFunId]
dfun_tvs [DFunInstType]
dfun_inst_tys
; ([Type], [Type]) -> TcM ([Type], [Type])
forall a. a -> IOEnv (Env TcGblEnv TcLclEnv) a
forall (m :: * -> *) a. Monad m => a -> m a
return ([Type]
inst_tys, (() :: Constraint) => TCvSubst -> [Type] -> [Type]
TCvSubst -> [Type] -> [Type]
substTheta TCvSubst
subst [Type]
dfun_theta) }
where
dfun_ty :: Type
dfun_ty = DFunId -> Type
idType DFunId
dfun_id
([DFunId]
dfun_tvs, [Type]
dfun_theta, Type
_) = Type -> ([DFunId], [Type], Type)
tcSplitSigmaTy Type
dfun_ty
empty_subst :: TCvSubst
empty_subst = InScopeSet -> TCvSubst
mkEmptyTCvSubst (VarSet -> InScopeSet
mkInScopeSet (Type -> VarSet
tyCoVarsOfType Type
dfun_ty))
go :: TCvSubst -> [TyVar] -> [DFunInstType] -> TcM (TCvSubst, [TcType])
go :: TCvSubst -> [DFunId] -> [DFunInstType] -> TcM (TCvSubst, [Type])
go TCvSubst
subst [] [] = (TCvSubst, [Type]) -> TcM (TCvSubst, [Type])
forall a. a -> IOEnv (Env TcGblEnv TcLclEnv) a
forall (m :: * -> *) a. Monad m => a -> m a
return (TCvSubst
subst, [])
go TCvSubst
subst (DFunId
tv:[DFunId]
tvs) (Just Type
ty : [DFunInstType]
mb_tys)
= do { (TCvSubst
subst', [Type]
tys) <- TCvSubst -> [DFunId] -> [DFunInstType] -> TcM (TCvSubst, [Type])
go (TCvSubst -> DFunId -> Type -> TCvSubst
extendTvSubstAndInScope TCvSubst
subst DFunId
tv Type
ty)
[DFunId]
tvs
[DFunInstType]
mb_tys
; (TCvSubst, [Type]) -> TcM (TCvSubst, [Type])
forall a. a -> IOEnv (Env TcGblEnv TcLclEnv) a
forall (m :: * -> *) a. Monad m => a -> m a
return (TCvSubst
subst', Type
ty Type -> [Type] -> [Type]
forall a. a -> [a] -> [a]
: [Type]
tys) }
go TCvSubst
subst (DFunId
tv:[DFunId]
tvs) (DFunInstType
Nothing : [DFunInstType]
mb_tys)
= do { (TCvSubst
subst', DFunId
tv') <- TCvSubst
-> DFunId -> IOEnv (Env TcGblEnv TcLclEnv) (TCvSubst, DFunId)
newMetaTyVarX TCvSubst
subst DFunId
tv
; (TCvSubst
subst'', [Type]
tys) <- TCvSubst -> [DFunId] -> [DFunInstType] -> TcM (TCvSubst, [Type])
go TCvSubst
subst' [DFunId]
tvs [DFunInstType]
mb_tys
; (TCvSubst, [Type]) -> TcM (TCvSubst, [Type])
forall a. a -> IOEnv (Env TcGblEnv TcLclEnv) a
forall (m :: * -> *) a. Monad m => a -> m a
return (TCvSubst
subst'', DFunId -> Type
mkTyVarTy DFunId
tv' Type -> [Type] -> [Type]
forall a. a -> [a] -> [a]
: [Type]
tys) }
go TCvSubst
_ [DFunId]
_ [DFunInstType]
_ = String -> SDoc -> TcM (TCvSubst, [Type])
forall a. HasCallStack => String -> SDoc -> a
pprPanic String
"instDFunTypes" (DFunId -> SDoc
forall a. Outputable a => a -> SDoc
ppr DFunId
dfun_id SDoc -> SDoc -> SDoc
$$ [DFunInstType] -> SDoc
forall a. Outputable a => a -> SDoc
ppr [DFunInstType]
dfun_inst_tys)
instStupidTheta :: CtOrigin -> TcThetaType -> TcM ()
instStupidTheta :: CtOrigin -> [Type] -> TcRn ()
instStupidTheta CtOrigin
orig [Type]
theta
= do { HsWrapper
_co <- CtOrigin -> [Type] -> TcM HsWrapper
instCallConstraints CtOrigin
orig [Type]
theta
; () -> TcRn ()
forall a. a -> IOEnv (Env TcGblEnv TcLclEnv) a
forall (m :: * -> *) a. Monad m => a -> m a
return () }
tcInstInvisibleTyBinders :: TcType -> TcKind -> TcM (TcType, TcKind)
tcInstInvisibleTyBinders :: Type -> Type -> TcM (Type, Type)
tcInstInvisibleTyBinders Type
ty Type
kind
= do { ([Type]
extra_args, Type
kind') <- Arity -> Type -> TcM ([Type], Type)
tcInstInvisibleTyBindersN Arity
n_invis Type
kind
; (Type, Type) -> TcM (Type, Type)
forall a. a -> IOEnv (Env TcGblEnv TcLclEnv) a
forall (m :: * -> *) a. Monad m => a -> m a
return (Type -> [Type] -> Type
mkAppTys Type
ty [Type]
extra_args, Type
kind') }
where
n_invis :: Arity
n_invis = Type -> Arity
invisibleTyBndrCount Type
kind
tcInstInvisibleTyBindersN :: Int -> TcKind -> TcM ([TcType], TcKind)
tcInstInvisibleTyBindersN :: Arity -> Type -> TcM ([Type], Type)
tcInstInvisibleTyBindersN Arity
0 Type
kind
= ([Type], Type) -> TcM ([Type], Type)
forall a. a -> IOEnv (Env TcGblEnv TcLclEnv) a
forall (m :: * -> *) a. Monad m => a -> m a
return ([], Type
kind)
tcInstInvisibleTyBindersN Arity
n Type
ty
= Arity -> TCvSubst -> Type -> TcM ([Type], Type)
forall {t}.
(Ord t, Num t) =>
t -> TCvSubst -> Type -> TcM ([Type], Type)
go Arity
n TCvSubst
empty_subst Type
ty
where
empty_subst :: TCvSubst
empty_subst = InScopeSet -> TCvSubst
mkEmptyTCvSubst (VarSet -> InScopeSet
mkInScopeSet (Type -> VarSet
tyCoVarsOfType Type
ty))
go :: t -> TCvSubst -> Type -> TcM ([Type], Type)
go t
n TCvSubst
subst Type
kind
| t
n t -> t -> Bool
forall a. Ord a => a -> a -> Bool
> t
0
, Just (TyBinder
bndr, Type
body) <- Type -> Maybe (TyBinder, Type)
tcSplitPiTy_maybe Type
kind
, TyBinder -> Bool
isInvisibleBinder TyBinder
bndr
= do { (TCvSubst
subst', Type
arg) <- TCvSubst -> TyBinder -> TcM (TCvSubst, Type)
tcInstInvisibleTyBinder TCvSubst
subst TyBinder
bndr
; ([Type]
args, Type
inner_ty) <- t -> TCvSubst -> Type -> TcM ([Type], Type)
go (t
nt -> t -> t
forall a. Num a => a -> a -> a
-t
1) TCvSubst
subst' Type
body
; ([Type], Type) -> TcM ([Type], Type)
forall a. a -> IOEnv (Env TcGblEnv TcLclEnv) a
forall (m :: * -> *) a. Monad m => a -> m a
return (Type
argType -> [Type] -> [Type]
forall a. a -> [a] -> [a]
:[Type]
args, Type
inner_ty) }
| Bool
otherwise
= ([Type], Type) -> TcM ([Type], Type)
forall a. a -> IOEnv (Env TcGblEnv TcLclEnv) a
forall (m :: * -> *) a. Monad m => a -> m a
return ([], (() :: Constraint) => TCvSubst -> Type -> Type
TCvSubst -> Type -> Type
substTy TCvSubst
subst Type
kind)
tcInstInvisibleTyBinder :: TCvSubst -> TyBinder -> TcM (TCvSubst, TcType)
tcInstInvisibleTyBinder :: TCvSubst -> TyBinder -> TcM (TCvSubst, Type)
tcInstInvisibleTyBinder TCvSubst
subst (Named (Bndr DFunId
tv ArgFlag
_))
= do { (TCvSubst
subst', DFunId
tv') <- TCvSubst
-> DFunId -> IOEnv (Env TcGblEnv TcLclEnv) (TCvSubst, DFunId)
newMetaTyVarX TCvSubst
subst DFunId
tv
; (TCvSubst, Type) -> TcM (TCvSubst, Type)
forall a. a -> IOEnv (Env TcGblEnv TcLclEnv) a
forall (m :: * -> *) a. Monad m => a -> m a
return (TCvSubst
subst', DFunId -> Type
mkTyVarTy DFunId
tv') }
tcInstInvisibleTyBinder TCvSubst
subst (Anon AnonArgFlag
af Scaled Type
ty)
| Just (Coercion -> TcM Type
mk, Type
k1, Type
k2) <- Type -> Maybe (Coercion -> TcM Type, Type, Type)
get_eq_tys_maybe ((() :: Constraint) => TCvSubst -> Type -> Type
TCvSubst -> Type -> Type
substTy TCvSubst
subst (Scaled Type -> Type
forall a. Scaled a -> a
scaledThing Scaled Type
ty))
= Bool -> TcM (TCvSubst, Type) -> TcM (TCvSubst, Type)
forall a. HasCallStack => Bool -> a -> a
assert (AnonArgFlag
af AnonArgFlag -> AnonArgFlag -> Bool
forall a. Eq a => a -> a -> Bool
== AnonArgFlag
InvisArg) (TcM (TCvSubst, Type) -> TcM (TCvSubst, Type))
-> TcM (TCvSubst, Type) -> TcM (TCvSubst, Type)
forall a b. (a -> b) -> a -> b
$
do { Coercion
co <- Maybe TypedThing -> Type -> Type -> TcM Coercion
unifyKind Maybe TypedThing
forall a. Maybe a
Nothing Type
k1 Type
k2
; Type
arg' <- Coercion -> TcM Type
mk Coercion
co
; (TCvSubst, Type) -> TcM (TCvSubst, Type)
forall a. a -> IOEnv (Env TcGblEnv TcLclEnv) a
forall (m :: * -> *) a. Monad m => a -> m a
return (TCvSubst
subst, Type
arg') }
| Bool
otherwise
= String -> SDoc -> TcM (TCvSubst, Type)
forall a. HasCallStack => String -> SDoc -> a
pprPanic String
"tcInvisibleTyBinder" (Scaled Type -> SDoc
forall a. Outputable a => a -> SDoc
ppr Scaled Type
ty)
get_eq_tys_maybe :: Type
-> Maybe ( Coercion -> TcM Type
, Type
, Type
)
get_eq_tys_maybe :: Type -> Maybe (Coercion -> TcM Type, Type, Type)
get_eq_tys_maybe Type
ty
| Just (TyCon
tc, [Type
_, Type
_, Type
k1, Type
k2]) <- (() :: Constraint) => Type -> Maybe (TyCon, [Type])
Type -> Maybe (TyCon, [Type])
splitTyConApp_maybe Type
ty
, TyCon
tc TyCon -> Unique -> Bool
forall a. Uniquable a => a -> Unique -> Bool
`hasKey` Unique
heqTyConKey
= (Coercion -> TcM Type, Type, Type)
-> Maybe (Coercion -> TcM Type, Type, Type)
forall a. a -> Maybe a
Just (\Coercion
co -> Coercion -> Type -> Type -> TcM Type
mkHEqBoxTy Coercion
co Type
k1 Type
k2, Type
k1, Type
k2)
| Just (TyCon
tc, [Type
_, Type
k1, Type
k2]) <- (() :: Constraint) => Type -> Maybe (TyCon, [Type])
Type -> Maybe (TyCon, [Type])
splitTyConApp_maybe Type
ty
, TyCon
tc TyCon -> Unique -> Bool
forall a. Uniquable a => a -> Unique -> Bool
`hasKey` Unique
eqTyConKey
= (Coercion -> TcM Type, Type, Type)
-> Maybe (Coercion -> TcM Type, Type, Type)
forall a. a -> Maybe a
Just (\Coercion
co -> Coercion -> Type -> Type -> TcM Type
mkEqBoxTy Coercion
co Type
k1 Type
k2, Type
k1, Type
k2)
| Bool
otherwise
= Maybe (Coercion -> TcM Type, Type, Type)
forall a. Maybe a
Nothing
mkHEqBoxTy :: TcCoercion -> Type -> Type -> TcM Type
mkHEqBoxTy :: Coercion -> Type -> Type -> TcM Type
mkHEqBoxTy Coercion
co Type
ty1 Type
ty2
= Type -> TcM Type
forall a. a -> IOEnv (Env TcGblEnv TcLclEnv) a
forall (m :: * -> *) a. Monad m => a -> m a
return (Type -> TcM Type) -> Type -> TcM Type
forall a b. (a -> b) -> a -> b
$
TyCon -> [Type] -> Type
mkTyConApp (DataCon -> TyCon
promoteDataCon DataCon
heqDataCon) [Type
k1, Type
k2, Type
ty1, Type
ty2, Coercion -> Type
mkCoercionTy Coercion
co]
where k1 :: Type
k1 = (() :: Constraint) => Type -> Type
Type -> Type
tcTypeKind Type
ty1
k2 :: Type
k2 = (() :: Constraint) => Type -> Type
Type -> Type
tcTypeKind Type
ty2
mkEqBoxTy :: TcCoercion -> Type -> Type -> TcM Type
mkEqBoxTy :: Coercion -> Type -> Type -> TcM Type
mkEqBoxTy Coercion
co Type
ty1 Type
ty2
= Type -> TcM Type
forall a. a -> IOEnv (Env TcGblEnv TcLclEnv) a
forall (m :: * -> *) a. Monad m => a -> m a
return (Type -> TcM Type) -> Type -> TcM Type
forall a b. (a -> b) -> a -> b
$
TyCon -> [Type] -> Type
mkTyConApp (DataCon -> TyCon
promoteDataCon DataCon
eqDataCon) [Type
k, Type
ty1, Type
ty2, Coercion -> Type
mkCoercionTy Coercion
co]
where k :: Type
k = (() :: Constraint) => Type -> Type
Type -> Type
tcTypeKind Type
ty1
tcInstType :: ([TyVar] -> TcM (TCvSubst, [TcTyVar]))
-> Id
-> TcM ([(Name, TcTyVar)], TcThetaType, TcType)
tcInstType :: ([DFunId] -> TcM (TCvSubst, [DFunId]))
-> DFunId -> TcM ([(Name, DFunId)], [Type], Type)
tcInstType [DFunId] -> TcM (TCvSubst, [DFunId])
inst_tyvars DFunId
id
| [DFunId] -> Bool
forall a. [a] -> Bool
forall (t :: * -> *) a. Foldable t => t a -> Bool
null [DFunId]
tyvars
= ([(Name, DFunId)], [Type], Type)
-> TcM ([(Name, DFunId)], [Type], Type)
forall a. a -> IOEnv (Env TcGblEnv TcLclEnv) a
forall (m :: * -> *) a. Monad m => a -> m a
return ([], [Type]
theta, Type
tau)
| Bool
otherwise
= do { (TCvSubst
subst, [DFunId]
tyvars') <- [DFunId] -> TcM (TCvSubst, [DFunId])
inst_tyvars [DFunId]
tyvars
; let tv_prs :: [(Name, DFunId)]
tv_prs = (DFunId -> Name) -> [DFunId] -> [Name]
forall a b. (a -> b) -> [a] -> [b]
map DFunId -> Name
tyVarName [DFunId]
tyvars [Name] -> [DFunId] -> [(Name, DFunId)]
forall a b. [a] -> [b] -> [(a, b)]
`zip` [DFunId]
tyvars'
subst' :: TCvSubst
subst' = TCvSubst -> VarSet -> TCvSubst
extendTCvInScopeSet TCvSubst
subst (Type -> VarSet
tyCoVarsOfType Type
rho)
; ([(Name, DFunId)], [Type], Type)
-> TcM ([(Name, DFunId)], [Type], Type)
forall a. a -> IOEnv (Env TcGblEnv TcLclEnv) a
forall (m :: * -> *) a. Monad m => a -> m a
return ([(Name, DFunId)]
tv_prs, (() :: Constraint) => TCvSubst -> [Type] -> [Type]
TCvSubst -> [Type] -> [Type]
substTheta TCvSubst
subst' [Type]
theta, (() :: Constraint) => TCvSubst -> Type -> Type
TCvSubst -> Type -> Type
substTy TCvSubst
subst' Type
tau) }
where
([DFunId]
tyvars, Type
rho) = Type -> ([DFunId], Type)
tcSplitForAllInvisTyVars (DFunId -> Type
idType DFunId
id)
([Type]
theta, Type
tau) = Type -> ([Type], Type)
tcSplitPhiTy Type
rho
tcInstTypeBndrs :: Id -> TcM ([(Name, InvisTVBinder)], TcThetaType, TcType)
tcInstTypeBndrs :: DFunId -> TcM ([(Name, InvisTVBinder)], [Type], Type)
tcInstTypeBndrs DFunId
id
| [InvisTVBinder] -> Bool
forall a. [a] -> Bool
forall (t :: * -> *) a. Foldable t => t a -> Bool
null [InvisTVBinder]
tyvars
= ([(Name, InvisTVBinder)], [Type], Type)
-> TcM ([(Name, InvisTVBinder)], [Type], Type)
forall a. a -> IOEnv (Env TcGblEnv TcLclEnv) a
forall (m :: * -> *) a. Monad m => a -> m a
return ([], [Type]
theta, Type
tau)
| Bool
otherwise
= do { (TCvSubst
subst, [InvisTVBinder]
tyvars') <- (TCvSubst
-> InvisTVBinder
-> IOEnv (Env TcGblEnv TcLclEnv) (TCvSubst, InvisTVBinder))
-> TCvSubst
-> [InvisTVBinder]
-> IOEnv (Env TcGblEnv TcLclEnv) (TCvSubst, [InvisTVBinder])
forall (m :: * -> *) acc x y.
Monad m =>
(acc -> x -> m (acc, y)) -> acc -> [x] -> m (acc, [y])
mapAccumLM TCvSubst
-> InvisTVBinder
-> IOEnv (Env TcGblEnv TcLclEnv) (TCvSubst, InvisTVBinder)
inst_invis_bndr TCvSubst
emptyTCvSubst [InvisTVBinder]
tyvars
; let tv_prs :: [(Name, InvisTVBinder)]
tv_prs = (InvisTVBinder -> Name) -> [InvisTVBinder] -> [Name]
forall a b. (a -> b) -> [a] -> [b]
map (DFunId -> Name
tyVarName (DFunId -> Name)
-> (InvisTVBinder -> DFunId) -> InvisTVBinder -> Name
forall b c a. (b -> c) -> (a -> b) -> a -> c
. InvisTVBinder -> DFunId
forall tv argf. VarBndr tv argf -> tv
binderVar) [InvisTVBinder]
tyvars [Name] -> [InvisTVBinder] -> [(Name, InvisTVBinder)]
forall a b. [a] -> [b] -> [(a, b)]
`zip` [InvisTVBinder]
tyvars'
subst' :: TCvSubst
subst' = TCvSubst -> VarSet -> TCvSubst
extendTCvInScopeSet TCvSubst
subst (Type -> VarSet
tyCoVarsOfType Type
rho)
; ([(Name, InvisTVBinder)], [Type], Type)
-> TcM ([(Name, InvisTVBinder)], [Type], Type)
forall a. a -> IOEnv (Env TcGblEnv TcLclEnv) a
forall (m :: * -> *) a. Monad m => a -> m a
return ([(Name, InvisTVBinder)]
tv_prs, (() :: Constraint) => TCvSubst -> [Type] -> [Type]
TCvSubst -> [Type] -> [Type]
substTheta TCvSubst
subst' [Type]
theta, (() :: Constraint) => TCvSubst -> Type -> Type
TCvSubst -> Type -> Type
substTy TCvSubst
subst' Type
tau) }
where
([InvisTVBinder]
tyvars, Type
rho) = Type -> ([InvisTVBinder], Type)
splitForAllInvisTVBinders (DFunId -> Type
idType DFunId
id)
([Type]
theta, Type
tau) = Type -> ([Type], Type)
tcSplitPhiTy Type
rho
inst_invis_bndr :: TCvSubst -> InvisTVBinder
-> TcM (TCvSubst, InvisTVBinder)
inst_invis_bndr :: TCvSubst
-> InvisTVBinder
-> IOEnv (Env TcGblEnv TcLclEnv) (TCvSubst, InvisTVBinder)
inst_invis_bndr TCvSubst
subst (Bndr DFunId
tv Specificity
spec)
= do { (TCvSubst
subst', DFunId
tv') <- TCvSubst
-> DFunId -> IOEnv (Env TcGblEnv TcLclEnv) (TCvSubst, DFunId)
newMetaTyVarTyVarX TCvSubst
subst DFunId
tv
; (TCvSubst, InvisTVBinder)
-> IOEnv (Env TcGblEnv TcLclEnv) (TCvSubst, InvisTVBinder)
forall a. a -> IOEnv (Env TcGblEnv TcLclEnv) a
forall (m :: * -> *) a. Monad m => a -> m a
return (TCvSubst
subst', DFunId -> Specificity -> InvisTVBinder
forall var argf. var -> argf -> VarBndr var argf
Bndr DFunId
tv' Specificity
spec) }
tcSkolDFunType :: SkolemInfo -> DFunId -> TcM ([TcTyVar], TcThetaType, TcType)
tcSkolDFunType :: SkolemInfo -> DFunId -> TcM ([DFunId], [Type], Type)
tcSkolDFunType SkolemInfo
skol_info DFunId
dfun
= do { ([(Name, DFunId)]
tv_prs, [Type]
theta, Type
tau) <- ([DFunId] -> TcM (TCvSubst, [DFunId]))
-> DFunId -> TcM ([(Name, DFunId)], [Type], Type)
tcInstType (SkolemInfo -> [DFunId] -> TcM (TCvSubst, [DFunId])
tcInstSuperSkolTyVars SkolemInfo
skol_info) DFunId
dfun
; ([DFunId], [Type], Type) -> TcM ([DFunId], [Type], Type)
forall a. a -> IOEnv (Env TcGblEnv TcLclEnv) a
forall (m :: * -> *) a. Monad m => a -> m a
return (((Name, DFunId) -> DFunId) -> [(Name, DFunId)] -> [DFunId]
forall a b. (a -> b) -> [a] -> [b]
map (Name, DFunId) -> DFunId
forall a b. (a, b) -> b
snd [(Name, DFunId)]
tv_prs, [Type]
theta, Type
tau) }
tcSuperSkolTyVars :: TcLevel -> SkolemInfo -> [TyVar] -> (TCvSubst, [TcTyVar])
tcSuperSkolTyVars :: TcLevel -> SkolemInfo -> [DFunId] -> (TCvSubst, [DFunId])
tcSuperSkolTyVars TcLevel
tc_lvl SkolemInfo
skol_info = (TCvSubst -> DFunId -> (TCvSubst, DFunId))
-> TCvSubst -> [DFunId] -> (TCvSubst, [DFunId])
forall (t :: * -> *) s a b.
Traversable t =>
(s -> a -> (s, b)) -> s -> t a -> (s, t b)
mapAccumL TCvSubst -> DFunId -> (TCvSubst, DFunId)
do_one TCvSubst
emptyTCvSubst
where
details :: TcTyVarDetails
details = SkolemInfo -> TcLevel -> Bool -> TcTyVarDetails
SkolemTv SkolemInfo
skol_info (TcLevel -> TcLevel
pushTcLevel TcLevel
tc_lvl)
Bool
True
do_one :: TCvSubst -> DFunId -> (TCvSubst, DFunId)
do_one TCvSubst
subst DFunId
tv = (TCvSubst -> DFunId -> DFunId -> TCvSubst
extendTvSubstWithClone TCvSubst
subst DFunId
tv DFunId
new_tv, DFunId
new_tv)
where
kind :: Type
kind = TCvSubst -> Type -> Type
substTyUnchecked TCvSubst
subst (DFunId -> Type
tyVarKind DFunId
tv)
new_tv :: DFunId
new_tv = Name -> Type -> TcTyVarDetails -> DFunId
mkTcTyVar (DFunId -> Name
tyVarName DFunId
tv) Type
kind TcTyVarDetails
details
tcInstSkolTyVars :: SkolemInfo -> [TyVar] -> TcM (TCvSubst, [TcTyVar])
tcInstSkolTyVars :: SkolemInfo -> [DFunId] -> TcM (TCvSubst, [DFunId])
tcInstSkolTyVars SkolemInfo
skol_info = SkolemInfo -> TCvSubst -> [DFunId] -> TcM (TCvSubst, [DFunId])
tcInstSkolTyVarsX SkolemInfo
skol_info TCvSubst
emptyTCvSubst
tcInstSkolTyVarsX :: SkolemInfo -> TCvSubst -> [TyVar] -> TcM (TCvSubst, [TcTyVar])
tcInstSkolTyVarsX :: SkolemInfo -> TCvSubst -> [DFunId] -> TcM (TCvSubst, [DFunId])
tcInstSkolTyVarsX SkolemInfo
skol_info = SkolemInfo
-> Bool -> TCvSubst -> [DFunId] -> TcM (TCvSubst, [DFunId])
tcInstSkolTyVarsPushLevel SkolemInfo
skol_info Bool
False
tcInstSuperSkolTyVars :: SkolemInfo -> [TyVar] -> TcM (TCvSubst, [TcTyVar])
tcInstSuperSkolTyVars :: SkolemInfo -> [DFunId] -> TcM (TCvSubst, [DFunId])
tcInstSuperSkolTyVars SkolemInfo
skol_info = SkolemInfo -> TCvSubst -> [DFunId] -> TcM (TCvSubst, [DFunId])
tcInstSuperSkolTyVarsX SkolemInfo
skol_info TCvSubst
emptyTCvSubst
tcInstSuperSkolTyVarsX :: SkolemInfo -> TCvSubst -> [TyVar] -> TcM (TCvSubst, [TcTyVar])
tcInstSuperSkolTyVarsX :: SkolemInfo -> TCvSubst -> [DFunId] -> TcM (TCvSubst, [DFunId])
tcInstSuperSkolTyVarsX SkolemInfo
skol_info TCvSubst
subst = SkolemInfo
-> Bool -> TCvSubst -> [DFunId] -> TcM (TCvSubst, [DFunId])
tcInstSkolTyVarsPushLevel SkolemInfo
skol_info Bool
True TCvSubst
subst
tcInstSkolTyVarsPushLevel :: SkolemInfo -> Bool
-> TCvSubst -> [TyVar]
-> TcM (TCvSubst, [TcTyVar])
tcInstSkolTyVarsPushLevel :: SkolemInfo
-> Bool -> TCvSubst -> [DFunId] -> TcM (TCvSubst, [DFunId])
tcInstSkolTyVarsPushLevel SkolemInfo
skol_info Bool
overlappable TCvSubst
subst [DFunId]
tvs
= do { TcLevel
tc_lvl <- TcM TcLevel
getTcLevel
; let !pushed_lvl :: TcLevel
pushed_lvl = TcLevel -> TcLevel
pushTcLevel TcLevel
tc_lvl
; SkolemInfo
-> TcLevel
-> Bool
-> TCvSubst
-> [DFunId]
-> TcM (TCvSubst, [DFunId])
tcInstSkolTyVarsAt SkolemInfo
skol_info TcLevel
pushed_lvl Bool
overlappable TCvSubst
subst [DFunId]
tvs }
tcInstSkolTyVarsAt :: SkolemInfo -> TcLevel -> Bool
-> TCvSubst -> [TyVar]
-> TcM (TCvSubst, [TcTyVar])
tcInstSkolTyVarsAt :: SkolemInfo
-> TcLevel
-> Bool
-> TCvSubst
-> [DFunId]
-> TcM (TCvSubst, [DFunId])
tcInstSkolTyVarsAt SkolemInfo
skol_info TcLevel
lvl Bool
overlappable TCvSubst
subst [DFunId]
tvs
= (Name -> Type -> DFunId)
-> TCvSubst -> [DFunId] -> TcM (TCvSubst, [DFunId])
freshenTyCoVarsX Name -> Type -> DFunId
new_skol_tv TCvSubst
subst [DFunId]
tvs
where
sk_details :: TcTyVarDetails
sk_details = SkolemInfo -> TcLevel -> Bool -> TcTyVarDetails
SkolemTv SkolemInfo
skol_info TcLevel
lvl Bool
overlappable
new_skol_tv :: Name -> Type -> DFunId
new_skol_tv Name
name Type
kind = Name -> Type -> TcTyVarDetails -> DFunId
mkTcTyVar Name
name Type
kind TcTyVarDetails
sk_details
tcSkolemiseInvisibleBndrs :: SkolemInfoAnon -> Type -> TcM ([TcTyVar], TcType)
tcSkolemiseInvisibleBndrs :: SkolemInfoAnon -> Type -> TcM ([DFunId], Type)
tcSkolemiseInvisibleBndrs SkolemInfoAnon
skol_info Type
ty
= do { let ([DFunId]
tvs, Type
body_ty) = Type -> ([DFunId], Type)
tcSplitForAllInvisTyVars Type
ty
; TcLevel
lvl <- TcM TcLevel
getTcLevel
; SkolemInfo
skol_info <- SkolemInfoAnon -> IOEnv (Env TcGblEnv TcLclEnv) SkolemInfo
forall (m :: * -> *). MonadIO m => SkolemInfoAnon -> m SkolemInfo
mkSkolemInfo SkolemInfoAnon
skol_info
; let details :: TcTyVarDetails
details = SkolemInfo -> TcLevel -> Bool -> TcTyVarDetails
SkolemTv SkolemInfo
skol_info TcLevel
lvl Bool
False
mk_skol_tv :: Name -> Type -> TcM DFunId
mk_skol_tv Name
name Type
kind = DFunId -> TcM DFunId
forall a. a -> IOEnv (Env TcGblEnv TcLclEnv) a
forall (m :: * -> *) a. Monad m => a -> m a
return (Name -> Type -> TcTyVarDetails -> DFunId
mkTcTyVar Name
name Type
kind TcTyVarDetails
details)
; (TCvSubst
subst, [DFunId]
tvs') <- (Name -> Type -> TcM DFunId)
-> TCvSubst -> [DFunId] -> TcM (TCvSubst, [DFunId])
instantiateTyVarsX Name -> Type -> TcM DFunId
mk_skol_tv TCvSubst
emptyTCvSubst [DFunId]
tvs
; ([DFunId], Type) -> TcM ([DFunId], Type)
forall a. a -> IOEnv (Env TcGblEnv TcLclEnv) a
forall (m :: * -> *) a. Monad m => a -> m a
return ([DFunId]
tvs', (() :: Constraint) => TCvSubst -> Type -> Type
TCvSubst -> Type -> Type
substTy TCvSubst
subst Type
body_ty) }
instantiateTyVarsX :: (Name -> Kind -> TcM TcTyVar)
-> TCvSubst -> [TyVar]
-> TcM (TCvSubst, [TcTyVar])
instantiateTyVarsX :: (Name -> Type -> TcM DFunId)
-> TCvSubst -> [DFunId] -> TcM (TCvSubst, [DFunId])
instantiateTyVarsX Name -> Type -> TcM DFunId
mk_tv TCvSubst
subst [DFunId]
tvs
= case [DFunId]
tvs of
[] -> (TCvSubst, [DFunId]) -> TcM (TCvSubst, [DFunId])
forall a. a -> IOEnv (Env TcGblEnv TcLclEnv) a
forall (m :: * -> *) a. Monad m => a -> m a
return (TCvSubst
subst, [])
(DFunId
tv:[DFunId]
tvs) -> do { let kind1 :: Type
kind1 = TCvSubst -> Type -> Type
substTyUnchecked TCvSubst
subst (DFunId -> Type
tyVarKind DFunId
tv)
; DFunId
tv' <- Name -> Type -> TcM DFunId
mk_tv (DFunId -> Name
tyVarName DFunId
tv) Type
kind1
; let subst1 :: TCvSubst
subst1 = TCvSubst -> DFunId -> DFunId -> TCvSubst
extendTCvSubstWithClone TCvSubst
subst DFunId
tv DFunId
tv'
; (TCvSubst
subst', [DFunId]
tvs') <- (Name -> Type -> TcM DFunId)
-> TCvSubst -> [DFunId] -> TcM (TCvSubst, [DFunId])
instantiateTyVarsX Name -> Type -> TcM DFunId
mk_tv TCvSubst
subst1 [DFunId]
tvs
; (TCvSubst, [DFunId]) -> TcM (TCvSubst, [DFunId])
forall a. a -> IOEnv (Env TcGblEnv TcLclEnv) a
forall (m :: * -> *) a. Monad m => a -> m a
return (TCvSubst
subst', DFunId
tv'DFunId -> [DFunId] -> [DFunId]
forall a. a -> [a] -> [a]
:[DFunId]
tvs') }
freshenTyVarBndrs :: [TyVar] -> TcM (TCvSubst, [TyVar])
freshenTyVarBndrs :: [DFunId] -> TcM (TCvSubst, [DFunId])
freshenTyVarBndrs = (Name -> Type -> DFunId) -> [DFunId] -> TcM (TCvSubst, [DFunId])
freshenTyCoVars Name -> Type -> DFunId
mkTyVar
freshenCoVarBndrsX :: TCvSubst -> [CoVar] -> TcM (TCvSubst, [CoVar])
freshenCoVarBndrsX :: TCvSubst -> [DFunId] -> TcM (TCvSubst, [DFunId])
freshenCoVarBndrsX TCvSubst
subst = (Name -> Type -> DFunId)
-> TCvSubst -> [DFunId] -> TcM (TCvSubst, [DFunId])
freshenTyCoVarsX Name -> Type -> DFunId
mkCoVar TCvSubst
subst
freshenTyCoVars :: (Name -> Kind -> TyCoVar)
-> [TyVar] -> TcM (TCvSubst, [TyCoVar])
freshenTyCoVars :: (Name -> Type -> DFunId) -> [DFunId] -> TcM (TCvSubst, [DFunId])
freshenTyCoVars Name -> Type -> DFunId
mk_tcv = (Name -> Type -> DFunId)
-> TCvSubst -> [DFunId] -> TcM (TCvSubst, [DFunId])
freshenTyCoVarsX Name -> Type -> DFunId
mk_tcv TCvSubst
emptyTCvSubst
freshenTyCoVarsX :: (Name -> Kind -> TyCoVar)
-> TCvSubst -> [TyCoVar]
-> TcM (TCvSubst, [TyCoVar])
freshenTyCoVarsX :: (Name -> Type -> DFunId)
-> TCvSubst -> [DFunId] -> TcM (TCvSubst, [DFunId])
freshenTyCoVarsX Name -> Type -> DFunId
mk_tcv
= (Name -> Type -> TcM DFunId)
-> TCvSubst -> [DFunId] -> TcM (TCvSubst, [DFunId])
instantiateTyVarsX Name -> Type -> TcM DFunId
freshen_tcv
where
freshen_tcv :: Name -> Kind -> TcM TcTyVar
freshen_tcv :: Name -> Type -> TcM DFunId
freshen_tcv Name
name Type
kind
= do { SrcSpan
loc <- TcRn SrcSpan
getSrcSpanM
; Unique
uniq <- TcRnIf TcGblEnv TcLclEnv Unique
forall gbl lcl. TcRnIf gbl lcl Unique
newUnique
; let !occ_name :: OccName
occ_name = Name -> OccName
forall a. NamedThing a => a -> OccName
getOccName Name
name
new_name :: Name
new_name = Unique -> OccName -> SrcSpan -> Name
mkInternalName Unique
uniq OccName
occ_name SrcSpan
loc
; DFunId -> TcM DFunId
forall a. a -> IOEnv (Env TcGblEnv TcLclEnv) a
forall (m :: * -> *) a. Monad m => a -> m a
return (Name -> Type -> DFunId
mk_tcv Name
new_name Type
kind) }
newOverloadedLit :: HsOverLit GhcRn
-> ExpRhoType
-> TcM (HsOverLit GhcTc)
newOverloadedLit :: HsOverLit GhcRn -> ExpRhoType -> TcM (HsOverLit GhcTc)
newOverloadedLit HsOverLit GhcRn
lit ExpRhoType
res_ty
= do { Maybe (HsOverLit GhcTc)
mb_lit' <- HsOverLit GhcRn -> ExpRhoType -> TcM (Maybe (HsOverLit GhcTc))
tcShortCutLit HsOverLit GhcRn
lit ExpRhoType
res_ty
; case Maybe (HsOverLit GhcTc)
mb_lit' of
Just HsOverLit GhcTc
lit' -> HsOverLit GhcTc -> TcM (HsOverLit GhcTc)
forall a. a -> IOEnv (Env TcGblEnv TcLclEnv) a
forall (m :: * -> *) a. Monad m => a -> m a
return HsOverLit GhcTc
lit'
Maybe (HsOverLit GhcTc)
Nothing -> HsOverLit GhcRn -> ExpRhoType -> TcM (HsOverLit GhcTc)
newNonTrivialOverloadedLit HsOverLit GhcRn
lit ExpRhoType
res_ty }
newNonTrivialOverloadedLit :: HsOverLit GhcRn
-> ExpRhoType
-> TcM (HsOverLit GhcTc)
newNonTrivialOverloadedLit :: HsOverLit GhcRn -> ExpRhoType -> TcM (HsOverLit GhcTc)
newNonTrivialOverloadedLit
lit :: HsOverLit GhcRn
lit@(OverLit { ol_val :: forall p. HsOverLit p -> OverLitVal
ol_val = OverLitVal
val, ol_ext :: forall p. HsOverLit p -> XOverLit p
ol_ext = OverLitRn Bool
rebindable (L SrcSpanAnnN
_ Name
meth_name) })
ExpRhoType
res_ty
= do { HsLit GhcTc
hs_lit <- OverLitVal -> TcM (HsLit GhcTc)
mkOverLit OverLitVal
val
; let lit_ty :: Type
lit_ty = HsLit GhcTc -> Type
forall (p :: Pass). HsLit (GhcPass p) -> Type
hsLitType HsLit GhcTc
hs_lit
; (()
_, SyntaxExprTc
fi') <- CtOrigin
-> SyntaxExprRn
-> [SyntaxOpType]
-> ExpRhoType
-> ([Type] -> [Type] -> TcRn ())
-> TcM ((), SyntaxExprTc)
forall a.
CtOrigin
-> SyntaxExprRn
-> [SyntaxOpType]
-> ExpRhoType
-> ([Type] -> [Type] -> TcM a)
-> TcM (a, SyntaxExprTc)
tcSyntaxOp CtOrigin
orig (Name -> SyntaxExprRn
mkRnSyntaxExpr Name
meth_name)
[Type -> SyntaxOpType
synKnownType Type
lit_ty] ExpRhoType
res_ty (([Type] -> [Type] -> TcRn ()) -> TcM ((), SyntaxExprTc))
-> ([Type] -> [Type] -> TcRn ()) -> TcM ((), SyntaxExprTc)
forall a b. (a -> b) -> a -> b
$
\[Type]
_ [Type]
_ -> () -> TcRn ()
forall a. a -> IOEnv (Env TcGblEnv TcLclEnv) a
forall (m :: * -> *) a. Monad m => a -> m a
return ()
; let L SrcSpanAnnA
_ HsExpr GhcTc
witness = SyntaxExprTc -> [LHsExpr GhcTc] -> LHsExpr GhcTc
nlHsSyntaxApps SyntaxExprTc
fi' [HsLit GhcTc -> LHsExpr GhcTc
forall (p :: Pass). HsLit (GhcPass p) -> LHsExpr (GhcPass p)
nlHsLit HsLit GhcTc
hs_lit]
; Type
res_ty <- ExpRhoType -> TcM Type
readExpType ExpRhoType
res_ty
; HsOverLit GhcTc -> TcM (HsOverLit GhcTc)
forall a. a -> IOEnv (Env TcGblEnv TcLclEnv) a
forall (m :: * -> *) a. Monad m => a -> m a
return (HsOverLit GhcRn
lit { ol_ext :: XOverLit GhcTc
ol_ext = OverLitTc { $sel:ol_rebindable:OverLitTc :: Bool
ol_rebindable = Bool
rebindable
, $sel:ol_witness:OverLitTc :: HsExpr GhcTc
ol_witness = HsExpr GhcTc
witness
, $sel:ol_type:OverLitTc :: Type
ol_type = Type
res_ty } }) }
where
orig :: CtOrigin
orig = HsOverLit GhcRn -> CtOrigin
LiteralOrigin HsOverLit GhcRn
lit
mkOverLit ::OverLitVal -> TcM (HsLit GhcTc)
mkOverLit :: OverLitVal -> TcM (HsLit GhcTc)
mkOverLit (HsIntegral IntegralLit
i)
= do { Type
integer_ty <- Name -> TcM Type
tcMetaTy Name
integerTyConName
; HsLit GhcTc -> TcM (HsLit GhcTc)
forall a. a -> IOEnv (Env TcGblEnv TcLclEnv) a
forall (m :: * -> *) a. Monad m => a -> m a
return (XHsInteger GhcTc -> Integer -> Type -> HsLit GhcTc
forall x. XHsInteger x -> Integer -> Type -> HsLit x
HsInteger (IntegralLit -> SourceText
il_text IntegralLit
i)
(IntegralLit -> Integer
il_value IntegralLit
i) Type
integer_ty) }
mkOverLit (HsFractional FractionalLit
r)
= do { Type
rat_ty <- Name -> TcM Type
tcMetaTy Name
rationalTyConName
; HsLit GhcTc -> TcM (HsLit GhcTc)
forall a. a -> IOEnv (Env TcGblEnv TcLclEnv) a
forall (m :: * -> *) a. Monad m => a -> m a
return (XHsRat GhcTc -> FractionalLit -> Type -> HsLit GhcTc
forall x. XHsRat x -> FractionalLit -> Type -> HsLit x
HsRat XHsRat GhcTc
NoExtField
noExtField FractionalLit
r Type
rat_ty) }
mkOverLit (HsIsString SourceText
src FastString
s) = HsLit GhcTc -> TcM (HsLit GhcTc)
forall a. a -> IOEnv (Env TcGblEnv TcLclEnv) a
forall (m :: * -> *) a. Monad m => a -> m a
return (XHsString GhcTc -> FastString -> HsLit GhcTc
forall x. XHsString x -> FastString -> HsLit x
HsString XHsString GhcTc
SourceText
src FastString
s)
tcSyntaxName :: CtOrigin
-> TcType
-> (Name, HsExpr GhcRn)
-> TcM (Name, HsExpr GhcTc)
tcSyntaxName :: CtOrigin
-> Type -> (Name, HsExpr GhcRn) -> TcM (Name, HsExpr GhcTc)
tcSyntaxName CtOrigin
orig Type
ty (Name
std_nm, HsVar XVar GhcRn
_ (L SrcSpanAnnN
_ Name
user_nm))
| Name
std_nm Name -> Name -> Bool
forall a. Eq a => a -> a -> Bool
== Name
user_nm
= do HsExpr GhcTc
rhs <- CtOrigin -> Name -> [Type] -> TcM (HsExpr GhcTc)
newMethodFromName CtOrigin
orig Name
std_nm [Type
ty]
(Name, HsExpr GhcTc) -> TcM (Name, HsExpr GhcTc)
forall a. a -> IOEnv (Env TcGblEnv TcLclEnv) a
forall (m :: * -> *) a. Monad m => a -> m a
return (Name
std_nm, HsExpr GhcTc
rhs)
tcSyntaxName CtOrigin
orig Type
ty (Name
std_nm, HsExpr GhcRn
user_nm_expr) = do
DFunId
std_id <- Name -> TcM DFunId
tcLookupId Name
std_nm
let
([DFunId
tv], [Type]
_, Type
tau) = Type -> ([DFunId], [Type], Type)
tcSplitSigmaTy (DFunId -> Type
idType DFunId
std_id)
sigma1 :: Type
sigma1 = [DFunId] -> [Type] -> Type -> Type
(() :: Constraint) => [DFunId] -> [Type] -> Type -> Type
substTyWith [DFunId
tv] [Type
ty] Type
tau
SrcSpan
span <- TcRn SrcSpan
getSrcSpanM
(TidyEnv -> TcM (TidyEnv, SDoc))
-> TcM (Name, HsExpr GhcTc) -> TcM (Name, HsExpr GhcTc)
forall a. (TidyEnv -> TcM (TidyEnv, SDoc)) -> TcM a -> TcM a
addErrCtxtM (HsExpr GhcRn
-> CtOrigin -> Type -> SrcSpan -> TidyEnv -> TcM (TidyEnv, SDoc)
syntaxNameCtxt HsExpr GhcRn
user_nm_expr CtOrigin
orig Type
sigma1 SrcSpan
span) (TcM (Name, HsExpr GhcTc) -> TcM (Name, HsExpr GhcTc))
-> TcM (Name, HsExpr GhcTc) -> TcM (Name, HsExpr GhcTc)
forall a b. (a -> b) -> a -> b
$ do
GenLocated SrcSpanAnnA (HsExpr GhcTc)
expr <- LHsExpr GhcRn -> Type -> TcM (LHsExpr GhcTc)
tcCheckPolyExpr (SrcSpanAnnA
-> HsExpr GhcRn -> GenLocated SrcSpanAnnA (HsExpr GhcRn)
forall l e. l -> e -> GenLocated l e
L (SrcSpan -> SrcSpanAnnA
forall ann. SrcSpan -> SrcAnn ann
noAnnSrcSpan SrcSpan
span) HsExpr GhcRn
user_nm_expr) Type
sigma1
Name -> HsExpr GhcRn -> Type -> TcRn ()
hasFixedRuntimeRepRes Name
std_nm HsExpr GhcRn
user_nm_expr Type
sigma1
(Name, HsExpr GhcTc) -> TcM (Name, HsExpr GhcTc)
forall a. a -> IOEnv (Env TcGblEnv TcLclEnv) a
forall (m :: * -> *) a. Monad m => a -> m a
return (Name
std_nm, GenLocated SrcSpanAnnA (HsExpr GhcTc) -> HsExpr GhcTc
forall l e. GenLocated l e -> e
unLoc GenLocated SrcSpanAnnA (HsExpr GhcTc)
expr)
syntaxNameCtxt :: HsExpr GhcRn -> CtOrigin -> Type -> SrcSpan -> TidyEnv
-> TcRn (TidyEnv, SDoc)
syntaxNameCtxt :: HsExpr GhcRn
-> CtOrigin -> Type -> SrcSpan -> TidyEnv -> TcM (TidyEnv, SDoc)
syntaxNameCtxt HsExpr GhcRn
name CtOrigin
orig Type
ty SrcSpan
loc TidyEnv
tidy_env = (TidyEnv, SDoc) -> TcM (TidyEnv, SDoc)
forall a. a -> IOEnv (Env TcGblEnv TcLclEnv) a
forall (m :: * -> *) a. Monad m => a -> m a
return (TidyEnv
tidy_env, SDoc
msg)
where
msg :: SDoc
msg = [SDoc] -> SDoc
vcat [ String -> SDoc
text String
"When checking that" SDoc -> SDoc -> SDoc
<+> SDoc -> SDoc
quotes (HsExpr GhcRn -> SDoc
forall a. Outputable a => a -> SDoc
ppr HsExpr GhcRn
name)
SDoc -> SDoc -> SDoc
<+> String -> SDoc
text String
"(needed by a syntactic construct)"
, Arity -> SDoc -> SDoc
nest Arity
2 (String -> SDoc
text String
"has the required type:"
SDoc -> SDoc -> SDoc
<+> Type -> SDoc
forall a. Outputable a => a -> SDoc
ppr (TidyEnv -> Type -> Type
tidyType TidyEnv
tidy_env Type
ty))
, Arity -> SDoc -> SDoc
nest Arity
2 ([SDoc] -> SDoc
sep [CtOrigin -> SDoc
forall a. Outputable a => a -> SDoc
ppr CtOrigin
orig, String -> SDoc
text String
"at" SDoc -> SDoc -> SDoc
<+> SrcSpan -> SDoc
forall a. Outputable a => a -> SDoc
ppr SrcSpan
loc])]
hasFixedRuntimeRepRes :: Name -> HsExpr GhcRn -> TcSigmaType -> TcM ()
hasFixedRuntimeRepRes :: Name -> HsExpr GhcRn -> Type -> TcRn ()
hasFixedRuntimeRepRes Name
std_nm HsExpr GhcRn
user_expr Type
ty = (Arity -> TcRn ()) -> Maybe Arity -> TcRn ()
forall (t :: * -> *) (m :: * -> *) a b.
(Foldable t, Monad m) =>
(a -> m b) -> t a -> m ()
mapM_ Arity -> TcRn ()
do_check Maybe Arity
mb_arity
where
do_check :: Arity -> TcM ()
do_check :: Arity -> TcRn ()
do_check Arity
arity =
let res_ty :: Type
res_ty = Arity -> (Type -> Type) -> Type -> Type
forall a. Arity -> (a -> a) -> a -> a
nTimes Arity
arity ((TyBinder, Type) -> Type
forall a b. (a, b) -> b
snd ((TyBinder, Type) -> Type)
-> (Type -> (TyBinder, Type)) -> Type -> Type
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Type -> (TyBinder, Type)
splitPiTy) Type
ty
in (() :: Constraint) => FixedRuntimeRepContext -> Type -> TcRn ()
FixedRuntimeRepContext -> Type -> TcRn ()
hasFixedRuntimeRep_syntactic (FRRArrowContext -> FixedRuntimeRepContext
FRRArrow (FRRArrowContext -> FixedRuntimeRepContext)
-> FRRArrowContext -> FixedRuntimeRepContext
forall a b. (a -> b) -> a -> b
$ HsExpr GhcRn -> FRRArrowContext
ArrowFun HsExpr GhcRn
user_expr) Type
res_ty
mb_arity :: Maybe Arity
mb_arity :: Maybe Arity
mb_arity
| Name
std_nm Name -> Name -> Bool
forall a. Eq a => a -> a -> Bool
== Name
arrAName
= Arity -> Maybe Arity
forall a. a -> Maybe a
Just Arity
3
| Name
std_nm Name -> Name -> Bool
forall a. Eq a => a -> a -> Bool
== Name
composeAName
= Arity -> Maybe Arity
forall a. a -> Maybe a
Just Arity
5
| Name
std_nm Name -> Name -> Bool
forall a. Eq a => a -> a -> Bool
== Name
firstAName
= Arity -> Maybe Arity
forall a. a -> Maybe a
Just Arity
4
| Name
std_nm Name -> Name -> Bool
forall a. Eq a => a -> a -> Bool
== Name
appAName
= Arity -> Maybe Arity
forall a. a -> Maybe a
Just Arity
2
| Name
std_nm Name -> Name -> Bool
forall a. Eq a => a -> a -> Bool
== Name
choiceAName
= Arity -> Maybe Arity
forall a. a -> Maybe a
Just Arity
5
| Name
std_nm Name -> Name -> Bool
forall a. Eq a => a -> a -> Bool
== Name
loopAName
= Arity -> Maybe Arity
forall a. a -> Maybe a
Just Arity
4
| Bool
otherwise
= Maybe Arity
forall a. Maybe a
Nothing
getOverlapFlag :: Maybe OverlapMode -> TcM OverlapFlag
getOverlapFlag :: Maybe OverlapMode -> TcM OverlapFlag
getOverlapFlag Maybe OverlapMode
overlap_mode
= do { DynFlags
dflags <- IOEnv (Env TcGblEnv TcLclEnv) DynFlags
forall (m :: * -> *). HasDynFlags m => m DynFlags
getDynFlags
; let overlap_ok :: Bool
overlap_ok = Extension -> DynFlags -> Bool
xopt Extension
LangExt.OverlappingInstances DynFlags
dflags
incoherent_ok :: Bool
incoherent_ok = Extension -> DynFlags -> Bool
xopt Extension
LangExt.IncoherentInstances DynFlags
dflags
use :: OverlapMode -> OverlapFlag
use OverlapMode
x = OverlapFlag { isSafeOverlap :: Bool
isSafeOverlap = DynFlags -> Bool
safeLanguageOn DynFlags
dflags
, overlapMode :: OverlapMode
overlapMode = OverlapMode
x }
default_oflag :: OverlapFlag
default_oflag | Bool
incoherent_ok = OverlapMode -> OverlapFlag
use (SourceText -> OverlapMode
Incoherent SourceText
NoSourceText)
| Bool
overlap_ok = OverlapMode -> OverlapFlag
use (SourceText -> OverlapMode
Overlaps SourceText
NoSourceText)
| Bool
otherwise = OverlapMode -> OverlapFlag
use (SourceText -> OverlapMode
NoOverlap SourceText
NoSourceText)
final_oflag :: OverlapFlag
final_oflag = OverlapFlag -> Maybe OverlapMode -> OverlapFlag
setOverlapModeMaybe OverlapFlag
default_oflag Maybe OverlapMode
overlap_mode
; OverlapFlag -> TcM OverlapFlag
forall a. a -> IOEnv (Env TcGblEnv TcLclEnv) a
forall (m :: * -> *) a. Monad m => a -> m a
return OverlapFlag
final_oflag }
tcGetInsts :: TcM [ClsInst]
tcGetInsts :: TcM [ClsInst]
tcGetInsts = (TcGblEnv -> [ClsInst])
-> IOEnv (Env TcGblEnv TcLclEnv) TcGblEnv -> TcM [ClsInst]
forall a b.
(a -> b)
-> IOEnv (Env TcGblEnv TcLclEnv) a
-> IOEnv (Env TcGblEnv TcLclEnv) b
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
fmap TcGblEnv -> [ClsInst]
tcg_insts IOEnv (Env TcGblEnv TcLclEnv) TcGblEnv
forall gbl lcl. TcRnIf gbl lcl gbl
getGblEnv
newClsInst :: Maybe OverlapMode -> Name -> [TyVar] -> ThetaType
-> Class -> [Type] -> TcM ClsInst
newClsInst :: Maybe OverlapMode
-> Name -> [DFunId] -> [Type] -> Class -> [Type] -> TcM ClsInst
newClsInst Maybe OverlapMode
overlap_mode Name
dfun_name [DFunId]
tvs [Type]
theta Class
clas [Type]
tys
= do { (TCvSubst
subst, [DFunId]
tvs') <- [DFunId] -> TcM (TCvSubst, [DFunId])
freshenTyVarBndrs [DFunId]
tvs
; let tys' :: [Type]
tys' = (() :: Constraint) => TCvSubst -> [Type] -> [Type]
TCvSubst -> [Type] -> [Type]
substTys TCvSubst
subst [Type]
tys
dfun :: DFunId
dfun = Name -> [DFunId] -> [Type] -> Class -> [Type] -> DFunId
mkDictFunId Name
dfun_name [DFunId]
tvs [Type]
theta Class
clas [Type]
tys
; OverlapFlag
oflag <- Maybe OverlapMode -> TcM OverlapFlag
getOverlapFlag Maybe OverlapMode
overlap_mode
; let inst :: ClsInst
inst = DFunId -> OverlapFlag -> [DFunId] -> Class -> [Type] -> ClsInst
mkLocalInstance DFunId
dfun OverlapFlag
oflag [DFunId]
tvs' Class
clas [Type]
tys'
; Bool -> TcRn () -> TcRn ()
forall (f :: * -> *). Applicative f => Bool -> f () -> f ()
when (IsOrphan -> Bool
isOrphan (ClsInst -> IsOrphan
is_orphan ClsInst
inst)) (TcRn () -> TcRn ()) -> TcRn () -> TcRn ()
forall a b. (a -> b) -> a -> b
$
TcRnMessage -> TcRn ()
addDiagnostic (ClsInst -> TcRnMessage
TcRnOrphanInstance ClsInst
inst)
; ClsInst -> TcM ClsInst
forall a. a -> IOEnv (Env TcGblEnv TcLclEnv) a
forall (m :: * -> *) a. Monad m => a -> m a
return ClsInst
inst }
tcExtendLocalInstEnv :: [ClsInst] -> TcM a -> TcM a
tcExtendLocalInstEnv :: forall a. [ClsInst] -> TcM a -> TcM a
tcExtendLocalInstEnv [ClsInst]
dfuns TcM a
thing_inside
= do { [ClsInst] -> TcRn ()
traceDFuns [ClsInst]
dfuns
; TcGblEnv
env <- IOEnv (Env TcGblEnv TcLclEnv) TcGblEnv
forall gbl lcl. TcRnIf gbl lcl gbl
getGblEnv
; let !init_inst_env :: InstEnv
init_inst_env = TcGblEnv -> InstEnv
tcg_inst_env TcGblEnv
env
!init_insts :: [ClsInst]
init_insts = TcGblEnv -> [ClsInst]
tcg_insts TcGblEnv
env
; (InstEnv
inst_env', [ClsInst]
cls_insts') <- ((InstEnv, [ClsInst])
-> ClsInst -> IOEnv (Env TcGblEnv TcLclEnv) (InstEnv, [ClsInst]))
-> (InstEnv, [ClsInst])
-> [ClsInst]
-> IOEnv (Env TcGblEnv TcLclEnv) (InstEnv, [ClsInst])
forall (t :: * -> *) (m :: * -> *) b a.
(Foldable t, Monad m) =>
(b -> a -> m b) -> b -> t a -> m b
foldlM (InstEnv, [ClsInst])
-> ClsInst -> IOEnv (Env TcGblEnv TcLclEnv) (InstEnv, [ClsInst])
addLocalInst
(InstEnv
init_inst_env, [ClsInst]
init_insts)
[ClsInst]
dfuns
; let env' :: TcGblEnv
env' = TcGblEnv
env { tcg_insts :: [ClsInst]
tcg_insts = [ClsInst]
cls_insts'
, tcg_inst_env :: InstEnv
tcg_inst_env = InstEnv
inst_env' }
; TcGblEnv -> TcM a -> TcM a
forall gbl' lcl a gbl.
gbl' -> TcRnIf gbl' lcl a -> TcRnIf gbl lcl a
setGblEnv TcGblEnv
env' TcM a
thing_inside }
addLocalInst :: (InstEnv, [ClsInst]) -> ClsInst -> TcM (InstEnv, [ClsInst])
addLocalInst :: (InstEnv, [ClsInst])
-> ClsInst -> IOEnv (Env TcGblEnv TcLclEnv) (InstEnv, [ClsInst])
addLocalInst (InstEnv
home_ie, [ClsInst]
my_insts) ClsInst
ispec
= do {
; Bool
isGHCi <- TcRn Bool
getIsGHCi
; ExternalPackageState
eps <- TcRnIf TcGblEnv TcLclEnv ExternalPackageState
forall gbl lcl. TcRnIf gbl lcl ExternalPackageState
getEps
; TcGblEnv
tcg_env <- IOEnv (Env TcGblEnv TcLclEnv) TcGblEnv
forall gbl lcl. TcRnIf gbl lcl gbl
getGblEnv
; let home_ie' :: InstEnv
home_ie'
| Bool
isGHCi = InstEnv -> ClsInst -> InstEnv
deleteFromInstEnv InstEnv
home_ie ClsInst
ispec
| Bool
otherwise = InstEnv
home_ie
global_ie :: InstEnv
global_ie = ExternalPackageState -> InstEnv
eps_inst_env ExternalPackageState
eps
inst_envs :: InstEnvs
inst_envs = InstEnvs { ie_global :: InstEnv
ie_global = InstEnv
global_ie
, ie_local :: InstEnv
ie_local = InstEnv
home_ie'
, ie_visible :: VisibleOrphanModules
ie_visible = TcGblEnv -> VisibleOrphanModules
tcVisibleOrphanMods TcGblEnv
tcg_env }
; let inconsistent_ispecs :: [ClsInst]
inconsistent_ispecs = InstEnvs -> ClsInst -> [ClsInst]
checkFunDeps InstEnvs
inst_envs ClsInst
ispec
; Bool -> TcRn () -> TcRn ()
forall (f :: * -> *). Applicative f => Bool -> f () -> f ()
unless ([ClsInst] -> Bool
forall a. [a] -> Bool
forall (t :: * -> *) a. Foldable t => t a -> Bool
null [ClsInst]
inconsistent_ispecs) (TcRn () -> TcRn ()) -> TcRn () -> TcRn ()
forall a b. (a -> b) -> a -> b
$
ClsInst -> [ClsInst] -> TcRn ()
funDepErr ClsInst
ispec [ClsInst]
inconsistent_ispecs
; let ([DFunId]
_tvs, Class
cls, [Type]
tys) = ClsInst -> ([DFunId], Class, [Type])
instanceHead ClsInst
ispec
([InstMatch]
matches, PotentialUnifiers
_, [InstMatch]
_) = Bool
-> InstEnvs
-> Class
-> [Type]
-> ([InstMatch], PotentialUnifiers, [InstMatch])
lookupInstEnv Bool
False InstEnvs
inst_envs Class
cls [Type]
tys
dups :: [ClsInst]
dups = (ClsInst -> Bool) -> [ClsInst] -> [ClsInst]
forall a. (a -> Bool) -> [a] -> [a]
filter (ClsInst -> ClsInst -> Bool
identicalClsInstHead ClsInst
ispec) ((InstMatch -> ClsInst) -> [InstMatch] -> [ClsInst]
forall a b. (a -> b) -> [a] -> [b]
map InstMatch -> ClsInst
forall a b. (a, b) -> a
fst [InstMatch]
matches)
; Bool -> TcRn () -> TcRn ()
forall (f :: * -> *). Applicative f => Bool -> f () -> f ()
unless ([ClsInst] -> Bool
forall a. [a] -> Bool
forall (t :: * -> *) a. Foldable t => t a -> Bool
null [ClsInst]
dups) (TcRn () -> TcRn ()) -> TcRn () -> TcRn ()
forall a b. (a -> b) -> a -> b
$
ClsInst -> ClsInst -> TcRn ()
dupInstErr ClsInst
ispec ([ClsInst] -> ClsInst
forall a. HasCallStack => [a] -> a
head [ClsInst]
dups)
; (InstEnv, [ClsInst])
-> IOEnv (Env TcGblEnv TcLclEnv) (InstEnv, [ClsInst])
forall a. a -> IOEnv (Env TcGblEnv TcLclEnv) a
forall (m :: * -> *) a. Monad m => a -> m a
return (InstEnv -> ClsInst -> InstEnv
extendInstEnv InstEnv
home_ie' ClsInst
ispec, ClsInst
ispec ClsInst -> [ClsInst] -> [ClsInst]
forall a. a -> [a] -> [a]
: [ClsInst]
my_insts) }
traceDFuns :: [ClsInst] -> TcRn ()
traceDFuns :: [ClsInst] -> TcRn ()
traceDFuns [ClsInst]
ispecs
= String -> SDoc -> TcRn ()
traceTc String
"Adding instances:" ([SDoc] -> SDoc
vcat ((ClsInst -> SDoc) -> [ClsInst] -> [SDoc]
forall a b. (a -> b) -> [a] -> [b]
map ClsInst -> SDoc
pp [ClsInst]
ispecs))
where
pp :: ClsInst -> SDoc
pp ClsInst
ispec = SDoc -> Arity -> SDoc -> SDoc
hang (DFunId -> SDoc
forall a. Outputable a => a -> SDoc
ppr (ClsInst -> DFunId
instanceDFunId ClsInst
ispec) SDoc -> SDoc -> SDoc
<+> SDoc
colon)
Arity
2 (ClsInst -> SDoc
forall a. Outputable a => a -> SDoc
ppr ClsInst
ispec)
funDepErr :: ClsInst -> [ClsInst] -> TcRn ()
funDepErr :: ClsInst -> [ClsInst] -> TcRn ()
funDepErr ClsInst
ispec [ClsInst]
ispecs
= (UnitState -> NonEmpty ClsInst -> TcRnMessage)
-> NonEmpty ClsInst -> TcRn ()
addClsInstsErr UnitState -> NonEmpty ClsInst -> TcRnMessage
TcRnFunDepConflict (ClsInst
ispec ClsInst -> [ClsInst] -> NonEmpty ClsInst
forall a. a -> [a] -> NonEmpty a
NE.:| [ClsInst]
ispecs)
dupInstErr :: ClsInst -> ClsInst -> TcRn ()
dupInstErr :: ClsInst -> ClsInst -> TcRn ()
dupInstErr ClsInst
ispec ClsInst
dup_ispec
= (UnitState -> NonEmpty ClsInst -> TcRnMessage)
-> NonEmpty ClsInst -> TcRn ()
addClsInstsErr UnitState -> NonEmpty ClsInst -> TcRnMessage
TcRnDupInstanceDecls (ClsInst
ispec ClsInst -> [ClsInst] -> NonEmpty ClsInst
forall a. a -> [a] -> NonEmpty a
NE.:| [ClsInst
dup_ispec])
addClsInstsErr :: (UnitState -> NE.NonEmpty ClsInst -> TcRnMessage)
-> NE.NonEmpty ClsInst
-> TcRn ()
addClsInstsErr :: (UnitState -> NonEmpty ClsInst -> TcRnMessage)
-> NonEmpty ClsInst -> TcRn ()
addClsInstsErr UnitState -> NonEmpty ClsInst -> TcRnMessage
mkErr NonEmpty ClsInst
ispecs = do
UnitState
unit_state <- (() :: Constraint) => HscEnv -> UnitState
HscEnv -> UnitState
hsc_units (HscEnv -> UnitState)
-> IOEnv (Env TcGblEnv TcLclEnv) HscEnv
-> IOEnv (Env TcGblEnv TcLclEnv) UnitState
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> IOEnv (Env TcGblEnv TcLclEnv) HscEnv
forall gbl lcl. TcRnIf gbl lcl HscEnv
getTopEnv
SrcSpan -> TcRn () -> TcRn ()
forall a. SrcSpan -> TcRn a -> TcRn a
setSrcSpan (ClsInst -> SrcSpan
forall a. NamedThing a => a -> SrcSpan
getSrcSpan (NonEmpty ClsInst -> ClsInst
forall a. NonEmpty a -> a
NE.head NonEmpty ClsInst
sorted)) (TcRn () -> TcRn ()) -> TcRn () -> TcRn ()
forall a b. (a -> b) -> a -> b
$
TcRnMessage -> TcRn ()
addErr (TcRnMessage -> TcRn ()) -> TcRnMessage -> TcRn ()
forall a b. (a -> b) -> a -> b
$ UnitState -> NonEmpty ClsInst -> TcRnMessage
mkErr UnitState
unit_state NonEmpty ClsInst
sorted
where
sorted :: NonEmpty ClsInst
sorted = (ClsInst -> ClsInst -> Ordering)
-> NonEmpty ClsInst -> NonEmpty ClsInst
forall a. (a -> a -> Ordering) -> NonEmpty a -> NonEmpty a
NE.sortBy (SrcSpan -> SrcSpan -> Ordering
SrcLoc.leftmost_smallest (SrcSpan -> SrcSpan -> Ordering)
-> (ClsInst -> SrcSpan) -> ClsInst -> ClsInst -> Ordering
forall b c a. (b -> b -> c) -> (a -> b) -> a -> a -> c
`on` ClsInst -> SrcSpan
forall a. NamedThing a => a -> SrcSpan
getSrcSpan) NonEmpty ClsInst
ispecs