Skip to content

Disabling worker/wrapper transformation per function

In my branch of GHC I have:

substScaledTyUnchecked :: TCvSubst -> Scaled Type -> Scaled Type
substScaledTyUnchecked subst scaled_ty
  | isEmptyTCvSubst subst = scaled_ty
  | otherwise             = subst_scaled_ty subst scaled_ty

subst_scaled_ty :: TCvSubst -> Scaled Type -> Scaled Type
subst_scaled_ty subst (Scaled m ty) = Scaled m' ty'
  where
    !m'  = subst_ty subst m
    !ty' = subst_ty subst ty

In substScaledTyUnchecked we are careful to preserve sharing if subst is empty. But in Core we get:

-- RHS size: {terms: 19, types: 19, coercions: 0, joins: 0/0}
substScaledTyUnchecked [InlPrag=[2]]
  :: TCvSubst -> Scaled Type -> Scaled Type
[GblId,
 Arity=2,
 Str=<SP(U,MU,U)><SP(U,U)>,
 Cpr=m1,
 Unf=Unf{Src=InlineStable, TopLvl=True, Value=True, ConLike=True,
         WorkFree=True, Expandable=True,
         Guidance=ALWAYS_IF(arity=2,unsat_ok=True,boring_ok=False)
         Tmpl= [...]}]
substScaledTyUnchecked
  = \ (w_s5KK :: TCvSubst) (w1_s5KL :: Scaled Type) ->
      case w_s5KK of { TCvSubst ww1_s5KO ww2_s5KP ww3_s5KQ ->
      case w1_s5KL of { Scaled ww5_s5KU ww6_s5KV ->
      case GHC.Core.TyCo.Subst.$wsubstScaledTyUnchecked
             ww1_s5KO ww2_s5KP ww3_s5KQ ww5_s5KU ww6_s5KV
      of
      { (# ww8_s5Nn, ww9_s5No #) ->
      GHC.Core.TyCo.Rep.Scaled @Type ww8_s5Nn ww9_s5No
      }
      }
      }

-- RHS size: {terms: 47, types: 26, coercions: 6, joins: 0/1}
GHC.Core.TyCo.Subst.$wsubstScaledTyUnchecked [InlPrag=[2]]
  :: InScopeSet
     -> TvSubstEnv -> CvSubstEnv -> Mult -> Type -> (# Mult, Type #)
[GblId,
 Arity=5,
 Str=<U><MU><U><U><U>,
 Unf=Unf{Src=<vanilla>, TopLvl=True, Value=True, ConLike=True,
         WorkFree=True, Expandable=True,
         Guidance=IF_ARGS [0 110 30 0 0] 220 30}]
GHC.Core.TyCo.Subst.$wsubstScaledTyUnchecked
  = \ (ww_s5KO :: InScopeSet)
      (ww1_s5KP :: TvSubstEnv)
      (ww2_s5KQ :: CvSubstEnv)
      (ww3_s5KU :: Mult)
      (ww4_s5KV :: Type) ->
      let {
        wild_Xq [Dmd=UP(U,U,U)] :: TCvSubst
        [LclId, Unf=OtherCon []]
        wild_Xq
          = GHC.Core.TyCo.Subst.TCvSubst ww_s5KO ww1_s5KP ww2_s5KQ } in
      case ww1_s5KP
           `cast` (GHC.Types.Unique.FM.N:UniqFM[0] <Var>_P <Type>_N
                   :: UniqFM Var Type ~R# Data.IntMap.Internal.IntMap Type)
      of {
        __DEFAULT ->
          case subst_ty wild_Xq ww4_s5KV of ty'_a2tY { __DEFAULT ->
          case subst_ty wild_Xq ww3_s5KU of m'_a2tX { __DEFAULT ->
          (# m'_a2tX, ty'_a2tY #)
          }
          };
        Data.IntMap.Internal.Nil ->
          case ww2_s5KQ
               `cast` (GHC.Types.Unique.FM.N:UniqFM[0] <Var>_P <Coercion>_N
                       :: UniqFM Var Coercion ~R# Data.IntMap.Internal.IntMap Coercion)
          of {
            __DEFAULT ->
              case subst_ty wild_Xq ww4_s5KV of ty'_a2tY { __DEFAULT ->
              case subst_ty wild_Xq ww3_s5KU of m'_a2tX { __DEFAULT ->
              (# m'_a2tX, ty'_a2tY #)
              }
              };
            Data.IntMap.Internal.Nil -> (# ww3_s5KU, ww4_s5KV #)
          }
      }

which destroys sharing.

I couldn't find a way to disable this transformation, except with an INLINE pragma (thanks to #19251) or globally with -fno-worker-wrapper but it's not really convenient. Could we add a pragma?

Could be related to #19232 (closed)

To upload designs, you'll need to enable LFS and have an admin enable hashed storage. More information