[GHC] #917: -O introduces space leak

GHC trac at galois.com
Thu Sep 28 19:38:21 EDT 2006


#917: -O introduces space leak
----------------------------------------+-----------------------------------
    Reporter:  claus.reinke at talk21.com  |        Owner:         
        Type:  bug                      |       Status:  new    
    Priority:  normal                   |    Milestone:         
   Component:  Compiler                 |      Version:  6.5    
    Severity:  normal                   |     Keywords:         
          Os:  Unknown                  |   Difficulty:  Unknown
Architecture:  Unknown                  |  
----------------------------------------+-----------------------------------
consider the following variant of a popular space problem
 {{{
 initlast :: (()->[a]) -> ([a], a)
 initlast xs = (init (xs ()), last (xs ()))

 main = print $ case initlast (\()->[0..1000000000]) of
                  (init, last) -> (length init, last)
 }}}

 the long list has been wrapped in abstractions to avoid
 sharing, gaining constant space processing rather than
 the space leak in the original code - see

 http://www.haskell.org/pipermail/haskell-cafe/2006-September/018447.html

 http://www.haskell.org/pipermail/haskell-cafe/2006-September/018464.html

 this works nicely if compiled without -O, but unfortunately,
 -O reintroduces the space leak (apparently lifting and sharing
 the common and space-expensive subexpression).

 1. I didn't see a ticket for this issue, so I wanted to record the example

 2. avoiding sharing isn't always possible, so it would be nice if one
 could
 "bypass" sharing in such cases. in the old g-machine, that might have
 been as simple as introducing a pragma that tells the compiler to omit
 the update after the eval in the code for some subexpression (so the
 original application node would not be overwritten by the space-expensive
 result, trading time for space). is there a chance for a similar trick
 in GHC? so one might write code like this (handwaving:-):
 {{{
 initlast :: [a] -> ([a], a)
 initlast xs = (init ({-# COPY #-} xs), last ({-# COPY #-} xs))

 main = print $ case initlast [0..1000000000] of
                  (init, last) -> (length init, last)
 }}}

-- 
Ticket URL: <http://hackage.haskell.org/trac/ghc/ticket/917>
GHC <http://www.haskell.org/ghc/>
The Glasgow Haskell Compiler


More information about the Glasgow-haskell-bugs mailing list