summaryrefslogtreecommitdiff
path: root/compiler
diff options
context:
space:
mode:
authorsimonpj@microsoft.com <unknown>2007-08-09 15:14:57 +0000
committersimonpj@microsoft.com <unknown>2007-08-09 15:14:57 +0000
commitfea8c9e4b1ef4973aa577f29b59d35ee12472ebb (patch)
treecd1ac7767a939d0196f13d8f0879bcc408e9c801 /compiler
parentfd7c5f3251794224e1d48d09eeffe18fd76420a2 (diff)
downloadhaskell-fea8c9e4b1ef4973aa577f29b59d35ee12472ebb.tar.gz
Better scoring for loop breakers; fixes simplifier loop in nofib/minimax
See Note [Inline candidates] in OccurAnal. We were getting a recursive loop exposed, which led to infinite inlinings. Doesn't bite much, but was obviously wrong. I've change the "scoring order" for loop breakers, which could possibly have a performance impact on other programs. A full nofib run exposed a 0.00% change in allocation in any nofib program, so I don't think it's likely, but keep an eye out.
Diffstat (limited to 'compiler')
-rw-r--r--compiler/simplCore/OccurAnal.lhs27
1 files changed, 22 insertions, 5 deletions
diff --git a/compiler/simplCore/OccurAnal.lhs b/compiler/simplCore/OccurAnal.lhs
index ae2b7b9023..5ed57fbe92 100644
--- a/compiler/simplCore/OccurAnal.lhs
+++ b/compiler/simplCore/OccurAnal.lhs
@@ -308,12 +308,10 @@ reOrderCycle bndrs (bind : binds)
-- Also vital to avoid risk of divergence:
-- Note [Recursive rules]
- | is_con_app rhs = 2 -- Data types help with cases
- -- This used to have a lower score than inlineCandidate, but
- -- it's *really* helpful if dictionaries get inlined fast,
- -- so I'm experimenting with giving higher priority to data-typed things
+ | inlineCandidate bndr rhs = 2 -- Likely to be inlined
+ -- Note [Inline candidates]
- | inlineCandidate bndr rhs = 1 -- Likely to be inlined
+ | is_con_app rhs = 1 -- Data types help with cases
| otherwise = 0
@@ -356,6 +354,25 @@ makeLoopBreaker bndrs rhs_usg bndr
rules_only = bndrs `intersectsUFM` rhs_usg
\end{code}
+Note [Inline candidates]
+~~~~~~~~~~~~~~~~~~~~~~~~
+At one point I gave is_con_app a higher score than inline-candidate,
+on the grounds that "it's *really* helpful if dictionaries get inlined fast".
+However a nofib run revealed no change if they were swapped so that
+inline-candidate has the higher score. And it's important that it does,
+else you can get a bad worker-wrapper split thus:
+ rec {
+ $wfoo x = ....foo x....
+
+ {-loop brk-} foo x = ...$wfoo x...
+ }
+But we *want* the wrapper to be inlined! If it isn't, the interface
+file sees the unfolding for $wfoo, and sees that foo is strict (and
+hence it gets an auto-generated wrapper. Result: an infinite inlining
+in the importing scope. So be a bit careful if you change this. A
+good example is Tree.repTree in nofib/spectral/minimax. If is_con_app
+has the higher score, then compiling Game.hs goes into an infinite loop.
+
Note [Recursive rules]
~~~~~~~~~~~~~~~~~~~~~~
Consider this group, which is typical of what SpecConstr builds: