[GHC] #10712: Regression: make TEST=exceptionsrun001 WAY=optasm is failing

GHC ghc-devs at haskell.org
Fri Jul 31 12:35:52 UTC 2015


#10712: Regression: make TEST=exceptionsrun001 WAY=optasm is failing
-------------------------------------+-------------------------------------
        Reporter:  thomie            |                   Owner:
            Type:  bug               |                  Status:  new
        Priority:  high              |               Milestone:  7.12.1
       Component:  Compiler          |                 Version:  7.11
      Resolution:                    |                Keywords:
Operating System:  Unknown/Multiple  |            Architecture:
                                     |  Unknown/Multiple
 Type of failure:  None/Unknown      |               Test Case:
                                     |  base/tests/exceptionsrun001
      Blocked By:                    |                Blocking:
 Related Tickets:                    |  Differential Revisions:
-------------------------------------+-------------------------------------
Changes (by simonpj):

 * cc: simonmar (added)


Comment:

 Bother. I totally missed that.

 I think it's reasonable that this should allow the exception to be raised
 somewhere else (imprecisely):
 {{{
 catch# (\s -> (raise# blah) `seq` blah2) (...) st
 }}}
 because `raise#` is in the pure world.  But `raiseIO#` is specifically
 intended to raise an exception precisely at the specified moment, so the
 new behaviour is unacceptable.

 Now I think about this more I'm also worried about
 {{{
   let r = \st -> raiseIO# blah st
   in
   catch (\st -> ...(r st)..) handler st
 }}}
 Now that I'm given `catch` a more aggressive strictness, I'll get a demand
 `C(S)` for `r`; that is, it is definitly called with one argument.  And so
 it is!  But the danger is that we'll feed `C(S)` into `r`'s rhs as the
 demand of the body, and say that that whole `let` will definitely diverge
 (which isn't true).

 However, we ''really'' want this function to be strict in `x`:
 {{{
 f x st = catch (\s -> case x of I# x' -> ...) handler st
 }}}
 Getting this strictness was the whole point of the offending commit:
 {{{
         Program           Size    Allocs   Runtime   Elapsed  TotalMem
 --------------------------------------------------------------------------------
             hpg          -0.4%     -2.9%     -0.9%     -1.0%     +0.0%
 reverse-complem          -0.4%    -10.9%    +10.7%    +10.9%     +0.0%
          simple          -0.3%     -0.0%    +26.2%    +26.2%     +3.7%
          sphere          -0.3%     -6.3%      0.09      0.09     +0.0%
 --------------------------------------------------------------------------------
             Min          -0.7%    -10.9%     -4.6%     -4.7%     -1.7%
             Max          -0.2%     +0.0%    +26.2%    +26.2%     +6.5%
  Geometric Mean          -0.4%     -0.3%     +2.1%     +2.1%     +0.1%
 }}}

 There's something very special about `catch`: it turns divergence into
 non-divergence.  (The strictness analyser treats divergence and exceptions
 identically.)

 I think #8598 is relevant.


 Bother bother.  I'm really not sure what to do.  Even if we revert, we
 should not revert all, just the strictness signatures for the `catch`
 primops.

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


More information about the ghc-tickets mailing list