Marge Bot pushed to branch master at Glasgow Haskell Compiler / GHC

Commits:

2 changed files:

Changes:

  • changelog.d/T27722-cbe-entry-block.md
    1
    +section: cmm
    
    2
    +issues: #27722
    
    3
    +mrs: !16592
    
    4
    +synopsis:
    
    5
    +  Fix common block elimination dropping entry block info table in hand written cmm.

  • compiler/GHC/Cmm/CommonBlockElim.hs
    ... ... @@ -26,6 +26,7 @@ import GHC.Types.Literal.Floating
    26 26
     import GHC.Types.Unique.FM
    
    27 27
     import GHC.Types.Unique
    
    28 28
     import GHC.Utils.Word64 (truncateWord64ToWord32)
    
    29
    +import GHC.Utils.Panic.Plain (assert)
    
    29 30
     import Control.Arrow (first, second)
    
    30 31
     import Data.List.NonEmpty (NonEmpty (..))
    
    31 32
     import qualified Data.List.NonEmpty as NE
    
    ... ... @@ -60,16 +61,31 @@ import qualified Data.List.NonEmpty as NE
    60 61
     
    
    61 62
     -- TODO: Use optimization fuel
    
    62 63
     elimCommonBlocks :: CmmGraph -> CmmGraph
    
    63
    -elimCommonBlocks g = replaceLabels env $ copyTicks env g
    
    64
    +elimCommonBlocks g =
    
    65
    +    assert (g_entry g == g_entry g') g'
    
    64 66
       where
    
    67
    +     g' = replaceLabels env $ copyTicks env g
    
    65 68
          env = iterate mapEmpty blocks_with_key
    
    66 69
          -- The order of blocks doesn't matter here. While we could use
    
    67 70
          -- revPostorder which drops unreachable blocks this is done in
    
    68 71
          -- ContFlowOpt already which runs before this pass. So we use
    
    69 72
          -- toBlockList since it is faster.
    
    70
    -     groups = groupByInt hash_block (toBlockList g) :: [[CmmBlock]]
    
    73
    +     -- One exception: The entry block most come first or we risk eliminating it
    
    74
    +     -- in favour of another block. See Note [Retain entry block during common block elimination.]
    
    75
    +     groups = groupByInt hash_block (toBlockListEntryFirst g) :: [[CmmBlock]]
    
    71 76
          blocks_with_key = [ [ (successors b, [b]) | b <- bs] | bs <- groups]
    
    72 77
     
    
    78
    +-- Note [Retain entry block during common block elimination.]
    
    79
    +-- ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
    
    80
    +-- At the stage we run common block elimination (CBE) we only have one info
    
    81
    +-- table for the entry label. Which means we can get away without applying the
    
    82
    +-- block label substitution to the info table *as long as we keep the first block*.
    
    83
    +-- When combining blocks the first block in the list of blocks is kept, and the later
    
    84
    +-- one eliminated, so we can achieve this by simply using toBlockListEntryFirst.
    
    85
    +--
    
    86
    +-- If we don't we end up with #27722 where the entry block was eliminated in favour
    
    87
    +-- of another block.
    
    88
    +
    
    73 89
     -- Invariant: The blocks in the list are pairwise distinct
    
    74 90
     -- (so avoid comparing them again)
    
    75 91
     type DistinctBlocks = [CmmBlock]