Ben Gamari pushed to branch wip/tick-prefer-anf at Glasgow Haskell Compiler / GHC

Commits:

4 changed files:

Changes:

  • compiler/GHC/Core/Utils.hs
    ... ... @@ -343,7 +343,7 @@ mk_tick preserve_anf t orig_expr = mkTick' orig_expr
    343 343
       mkTick' expr
    
    344 344
         -- Deal with ticking a expression headed by one or more ticks.
    
    345 345
         | Just (ts, e) <- tickedExpr_maybe expr
    
    346
    -    = tickTickedExpr t ts e
    
    346
    +    = tickTickedExpr preserve_anf t ts e
    
    347 347
       mkTick' expr = case expr of
    
    348 348
     
    
    349 349
         Lam x e
    
    ... ... @@ -413,11 +413,13 @@ mk_tick preserve_anf t orig_expr = mkTick' orig_expr
    413 413
     
    
    414 414
     -- | Apply a tick to an expression headed by ticks.
    
    415 415
     tickTickedExpr
    
    416
    -  :: CoreTickish             -- ^ tick to add
    
    416
    +  :: Bool                    -- ^ preserve ANF? (See 'mkTickCpe' and
    
    417
    +                             --   Note [mkTick breaks ANF] in GHC.CoreToStg.Prep)
    
    418
    +  -> CoreTickish             -- ^ tick to add
    
    417 419
       -> NE.NonEmpty CoreTickish -- ^ existing stack of ticks
    
    418 420
       -> CoreExpr                -- ^ inner core expression
    
    419 421
       -> CoreExpr
    
    420
    -tickTickedExpr t1 t2s e
    
    422
    +tickTickedExpr preserve_anf t1 t2s e
    
    421 423
     
    
    422 424
       -- Case 1: common up 't1' with a tick in the stack.
    
    423 425
       --
    
    ... ... @@ -431,8 +433,24 @@ tickTickedExpr t1 t2s e
    431 433
       -- Case 2: 't1' can be commuted past all the ticks in the stack, e.g. because
    
    432 434
       -- it has tighter placement properties than all the ticks in the stack.
    
    433 435
       -- Push it inwards to expose cancellation opportunities.
    
    436
    +  --
    
    437
    +  -- We must thread 'preserve_anf' through here.  Otherwise we may turn the
    
    438
    +  -- argument
    
    439
    +  --
    
    440
    +  --     scc<f> (src<l> (Just x))
    
    441
    +  --
    
    442
    +  -- into the ill-formed argument
    
    443
    +  --
    
    444
    +  --     src<l> (Just (scc<f> x))   -- SCC on an argument: not a CpeArg!
    
    445
    +  --
    
    446
    +  -- whereas with preserve_anf we keep the SCC outside the application,
    
    447
    +  -- respecting ANF:
    
    448
    +  --
    
    449
    +  --     src<l> (scc<f> (Just breakpoint))
    
    450
    +  --
    
    451
    +  -- See Note [mkTick breaks ANF] in GHC.CoreToStg.Prep and #27415.
    
    434 452
       | all (tickishCommutable t1) t2s
    
    435
    -  = apply_ticks t2s $ mkTick t1 e
    
    453
    +  = apply_ticks t2s $ mk_tick preserve_anf t1 e
    
    436 454
     
    
    437 455
       -- Fallback: keep the new tick on the outside.
    
    438 456
       | otherwise
    
    ... ... @@ -455,7 +473,7 @@ tickTickedExpr t1 t2s e
    455 473
     
    
    456 474
     {- Note [Pushing SCCs inwards]
    
    457 475
     ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
    
    458
    -Amongst all ticks, SCCs have the laxest placement properties (PlaceCostCentre,
    
    476
    +Amongst all ticks, SCCs have the most lax placement properties (PlaceCostCentre,
    
    459 477
     as described in Note [Tickish placement] GHC.Types.Tickish):
    
    460 478
     
    
    461 479
       (PSCC1) SCCs around non-function variables can be eliminated.
    

  • compiler/GHC/CoreToStg/Prep.hs
    ... ... @@ -918,10 +918,14 @@ mkTick will push the SCC into the constructor application, resulting in:
    918 918
     
    
    919 919
       \ (eta :: Char -> Bool) -> BindP (p :: Int) (scc<oneM> eta)
    
    920 920
     
    
    921
    +i.e. the SCC ends up on the argument `eta`, which is no longer a valid `arg`.
    
    922
    +
    
    921 923
     To avoid this problem (at least until 'mkTick' is more thoroughly reworked to
    
    922 924
     avoid this infelicity, see #27141), we define a variant of 'mkTick', called
    
    923 925
     'mkTickCpe', which does not push ticks into constructor applications (this is
    
    924
    -the only optimisation done by 'mkTick' that can break ANF).
    
    926
    +the only optimisation done by 'mkTick' that can break ANF). This is the concrete
    
    927
    +meaning of the 'preserve_anf' flag threaded through 'GHC.Core.Utils.mk_tick':
    
    928
    +when set, 'mk_tick' will not push a tick onto an application's arguments (PSCC3).
    
    925 929
     
    
    926 930
     We prefer using a small variant of 'mkTick' rather than using the 'Tick'
    
    927 931
     constructor, as the latter can slightly degrade profiling reports by failing to
    

  • testsuite/tests/profiling/should_compile/T27415.hs
    1
    +{-# LANGUAGE ExistentialQuantification #-}
    
    2
    +
    
    3
    +module T27415 where
    
    4
    +
    
    5
    +import Control.Concurrent.MVar
    
    6
    +
    
    7
    +data ResultVar b = forall a . ResultVar (a -> b) (MVar (Maybe a))
    
    8
    +
    
    9
    +mkResultVar :: MVar (Maybe a) -> ResultVar a
    
    10
    +mkResultVar = ResultVar id

  • testsuite/tests/profiling/should_compile/all.T
    ... ... @@ -23,3 +23,4 @@ test('T20938', [test_opts], compile, ['-O -prof'])
    23 23
     test('T26056', [test_opts], compile, ['-O -prof'])
    
    24 24
     test('T27121', [test_opts, extra_files(['T27121_aux.hs'])], multimod_compile, ['T27121', '-v0 -O -prof -fprof-auto'])
    
    25 25
     test('T27182', [test_opts], compile, ['-O -prof -fprof-late'])
    
    26
    +test('T27415', [test_opts], compile, ['-O -prof -fprof-auto -finfo-table-map'])