
#7865: SpecConstr duplicating computations ------------------------------------+--------------------------------------- Reporter: amosrobinson | Owner: Type: bug | Status: new Priority: normal | Component: Compiler Version: | Keywords: SpecConstr Os: Unknown/Multiple | Architecture: Unknown/Multiple Failure: Runtime performance bug | Blockedby: Blocking: | Related: ------------------------------------+--------------------------------------- In some (very rare) cases, SpecConstr can actually duplicate let bindings. When SpecConstr sees something like {{{ let tuple = (let x = expensive in x, simple) case tuple of (a,b) -> a + a }}} it records the value of tuple, and replaces the case with {{{ (let x = expensive in x) + (let x = expensive in x) }}} Usually we wouldn't notice this, because the Simplifier would let-float expensive out of the tuple before SpecConstr runs. In some cases though, the tuple constructor will only be exposed after specialisation happens. To test, compile TSpecConstr_DoubleInline with {{{ ghc TSpecConstr_DoubleInline.hs -O2 -fspec-constr -dverbose-core2core -fforce-recomp -dppr-case-as-let -dsuppress-all | less }}} and search for the SpecConstr pass. The first specialisation is {{{ $srecursive_sf3 $srecursive_sf3 = \ sc_seR sc_seS sc_seT sc_seU -> let { a'_sep a'_sep = (let { I# x_adP ~ _ <- expensive sc_seR } in I# (*# x_adP 2), sc_seR) } in let { ds_seq ds_seq = recursive (: sc_seR (: sc_seR (: sc_seS sc_seT))) (sc_seR, let { I# x_adP ~ _ <- expensive sc_seR } in I# (*# x_adP 2)) } in (let { (p_XdA, q_Xdu) ~ _ <- ds_seq } in let { I# x_ae7 ~ _ <- p_XdA } in let { I# y_aeb ~ _ <- let { I# x_adP ~ _ <- expensive sc_seR } in I# (*# x_adP 2) } in I# (+# x_ae7 y_aeb), let { (p_adg, q_XdA) ~ _ <- ds_seq } in let { I# x_ae7 ~ _ <- q_XdA } in let { I# y_aeb ~ _ <- sc_seR } in I# (+# x_ae7 y_aeb)) }}} With three calls to expensive. If you look at the -ddump-prep, one of the calls is simplified out, but there is still one too many at the end. This is happening on at least 7.4.1 and head. -- Ticket URL: http://hackage.haskell.org/trac/ghc/ticket/7865 GHC http://www.haskell.org/ghc/ The Glasgow Haskell Compiler