[commit: ghc] wip/T8598: Do not forget CPR information after an IO action (a2f7d68)
git at git.haskell.org
git at git.haskell.org
Fri Dec 6 23:15:18 UTC 2013
Repository : ssh://git@git.haskell.org/ghc
On branch : wip/T8598
Link : http://ghc.haskell.org/trac/ghc/changeset/a2f7d686fbbcd822a59211b16142d151b99ffa43/ghc
>---------------------------------------------------------------
commit a2f7d686fbbcd822a59211b16142d151b99ffa43
Author: Joachim Breitner <mail at joachim-breitner.de>
Date: Fri Dec 6 17:58:29 2013 +0000
Do not forget CPR information after an IO action
but do forget about certain divergence, if required. Fixes one part of
ticket #8598.
>---------------------------------------------------------------
a2f7d686fbbcd822a59211b16142d151b99ffa43
compiler/basicTypes/Demand.lhs | 31 +++++++++++++++++++------------
compiler/stranal/DmdAnal.lhs | 2 +-
2 files changed, 20 insertions(+), 13 deletions(-)
diff --git a/compiler/basicTypes/Demand.lhs b/compiler/basicTypes/Demand.lhs
index cd844a1..f03de42 100644
--- a/compiler/basicTypes/Demand.lhs
+++ b/compiler/basicTypes/Demand.lhs
@@ -19,7 +19,7 @@ module Demand (
peelUseCall, cleanUseDmd_maybe, strictenDmd, bothCleanDmd,
DmdType(..), dmdTypeDepth, lubDmdType, bothDmdEnv, bothDmdType,
- topDmdType, botDmdType, mkDmdType, mkTopDmdType,
+ topDmdType, botDmdType, exitDmdType, mkDmdType, mkTopDmdType,
DmdEnv, emptyDmdEnv,
@@ -715,14 +715,15 @@ splitProdDmd_maybe (JD {strd = s, absd = u})
data CPRResult = NoCPR -- Top of the lattice
| RetProd -- Returns a constructor from a product type
| RetSum ConTag -- Returns a constructor from a sum type with this tag
- | BotCPR -- Returns a constructor with any tag
- -- Bottom of the domain
+ | ExitCPR -- Exits cleanly
+ | BotCPR -- Diverges
deriving( Eq, Show )
lubCPR :: CPRResult -> CPRResult -> CPRResult
lubCPR BotCPR r = r
-lubCPR RetProd BotCPR = RetProd
-lubCPR (RetSum t) BotCPR = RetSum t
+lubCPR r BotCPR = r
+lubCPR ExitCPR r = r
+lubCPR r ExitCPR = r
lubCPR (RetSum t1) (RetSum t2)
| t1 == t2 = RetSum t1
lubCPR RetProd RetProd = RetProd
@@ -730,12 +731,14 @@ lubCPR _ _ = NoCPR
bothCPR :: CPRResult -> CPRResult -> CPRResult
-- See Note [Asymmetry of 'both' for DmdType and DmdResult]
-bothCPR _ BotCPR = BotCPR -- If either diverges, we diverge
-bothCPR r _ = r
+bothCPR _ BotCPR = BotCPR -- If either diverges, we diverge
+bothCPR _ ExitCPR = ExitCPR -- If either exists, we exit
+bothCPR r _ = r -- otherwise, the second argument is irrelevant
instance Outputable DmdResult where
ppr RetProd = char 'm'
ppr (RetSum n) = char 'm' <> int n
+ ppr ExitCPR = char 'e'
ppr BotCPR = char 'b'
ppr NoCPR = empty -- Keep these distinct from Demand letters
@@ -755,8 +758,9 @@ seqDmdResult r = r `seq` ()
-- [cprRes] lets us switch off CPR analysis
-- by making sure that everything uses TopRes
-topRes, botRes :: DmdResult
+topRes, exitRes, botRes :: DmdResult
topRes = NoCPR
+exitRes = ExitCPR
botRes = BotCPR
cprSumRes :: ConTag -> DmdResult
@@ -1030,9 +1034,10 @@ instance Outputable DmdType where
emptyDmdEnv :: VarEnv Demand
emptyDmdEnv = emptyVarEnv
-topDmdType, botDmdType :: DmdType
-topDmdType = DmdType emptyDmdEnv [] topRes
-botDmdType = DmdType emptyDmdEnv [] botRes
+topDmdType, exitDmdType, botDmdType :: DmdType
+topDmdType = DmdType emptyDmdEnv [] topRes
+exitDmdType = DmdType emptyDmdEnv [] exitRes
+botDmdType = DmdType emptyDmdEnv [] botRes
cprProdDmdType :: DmdType
cprProdDmdType = DmdType emptyDmdEnv [] cprProdRes
@@ -1583,6 +1588,7 @@ instance Binary CPRResult where
put_ bh RetProd = putByte bh 1
put_ bh NoCPR = putByte bh 2
put_ bh BotCPR = putByte bh 3
+ put_ bh ExitCPR = putByte bh 4
get bh = do
h <- getByte bh
@@ -1590,5 +1596,6 @@ instance Binary CPRResult where
0 -> do { n <- get bh; return (RetSum n) }
1 -> return RetProd
2 -> return NoCPR
- _ -> return BotCPR
+ 3 -> return BotCPR
+ _ -> return ExitCPR
\end{code}
diff --git a/compiler/stranal/DmdAnal.lhs b/compiler/stranal/DmdAnal.lhs
index 99eb7ac..094f74a 100644
--- a/compiler/stranal/DmdAnal.lhs
+++ b/compiler/stranal/DmdAnal.lhs
@@ -332,7 +332,7 @@ dmdAnalAlt env dmd (con,bndrs,rhs)
(rhs_ty, rhs') = dmdAnal env dmd rhs
rhs_ty' = addDataConPatDmds con bndrs rhs_ty
(alt_ty, bndrs') = annotateBndrs env rhs_ty' bndrs
- final_alt_ty | io_hack_reqd = alt_ty `lubDmdType` topDmdType
+ final_alt_ty | io_hack_reqd = alt_ty `lubDmdType` exitDmdType
| otherwise = alt_ty
-- There's a hack here for I/O operations. Consider
More information about the ghc-commits
mailing list