X-Git-Url: http://git.megacz.com/?a=blobdiff_plain;f=compiler%2Ftypecheck%2FTcTyClsDecls.lhs;h=9e302c3a6168517439296fa036d235ce9b6df19a;hb=fcb83d8469d4d7f282754387369aa86d40429dcf;hp=56ff0e1bca581364956792b3b1b5cb60da3256cd;hpb=485c8034041b7d7f26688c24b88a50a62e3d3229;p=ghc-hetmet.git diff --git a/compiler/typecheck/TcTyClsDecls.lhs b/compiler/typecheck/TcTyClsDecls.lhs index 56ff0e1..9e302c3 100644 --- a/compiler/typecheck/TcTyClsDecls.lhs +++ b/compiler/typecheck/TcTyClsDecls.lhs @@ -44,7 +44,7 @@ import ListSetOps import Digraph import DynFlags -import Data.List ( partition, elemIndex ) +import Data.List import Control.Monad ( mplus ) \end{code} @@ -267,8 +267,13 @@ tcFamInstDecl1 (decl@TySynonym {tcdLName = L loc tc_name}) ; t_typats <- mappM tcHsKindedType k_typats ; t_rhs <- tcHsKindedType k_rhs - ; -- (3) check that the right-hand side is a tau type - ; unless (isTauTy t_rhs) $ + -- (3) check that + -- - left-hand side contains no type family applications + -- (vanilla synonyms are fine, though) + ; mappM_ checkTyFamFreeness t_typats + + -- - the right-hand side is a tau type + ; unless (isTauTy t_rhs) $ addErr (polyTyErr t_rhs) -- (4) construct representation tycon @@ -299,17 +304,23 @@ tcFamInstDecl1 (decl@TyData {tcdND = new_or_data, tcdLName = L loc tc_name, ; tcTyVarBndrs k_tvs $ \t_tvs -> do { -- turn kinded into proper tyvars ; unbox_strict <- doptM Opt_UnboxStrictFields - -- Check that we don't use GADT syntax for indexed types + -- kind check the type indexes and the context + ; t_typats <- mappM tcHsKindedType k_typats + ; stupid_theta <- tcHsKindedContext k_ctxt + + -- (3) Check that + -- - left-hand side contains no type family applications + -- (vanilla synonyms are fine, though) + ; mappM_ checkTyFamFreeness t_typats + + -- - we don't use GADT syntax for indexed types ; checkTc h98_syntax (badGadtIdxTyDecl tc_name) - -- Check that a newtype has exactly one constructor + -- - a newtype has exactly one constructor ; checkTc (new_or_data == DataType || isSingleton k_cons) $ newtypeConError tc_name (length k_cons) - ; t_typats <- mappM tcHsKindedType k_typats - ; stupid_theta <- tcHsKindedContext k_ctxt - - -- (3) construct representation tycon + -- (4) construct representation tycon ; rep_tc_name <- newFamInstTyConName tc_name loc ; tycon <- fixM (\ tycon -> do { data_cons <- mappM (addLocM (tcConDecl unbox_strict tycon t_tvs)) @@ -336,6 +347,27 @@ tcFamInstDecl1 (decl@TyData {tcdND = new_or_data, tcdLName = L loc tc_name, L _ (ConDecl { con_res = ResTyGADT _ }) : _ -> False other -> True +-- Check that a type index does not contain any type family applications +-- +-- * Earlier phases have already checked that there are no foralls in the +-- type; we also cannot have PredTys and NoteTys are being skipped by using +-- the core view. +-- +checkTyFamFreeness :: Type -> TcM () +checkTyFamFreeness ty | Just (tycon, tys) <- splitTyConApp_maybe ty + = if isSynTyCon tycon + then addErr $ tyFamAppInIndexErr ty + else mappM_ checkTyFamFreeness tys + -- splitTyConApp_maybe uses the core view; hence, + -- any synonym tycon must be a family tycon + + | Just (ty1, ty2) <- splitAppTy_maybe ty + = checkTyFamFreeness ty1 >> checkTyFamFreeness ty2 + + | otherwise -- only vars remaining + = return () + + -- Kind checking of indexed types -- - @@ -661,7 +693,8 @@ tcTyClDecl1 calc_isrec ; stupid_theta <- tcHsKindedContext ctxt ; want_generic <- doptM Opt_Generics ; unbox_strict <- doptM Opt_UnboxStrictFields - ; gla_exts <- doptM Opt_GlasgowExts + ; empty_data_decls <- doptM Opt_EmptyDataDecls + ; kind_signatures <- doptM Opt_KindSignatures ; gadt_ok <- doptM Opt_GADTs ; is_boot <- tcIsHsBoot -- Are we compiling an hs-boot file? @@ -669,14 +702,14 @@ tcTyClDecl1 calc_isrec ; checkTc (gadt_ok || h98_syntax) (badGadtDecl tc_name) -- Check that we don't use kind signatures without Glasgow extensions - ; checkTc (gla_exts || isNothing mb_ksig) (badSigTyDecl tc_name) + ; checkTc (kind_signatures || isNothing mb_ksig) (badSigTyDecl tc_name) -- Check that the stupid theta is empty for a GADT-style declaration ; checkTc (null stupid_theta || h98_syntax) (badStupidTheta tc_name) -- Check that there's at least one condecl, - -- or else we're reading an hs-boot file, or -fglasgow-exts - ; checkTc (not (null cons) || gla_exts || is_boot) + -- or else we're reading an hs-boot file, or -XEmptyDataDecls + ; checkTc (not (null cons) || empty_data_decls || is_boot) (emptyConDeclsErr tc_name) -- Check that a newtype has exactly one constructor @@ -1026,10 +1059,13 @@ checkValidClass :: Class -> TcM () checkValidClass cls = do { -- CHECK ARITY 1 FOR HASKELL 1.4 gla_exts <- doptM Opt_GlasgowExts + ; multi_param_type_classes <- doptM Opt_MultiParamTypeClasses + ; fundep_classes <- doptM Opt_FunctionalDependencies -- Check that the class is unary, unless GlaExs ; checkTc (notNull tyvars) (nullaryClassErr cls) - ; checkTc (gla_exts || unary) (classArityErr cls) + ; checkTc (multi_param_type_classes || unary) (classArityErr cls) + ; checkTc (fundep_classes || null fundeps) (classFunDepsErr cls) -- Check the super-classes ; checkValidTheta (ClassSCCtxt (className cls)) theta @@ -1043,7 +1079,7 @@ checkValidClass cls ; checkTc (unary || no_generics) (genericMultiParamErr cls) } where - (tyvars, theta, _, op_stuff) = classBigSig cls + (tyvars, fundeps, theta, _, _, op_stuff) = classExtraBigSig cls unary = isSingleton tyvars no_generics = null [() | (_, GenDefMeth) <- op_stuff] @@ -1104,7 +1140,11 @@ nullaryClassErr cls classArityErr cls = vcat [ptext SLIT("Too many parameters for class") <+> quotes (ppr cls), - parens (ptext SLIT("Use -fglasgow-exts to allow multi-parameter classes"))] + parens (ptext SLIT("Use -XMultiParamTypeClasses to allow multi-parameter classes"))] + +classFunDepsErr cls + = vcat [ptext SLIT("Fundeps in class") <+> quotes (ppr cls), + parens (ptext SLIT("Use -XFunctionalDependencies to allow fundeps"))] noClassTyVarErr clas op = sep [ptext SLIT("The class method") <+> quotes (ppr op), @@ -1176,7 +1216,7 @@ newtypeFieldErr con_name n_flds badSigTyDecl tc_name = vcat [ ptext SLIT("Illegal kind signature") <+> quotes (ppr tc_name) - , nest 2 (parens $ ptext SLIT("Use -fglasgow-exts to allow kind signatures")) ] + , nest 2 (parens $ ptext SLIT("Use -XKindSignatures to allow kind signatures")) ] badFamInstDecl tc_name = vcat [ ptext SLIT("Illegal family instance for") <+> @@ -1211,7 +1251,12 @@ polyTyErr ty = hang (ptext SLIT("Illegal polymorphic type in type instance") <> colon) 4 $ ppr ty +tyFamAppInIndexErr ty + = hang (ptext SLIT("Illegal type family application in type instance") <> + colon) 4 $ + ppr ty + emptyConDeclsErr tycon = sep [quotes (ppr tycon) <+> ptext SLIT("has no constructors"), - nest 2 $ ptext SLIT("(-fglasgow-exts permits this)")] + nest 2 $ ptext SLIT("(-XEmptyDataDecls permits this)")] \end{code}