2 collectAnnTypeBinders, collectAnnTypeArgs, isAnnTypeArg,
4 mkPADictType, mkPArrayType,
5 paDictArgType, paDictOfType,
6 paMethod, lengthPA, replicatePA, emptyPA,
7 abstractOverTyVars, applyToTypes,
12 #include "HsVersions.h"
27 import Control.Monad ( liftM, zipWithM_ )
29 collectAnnTypeArgs :: AnnExpr b ann -> (AnnExpr b ann, [Type])
30 collectAnnTypeArgs expr = go expr []
32 go (_, AnnApp f (_, AnnType ty)) tys = go f (ty : tys)
35 collectAnnTypeBinders :: AnnExpr Var ann -> ([Var], AnnExpr Var ann)
36 collectAnnTypeBinders expr = go [] expr
38 go bs (_, AnnLam b e) | isTyVar b = go (b:bs) e
39 go bs e = (reverse bs, e)
41 isAnnTypeArg :: AnnExpr b ann -> Bool
42 isAnnTypeArg (_, AnnType t) = True
43 isAnnTypeArg _ = False
45 isClosureTyCon :: TyCon -> Bool
46 isClosureTyCon tc = tyConUnique tc == closureTyConKey
48 splitClosureTy :: Type -> (Type, Type)
50 | Just (tc, [arg_ty, res_ty]) <- splitTyConApp_maybe ty
54 | otherwise = pprPanic "splitClosureTy" (ppr ty)
56 mkPADictType :: Type -> VM Type
59 tc <- builtin paDictTyCon
60 return $ TyConApp tc [ty]
62 mkPArrayType :: Type -> VM Type
65 tc <- builtin parrayTyCon
66 return $ TyConApp tc [ty]
68 paDictArgType :: TyVar -> VM (Maybe Type)
69 paDictArgType tv = go (TyVarTy tv) (tyVarKind tv)
71 go ty k | Just k' <- kindView k = go ty k'
74 tv <- newTyVar FSLIT("a") k1
75 mty1 <- go (TyVarTy tv) k1
78 mty2 <- go (AppTy ty (TyVarTy tv)) k2
79 return $ fmap (ForAllTy tv . FunTy ty1) mty2
84 = liftM Just (mkPADictType ty)
86 go ty k = return Nothing
88 paDictOfType :: Type -> VM CoreExpr
89 paDictOfType ty = paDictOfTyApp ty_fn ty_args
91 (ty_fn, ty_args) = splitAppTys ty
93 paDictOfTyApp :: Type -> [Type] -> VM CoreExpr
94 paDictOfTyApp ty_fn ty_args
95 | Just ty_fn' <- coreView ty_fn = paDictOfTyApp ty_fn' ty_args
96 paDictOfTyApp (TyVarTy tv) ty_args
98 dfun <- maybeV (lookupTyVarPA tv)
99 paDFunApply dfun ty_args
100 paDictOfTyApp (TyConApp tc _) ty_args
102 pa_class <- builtin paClass
103 (dfun, ty_args') <- lookupInst pa_class [TyConApp tc ty_args]
104 paDFunApply (Var dfun) ty_args'
105 paDictOfTyApp ty ty_args = pprPanic "paDictOfTyApp" (ppr ty)
107 paDFunApply :: CoreExpr -> [Type] -> VM CoreExpr
110 dicts <- mapM paDictOfType tys
111 return $ mkApps (mkTyApps dfun tys) dicts
113 paMethod :: (Builtins -> Var) -> Type -> VM CoreExpr
117 dict <- paDictOfType ty
118 return $ mkApps (Var fn) [Type ty, dict]
120 lengthPA :: CoreExpr -> VM CoreExpr
121 lengthPA x = liftM (`App` x) (paMethod lengthPAVar (exprType x))
123 replicatePA :: CoreExpr -> CoreExpr -> VM CoreExpr
124 replicatePA len x = liftM (`mkApps` [len,x])
125 (paMethod replicatePAVar (exprType x))
127 emptyPA :: Type -> VM CoreExpr
128 emptyPA = paMethod emptyPAVar
130 abstractOverTyVars :: [TyVar] -> ((CoreExpr -> CoreExpr) -> VM a) -> VM a
131 abstractOverTyVars tvs p
133 mdicts <- mapM mk_dict_var tvs
134 zipWithM_ (\tv -> maybe (defLocalTyVar tv) (defLocalTyVarWithPA tv . Var)) tvs mdicts
138 r <- paDictArgType tv
140 Just ty -> liftM Just (newLocalVar FSLIT("dPA") ty)
141 Nothing -> return Nothing
143 mk_lams mdicts = mkLams (tvs ++ [dict | Just dict <- mdicts])
145 applyToTypes :: CoreExpr -> [Type] -> VM CoreExpr
146 applyToTypes expr tys
148 dicts <- mapM paDictOfType tys
149 return $ expr `mkTyApps` tys `mkApps` dicts
151 lookupPArrayFamInst :: Type -> VM (TyCon, [Type])
152 lookupPArrayFamInst ty = builtin parrayTyCon >>= (`lookupFamInst` [ty])
154 hoistExpr :: FastString -> CoreExpr -> VM Var
157 var <- newLocalVar fs (exprType expr)
159 env { global_bindings = (var, expr) : global_bindings env }
162 takeHoisted :: VM [(Var, CoreExpr)]
166 setGEnv $ env { global_bindings = [] }
167 return $ global_bindings env