Simon Peyton Jones pushed to branch wip/T26989 at Glasgow Haskell Compiler / GHC

Commits:

11 changed files:

Changes:

  • compiler/GHC/Core.hs
    ... ... @@ -84,9 +84,13 @@ module GHC.Core (
    84 84
             IsOrphan(..), isOrphan, notOrphan, chooseOrphanAnchor,
    
    85 85
     
    
    86 86
             -- * Core rule data types
    
    87
    -        CoreRule(..),
    
    87
    +        CoreRule(..), RuleMatch(..),
    
    88 88
             RuleName, RuleFun, IdUnfoldingFun, InScopeEnv(..), RuleOpts,
    
    89 89
     
    
    90
    +        -- * Floats
    
    91
    +        FloatBind(..), FloatBinds, emptyFloatBinds, isEmptyFloatBinds,
    
    92
    +        floatBinders, floatsBinders,
    
    93
    +
    
    90 94
             -- ** Operations on 'CoreRule's
    
    91 95
             ruleArity, ruleName, ruleIdName, ruleActivation,
    
    92 96
             setRuleIdName, ruleModule,
    
    ... ... @@ -116,6 +120,8 @@ import GHC.Utils.Misc
    116 120
     import GHC.Utils.Outputable
    
    117 121
     import GHC.Utils.Panic
    
    118 122
     
    
    123
    +import GHC.Data.OrdList
    
    124
    +
    
    119 125
     import Data.Data hiding (TyCon)
    
    120 126
     import Data.Int
    
    121 127
     import Data.List.NonEmpty (nonEmpty)
    
    ... ... @@ -1574,7 +1580,25 @@ data CoreRule
    1574 1580
         }
    
    1575 1581
                     -- See Note [Extra args in the target] in GHC.Core.Rules
    
    1576 1582
     
    
    1577
    -type RuleFun = RuleOpts -> InScopeEnv -> Id -> [CoreExpr] -> Maybe CoreExpr
    
    1583
    +type RuleFun = RuleOpts -> InScopeEnv
    
    1584
    +               -> Id -> [CoreExpr]   -- Function applied to these arguments
    
    1585
    +               -> Maybe RuleMatch
    
    1586
    +
    
    1587
    +data RuleMatch
    
    1588
    +  = RM { rm_rule   :: CoreRule
    
    1589
    +       , rm_rhs    :: CoreExpr      -- Rhs of the rule
    
    1590
    +       , rm_args   :: [CoreExpr]    -- The args of the RHS
    
    1591
    +       , rm_floats :: FloatBinds    -- Floated let-bindings
    
    1592
    +                                    -- See Note [Matching lets]
    
    1593
    +       }
    
    1594
    +  -- E.g. match  r = RULE forall x,y. f (Just (y,x)) = g x y True
    
    1595
    +  --      target f (let v = ev in Just (ey, ex)) ez
    
    1596
    +  -- We get the RuleMatch
    
    1597
    +  --    RMM { rm_rule   = r, rm_rhs = \xy. g x y True
    
    1598
    +  --        , rm_args   = [ex, ey]
    
    1599
    +  --        , rm_floats = Let v=ev }
    
    1600
    +  -- The leftover `ez` is not returned; the caller is responsible for
    
    1601
    +  -- counting (ruleArity r) arguments
    
    1578 1602
     
    
    1579 1603
     -- | The 'InScopeSet' in the 'InScopeEnv' is a /superset/ of variables that are
    
    1580 1604
     -- currently in scope. See Note [The InScopeSet invariant].
    
    ... ... @@ -1622,6 +1646,37 @@ isLocalRule (Rule { ru_local = is_local }) = is_local
    1622 1646
     setRuleIdName :: Name -> CoreRule -> CoreRule
    
    1623 1647
     setRuleIdName nm ru = ru { ru_fn = nm }
    
    1624 1648
     
    
    1649
    +{-
    
    1650
    +************************************************************************
    
    1651
    +*                                                                      *
    
    1652
    +                Floats
    
    1653
    +*                                                                      *
    
    1654
    +************************************************************************
    
    1655
    +-}
    
    1656
    +
    
    1657
    +type FloatBinds = OrdList FloatBind
    
    1658
    +
    
    1659
    +emptyFloatBinds :: FloatBinds
    
    1660
    +emptyFloatBinds = nilOL
    
    1661
    +
    
    1662
    +isEmptyFloatBinds :: FloatBinds -> Bool
    
    1663
    +isEmptyFloatBinds = isNilOL
    
    1664
    +
    
    1665
    +data FloatBind
    
    1666
    +  = FloatLet  CoreBind
    
    1667
    +  | FloatCase CoreExpr CoreBndr AltCon [CoreBndr]
    
    1668
    +      -- case e of y { C ys -> ... }
    
    1669
    +      -- See Note [Floating single-alternative cases] in GHC.Core.Opt.SetLevels
    
    1670
    +  | FloatTick CoreTickish
    
    1671
    +
    
    1672
    +floatsBinders :: FloatBinds -> [Var]
    
    1673
    +floatsBinders fs = foldr ((++) . floatBinders) [] fs
    
    1674
    +
    
    1675
    +floatBinders :: FloatBind -> [Var]
    
    1676
    +floatBinders (FloatLet bnd)       = bindersOf bnd
    
    1677
    +floatBinders (FloatCase _ b _ bs) = b:bs
    
    1678
    +floatBinders (FloatTick {})       = []
    
    1679
    +
    
    1625 1680
     {-
    
    1626 1681
     ************************************************************************
    
    1627 1682
     *                                                                      *
    

  • compiler/GHC/Core/Make.hs
    ... ... @@ -18,11 +18,6 @@ module GHC.Core.Make (
    18 18
             mkCharExpr, mkStringExpr, mkStringExprFS, mkStringExprFSWith,
    
    19 19
             MkStringIds (..), getMkStringIds,
    
    20 20
     
    
    21
    -        -- * Floats
    
    22
    -        FloatBind(..), FloatBinds,
    
    23
    -        wrapFloat, wrapFloats, floatBindings,
    
    24
    -        emptyFloatBinds, isEmptyFloatBinds,
    
    25
    -
    
    26 21
             -- * Constructing small tuples
    
    27 22
             mkCoreVarTupTy, mkCoreTup, mkCoreUnboxedTuple, mkCoreUnboxedSum,
    
    28 23
             mkCoreTupBoxity, unitExpr,
    
    ... ... @@ -43,6 +38,9 @@ module GHC.Core.Make (
    43 38
             -- * Constructing Maybe expressions
    
    44 39
             mkNothingExpr, mkJustExpr,
    
    45 40
     
    
    41
    +        -- * Floats
    
    42
    +        wrapFloat, wrapFloats,
    
    43
    +
    
    46 44
             -- * Error Ids
    
    47 45
             mkRuntimeErrorApp, mkImpossibleExpr, mkAbsentErrorApp, errorIds,
    
    48 46
             rEC_CON_ERROR_ID,
    
    ... ... @@ -63,7 +61,6 @@ import GHC.Types.Basic( TypeOrConstraint(..) )
    63 61
     import GHC.Types.Demand
    
    64 62
     import GHC.Types.Name      hiding ( varName )
    
    65 63
     import GHC.Types.Literal
    
    66
    -import GHC.Types.Tickish
    
    67 64
     import GHC.Types.Unique.Supply
    
    68 65
     
    
    69 66
     import GHC.Core
    
    ... ... @@ -740,54 +737,6 @@ mkSmallTupleCase vars body scrut_var scrut
    740 737
       = Case scrut scrut_var (exprType body)
    
    741 738
              [Alt (DataAlt (tupleDataCon Boxed (length vars))) vars body]
    
    742 739
     
    
    743
    -{-
    
    744
    -************************************************************************
    
    745
    -*                                                                      *
    
    746
    -                Floats
    
    747
    -*                                                                      *
    
    748
    -************************************************************************
    
    749
    --}
    
    750
    -
    
    751
    -type FloatBinds = OrdList FloatBind
    
    752
    -
    
    753
    -emptyFloatBinds :: FloatBinds
    
    754
    -emptyFloatBinds = nilOL
    
    755
    -
    
    756
    -isEmptyFloatBinds :: FloatBinds -> Bool
    
    757
    -isEmptyFloatBinds = isNilOL
    
    758
    -
    
    759
    -data FloatBind
    
    760
    -  = FloatLet  CoreBind
    
    761
    -  | FloatCase CoreExpr Id AltCon [Var]
    
    762
    -      -- case e of y { C ys -> ... }
    
    763
    -      -- See Note [Floating single-alternative cases] in GHC.Core.Opt.SetLevels
    
    764
    -  | FloatTick CoreTickish
    
    765
    -
    
    766
    -instance Outputable FloatBind where
    
    767
    -  ppr (FloatTick t) = text "TICK" <+> ppr t
    
    768
    -  ppr (FloatLet b)  = text "LET" <+> ppr b
    
    769
    -  ppr (FloatCase e b c bs) = hang (text "CASE" <+> ppr e <+> text "of" <+> ppr b)
    
    770
    -                                2 (ppr c <+> ppr bs)
    
    771
    -
    
    772
    -wrapFloat :: FloatBind -> CoreExpr -> CoreExpr
    
    773
    -wrapFloat (FloatTick t)          body = mkTick t body
    
    774
    -wrapFloat (FloatLet defns)       body = Let defns body
    
    775
    -wrapFloat (FloatCase e b con bs) body = mkSingleAltCase e b con bs body
    
    776
    -
    
    777
    --- | Applies the floats from right to left. That is @wrapFloats [b1, b2, …, bn]
    
    778
    --- u = let b1 in let b2 in … in let bn in u@
    
    779
    -wrapFloats :: FloatBinds -> CoreExpr -> CoreExpr
    
    780
    -wrapFloats floats expr = foldrOL wrapFloat expr floats
    
    781
    -
    
    782
    -bindBindings :: CoreBind -> [Var]
    
    783
    -bindBindings (NonRec b _) = [b]
    
    784
    -bindBindings (Rec bnds) = map fst bnds
    
    785
    -
    
    786
    -floatBindings :: FloatBind -> [Var]
    
    787
    -floatBindings (FloatLet bnd)       = bindBindings bnd
    
    788
    -floatBindings (FloatCase _ b _ bs) = b:bs
    
    789
    -floatBindings (FloatTick {})       = []
    
    790
    -
    
    791 740
     {-
    
    792 741
     ************************************************************************
    
    793 742
     *                                                                      *
    
    ... ... @@ -867,6 +816,25 @@ mkJustExpr :: Type -> CoreExpr -> CoreExpr
    867 816
     mkJustExpr ty val = mkConApp justDataCon [Type ty, val]
    
    868 817
     
    
    869 818
     
    
    819
    +{-
    
    820
    +************************************************************************
    
    821
    +*                                                                      *
    
    822
    +             Manipulating Floats
    
    823
    +*                                                                      *
    
    824
    +************************************************************************
    
    825
    +-}
    
    826
    +
    
    827
    +wrapFloat :: FloatBind -> CoreExpr -> CoreExpr
    
    828
    +wrapFloat (FloatTick t)          body = mkTick t body
    
    829
    +wrapFloat (FloatLet defns)       body = Let defns body
    
    830
    +wrapFloat (FloatCase e b con bs) body = mkSingleAltCase e b con bs body
    
    831
    +
    
    832
    +-- | Applies the floats from right to left. That is @wrapFloats [b1, b2, …, bn]
    
    833
    +-- u = let b1 in let b2 in … in let bn in u@
    
    834
    +wrapFloats :: FloatBinds -> CoreExpr -> CoreExpr
    
    835
    +wrapFloats floats expr = foldrOL wrapFloat expr floats
    
    836
    +
    
    837
    +
    
    870 838
     {-
    
    871 839
     ************************************************************************
    
    872 840
     *                                                                      *
    

  • compiler/GHC/Core/Opt/ConstantFold.hs
    ... ... @@ -870,7 +870,7 @@ primOpRules nm = \case
    870 870
     
    
    871 871
     -- useful shorthands
    
    872 872
     mkPrimOpRule :: Name -> Int -> [RuleM CoreExpr] -> Maybe CoreRule
    
    873
    -mkPrimOpRule nm arity rules = Just $ mkBasicRule nm arity (msum rules)
    
    873
    +mkPrimOpRule nm arity rules = Just $ mkBasicRule1 nm arity (msum rules)
    
    874 874
     
    
    875 875
     mkRelOpRule :: Name -> (forall a . Ord a => a -> a -> Bool)
    
    876 876
                 -> [RuleM CoreExpr] -> Maybe CoreRule
    
    ... ... @@ -1679,16 +1679,35 @@ but that is only a historical accident.
    1679 1679
     ************************************************************************
    
    1680 1680
     -}
    
    1681 1681
     
    
    1682
    -mkBasicRule :: Name -> Int -> RuleM CoreExpr -> CoreRule
    
    1682
    +mkBasicRule1 :: Name -> Int -> RuleM CoreExpr -> CoreRule
    
    1683 1683
     -- Gives the Rule the same name as the primop itself
    
    1684
    -mkBasicRule op_name n_args rm
    
    1685
    -  = BuiltinRule { ru_name  = occNameFS (nameOccName op_name),
    
    1686
    -                  ru_fn    = op_name,
    
    1687
    -                  ru_nargs = n_args,
    
    1688
    -                  ru_try   = runRuleM rm }
    
    1689
    -
    
    1690
    -newtype RuleM r = RuleM
    
    1691
    -  { runRuleM :: RuleOpts -> InScopeEnv -> Id -> [CoreExpr] -> Maybe r }
    
    1684
    +mkBasicRule1 op_name n_args rm
    
    1685
    +  = mkBasicRule (occNameFS (nameOccName op_name)) op_name n_args rm
    
    1686
    +
    
    1687
    +mkBasicRule :: RuleName -> Name -> Int -> RuleM CoreExpr -> CoreRule
    
    1688
    +-- The Builtin rules in this module all produce an expression
    
    1689
    +-- with no args; hence rm_args = [].  The `rm_rhs` is the complete
    
    1690
    +-- result of the rule rewrite.  This is OK because it's always
    
    1691
    +-- small (I think).
    
    1692
    +mkBasicRule rule_name op_name n_args rm
    
    1693
    +  = rule
    
    1694
    +  where
    
    1695
    +    rule = BuiltinRule { ru_name  = rule_name
    
    1696
    +                       , ru_fn    = op_name
    
    1697
    +                       , ru_nargs = n_args
    
    1698
    +                       , ru_try   = try }
    
    1699
    +
    
    1700
    +    try opts in_scope fn args
    
    1701
    +      = case runRuleM rm opts in_scope fn args of
    
    1702
    +          Nothing  -> Nothing
    
    1703
    +          Just rhs -> Just (RM { rm_rule = rule
    
    1704
    +                               , rm_rhs  = rhs
    
    1705
    +                               , rm_args = []
    
    1706
    +                               , rm_floats = emptyFloatBinds })
    
    1707
    +
    
    1708
    +type CFRuleFun r = RuleOpts -> InScopeEnv -> Id -> [CoreExpr] -> Maybe r
    
    1709
    +
    
    1710
    +newtype RuleM r = RuleM { runRuleM :: CFRuleFun r }
    
    1692 1711
       deriving (Functor)
    
    1693 1712
     
    
    1694 1713
     instance Applicative RuleM where
    
    ... ... @@ -2132,28 +2151,16 @@ is fine.
    2132 2151
     builtinRules :: [CoreRule]
    
    2133 2152
     -- Rules for non-primops that can't be expressed using a RULE pragma
    
    2134 2153
     builtinRules
    
    2135
    -  = [BuiltinRule { ru_name = fsLit "CStringFoldrLit",
    
    2136
    -                   ru_fn = unpackCStringFoldrName,
    
    2137
    -                   ru_nargs = 4, ru_try = match_cstring_foldr_lit_C },
    
    2138
    -     BuiltinRule { ru_name = fsLit "CStringFoldrLitUtf8",
    
    2139
    -                   ru_fn = unpackCStringFoldrUtf8Name,
    
    2140
    -                   ru_nargs = 4, ru_try = match_cstring_foldr_lit_utf8 },
    
    2141
    -     BuiltinRule { ru_name = fsLit "CStringAppendLit",
    
    2142
    -                   ru_fn = unpackCStringAppendName,
    
    2143
    -                   ru_nargs = 2, ru_try = match_cstring_append_lit_C },
    
    2144
    -     BuiltinRule { ru_name = fsLit "CStringAppendLitUtf8",
    
    2145
    -                   ru_fn = unpackCStringAppendUtf8Name,
    
    2146
    -                   ru_nargs = 2, ru_try = match_cstring_append_lit_utf8 },
    
    2147
    -     BuiltinRule { ru_name = fsLit "EqString", ru_fn = eqStringName,
    
    2148
    -                   ru_nargs = 2, ru_try = match_eq_string },
    
    2149
    -     BuiltinRule { ru_name = fsLit "CStringLength", ru_fn = cstringLengthName,
    
    2150
    -                   ru_nargs = 1, ru_try = match_cstring_length },
    
    2151
    -     BuiltinRule { ru_name = fsLit "Inline", ru_fn = inlineIdName,
    
    2152
    -                   ru_nargs = 2, ru_try = \_ _ _ -> match_inline },
    
    2153
    -
    
    2154
    -     mkBasicRule unsafeEqualityProofName 3 unsafeEqualityProofRule,
    
    2155
    -
    
    2156
    -     mkBasicRule divIntName 2 $ msum
    
    2154
    +  = [ mkBasicRule1 unpackCStringFoldrName      4 (RuleM match_cstring_foldr_lit_C)
    
    2155
    +    , mkBasicRule1 unpackCStringFoldrUtf8Name  4 (RuleM match_cstring_foldr_lit_utf8)
    
    2156
    +    , mkBasicRule1 unpackCStringAppendName     2 (RuleM match_cstring_append_lit_C)
    
    2157
    +    , mkBasicRule1 unpackCStringAppendUtf8Name 2 (RuleM match_cstring_append_lit_utf8)
    
    2158
    +    , mkBasicRule1 eqStringName                2 (RuleM match_eq_string)
    
    2159
    +    , mkBasicRule1 cstringLengthName           1 (RuleM match_cstring_length)
    
    2160
    +    , mkBasicRule1 inlineIdName                2 (RuleM match_inline)
    
    2161
    +    , mkBasicRule1 unsafeEqualityProofName     3 unsafeEqualityProofRule
    
    2162
    +
    
    2163
    +    , mkBasicRule1 divIntName 2 $ msum
    
    2157 2164
             [ nonZeroLit 1 >> binaryLit (intOp2 div)
    
    2158 2165
             , leftZero
    
    2159 2166
             , do
    
    ... ... @@ -2161,9 +2168,9 @@ builtinRules
    2161 2168
               Just n <- return $ exactLog2 d
    
    2162 2169
               platform <- getPlatform
    
    2163 2170
               return $ Var (primOpId IntSraOp) `App` arg `App` mkIntVal platform n
    
    2164
    -        ],
    
    2171
    +        ]
    
    2165 2172
     
    
    2166
    -     mkBasicRule modIntName 2 $ msum
    
    2173
    +    , mkBasicRule1 modIntName 2 $ msum
    
    2167 2174
             [ nonZeroLit 1 >> binaryLit (intOp2 mod)
    
    2168 2175
             , leftZero
    
    2169 2176
             , do
    
    ... ... @@ -2322,15 +2329,9 @@ builtinBignumRules =
    2322 2329
           encodeLitDouble LitDouble
    
    2323 2330
       ]
    
    2324 2331
       where
    
    2325
    -    mkRule str name nargs f = BuiltinRule
    
    2326
    -      { ru_name = fsLit str
    
    2327
    -      , ru_fn = name
    
    2328
    -      , ru_nargs = nargs
    
    2329
    -      , ru_try = runRuleM $ do
    
    2330
    -          env <- getRuleOpts
    
    2331
    -          guard (roBignumRules env)
    
    2332
    -          f
    
    2333
    -      }
    
    2332
    +    mkRule str name nargs f = mkBasicRule (fsLit str) name nargs rm
    
    2333
    +      where
    
    2334
    +        rm = do { env <- getRuleOpts; guard (roBignumRules env); f }
    
    2334 2335
     
    
    2335 2336
         integer_to_lit str name convert = mkRule str name 1 $ do
    
    2336 2337
           [a0] <- getArgs
    
    ... ... @@ -2506,15 +2507,15 @@ builtinBignumRules =
    2506 2507
     --
    
    2507 2508
     
    
    2508 2509
     -- CString version
    
    2509
    -match_cstring_append_lit_C :: RuleFun
    
    2510
    +match_cstring_append_lit_C :: CFRuleFun CoreExpr
    
    2510 2511
     match_cstring_append_lit_C = match_cstring_append_lit unpackCStringAppendIdKey unpackCStringIdKey
    
    2511 2512
     
    
    2512 2513
     -- CStringUTF8 version
    
    2513
    -match_cstring_append_lit_utf8 :: RuleFun
    
    2514
    +match_cstring_append_lit_utf8 :: CFRuleFun CoreExpr
    
    2514 2515
     match_cstring_append_lit_utf8 = match_cstring_append_lit unpackCStringAppendUtf8IdKey unpackCStringUtf8IdKey
    
    2515 2516
     
    
    2516 2517
     {-# INLINE match_cstring_append_lit #-}
    
    2517
    -match_cstring_append_lit :: Unique -> Unique -> RuleFun
    
    2518
    +match_cstring_append_lit :: Unique -> Unique -> CFRuleFun CoreExpr
    
    2518 2519
     match_cstring_append_lit append_key unpack_key _ env _ [lit1, e2]
    
    2519 2520
       | Just (LitString s1) <- exprIsLiteral_maybe env lit1
    
    2520 2521
       , (strTicks, Var unpk `App` lit2) <- stripStrTopTicks env e2
    
    ... ... @@ -2540,15 +2541,15 @@ match_cstring_append_lit _ _ _ _ _ _ = Nothing
    2540 2541
     -- See also Note [String literals in GHC] in CString.hs
    
    2541 2542
     
    
    2542 2543
     -- CString version
    
    2543
    -match_cstring_foldr_lit_C :: RuleFun
    
    2544
    +match_cstring_foldr_lit_C :: CFRuleFun CoreExpr
    
    2544 2545
     match_cstring_foldr_lit_C = match_cstring_foldr_lit unpackCStringFoldrIdKey
    
    2545 2546
     
    
    2546 2547
     -- CStringUTF8 version
    
    2547
    -match_cstring_foldr_lit_utf8 :: RuleFun
    
    2548
    +match_cstring_foldr_lit_utf8 :: CFRuleFun CoreExpr
    
    2548 2549
     match_cstring_foldr_lit_utf8 = match_cstring_foldr_lit unpackCStringFoldrUtf8IdKey
    
    2549 2550
     
    
    2550 2551
     {-# INLINE match_cstring_foldr_lit #-}
    
    2551
    -match_cstring_foldr_lit :: Unique -> RuleFun
    
    2552
    +match_cstring_foldr_lit :: Unique -> CFRuleFun CoreExpr
    
    2552 2553
     match_cstring_foldr_lit foldVariant _ env _
    
    2553 2554
             [ Type ty1
    
    2554 2555
             , lit1
    
    ... ... @@ -2595,7 +2596,7 @@ stripStrTopTicksT e = stripTicksTopT tickishFloatable e
    2595 2596
     --      eqString (unpackCString# (Lit s1)) (unpackCString# (Lit s2)) = s1==s2
    
    2596 2597
     -- Also  matches unpackCStringUtf8#
    
    2597 2598
     
    
    2598
    -match_eq_string :: RuleFun
    
    2599
    +match_eq_string :: CFRuleFun CoreExpr
    
    2599 2600
     match_eq_string _ env _ [e1, e2]
    
    2600 2601
       | (ticks1, Var unpk1 `App` lit1) <- stripStrTopTicks env e1
    
    2601 2602
       , (ticks2, Var unpk2 `App` lit2) <- stripStrTopTicks env e2
    
    ... ... @@ -2628,7 +2629,7 @@ match_eq_string _ _ _ _ = Nothing
    2628 2629
     -- helpful when using OverloadedStrings to create a ByteString since the
    
    2629 2630
     -- function computing the length of such ByteStrings can often be constant
    
    2630 2631
     -- folded.
    
    2631
    -match_cstring_length :: RuleFun
    
    2632
    +match_cstring_length :: CFRuleFun CoreExpr
    
    2632 2633
     match_cstring_length rule_env env _ [lit1]
    
    2633 2634
       | Just (LitString str) <- exprIsLiteral_maybe env lit1
    
    2634 2635
         -- If elemIndex returns Just, it has the index of the first embedded NUL
    
    ... ... @@ -2676,8 +2677,8 @@ The moving parts are simple:
    2676 2677
       Also, don't forget about 'inline's type argument!
    
    2677 2678
     -}
    
    2678 2679
     
    
    2679
    -match_inline :: [Expr CoreBndr] -> Maybe (Expr CoreBndr)
    
    2680
    -match_inline (Type _ : e : _) = go e
    
    2680
    +match_inline :: CFRuleFun CoreExpr
    
    2681
    +match_inline _ _ _ (Type _ : e : _) = go e
    
    2681 2682
       -- Maybe Monad ahead:
    
    2682 2683
       where
    
    2683 2684
         go (Var f)      = -- Ignore the IdUnfoldingFun here!
    
    ... ... @@ -2689,7 +2690,7 @@ match_inline (Type _ : e : _) = go e
    2689 2690
         go (Tick t e)   = do { app <- go e; pure (Tick t app) }
    
    2690 2691
         go _            = Nothing
    
    2691 2692
     
    
    2692
    -match_inline _ = Nothing
    
    2693
    +match_inline _ _ _ _ = Nothing
    
    2693 2694
     
    
    2694 2695
     --------------------------------------------------------
    
    2695 2696
     -- Note [Constant folding through nested expressions]
    

  • compiler/GHC/Core/Opt/Simplify/Iteration.hs
    ... ... @@ -42,7 +42,7 @@ import GHC.Core.Opt.Arity ( ArityType, exprArity, arityTypeBotSigs_maybe
    42 42
                               , typeArity, arityTypeArity, etaExpandAT )
    
    43 43
     import GHC.Core.SimpleOpt ( exprIsConApp_maybe, joinPointBinding_maybe, joinPointBindings_maybe )
    
    44 44
     import GHC.Core.FVs     ( mkRuleInfo {- exprsFreeIds -} )
    
    45
    -import GHC.Core.Rules   ( RuleMatch(..), lookupRule, getRules )
    
    45
    +import GHC.Core.Rules   ( lookupRule, getRules )
    
    46 46
     import GHC.Core.Multiplicity
    
    47 47
     
    
    48 48
     import GHC.Hs.Extension
    
    ... ... @@ -2486,11 +2486,11 @@ simplOutId env fun cont
    2486 2486
                          else return Nothing
    
    2487 2487
            ; case mb_match of {
    
    2488 2488
                  Just (RM { rm_rule = rule, rm_rhs = rhs
    
    2489
    -                      , rm_args = rhs_args, rm_binds = wrap })
    
    2489
    +                      , rm_args = rhs_args, rm_floats = float_bs })
    
    2490 2490
                       -> simplExprF env rhs' $
    
    2491 2491
                          dropContArgs (ruleArity rule) cont
    
    2492 2492
                       where
    
    2493
    -                    rhs' = GHC.Core.Make.wrapFloats wrap $
    
    2493
    +                    rhs' = GHC.Core.Make.wrapFloats float_bs $
    
    2494 2494
                                mkApps rhs rhs_args
    
    2495 2495
                ; Nothing ->
    
    2496 2496
     
    
    ... ... @@ -2765,15 +2765,15 @@ fireRuleAFTER :: SimplEnv -> RuleMatch
    2765 2765
                   -> SimplM (SimplFloats, CoreExpr)
    
    2766 2766
     fireRuleAFTER env rule_match arg_specs cont
    
    2767 2767
       | RM { rm_rule = rule, rm_rhs = rhs, rm_args = rhs_args
    
    2768
    -       , rm_binds = wrap, rm_bndrs = bndrs } <- rule_match
    
    2769
    -  = do { let env' = env `addNewInScopeIds` bndrs
    
    2768
    +       , rm_floats = float_bs } <- rule_match
    
    2769
    +  = do { let env' = env `addNewInScopeIds` floatsBinders float_bs
    
    2770 2770
            ; (floats, e') <- simplExprF env' rhs $
    
    2771 2771
                              pushOutArgs (exprType rhs) rhs_args $
    
    2772 2772
                              pushArgSpecs (drop (ruleArity rule) arg_specs) cont
    
    2773 2773
            ; return $
    
    2774
    -         if isEmptyFloatBinds wrap  -- Not very pretty
    
    2774
    +         if isEmptyFloatBinds float_bs  -- Not very pretty
    
    2775 2775
              then (floats, e')
    
    2776
    -         else (emptyFloats env', GHC.Core.Make.wrapFloats wrap $
    
    2776
    +         else (emptyFloats env', GHC.Core.Make.wrapFloats float_bs $
    
    2777 2777
                                      wrapFloats floats e') }
    
    2778 2778
     
    
    2779 2779
     
    
    ... ... @@ -3895,10 +3895,10 @@ wrapDataConFloats env wfloats case_bndr cont thing_inside
    3895 3895
         -- scale_float scales case-floats by the multiplicity of the continuation hole
    
    3896 3896
         -- (see Note [Scaling in case-of-case]).
    
    3897 3897
         -- Let floats are _not_ scaled, because they are aliases anyway.
    
    3898
    -    scale_float (GHC.Core.Make.FloatCase scrut case_bndr con vars)
    
    3899
    -      = GHC.Core.Make.FloatCase scrut (scale_id case_bndr) con (map scale_id vars)
    
    3900
    -    scale_float flt@(GHC.Core.Make.FloatLet {})  = flt
    
    3901
    -    scale_float flt@(GHC.Core.Make.FloatTick {}) = flt
    
    3898
    +    scale_float (GHC.Core.FloatCase scrut case_bndr con vars)
    
    3899
    +      = GHC.Core.FloatCase scrut (scale_id case_bndr) con (map scale_id vars)
    
    3900
    +    scale_float flt@(GHC.Core.FloatLet {})  = flt
    
    3901
    +    scale_float flt@(GHC.Core.FloatTick {}) = flt
    
    3902 3902
     
    
    3903 3903
         scale_id id = scaleVarBy holeScaling id
    
    3904 3904
     
    

  • compiler/GHC/Core/Opt/SpecConstr.hs
    ... ... @@ -2906,8 +2906,8 @@ betterPat is (CP { cp_qvars = vs1, cp_args = as1 })
    2906 2906
                  (CP { cp_qvars = vs2, cp_args = as2 })
    
    2907 2907
       | equalLength as1 as2
    
    2908 2908
       = case matchExprs ise vs1 as1 as2 of
    
    2909
    -      Just (ms,_,_) -> all exprIsTrivial ms
    
    2910
    -      Nothing       -> False
    
    2909
    +      Just (ms,_) -> all exprIsTrivial ms
    
    2910
    +      Nothing     -> False
    
    2911 2911
     
    
    2912 2912
       | otherwise -- We must handle patterns of unequal length separately (#24282)
    
    2913 2913
       = False  -- For the pattern with more args, the last arg is "interesting"
    

  • compiler/GHC/Core/Opt/Specialise.hs
    ... ... @@ -1823,8 +1823,8 @@ specLookupRule env fn args is_active rules
    1823 1823
       | otherwise
    
    1824 1824
       = case lookupRule ropts in_scope_env is_active fn args rules of
    
    1825 1825
           Just (RM { rm_rule = rule, rm_rhs = rule_rhs
    
    1826
    -               , rm_binds = wrap, rm_args = rule_args })
    
    1827
    -        -> Just (rule, wrapFloats wrap (mkApps rule_rhs rule_args))
    
    1826
    +               , rm_floats = float_bs, rm_args = rule_args })
    
    1827
    +        -> Just (rule, wrapFloats float_bs (mkApps rule_rhs rule_args))
    
    1828 1828
           Nothing -> Nothing
    
    1829 1829
       where
    
    1830 1830
         dflags       = se_dflags env
    

  • compiler/GHC/Core/Ppr.hs
    ... ... @@ -80,6 +80,12 @@ instance OutputableBndr b => Outputable (Expr b) where
    80 80
     instance OutputableBndr b => Outputable (Alt b) where
    
    81 81
         ppr expr = pprCoreAlt expr
    
    82 82
     
    
    83
    +instance Outputable FloatBind where
    
    84
    +  ppr (FloatTick t) = text "TICK" <+> ppr t
    
    85
    +  ppr (FloatLet b)  = text "LET" <+> ppr b
    
    86
    +  ppr (FloatCase e b c bs) = hang (text "CASE" <+> ppr e <+> text "of" <+> ppr b)
    
    87
    +                                2 (ppr c <+> ppr bs)
    
    88
    +
    
    83 89
     {-
    
    84 90
     ************************************************************************
    
    85 91
     *                                                                      *
    

  • compiler/GHC/Core/Rules.hs
    ... ... @@ -543,22 +543,6 @@ map.
    543 543
     ************************************************************************
    
    544 544
     -}
    
    545 545
     
    
    546
    -data RuleMatch
    
    547
    -  = RM { rm_rule  :: CoreRule
    
    548
    -       , rm_rhs   :: CoreExpr
    
    549
    -       , rm_args  :: [CoreExpr]
    
    550
    -       , rm_binds :: FloatBinds    -- Floated let-bindings
    
    551
    -                                   -- See Note [Matching lets]
    
    552
    -       , rm_bndrs :: [Var]         -- Binders of rm_binds
    
    553
    -       }
    
    554
    -  -- E.g. match  r = RULE forall x,y. f (Just (y,x)) = g x y True
    
    555
    -  --      target f (let v = ev in Just (ey, ex)) ez
    
    556
    -  -- We get the RuleMatch
    
    557
    -  --    RMM { rm_rule = r, rm_rhs = \xy. g x y True
    
    558
    -  --        , rm_args = [ex, ey]
    
    559
    -  --        , rm_binds = Let v=ev, rm_bndrs = [v] )
    
    560
    -  -- The leftover `ez` is not returned; the caller is responsible for
    
    561
    -  -- counting (ruleArity r) arguments
    
    562 546
     
    
    563 547
     -- | The main rule matching function. Attempts to apply all (active)
    
    564 548
     -- supplied rules to this instance of an application in a given
    
    ... ... @@ -592,7 +576,7 @@ lookupRule opts rule_env@(ISE in_scope _) is_active fn args rules
    592 576
         go ms [] = ms
    
    593 577
         go ms (r:rs)
    
    594 578
           | Just rm <- matchRule opts rule_env is_active fn args' rough_args r
    
    595
    -      = go (rm { rm_binds = toOL (map FloatTick ticks) `appOL` rm_binds rm } : ms) rs
    
    579
    +      = go (rm { rm_floats = toOL (map FloatTick ticks) `appOL` rm_floats rm } : ms) rs
    
    596 580
           | otherwise
    
    597 581
           = -- pprTrace "match failed" (ppr r $$ ppr args $$
    
    598 582
             --   ppr [ (arg_id, maybeUnfoldingTemplate unf)
    
    ... ... @@ -741,14 +725,9 @@ matchRule :: HasDebugCallStack
    741 725
     -- of the actual arguments.
    
    742 726
     
    
    743 727
     matchRule opts rule_env _is_active fn args _rough_args
    
    744
    -          rule@(BuiltinRule { ru_try = match_fn })
    
    728
    +          (BuiltinRule { ru_try = match_fn })
    
    745 729
       = do { guard (roBuiltinRules opts)
    
    746
    -       ; rhs <- match_fn opts rule_env fn args
    
    747
    -       ; return (RM { rm_rule = rule
    
    748
    -                    , rm_rhs = rhs
    
    749
    -                    , rm_args = []
    
    750
    -                    , rm_binds = emptyFloatBinds
    
    751
    -                    , rm_bndrs = [] }) }
    
    730
    +       ; match_fn opts rule_env fn args }
    
    752 731
     
    
    753 732
     matchRule _opts rule_env is_active _fn target_es rough_args
    
    754 733
               rule@(Rule { ru_act = act, ru_rough = tpl_tops
    
    ... ... @@ -758,25 +737,22 @@ matchRule _opts rule_env is_active _fn target_es rough_args
    758 737
       | ruleCantMatch tpl_tops rough_args
    
    759 738
       = Nothing
    
    760 739
       | otherwise
    
    761
    -  = do { (matched_es, bind_wrapper, wrap_bndrs)
    
    762
    -            <- matchExprs rule_env tpl_vars tpl_args target_es
    
    763
    -
    
    740
    +  = do { (matched_es, float_bs) <- matchExprs rule_env tpl_vars tpl_args target_es
    
    764 741
             ; return (RM { rm_rule  = rule
    
    765 742
                          , rm_rhs   = mkLams tpl_vars rhs
    
    766 743
                          , rm_args  = matched_es
    
    767
    -                     , rm_binds = bind_wrapper
    
    768
    -                     , rm_bndrs = wrap_bndrs }) }
    
    744
    +                     , rm_floats = float_bs }) }
    
    769 745
     
    
    770 746
     matchExprs :: HasDebugCallStack
    
    771 747
                => InScopeEnv -> [Var] -> [CoreExpr] -> [CoreExpr]
    
    772
    -           -> Maybe ( [CoreExpr]  -- 1-1 with the incoming [Var]
    
    773
    -                    , FloatBinds, [Var])  -- Floated binds
    
    748
    +           -> Maybe ( [CoreExpr]    -- 1-1 with the incoming [Var]
    
    749
    +                    , FloatBinds )  -- Floated binds
    
    774 750
     matchExprs (ISE in_scope id_unf) tmpl_vars tmpl_es target_es
    
    775 751
       = do  { rule_subst <- match_exprs init_menv emptyRuleSubst tmpl_es target_es
    
    776 752
             ; let (_, matched_es) = mapAccumL (lookup_tmpl rule_subst)
    
    777 753
                                               (mkEmptySubst in_scope) $
    
    778 754
                                     tmpl_vars `zip` tmpl_vars1
    
    779
    -        ; return (matched_es, rs_binds rule_subst, rs_bndrs rule_subst) }
    
    755
    +        ; return (matched_es, rs_binds rule_subst) }
    
    780 756
       where
    
    781 757
         (init_rn_env, tmpl_vars1) = mapAccumL rnBndrL (mkRnEnv2 in_scope) tmpl_vars
    
    782 758
                       -- See Note [Cloning the template binders]
    

  • compiler/GHC/CoreToStg/Prep.hs
    ... ... @@ -32,9 +32,9 @@ import GHC.Builtin.Types.Prim
    32 32
     import GHC.Core.Utils
    
    33 33
     import GHC.Core.Opt.Arity
    
    34 34
     import GHC.Core.Lint    ( EndPassConfig(..), endPassIO )
    
    35
    -import GHC.Core
    
    35
    +import GHC.Core hiding( FloatBind(..) )
    
    36 36
     import GHC.Core.Subst
    
    37
    -import GHC.Core.Make hiding( FloatBind(..) )   -- We use our own FloatBind here
    
    37
    +import GHC.Core.Make
    
    38 38
     import GHC.Core.Type
    
    39 39
     import GHC.Core.Coercion
    
    40 40
     import GHC.Core.TyCon
    
    ... ... @@ -2108,6 +2108,8 @@ instance Outputable FloatInfo where
    2108 2108
     
    
    2109 2109
     -- See Note [Floating in CorePrep]
    
    2110 2110
     -- and Note [BindInfo and FloatInfo]
    
    2111
    +-- This data type is very like GHC.Core.FloatBind,
    
    2112
    +-- but with extra info on the let-bindings
    
    2111 2113
     data FloatingBind
    
    2112 2114
       = Float !CoreBind !BindInfo !FloatInfo    -- Never a join-point binding
    
    2113 2115
       | UnsafeEqualityCase !CoreExpr !CoreBndr !AltCon ![CoreBndr]
    

  • compiler/GHC/HsToCore/Pmc/Solver.hs
    ... ... @@ -65,7 +65,7 @@ import GHC.Core.Map.Expr
    65 65
     import GHC.Core.Predicate (typeDeterminesValue, mkNomEqPred)
    
    66 66
     import GHC.Core.SimpleOpt (simpleOptExpr, exprIsConApp_maybe)
    
    67 67
     import GHC.Core.Utils     (exprType)
    
    68
    -import GHC.Core.Make      (mkListExpr, mkCharExpr, mkImpossibleExpr, isEmptyFloatBinds)
    
    68
    +import GHC.Core.Make      (mkListExpr, mkCharExpr, mkImpossibleExpr)
    
    69 69
     
    
    70 70
     import GHC.Data.FastString
    
    71 71
     import GHC.Types.SrcLoc
    

  • compiler/GHC/Types/Id/Make.hs
    ... ... @@ -513,11 +513,7 @@ mkDictSelId name clas
    513 513
     
    
    514 514
         -- This is the built-in rule that goes
    
    515 515
         --      op (dfT d1 d2) --->  opT d1 d2
    
    516
    -    rule = BuiltinRule { ru_name = fsLit "Class op " `appendFS`
    
    517
    -                                     occNameFS (getOccName name)
    
    518
    -                       , ru_fn    = name
    
    519
    -                       , ru_nargs = n_ty_args + 1
    
    520
    -                       , ru_try   = dictSelRule val_index n_ty_args }
    
    516
    +    rule = dictSelRule name n_ty_args val_index
    
    521 517
     
    
    522 518
             -- The strictness signature is of the form U(AAAVAAAA) -> T
    
    523 519
             -- where the V depends on which item we are selecting
    
    ... ... @@ -561,20 +557,35 @@ mkDictSelRhs clas val_index
    561 557
                                     -- varToCoreExpr needed for equality superclass selectors
    
    562 558
                                     --   sel a b d = case x of { MkC _ (g:a~b) _ -> CO g }
    
    563 559
     
    
    564
    -dictSelRule :: Int -> Arity -> RuleFun
    
    560
    +dictSelRule :: Name -> Arity -> Int -> CoreRule
    
    565 561
     -- Tries to persuade the argument to look like a constructor
    
    566 562
     -- application, using exprIsConApp_maybe, and then selects
    
    567 563
     -- from it
    
    568 564
     --       sel_i t1..tk (D t1..tk op1 ... opm) = opi
    
    569 565
     --
    
    570 566
     -- See Note [ClassOp/DFun selection] in GHC.Tc.TyCl.Instance
    
    571
    -dictSelRule val_index n_ty_args _ in_scope_env _ args
    
    572
    -  | (dict_arg : _) <- drop n_ty_args args
    
    573
    -  , Just (_, floats, _, _, con_args)
    
    574
    -             <- exprIsConApp_maybe in_scope_env dict_arg
    
    575
    -  = Just (wrapFloats floats $ getNth con_args val_index)
    
    576
    -  | otherwise
    
    577
    -  = Nothing
    
    567
    +dictSelRule name val_index n_ty_args
    
    568
    +  = rule
    
    569
    +  where
    
    570
    +    rule = BuiltinRule { ru_name = fsLit "Class op " `appendFS`
    
    571
    +                                     occNameFS (getOccName name)
    
    572
    +                       , ru_fn    = name
    
    573
    +                       , ru_nargs = n_ty_args + 1
    
    574
    +                       , ru_try   = try }
    
    575
    +
    
    576
    +
    
    577
    +    try :: RuleFun
    
    578
    +    try _opts in_scope_env _fn args
    
    579
    +      | (dict_arg : _) <- drop n_ty_args args
    
    580
    +      , Just (_, floats, _, _, con_args) <- exprIsConApp_maybe in_scope_env dict_arg
    
    581
    +      , let meth_e = getNth con_args val_index
    
    582
    +            meth_id = mkTemplateLocal 1 (exprType meth_e)
    
    583
    +      = Just (RM { rm_floats = floats
    
    584
    +                 , rm_rhs  = Lam meth_id (Var meth_id)
    
    585
    +                 , rm_args = [meth_e]
    
    586
    +                 , rm_rule = rule })
    
    587
    +      | otherwise
    
    588
    +      = Nothing
    
    578 589
     
    
    579 590
     {-
    
    580 591
     ************************************************************************