Need a bit more case-of-case in Inital Phase
In the nofib
simple benchmark we have
polynomial degree ... = ....(\xyz. foldr k z [1..degree])....
By the time we get to FloatOut we have (roughly)
polynomial degree ... = ....(\xyz. foldr k z (case degree of I# d# -> build (enum 1# d#))...
Do we float that
[1..degree] out of the
\xyz? Doing so kills fusion; but it shares the
[1..degree] which in general may be a big win.
General principle: trust the programmer: if fusion can happen, do it, even at the cost of floating.
- Fusion does not happen in
casegets in between the
casedoes not get pulled out of the strict argument because
sm_case_caseis off in
- We don't float because of the bizarre
Case [MFEs]in SetLevels (c.f. #19001). It's a strict argument position, headed by a
caseso we don't float. I'm trying to get rid of this strange special case.
- So in the subsequent Phase 2 simplification (with
sm_case_caseon) fusion can happen, quite coincidentally.
So in HEAD we get fusion, but only by a fluke; and !7997 (merged) removes some of the bizarreness, so the fluke no longer happens.
As a result,
simple allocates 28% more.
I think the right solution is to make more fusion happen in
InitialPhase. Maybe we can make
sm_case_case switch off case-of-case only for multi-alternative cases. I think those are the ones that are the true target of
sm_case_case=False (a sadly un-documented design).