[GHC] #13080: Memory leak caused by nested monadic loops

GHC ghc-devs at haskell.org
Fri Jan 13 06:12:22 UTC 2017


#13080: Memory leak caused by nested monadic loops
-------------------------------------+-------------------------------------
        Reporter:  Feuerbach         |                Owner:
            Type:  bug               |               Status:  new
        Priority:  normal            |            Milestone:  8.2.1
       Component:  Compiler          |              Version:  8.0.1
      Resolution:                    |             Keywords:
Operating System:  Unknown/Multiple  |         Architecture:
 Type of failure:  Runtime           |  Unknown/Multiple
  performance bug                    |            Test Case:
      Blocked By:                    |             Blocking:
 Related Tickets:                    |  Differential Rev(s):
       Wiki Page:                    |
-------------------------------------+-------------------------------------

Comment (by Feuerbach):

 David:

 If `foo` is marked as function-like by the programmer, `bar` and `baz` are
 recomputed on each invocation of `foo`. If `foo` is marked as value-like
 and is shared, `bar` and `baz` are shared, too. Furthermore, `bar` and
 `baz` could have their own annotations.

 Examples:

 {{{#!hs
 {-# FUNCTION_LIKE fib #-}
 fib = (fibs !!) where
   {- VALUE_LIKE fibs #-}
   fibs = 0 : 1 : zipWith (+) fibs (tail fibs)
 }}}

 {{{#!hs
 {-# VALUE_LIKE val #-}
 val = sum $ map f [1..10^6] where
   {-# FUNCTION_LIKE f #-}
   f = (+5) . (^2)
 }}}

 Now, what would FUNCTION_LIKE mean, exactly? In the `fib` example above,
 there
 can be two interpretations:

 1. Don't bother "remembering" the PAP `(!!) fibs`, but do remember
 something like `fibs !! n`.
 2. Don't even remember `fibs !! n`.

 The second interpretation is useful in cases like

 {{{#!hs
 mk_action :: Monad m => Int -> m ()
 mk_action = flip replicateM_ (return ())
 }}}

 where we may want to say, "don't bother to remember either the expansion
 or the result of mk_action".

 So, simple FUNCTION_LIKE can be ambiguous. What if we annotated functions
 with
 arities? Assigning an explicit arity to a function means that:

 1. ghc attempts to perform eta reductions or expansions to match the
 declared arity;
 2. ghc doesn't float things out of lambdas with declared arity >= 1.

 E.g. following Reid's example
 (https://ghc.haskell.org/trac/ghc/timeline?from=2017-01-07T14%3A42%3A24Z&precision=second),
 he could write
 {{{#!hs
 poll a = r >>= f
   where
     {-# ARITY 1 f #-}
     f _ -> poll a
 }}}

 and ghc would not transform `f` to `(let s = poll a in \_ -> s)`.

 And, of course, the original problem could be easily solved by annotating
 `poll`
 with the correct arity, as I point out in the blog post.

 It is also possible that these two things — forcing eta-expansion and not
 floating out local bindings — should be two different and orthogonal
 pragmass.
 What do you all think?

--
Ticket URL: <http://ghc.haskell.org/trac/ghc/ticket/13080#comment:17>
GHC <http://www.haskell.org/ghc/>
The Glasgow Haskell Compiler


More information about the ghc-tickets mailing list