remove empty dir
[ghc-hetmet.git] / ghc / compiler / prelude / PrelRules.lhs
index 3ab8d6e..9cdddc9 100644 (file)
@@ -20,7 +20,7 @@ module PrelRules ( primOpRules, builtinRules ) where
 #include "HsVersions.h"
 
 import CoreSyn
-import Id              ( mkWildId )
+import Id              ( mkWildId, isPrimOpId_maybe )
 import Literal         ( Literal(..), mkMachInt, mkMachWord
                        , literalType
                        , word2IntLit, int2WordLit
@@ -31,20 +31,19 @@ import Literal              ( Literal(..), mkMachInt, mkMachWord
                        , float2DoubleLit, double2FloatLit
                        )
 import PrimOp          ( PrimOp(..), primOpOcc )
--- gaw 2004
 import TysWiredIn      ( boolTy, trueDataConId, falseDataConId )
 import TyCon           ( tyConDataCons_maybe, isEnumerationTyCon, isNewTyCon )
 import DataCon         ( dataConTag, dataConTyCon, dataConWorkId, fIRST_TAG )
 import CoreUtils       ( cheapEqExpr, exprIsConApp_maybe )
 import Type            ( tyConAppTyCon, coreEqType )
-import OccName         ( occNameUserString)
+import OccName         ( occNameFS )
 import PrelNames       ( unpackCStringFoldrName, unpackCStringFoldrIdKey, hasKey,
                          eqStringName, unpackCStringIdKey )
 import Maybes          ( orElse )
 import Name            ( Name )
 import Outputable
 import FastString
-import CmdLineOpts      ( opt_SimplExcessPrecision )
+import StaticFlags      ( opt_SimplExcessPrecision )
 
 import DATA_BITS       ( Bits(..) )
 #if __GLASGOW_HASKELL__ >= 500
@@ -56,14 +55,19 @@ import DATA_WORD    ( Word64 )
 
 
 \begin{code}
-primOpRules :: PrimOp -> [CoreRule]
-primOpRules op = primop_rule op
+primOpRules :: PrimOp -> Name -> [CoreRule]
+primOpRules op op_name = primop_rule op
   where
-    op_name = mkFastString (occNameUserString (primOpOcc op))
-    op_name_case = op_name `appendFS` FSLIT("->case")
+    rule_name = occNameFS (primOpOcc op)
+    rule_name_case = rule_name `appendFS` FSLIT("->case")
 
        -- A useful shorthand
-    one_rule rule_fn = [BuiltinRule op_name rule_fn]
+    one_rule rule_fn = [BuiltinRule { ru_name = rule_name, 
+                                     ru_fn = op_name, 
+                                     ru_try = rule_fn }]
+    case_rule rule_fn = [BuiltinRule { ru_name = rule_name_case, 
+                                      ru_fn = op_name, 
+                                      ru_try = rule_fn }]
 
     -- ToDo:   something for integer-shift ops?
     --         NotOp
@@ -127,10 +131,10 @@ primOpRules op = primop_rule op
     primop_rule DoubleNegOp   = one_rule (oneLit  negOp)
 
        -- Relational operators
-    primop_rule IntEqOp  = [BuiltinRule op_name (relop (==)), BuiltinRule op_name_case (litEq True)]
-    primop_rule IntNeOp  = [BuiltinRule op_name (relop (/=)), BuiltinRule op_name_case (litEq False)]
-    primop_rule CharEqOp = [BuiltinRule op_name (relop (==)), BuiltinRule op_name_case (litEq True)]
-    primop_rule CharNeOp = [BuiltinRule op_name (relop (/=)), BuiltinRule op_name_case (litEq False)]
+    primop_rule IntEqOp  = one_rule (relop (==)) ++ case_rule (litEq True)
+    primop_rule IntNeOp  = one_rule (relop (/=)) ++ case_rule (litEq False)
+    primop_rule CharEqOp = one_rule (relop (==)) ++ case_rule (litEq True)
+    primop_rule CharNeOp = one_rule (relop (/=)) ++ case_rule (litEq False)
 
     primop_rule IntGtOp                = one_rule (relop (>))
     primop_rule IntGeOp                = one_rule (relop (>=))
@@ -381,12 +385,15 @@ For dataToTag#, we can reduce if either
        (b) the argument is a variable whose unfolding is a known constructor
 
 \begin{code}
-dataToTagRule [_, val_arg]
-  = case exprIsConApp_maybe val_arg of
-       Just (dc,_) -> ASSERT( not (isNewTyCon (dataConTyCon dc)) )
-                      Just (mkIntVal (toInteger (dataConTag dc - fIRST_TAG)))
+dataToTagRule [Type ty1, Var tag_to_enum `App` Type ty2 `App` tag]
+  | Just TagToEnumOp <- isPrimOpId_maybe tag_to_enum
+  , ty1 `coreEqType` ty2
+  = Just tag   -- dataToTag (tagToEnum x)   ==>   x
 
-       other       -> Nothing
+dataToTagRule [_, val_arg]
+  | Just (dc,_) <- exprIsConApp_maybe val_arg
+  = ASSERT( not (isNewTyCon (dataConTyCon dc)) )
+    Just (mkIntVal (toInteger (dataConTag dc - fIRST_TAG)))
 
 dataToTagRule other = Nothing
 \end{code}
@@ -398,11 +405,11 @@ dataToTagRule other = Nothing
 %************************************************************************
 
 \begin{code}
-builtinRules :: [(Name, CoreRule)]
+builtinRules :: [CoreRule]
 -- Rules for non-primops that can't be expressed using a RULE pragma
 builtinRules
-  = [ (unpackCStringFoldrName, BuiltinRule FSLIT("AppendLitString") match_append_lit),
-      (eqStringName,          BuiltinRule FSLIT("EqString") match_eq_string)
+  = [ BuiltinRule FSLIT("AppendLitString") unpackCStringFoldrName match_append_lit,
+      BuiltinRule FSLIT("EqString") eqStringName match_eq_string
     ]