Skip to content
  • Simon Peyton Jones's avatar
    [project @ 2001-06-25 08:08:32 by simonpj] · 3622a7de
    Simon Peyton Jones authored
    ---------------------------
    	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.
    3622a7de