Removing "case" with duplicate branches from Haskell's Core
haskell, repa
Solution
Indeed the two branches of the `case ># x_s32E 0 of` are identical, and hence that `case` is redundant. It seems that the `case`-elimination for identical branches isn't run after both branches became identical - probably worth a bug report. This one may be pertinent, but since the core generated for negative divisors is good, I filed a new bug.
Using the simpler `quot` - if `i` cannot legitimately negative - that directly maps to the machine division operator makes the code simpler, so that no branches need to be generated for that.
Problem
I have a piece of Haskell code that looks like this: ``` fst . f $ (Z :. i `div` 2) ``` `Z` and `:.` are taken from Repa library and are defined like this: ``` data Z = Z deriving (Show, Read, Eq, Ord) infixl 3 :. data tail :. head = !tail :. !head deriving (Show, Read, Eq, Ord) ``` The expression right of `$` defines an array index, while `f` is a function that takes that index and returns a pair. This compiles to following Core: ``` case f_a2pC (case ># x_s32E 0 of _ { False -> case <# x_s32E 0 of _ { False -> :. Z (I# (quotInt# x_s32E 2)); True -> :. Z (I# (-# (quotInt# (+# x_s32E 1) 2) 1)) }; True -> case <# x_s32E 0 of _ { False -> :. Z (I# (quotInt# x_s32E 2)); True -> :. Z (I# (-# (quotInt# (+# x_s32E 1) 2) 1)) } }) of _ { (x1_a2Cv, _) -> x1_a2Cv } ``` To me it seems obvious (perhaps incorrectly) that the middle case statement (the one with `># x_s32E 0` as scrutinee) is redundant, as both branches are identical. Is there anything I can do to get rid of it? I compile my code using GHC options recommended in Repa documentation: -O2 -Odph -fno-liberate-case -funfolding-use-threshold1000 -funfolding-keeness-factor1000