Skip to content
  • Sebastian Graf's avatar
    CorePrep: Eliminate EmptyCase and unsafeEqualityProof in CoreToStg instead · 59202c80
    Sebastian Graf authored and Marge Bot's avatar Marge Bot committed
    We eliminate EmptyCase by way of `coreToStg (Case e _ _ []) = coreToStg e` now.
    The main reason is that it plays far better in conjunction with eta expansion
    (as we aim to do for arguments in CorePrep, #23083), because we can discard
    any arguments, `(case e of {}) eta == case e of {}`, whereas in `(e |> co) eta`
    it's impossible to discard the argument.
    
    We do also give the same treatment to unsafeCoerce proofs and treat them as
    trivial iff their RHS is trivial.
    
    It is also both much simpler to describe than the previous mechanism of emitting
    an unsafe coercion and simpler to implement, removing quite a bit of commentary
    and `CorePrepProv`.
    
    In the ghc/alloc perf test `LargeRecord`, we introduce an additional Simplifier
    iteration due to #17910. E.g., FloatOut produces a binding
    ```
    lvl_s6uK [Occ=Once1] :: GHC.Types.Int
    [LclId]
    lvl_s6uK = GHC.Types.I# 2#
    
    lvl_s6uL [Occ=Once1] :: GHC.Types.Any
    [LclId]
    lvl_s6uL
      = case Unsafe.Coerce.unsafeEqualityProof ... of
        { Unsafe.Coerce.UnsafeRefl v2_i6tr -> lvl_s6uK `cast` (... v2_i6tr ...)
        }
    ```
    That occurs once and hence is pre-inlined unconditionally in the next Simplifier
    pass. It's non-trivial to find a way around that, but not really harmful
    otherwise. Hence we accept a 1.2% increase on some architectures.
    
    Metric Increase:
        LargeRecord
    59202c80