Skip to content

TemplateHaskell: RULE TH:lift renders output of lift dependent on optimisation level

This is RULE TH:lift:

liftString :: Quote m => String -> m Exp
-- Used in GHC.Tc.Gen.Expr to short-circuit the lifting for strings
liftString s = return (LitE (StringL s))


-- TH has a special form for literal strings,
-- which we should take advantage of.
-- NB: the lhs of the rule has no args, so that
--     the rule will apply to a 'lift' all on its own
--     which happens to be the way the type checker
--     creates it.
{-# RULES "TH:liftString" lift = liftString #-}

I think we should try to remove it in favor of an overlapping instance for Lift [Char].

One reason is the fact that it only seems to trigger in the auto-specialised definition of lift @[Char].

The main reason is that optimisation may cause this RULE to apply more often, whenever an a in lift @[a] gets substituted to Char, hence lift @[Char]. This means we get either LitE (StringL []) or... ConE (List... []), and the former "potentially more often" than the latter with -O2. I'm convinced that optimisation level should not matter for the syntax produced by Lift, and the overlapping instance achieves this.

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