[project @ 1996-03-19 08:58:34 by partain]
[ghc-hetmet.git] / ghc / compiler / simplStg / LambdaLift.lhs
index 5e406d1..40d180a 100644 (file)
@@ -10,14 +10,13 @@ module LambdaLift ( liftProgram ) where
 
 import StgSyn
 
-import AbsUniType      ( mkForallTy, splitForalls, glueTyArgs,
-                         UniType, RhoType(..), TauType(..)
+import Type            ( mkForallTy, splitForalls, glueTyArgs,
+                         Type, RhoType(..), TauType(..)
                        )
 import Bag
-import Id              ( mkSysLocal, getIdUniType, addIdArity, Id )
-import IdEnv
+import Id              ( mkSysLocal, idType, addIdArity, Id )
 import Maybes
-import SplitUniq
+import UniqSupply
 import SrcLoc          ( mkUnknownSrcLoc, SrcLoc )
 import UniqSet
 import Util
@@ -32,8 +31,8 @@ supercombinators on a selective basis:
 * Non-recursive bindings whose RHS is a lambda abstractions are lifted,
   provided all the occurrences of the bound variable is in a function
   postition.  In this example, f will be lifted:
-       
-       let     
+
+       let
          f = \x -> e
        in
        ..(f a1)...(f a2)...
@@ -47,7 +46,7 @@ supercombinators on a selective basis:
 
   But in this case, f won't be lifted:
 
-       let     
+       let
          f = \x -> e
        in
        ..(g f)...(f a2)...
@@ -58,22 +57,22 @@ supercombinators on a selective basis:
 
        let
          f = $f p q r
-       in 
+       in
        ..(g f)...($f p q r a2)..
 
   so it might as well be the original lambda abstraction.
 
   We also do not lift if the function has an occurrence with no arguments, e.g.
-  
-        let
-          f = \x -> e
-        in f
-        
+
+       let
+         f = \x -> e
+       in f
+
   as this form is more efficient than if we create a partial application
 
   $f p q r x = e      -- Supercombinator
 
-        f p q r
+       f p q r
 
 * Recursive bindings *all* of whose RHSs are lambda abstractions are
   lifted iff
@@ -81,7 +80,7 @@ supercombinators on a selective basis:
        - there aren't ``too many'' free variables.
 
   Same reasoning as before for the function-position stuff.  The ``too many
-  free variable'' part comes from considering the (potentially many) 
+  free variable'' part comes from considering the (potentially many)
   recursive calls, which may now have lots of free vars.
 
 Recent Observations:
@@ -93,19 +92,19 @@ Recent Observations:
 * We do not lambda lift if the function has at least one occurrence
   without any arguments. This caused lots of problems. Ex:
   h = \ x -> ... let y = ...
-                 in let let f = \x -> ...y...
-                    in f
-  ==> 
+                in let let f = \x -> ...y...
+                   in f
+  ==>
   f = \y x -> ...y...
   h = \ x -> ... let y = ...
-                 in f y
-  
+                in f y
+
   now f y is a partial application, so it will be updated, and this
   is Bad.
 
 
 --- NOT RELEVANT FOR STG ----
-* All ``lone'' lambda abstractions are lifted.  Notably this means lambda 
+* All ``lone'' lambda abstractions are lifted.  Notably this means lambda
   abstractions:
        - in a case alternative: case e of True -> (\x->b)
        - in the body of a let:  let x=e in (\y->b)
@@ -118,11 +117,11 @@ Recent Observations:
 %************************************************************************
 
 \begin{code}
-liftProgram :: SplitUniqSupply -> [PlainStgBinding] -> [PlainStgBinding]
+liftProgram :: UniqSupply -> [StgBinding] -> [StgBinding]
 liftProgram us prog = concat (runLM Nothing us (mapLM liftTopBind prog))
 
 
-liftTopBind :: PlainStgBinding -> LiftM [PlainStgBinding]
+liftTopBind :: StgBinding -> LiftM [StgBinding]
 liftTopBind (StgNonRec id rhs)
   = dontLiftRhs rhs            `thenLM` \ (rhs', rhs_info) ->
     returnLM (getScBinds rhs_info ++ [StgNonRec id rhs'])
@@ -138,20 +137,20 @@ liftTopBind (StgRec pairs)
 
 
 \begin{code}
-liftExpr :: PlainStgExpr
-        -> LiftM (PlainStgExpr, LiftInfo)
+liftExpr :: StgExpr
+        -> LiftM (StgExpr, LiftInfo)
 
 
-liftExpr expr@(StgConApp con args lvs) = returnLM (expr, emptyLiftInfo)
-liftExpr expr@(StgPrimApp op args lvs) = returnLM (expr, emptyLiftInfo)
+liftExpr expr@(StgCon con args lvs) = returnLM (expr, emptyLiftInfo)
+liftExpr expr@(StgPrim op args lvs) = returnLM (expr, emptyLiftInfo)
 
-liftExpr expr@(StgApp (StgLitAtom lit) args lvs) = returnLM (expr, emptyLiftInfo)
-liftExpr expr@(StgApp (StgVarAtom v)  args lvs)
+liftExpr expr@(StgApp (StgLitArg lit) args lvs) = returnLM (expr, emptyLiftInfo)
+liftExpr expr@(StgApp (StgVarArg v)  args lvs)
   = lookup v           `thenLM` \ ~(sc, sc_args) ->    -- NB the ~.  We don't want to
                                                        -- poke these bindings too early!
-    returnLM (StgApp (StgVarAtom sc) (map StgVarAtom sc_args ++ args) lvs,
+    returnLM (StgApp (StgVarArg sc) (map StgVarArg sc_args ++ args) lvs,
              emptyLiftInfo)
-       -- The lvs field is probably wrong, but we reconstruct it 
+       -- The lvs field is probably wrong, but we reconstruct it
        -- anyway following lambda lifting
 
 liftExpr (StgCase scrut lv1 lv2 uniq alts)
@@ -191,8 +190,8 @@ lambda anyway.
 liftExpr (StgLetNoEscape _ _ (StgNonRec binder rhs) body)
   = dontLiftRhs rhs    `thenLM` \ (rhs', rhs_info) ->
     liftExpr body      `thenLM` \ (body', body_info) ->
-    returnLM (StgLet (StgNonRec binder rhs') body', 
-              rhs_info `unionLiftInfo` body_info)
+    returnLM (StgLet (StgNonRec binder rhs') body',
+             rhs_info `unionLiftInfo` body_info)
 
 liftExpr (StgLetNoEscape _ _ (StgRec pairs) body)
   = liftExpr body                      `thenLM` \ (body', body_info) ->
@@ -208,26 +207,26 @@ liftExpr (StgLet (StgNonRec binder rhs) body)
   | not (isLiftable rhs)
   = dontLiftRhs rhs    `thenLM` \ (rhs', rhs_info) ->
     liftExpr body      `thenLM` \ (body', body_info) ->
-    returnLM (StgLet (StgNonRec binder rhs') body', 
-              rhs_info `unionLiftInfo` body_info)
+    returnLM (StgLet (StgNonRec binder rhs') body',
+             rhs_info `unionLiftInfo` body_info)
 
   | otherwise  -- It's a lambda
   =    -- Do the body of the let
     fixLM (\ ~(sc_inline, _, _) ->
       addScInlines [binder] [sc_inline]        (
-       liftExpr body   
+       liftExpr body
       )                        `thenLM` \ (body', body_info) ->
 
        -- Deal with the RHS
-      dontLiftRhs rhs          `thenLM` \ (rhs', rhs_info) -> 
+      dontLiftRhs rhs          `thenLM` \ (rhs', rhs_info) ->
 
        -- All occurrences in function position, so lambda lift
       getFinalFreeVars (rhsFreeVars rhs)    `thenLM` \ final_free_vars ->
 
-      mkScPieces final_free_vars (binder,rhs') `thenLM` \ (sc_inline, sc_bind) -> 
+      mkScPieces final_free_vars (binder,rhs') `thenLM` \ (sc_inline, sc_bind) ->
 
-      returnLM (sc_inline, 
-               body', 
+      returnLM (sc_inline,
+               body',
                nonRecScBind rhs_info sc_bind `unionLiftInfo` body_info)
 
     )                  `thenLM` \ (_, expr', final_info) ->
@@ -235,7 +234,7 @@ liftExpr (StgLet (StgNonRec binder rhs) body)
     returnLM (expr', final_info)
 
 liftExpr (StgLet (StgRec pairs) body)
---[Andre-testing]  
+--[Andre-testing]
   | not (all isLiftableRec rhss)
   = liftExpr body                      `thenLM` \ (body', body_info) ->
     mapAndUnzipLM dontLiftRhs rhss     `thenLM` \ (rhss', rhs_infos) ->
@@ -250,11 +249,11 @@ liftExpr (StgLet (StgRec pairs) body)
       liftExpr body                    `thenLM` \ (body', body_info) ->
       mapAndUnzipLM dontLiftRhs rhss   `thenLM` \ (rhss', rhs_infos) ->
       let
-       -- Find the free vars of all the rhss, 
+       -- Find the free vars of all the rhss,
        -- excluding the binders themselves.
        rhs_free_vars = unionManyUniqSets (map rhsFreeVars rhss)
-                       `minusUniqSet`
-                       mkUniqSet binders
+                       `minusUniqSet`
+                       mkUniqSet binders
 
        rhs_info      = unionLiftInfos rhs_infos
       in
@@ -262,8 +261,8 @@ liftExpr (StgLet (StgRec pairs) body)
 
       mapAndUnzipLM (mkScPieces final_free_vars) (binders `zip` rhss')
                                        `thenLM` \ (sc_inlines, sc_pairs) ->
-      returnLM (sc_inlines, 
-               body', 
+      returnLM (sc_inlines,
+               body',
                recScBind rhs_info sc_pairs `unionLiftInfo` body_info)
 
     ))                 `thenLM` \ (_, expr', final_info) ->
@@ -283,9 +282,9 @@ A binding is liftable if it's a *function* (args not null) and never
 occurs in an argument position.
 
 \begin{code}
-isLiftable :: PlainStgRhs -> Bool
+isLiftable :: StgRhs -> Bool
 
-isLiftable (StgRhsClosure _ (StgBinderInfo arg_occ _ _ _ unapplied_occ) fvs _ args _) 
+isLiftable (StgRhsClosure _ (StgBinderInfo arg_occ _ _ _ unapplied_occ) fvs _ args _)
 
   -- Experimental evidence suggests we should lift only if we will be
   -- abstracting up to 4 fvs.
@@ -294,12 +293,12 @@ isLiftable (StgRhsClosure _ (StgBinderInfo arg_occ _ _ _ unapplied_occ) fvs _ ar
         unapplied_occ  ||      -- Has an occ with no args at all
         arg_occ        ||      -- Occurs in arg position
         length fvs > 4         -- Too many free variables
-        )
+       )
     then {-trace ("LL: " ++ show (length fvs))-} True
     else False
 isLiftable other_rhs = False
 
-isLiftableRec :: PlainStgRhs -> Bool
+isLiftableRec :: StgRhs -> Bool
 
 -- this is just the same as for non-rec, except we only lift to
 -- abstract up to 1 argument this avoids undoing Static Argument
@@ -307,9 +306,9 @@ isLiftableRec :: PlainStgRhs -> Bool
 
 {- Andre's longer comment about isLiftableRec: 1996/01:
 
-A rec binding is "liftable" (according to our heuristics) if: 
-* It is a function, 
-* all occurrences have arguments, 
+A rec binding is "liftable" (according to our heuristics) if:
+* It is a function,
+* all occurrences have arguments,
 * does not occur in an argument position and
 * has up to *2* free variables (including the rec binding variable
   itself!)
@@ -325,17 +324,17 @@ static arguments, if we change things there we should change things
 here).
 -}
 
-isLiftableRec (StgRhsClosure _ (StgBinderInfo arg_occ _ _ _ unapplied_occ) fvs _ args _) 
+isLiftableRec (StgRhsClosure _ (StgBinderInfo arg_occ _ _ _ unapplied_occ) fvs _ args _)
   = if not (null args  ||      -- Not a function
         unapplied_occ  ||      -- Has an occ with no args at all
         arg_occ        ||      -- Occurs in arg position
         length fvs > 2         -- Too many free variables
-        )
+       )
     then {-trace ("LLRec: " ++ show (length fvs))-} True
     else False
 isLiftableRec other_rhs = False
 
-rhsFreeVars :: PlainStgRhs -> IdSet
+rhsFreeVars :: StgRhs -> IdSet
 rhsFreeVars (StgRhsClosure _ _ fvs _ _ _) = mkUniqSet fvs
 rhsFreeVars other                        = panic "rhsFreeVars"
 \end{code}
@@ -346,21 +345,21 @@ definitions where we've decided *not* to lift: for example, top-level
 ones or mutually-recursive ones where not all are lambdas.
 
 \begin{code}
-dontLiftRhs :: PlainStgRhs -> LiftM (PlainStgRhs, LiftInfo)
+dontLiftRhs :: StgRhs -> LiftM (StgRhs, LiftInfo)
 
 dontLiftRhs rhs@(StgRhsCon cc v args) = returnLM (rhs, emptyLiftInfo)
 
-dontLiftRhs (StgRhsClosure cc bi fvs upd args body) 
+dontLiftRhs (StgRhsClosure cc bi fvs upd args body)
   = liftExpr body      `thenLM` \ (body', body_info) ->
     returnLM (StgRhsClosure cc bi fvs upd args body', body_info)
 \end{code}
 
 \begin{code}
 mkScPieces :: IdSet            -- Extra args for the supercombinator
-          -> (Id, PlainStgRhs) -- The processed RHS and original Id
+          -> (Id, StgRhs)      -- The processed RHS and original Id
           -> LiftM ((Id,[Id]),         -- Replace abstraction with this;
                                                -- the set is its free vars
-                    (Id,PlainStgRhs))  -- Binding for supercombinator
+                    (Id,StgRhs))       -- Binding for supercombinator
 
 mkScPieces extra_arg_set (id, StgRhsClosure cc bi _ upd args body)
   = ASSERT( n_args > 0 )
@@ -377,8 +376,8 @@ mkScPieces extra_arg_set (id, StgRhsClosure cc bi _ upd args body)
     arity      = n_args + length extra_args
 
        -- Construct the supercombinator type
-    type_of_original_id = getIdUniType id
-    extra_arg_tys       = map getIdUniType extra_args
+    type_of_original_id = idType id
+    extra_arg_tys       = map idType extra_args
     (tyvars, rest)      = splitForalls type_of_original_id
     sc_ty              = mkForallTy tyvars (glueTyArgs extra_arg_tys rest)
 
@@ -396,10 +395,10 @@ The monad is used only to distribute global stuff, and the unique supply.
 
 \begin{code}
 type LiftM a =  LiftFlags
-            -> SplitUniqSupply
+            -> UniqSupply
             -> (IdEnv                          -- Domain = candidates for lifting
                       (Id,                     -- The supercombinator
-                       [Id])                   -- Args to apply it to
+                       [Id])                   -- Args to apply it to
                 )
             -> a
 
@@ -408,7 +407,7 @@ type LiftFlags = Maybe Int  -- No of fvs reqd to float recursive
                                -- binding; Nothing == infinity
 
 
-runLM :: LiftFlags -> SplitUniqSupply -> LiftM a -> a
+runLM :: LiftFlags -> UniqSupply -> LiftM a -> a
 runLM flags us m = m flags us nullIdEnv
 
 thenLM :: LiftM a -> (a -> LiftM b) -> LiftM b
@@ -439,7 +438,7 @@ mapAndUnzipLM f (a:as) = f a                        `thenLM` \ (b,c) ->
 \end{code}
 
 \begin{code}
-newSupercombinator :: UniType 
+newSupercombinator :: Type
                   -> Int               -- Arity
                   -> LiftM Id
 
@@ -448,10 +447,10 @@ newSupercombinator ty arity ci us idenv
     `addIdArity` arity
        -- ToDo: rm the addIdArity?  Just let subsequent stg-saturation pass do it?
   where
-    uniq = getSUnique us
-    
+    uniq = getUnique us
+
 lookup :: Id -> LiftM (Id,[Id])
-lookup v ci us idenv 
+lookup v ci us idenv
   = case lookupIdEnv idenv v of
        Just result -> result
        Nothing     -> (v, [])
@@ -488,7 +487,7 @@ addScInlines ids values m ci us idenv
 
 getFinalFreeVars :: IdSet -> LiftM IdSet
 
-getFinalFreeVars free_vars ci us idenv 
+getFinalFreeVars free_vars ci us idenv
   = unionManyUniqSets (map munge_it (uniqSetToList free_vars))
   where
     munge_it :: Id -> IdSet    -- Takes a free var and maps it to the "real"
@@ -496,7 +495,7 @@ getFinalFreeVars free_vars ci us idenv
     munge_it id = case lookupIdEnv idenv id of
                        Just (_, args) -> mkUniqSet args
                        Nothing        -> singletonUniqSet id
-  
+
 \end{code}
 
 
@@ -507,21 +506,21 @@ getFinalFreeVars free_vars ci us idenv
 %************************************************************************
 
 \begin{code}
-type LiftInfo = Bag PlainStgBinding    -- Float to top
+type LiftInfo = Bag StgBinding -- Float to top
 
 emptyLiftInfo = emptyBag
-                       
+
 unionLiftInfo :: LiftInfo -> LiftInfo -> LiftInfo
 unionLiftInfo binds1 binds2 = binds1 `unionBags` binds2
 
 unionLiftInfos :: [LiftInfo] -> LiftInfo
 unionLiftInfos infos = foldr unionLiftInfo emptyLiftInfo infos
 
-mkScInfo :: PlainStgBinding -> LiftInfo
+mkScInfo :: StgBinding -> LiftInfo
 mkScInfo bind = unitBag bind
 
 nonRecScBind :: LiftInfo               -- From body of supercombinator
-            -> (Id, PlainStgRhs)       -- Supercombinator and its rhs
+            -> (Id, StgRhs)    -- Supercombinator and its rhs
             -> LiftInfo
 nonRecScBind binds (sc_id,sc_rhs) = binds `snocBag` (StgNonRec sc_id sc_rhs)
 
@@ -531,22 +530,22 @@ nonRecScBind binds (sc_id,sc_rhs) = binds `snocBag` (StgNonRec sc_id sc_rhs)
 -- So we flatten the whole lot into a single recursive group.
 
 recScBind :: LiftInfo                  -- From body of supercombinator
-          -> [(Id,PlainStgRhs)]        -- Supercombinator rhs
+          -> [(Id,StgRhs)]     -- Supercombinator rhs
           -> LiftInfo
 
 recScBind binds pairs = unitBag (co_rec_ify (StgRec pairs : bagToList binds))
 
-co_rec_ify :: [PlainStgBinding] -> PlainStgBinding
+co_rec_ify :: [StgBinding] -> StgBinding
 co_rec_ify binds = StgRec (concat (map f binds))
   where
     f (StgNonRec id rhs) = [(id,rhs)]
     f (StgRec pairs)     = pairs
 
 
-getScBinds :: LiftInfo -> [PlainStgBinding]
+getScBinds :: LiftInfo -> [StgBinding]
 getScBinds binds = bagToList binds
 
-looksLikeSATRhs [(f,StgRhsClosure _ _ _ _ ls _)] (StgApp (StgVarAtom f') args _)
+looksLikeSATRhs [(f,StgRhsClosure _ _ _ _ ls _)] (StgApp (StgVarArg f') args _)
   = (f == f') && (length args == length ls)
 looksLikeSATRhs _ _ = False
 \end{code}