-getTyBinding1 :: RenamedTyClDecl -> NF_TcM s (Name, (TcKind, Maybe Arity, TcTyThing))
-getTyBinding1 (TySynonym name tyvars _ _)
- = mapNF_Tc kcHsTyVar tyvars `thenNF_Tc` \ arg_kinds ->
- newKindVar `thenNF_Tc` \ result_kind ->
- returnNF_Tc (name, (foldr mkArrowKind result_kind arg_kinds,
- Just (length tyvars),
- ATyCon (pprPanic "ATyCon: syn" (ppr name))))
-
-getTyBinding1 (TyData _ _ name tyvars _ _ _ _)
- = mapNF_Tc kcHsTyVar tyvars `thenNF_Tc` \ arg_kinds ->
- returnNF_Tc (name, (foldr mkArrowKind boxedTypeKind arg_kinds,
- Nothing,
- ATyCon (error "ATyCon: data")))
-
-getTyBinding1 (ClassDecl _ name tyvars _ _ _ _ _ _ _)
- = mapNF_Tc kcHsTyVar tyvars `thenNF_Tc` \ arg_kinds ->
- returnNF_Tc (name, (foldr mkArrowKind boxedTypeKind arg_kinds,
- Just (length tyvars),
- AClass (error "AClass")))
-
--- Zonk the kind to its final form, and lookup the
--- recursive tycon/class
-getTyBinding2 rec_env (name, (tc_kind, maybe_arity, thing))
- = zonkTcKindToKind tc_kind `thenNF_Tc` \ kind ->
- returnNF_Tc (name, (kind, maybe_arity, mk_thing thing (lookupUFM rec_env name)))
+kcTyClDecls syn_decls alg_decls
+ = do { -- First extend the kind env with each data
+ -- type and class, mapping them to a type variable
+ alg_kinds <- mappM getInitialKind alg_decls
+ ; tcExtendKindEnv alg_kinds $ do
+
+ -- Now kind-check the type synonyms, in dependency order
+ -- We do these differently to data type and classes,
+ -- because a type synonym can be an unboxed type
+ -- type Foo = Int#
+ -- and a kind variable can't unify with UnboxedTypeKind
+ -- So we infer their kinds in dependency order
+ { (kc_syn_decls, syn_kinds) <- kcSynDecls (calcSynCycles syn_decls)
+ ; tcExtendKindEnv syn_kinds $ do
+
+ -- Now kind-check the data type and class declarations,
+ -- returning kind-annotated decls
+ { kc_alg_decls <- mappM (wrapLocM kcTyClDecl) alg_decls
+
+ ; return (kc_syn_decls, kc_alg_decls) }}}
+
+------------------------------------------------------------------------
+getInitialKind :: LTyClDecl Name -> TcM (Name, TcKind)
+
+getInitialKind decl
+ = newKindVar `thenM` \ kind ->
+ returnM (unLoc (tcdLName (unLoc decl)), kind)
+
+----------------
+kcSynDecls :: [SCC (LTyClDecl Name)]
+ -> TcM ([LTyClDecl Name], -- Kind-annotated decls
+ [(Name,TcKind)]) -- Kind bindings
+kcSynDecls []
+ = return ([], [])
+kcSynDecls (group : groups)
+ = do { (decl, nk) <- kcSynDecl group
+ ; (decls, nks) <- tcExtendKindEnv [nk] (kcSynDecls groups)
+ ; return (decl:decls, nk:nks) }
+
+----------------
+kcSynDecl :: SCC (LTyClDecl Name)
+ -> TcM (LTyClDecl Name, -- Kind-annotated decls
+ (Name,TcKind)) -- Kind bindings
+kcSynDecl (AcyclicSCC ldecl@(L loc decl))
+ = tcAddDeclCtxt decl $
+ kcHsTyVars (tcdTyVars decl) (\ k_tvs ->
+ do { traceTc (text "kcd1" <+> ppr (unLoc (tcdLName decl)) <+> brackets (ppr (tcdTyVars decl))
+ <+> brackets (ppr k_tvs))
+ ; (k_rhs, rhs_kind) <- kcHsType (tcdSynRhs decl)
+ ; traceTc (text "kcd2" <+> ppr (unLoc (tcdLName decl)))
+ ; let tc_kind = foldr (mkArrowKind . kindedTyVarKind) rhs_kind k_tvs
+ ; return (L loc (decl { tcdTyVars = k_tvs, tcdSynRhs = k_rhs }),
+ (unLoc (tcdLName decl), tc_kind)) })
+
+kcSynDecl (CyclicSCC decls)
+ = do { recSynErr decls; failM } -- Fail here to avoid error cascade
+ -- of out-of-scope tycons
+
+------------------------------------------------------------------------
+kcTyClDecl :: TyClDecl Name -> TcM (TyClDecl Name)
+ -- Not used for type synonyms (see kcSynDecl)
+
+kcTyClDecl decl@(TyData {tcdND = new_or_data, tcdCtxt = ctxt, tcdCons = cons})
+ = kcTyClDeclBody decl $ \ tvs' ->
+ do { ctxt' <- kcHsContext ctxt
+ ; cons' <- mappM (wrapLocM kc_con_decl) cons
+ ; return (decl {tcdTyVars = tvs', tcdCtxt = ctxt', tcdCons = cons'}) }
+ where
+ kc_con_decl (ConDecl name ex_tvs ex_ctxt details)
+ = kcHsTyVars ex_tvs $ \ ex_tvs' ->
+ do { ex_ctxt' <- kcHsContext ex_ctxt
+ ; details' <- kc_con_details details
+ ; return (ConDecl name ex_tvs' ex_ctxt' details')}
+ kc_con_decl (GadtDecl name ty)
+ = do { ty' <- kcHsSigType ty
+ ; return (GadtDecl name ty') }
+
+ kc_con_details (PrefixCon btys)
+ = do { btys' <- mappM kc_larg_ty btys ; return (PrefixCon btys') }
+ kc_con_details (InfixCon bty1 bty2)
+ = do { bty1' <- kc_larg_ty bty1; bty2' <- kc_larg_ty bty2; return (InfixCon bty1' bty2') }
+ kc_con_details (RecCon fields)
+ = do { fields' <- mappM kc_field fields; return (RecCon fields') }
+
+ kc_field (fld, bty) = do { bty' <- kc_larg_ty bty ; return (fld, bty') }
+
+ kc_larg_ty bty = case new_or_data of
+ DataType -> kcHsSigType bty
+ NewType -> kcHsLiftedSigType bty
+ -- Can't allow an unlifted type for newtypes, because we're effectively
+ -- going to remove the constructor while coercing it to a lifted type.
+ -- And newtypes can't be bang'd
+
+kcTyClDecl decl@(ClassDecl {tcdCtxt = ctxt, tcdSigs = sigs})
+ = kcTyClDeclBody decl $ \ tvs' ->
+ do { ctxt' <- kcHsContext ctxt
+ ; sigs' <- mappM (wrapLocM kc_sig) sigs
+ ; return (decl {tcdTyVars = tvs', tcdCtxt = ctxt', tcdSigs = sigs'}) }
+ where
+ kc_sig (Sig nm op_ty) = do { op_ty' <- kcHsLiftedSigType op_ty
+ ; return (Sig nm op_ty') }
+ kc_sig other_sig = return other_sig
+
+kcTyClDecl decl@(ForeignType {})
+ = return decl
+
+kcTyClDeclBody :: TyClDecl Name
+ -> ([LHsTyVarBndr Name] -> TcM a)
+ -> TcM a
+ -- Extend the env with bindings for the tyvars, taken from
+ -- the kind of the tycon/class. Give it to the thing inside, and
+ -- check the result kind matches
+kcTyClDeclBody decl thing_inside
+ = tcAddDeclCtxt decl $
+ kcHsTyVars (tyClDeclTyVars decl) $ \ kinded_tvs ->
+ do { tc_ty_thing <- tcLookupLocated (tcdLName decl)
+ ; let tc_kind = case tc_ty_thing of { AThing k -> k }
+ ; unifyKind tc_kind (foldr (mkArrowKind . kindedTyVarKind)
+ (result_kind decl)
+ kinded_tvs)
+ ; thing_inside kinded_tvs }