Opened 6 years ago

Closed 6 years ago

Last modified 4 years ago

#2163 closed bug (invalid)

GHC makes thunks for Integers we are strict in

Reported by: igloo Owned by:
Priority: normal Milestone: 6.8.3
Component: Compiler Version: 6.9
Keywords: Cc: dons@…
Operating System: Unknown/Multiple Architecture: Unknown/Multiple
Type of failure: Runtime performance bug Difficulty: Unknown
Test Case: Blocked By:
Blocking: Related Tickets:

Description

We know that timesInteger is strict in both arguments:

$ ./ghc --show-iface ~/ghc/darcs/val/libraries/base/dist/build/GHC/Num.hi | grep -C2 "^timesInteger"
plusInteger :: GHC.Num.Integer -> GHC.Num.Integer -> GHC.Num.Integer
  {- Arity: 2 HasNoCafRefs Strictness: SS -}
timesInteger :: GHC.Num.Integer -> GHC.Num.Integer -> GHC.Num.Integer
  {- Arity: 2 HasNoCafRefs Strictness: SS -}
class (GHC.Base.Eq a, GHC.Show.Show a) => Num a

but given this code:

module W where

f :: Integer -> Integer
f x = let x' = x + 3
      in x' * x'

we still make a thunk for x':

$ ./ghc -c w.hs -O -fforce-recomp -ddump-simpl
==================== Tidy Core ====================
W.lvl :: GHC.Num.Integer
[GlobalId]
[NoCafRefs
 Str: DmdType]
W.lvl = GHC.Num.S# 3

W.f :: GHC.Num.Integer -> GHC.Num.Integer
[GlobalId]
[Arity 1
 NoCafRefs
 Str: DmdType S]
W.f =
  \ (x_a5h :: GHC.Num.Integer) ->
    let {
      x'_sa7 [ALWAYS Just S] :: GHC.Num.Integer
      [Str: DmdType]
      x'_sa7 = GHC.Num.plusInteger x_a5h W.lvl } in
    GHC.Num.timesInteger x'_sa7 x'_sa7

The same is true in both the 6.8 branch and the HEAD.

Change History (6)

comment:1 Changed 6 years ago by dons

  • Cc dons@… added

Weird, I get this code, with -O

W.lvl :: GHC.Num.Integer
[GlobalId]
[NoCafRefs
 Str: DmdType]
W.lvl = GHC.Num.S# 3

W.f :: GHC.Num.Integer -> GHC.Num.Integer
[GlobalId]
[Arity 1
 NoCafRefs
 Str: DmdType S]
W.f =
  \ (x_a5l :: GHC.Num.Integer) ->
    case GHC.Num.plusInteger x_a5l W.lvl of wild_ab3 {
      GHC.Num.S# i_ab5 ->
        case GHC.Prim.mulIntMayOflo# i_ab5 i_ab5 of wild2_abb {
          __DEFAULT ->
            case GHC.Prim.int2Integer# i_ab5 of wild3_abc { (# s_abe, d_abf #) ->
            GHC.Num.$stimesInteger s_abe d_abf s_abe d_abf
            };
          0 -> GHC.Num.S# (GHC.Prim.*# i_ab5 i_ab5)
        };
      GHC.Num.J# ds_abw ds1_abx ->
        case GHC.Prim.timesInteger# ds_abw ds1_abx ds_abw ds1_abx
        of wild2_abM { (# s_abO, d_abP #) ->
        GHC.Num.J# s_abO d_abP
        }
    }

and -O2:

{{{W.lvl :: GHC.Num.Integer
[GlobalId?]
[NoCafRefs?

Str: DmdType?]

W.lvl = GHC.Num.S# 3

W.f :: GHC.Num.Integer -> GHC.Num.Integer
[GlobalId?]
[Arity 1

NoCafRefs?
Str: DmdType? S]

W.f =

\ (x_a5l
GHC.Num.Integer) -> case GHC.Num.plusInteger x_a5l W.lvl of wild_ab3 { GHC.Num.S# i_ab5 -> case GHC.Prim.mulIntMayOflo# i_ab5 i_ab5 of wild2_abb { DEFAULT -> case GHC.Prim.int2Integer# i_ab5 of wild3_abc { (# s_abe, d_abf #) -> GHC.Num.$stimesInteger s_abe d_abf s_abe d_abf }; 0 -> GHC.Num.S# (GHC.Prim.*# i_ab5 i_ab5) }; GHC.Num.J# ds_abw ds1_abx -> case GHC.Prim.timesInteger# ds_abw ds1_abx ds_abw ds1_abx of wild2_abM { (# s_abO, d_abP #) -> GHC.Num.J# s_abO d_abP } }
}}}

comment:2 Changed 6 years ago by igloo

We discussed this on IRC - the difference is that Don has an unfolding for timesInteger, presumably because he has

SRC_HC_OPTS   = -H32m -O2

in his mk/build.mk.

comment:3 Changed 6 years ago by simonmar

  • Resolution set to invalid
  • Status changed from new to closed

let can be strict in Core - it doesn't always indicate a thunk. If you use -ddump-stg you'll see that the expression is evaluated strictly, no thunk is built.

(don't worry, this often catches me out too. Perhaps a strict let should be indicated more explicitly in -ddump-simpl).

comment:4 Changed 6 years ago by simonmar

  • Architecture changed from Unknown to Unknown/Multiple

comment:5 Changed 6 years ago by simonmar

  • Operating System changed from Unknown to Unknown/Multiple

comment:6 Changed 4 years ago by simonmar

  • Type of failure set to Runtime performance bug
Note: See TracTickets for help on using tickets.