[commit: ghc] master: Comments only (86a2ebf)

git at git.haskell.org git at git.haskell.org
Thu Aug 28 11:12:27 UTC 2014


Repository : ssh://git@git.haskell.org/ghc

On branch  : master
Link       : http://ghc.haskell.org/trac/ghc/changeset/86a2ebf8deae9505c7a183acf0847b3e53b43fee/ghc

>---------------------------------------------------------------

commit 86a2ebf8deae9505c7a183acf0847b3e53b43fee
Author: Simon Peyton Jones <simonpj at microsoft.com>
Date:   Fri May 23 09:16:00 2014 +0100

    Comments only


>---------------------------------------------------------------

86a2ebf8deae9505c7a183acf0847b3e53b43fee
 compiler/simplCore/SetLevels.lhs   |  3 +++
 compiler/specialise/Specialise.lhs | 35 ++++++++++++++++++++++++++---------
 compiler/stranal/WorkWrap.lhs      |  6 +++++-
 3 files changed, 34 insertions(+), 10 deletions(-)

diff --git a/compiler/simplCore/SetLevels.lhs b/compiler/simplCore/SetLevels.lhs
index c69687b..5f63096 100644
--- a/compiler/simplCore/SetLevels.lhs
+++ b/compiler/simplCore/SetLevels.lhs
@@ -352,6 +352,9 @@ lvlExpr env expr@(_, AnnLam {})
 lvlExpr env (_, AnnLet bind body)
   = do { (bind', new_env) <- lvlBind env bind
        ; body' <- lvlExpr new_env body
+           -- No point in going via lvlMFE here.  If the binding is alive
+           -- (mentioned in body), and the whole let-expression doesn't
+           -- float, then neither will the body
        ; return (Let bind' body') }
 
 lvlExpr env (_, AnnCase scrut@(scrut_fvs,_) case_bndr ty alts)
diff --git a/compiler/specialise/Specialise.lhs b/compiler/specialise/Specialise.lhs
index 5a2b8cd..ee8f693 100644
--- a/compiler/specialise/Specialise.lhs
+++ b/compiler/specialise/Specialise.lhs
@@ -1496,9 +1496,9 @@ Here is what we do with the InlinePragma of the original function
        (a) An INLINE pragma is transferred
        (b) An INLINABLE pragma is *not* transferred
 
-Why (a)? Previously the idea is that the point of INLINE was
-precisely to specialise the function at its call site, and that's not
-so important for the specialised copies.  But *pragma-directed*
+Why (a): transfer INLINE pragmas? The point of INLINE was precisely to
+specialise the function at its call site, and arguably that's not so
+important for the specialised copies.  BUT *pragma-directed*
 specialisation now takes place in the typechecker/desugarer, with
 manually specified INLINEs.  The specialisation here is automatic.
 It'd be very odd if a function marked INLINE was specialised (because
@@ -1509,16 +1509,33 @@ programmer said INLINE!
 You might wonder why we specialise INLINE functions at all.  After
 all they should be inlined, right?  Two reasons:
 
- * Even INLINE functions are sometimes not inlined, when
-   they aren't applied to interesting arguments.  But perhaps the type
-   arguments alone are enough to specialise (even though the args are too
-   boring to trigger inlining), and it's certainly better to call the
+ * Even INLINE functions are sometimes not inlined, when they aren't
+   applied to interesting arguments.  But perhaps the type arguments
+   alone are enough to specialise (even though the args are too boring
+   to trigger inlining), and it's certainly better to call the
    specialised version.
 
  * The RHS of an INLINE function might call another overloaded function,
    and we'd like to generate a specialised version of that function too.
-
-Why (b)? See Trac #4874 for persuasive examples.  Suppose we have
+   This actually happens a lot. Consider
+      replicateM_ :: (Monad m) => Int -> m a -> m ()
+      {-# INLINABLE replicateM_ #-}
+      replicateM_ d x ma = ...
+   The strictness analyser may transform to
+      replicateM_ :: (Monad m) => Int -> m a -> m ()
+      {-# INLINE replicateM_ #-}
+      replicateM_ d x ma = case x of I# x' -> $wreplicateM_ d x' ma
+
+      $wreplicateM_ :: (Monad m) => Int# -> m a -> m ()
+      {-# INLINABLE $wreplicateM_ #-}
+      $wreplicateM_ = ...
+   Now an importing module has a specialised call to replicateM_, say
+   (replicateM_ dMonadIO).  We certainly want to specialise $wreplicateM_!
+   This particular example had a huge effect on the call to replicateM_ 
+   in nofib/shootout/n-body.
+
+Why (b): discard INLINEABLE pragmas? See Trac #4874 for persuasive examples.
+Suppose we have
     {-# INLINABLE f #-}
     f :: Ord a => [a] -> Int
     f xs = letrec f' = ...f'... in f'
diff --git a/compiler/stranal/WorkWrap.lhs b/compiler/stranal/WorkWrap.lhs
index f845151..f7717ed 100644
--- a/compiler/stranal/WorkWrap.lhs
+++ b/compiler/stranal/WorkWrap.lhs
@@ -232,7 +232,7 @@ strictness.  Eg if we have
     g :: Int -> Int
     g x = f x x            -- Provokes a specialisation for f
 
-  module Bsr where
+  module Bar where
     import Foo
 
     h :: Int -> Int
@@ -246,6 +246,10 @@ more robust to give the wrapper an Activation of (ActiveAfter 0),
 so that it becomes active in an importing module at the same time that
 it appears in the first place in the defining module.
 
+At one stage I tried making the wrapper inlining always-active, and
+that had a very bad effect on nofib/imaginary/x2n1; a wrapper was
+inlined before the specialisation fired.
+
 \begin{code}
 tryWW   :: DynFlags
         -> FamInstEnvs



More information about the ghc-commits mailing list