X-Git-Url: http://git.megacz.com/?a=blobdiff_plain;f=ghc%2Fcompiler%2Ftypecheck%2FTcGenDeriv.lhs;h=ab7468341bc138641e1c02fc869675c4df30e132;hb=629b8c60bf0656a2a977e12a6f1f05c04dc00959;hp=41e366eecb05e15aa264c1ac7c3d63f71f70a5ec;hpb=f74e9e28c66072f93150fe026f87549e2f255128;p=ghc-hetmet.git diff --git a/ghc/compiler/typecheck/TcGenDeriv.lhs b/ghc/compiler/typecheck/TcGenDeriv.lhs index 41e366e..ab74683 100644 --- a/ghc/compiler/typecheck/TcGenDeriv.lhs +++ b/ghc/compiler/typecheck/TcGenDeriv.lhs @@ -28,13 +28,13 @@ module TcGenDeriv ( import HsSyn ( InPat(..), HsExpr(..), MonoBinds(..), Match(..), GRHSs(..), Stmt(..), HsLit(..), - HsBinds(..), StmtCtxt(..), HsType(..), - unguardedRHS, mkSimpleMatch, mkMonoBind, andMonoBindList + HsBinds(..), HsType(..), HsDoContext(..), + unguardedRHS, mkSimpleMatch, mkMonoBind, andMonoBindList, placeHolderType ) import RdrHsSyn ( mkHsOpApp, RdrNameMonoBinds, RdrNameHsExpr, RdrNamePat ) import RdrName ( RdrName, mkUnqual ) import BasicTypes ( RecFlag(..), Fixity(..), FixityDirection(..) - , maxPrecedence + , maxPrecedence, defaultFixity , Boxity(..) ) import FieldLabel ( fieldLabelName ) @@ -53,17 +53,16 @@ import SrcLoc ( generatedSrcLoc, SrcLoc ) import TyCon ( TyCon, isNewTyCon, tyConDataCons, isEnumerationTyCon, maybeTyConSingleCon, tyConFamilySize ) -import Type ( isUnLiftedType, isUnboxedType, Type ) +import TcType ( isUnLiftedType, tcEqType, Type ) import TysPrim ( charPrimTy, intPrimTy, wordPrimTy, addrPrimTy, floatPrimTy, doublePrimTy ) -import Util ( mapAccumL, zipEqual, zipWithEqual, +import Util ( mapAccumL, zipEqual, zipWithEqual, isSingleton, zipWith3Equal, nOfThem ) import Panic ( panic, assertPanic ) -import Maybes ( maybeToBool ) +import Maybes ( maybeToBool, orElse ) import Constants import List ( partition, intersperse ) -import Outputable ( pprPanic, ppr, pprTrace ) #if __GLASGOW_HASKELL__ >= 404 import GlaExts ( fromInt ) @@ -103,7 +102,7 @@ data Foo ... = N1 | N2 ... | Nn | O1 a b | O2 Int | O3 Double b b | ... (==) (O3 a1 b1 c1) (O3 a2 b2 c2) = a1 == a2 && b1 == b2 && c1 == c2 \end{verbatim} - Note: if we're comparing unboxed things, e.g., if \tr{a1} and + Note: if we're comparing unlifted things, e.g., if \tr{a1} and \tr{a2} are \tr{Float#}s, then we have to generate \begin{verbatim} case (a1 `eqFloat#` a2) of @@ -185,7 +184,7 @@ gen_Eq_binds tycon else -- calc. and compare the tags [([a_Pat, b_Pat], untag_Expr tycon [(a_RDR,ah_RDR), (b_RDR,bh_RDR)] - (cmp_tags_Expr eqH_Int_RDR ah_RDR bh_RDR true_Expr false_Expr))] + (genOpApp (HsVar ah_RDR) eqH_Int_RDR (HsVar bh_RDR)))] in mk_FunMonoBind tycon_loc eq_RDR ((map pats_etc nonnullary_cons) ++ rest) `AndMonoBinds` @@ -288,7 +287,7 @@ cmp_eq (O3 a1 b1 c1) (O3 a2 b2 c2) } \end{verbatim} - Again, we must be careful about unboxed comparisons. For example, + Again, we must be careful about unlifted comparisons. For example, if \tr{a1} and \tr{a2} were \tr{Int#}s in the 2nd example above, we'd need to generate: @@ -324,7 +323,7 @@ gen_Ord_binds tycon (if maybeToBool (maybeTyConSingleCon tycon) then -- cmp_eq_Expr ltTag_Expr eqTag_Expr gtTag_Expr a_Expr b_Expr --- Wierd. Was: case (cmp a b) of { LT -> LT; EQ -> EQ; GT -> GT } +-- Weird. Was: case (cmp a b) of { LT -> LT; EQ -> EQ; GT -> GT } cmp_eq_Expr a_Expr b_Expr else @@ -352,7 +351,7 @@ gen_Ord_binds tycon cmp_eq = mk_FunMonoBind tycon_loc cmp_eq_RDR - (if null nonnullary_cons && (length nullary_cons == 1) then + (if null nonnullary_cons && isSingleton nullary_cons then -- catch this specially to avoid warnings -- about overlapping patterns from the desugarer. let @@ -364,7 +363,7 @@ gen_Ord_binds tycon else map pats_etc nonnullary_cons ++ -- leave out wildcards to silence desugarer. - (if length tycon_data_cons == 1 then + (if isSingleton tycon_data_cons then [] else [([WildPatIn, WildPatIn], default_rhs)])) @@ -393,26 +392,6 @@ gen_Ord_binds tycon -- inexhaustive patterns | otherwise = eqTag_Expr -- Some nullary constructors; -- Tags are equal, no args => return EQ - -------------------------------------------------------------------- - -{- Not necessary: the default decls in PrelBase handle these - -defaulted = foldr1 AndMonoBinds [lt, le, ge, gt, max_, min_] - -lt = mk_easy_FunMonoBind generatedSrcLoc lt_RDR [a_Pat, b_Pat] [] ( - compare_Case true_Expr false_Expr false_Expr a_Expr b_Expr) -le = mk_easy_FunMonoBind generatedSrcLoc le_RDR [a_Pat, b_Pat] [] ( - compare_Case true_Expr true_Expr false_Expr a_Expr b_Expr) -ge = mk_easy_FunMonoBind generatedSrcLoc ge_RDR [a_Pat, b_Pat] [] ( - compare_Case false_Expr true_Expr true_Expr a_Expr b_Expr) -gt = mk_easy_FunMonoBind generatedSrcLoc gt_RDR [a_Pat, b_Pat] [] ( - compare_Case false_Expr false_Expr true_Expr a_Expr b_Expr) - -max_ = mk_easy_FunMonoBind generatedSrcLoc max_RDR [a_Pat, b_Pat] [] ( - compare_Case b_Expr a_Expr a_Expr a_Expr b_Expr) -min_ = mk_easy_FunMonoBind generatedSrcLoc min_RDR [a_Pat, b_Pat] [] ( - compare_Case a_Expr b_Expr b_Expr a_Expr b_Expr) --} \end{code} %************************************************************************ @@ -548,7 +527,7 @@ gen_Bounded_binds tycon = if isEnumerationTyCon tycon then min_bound_enum `AndMonoBinds` max_bound_enum else - ASSERT(length data_cons == 1) + ASSERT(isSingleton data_cons) min_bound_1con `AndMonoBinds` max_bound_1con where data_cons = tyConDataCons tycon @@ -621,7 +600,7 @@ instance ... Ix (Foo ...) where False }}} \end{verbatim} -(modulo suitable case-ification to handle the unboxed tags) +(modulo suitable case-ification to handle the unlifted tags) For a single-constructor type (NB: this includes all tuples), e.g., \begin{verbatim} @@ -667,7 +646,7 @@ gen_Ix_binds tycon in HsCase (genOpApp (HsVar dh_RDR) minusH_RDR (HsVar ah_RDR)) - [mkSimpleMatch [VarPatIn c_RDR] rhs Nothing tycon_loc] + [mkSimpleMatch [VarPatIn c_RDR] rhs placeHolderType tycon_loc] tycon_loc )) ) {-else-} ( @@ -719,7 +698,7 @@ gen_Ix_binds tycon where stmts = zipWith3Equal "single_con_range" mk_qual as_needed bs_needed cs_needed ++ - [ReturnStmt con_expr] + [ResultStmt con_expr tycon_loc] mk_qual a b c = BindStmt (VarPatIn c) (HsApp (HsVar range_RDR) @@ -908,7 +887,7 @@ gen_Read_binds get_fixity tycon | is_infix = let (h:t) = field_quals in (h:con_qual:t) | otherwise = con_qual:field_quals - stmts = quals ++ [ReturnStmt result_expr] + stmts = quals ++ [ResultStmt result_expr tycon_loc] {- c.f. Figure 18 in Haskell 1.1 report. @@ -1060,21 +1039,14 @@ getPrecedence :: (Name -> Maybe Fixity) -> Name -> Integer getPrecedence get_fixity nm = case get_fixity nm of Just (Fixity x _) -> fromInt x - other -> pprTrace "TcGenDeriv.getPrecedence" (ppr nm) defaultPrecedence + other -> defaultPrecedence isLRAssoc :: (Name -> Maybe Fixity) -> Name -> (Bool, Bool) isLRAssoc get_fixity nm = - case get_fixity nm of - Just (Fixity _ InfixN) -> (False, False) - Just (Fixity _ InfixR) -> (False, True) - Just (Fixity _ InfixL) -> (True, False) - other -> pprPanic "TcGenDeriv.isLRAssoc" (ppr nm) - -isInfixOccName :: String -> Bool -isInfixOccName str = - case str of - (':':_) -> True - _ -> False + case get_fixity nm `orElse` defaultFixity of + Fixity _ InfixN -> (False, False) + Fixity _ InfixR -> (False, True) + Fixity _ InfixL -> (True, False) \end{code} @@ -1089,7 +1061,7 @@ data Foo ... = ... con2tag_Foo :: Foo ... -> Int# tag2con_Foo :: Int -> Foo ... -- easier if Int, not Int# -maxtag_Foo :: Int -- ditto (NB: not unboxed) +maxtag_Foo :: Int -- ditto (NB: not unlifted) \end{verbatim} The `tags' here start at zero, hence the @fIRST_TAG@ (currently one) @@ -1183,8 +1155,8 @@ mk_FunMonoBind loc fun pats_and_exprs loc mk_match loc pats expr binds - = Match [] (map paren pats) Nothing - (GRHSs (unguardedRHS expr loc) binds Nothing) + = Match (map paren pats) Nothing + (GRHSs (unguardedRHS expr loc) binds placeHolderType) where paren p@(VarPatIn _) = p paren other_p = ParPatIn other_p @@ -1197,10 +1169,6 @@ mk_easy_App f xs = foldl HsApp (HsVar f) (map HsVar xs) ToDo: Better SrcLocs. \begin{code} -compare_Case :: - RdrNameHsExpr -> RdrNameHsExpr -> RdrNameHsExpr - -> RdrNameHsExpr -> RdrNameHsExpr - -> RdrNameHsExpr compare_gen_Case :: RdrName -> RdrNameHsExpr -> RdrNameHsExpr -> RdrNameHsExpr @@ -1212,22 +1180,21 @@ careful_compare_Case :: -- checks for primitive types... -> RdrNameHsExpr -> RdrNameHsExpr -> RdrNameHsExpr -compare_Case = compare_gen_Case compare_RDR cmp_eq_Expr a b = HsApp (HsApp (HsVar cmp_eq_RDR) a) b -- Was: compare_gen_Case cmp_eq_RDR compare_gen_Case fun lt eq gt a b = HsCase (HsPar (HsApp (HsApp (HsVar fun) a) b)) {-of-} - [mkSimpleMatch [ConPatIn ltTag_RDR []] lt Nothing generatedSrcLoc, - mkSimpleMatch [ConPatIn eqTag_RDR []] eq Nothing generatedSrcLoc, - mkSimpleMatch [ConPatIn gtTag_RDR []] gt Nothing generatedSrcLoc] + [mkSimpleMatch [ConPatIn ltTag_RDR []] lt placeHolderType generatedSrcLoc, + mkSimpleMatch [ConPatIn eqTag_RDR []] eq placeHolderType generatedSrcLoc, + mkSimpleMatch [ConPatIn gtTag_RDR []] gt placeHolderType generatedSrcLoc] generatedSrcLoc careful_compare_Case ty lt eq gt a b - = if not (isUnboxedType ty) then + | not (isUnLiftedType ty) = compare_gen_Case compare_RDR lt eq gt a b - - else -- we have to do something special for primitive things... + | otherwise = + -- we have to do something special for primitive things... HsIf (genOpApp a relevant_eq_op b) eq (HsIf (genOpApp a relevant_lt_op b) lt gt generatedSrcLoc) @@ -1240,7 +1207,7 @@ assoc_ty_id tyids ty = if null res then panic "assoc_ty" else head res where - res = [id | (ty',id) <- tyids, ty == ty'] + res = [id | (ty',id) <- tyids, ty `tcEqType` ty'] eq_op_tbl = [(charPrimTy, eqH_Char_RDR) @@ -1270,13 +1237,14 @@ append_Expr a b = genOpApp a append_RDR b ----------------------------------------------------------------------- eq_Expr :: Type -> RdrNameHsExpr -> RdrNameHsExpr -> RdrNameHsExpr -eq_Expr ty a b - = if not (isUnboxedType ty) then - genOpApp a eq_RDR b - else -- we have to do something special for primitive things... - genOpApp a relevant_eq_op b - where - relevant_eq_op = assoc_ty_id eq_op_tbl ty +eq_Expr ty a b = genOpApp a eq_op b + where + eq_op + | not (isUnLiftedType ty) = eq_RDR + | otherwise = + -- we have to do something special for primitive things... + assoc_ty_id eq_op_tbl ty + \end{code} \begin{code} @@ -1284,7 +1252,7 @@ untag_Expr :: TyCon -> [(RdrName, RdrName)] -> RdrNameHsExpr -> RdrNameHsExpr untag_Expr tycon [] expr = expr untag_Expr tycon ((untag_this, put_tag_here) : more) expr = HsCase (HsPar (HsApp (con2tag_Expr tycon) (HsVar untag_this))) {-of-} - [mkSimpleMatch [VarPatIn put_tag_here] (untag_Expr tycon more expr) Nothing generatedSrcLoc] + [mkSimpleMatch [VarPatIn put_tag_here] (untag_Expr tycon more expr) placeHolderType generatedSrcLoc] generatedSrcLoc cmp_tags_Expr :: RdrName -- Comparison op