[project @ 2001-06-25 08:08:32 by simonpj]
authorsimonpj <unknown>
Mon, 25 Jun 2001 08:08:32 +0000 (08:08 +0000)
committersimonpj <unknown>
Mon, 25 Jun 2001 08:08:32 +0000 (08:08 +0000)
commit3622a7de695b4cb795171c8cb59bfe41c7f4d85f
tree9d01759eec9e96c4186eb98460f998933367c0c8
parenta12bed5371650117aab631ac032fb1b525570c00
[project @ 2001-06-25 08:08:32 by simonpj]
---------------------------
Add a new case optimisation
---------------------------

I found that lib/std/PrelCError had a case-expression that was
generating terrible code.   Something like this

x | p `is` 1 -> e1
  | p `is` 2 -> e2
...etc...

where @is@ was something like

p `is` n = p /= (-1) && p == n

This gave rise to a horrible sequence of cases

case p of
  (-1) -> $j p
  1    -> e1
  DEFAULT -> $j p

and similarly in cascade for all the join points!

Solution: add the following transformation:

case e of =====>     case e of
  C _ -> <expr>      D v -> ....v....
  D v -> ....v....      DEFAULT -> <expr>
  DEFAULT -> <expr>

The point is that we merge common RHSs, at least for the DEFAULT case.
[One could do something more elaborate but I've never seen it needed.]

This transformation is implemented in SimplUtils.mkCase

*** WARNING ***
To make this transformation easy, I have switched the convention
for DEFAULT clauses.  They must now occur FIRST in the list of
alternatives for a Core case expression.  (The semantics is
unchanged: they still are a catch-all case.)

The reason is that DEFAULT clauses sometimes need special treatment,
and it's a lot easier to find them at the front.

The easiest way to be insensitive to this change is to use
CoreUtils.findDefault to pull the default clause out.

I've made the (surprisingly few) changes consequent on this changed
of convention, but they aren't in this commit.  Instead they are part
of the big commit on newtypes I'm doing at the same time.
ghc/compiler/coreSyn/CoreSyn.lhs
ghc/compiler/coreSyn/CoreUtils.lhs
ghc/compiler/simplCore/SimplUtils.lhs