[project @ 2001-05-04 08:10:30 by simonpj]
[ghc-hetmet.git] / ghc / compiler / coreSyn / CoreSyn.lhs
index 6a574c4..a69c239 100644 (file)
@@ -15,7 +15,7 @@ module CoreSyn (
        mkConApp, 
        varToCoreExpr,
 
-       isTyVar, isId, isLocalVar, mustHaveLocalBinding,
+       isTyVar, isId, 
        bindersOf, bindersOfBinds, rhssOfBind, rhssOfAlts, 
        collectBinders, collectTyBinders, collectValBinders, collectTyAndValBinders,
        collectArgs, collectBindersIgnoringNotes,
@@ -35,7 +35,8 @@ module CoreSyn (
        seqRules, seqExpr, seqExprs, seqUnfolding,
 
        -- Annotated expressions
-       AnnExpr, AnnExpr'(..), AnnBind(..), AnnAlt, deAnnotate, deAnnotate',
+       AnnExpr, AnnExpr'(..), AnnBind(..), AnnAlt, 
+       deAnnotate, deAnnotate', deAnnAlt,
 
        -- Core rules
        CoreRules(..),  -- Representation needed by friends
@@ -104,30 +105,34 @@ data Note
 
   | InlineMe           -- Instructs simplifer to treat the enclosed expression
                        -- as very small, and inline it at its call sites
+
+-- NOTE: we also treat expressions wrapped in InlineMe as
+-- 'cheap' and 'dupable' (in the sense of exprIsCheap, exprIsDupable)
+-- What this means is that we obediently inline even things that don't
+-- look like valuse.  This is sometimes important:
+--     {-# INLINE f #-}
+--     f = g . h
+-- Here, f looks like a redex, and we aren't going to inline (.) because it's
+-- inside an INLINE, so it'll stay looking like a redex.  Nevertheless, we 
+-- should inline f even inside lambdas.  In effect, we should trust the programmer.
 \end{code}
 
+INVARIANTS:
 
-%************************************************************************
-%*                                                                     *
-\subsection{isLocalVar}
-%*                                                                     *
-%************************************************************************
+* The RHS of a letrec, and the RHSs of all top-level lets,
+  must be of LIFTED type.
 
-@isLocalVar@ returns True of all TyVars, and of Ids that are defined in 
-this module and are not constants like data constructors and record selectors.
-These are the variables that we need to pay attention to when finding free
-variables, or doing dependency analysis.
+* The RHS of a let, may be of UNLIFTED type, but only if the expression 
+  is ok-for-speculation.  This means that the let can be floated around 
+  without difficulty.  e.g.
+       y::Int# = x +# 1#       ok
+       y::Int# = fac 4#        not ok [use case instead]
 
-\begin{code}
-isLocalVar :: Var -> Bool
-isLocalVar v = isTyVar v || isLocalId v
-\end{code}
+* The argument of an App can be of any type.
 
-\begin{code}
-mustHaveLocalBinding :: Var -> Bool
--- True <=> the variable must have a binding in this module
-mustHaveLocalBinding v = isTyVar v || (isLocalId v && not (hasNoBinding v))
-\end{code}
+* The simplifier tries to ensure that if the RHS of a let is a constructor
+  application, its arguments are trivial, so that the constructor can be
+  inlined vigorously.
 
 
 %************************************************************************
@@ -478,6 +483,7 @@ coreExprCc other               = noCostCentre
 \end{code}
 
 
+
 %************************************************************************
 %*                                                                     *
 \subsection{Predicates}
@@ -595,7 +601,8 @@ deAnnotate' (AnnLet bind body)
 
 deAnnotate' (AnnCase scrut v alts)
   = Case (deAnnotate scrut) v (map deAnnAlt alts)
-  where
-    deAnnAlt (con,args,rhs) = (con,args,deAnnotate rhs)
+
+deAnnAlt :: AnnAlt bndr annot -> Alt bndr
+deAnnAlt (con,args,rhs) = (con,args,deAnnotate rhs)
 \end{code}