| ... |
... |
@@ -66,25 +66,23 @@ elimCommonBlocks g = |
|
66
|
66
|
where
|
|
67
|
67
|
g' = replaceLabels env $ copyTicks env g
|
|
68
|
68
|
env = iterate mapEmpty blocks_with_key
|
|
69
|
|
- -- The order of blocks doesn't matter here. While we could use
|
|
70
|
|
- -- revPostorder which drops unreachable blocks this is done in
|
|
71
|
|
- -- ContFlowOpt already which runs before this pass. So we use
|
|
72
|
|
- -- toBlockList since it is faster.
|
|
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]]
|
|
76
|
69
|
blocks_with_key = [ [ (successors b, [b]) | b <- bs] | bs <- groups]
|
|
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.
|
|
|
70
|
+ groups = groupByInt hash_block candidates :: [[CmmBlock]]
|
|
|
71
|
+ -- See Note [Retain entry block during common block elimination]
|
|
|
72
|
+ candidates = filter ((/= g_entry g) . entryLabel) (toBlockList g)
|
|
|
73
|
+
|
|
|
74
|
+-- Note [Retain entry block during common block elimination]
|
|
|
75
|
+-- ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
|
|
76
|
+-- When CBE runs, only the entry label has an info table, so we can get away
|
|
|
77
|
+-- without applying the block label substitution to info tables, as long as we
|
|
|
78
|
+-- preserve the entry block (#27722). We achieve this by simply keeping it out
|
|
|
79
|
+-- of the list of candidates for elimination.
|
|
85
|
80
|
--
|
|
86
|
|
--- If we don't we end up with #27722 where the entry block was eliminated in favour
|
|
87
|
|
--- of another block.
|
|
|
81
|
+-- The downside is that any duplicates of the entry block stay unmerged. This
|
|
|
82
|
+-- should be very rare though, and only affects hand-written Cmm: the entry
|
|
|
83
|
+-- block of any proc generated from STG contains the stack check (see
|
|
|
84
|
+-- entryHeapCheck in GHC.StgToCmm.Heap) and is therefore distinct from any
|
|
|
85
|
+-- other block in the same proc.
|
|
88
|
86
|
|
|
89
|
87
|
-- Invariant: The blocks in the list are pairwise distinct
|
|
90
|
88
|
-- (so avoid comparing them again)
|