    {-
    (c) The University of Glasgow 2006
    (c) The GRASP/AQUA Project, Glasgow University, 1992-1998
    -}

    {-# LANGUAGE CPP, DeriveDataTypeable, ScopedTypeVariables #-}
    {-# LANGUAGE StandaloneDeriving #-}
    {-# LANGUAGE FlexibleContexts #-}
    {-# LANGUAGE FlexibleInstances #-}
    {-# LANGUAGE UndecidableInstances #-} -- Wrinkle in Note [Trees That Grow]
                                          -- in module GHC.Hs.Extension
    {-# LANGUAGE ConstraintKinds #-}
    {-# LANGUAGE ExistentialQuantification #-}
    {-# LANGUAGE DeriveFunctor #-}
    {-# LANGUAGE FlexibleInstances #-}
    {-# LANGUAGE TypeFamilies #-}
    {-# LANGUAGE ViewPatterns #-}
    {-# LANGUAGE TypeApplications #-}
    {-# LANGUAGE DataKinds #-}
    {-# LANGUAGE TypeFamilyDependencies #-}
    {-# LANGUAGE LambdaCase #-}

    {-# OPTIONS_GHC -Wno-incomplete-uni-patterns #-}

    -- | Abstract Haskell syntax for expressions.
    module GHC.Hs.Expr where

    #include "HsVersions.h"

    -- friends:
    import GHC.Prelude

    import GHC.Hs.Decls
    import GHC.Hs.Pat
    import GHC.Hs.Lit
    import GHC.Hs.Extension
    import GHC.Hs.Type
    import GHC.Hs.Binds

    -- others:
    import GHC.Tc.Types.Evidence
    import GHC.Core
    import GHC.Types.Name
    import GHC.Types.Name.Set
    import GHC.Types.Basic
    import GHC.Core.ConLike
    import GHC.Types.SrcLoc
    import GHC.Unit.Module (ModuleName)
    import GHC.Utils.Misc
    import GHC.Utils.Outputable
    import GHC.Data.FastString
    import GHC.Core.Type
    import GHC.Builtin.Types (mkTupleStr)
    import GHC.Tc.Utils.TcType (TcType)
    import {-# SOURCE #-} GHC.Tc.Types (TcLclEnv)

    -- libraries:
    import Data.Data hiding (Fixity(..))
    import qualified Data.Data as Data (Fixity(..))
    import qualified Data.Kind
    import Data.Maybe (isJust)

    import GHCi.RemoteTypes ( ForeignRef )
    import qualified Language.Haskell.TH as TH (Q)

    {-
    ************************************************************************
    *                                                                      *
    \subsection{Expressions proper}
    *                                                                      *
    ************************************************************************
    -}

    -- * Expressions proper

    -- | Located Haskell Expression
    type LHsExpr p = Located (HsExpr p)
      -- ^ May have 'GHC.Parser.Annotation.AnnKeywordId' : 'GHC.Parser.Annotation.AnnComma' when
      --   in a list

      -- For details on above see note [Api annotations] in GHC.Parser.Annotation

    -------------------------
    -- | Post-Type checking Expression
    --
    -- PostTcExpr is an evidence expression attached to the syntax tree by the
    -- type checker (c.f. postTcType).
    type PostTcExpr  = HsExpr GhcTc

    -- | Post-Type checking Table
    --
    -- We use a PostTcTable where there are a bunch of pieces of evidence, more
    -- than is convenient to keep individually.
    type PostTcTable = [(Name, PostTcExpr)]

    -------------------------
    {- Note [NoSyntaxExpr]
    ~~~~~~~~~~~~~~~~~~~~~~
    Syntax expressions can be missing (NoSyntaxExprRn or NoSyntaxExprTc)
    for several reasons:

     1. As described in Note [Rebindable if]

     2. In order to suppress "not in scope: xyz" messages when a bit of
        rebindable syntax does not apply. For example, when using an irrefutable
        pattern in a BindStmt, we don't need a `fail` operator.

     3. Rebindable syntax might just not make sense. For example, a BodyStmt
        contains the syntax for `guard`, but that's used only in monad comprehensions.
        If we had more of a whiz-bang type system, we might be able to rule this
        case out statically.
    -}

    -- | Syntax Expression
    --
    -- SyntaxExpr is represents the function used in interpreting rebindable
    -- syntax. In the parser, we have no information to supply; in the renamer,
    -- we have the name of the function (but see
    -- Note [Monad fail : Rebindable syntax, overloaded strings] for a wrinkle)
    -- and in the type-checker we have a more elaborate structure 'SyntaxExprTc'.
    --
    -- In some contexts, rebindable syntax is not implemented, and so we have
    -- constructors to represent that possibility in both the renamer and
    -- typechecker instantiations.
    --
    -- E.g. @(>>=)@ is filled in before the renamer by the appropriate 'Name' for
    --      @(>>=)@, and then instantiated by the type checker with its type args
    --      etc
    type family SyntaxExpr p

    -- Defining SyntaxExpr in two stages allows for better type inference, because
    -- we can declare SyntaxExprGhc to be injective (and closed). Without injectivity,
    -- noSyntaxExpr would be ambiguous.
    type instance SyntaxExpr (GhcPass p) = SyntaxExprGhc p

    type family SyntaxExprGhc (p :: Pass) = (r :: Data.Kind.Type) | r -> p where
      SyntaxExprGhc 'Parsed      = NoExtField
      SyntaxExprGhc 'Renamed     = SyntaxExprRn
      SyntaxExprGhc 'Typechecked = SyntaxExprTc

    -- | The function to use in rebindable syntax. See Note [NoSyntaxExpr].
    data SyntaxExprRn = SyntaxExprRn (HsExpr GhcRn)
        -- Why is the payload not just a Name?
        -- See Note [Monad fail : Rebindable syntax, overloaded strings] in "GHC.Rename.Expr"
                      | NoSyntaxExprRn

    -- | An expression with wrappers, used for rebindable syntax
    --
    -- This should desugar to
    --
    -- > syn_res_wrap $ syn_expr (syn_arg_wraps[0] arg0)
    -- >                         (syn_arg_wraps[1] arg1) ...
    --
    -- where the actual arguments come from elsewhere in the AST.
    data SyntaxExprTc = SyntaxExprTc { SyntaxExprTc -> HsExpr GhcTc
    syn_expr      :: HsExpr GhcTc
                                     , SyntaxExprTc -> [HsWrapper]
    syn_arg_wraps :: [HsWrapper]
                                     , SyntaxExprTc -> HsWrapper
    syn_res_wrap  :: HsWrapper }
                      | NoSyntaxExprTc  -- See Note [NoSyntaxExpr]

    -- | This is used for rebindable-syntax pieces that are too polymorphic
    -- for tcSyntaxOp (trS_fmap and the mzip in ParStmt)
    noExpr :: HsExpr (GhcPass p)
    noExpr :: forall (p :: Pass). HsExpr (GhcPass p)
    noExpr = XLitE (GhcPass p) -> HsLit (GhcPass p) -> HsExpr (GhcPass p)
    forall p. XLitE p -> HsLit p -> HsExpr p
    HsLit NoExtField
    XLitE (GhcPass p)
    noExtField (XHsString (GhcPass p) -> FastString -> HsLit (GhcPass p)
    forall x. XHsString x -> FastString -> HsLit x
    HsString (String -> SourceText
    SourceText  String
    "noExpr") (String -> FastString
    fsLit String
    "noExpr"))

    noSyntaxExpr :: forall p. IsPass p => SyntaxExpr (GhcPass p)
                                  -- Before renaming, and sometimes after
                                  -- See Note [NoSyntaxExpr]
    noSyntaxExpr :: forall (p :: Pass). IsPass p => SyntaxExpr (GhcPass p)
    noSyntaxExpr = case forall (p :: Pass). IsPass p => GhcPass p
    ghcPass @p of
      GhcPass p
    GhcPs -> NoExtField
    SyntaxExpr (GhcPass p)
    noExtField
      GhcPass p
    GhcRn -> SyntaxExpr (GhcPass p)
    SyntaxExprRn
    NoSyntaxExprRn
      GhcPass p
    GhcTc -> SyntaxExpr (GhcPass p)
    SyntaxExprTc
    NoSyntaxExprTc

    -- | Make a 'SyntaxExpr GhcRn' from an expression
    -- Used only in getMonadFailOp.
    -- See Note [Monad fail : Rebindable syntax, overloaded strings] in "GHC.Rename.Expr"
    mkSyntaxExpr :: HsExpr GhcRn -> SyntaxExprRn
    mkSyntaxExpr :: HsExpr GhcRn -> SyntaxExprRn
    mkSyntaxExpr = HsExpr GhcRn -> SyntaxExprRn
    SyntaxExprRn

    -- | Make a 'SyntaxExpr' from a 'Name' (the "rn" is because this is used in the
    -- renamer).
    mkRnSyntaxExpr :: Name -> SyntaxExprRn
    mkRnSyntaxExpr :: Name -> SyntaxExprRn
    mkRnSyntaxExpr Name
    name = HsExpr GhcRn -> SyntaxExprRn
    SyntaxExprRn (HsExpr GhcRn -> SyntaxExprRn) -> HsExpr GhcRn -> SyntaxExprRn
    forall a b. (a -> b) -> a -> b
    $ XVar GhcRn -> Located (IdP GhcRn) -> HsExpr GhcRn
    forall p. XVar p -> Located (IdP p) -> HsExpr p
    HsVar NoExtField
    XVar GhcRn
    noExtField (Located (IdP GhcRn) -> HsExpr GhcRn)
    -> Located (IdP GhcRn) -> HsExpr GhcRn
    forall a b. (a -> b) -> a -> b
    $ Name -> Located Name
    forall e. e -> Located e
    noLoc Name
    name

    instance Outputable SyntaxExprRn where
      ppr :: SyntaxExprRn -> SDoc
    ppr (SyntaxExprRn HsExpr GhcRn
    expr) = HsExpr GhcRn -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr HsExpr GhcRn
    expr
      ppr SyntaxExprRn
    NoSyntaxExprRn      = String -> SDoc
    text String
    "<no syntax expr>"

    instance Outputable SyntaxExprTc where
      ppr :: SyntaxExprTc -> SDoc
    ppr (SyntaxExprTc { syn_expr :: SyntaxExprTc -> HsExpr GhcTc
    syn_expr      = HsExpr GhcTc
    expr
                        , syn_arg_wraps :: SyntaxExprTc -> [HsWrapper]
    syn_arg_wraps = [HsWrapper]
    arg_wraps
                        , syn_res_wrap :: SyntaxExprTc -> HsWrapper
    syn_res_wrap  = HsWrapper
    res_wrap })
        = (SDocContext -> Bool) -> (Bool -> SDoc) -> SDoc
    forall a. (SDocContext -> a) -> (a -> SDoc) -> SDoc
    sdocOption SDocContext -> Bool
    sdocPrintExplicitCoercions ((Bool -> SDoc) -> SDoc) -> (Bool -> SDoc) -> SDoc
    forall a b. (a -> b) -> a -> b
    $ \Bool
    print_co ->
          (Bool -> SDoc) -> SDoc
    getPprDebug ((Bool -> SDoc) -> SDoc) -> (Bool -> SDoc) -> SDoc
    forall a b. (a -> b) -> a -> b
    $ \Bool
    debug ->
          if Bool
    debug Bool -> Bool -> Bool
    || Bool
    print_co
          then HsExpr GhcTc -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr HsExpr GhcTc
    expr SDoc -> SDoc -> SDoc
    <> SDoc -> SDoc
    braces ((HsWrapper -> SDoc) -> [HsWrapper] -> SDoc
    forall a. (a -> SDoc) -> [a] -> SDoc
    pprWithCommas HsWrapper -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr [HsWrapper]
    arg_wraps)
                        SDoc -> SDoc -> SDoc
    <> SDoc -> SDoc
    braces (HsWrapper -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr HsWrapper
    res_wrap)
          else HsExpr GhcTc -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr HsExpr GhcTc
    expr

      ppr SyntaxExprTc
    NoSyntaxExprTc = String -> SDoc
    text String
    "<no syntax expr>"

    -- | Command Syntax Table (for Arrow syntax)
    type CmdSyntaxTable p = [(Name, HsExpr p)]
    -- See Note [CmdSyntaxTable]

    {-
    Note [CmdSyntaxTable]
    ~~~~~~~~~~~~~~~~~~~~~
    Used only for arrow-syntax stuff (HsCmdTop), the CmdSyntaxTable keeps
    track of the methods needed for a Cmd.

    * Before the renamer, this list is an empty list

    * After the renamer, it takes the form @[(std_name, HsVar actual_name)]@
      For example, for the 'arr' method
       * normal case:            (GHC.Control.Arrow.arr, HsVar GHC.Control.Arrow.arr)
       * with rebindable syntax: (GHC.Control.Arrow.arr, arr_22)
                 where @arr_22@ is whatever 'arr' is in scope

    * After the type checker, it takes the form [(std_name, <expression>)]
      where <expression> is the evidence for the method.  This evidence is
      instantiated with the class, but is still polymorphic in everything
      else.  For example, in the case of 'arr', the evidence has type
             forall b c. (b->c) -> a b c
      where 'a' is the ambient type of the arrow.  This polymorphism is
      important because the desugarer uses the same evidence at multiple
      different types.

    This is Less Cool than what we normally do for rebindable syntax, which is to
    make fully-instantiated piece of evidence at every use site.  The Cmd way
    is Less Cool because
      * The renamer has to predict which methods are needed.
        See the tedious GHC.Rename.Expr.methodNamesCmd.

      * The desugarer has to know the polymorphic type of the instantiated
        method. This is checked by Inst.tcSyntaxName, but is less flexible
        than the rest of rebindable syntax, where the type is less
        pre-ordained.  (And this flexibility is useful; for example we can
        typecheck do-notation with (>>=) :: m1 a -> (a -> m2 b) -> m2 b.)
    -}

    -- | A Haskell expression.
    data HsExpr p
      = HsVar     (XVar p)
                  (Located (IdP p)) -- ^ Variable

                                 -- See Note [Located RdrNames]

      | HsUnboundVar (XUnboundVar p)
                     OccName     -- ^ Unbound variable; also used for "holes"
                                 --   (_ or _x).
                                 -- Turned from HsVar to HsUnboundVar by the
                                 --   renamer, when it finds an out-of-scope
                                 --   variable or hole.
                                 -- Turned into HsVar by type checker, to support
                                 --   deferred type errors.

      | HsConLikeOut (XConLikeOut p)
                     ConLike     -- ^ After typechecker only; must be different
                                 -- HsVar for pretty printing

      | HsRecFld  (XRecFld p)
                  (AmbiguousFieldOcc p) -- ^ Variable pointing to record selector
                                        -- Not in use after typechecking

      | HsOverLabel (XOverLabel p)
                    (Maybe (IdP p)) FastString
         -- ^ Overloaded label (Note [Overloaded labels] in GHC.OverloadedLabels)
         --   @Just id@ means @RebindableSyntax@ is in use, and gives the id of the
         --   in-scope 'fromLabel'.
         --   NB: Not in use after typechecking

      | HsIPVar   (XIPVar p)
                  HsIPName   -- ^ Implicit parameter (not in use after typechecking)
      | HsOverLit (XOverLitE p)
                  (HsOverLit p)  -- ^ Overloaded literals

      | HsLit     (XLitE p)
                  (HsLit p)      -- ^ Simple (non-overloaded) literals

      | HsLam     (XLam p)
                  (MatchGroup p (LHsExpr p))
                           -- ^ Lambda abstraction. Currently always a single match
           --
           -- - 'GHC.Parser.Annotation.AnnKeywordId' : 'GHC.Parser.Annotation.AnnLam',
           --       'GHC.Parser.Annotation.AnnRarrow',

           -- For details on above see note [Api annotations] in GHC.Parser.Annotation

      | HsLamCase (XLamCase p) (MatchGroup p (LHsExpr p)) -- ^ Lambda-case
           --
           -- - 'GHC.Parser.Annotation.AnnKeywordId' : 'GHC.Parser.Annotation.AnnLam',
           --           'GHC.Parser.Annotation.AnnCase','GHC.Parser.Annotation.AnnOpen',
           --           'GHC.Parser.Annotation.AnnClose'

           -- For details on above see note [Api annotations] in GHC.Parser.Annotation

      | HsApp     (XApp p) (LHsExpr p) (LHsExpr p) -- ^ Application

      | HsAppType (XAppTypeE p) -- After typechecking: the type argument
                  (LHsExpr p)
                  (LHsWcType (NoGhcTc p))  -- ^ Visible type application
           --
           -- Explicit type argument; e.g  f @Int x y
           -- NB: Has wildcards, but no implicit quantification
           --
           -- - 'GHC.Parser.Annotation.AnnKeywordId' : 'GHC.Parser.Annotation.AnnAt',

      -- | Operator applications:
      -- NB Bracketed ops such as (+) come out as Vars.

      -- NB We need an expr for the operator in an OpApp/Section since
      -- the typechecker may need to apply the operator to a few types.

      | OpApp       (XOpApp p)
                    (LHsExpr p)       -- left operand
                    (LHsExpr p)       -- operator
                    (LHsExpr p)       -- right operand

      -- | Negation operator. Contains the negated expression and the name
      -- of 'negate'
      --
      --  - 'GHC.Parser.Annotation.AnnKeywordId' : 'GHC.Parser.Annotation.AnnMinus'

      -- For details on above see note [Api annotations] in GHC.Parser.Annotation
      | NegApp      (XNegApp p)
                    (LHsExpr p)
                    (SyntaxExpr p)

      -- | - 'GHC.Parser.Annotation.AnnKeywordId' : 'GHC.Parser.Annotation.AnnOpen' @'('@,
      --             'GHC.Parser.Annotation.AnnClose' @')'@

      -- For details on above see note [Api annotations] in GHC.Parser.Annotation
      | HsPar       (XPar p)
                    (LHsExpr p)  -- ^ Parenthesised expr; see Note [Parens in HsSyn]

      | SectionL    (XSectionL p)
                    (LHsExpr p)    -- operand; see Note [Sections in HsSyn]
                    (LHsExpr p)    -- operator
      | SectionR    (XSectionR p)
                    (LHsExpr p)    -- operator; see Note [Sections in HsSyn]
                    (LHsExpr p)    -- operand

      -- | Used for explicit tuples and sections thereof
      --
      --  - 'GHC.Parser.Annotation.AnnKeywordId' : 'GHC.Parser.Annotation.AnnOpen',
      --         'GHC.Parser.Annotation.AnnClose'

      -- For details on above see note [Api annotations] in GHC.Parser.Annotation
      -- Note [ExplicitTuple]
      | ExplicitTuple
            (XExplicitTuple p)
            [LHsTupArg p]
            Boxity

      -- | Used for unboxed sum types
      --
      --  - 'GHC.Parser.Annotation.AnnKeywordId' : 'GHC.Parser.Annotation.AnnOpen' @'(#'@,
      --          'GHC.Parser.Annotation.AnnVbar', 'GHC.Parser.Annotation.AnnClose' @'#)'@,
      --
      --  There will be multiple 'GHC.Parser.Annotation.AnnVbar', (1 - alternative) before
      --  the expression, (arity - alternative) after it
      | ExplicitSum
              (XExplicitSum p)
              ConTag --  Alternative (one-based)
              Arity  --  Sum arity
              (LHsExpr p)

      -- | - 'GHC.Parser.Annotation.AnnKeywordId' : 'GHC.Parser.Annotation.AnnCase',
      --       'GHC.Parser.Annotation.AnnOf','GHC.Parser.Annotation.AnnOpen' @'{'@,
      --       'GHC.Parser.Annotation.AnnClose' @'}'@

      -- For details on above see note [Api annotations] in GHC.Parser.Annotation
      | HsCase      (XCase p)
                    (LHsExpr p)
                    (MatchGroup p (LHsExpr p))

      -- | - 'GHC.Parser.Annotation.AnnKeywordId' : 'GHC.Parser.Annotation.AnnIf',
      --       'GHC.Parser.Annotation.AnnSemi',
      --       'GHC.Parser.Annotation.AnnThen','GHC.Parser.Annotation.AnnSemi',
      --       'GHC.Parser.Annotation.AnnElse',

      -- For details on above see note [Api annotations] in GHC.Parser.Annotation
      | HsIf        (XIf p)        -- GhcPs: this is a Bool; False <=> do not use
                                   --  rebindable syntax
                    (LHsExpr p)    --  predicate
                    (LHsExpr p)    --  then part
                    (LHsExpr p)    --  else part

      -- | Multi-way if
      --
      -- - 'GHC.Parser.Annotation.AnnKeywordId' : 'GHC.Parser.Annotation.AnnIf'
      --       'GHC.Parser.Annotation.AnnOpen','GHC.Parser.Annotation.AnnClose',

      -- For details on above see note [Api annotations] in GHC.Parser.Annotation
      | HsMultiIf   (XMultiIf p) [LGRHS p (LHsExpr p)]

      -- | let(rec)
      --
      -- - 'GHC.Parser.Annotation.AnnKeywordId' : 'GHC.Parser.Annotation.AnnLet',
      --       'GHC.Parser.Annotation.AnnOpen' @'{'@,
      --       'GHC.Parser.Annotation.AnnClose' @'}'@,'GHC.Parser.Annotation.AnnIn'

      -- For details on above see note [Api annotations] in GHC.Parser.Annotation
      | HsLet       (XLet p)
                    (LHsLocalBinds p)
                    (LHsExpr  p)

      -- | - 'GHC.Parser.Annotation.AnnKeywordId' : 'GHC.Parser.Annotation.AnnDo',
      --             'GHC.Parser.Annotation.AnnOpen', 'GHC.Parser.Annotation.AnnSemi',
      --             'GHC.Parser.Annotation.AnnVbar',
      --             'GHC.Parser.Annotation.AnnClose'

      -- For details on above see note [Api annotations] in GHC.Parser.Annotation
      | HsDo        (XDo p)                  -- Type of the whole expression
                    (HsStmtContext GhcRn)    -- The parameterisation is unimportant
                                             -- because in this context we never use
                                             -- the PatGuard or ParStmt variant
                    (Located [ExprLStmt p]) -- "do":one or more stmts

      -- | Syntactic list: [a,b,c,...]
      --
      --  - 'GHC.Parser.Annotation.AnnKeywordId' : 'GHC.Parser.Annotation.AnnOpen' @'['@,
      --              'GHC.Parser.Annotation.AnnClose' @']'@

      -- For details on above see note [Api annotations] in GHC.Parser.Annotation
      -- See Note [Empty lists]
      | ExplicitList
                    (XExplicitList p)  -- Gives type of components of list
                    (Maybe (SyntaxExpr p))
                                       -- For OverloadedLists, the fromListN witness
                    [LHsExpr p]

      -- | Record construction
      --
      --  - 'GHC.Parser.Annotation.AnnKeywordId' : 'GHC.Parser.Annotation.AnnOpen' @'{'@,
      --         'GHC.Parser.Annotation.AnnDotdot','GHC.Parser.Annotation.AnnClose' @'}'@

      -- For details on above see note [Api annotations] in GHC.Parser.Annotation
      | RecordCon
          { forall p. HsExpr p -> XRecordCon p
    rcon_ext      :: XRecordCon p
          , forall p. HsExpr p -> Located (IdP p)
    rcon_con_name :: Located (IdP p)    -- The constructor name;
                                                --  not used after type checking
          , forall p. HsExpr p -> HsRecordBinds p
    rcon_flds     :: HsRecordBinds p }  -- The fields

      -- | Record update
      --
      --  - 'GHC.Parser.Annotation.AnnKeywordId' : 'GHC.Parser.Annotation.AnnOpen' @'{'@,
      --         'GHC.Parser.Annotation.AnnDotdot','GHC.Parser.Annotation.AnnClose' @'}'@

      -- For details on above see note [Api annotations] in GHC.Parser.Annotation
      | RecordUpd
          { forall p. HsExpr p -> XRecordUpd p
    rupd_ext  :: XRecordUpd p
          , forall p. HsExpr p -> LHsExpr p
    rupd_expr :: LHsExpr p
          , forall p. HsExpr p -> [LHsRecUpdField p]
    rupd_flds :: [LHsRecUpdField p]
          }
      -- For a type family, the arg types are of the *instance* tycon,
      -- not the family tycon

      -- | Expression with an explicit type signature. @e :: type@
      --
      --  - 'GHC.Parser.Annotation.AnnKeywordId' : 'GHC.Parser.Annotation.AnnDcolon'

      -- For details on above see note [Api annotations] in GHC.Parser.Annotation
      | ExprWithTySig
                    (XExprWithTySig p)

                    (LHsExpr p)
                    (LHsSigWcType (NoGhcTc p))

      -- | Arithmetic sequence
      --
      --  - 'GHC.Parser.Annotation.AnnKeywordId' : 'GHC.Parser.Annotation.AnnOpen' @'['@,
      --              'GHC.Parser.Annotation.AnnComma','GHC.Parser.Annotation.AnnDotdot',
      --              'GHC.Parser.Annotation.AnnClose' @']'@

      -- For details on above see note [Api annotations] in GHC.Parser.Annotation
      | ArithSeq
                    (XArithSeq p)
                    (Maybe (SyntaxExpr p))
                                      -- For OverloadedLists, the fromList witness
                    (ArithSeqInfo p)

      -- For details on above see note [Api annotations] in GHC.Parser.Annotation

      -----------------------------------------------------------
      -- MetaHaskell Extensions

      -- | - 'GHC.Parser.Annotation.AnnKeywordId' : 'GHC.Parser.Annotation.AnnOpen',
      --         'GHC.Parser.Annotation.AnnOpenE','GHC.Parser.Annotation.AnnOpenEQ',
      --         'GHC.Parser.Annotation.AnnClose','GHC.Parser.Annotation.AnnCloseQ'

      -- For details on above see note [Api annotations] in GHC.Parser.Annotation
      | HsBracket    (XBracket p) (HsBracket p)

        -- See Note [Pending Splices]
      | HsRnBracketOut
          (XRnBracketOut p)
          (HsBracket GhcRn)    -- Output of the renamer is the *original* renamed
                               -- expression, plus
          [PendingRnSplice]    -- _renamed_ splices to be type checked

      | HsTcBracketOut
          (XTcBracketOut p)
          (Maybe QuoteWrapper) -- The wrapper to apply type and dictionary argument
                               -- to the quote.
          (HsBracket GhcRn)    -- Output of the type checker is the *original*
                               -- renamed expression, plus
          [PendingTcSplice]    -- _typechecked_ splices to be
                               -- pasted back in by the desugarer

      -- | - 'GHC.Parser.Annotation.AnnKeywordId' : 'GHC.Parser.Annotation.AnnOpen',
      --         'GHC.Parser.Annotation.AnnClose'

      -- For details on above see note [Api annotations] in GHC.Parser.Annotation
      | HsSpliceE  (XSpliceE p) (HsSplice p)

      -----------------------------------------------------------
      -- Arrow notation extension

      -- | @proc@ notation for Arrows
      --
      --  - 'GHC.Parser.Annotation.AnnKeywordId' : 'GHC.Parser.Annotation.AnnProc',
      --          'GHC.Parser.Annotation.AnnRarrow'

      -- For details on above see note [Api annotations] in GHC.Parser.Annotation
      | HsProc      (XProc p)
                    (LPat p)               -- arrow abstraction, proc
                    (LHsCmdTop p)          -- body of the abstraction
                                           -- always has an empty stack

      ---------------------------------------
      -- static pointers extension
      -- | - 'GHC.Parser.Annotation.AnnKeywordId' : 'GHC.Parser.Annotation.AnnStatic',

      -- For details on above see note [Api annotations] in GHC.Parser.Annotation
      | HsStatic (XStatic p) -- Free variables of the body
                 (LHsExpr p)        -- Body

      ---------------------------------------
      -- Haskell program coverage (Hpc) Support

      | HsTick
         (XTick p)
         (Tickish (IdP p))
         (LHsExpr p)                       -- sub-expression

      | HsBinTick
         (XBinTick p)
         Int                                -- module-local tick number for True
         Int                                -- module-local tick number for False
         (LHsExpr p)                        -- sub-expression

      ---------------------------------------
      -- Expressions annotated with pragmas, written as {-# ... #-}
      | HsPragE (XPragE p) (HsPragE p) (LHsExpr p)

      | XExpr       !(XXExpr p)
      -- Note [Trees that Grow] extension constructor for the
      -- general idea, and Note [Rebindable syntax and HsExpansion]
      -- for an example of how we use it.

    -- | Extra data fields for a 'RecordCon', added by the type checker
    data RecordConTc = RecordConTc
          { RecordConTc -> ConLike
    rcon_con_like :: ConLike      -- The data constructor or pattern synonym
          , RecordConTc -> HsExpr GhcTc
    rcon_con_expr :: PostTcExpr   -- Instantiated constructor function
          }

    -- | Extra data fields for a 'RecordUpd', added by the type checker
    data RecordUpdTc = RecordUpdTc
          { RecordUpdTc -> [ConLike]
    rupd_cons :: [ConLike]
                    -- Filled in by the type checker to the
                    -- _non-empty_ list of DataCons that have
                    -- all the upd'd fields

          , RecordUpdTc -> [Type]
    rupd_in_tys  :: [Type]  -- Argument types of *input* record type
          , RecordUpdTc -> [Type]
    rupd_out_tys :: [Type]  --             and  *output* record type
                    -- For a data family, these are the type args of the
                    -- /representation/ type constructor

          , RecordUpdTc -> HsWrapper
    rupd_wrap :: HsWrapper  -- See note [Record Update HsWrapper]
          }

    -- | HsWrap appears only in typechecker output
    -- Invariant: The contained Expr is *NOT* itself an HsWrap.
    -- See Note [Detecting forced eta expansion] in "GHC.HsToCore.Expr".
    -- This invariant is maintained by 'GHC.Hs.Utils.mkHsWrap'.
    -- hs_syn is something like HsExpr or HsCmd
    data HsWrap hs_syn = HsWrap HsWrapper      -- the wrapper
                                (hs_syn GhcTc) -- the thing that is wrapped

    deriving instance (Data (hs_syn GhcTc), Typeable hs_syn) => Data (HsWrap hs_syn)

    -- ---------------------------------------------------------------------

    type instance XVar           (GhcPass _) = NoExtField
    type instance XUnboundVar    (GhcPass _) = NoExtField
    type instance XConLikeOut    (GhcPass _) = NoExtField
    type instance XRecFld        (GhcPass _) = NoExtField
    type instance XOverLabel     (GhcPass _) = NoExtField
    type instance XIPVar         (GhcPass _) = NoExtField
    type instance XOverLitE      (GhcPass _) = NoExtField
    type instance XLitE          (GhcPass _) = NoExtField
    type instance XLam           (GhcPass _) = NoExtField
    type instance XLamCase       (GhcPass _) = NoExtField
    type instance XApp           (GhcPass _) = NoExtField

    type instance XAppTypeE      GhcPs = NoExtField
    type instance XAppTypeE      GhcRn = NoExtField
    type instance XAppTypeE      GhcTc = Type

    type instance XOpApp         GhcPs = NoExtField
    type instance XOpApp         GhcRn = Fixity
    type instance XOpApp         GhcTc = Fixity

    type instance XNegApp        (GhcPass _) = NoExtField
    type instance XPar           (GhcPass _) = NoExtField
    type instance XSectionL      (GhcPass _) = NoExtField
    type instance XSectionR      (GhcPass _) = NoExtField
    type instance XExplicitTuple (GhcPass _) = NoExtField

    type instance XExplicitSum   GhcPs = NoExtField
    type instance XExplicitSum   GhcRn = NoExtField
    type instance XExplicitSum   GhcTc = [Type]

    type instance XCase          (GhcPass _) = NoExtField

    type instance XIf            (GhcPass _) = NoExtField

    type instance XMultiIf       GhcPs = NoExtField
    type instance XMultiIf       GhcRn = NoExtField
    type instance XMultiIf       GhcTc = Type

    type instance XLet           (GhcPass _) = NoExtField

    type instance XDo            GhcPs = NoExtField
    type instance XDo            GhcRn = NoExtField
    type instance XDo            GhcTc = Type

    type instance XExplicitList  GhcPs = NoExtField
    type instance XExplicitList  GhcRn = NoExtField
    type instance XExplicitList  GhcTc = Type

    type instance XRecordCon     GhcPs = NoExtField
    type instance XRecordCon     GhcRn = NoExtField
    type instance XRecordCon     GhcTc = RecordConTc

    type instance XRecordUpd     GhcPs = NoExtField
    type instance XRecordUpd     GhcRn = NoExtField
    type instance XRecordUpd     GhcTc = RecordUpdTc

    type instance XExprWithTySig (GhcPass _) = NoExtField

    type instance XArithSeq      GhcPs = NoExtField
    type instance XArithSeq      GhcRn = NoExtField
    type instance XArithSeq      GhcTc = PostTcExpr

    type instance XBracket       (GhcPass _) = NoExtField

    type instance XRnBracketOut  (GhcPass _) = NoExtField
    type instance XTcBracketOut  (GhcPass _) = NoExtField

    type instance XSpliceE       (GhcPass _) = NoExtField
    type instance XProc          (GhcPass _) = NoExtField

    type instance XStatic        GhcPs = NoExtField
    type instance XStatic        GhcRn = NameSet
    type instance XStatic        GhcTc = NameSet

    type instance XTick          (GhcPass _) = NoExtField
    type instance XBinTick       (GhcPass _) = NoExtField

    type instance XPragE         (GhcPass _) = NoExtField

    type instance XXExpr         GhcPs       = NoExtCon

    -- See Note [Rebindable syntax and HsExpansion] below
    type instance XXExpr         GhcRn       = HsExpansion (HsExpr GhcRn)
                                                           (HsExpr GhcRn)
    type instance XXExpr         GhcTc       = XXExprGhcTc

    data XXExprGhcTc
      = WrapExpr {-# UNPACK #-} !(HsWrap HsExpr)
      | ExpansionExpr {-# UNPACK #-} !(HsExpansion (HsExpr GhcRn) (HsExpr GhcTc))

    {-
    Note [Rebindable syntax and HsExpansion]
    ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

    We implement rebindable syntax (RS) support by performing a desugaring
    in the renamer. We transform GhcPs expressions affected by RS into the
    appropriate desugared form, but **annotated with the original expression**.

    Let us consider a piece of code like:

        {-# LANGUAGE RebindableSyntax #-}
        ifThenElse :: Char -> () -> () -> ()
        ifThenElse _ _ _ = ()
        x = if 'a' then () else True

    The parsed AST for the RHS of x would look something like (slightly simplified):

        L locif (HsIf (L loca 'a') (L loctrue ()) (L locfalse True))

    Upon seeing such an AST with RS on, we could transform it into a
    mere function call, as per the RS rules, equivalent to the
    following function application:

        ifThenElse 'a' () True

    which doesn't typecheck. But GHC would report an error about
    not being able to match the third argument's type (Bool) with the
    expected type: (), in the expression _as desugared_, i.e in
    the aforementioned function application. But the user never
    wrote a function application! This would be pretty bad.

    To remedy this, instead of transforming the original HsIf
    node into mere applications of 'ifThenElse', we keep the
    original 'if' expression around too, using the TTG
    XExpr extension point to allow GHC to construct an
    'HsExpansion' value that will keep track of the original
    expression in its first field, and the desugared one in the
    second field. The resulting renamed AST would look like:

        L locif (XExpr
          (HsExpanded
            (HsIf (L loca 'a')
                  (L loctrue ())
                  (L locfalse True)
            )
            (App (L generatedSrcSpan
                    (App (L generatedSrcSpan
                            (App (L generatedSrcSpan (Var ifThenElse))
                                 (L loca 'a')
                            )
                         )
                         (L loctrue ())
                    )
                 )
                 (L locfalse True)
            )
          )
        )

    When comes the time to typecheck the program, we end up calling
    tcMonoExpr on the AST above. If this expression gives rise to
    a type error, then it will appear in a context line and GHC
    will pretty-print it using the 'Outputable (HsExpansion a b)'
    instance defined below, which *only prints the original
    expression*. This is the gist of the idea, but is not quite
    enough to recover the error messages that we had with the
    SyntaxExpr-based, typechecking/desugaring-to-core time
    implementation of rebindable syntax. The key idea is to decorate
    some elements of the desugared expression so as to be able to
    give them a special treatment when typechecking the desugared
    expression, to print a different context line or skip one
    altogether.

    Whenever we 'setSrcSpan' a 'generatedSrcSpan', we update a field in
    TcLclEnv called 'tcl_in_gen_code', setting it to True, which indicates that we
    entered generated code, i.e code fabricated by the compiler when rebinding some
    syntax. If someone tries to push some error context line while that field is set
    to True, the pushing won't actually happen and the context line is just dropped.
    Once we 'setSrcSpan' a real span (for an expression that was in the original
    source code), we set 'tcl_in_gen_code' back to False, indicating that we
    "emerged from the generated code tunnel", and that the expressions we will be
    processing are relevant to report in context lines again.

    You might wonder why we store a RealSrcSpan in addition to a Bool in
    the TcLclEnv: could we not store a Maybe RealSrcSpan? The problem is
    that we still generate constraints when processing generated code,
    and a CtLoc must contain a RealSrcSpan -- otherwise, error messages
    might appear without source locations. So we keep the RealSrcSpan of
    the last location spotted that wasn't generated; it's as good as
    we're going to get in generated code. Once we get to sub-trees that
    are not generated, then we update the RealSrcSpan appropriately, and
    set the tcl_in_gen_code Bool to False.

    ---

    A general recipe to follow this approach for new constructs could go as follows:

    - Remove any GhcRn-time SyntaxExpr extensions to the relevant constructor for your
      construct, in HsExpr or related syntax data types.
    - At renaming-time:
        - take your original node of interest (HsIf above)
        - rename its subexpressions (condition, true branch, false branch above)
        - construct the suitable "rebound"-and-renamed result (ifThenElse call
          above), where the 'SrcSpan' attached to any _fabricated node_ (the
          HsVar/HsApp nodes, above) is set to 'generatedSrcSpan'
        - take both the original node and that rebound-and-renamed result and wrap
          them in an XExpr: XExpr (HsExpanded <original node> <desugared>)
     - At typechecking-time:
        - remove any logic that was previously dealing with your rebindable
          construct, typically involving [tc]SyntaxOp, SyntaxExpr and friends.
        - the XExpr (HsExpanded ... ...) case in tcExpr already makes sure that we
          typecheck the desugared expression while reporting the original one in
          errors

    -}

    -- See Note [Rebindable syntax and HsExpansion] just above.
    data HsExpansion a b
      = HsExpanded a b
      deriving Typeable (HsExpansion a b)
    Typeable (HsExpansion a b)
    -> (forall (c :: * -> *).
        (forall d b. Data d => c (d -> b) -> d -> c b)
        -> (forall g. g -> c g) -> HsExpansion a b -> c (HsExpansion a b))
    -> (forall (c :: * -> *).
        (forall b r. Data b => c (b -> r) -> c r)
        -> (forall r. r -> c r) -> Constr -> c (HsExpansion a b))
    -> (HsExpansion a b -> Constr)
    -> (HsExpansion a b -> DataType)
    -> (forall (t :: * -> *) (c :: * -> *).
        Typeable t =>
        (forall d. Data d => c (t d)) -> Maybe (c (HsExpansion a b)))
    -> (forall (t :: * -> * -> *) (c :: * -> *).
        Typeable t =>
        (forall d e. (Data d, Data e) => c (t d e))
        -> Maybe (c (HsExpansion a b)))
    -> ((forall b. Data b => b -> b)
        -> HsExpansion a b -> HsExpansion a b)
    -> (forall r r'.
        (r -> r' -> r)
        -> r -> (forall d. Data d => d -> r') -> HsExpansion a b -> r)
    -> (forall r r'.
        (r' -> r -> r)
        -> r -> (forall d. Data d => d -> r') -> HsExpansion a b -> r)
    -> (forall u.
        (forall d. Data d => d -> u) -> HsExpansion a b -> [u])
    -> (forall u.
        Int -> (forall d. Data d => d -> u) -> HsExpansion a b -> u)
    -> (forall (m :: * -> *).
        Monad m =>
        (forall d. Data d => d -> m d)
        -> HsExpansion a b -> m (HsExpansion a b))
    -> (forall (m :: * -> *).
        MonadPlus m =>
        (forall d. Data d => d -> m d)
        -> HsExpansion a b -> m (HsExpansion a b))
    -> (forall (m :: * -> *).
        MonadPlus m =>
        (forall d. Data d => d -> m d)
        -> HsExpansion a b -> m (HsExpansion a b))
    -> Data (HsExpansion a b)
    HsExpansion a b -> DataType
    HsExpansion a b -> Constr
    (forall b. Data b => b -> b) -> HsExpansion a b -> HsExpansion a b
    forall a.
    Typeable a
    -> (forall (c :: * -> *).
        (forall d b. Data d => c (d -> b) -> d -> c b)
        -> (forall g. g -> c g) -> a -> c a)
    -> (forall (c :: * -> *).
        (forall b r. Data b => c (b -> r) -> c r)
        -> (forall r. r -> c r) -> Constr -> c a)
    -> (a -> Constr)
    -> (a -> DataType)
    -> (forall (t :: * -> *) (c :: * -> *).
        Typeable t =>
        (forall d. Data d => c (t d)) -> Maybe (c a))
    -> (forall (t :: * -> * -> *) (c :: * -> *).
        Typeable t =>
        (forall d e. (Data d, Data e) => c (t d e)) -> Maybe (c a))
    -> ((forall b. Data b => b -> b) -> a -> a)
    -> (forall r r'.
        (r -> r' -> r) -> r -> (forall d. Data d => d -> r') -> a -> r)
    -> (forall r r'.
        (r' -> r -> r) -> r -> (forall d. Data d => d -> r') -> a -> r)
    -> (forall u. (forall d. Data d => d -> u) -> a -> [u])
    -> (forall u. Int -> (forall d. Data d => d -> u) -> a -> u)
    -> (forall (m :: * -> *).
        Monad m =>
        (forall d. Data d => d -> m d) -> a -> m a)
    -> (forall (m :: * -> *).
        MonadPlus m =>
        (forall d. Data d => d -> m d) -> a -> m a)
    -> (forall (m :: * -> *).
        MonadPlus m =>
        (forall d. Data d => d -> m d) -> a -> m a)
    -> Data a
    forall u.
    Int -> (forall d. Data d => d -> u) -> HsExpansion a b -> u
    forall u. (forall d. Data d => d -> u) -> HsExpansion a b -> [u]
    forall {a} {b}. (Data a, Data b) => Typeable (HsExpansion a b)
    forall a b. (Data a, Data b) => HsExpansion a b -> DataType
    forall a b. (Data a, Data b) => HsExpansion a b -> Constr
    forall a b.
    (Data a, Data b) =>
    (forall b. Data b => b -> b) -> HsExpansion a b -> HsExpansion a b
    forall a b u.
    (Data a, Data b) =>
    Int -> (forall d. Data d => d -> u) -> HsExpansion a b -> u
    forall a b u.
    (Data a, Data b) =>
    (forall d. Data d => d -> u) -> HsExpansion a b -> [u]
    forall a b r r'.
    (Data a, Data b) =>
    (r -> r' -> r)
    -> r -> (forall d. Data d => d -> r') -> HsExpansion a b -> r
    forall a b r r'.
    (Data a, Data b) =>
    (r' -> r -> r)
    -> r -> (forall d. Data d => d -> r') -> HsExpansion a b -> r
    forall a b (m :: * -> *).
    (Data a, Data b, Monad m) =>
    (forall d. Data d => d -> m d)
    -> HsExpansion a b -> m (HsExpansion a b)
    forall a b (m :: * -> *).
    (Data a, Data b, MonadPlus m) =>
    (forall d. Data d => d -> m d)
    -> HsExpansion a b -> m (HsExpansion a b)
    forall a b (c :: * -> *).
    (Data a, Data b) =>
    (forall b r. Data b => c (b -> r) -> c r)
    -> (forall r. r -> c r) -> Constr -> c (HsExpansion a b)
    forall a b (c :: * -> *).
    (Data a, Data b) =>
    (forall d b. Data d => c (d -> b) -> d -> c b)
    -> (forall g. g -> c g) -> HsExpansion a b -> c (HsExpansion a b)
    forall a b (t :: * -> *) (c :: * -> *).
    (Data a, Data b, Typeable t) =>
    (forall d. Data d => c (t d)) -> Maybe (c (HsExpansion a b))
    forall a b (t :: * -> * -> *) (c :: * -> *).
    (Data a, Data b, Typeable t) =>
    (forall d e. (Data d, Data e) => c (t d e))
    -> Maybe (c (HsExpansion a b))
    forall r r'.
    (r -> r' -> r)
    -> r -> (forall d. Data d => d -> r') -> HsExpansion a b -> r
    forall r r'.
    (r' -> r -> r)
    -> r -> (forall d. Data d => d -> r') -> HsExpansion a b -> r
    forall (m :: * -> *).
    Monad m =>
    (forall d. Data d => d -> m d)
    -> HsExpansion a b -> m (HsExpansion a b)
    forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d)
    -> HsExpansion a b -> m (HsExpansion a b)
    forall (c :: * -> *).
    (forall b r. Data b => c (b -> r) -> c r)
    -> (forall r. r -> c r) -> Constr -> c (HsExpansion a b)
    forall (c :: * -> *).
    (forall d b. Data d => c (d -> b) -> d -> c b)
    -> (forall g. g -> c g) -> HsExpansion a b -> c (HsExpansion a b)
    forall (t :: * -> *) (c :: * -> *).
    Typeable t =>
    (forall d. Data d => c (t d)) -> Maybe (c (HsExpansion a b))
    forall (t :: * -> * -> *) (c :: * -> *).
    Typeable t =>
    (forall d e. (Data d, Data e) => c (t d e))
    -> Maybe (c (HsExpansion a b))
    gmapMo :: forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d)
    -> HsExpansion a b -> m (HsExpansion a b)
    $cgmapMo :: forall a b (m :: * -> *).
    (Data a, Data b, MonadPlus m) =>
    (forall d. Data d => d -> m d)
    -> HsExpansion a b -> m (HsExpansion a b)
    gmapMp :: forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d)
    -> HsExpansion a b -> m (HsExpansion a b)
    $cgmapMp :: forall a b (m :: * -> *).
    (Data a, Data b, MonadPlus m) =>
    (forall d. Data d => d -> m d)
    -> HsExpansion a b -> m (HsExpansion a b)
    gmapM :: forall (m :: * -> *).
    Monad m =>
    (forall d. Data d => d -> m d)
    -> HsExpansion a b -> m (HsExpansion a b)
    $cgmapM :: forall a b (m :: * -> *).
    (Data a, Data b, Monad m) =>
    (forall d. Data d => d -> m d)
    -> HsExpansion a b -> m (HsExpansion a b)
    gmapQi :: forall u.
    Int -> (forall d. Data d => d -> u) -> HsExpansion a b -> u
    $cgmapQi :: forall a b u.
    (Data a, Data b) =>
    Int -> (forall d. Data d => d -> u) -> HsExpansion a b -> u
    gmapQ :: forall u. (forall d. Data d => d -> u) -> HsExpansion a b -> [u]
    $cgmapQ :: forall a b u.
    (Data a, Data b) =>
    (forall d. Data d => d -> u) -> HsExpansion a b -> [u]
    gmapQr :: forall r r'.
    (r' -> r -> r)
    -> r -> (forall d. Data d => d -> r') -> HsExpansion a b -> r
    $cgmapQr :: forall a b r r'.
    (Data a, Data b) =>
    (r' -> r -> r)
    -> r -> (forall d. Data d => d -> r') -> HsExpansion a b -> r
    gmapQl :: forall r r'.
    (r -> r' -> r)
    -> r -> (forall d. Data d => d -> r') -> HsExpansion a b -> r
    $cgmapQl :: forall a b r r'.
    (Data a, Data b) =>
    (r -> r' -> r)
    -> r -> (forall d. Data d => d -> r') -> HsExpansion a b -> r
    gmapT :: (forall b. Data b => b -> b) -> HsExpansion a b -> HsExpansion a b
    $cgmapT :: forall a b.
    (Data a, Data b) =>
    (forall b. Data b => b -> b) -> HsExpansion a b -> HsExpansion a b
    dataCast2 :: forall (t :: * -> * -> *) (c :: * -> *).
    Typeable t =>
    (forall d e. (Data d, Data e) => c (t d e))
    -> Maybe (c (HsExpansion a b))
    $cdataCast2 :: forall a b (t :: * -> * -> *) (c :: * -> *).
    (Data a, Data b, Typeable t) =>
    (forall d e. (Data d, Data e) => c (t d e))
    -> Maybe (c (HsExpansion a b))
    dataCast1 :: forall (t :: * -> *) (c :: * -> *).
    Typeable t =>
    (forall d. Data d => c (t d)) -> Maybe (c (HsExpansion a b))
    $cdataCast1 :: forall a b (t :: * -> *) (c :: * -> *).
    (Data a, Data b, Typeable t) =>
    (forall d. Data d => c (t d)) -> Maybe (c (HsExpansion a b))
    dataTypeOf :: HsExpansion a b -> DataType
    $cdataTypeOf :: forall a b. (Data a, Data b) => HsExpansion a b -> DataType
    toConstr :: HsExpansion a b -> Constr
    $ctoConstr :: forall a b. (Data a, Data b) => HsExpansion a b -> Constr
    gunfold :: forall (c :: * -> *).
    (forall b r. Data b => c (b -> r) -> c r)
    -> (forall r. r -> c r) -> Constr -> c (HsExpansion a b)
    $cgunfold :: forall a b (c :: * -> *).
    (Data a, Data b) =>
    (forall b r. Data b => c (b -> r) -> c r)
    -> (forall r. r -> c r) -> Constr -> c (HsExpansion a b)
    gfoldl :: forall (c :: * -> *).
    (forall d b. Data d => c (d -> b) -> d -> c b)
    -> (forall g. g -> c g) -> HsExpansion a b -> c (HsExpansion a b)
    $cgfoldl :: forall a b (c :: * -> *).
    (Data a, Data b) =>
    (forall d b. Data d => c (d -> b) -> d -> c b)
    -> (forall g. g -> c g) -> HsExpansion a b -> c (HsExpansion a b)
    Data

    -- | Build a "wrapped" 'HsExpansion' out of an extension constructor,
    --   and the two components of the expansion: original and desugared
    --   expressions.
    --
    --   See Note [Rebindable Syntax and HsExpansion] above for more details.
    mkExpanded
      :: (HsExpansion a b -> b) -- ^ XExpr, XCmd, ...
      -> a                      -- ^ source expression ('GhcPs')
      -> b                      -- ^ "desugared" expression
                                --   ('GhcRn')
      -> b                      -- ^ suitably wrapped
                                --   'HsExpansion'
    mkExpanded :: forall a b. (HsExpansion a b -> b) -> a -> b -> b
    mkExpanded HsExpansion a b -> b
    xwrap a
    a b
    b = HsExpansion a b -> b
    xwrap (a -> b -> HsExpansion a b
    forall a b. a -> b -> HsExpansion a b
    HsExpanded a
    a b
    b)

    -- | Just print the original expression (the @a@).
    instance (Outputable a, Outputable b) => Outputable (HsExpansion a b) where
      ppr :: HsExpansion a b -> SDoc
    ppr (HsExpanded a
    a b
    b) = SDoc -> SDoc -> SDoc
    ifPprDebug ([SDoc] -> SDoc
    vcat [a -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr a
    a, b -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr b
    b]) (a -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr a
    a)

    -- ---------------------------------------------------------------------

    -- | A pragma, written as {-# ... #-}, that may appear within an expression.
    data HsPragE p
      = HsPragSCC   (XSCC p)
                    SourceText            -- Note [Pragma source text] in GHC.Types.Basic
                    StringLiteral         -- "set cost centre" SCC pragma

      -- | - 'GHC.Parser.Annotation.AnnKeywordId' : 'GHC.Parser.Annotation.AnnOpen',
      --       'GHC.Parser.Annotation.AnnOpen' @'{-\# GENERATED'@,
      --       'GHC.Parser.Annotation.AnnVal','GHC.Parser.Annotation.AnnVal',
      --       'GHC.Parser.Annotation.AnnColon','GHC.Parser.Annotation.AnnVal',
      --       'GHC.Parser.Annotation.AnnMinus',
      --       'GHC.Parser.Annotation.AnnVal','GHC.Parser.Annotation.AnnColon',
      --       'GHC.Parser.Annotation.AnnVal',
      --       'GHC.Parser.Annotation.AnnClose' @'\#-}'@

      -- For details on above see note [Api annotations] in GHC.Parser.Annotation
      | HsPragTick                        -- A pragma introduced tick
         (XTickPragma p)
         SourceText                       -- Note [Pragma source text] in GHC.Types.Basic
         (StringLiteral,(Int,Int),(Int,Int))
                                          -- external span for this tick
         ((SourceText,SourceText),(SourceText,SourceText))
            -- Source text for the four integers used in the span.
            -- See note [Pragma source text] in GHC.Types.Basic

      | XHsPragE !(XXPragE p)

    type instance XSCC           (GhcPass _) = NoExtField
    type instance XCoreAnn       (GhcPass _) = NoExtField
    type instance XTickPragma    (GhcPass _) = NoExtField
    type instance XXPragE        (GhcPass _) = NoExtCon

    -- | Located Haskell Tuple Argument
    --
    -- 'HsTupArg' is used for tuple sections
    -- @(,a,)@ is represented by
    -- @ExplicitTuple [Missing ty1, Present a, Missing ty3]@
    -- Which in turn stands for @(\x:ty1 \y:ty2. (x,a,y))@
    type LHsTupArg id = Located (HsTupArg id)
    -- | - 'GHC.Parser.Annotation.AnnKeywordId' : 'GHC.Parser.Annotation.AnnComma'

    -- For details on above see note [Api annotations] in GHC.Parser.Annotation

    -- | Haskell Tuple Argument
    data HsTupArg id
      = Present (XPresent id) (LHsExpr id)     -- ^ The argument
      | Missing (XMissing id)    -- ^ The argument is missing, but this is its type
      | XTupArg !(XXTupArg id)   -- ^ Note [Trees that Grow] extension point

    type instance XPresent         (GhcPass _) = NoExtField

    type instance XMissing         GhcPs = NoExtField
    type instance XMissing         GhcRn = NoExtField
    type instance XMissing         GhcTc = Scaled Type

    type instance XXTupArg         (GhcPass _) = NoExtCon

    tupArgPresent :: LHsTupArg id -> Bool
    tupArgPresent :: forall id. LHsTupArg id -> Bool
    tupArgPresent (L SrcSpan
    _ (Present {})) = Bool
    True
    tupArgPresent (L SrcSpan
    _ (Missing {})) = Bool
    False
    tupArgPresent (L SrcSpan
    _ (XTupArg {})) = Bool
    False

    {-
    Note [Parens in HsSyn]
    ~~~~~~~~~~~~~~~~~~~~~~
    HsPar (and ParPat in patterns, HsParTy in types) is used as follows

      * HsPar is required; the pretty printer does not add parens.

      * HsPars are respected when rearranging operator fixities.
        So   a * (b + c)  means what it says (where the parens are an HsPar)

      * For ParPat and HsParTy the pretty printer does add parens but this should be
        a no-op for ParsedSource, based on the pretty printer round trip feature
        introduced in
        https://phabricator.haskell.org/rGHC499e43824bda967546ebf95ee33ec1f84a114a7c

      * ParPat and HsParTy are pretty printed as '( .. )' regardless of whether or
        not they are strictly necessary. This should be addressed when #13238 is
        completed, to be treated the same as HsPar.

    Note [Sections in HsSyn]
    ~~~~~~~~~~~~~~~~~~~~~~~~
    Sections should always appear wrapped in an HsPar, thus
             HsPar (SectionR ...)
    The parser parses sections in a wider variety of situations
    (See Note [Parsing sections]), but the renamer checks for those
    parens.  This invariant makes pretty-printing easier; we don't need
    a special case for adding the parens round sections.

    Note [Rebindable if]
    ~~~~~~~~~~~~~~~~~~~~
    The rebindable syntax for 'if' is a bit special, because when
    rebindable syntax is *off* we do not want to treat
       (if c then t else e)
    as if it was an application (ifThenElse c t e).  Why not?
    Because we allow an 'if' to return *unboxed* results, thus
      if blah then 3# else 4#
    whereas that would not be possible using a all to a polymorphic function
    (because you can't call a polymorphic function at an unboxed type).

    So we use NoSyntaxExpr to mean "use the old built-in typing rule".

    A further complication is that, in the `deriving` code, we never want
    to use rebindable syntax. So, even in GhcPs, we want to denote whether
    to use rebindable syntax or not. This is done via the type instance
    for XIf GhcPs.

    Note [Record Update HsWrapper]
    ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
    There is a wrapper in RecordUpd which is used for the *required*
    constraints for pattern synonyms. This wrapper is created in the
    typechecking and is then directly used in the desugaring without
    modification.

    For example, if we have the record pattern synonym P,
      pattern P :: (Show a) => a -> Maybe a
      pattern P{x} = Just x

      foo = (Just True) { x = False }
    then `foo` desugars to something like
      foo = case Just True of
              P x -> P False
    hence we need to provide the correct dictionaries to P's matcher on
    the RHS so that we can build the expression.

    Note [Located RdrNames]
    ~~~~~~~~~~~~~~~~~~~~~~~
    A number of syntax elements have seemingly redundant locations attached to them.
    This is deliberate, to allow transformations making use of the API Annotations
    to easily correlate a Located Name in the RenamedSource with a Located RdrName
    in the ParsedSource.

    There are unfortunately enough differences between the ParsedSource and the
    RenamedSource that the API Annotations cannot be used directly with
    RenamedSource, so this allows a simple mapping to be used based on the location.

    Note [ExplicitTuple]
    ~~~~~~~~~~~~~~~~~~~~
    An ExplicitTuple is never just a data constructor like (,,,).
    That is, the `[LHsTupArg p]` argument of `ExplicitTuple` has at least
    one `Present` member (and is thus never empty).

    A tuple data constructor like () or (,,,) is parsed as an `HsVar`, not an
    `ExplicitTuple`, and stays that way. This is important for two reasons:

      1. We don't need -XTupleSections for (,,,)
      2. The type variables in (,,,) can be instantiated with visible type application.
         That is,

           (,,)     :: forall a b c. a -> b -> c -> (a,b,c)
           (True,,) :: forall {b} {c}. b -> c -> (Bool,b,c)

         Note that the tuple section has *inferred* arguments, while the data
         constructor has *specified* ones.
         (See Note [Required, Specified, and Inferred for types] in GHC.Tc.TyCl
         for background.)

    Sadly, the grammar for this is actually ambiguous, and it's only thanks to the
    preference of a shift in a shift/reduce conflict that the parser works as this
    Note details. Search for a reference to this Note in GHC.Parser for further
    explanation.

    Note [Empty lists]
    ~~~~~~~~~~~~~~~~~~
    An empty list could be considered either a data constructor (stored with
    HsVar) or an ExplicitList. This Note describes how empty lists flow through the
    various phases and why.

    Parsing
    -------
    An empty list is parsed by the sysdcon nonterminal. It thus comes to life via
    HsVar nilDataCon (defined in GHC.Builtin.Types). A freshly-parsed (HsExpr GhcPs) empty list
    is never a ExplicitList.

    Renaming
    --------
    If -XOverloadedLists is enabled, we must type-check the empty list as if it
    were a call to fromListN. (This is true regardless of the setting of
    -XRebindableSyntax.) This is very easy if the empty list is an ExplicitList,
    but an annoying special case if it's an HsVar. So the renamer changes a
    HsVar nilDataCon to an ExplicitList [], but only if -XOverloadedLists is on.
    (Why not always? Read on, dear friend.) This happens in the HsVar case of rnExpr.

    Type-checking
    -------------
    We want to accept an expression like [] @Int. To do this, we must infer that
    [] :: forall a. [a]. This is easy if [] is a HsVar with the right DataCon inside.
    However, the type-checking for explicit lists works differently: [x,y,z] is never
    polymorphic. Instead, we unify the types of x, y, and z together, and use the
    unified type as the argument to the cons and nil constructors. Thus, treating
    [] as an empty ExplicitList in the type-checker would prevent [] @Int from working.

    However, if -XOverloadedLists is on, then [] @Int really shouldn't be allowed:
    it's just like fromListN 0 [] @Int. Since
      fromListN :: forall list. IsList list => Int -> [Item list] -> list
    that expression really should be rejected. Thus, the renamer's behaviour is
    exactly what we want: treat [] as a datacon when -XNoOverloadedLists, and as
    an empty ExplicitList when -XOverloadedLists.

    See also #13680, which requested [] @Int to work.
    -}

    instance (OutputableBndrId p) => Outputable (HsExpr (GhcPass p)) where
        ppr :: HsExpr (GhcPass p) -> SDoc
    ppr HsExpr (GhcPass p)
    expr = HsExpr (GhcPass p) -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    HsExpr (GhcPass p) -> SDoc
    pprExpr HsExpr (GhcPass p)
    expr

    -----------------------
    -- pprExpr, pprLExpr, pprBinds call pprDeeper;
    -- the underscore versions do not
    pprLExpr :: (OutputableBndrId p) => LHsExpr (GhcPass p) -> SDoc
    pprLExpr :: forall (p :: Pass).
    OutputableBndrId p =>
    LHsExpr (GhcPass p) -> SDoc
    pprLExpr (L SrcSpan
    _ HsExpr (GhcPass p)
    e) = HsExpr (GhcPass p) -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    HsExpr (GhcPass p) -> SDoc
    pprExpr HsExpr (GhcPass p)
    e

    pprExpr :: (OutputableBndrId p) => HsExpr (GhcPass p) -> SDoc
    pprExpr :: forall (p :: Pass).
    OutputableBndrId p =>
    HsExpr (GhcPass p) -> SDoc
    pprExpr HsExpr (GhcPass p)
    e | HsExpr (GhcPass p) -> Bool
    forall (p :: Pass). IsPass p => HsExpr (GhcPass p) -> Bool
    isAtomicHsExpr HsExpr (GhcPass p)
    e Bool -> Bool -> Bool
    || HsExpr (GhcPass p) -> Bool
    forall id. HsExpr id -> Bool
    isQuietHsExpr HsExpr (GhcPass p)
    e =            HsExpr (GhcPass p) -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    HsExpr (GhcPass p) -> SDoc
    ppr_expr HsExpr (GhcPass p)
    e
              | Bool
    otherwise                           = SDoc -> SDoc
    pprDeeper (HsExpr (GhcPass p) -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    HsExpr (GhcPass p) -> SDoc
    ppr_expr HsExpr (GhcPass p)
    e)

    isQuietHsExpr :: HsExpr id -> Bool
    -- Parentheses do display something, but it gives little info and
    -- if we go deeper when we go inside them then we get ugly things
    -- like (...)
    isQuietHsExpr :: forall id. HsExpr id -> Bool
    isQuietHsExpr (HsPar {})        = Bool
    True
    -- applications don't display anything themselves
    isQuietHsExpr (HsApp {})        = Bool
    True
    isQuietHsExpr (HsAppType {})    = Bool
    True
    isQuietHsExpr (OpApp {})        = Bool
    True
    isQuietHsExpr HsExpr id
    _ = Bool
    False

    pprBinds :: (OutputableBndrId idL, OutputableBndrId idR)
             => HsLocalBindsLR (GhcPass idL) (GhcPass idR) -> SDoc
    pprBinds :: forall (idL :: Pass) (idR :: Pass).
    (OutputableBndrId idL, OutputableBndrId idR) =>
    HsLocalBindsLR (GhcPass idL) (GhcPass idR) -> SDoc
    pprBinds HsLocalBindsLR (GhcPass idL) (GhcPass idR)
    b = SDoc -> SDoc
    pprDeeper (HsLocalBindsLR (GhcPass idL) (GhcPass idR) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr HsLocalBindsLR (GhcPass idL) (GhcPass idR)
    b)

    -----------------------
    ppr_lexpr :: (OutputableBndrId p) => LHsExpr (GhcPass p) -> SDoc
    ppr_lexpr :: forall (p :: Pass).
    OutputableBndrId p =>
    LHsExpr (GhcPass p) -> SDoc
    ppr_lexpr LHsExpr (GhcPass p)
    e = HsExpr (GhcPass p) -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    HsExpr (GhcPass p) -> SDoc
    ppr_expr (LHsExpr (GhcPass p) -> HsExpr (GhcPass p)
    forall l e. GenLocated l e -> e
    unLoc LHsExpr (GhcPass p)
    e)

    ppr_expr :: forall p. (OutputableBndrId p)
             => HsExpr (GhcPass p) -> SDoc
    ppr_expr :: forall (p :: Pass).
    OutputableBndrId p =>
    HsExpr (GhcPass p) -> SDoc
    ppr_expr (HsVar XVar (GhcPass p)
    _ (L SrcSpan
    _ IdP (GhcPass p)
    v))  = IdGhcP p -> SDoc
    forall a. OutputableBndr a => a -> SDoc
    pprPrefixOcc IdGhcP p
    IdP (GhcPass p)
    v
    ppr_expr (HsUnboundVar XUnboundVar (GhcPass p)
    _ OccName
    uv)= OccName -> SDoc
    forall a. OutputableBndr a => a -> SDoc
    pprPrefixOcc OccName
    uv
    ppr_expr (HsConLikeOut XConLikeOut (GhcPass p)
    _ ConLike
    c) = ConLike -> SDoc
    forall a. OutputableBndr a => a -> SDoc
    pprPrefixOcc ConLike
    c
    ppr_expr (HsIPVar XIPVar (GhcPass p)
    _ HsIPName
    v)      = HsIPName -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr HsIPName
    v
    ppr_expr (HsOverLabel XOverLabel (GhcPass p)
    _ Maybe (IdP (GhcPass p))
    _ FastString
    l)= Char -> SDoc
    char Char
    '#' SDoc -> SDoc -> SDoc
    <> FastString -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr FastString
    l
    ppr_expr (HsLit XLitE (GhcPass p)
    _ HsLit (GhcPass p)
    lit)      = HsLit (GhcPass p) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr HsLit (GhcPass p)
    lit
    ppr_expr (HsOverLit XOverLitE (GhcPass p)
    _ HsOverLit (GhcPass p)
    lit)  = HsOverLit (GhcPass p) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr HsOverLit (GhcPass p)
    lit
    ppr_expr (HsPar XPar (GhcPass p)
    _ LHsExpr (GhcPass p)
    e)        = SDoc -> SDoc
    parens (LHsExpr (GhcPass p) -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    LHsExpr (GhcPass p) -> SDoc
    ppr_lexpr LHsExpr (GhcPass p)
    e)

    ppr_expr (HsPragE XPragE (GhcPass p)
    _ HsPragE (GhcPass p)
    prag LHsExpr (GhcPass p)
    e) = [SDoc] -> SDoc
    sep [HsPragE (GhcPass p) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr HsPragE (GhcPass p)
    prag, LHsExpr (GhcPass p) -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    LHsExpr (GhcPass p) -> SDoc
    ppr_lexpr LHsExpr (GhcPass p)
    e]

    ppr_expr e :: HsExpr (GhcPass p)
    e@(HsApp {})        = HsExpr (GhcPass p)
    -> [Either (LHsExpr (GhcPass p)) (LHsWcType (NoGhcTc (GhcPass p)))]
    -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    HsExpr (GhcPass p)
    -> [Either (LHsExpr (GhcPass p)) (LHsWcType (NoGhcTc (GhcPass p)))]
    -> SDoc
    ppr_apps HsExpr (GhcPass p)
    e []
    ppr_expr e :: HsExpr (GhcPass p)
    e@(HsAppType {})    = HsExpr (GhcPass p)
    -> [Either (LHsExpr (GhcPass p)) (LHsWcType (NoGhcTc (GhcPass p)))]
    -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    HsExpr (GhcPass p)
    -> [Either (LHsExpr (GhcPass p)) (LHsWcType (NoGhcTc (GhcPass p)))]
    -> SDoc
    ppr_apps HsExpr (GhcPass p)
    e []

    ppr_expr (OpApp XOpApp (GhcPass p)
    _ LHsExpr (GhcPass p)
    e1 LHsExpr (GhcPass p)
    op LHsExpr (GhcPass p)
    e2)
      | Just SDoc
    pp_op <- HsExpr (GhcPass p) -> Maybe SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    HsExpr (GhcPass p) -> Maybe SDoc
    ppr_infix_expr (LHsExpr (GhcPass p) -> HsExpr (GhcPass p)
    forall l e. GenLocated l e -> e
    unLoc LHsExpr (GhcPass p)
    op)
      = SDoc -> SDoc
    pp_infixly SDoc
    pp_op
      | Bool
    otherwise
      = SDoc
    pp_prefixly

      where
        pp_e1 :: SDoc
    pp_e1 = PprPrec -> LHsExpr (GhcPass p) -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    PprPrec -> LHsExpr (GhcPass p) -> SDoc
    pprDebugParendExpr PprPrec
    opPrec LHsExpr (GhcPass p)
    e1   -- In debug mode, add parens
        pp_e2 :: SDoc
    pp_e2 = PprPrec -> LHsExpr (GhcPass p) -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    PprPrec -> LHsExpr (GhcPass p) -> SDoc
    pprDebugParendExpr PprPrec
    opPrec LHsExpr (GhcPass p)
    e2   -- to make precedence clear

        pp_prefixly :: SDoc
    pp_prefixly
          = SDoc -> Int -> SDoc -> SDoc
    hang (LHsExpr (GhcPass p) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr LHsExpr (GhcPass p)
    op) Int
    2 ([SDoc] -> SDoc
    sep [SDoc
    pp_e1, SDoc
    pp_e2])

        pp_infixly :: SDoc -> SDoc
    pp_infixly SDoc
    pp_op
          = SDoc -> Int -> SDoc -> SDoc
    hang SDoc
    pp_e1 Int
    2 ([SDoc] -> SDoc
    sep [SDoc
    pp_op, Int -> SDoc -> SDoc
    nest Int
    2 SDoc
    pp_e2])

    ppr_expr (NegApp XNegApp (GhcPass p)
    _ LHsExpr (GhcPass p)
    e SyntaxExpr (GhcPass p)
    _) = Char -> SDoc
    char Char
    '-' SDoc -> SDoc -> SDoc
    <+> PprPrec -> LHsExpr (GhcPass p) -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    PprPrec -> LHsExpr (GhcPass p) -> SDoc
    pprDebugParendExpr PprPrec
    appPrec LHsExpr (GhcPass p)
    e

    ppr_expr (SectionL XSectionL (GhcPass p)
    _ LHsExpr (GhcPass p)
    expr LHsExpr (GhcPass p)
    op)
      | Just SDoc
    pp_op <- HsExpr (GhcPass p) -> Maybe SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    HsExpr (GhcPass p) -> Maybe SDoc
    ppr_infix_expr (LHsExpr (GhcPass p) -> HsExpr (GhcPass p)
    forall l e. GenLocated l e -> e
    unLoc LHsExpr (GhcPass p)
    op)
      = SDoc -> SDoc
    pp_infixly SDoc
    pp_op
      | Bool
    otherwise
      = SDoc
    pp_prefixly
      where
        pp_expr :: SDoc
    pp_expr = PprPrec -> LHsExpr (GhcPass p) -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    PprPrec -> LHsExpr (GhcPass p) -> SDoc
    pprDebugParendExpr PprPrec
    opPrec LHsExpr (GhcPass p)
    expr

        pp_prefixly :: SDoc
    pp_prefixly = SDoc -> Int -> SDoc -> SDoc
    hang ([SDoc] -> SDoc
    hsep [String -> SDoc
    text String
    " \\ x_ ->", LHsExpr (GhcPass p) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr LHsExpr (GhcPass p)
    op])
                           Int
    4 ([SDoc] -> SDoc
    hsep [SDoc
    pp_expr, String -> SDoc
    text String
    "x_ )"])

        pp_infixly :: SDoc -> SDoc
    pp_infixly SDoc
    v = ([SDoc] -> SDoc
    sep [SDoc
    pp_expr, SDoc
    v])

    ppr_expr (SectionR XSectionR (GhcPass p)
    _ LHsExpr (GhcPass p)
    op LHsExpr (GhcPass p)
    expr)
      | Just SDoc
    pp_op <- HsExpr (GhcPass p) -> Maybe SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    HsExpr (GhcPass p) -> Maybe SDoc
    ppr_infix_expr (LHsExpr (GhcPass p) -> HsExpr (GhcPass p)
    forall l e. GenLocated l e -> e
    unLoc LHsExpr (GhcPass p)
    op)
      = SDoc -> SDoc
    pp_infixly SDoc
    pp_op
      | Bool
    otherwise
      = SDoc
    pp_prefixly
      where
        pp_expr :: SDoc
    pp_expr = PprPrec -> LHsExpr (GhcPass p) -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    PprPrec -> LHsExpr (GhcPass p) -> SDoc
    pprDebugParendExpr PprPrec
    opPrec LHsExpr (GhcPass p)
    expr

        pp_prefixly :: SDoc
    pp_prefixly = SDoc -> Int -> SDoc -> SDoc
    hang ([SDoc] -> SDoc
    hsep [String -> SDoc
    text String
    "( \\ x_ ->", LHsExpr (GhcPass p) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr LHsExpr (GhcPass p)
    op, String -> SDoc
    text String
    "x_"])
                           Int
    4 (SDoc
    pp_expr SDoc -> SDoc -> SDoc
    <> SDoc
    rparen)

        pp_infixly :: SDoc -> SDoc
    pp_infixly SDoc
    v = [SDoc] -> SDoc
    sep [SDoc
    v, SDoc
    pp_expr]

    ppr_expr (ExplicitTuple XExplicitTuple (GhcPass p)
    _ [LHsTupArg (GhcPass p)]
    exprs Boxity
    boxity)
        -- Special-case unary boxed tuples so that they are pretty-printed as
        -- `Solo x`, not `(x)`
      | [L SrcSpan
    _ (Present XPresent (GhcPass p)
    _ LHsExpr (GhcPass p)
    expr)] <- [LHsTupArg (GhcPass p)]
    exprs
      , Boxity
    Boxed <- Boxity
    boxity
      = [SDoc] -> SDoc
    hsep [String -> SDoc
    text (Boxity -> Int -> String
    mkTupleStr Boxity
    Boxed Int
    1), LHsExpr (GhcPass p) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr LHsExpr (GhcPass p)
    expr]
      | Bool
    otherwise
      = TupleSort -> SDoc -> SDoc
    tupleParens (Boxity -> TupleSort
    boxityTupleSort Boxity
    boxity) ([SDoc] -> SDoc
    fcat ([HsTupArg (GhcPass p)] -> [SDoc]
    forall {p :: Pass}.
    (OutputableBndr (IdGhcP p),
     OutputableBndr (IdGhcP (NoGhcTcPass p)), IsPass p) =>
    [HsTupArg (GhcPass p)] -> [SDoc]
    ppr_tup_args ([HsTupArg (GhcPass p)] -> [SDoc])
    -> [HsTupArg (GhcPass p)] -> [SDoc]
    forall a b. (a -> b) -> a -> b
    $ (LHsTupArg (GhcPass p) -> HsTupArg (GhcPass p))
    -> [LHsTupArg (GhcPass p)] -> [HsTupArg (GhcPass p)]
    forall a b. (a -> b) -> [a] -> [b]
    map LHsTupArg (GhcPass p) -> HsTupArg (GhcPass p)
    forall l e. GenLocated l e -> e
    unLoc [LHsTupArg (GhcPass p)]
    exprs))
      where
        ppr_tup_args :: [HsTupArg (GhcPass p)] -> [SDoc]
    ppr_tup_args []               = []
        ppr_tup_args (Present XPresent (GhcPass p)
    _ LHsExpr (GhcPass p)
    e : [HsTupArg (GhcPass p)]
    es) = (LHsExpr (GhcPass p) -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    LHsExpr (GhcPass p) -> SDoc
    ppr_lexpr LHsExpr (GhcPass p)
    e SDoc -> SDoc -> SDoc
    <> [HsTupArg (GhcPass p)] -> SDoc
    forall {id}. [HsTupArg id] -> SDoc
    punc [HsTupArg (GhcPass p)]
    es) SDoc -> [SDoc] -> [SDoc]
    forall a. a -> [a] -> [a]
    : [HsTupArg (GhcPass p)] -> [SDoc]
    ppr_tup_args [HsTupArg (GhcPass p)]
    es
        ppr_tup_args (Missing XMissing (GhcPass p)
    _   : [HsTupArg (GhcPass p)]
    es) = [HsTupArg (GhcPass p)] -> SDoc
    forall {id}. [HsTupArg id] -> SDoc
    punc [HsTupArg (GhcPass p)]
    es SDoc -> [SDoc] -> [SDoc]
    forall a. a -> [a] -> [a]
    : [HsTupArg (GhcPass p)] -> [SDoc]
    ppr_tup_args [HsTupArg (GhcPass p)]
    es

        punc :: [HsTupArg id] -> SDoc
    punc (Present {} : [HsTupArg id]
    _) = SDoc
    comma SDoc -> SDoc -> SDoc
    <> SDoc
    space
        punc (Missing {} : [HsTupArg id]
    _) = SDoc
    comma
        punc (XTupArg {} : [HsTupArg id]
    _) = SDoc
    comma SDoc -> SDoc -> SDoc
    <> SDoc
    space
        punc []               = SDoc
    empty

    ppr_expr (ExplicitSum XExplicitSum (GhcPass p)
    _ Int
    alt Int
    arity LHsExpr (GhcPass p)
    expr)
      = String -> SDoc
    text String
    "(#" SDoc -> SDoc -> SDoc
    <+> Int -> SDoc
    ppr_bars (Int
    alt Int -> Int -> Int
    forall a. Num a => a -> a -> a
    - Int
    1) SDoc -> SDoc -> SDoc
    <+> LHsExpr (GhcPass p) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr LHsExpr (GhcPass p)
    expr SDoc -> SDoc -> SDoc
    <+> Int -> SDoc
    ppr_bars (Int
    arity Int -> Int -> Int
    forall a. Num a => a -> a -> a
    - Int
    alt) SDoc -> SDoc -> SDoc
    <+> String -> SDoc
    text String
    "#)"
      where
        ppr_bars :: Int -> SDoc
    ppr_bars Int
    n = [SDoc] -> SDoc
    hsep (Int -> SDoc -> [SDoc]
    forall a. Int -> a -> [a]
    replicate Int
    n (Char -> SDoc
    char Char
    '|'))

    ppr_expr (HsLam XLam (GhcPass p)
    _ MatchGroup (GhcPass p) (LHsExpr (GhcPass p))
    matches)
      = MatchGroup (GhcPass p) (LHsExpr (GhcPass p)) -> SDoc
    forall (idR :: Pass) body.
    (OutputableBndrId idR, Outputable body) =>
    MatchGroup (GhcPass idR) body -> SDoc
    pprMatches MatchGroup (GhcPass p) (LHsExpr (GhcPass p))
    matches

    ppr_expr (HsLamCase XLamCase (GhcPass p)
    _ MatchGroup (GhcPass p) (LHsExpr (GhcPass p))
    matches)
      = [SDoc] -> SDoc
    sep [ [SDoc] -> SDoc
    sep [String -> SDoc
    text String
    "\\case"],
              Int -> SDoc -> SDoc
    nest Int
    2 (MatchGroup (GhcPass p) (LHsExpr (GhcPass p)) -> SDoc
    forall (idR :: Pass) body.
    (OutputableBndrId idR, Outputable body) =>
    MatchGroup (GhcPass idR) body -> SDoc
    pprMatches MatchGroup (GhcPass p) (LHsExpr (GhcPass p))
    matches) ]

    ppr_expr (HsCase XCase (GhcPass p)
    _ LHsExpr (GhcPass p)
    expr matches :: MatchGroup (GhcPass p) (LHsExpr (GhcPass p))
    matches@(MG { mg_alts :: forall p body. MatchGroup p body -> Located [LMatch p body]
    mg_alts = L SrcSpan
    _ [LMatch (GhcPass p) (LHsExpr (GhcPass p))
    _] }))
      = [SDoc] -> SDoc
    sep [ [SDoc] -> SDoc
    sep [String -> SDoc
    text String
    "case", Int -> SDoc -> SDoc
    nest Int
    4 (LHsExpr (GhcPass p) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr LHsExpr (GhcPass p)
    expr), PtrString -> SDoc
    ptext (String -> PtrString
    sLit String
    "of {")],
              Int -> SDoc -> SDoc
    nest Int
    2 (MatchGroup (GhcPass p) (LHsExpr (GhcPass p)) -> SDoc
    forall (idR :: Pass) body.
    (OutputableBndrId idR, Outputable body) =>
    MatchGroup (GhcPass idR) body -> SDoc
    pprMatches MatchGroup (GhcPass p) (LHsExpr (GhcPass p))
    matches) SDoc -> SDoc -> SDoc
    <+> Char -> SDoc
    char Char
    '}']
    ppr_expr (HsCase XCase (GhcPass p)
    _ LHsExpr (GhcPass p)
    expr MatchGroup (GhcPass p) (LHsExpr (GhcPass p))
    matches)
      = [SDoc] -> SDoc
    sep [ [SDoc] -> SDoc
    sep [String -> SDoc
    text String
    "case", Int -> SDoc -> SDoc
    nest Int
    4 (LHsExpr (GhcPass p) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr LHsExpr (GhcPass p)
    expr), PtrString -> SDoc
    ptext (String -> PtrString
    sLit String
    "of")],
              Int -> SDoc -> SDoc
    nest Int
    2 (MatchGroup (GhcPass p) (LHsExpr (GhcPass p)) -> SDoc
    forall (idR :: Pass) body.
    (OutputableBndrId idR, Outputable body) =>
    MatchGroup (GhcPass idR) body -> SDoc
    pprMatches MatchGroup (GhcPass p) (LHsExpr (GhcPass p))
    matches) ]

    ppr_expr (HsIf XIf (GhcPass p)
    _ LHsExpr (GhcPass p)
    e1 LHsExpr (GhcPass p)
    e2 LHsExpr (GhcPass p)
    e3)
      = [SDoc] -> SDoc
    sep [[SDoc] -> SDoc
    hsep [String -> SDoc
    text String
    "if", Int -> SDoc -> SDoc
    nest Int
    2 (LHsExpr (GhcPass p) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr LHsExpr (GhcPass p)
    e1), PtrString -> SDoc
    ptext (String -> PtrString
    sLit String
    "then")],
             Int -> SDoc -> SDoc
    nest Int
    4 (LHsExpr (GhcPass p) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr LHsExpr (GhcPass p)
    e2),
             String -> SDoc
    text String
    "else",
             Int -> SDoc -> SDoc
    nest Int
    4 (LHsExpr (GhcPass p) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr LHsExpr (GhcPass p)
    e3)]

    ppr_expr (HsMultiIf XMultiIf (GhcPass p)
    _ [LGRHS (GhcPass p) (LHsExpr (GhcPass p))]
    alts)
      = SDoc -> Int -> SDoc -> SDoc
    hang (String -> SDoc
    text String
    "if") Int
    3  ([SDoc] -> SDoc
    vcat ((LGRHS (GhcPass p) (LHsExpr (GhcPass p)) -> SDoc)
    -> [LGRHS (GhcPass p) (LHsExpr (GhcPass p))] -> [SDoc]
    forall a b. (a -> b) -> [a] -> [b]
    map LGRHS (GhcPass p) (LHsExpr (GhcPass p)) -> SDoc
    forall {a} {p} {l}.
    (Outputable a, Outputable (XXGRHS p a),
     Outputable (StmtLR p p (LHsExpr p))) =>
    GenLocated l (GRHS p a) -> SDoc
    ppr_alt [LGRHS (GhcPass p) (LHsExpr (GhcPass p))]
    alts))
      where ppr_alt :: GenLocated l (GRHS p a) -> SDoc
    ppr_alt (L l
    _ (GRHS XCGRHS p a
    _ [GuardLStmt p]
    guards a
    expr)) =
              SDoc -> Int -> SDoc -> SDoc
    hang SDoc
    vbar Int
    2 ([SDoc] -> SDoc
    ppr_one [SDoc]
    one_alt)
              where
                ppr_one :: [SDoc] -> SDoc
    ppr_one [] = String -> SDoc
    forall a. String -> a
    panic String
    "ppr_exp HsMultiIf"
                ppr_one (SDoc
    h:[SDoc]
    t) = SDoc -> Int -> SDoc -> SDoc
    hang SDoc
    h Int
    2 ([SDoc] -> SDoc
    sep [SDoc]
    t)
                one_alt :: [SDoc]
    one_alt = [ [GuardLStmt p] -> SDoc
    forall a. Outputable a => [a] -> SDoc
    interpp'SP [GuardLStmt p]
    guards
                          , String -> SDoc
    text String
    "->" SDoc -> SDoc -> SDoc
    <+> SDoc -> SDoc
    pprDeeper (a -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr a
    expr) ]
            ppr_alt (L l
    _ (XGRHS XXGRHS p a
    x)) = XXGRHS p a -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr XXGRHS p a
    x

    -- special case: let ... in let ...
    ppr_expr (HsLet XLet (GhcPass p)
    _ (L SrcSpan
    _ HsLocalBinds (GhcPass p)
    binds) expr :: LHsExpr (GhcPass p)
    expr@(L SrcSpan
    _ (HsLet XLet (GhcPass p)
    _ GenLocated SrcSpan (HsLocalBinds (GhcPass p))
    _ LHsExpr (GhcPass p)
    _)))
      = [SDoc] -> SDoc
    sep [SDoc -> Int -> SDoc -> SDoc
    hang (String -> SDoc
    text String
    "let") Int
    2 ([SDoc] -> SDoc
    hsep [HsLocalBinds (GhcPass p) -> SDoc
    forall (idL :: Pass) (idR :: Pass).
    (OutputableBndrId idL, OutputableBndrId idR) =>
    HsLocalBindsLR (GhcPass idL) (GhcPass idR) -> SDoc
    pprBinds HsLocalBinds (GhcPass p)
    binds, PtrString -> SDoc
    ptext (String -> PtrString
    sLit String
    "in")]),
             LHsExpr (GhcPass p) -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    LHsExpr (GhcPass p) -> SDoc
    ppr_lexpr LHsExpr (GhcPass p)
    expr]

    ppr_expr (HsLet XLet (GhcPass p)
    _ (L SrcSpan
    _ HsLocalBinds (GhcPass p)
    binds) LHsExpr (GhcPass p)
    expr)
      = [SDoc] -> SDoc
    sep [SDoc -> Int -> SDoc -> SDoc
    hang (String -> SDoc
    text String
    "let") Int
    2 (HsLocalBinds (GhcPass p) -> SDoc
    forall (idL :: Pass) (idR :: Pass).
    (OutputableBndrId idL, OutputableBndrId idR) =>
    HsLocalBindsLR (GhcPass idL) (GhcPass idR) -> SDoc
    pprBinds HsLocalBinds (GhcPass p)
    binds),
             SDoc -> Int -> SDoc -> SDoc
    hang (String -> SDoc
    text String
    "in")  Int
    2 (LHsExpr (GhcPass p) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr LHsExpr (GhcPass p)
    expr)]

    ppr_expr (HsDo XDo (GhcPass p)
    _ HsStmtContext GhcRn
    do_or_list_comp (L SrcSpan
    _ [ExprLStmt (GhcPass p)]
    stmts)) = HsStmtContext GhcRn -> [ExprLStmt (GhcPass p)] -> SDoc
    forall (p :: Pass) body any.
    (OutputableBndrId p, Outputable body) =>
    HsStmtContext any -> [LStmt (GhcPass p) body] -> SDoc
    pprDo HsStmtContext GhcRn
    do_or_list_comp [ExprLStmt (GhcPass p)]
    stmts

    ppr_expr (ExplicitList XExplicitList (GhcPass p)
    _ Maybe (SyntaxExpr (GhcPass p))
    _ [LHsExpr (GhcPass p)]
    exprs)
      = SDoc -> SDoc
    brackets (([SDoc] -> SDoc) -> [SDoc] -> SDoc
    pprDeeperList [SDoc] -> SDoc
    fsep (SDoc -> [SDoc] -> [SDoc]
    punctuate SDoc
    comma ((LHsExpr (GhcPass p) -> SDoc) -> [LHsExpr (GhcPass p)] -> [SDoc]
    forall a b. (a -> b) -> [a] -> [b]
    map LHsExpr (GhcPass p) -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    LHsExpr (GhcPass p) -> SDoc
    ppr_lexpr [LHsExpr (GhcPass p)]
    exprs)))

    ppr_expr (RecordCon { rcon_con_name :: forall p. HsExpr p -> Located (IdP p)
    rcon_con_name = GenLocated SrcSpan (IdP (GhcPass p))
    con_id, rcon_flds :: forall p. HsExpr p -> HsRecordBinds p
    rcon_flds = HsRecordBinds (GhcPass p)
    rbinds })
      = SDoc -> Int -> SDoc -> SDoc
    hang (Located (IdGhcP p) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr Located (IdGhcP p)
    GenLocated SrcSpan (IdP (GhcPass p))
    con_id) Int
    2 (HsRecordBinds (GhcPass p) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr HsRecordBinds (GhcPass p)
    rbinds)

    ppr_expr (RecordUpd { rupd_expr :: forall p. HsExpr p -> LHsExpr p
    rupd_expr = L SrcSpan
    _ HsExpr (GhcPass p)
    aexp, rupd_flds :: forall p. HsExpr p -> [LHsRecUpdField p]
    rupd_flds = [LHsRecUpdField (GhcPass p)]
    rbinds })
      = SDoc -> Int -> SDoc -> SDoc
    hang (HsExpr (GhcPass p) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr HsExpr (GhcPass p)
    aexp) Int
    2 (SDoc -> SDoc
    braces ([SDoc] -> SDoc
    fsep (SDoc -> [SDoc] -> [SDoc]
    punctuate SDoc
    comma ((LHsRecUpdField (GhcPass p) -> SDoc)
    -> [LHsRecUpdField (GhcPass p)] -> [SDoc]
    forall a b. (a -> b) -> [a] -> [b]
    map LHsRecUpdField (GhcPass p) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr [LHsRecUpdField (GhcPass p)]
    rbinds))))

    ppr_expr (ExprWithTySig XExprWithTySig (GhcPass p)
    _ LHsExpr (GhcPass p)
    expr LHsSigWcType (NoGhcTc (GhcPass p))
    sig)
      = SDoc -> Int -> SDoc -> SDoc
    hang (Int -> SDoc -> SDoc
    nest Int
    2 (LHsExpr (GhcPass p) -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    LHsExpr (GhcPass p) -> SDoc
    ppr_lexpr LHsExpr (GhcPass p)
    expr) SDoc -> SDoc -> SDoc
    <+> SDoc
    dcolon)
             Int
    4 (LHsSigWcType (GhcPass (NoGhcTcPass p)) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr LHsSigWcType (GhcPass (NoGhcTcPass p))
    LHsSigWcType (NoGhcTc (GhcPass p))
    sig)

    ppr_expr (ArithSeq XArithSeq (GhcPass p)
    _ Maybe (SyntaxExpr (GhcPass p))
    _ ArithSeqInfo (GhcPass p)
    info) = SDoc -> SDoc
    brackets (ArithSeqInfo (GhcPass p) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr ArithSeqInfo (GhcPass p)
    info)

    ppr_expr (HsSpliceE XSpliceE (GhcPass p)
    _ HsSplice (GhcPass p)
    s)         = HsSplice (GhcPass p) -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    HsSplice (GhcPass p) -> SDoc
    pprSplice HsSplice (GhcPass p)
    s
    ppr_expr (HsBracket XBracket (GhcPass p)
    _ HsBracket (GhcPass p)
    b)         = HsBracket (GhcPass p) -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    HsBracket (GhcPass p) -> SDoc
    pprHsBracket HsBracket (GhcPass p)
    b
    ppr_expr (HsRnBracketOut XRnBracketOut (GhcPass p)
    _ HsBracket GhcRn
    e []) = HsBracket GhcRn -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr HsBracket GhcRn
    e
    ppr_expr (HsRnBracketOut XRnBracketOut (GhcPass p)
    _ HsBracket GhcRn
    e [PendingRnSplice]
    ps) = HsBracket GhcRn -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr HsBracket GhcRn
    e SDoc -> SDoc -> SDoc
    $$ String -> SDoc
    text String
    "pending(rn)" SDoc -> SDoc -> SDoc
    <+> [PendingRnSplice] -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr [PendingRnSplice]
    ps
    ppr_expr (HsTcBracketOut XTcBracketOut (GhcPass p)
    _ Maybe QuoteWrapper
    _wrap HsBracket GhcRn
    e []) = HsBracket GhcRn -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr HsBracket GhcRn
    e
    ppr_expr (HsTcBracketOut XTcBracketOut (GhcPass p)
    _ Maybe QuoteWrapper
    _wrap HsBracket GhcRn
    e [PendingTcSplice]
    ps) = HsBracket GhcRn -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr HsBracket GhcRn
    e SDoc -> SDoc -> SDoc
    $$ String -> SDoc
    text String
    "pending(tc)" SDoc -> SDoc -> SDoc
    <+> forall (p :: Pass).
    IsPass p =>
    ((p ~ 'Typechecked) => SDoc) -> SDoc
    pprIfTc @p ([PendingTcSplice] -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr [PendingTcSplice]
    ps)

    ppr_expr (HsProc XProc (GhcPass p)
    _ LPat (GhcPass p)
    pat (L SrcSpan
    _ (HsCmdTop XCmdTop (GhcPass p)
    _ LHsCmd (GhcPass p)
    cmd)))
      = [SDoc] -> SDoc
    hsep [String -> SDoc
    text String
    "proc", Located (Pat (GhcPass p)) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr Located (Pat (GhcPass p))
    LPat (GhcPass p)
    pat, PtrString -> SDoc
    ptext (String -> PtrString
    sLit String
    "->"), LHsCmd (GhcPass p) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr LHsCmd (GhcPass p)
    cmd]

    ppr_expr (HsStatic XStatic (GhcPass p)
    _ LHsExpr (GhcPass p)
    e)
      = [SDoc] -> SDoc
    hsep [String -> SDoc
    text String
    "static", LHsExpr (GhcPass p) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr LHsExpr (GhcPass p)
    e]

    ppr_expr (HsTick XTick (GhcPass p)
    _ Tickish (IdP (GhcPass p))
    tickish LHsExpr (GhcPass p)
    exp)
      = SDoc -> SDoc -> SDoc
    pprTicks (LHsExpr (GhcPass p) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr LHsExpr (GhcPass p)
    exp) (SDoc -> SDoc) -> SDoc -> SDoc
    forall a b. (a -> b) -> a -> b
    $
        Tickish (IdGhcP p) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr Tickish (IdGhcP p)
    Tickish (IdP (GhcPass p))
    tickish SDoc -> SDoc -> SDoc
    <+> LHsExpr (GhcPass p) -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    LHsExpr (GhcPass p) -> SDoc
    ppr_lexpr LHsExpr (GhcPass p)
    exp
    ppr_expr (HsBinTick XBinTick (GhcPass p)
    _ Int
    tickIdTrue Int
    tickIdFalse LHsExpr (GhcPass p)
    exp)
      = SDoc -> SDoc -> SDoc
    pprTicks (LHsExpr (GhcPass p) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr LHsExpr (GhcPass p)
    exp) (SDoc -> SDoc) -> SDoc -> SDoc
    forall a b. (a -> b) -> a -> b
    $
        [SDoc] -> SDoc
    hcat [String -> SDoc
    text String
    "bintick<",
              Int -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr Int
    tickIdTrue,
              String -> SDoc
    text String
    ",",
              Int -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr Int
    tickIdFalse,
              String -> SDoc
    text String
    ">(",
              LHsExpr (GhcPass p) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr LHsExpr (GhcPass p)
    exp, String -> SDoc
    text String
    ")"]

    ppr_expr (HsRecFld XRecFld (GhcPass p)
    _ AmbiguousFieldOcc (GhcPass p)
    f) = AmbiguousFieldOcc (GhcPass p) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr AmbiguousFieldOcc (GhcPass p)
    f
    ppr_expr (XExpr XXExpr (GhcPass p)
    x) = case forall (p :: Pass). IsPass p => GhcPass p
    ghcPass @p of
    #if __GLASGOW_HASKELL__ < 811
      GhcPs -> ppr x
    #endif
      GhcPass p
    GhcRn -> HsExpansion (HsExpr GhcRn) (HsExpr GhcRn) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr XXExpr (GhcPass p)
    HsExpansion (HsExpr GhcRn) (HsExpr GhcRn)
    x
      GhcPass p
    GhcTc -> case XXExpr (GhcPass p)
    x of
        WrapExpr (HsWrap HsWrapper
    co_fn HsExpr GhcTc
    e) -> HsWrapper -> (Bool -> SDoc) -> SDoc
    pprHsWrapper HsWrapper
    co_fn
          (\Bool
    parens -> if Bool
    parens then HsExpr GhcTc -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    HsExpr (GhcPass p) -> SDoc
    pprExpr HsExpr GhcTc
    e else HsExpr GhcTc -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    HsExpr (GhcPass p) -> SDoc
    pprExpr HsExpr GhcTc
    e)
        ExpansionExpr HsExpansion (HsExpr GhcRn) (HsExpr GhcTc)
    e -> HsExpansion (HsExpr GhcRn) (HsExpr GhcTc) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr HsExpansion (HsExpr GhcRn) (HsExpr GhcTc)
    e -- e is an HsExpansion, we print the original
                                 -- expression (LHsExpr GhcPs), not the
                                 -- desugared one (LHsExpr GhcT).

    ppr_infix_expr :: forall p. (OutputableBndrId p) => HsExpr (GhcPass p) -> Maybe SDoc
    ppr_infix_expr :: forall (p :: Pass).
    OutputableBndrId p =>
    HsExpr (GhcPass p) -> Maybe SDoc
    ppr_infix_expr (HsVar XVar (GhcPass p)
    _ (L SrcSpan
    _ IdP (GhcPass p)
    v))    = SDoc -> Maybe SDoc
    forall a. a -> Maybe a
    Just (IdGhcP p -> SDoc
    forall a. OutputableBndr a => a -> SDoc
    pprInfixOcc IdGhcP p
    IdP (GhcPass p)
    v)
    ppr_infix_expr (HsConLikeOut XConLikeOut (GhcPass p)
    _ ConLike
    c)   = SDoc -> Maybe SDoc
    forall a. a -> Maybe a
    Just (Name -> SDoc
    forall a. OutputableBndr a => a -> SDoc
    pprInfixOcc (ConLike -> Name
    conLikeName ConLike
    c))
    ppr_infix_expr (HsRecFld XRecFld (GhcPass p)
    _ AmbiguousFieldOcc (GhcPass p)
    f)       = SDoc -> Maybe SDoc
    forall a. a -> Maybe a
    Just (AmbiguousFieldOcc (GhcPass p) -> SDoc
    forall a. OutputableBndr a => a -> SDoc
    pprInfixOcc AmbiguousFieldOcc (GhcPass p)
    f)
    ppr_infix_expr (HsUnboundVar XUnboundVar (GhcPass p)
    _ OccName
    occ) = SDoc -> Maybe SDoc
    forall a. a -> Maybe a
    Just (OccName -> SDoc
    forall a. OutputableBndr a => a -> SDoc
    pprInfixOcc OccName
    occ)
    ppr_infix_expr (XExpr XXExpr (GhcPass p)
    x)            = case (forall (p :: Pass). IsPass p => GhcPass p
    ghcPass @p, XXExpr (GhcPass p)
    x) of
      (GhcPass p
    GhcPs, XXExpr (GhcPass p)
    _)                              -> Maybe SDoc
    forall a. Maybe a
    Nothing
      (GhcPass p
    GhcRn, HsExpanded HsExpr GhcRn
    a HsExpr GhcRn
    _)                 -> HsExpr GhcRn -> Maybe SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    HsExpr (GhcPass p) -> Maybe SDoc
    ppr_infix_expr HsExpr GhcRn
    a
      (GhcPass p
    GhcTc, WrapExpr (HsWrap HsWrapper
    _ HsExpr GhcTc
    e))          -> HsExpr GhcTc -> Maybe SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    HsExpr (GhcPass p) -> Maybe SDoc
    ppr_infix_expr HsExpr GhcTc
    e
      (GhcPass p
    GhcTc, ExpansionExpr (HsExpanded HsExpr GhcRn
    a HsExpr GhcTc
    _)) -> HsExpr GhcRn -> Maybe SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    HsExpr (GhcPass p) -> Maybe SDoc
    ppr_infix_expr HsExpr GhcRn
    a
    ppr_infix_expr HsExpr (GhcPass p)
    _ = Maybe SDoc
    forall a. Maybe a
    Nothing

    ppr_apps :: (OutputableBndrId p)
             => HsExpr (GhcPass p)
             -> [Either (LHsExpr (GhcPass p)) (LHsWcType (NoGhcTc (GhcPass p)))]
             -> SDoc
    ppr_apps :: forall (p :: Pass).
    OutputableBndrId p =>
    HsExpr (GhcPass p)
    -> [Either (LHsExpr (GhcPass p)) (LHsWcType (NoGhcTc (GhcPass p)))]
    -> SDoc
    ppr_apps (HsApp XApp (GhcPass p)
    _ (L SrcSpan
    _ HsExpr (GhcPass p)
    fun) LHsExpr (GhcPass p)
    arg)        [Either (LHsExpr (GhcPass p)) (LHsWcType (NoGhcTc (GhcPass p)))]
    args
      = HsExpr (GhcPass p)
    -> [Either (LHsExpr (GhcPass p)) (LHsWcType (NoGhcTc (GhcPass p)))]
    -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    HsExpr (GhcPass p)
    -> [Either (LHsExpr (GhcPass p)) (LHsWcType (NoGhcTc (GhcPass p)))]
    -> SDoc
    ppr_apps HsExpr (GhcPass p)
    fun (LHsExpr (GhcPass p)
    -> Either
         (LHsExpr (GhcPass p)) (LHsWcType (GhcPass (NoGhcTcPass p)))
    forall a b. a -> Either a b
    Left LHsExpr (GhcPass p)
    arg Either (LHsExpr (GhcPass p)) (LHsWcType (GhcPass (NoGhcTcPass p)))
    -> [Either
          (LHsExpr (GhcPass p)) (LHsWcType (GhcPass (NoGhcTcPass p)))]
    -> [Either
          (LHsExpr (GhcPass p)) (LHsWcType (GhcPass (NoGhcTcPass p)))]
    forall a. a -> [a] -> [a]
    : [Either
       (LHsExpr (GhcPass p)) (LHsWcType (GhcPass (NoGhcTcPass p)))]
    [Either (LHsExpr (GhcPass p)) (LHsWcType (NoGhcTc (GhcPass p)))]
    args)
    ppr_apps (HsAppType XAppTypeE (GhcPass p)
    _ (L SrcSpan
    _ HsExpr (GhcPass p)
    fun) LHsWcType (NoGhcTc (GhcPass p))
    arg)    [Either (LHsExpr (GhcPass p)) (LHsWcType (NoGhcTc (GhcPass p)))]
    args
      = HsExpr (GhcPass p)
    -> [Either (LHsExpr (GhcPass p)) (LHsWcType (NoGhcTc (GhcPass p)))]
    -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    HsExpr (GhcPass p)
    -> [Either (LHsExpr (GhcPass p)) (LHsWcType (NoGhcTc (GhcPass p)))]
    -> SDoc
    ppr_apps HsExpr (GhcPass p)
    fun (LHsWcType (GhcPass (NoGhcTcPass p))
    -> Either
         (LHsExpr (GhcPass p)) (LHsWcType (GhcPass (NoGhcTcPass p)))
    forall a b. b -> Either a b
    Right LHsWcType (GhcPass (NoGhcTcPass p))
    LHsWcType (NoGhcTc (GhcPass p))
    arg Either (LHsExpr (GhcPass p)) (LHsWcType (GhcPass (NoGhcTcPass p)))
    -> [Either
          (LHsExpr (GhcPass p)) (LHsWcType (GhcPass (NoGhcTcPass p)))]
    -> [Either
          (LHsExpr (GhcPass p)) (LHsWcType (GhcPass (NoGhcTcPass p)))]
    forall a. a -> [a] -> [a]
    : [Either
       (LHsExpr (GhcPass p)) (LHsWcType (GhcPass (NoGhcTcPass p)))]
    [Either (LHsExpr (GhcPass p)) (LHsWcType (NoGhcTc (GhcPass p)))]
    args)
    ppr_apps HsExpr (GhcPass p)
    fun [Either (LHsExpr (GhcPass p)) (LHsWcType (NoGhcTc (GhcPass p)))]
    args = SDoc -> Int -> SDoc -> SDoc
    hang (HsExpr (GhcPass p) -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    HsExpr (GhcPass p) -> SDoc
    ppr_expr HsExpr (GhcPass p)
    fun) Int
    2 ([SDoc] -> SDoc
    fsep ((Either (LHsExpr (GhcPass p)) (LHsWcType (GhcPass (NoGhcTcPass p)))
     -> SDoc)
    -> [Either
          (LHsExpr (GhcPass p)) (LHsWcType (GhcPass (NoGhcTcPass p)))]
    -> [SDoc]
    forall a b. (a -> b) -> [a] -> [b]
    map Either (LHsExpr (GhcPass p)) (LHsWcType (GhcPass (NoGhcTcPass p)))
    -> SDoc
    forall {a} {a}. (Outputable a, Outputable a) => Either a a -> SDoc
    pp [Either
       (LHsExpr (GhcPass p)) (LHsWcType (GhcPass (NoGhcTcPass p)))]
    [Either (LHsExpr (GhcPass p)) (LHsWcType (NoGhcTc (GhcPass p)))]
    args))
      where
        pp :: Either a a -> SDoc
    pp (Left a
    arg)                             = a -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr a
    arg
        -- pp (Right (LHsWcTypeX (HsWC { hswc_body = L _ arg })))
        --   = char '@' <> pprHsType arg
        pp (Right a
    arg)
          = String -> SDoc
    text String
    "@" SDoc -> SDoc -> SDoc
    <> a -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr a
    arg

    pprExternalSrcLoc :: (StringLiteral,(Int,Int),(Int,Int)) -> SDoc
    pprExternalSrcLoc :: (StringLiteral, (Int, Int), (Int, Int)) -> SDoc
    pprExternalSrcLoc (StringLiteral SourceText
    _ FastString
    src,(Int
    n1,Int
    n2),(Int
    n3,Int
    n4))
      = (FastString, (Int, Int), (Int, Int)) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr (FastString
    src,(Int
    n1,Int
    n2),(Int
    n3,Int
    n4))

    {-
    HsSyn records exactly where the user put parens, with HsPar.
    So generally speaking we print without adding any parens.
    However, some code is internally generated, and in some places
    parens are absolutely required; so for these places we use
    pprParendLExpr (but don't print double parens of course).

    For operator applications we don't add parens, because the operator
    fixities should do the job, except in debug mode (-dppr-debug) so we
    can see the structure of the parse tree.
    -}

    pprDebugParendExpr :: (OutputableBndrId p)
                       => PprPrec -> LHsExpr (GhcPass p) -> SDoc
    pprDebugParendExpr :: forall (p :: Pass).
    OutputableBndrId p =>
    PprPrec -> LHsExpr (GhcPass p) -> SDoc
    pprDebugParendExpr PprPrec
    p LHsExpr (GhcPass p)
    expr
      = (Bool -> SDoc) -> SDoc
    getPprDebug ((Bool -> SDoc) -> SDoc) -> (Bool -> SDoc) -> SDoc
    forall a b. (a -> b) -> a -> b
    $ \case
          Bool
    True  -> PprPrec -> LHsExpr (GhcPass p) -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    PprPrec -> LHsExpr (GhcPass p) -> SDoc
    pprParendLExpr PprPrec
    p LHsExpr (GhcPass p)
    expr
          Bool
    False -> LHsExpr (GhcPass p) -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    LHsExpr (GhcPass p) -> SDoc
    pprLExpr         LHsExpr (GhcPass p)
    expr

    pprParendLExpr :: (OutputableBndrId p)
                   => PprPrec -> LHsExpr (GhcPass p) -> SDoc
    pprParendLExpr :: forall (p :: Pass).
    OutputableBndrId p =>
    PprPrec -> LHsExpr (GhcPass p) -> SDoc
    pprParendLExpr PprPrec
    p (L SrcSpan
    _ HsExpr (GhcPass p)
    e) = PprPrec -> HsExpr (GhcPass p) -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    PprPrec -> HsExpr (GhcPass p) -> SDoc
    pprParendExpr PprPrec
    p HsExpr (GhcPass p)
    e

    pprParendExpr :: (OutputableBndrId p)
                  => PprPrec -> HsExpr (GhcPass p) -> SDoc
    pprParendExpr :: forall (p :: Pass).
    OutputableBndrId p =>
    PprPrec -> HsExpr (GhcPass p) -> SDoc
    pprParendExpr PprPrec
    p HsExpr (GhcPass p)
    expr
      | PprPrec -> HsExpr (GhcPass p) -> Bool
    forall (p :: Pass).
    IsPass p =>
    PprPrec -> HsExpr (GhcPass p) -> Bool
    hsExprNeedsParens PprPrec
    p HsExpr (GhcPass p)
    expr = SDoc -> SDoc
    parens (HsExpr (GhcPass p) -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    HsExpr (GhcPass p) -> SDoc
    pprExpr HsExpr (GhcPass p)
    expr)
      | Bool
    otherwise                = HsExpr (GhcPass p) -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    HsExpr (GhcPass p) -> SDoc
    pprExpr HsExpr (GhcPass p)
    expr
            -- Using pprLExpr makes sure that we go 'deeper'
            -- I think that is usually (always?) right

    -- | @'hsExprNeedsParens' p e@ returns 'True' if the expression @e@ needs
    -- parentheses under precedence @p@.
    hsExprNeedsParens :: forall p. IsPass p => PprPrec -> HsExpr (GhcPass p) -> Bool
    hsExprNeedsParens :: forall (p :: Pass).
    IsPass p =>
    PprPrec -> HsExpr (GhcPass p) -> Bool
    hsExprNeedsParens PprPrec
    p = HsExpr (GhcPass p) -> Bool
    go
      where
        go :: HsExpr (GhcPass p) -> Bool
    go (HsVar{})                      = Bool
    False
        go (HsUnboundVar{})               = Bool
    False
        go (HsConLikeOut{})               = Bool
    False
        go (HsIPVar{})                    = Bool
    False
        go (HsOverLabel{})                = Bool
    False
        go (HsLit XLitE (GhcPass p)
    _ HsLit (GhcPass p)
    l)                    = PprPrec -> HsLit (GhcPass p) -> Bool
    forall x. PprPrec -> HsLit x -> Bool
    hsLitNeedsParens PprPrec
    p HsLit (GhcPass p)
    l
        go (HsOverLit XOverLitE (GhcPass p)
    _ HsOverLit (GhcPass p)
    ol)               = PprPrec -> HsOverLit (GhcPass p) -> Bool
    forall x. PprPrec -> HsOverLit x -> Bool
    hsOverLitNeedsParens PprPrec
    p HsOverLit (GhcPass p)
    ol
        go (HsPar{})                      = Bool
    False
        go (HsApp{})                      = PprPrec
    p PprPrec -> PprPrec -> Bool
    forall a. Ord a => a -> a -> Bool
    >= PprPrec
    appPrec
        go (HsAppType {})                 = PprPrec
    p PprPrec -> PprPrec -> Bool
    forall a. Ord a => a -> a -> Bool
    >= PprPrec
    appPrec
        go (OpApp{})                      = PprPrec
    p PprPrec -> PprPrec -> Bool
    forall a. Ord a => a -> a -> Bool
    >= PprPrec
    opPrec
        go (NegApp{})                     = PprPrec
    p PprPrec -> PprPrec -> Bool
    forall a. Ord a => a -> a -> Bool
    > PprPrec
    topPrec
        go (SectionL{})                   = Bool
    True
        go (SectionR{})                   = Bool
    True
        go (ExplicitTuple{})              = Bool
    False
        go (ExplicitSum{})                = Bool
    False
        go (HsLam{})                      = PprPrec
    p PprPrec -> PprPrec -> Bool
    forall a. Ord a => a -> a -> Bool
    > PprPrec
    topPrec
        go (HsLamCase{})                  = PprPrec
    p PprPrec -> PprPrec -> Bool
    forall a. Ord a => a -> a -> Bool
    > PprPrec
    topPrec
        go (HsCase{})                     = PprPrec
    p PprPrec -> PprPrec -> Bool
    forall a. Ord a => a -> a -> Bool
    > PprPrec
    topPrec
        go (HsIf{})                       = PprPrec
    p PprPrec -> PprPrec -> Bool
    forall a. Ord a => a -> a -> Bool
    > PprPrec
    topPrec
        go (HsMultiIf{})                  = PprPrec
    p PprPrec -> PprPrec -> Bool
    forall a. Ord a => a -> a -> Bool
    > PprPrec
    topPrec
        go (HsLet{})                      = PprPrec
    p PprPrec -> PprPrec -> Bool
    forall a. Ord a => a -> a -> Bool
    > PprPrec
    topPrec
        go (HsDo XDo (GhcPass p)
    _ HsStmtContext GhcRn
    sc Located [ExprLStmt (GhcPass p)]
    _)
          | HsStmtContext GhcRn -> Bool
    forall id. HsStmtContext id -> Bool
    isComprehensionContext HsStmtContext GhcRn
    sc     = Bool
    False
          | Bool
    otherwise                     = PprPrec
    p PprPrec -> PprPrec -> Bool
    forall a. Ord a => a -> a -> Bool
    > PprPrec
    topPrec
        go (ExplicitList{})               = Bool
    False
        go (RecordUpd{})                  = Bool
    False
        go (ExprWithTySig{})              = PprPrec
    p PprPrec -> PprPrec -> Bool
    forall a. Ord a => a -> a -> Bool
    >= PprPrec
    sigPrec
        go (ArithSeq{})                   = Bool
    False
        go (HsPragE{})                    = PprPrec
    p PprPrec -> PprPrec -> Bool
    forall a. Ord a => a -> a -> Bool
    >= PprPrec
    appPrec
        go (HsSpliceE{})                  = Bool
    False
        go (HsBracket{})                  = Bool
    False
        go (HsRnBracketOut{})             = Bool
    False
        go (HsTcBracketOut{})             = Bool
    False
        go (HsProc{})                     = PprPrec
    p PprPrec -> PprPrec -> Bool
    forall a. Ord a => a -> a -> Bool
    > PprPrec
    topPrec
        go (HsStatic{})                   = PprPrec
    p PprPrec -> PprPrec -> Bool
    forall a. Ord a => a -> a -> Bool
    >= PprPrec
    appPrec
        go (HsTick XTick (GhcPass p)
    _ Tickish (IdP (GhcPass p))
    _ (L SrcSpan
    _ HsExpr (GhcPass p)
    e))           = HsExpr (GhcPass p) -> Bool
    go HsExpr (GhcPass p)
    e
        go (HsBinTick XBinTick (GhcPass p)
    _ Int
    _ Int
    _ (L SrcSpan
    _ HsExpr (GhcPass p)
    e))      = HsExpr (GhcPass p) -> Bool
    go HsExpr (GhcPass p)
    e
        go (RecordCon{})                  = Bool
    False
        go (HsRecFld{})                   = Bool
    False
        go (XExpr XXExpr (GhcPass p)
    x)
          | GhcPass p
    GhcTc <- forall (p :: Pass). IsPass p => GhcPass p
    ghcPass @p
          = case XXExpr (GhcPass p)
    x of
              WrapExpr      (HsWrap HsWrapper
    _ HsExpr GhcTc
    e)     -> HsExpr (GhcPass p) -> Bool
    go HsExpr (GhcPass p)
    HsExpr GhcTc
    e
              ExpansionExpr (HsExpanded HsExpr GhcRn
    a HsExpr GhcTc
    _) -> PprPrec -> HsExpr GhcRn -> Bool
    forall (p :: Pass).
    IsPass p =>
    PprPrec -> HsExpr (GhcPass p) -> Bool
    hsExprNeedsParens PprPrec
    p HsExpr GhcRn
    a
          | GhcPass p
    GhcRn <- forall (p :: Pass). IsPass p => GhcPass p
    ghcPass @p
          = case XXExpr (GhcPass p)
    x of HsExpanded HsExpr GhcRn
    a HsExpr GhcRn
    _ -> PprPrec -> HsExpr GhcRn -> Bool
    forall (p :: Pass).
    IsPass p =>
    PprPrec -> HsExpr (GhcPass p) -> Bool
    hsExprNeedsParens PprPrec
    p HsExpr GhcRn
    a
          | Bool
    otherwise
          = Bool
    True

    -- | @'parenthesizeHsExpr' p e@ checks if @'hsExprNeedsParens' p e@ is true,
    -- and if so, surrounds @e@ with an 'HsPar'. Otherwise, it simply returns @e@.
    parenthesizeHsExpr :: IsPass p => PprPrec -> LHsExpr (GhcPass p) -> LHsExpr (GhcPass p)
    parenthesizeHsExpr :: forall (p :: Pass).
    IsPass p =>
    PprPrec -> LHsExpr (GhcPass p) -> LHsExpr (GhcPass p)
    parenthesizeHsExpr PprPrec
    p le :: LHsExpr (GhcPass p)
    le@(L SrcSpan
    loc HsExpr (GhcPass p)
    e)
      | PprPrec -> HsExpr (GhcPass p) -> Bool
    forall (p :: Pass).
    IsPass p =>
    PprPrec -> HsExpr (GhcPass p) -> Bool
    hsExprNeedsParens PprPrec
    p HsExpr (GhcPass p)
    e = SrcSpan -> HsExpr (GhcPass p) -> LHsExpr (GhcPass p)
    forall l e. l -> e -> GenLocated l e
    L SrcSpan
    loc (XPar (GhcPass p) -> LHsExpr (GhcPass p) -> HsExpr (GhcPass p)
    forall p. XPar p -> LHsExpr p -> HsExpr p
    HsPar NoExtField
    XPar (GhcPass p)
    noExtField LHsExpr (GhcPass p)
    le)
      | Bool
    otherwise             = LHsExpr (GhcPass p)
    le

    stripParensLHsExpr :: LHsExpr (GhcPass p) -> LHsExpr (GhcPass p)
    stripParensLHsExpr :: forall (p :: Pass). LHsExpr (GhcPass p) -> LHsExpr (GhcPass p)
    stripParensLHsExpr (L SrcSpan
    _ (HsPar XPar (GhcPass p)
    _ GenLocated SrcSpan (HsExpr (GhcPass p))
    e)) = GenLocated SrcSpan (HsExpr (GhcPass p))
    -> GenLocated SrcSpan (HsExpr (GhcPass p))
    forall (p :: Pass). LHsExpr (GhcPass p) -> LHsExpr (GhcPass p)
    stripParensLHsExpr GenLocated SrcSpan (HsExpr (GhcPass p))
    e
    stripParensLHsExpr GenLocated SrcSpan (HsExpr (GhcPass p))
    e = GenLocated SrcSpan (HsExpr (GhcPass p))
    e

    stripParensHsExpr :: HsExpr (GhcPass p) -> HsExpr (GhcPass p)
    stripParensHsExpr :: forall (p :: Pass). HsExpr (GhcPass p) -> HsExpr (GhcPass p)
    stripParensHsExpr (HsPar XPar (GhcPass p)
    _ (L SrcSpan
    _ HsExpr (GhcPass p)
    e)) = HsExpr (GhcPass p) -> HsExpr (GhcPass p)
    forall (p :: Pass). HsExpr (GhcPass p) -> HsExpr (GhcPass p)
    stripParensHsExpr HsExpr (GhcPass p)
    e
    stripParensHsExpr HsExpr (GhcPass p)
    e = HsExpr (GhcPass p)
    e

    isAtomicHsExpr :: forall p. IsPass p => HsExpr (GhcPass p) -> Bool
    -- True of a single token
    isAtomicHsExpr :: forall (p :: Pass). IsPass p => HsExpr (GhcPass p) -> Bool
    isAtomicHsExpr (HsVar {})        = Bool
    True
    isAtomicHsExpr (HsConLikeOut {}) = Bool
    True
    isAtomicHsExpr (HsLit {})        = Bool
    True
    isAtomicHsExpr (HsOverLit {})    = Bool
    True
    isAtomicHsExpr (HsIPVar {})      = Bool
    True
    isAtomicHsExpr (HsOverLabel {})  = Bool
    True
    isAtomicHsExpr (HsUnboundVar {}) = Bool
    True
    isAtomicHsExpr (HsPar XPar (GhcPass p)
    _ LHsExpr (GhcPass p)
    e)       = HsExpr (GhcPass p) -> Bool
    forall (p :: Pass). IsPass p => HsExpr (GhcPass p) -> Bool
    isAtomicHsExpr (LHsExpr (GhcPass p) -> HsExpr (GhcPass p)
    forall l e. GenLocated l e -> e
    unLoc LHsExpr (GhcPass p)
    e)
    isAtomicHsExpr (HsRecFld{})      = Bool
    True
    isAtomicHsExpr (XExpr XXExpr (GhcPass p)
    x)
      | GhcPass p
    GhcTc <- forall (p :: Pass). IsPass p => GhcPass p
    ghcPass @p          = case XXExpr (GhcPass p)
    x of
          WrapExpr      (HsWrap HsWrapper
    _ HsExpr GhcTc
    e)     -> HsExpr GhcTc -> Bool
    forall (p :: Pass). IsPass p => HsExpr (GhcPass p) -> Bool
    isAtomicHsExpr HsExpr GhcTc
    e
          ExpansionExpr (HsExpanded HsExpr GhcRn
    a HsExpr GhcTc
    _) -> HsExpr GhcRn -> Bool
    forall (p :: Pass). IsPass p => HsExpr (GhcPass p) -> Bool
    isAtomicHsExpr HsExpr GhcRn
    a
      | GhcPass p
    GhcRn <- forall (p :: Pass). IsPass p => GhcPass p
    ghcPass @p          = case XXExpr (GhcPass p)
    x of
          HsExpanded HsExpr GhcRn
    a HsExpr GhcRn
    _         -> HsExpr GhcRn -> Bool
    forall (p :: Pass). IsPass p => HsExpr (GhcPass p) -> Bool
    isAtomicHsExpr HsExpr GhcRn
    a
    isAtomicHsExpr HsExpr (GhcPass p)
    _                 = Bool
    False

    instance Outputable (HsPragE (GhcPass p)) where
      ppr :: HsPragE (GhcPass p) -> SDoc
    ppr (HsPragSCC XSCC (GhcPass p)
    _ SourceText
    st (StringLiteral SourceText
    stl FastString
    lbl)) =
        SourceText -> SDoc -> SDoc
    pprWithSourceText SourceText
    st (String -> SDoc
    text String
    "{-# SCC")
         -- no doublequotes if stl empty, for the case where the SCC was written
         -- without quotes.
        SDoc -> SDoc -> SDoc
    <+> SourceText -> SDoc -> SDoc
    pprWithSourceText SourceText
    stl (FastString -> SDoc
    ftext FastString
    lbl) SDoc -> SDoc -> SDoc
    <+> String -> SDoc
    text String
    "#-}"
      ppr (HsPragTick XTickPragma (GhcPass p)
    _ SourceText
    st (StringLiteral SourceText
    sta FastString
    s, (Int
    v1,Int
    v2), (Int
    v3,Int
    v4)) ((SourceText
    s1,SourceText
    s2),(SourceText
    s3,SourceText
    s4))) =
        SourceText -> SDoc -> SDoc
    pprWithSourceText SourceText
    st (String -> SDoc
    text String
    "{-# GENERATED")
        SDoc -> SDoc -> SDoc
    <+> SourceText -> SDoc -> SDoc
    pprWithSourceText SourceText
    sta (SDoc -> SDoc
    doubleQuotes (SDoc -> SDoc) -> SDoc -> SDoc
    forall a b. (a -> b) -> a -> b
    $ FastString -> SDoc
    ftext FastString
    s)
        SDoc -> SDoc -> SDoc
    <+> SourceText -> SDoc -> SDoc
    pprWithSourceText SourceText
    s1 (Int -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr Int
    v1) SDoc -> SDoc -> SDoc
    <+> Char -> SDoc
    char Char
    ':' SDoc -> SDoc -> SDoc
    <+> SourceText -> SDoc -> SDoc
    pprWithSourceText SourceText
    s2 (Int -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr Int
    v2)
        SDoc -> SDoc -> SDoc
    <+> Char -> SDoc
    char Char
    '-'
        SDoc -> SDoc -> SDoc
    <+> SourceText -> SDoc -> SDoc
    pprWithSourceText SourceText
    s3 (Int -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr Int
    v3) SDoc -> SDoc -> SDoc
    <+> Char -> SDoc
    char Char
    ':' SDoc -> SDoc -> SDoc
    <+> SourceText -> SDoc -> SDoc
    pprWithSourceText SourceText
    s4 (Int -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr Int
    v4)
        SDoc -> SDoc -> SDoc
    <+> String -> SDoc
    text String
    "#-}"

    {-
    ************************************************************************
    *                                                                      *
    \subsection{Commands (in arrow abstractions)}
    *                                                                      *
    ************************************************************************

    We re-use HsExpr to represent these.
    -}

    -- | Located Haskell Command (for arrow syntax)
    type LHsCmd id = Located (HsCmd id)

    -- | Haskell Command (e.g. a "statement" in an Arrow proc block)
    data HsCmd id
      -- | - 'GHC.Parser.Annotation.AnnKeywordId' : 'GHC.Parser.Annotation.Annlarrowtail',
      --          'GHC.Parser.Annotation.Annrarrowtail','GHC.Parser.Annotation.AnnLarrowtail',
      --          'GHC.Parser.Annotation.AnnRarrowtail'

      -- For details on above see note [Api annotations] in GHC.Parser.Annotation
      = HsCmdArrApp          -- Arrow tail, or arrow application (f -< arg)
            (XCmdArrApp id)  -- type of the arrow expressions f,
                             -- of the form a t t', where arg :: t
            (LHsExpr id)     -- arrow expression, f
            (LHsExpr id)     -- input expression, arg
            HsArrAppType     -- higher-order (-<<) or first-order (-<)
            Bool             -- True => right-to-left (f -< arg)
                             -- False => left-to-right (arg >- f)

      -- | - 'GHC.Parser.Annotation.AnnKeywordId' : 'GHC.Parser.Annotation.AnnOpenB' @'(|'@,
      --         'GHC.Parser.Annotation.AnnCloseB' @'|)'@

      -- For details on above see note [Api annotations] in GHC.Parser.Annotation
      | HsCmdArrForm         -- Command formation,  (| e cmd1 .. cmdn |)
            (XCmdArrForm id)
            (LHsExpr id)     -- The operator.
                             -- After type-checking, a type abstraction to be
                             -- applied to the type of the local environment tuple
            LexicalFixity    -- Whether the operator appeared prefix or infix when
                             -- parsed.
            (Maybe Fixity)   -- fixity (filled in by the renamer), for forms that
                             -- were converted from OpApp's by the renamer
            [LHsCmdTop id]   -- argument commands

      | HsCmdApp    (XCmdApp id)
                    (LHsCmd id)
                    (LHsExpr id)

      | HsCmdLam    (XCmdLam id)
                    (MatchGroup id (LHsCmd id))     -- kappa
           -- ^ - 'GHC.Parser.Annotation.AnnKeywordId' : 'GHC.Parser.Annotation.AnnLam',
           --       'GHC.Parser.Annotation.AnnRarrow',

           -- For details on above see note [Api annotations] in GHC.Parser.Annotation

      | HsCmdPar    (XCmdPar id)
                    (LHsCmd id)                     -- parenthesised command
        -- ^ - 'GHC.Parser.Annotation.AnnKeywordId' : 'GHC.Parser.Annotation.AnnOpen' @'('@,
        --             'GHC.Parser.Annotation.AnnClose' @')'@

        -- For details on above see note [Api annotations] in GHC.Parser.Annotation

      | HsCmdCase   (XCmdCase id)
                    (LHsExpr id)
                    (MatchGroup id (LHsCmd id))     -- bodies are HsCmd's
        -- ^ - 'GHC.Parser.Annotation.AnnKeywordId' : 'GHC.Parser.Annotation.AnnCase',
        --       'GHC.Parser.Annotation.AnnOf','GHC.Parser.Annotation.AnnOpen' @'{'@,
        --       'GHC.Parser.Annotation.AnnClose' @'}'@

        -- For details on above see note [Api annotations] in GHC.Parser.Annotation

      | HsCmdLamCase (XCmdLamCase id)
                     (MatchGroup id (LHsCmd id))    -- bodies are HsCmd's
        -- ^ - 'GHC.Parser.Annotation.AnnKeywordId' : 'GHC.Parser.Annotation.AnnLam',
        --       'GHC.Parser.Annotation.AnnCase','GHC.Parser.Annotation.AnnOpen' @'{'@,
        --       'GHC.Parser.Annotation.AnnClose' @'}'@

        -- For details on above see note [Api annotations] in GHC.Parser.Annotation

      | HsCmdIf     (XCmdIf id)
                    (SyntaxExpr id)         -- cond function
                    (LHsExpr id)            -- predicate
                    (LHsCmd id)             -- then part
                    (LHsCmd id)             -- else part
        -- ^ - 'GHC.Parser.Annotation.AnnKeywordId' : 'GHC.Parser.Annotation.AnnIf',
        --       'GHC.Parser.Annotation.AnnSemi',
        --       'GHC.Parser.Annotation.AnnThen','GHC.Parser.Annotation.AnnSemi',
        --       'GHC.Parser.Annotation.AnnElse',

        -- For details on above see note [Api annotations] in GHC.Parser.Annotation

      | HsCmdLet    (XCmdLet id)
                    (LHsLocalBinds id)      -- let(rec)
                    (LHsCmd  id)
        -- ^ - 'GHC.Parser.Annotation.AnnKeywordId' : 'GHC.Parser.Annotation.AnnLet',
        --       'GHC.Parser.Annotation.AnnOpen' @'{'@,
        --       'GHC.Parser.Annotation.AnnClose' @'}'@,'GHC.Parser.Annotation.AnnIn'

        -- For details on above see note [Api annotations] in GHC.Parser.Annotation

      | HsCmdDo     (XCmdDo id)                     -- Type of the whole expression
                    (Located [CmdLStmt id])
        -- ^ - 'GHC.Parser.Annotation.AnnKeywordId' : 'GHC.Parser.Annotation.AnnDo',
        --             'GHC.Parser.Annotation.AnnOpen', 'GHC.Parser.Annotation.AnnSemi',
        --             'GHC.Parser.Annotation.AnnVbar',
        --             'GHC.Parser.Annotation.AnnClose'

        -- For details on above see note [Api annotations] in GHC.Parser.Annotation

      | XCmd        !(XXCmd id)     -- Note [Trees that Grow] extension point

    type instance XCmdArrApp  GhcPs = NoExtField
    type instance XCmdArrApp  GhcRn = NoExtField
    type instance XCmdArrApp  GhcTc = Type

    type instance XCmdArrForm (GhcPass _) = NoExtField
    type instance XCmdApp     (GhcPass _) = NoExtField
    type instance XCmdLam     (GhcPass _) = NoExtField
    type instance XCmdPar     (GhcPass _) = NoExtField
    type instance XCmdCase    (GhcPass _) = NoExtField
    type instance XCmdLamCase (GhcPass _) = NoExtField
    type instance XCmdIf      (GhcPass _) = NoExtField
    type instance XCmdLet     (GhcPass _) = NoExtField

    type instance XCmdDo      GhcPs = NoExtField
    type instance XCmdDo      GhcRn = NoExtField
    type instance XCmdDo      GhcTc = Type

    type instance XCmdWrap    (GhcPass _) = NoExtField

    type instance XXCmd       GhcPs = NoExtCon
    type instance XXCmd       GhcRn = NoExtCon
    type instance XXCmd       GhcTc = HsWrap HsCmd
        -- If   cmd :: arg1 --> res
        --      wrap :: arg1 "->" arg2
        -- Then (XCmd (HsWrap wrap cmd)) :: arg2 --> res

    -- | Haskell Array Application Type
    data HsArrAppType = HsHigherOrderApp | HsFirstOrderApp
      deriving Typeable HsArrAppType
    Typeable HsArrAppType
    -> (forall (c :: * -> *).
        (forall d b. Data d => c (d -> b) -> d -> c b)
        -> (forall g. g -> c g) -> HsArrAppType -> c HsArrAppType)
    -> (forall (c :: * -> *).
        (forall b r. Data b => c (b -> r) -> c r)
        -> (forall r. r -> c r) -> Constr -> c HsArrAppType)
    -> (HsArrAppType -> Constr)
    -> (HsArrAppType -> DataType)
    -> (forall (t :: * -> *) (c :: * -> *).
        Typeable t =>
        (forall d. Data d => c (t d)) -> Maybe (c HsArrAppType))
    -> (forall (t :: * -> * -> *) (c :: * -> *).
        Typeable t =>
        (forall d e. (Data d, Data e) => c (t d e))
        -> Maybe (c HsArrAppType))
    -> ((forall b. Data b => b -> b) -> HsArrAppType -> HsArrAppType)
    -> (forall r r'.
        (r -> r' -> r)
        -> r -> (forall d. Data d => d -> r') -> HsArrAppType -> r)
    -> (forall r r'.
        (r' -> r -> r)
        -> r -> (forall d. Data d => d -> r') -> HsArrAppType -> r)
    -> (forall u. (forall d. Data d => d -> u) -> HsArrAppType -> [u])
    -> (forall u.
        Int -> (forall d. Data d => d -> u) -> HsArrAppType -> u)
    -> (forall (m :: * -> *).
        Monad m =>
        (forall d. Data d => d -> m d) -> HsArrAppType -> m HsArrAppType)
    -> (forall (m :: * -> *).
        MonadPlus m =>
        (forall d. Data d => d -> m d) -> HsArrAppType -> m HsArrAppType)
    -> (forall (m :: * -> *).
        MonadPlus m =>
        (forall d. Data d => d -> m d) -> HsArrAppType -> m HsArrAppType)
    -> Data HsArrAppType
    HsArrAppType -> DataType
    HsArrAppType -> Constr
    (forall b. Data b => b -> b) -> HsArrAppType -> HsArrAppType
    forall a.
    Typeable a
    -> (forall (c :: * -> *).
        (forall d b. Data d => c (d -> b) -> d -> c b)
        -> (forall g. g -> c g) -> a -> c a)
    -> (forall (c :: * -> *).
        (forall b r. Data b => c (b -> r) -> c r)
        -> (forall r. r -> c r) -> Constr -> c a)
    -> (a -> Constr)
    -> (a -> DataType)
    -> (forall (t :: * -> *) (c :: * -> *).
        Typeable t =>
        (forall d. Data d => c (t d)) -> Maybe (c a))
    -> (forall (t :: * -> * -> *) (c :: * -> *).
        Typeable t =>
        (forall d e. (Data d, Data e) => c (t d e)) -> Maybe (c a))
    -> ((forall b. Data b => b -> b) -> a -> a)
    -> (forall r r'.
        (r -> r' -> r) -> r -> (forall d. Data d => d -> r') -> a -> r)
    -> (forall r r'.
        (r' -> r -> r) -> r -> (forall d. Data d => d -> r') -> a -> r)
    -> (forall u. (forall d. Data d => d -> u) -> a -> [u])
    -> (forall u. Int -> (forall d. Data d => d -> u) -> a -> u)
    -> (forall (m :: * -> *).
        Monad m =>
        (forall d. Data d => d -> m d) -> a -> m a)
    -> (forall (m :: * -> *).
        MonadPlus m =>
        (forall d. Data d => d -> m d) -> a -> m a)
    -> (forall (m :: * -> *).
        MonadPlus m =>
        (forall d. Data d => d -> m d) -> a -> m a)
    -> Data a
    forall u. Int -> (forall d. Data d => d -> u) -> HsArrAppType -> u
    forall u. (forall d. Data d => d -> u) -> HsArrAppType -> [u]
    forall r r'.
    (r -> r' -> r)
    -> r -> (forall d. Data d => d -> r') -> HsArrAppType -> r
    forall r r'.
    (r' -> r -> r)
    -> r -> (forall d. Data d => d -> r') -> HsArrAppType -> r
    forall (m :: * -> *).
    Monad m =>
    (forall d. Data d => d -> m d) -> HsArrAppType -> m HsArrAppType
    forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d) -> HsArrAppType -> m HsArrAppType
    forall (c :: * -> *).
    (forall b r. Data b => c (b -> r) -> c r)
    -> (forall r. r -> c r) -> Constr -> c HsArrAppType
    forall (c :: * -> *).
    (forall d b. Data d => c (d -> b) -> d -> c b)
    -> (forall g. g -> c g) -> HsArrAppType -> c HsArrAppType
    forall (t :: * -> *) (c :: * -> *).
    Typeable t =>
    (forall d. Data d => c (t d)) -> Maybe (c HsArrAppType)
    forall (t :: * -> * -> *) (c :: * -> *).
    Typeable t =>
    (forall d e. (Data d, Data e) => c (t d e))
    -> Maybe (c HsArrAppType)
    gmapMo :: forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d) -> HsArrAppType -> m HsArrAppType
    $cgmapMo :: forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d) -> HsArrAppType -> m HsArrAppType
    gmapMp :: forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d) -> HsArrAppType -> m HsArrAppType
    $cgmapMp :: forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d) -> HsArrAppType -> m HsArrAppType
    gmapM :: forall (m :: * -> *).
    Monad m =>
    (forall d. Data d => d -> m d) -> HsArrAppType -> m HsArrAppType
    $cgmapM :: forall (m :: * -> *).
    Monad m =>
    (forall d. Data d => d -> m d) -> HsArrAppType -> m HsArrAppType
    gmapQi :: forall u. Int -> (forall d. Data d => d -> u) -> HsArrAppType -> u
    $cgmapQi :: forall u. Int -> (forall d. Data d => d -> u) -> HsArrAppType -> u
    gmapQ :: forall u. (forall d. Data d => d -> u) -> HsArrAppType -> [u]
    $cgmapQ :: forall u. (forall d. Data d => d -> u) -> HsArrAppType -> [u]
    gmapQr :: forall r r'.
    (r' -> r -> r)
    -> r -> (forall d. Data d => d -> r') -> HsArrAppType -> r
    $cgmapQr :: forall r r'.
    (r' -> r -> r)
    -> r -> (forall d. Data d => d -> r') -> HsArrAppType -> r
    gmapQl :: forall r r'.
    (r -> r' -> r)
    -> r -> (forall d. Data d => d -> r') -> HsArrAppType -> r
    $cgmapQl :: forall r r'.
    (r -> r' -> r)
    -> r -> (forall d. Data d => d -> r') -> HsArrAppType -> r
    gmapT :: (forall b. Data b => b -> b) -> HsArrAppType -> HsArrAppType
    $cgmapT :: (forall b. Data b => b -> b) -> HsArrAppType -> HsArrAppType
    dataCast2 :: forall (t :: * -> * -> *) (c :: * -> *).
    Typeable t =>
    (forall d e. (Data d, Data e) => c (t d e))
    -> Maybe (c HsArrAppType)
    $cdataCast2 :: forall (t :: * -> * -> *) (c :: * -> *).
    Typeable t =>
    (forall d e. (Data d, Data e) => c (t d e))
    -> Maybe (c HsArrAppType)
    dataCast1 :: forall (t :: * -> *) (c :: * -> *).
    Typeable t =>
    (forall d. Data d => c (t d)) -> Maybe (c HsArrAppType)
    $cdataCast1 :: forall (t :: * -> *) (c :: * -> *).
    Typeable t =>
    (forall d. Data d => c (t d)) -> Maybe (c HsArrAppType)
    dataTypeOf :: HsArrAppType -> DataType
    $cdataTypeOf :: HsArrAppType -> DataType
    toConstr :: HsArrAppType -> Constr
    $ctoConstr :: HsArrAppType -> Constr
    gunfold :: forall (c :: * -> *).
    (forall b r. Data b => c (b -> r) -> c r)
    -> (forall r. r -> c r) -> Constr -> c HsArrAppType
    $cgunfold :: forall (c :: * -> *).
    (forall b r. Data b => c (b -> r) -> c r)
    -> (forall r. r -> c r) -> Constr -> c HsArrAppType
    gfoldl :: forall (c :: * -> *).
    (forall d b. Data d => c (d -> b) -> d -> c b)
    -> (forall g. g -> c g) -> HsArrAppType -> c HsArrAppType
    $cgfoldl :: forall (c :: * -> *).
    (forall d b. Data d => c (d -> b) -> d -> c b)
    -> (forall g. g -> c g) -> HsArrAppType -> c HsArrAppType
    Data

    {- | Top-level command, introducing a new arrow.
    This may occur inside a proc (where the stack is empty) or as an
    argument of a command-forming operator.
    -}

    -- | Located Haskell Top-level Command
    type LHsCmdTop p = Located (HsCmdTop p)

    -- | Haskell Top-level Command
    data HsCmdTop p
      = HsCmdTop (XCmdTop p)
                 (LHsCmd p)
      | XCmdTop !(XXCmdTop p)        -- Note [Trees that Grow] extension point

    data CmdTopTc
      = CmdTopTc Type    -- Nested tuple of inputs on the command's stack
                 Type    -- return type of the command
                 (CmdSyntaxTable GhcTc) -- See Note [CmdSyntaxTable]

    type instance XCmdTop  GhcPs = NoExtField
    type instance XCmdTop  GhcRn = CmdSyntaxTable GhcRn -- See Note [CmdSyntaxTable]
    type instance XCmdTop  GhcTc = CmdTopTc

    type instance XXCmdTop (GhcPass _) = NoExtCon

    instance (OutputableBndrId p) => Outputable (HsCmd (GhcPass p)) where
        ppr :: HsCmd (GhcPass p) -> SDoc
    ppr HsCmd (GhcPass p)
    cmd = HsCmd (GhcPass p) -> SDoc
    forall (p :: Pass). OutputableBndrId p => HsCmd (GhcPass p) -> SDoc
    pprCmd HsCmd (GhcPass p)
    cmd

    -----------------------
    -- pprCmd and pprLCmd call pprDeeper;
    -- the underscore versions do not
    pprLCmd :: (OutputableBndrId p) => LHsCmd (GhcPass p) -> SDoc
    pprLCmd :: forall (p :: Pass).
    OutputableBndrId p =>
    LHsCmd (GhcPass p) -> SDoc
    pprLCmd (L SrcSpan
    _ HsCmd (GhcPass p)
    c) = HsCmd (GhcPass p) -> SDoc
    forall (p :: Pass). OutputableBndrId p => HsCmd (GhcPass p) -> SDoc
    pprCmd HsCmd (GhcPass p)
    c

    pprCmd :: (OutputableBndrId p) => HsCmd (GhcPass p) -> SDoc
    pprCmd :: forall (p :: Pass). OutputableBndrId p => HsCmd (GhcPass p) -> SDoc
    pprCmd HsCmd (GhcPass p)
    c | HsCmd (GhcPass p) -> Bool
    forall id. HsCmd id -> Bool
    isQuietHsCmd HsCmd (GhcPass p)
    c =            HsCmd (GhcPass p) -> SDoc
    forall (p :: Pass). OutputableBndrId p => HsCmd (GhcPass p) -> SDoc
    ppr_cmd HsCmd (GhcPass p)
    c
             | Bool
    otherwise      = SDoc -> SDoc
    pprDeeper (HsCmd (GhcPass p) -> SDoc
    forall (p :: Pass). OutputableBndrId p => HsCmd (GhcPass p) -> SDoc
    ppr_cmd HsCmd (GhcPass p)
    c)

    isQuietHsCmd :: HsCmd id -> Bool
    -- Parentheses do display something, but it gives little info and
    -- if we go deeper when we go inside them then we get ugly things
    -- like (...)
    isQuietHsCmd :: forall id. HsCmd id -> Bool
    isQuietHsCmd (HsCmdPar {}) = Bool
    True
    -- applications don't display anything themselves
    isQuietHsCmd (HsCmdApp {}) = Bool
    True
    isQuietHsCmd HsCmd id
    _ = Bool
    False

    -----------------------
    ppr_lcmd :: (OutputableBndrId p) => LHsCmd (GhcPass p) -> SDoc
    ppr_lcmd :: forall (p :: Pass).
    OutputableBndrId p =>
    LHsCmd (GhcPass p) -> SDoc
    ppr_lcmd LHsCmd (GhcPass p)
    c = HsCmd (GhcPass p) -> SDoc
    forall (p :: Pass). OutputableBndrId p => HsCmd (GhcPass p) -> SDoc
    ppr_cmd (LHsCmd (GhcPass p) -> HsCmd (GhcPass p)
    forall l e. GenLocated l e -> e
    unLoc LHsCmd (GhcPass p)
    c)

    ppr_cmd :: forall p. (OutputableBndrId p) => HsCmd (GhcPass p) -> SDoc
    ppr_cmd :: forall (p :: Pass). OutputableBndrId p => HsCmd (GhcPass p) -> SDoc
    ppr_cmd (HsCmdPar XCmdPar (GhcPass p)
    _ LHsCmd (GhcPass p)
    c) = SDoc -> SDoc
    parens (LHsCmd (GhcPass p) -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    LHsCmd (GhcPass p) -> SDoc
    ppr_lcmd LHsCmd (GhcPass p)
    c)

    ppr_cmd (HsCmdApp XCmdApp (GhcPass p)
    _ LHsCmd (GhcPass p)
    c LHsExpr (GhcPass p)
    e)
      = let (LHsCmd (GhcPass p)
    fun, [LHsExpr (GhcPass p)]
    args) = LHsCmd (GhcPass p)
    -> [LHsExpr (GhcPass p)]
    -> (LHsCmd (GhcPass p), [LHsExpr (GhcPass p)])
    forall {id}. LHsCmd id -> [LHsExpr id] -> (LHsCmd id, [LHsExpr id])
    collect_args LHsCmd (GhcPass p)
    c [LHsExpr (GhcPass p)
    e] in
        SDoc -> Int -> SDoc -> SDoc
    hang (LHsCmd (GhcPass p) -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    LHsCmd (GhcPass p) -> SDoc
    ppr_lcmd LHsCmd (GhcPass p)
    fun) Int
    2 ([SDoc] -> SDoc
    sep ((LHsExpr (GhcPass p) -> SDoc) -> [LHsExpr (GhcPass p)] -> [SDoc]
    forall a b. (a -> b) -> [a] -> [b]
    map LHsExpr (GhcPass p) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr [LHsExpr (GhcPass p)]
    args))
      where
        collect_args :: LHsCmd id -> [LHsExpr id] -> (LHsCmd id, [LHsExpr id])
    collect_args (L SrcSpan
    _ (HsCmdApp XCmdApp id
    _ LHsCmd id
    fun LHsExpr id
    arg)) [LHsExpr id]
    args = LHsCmd id -> [LHsExpr id] -> (LHsCmd id, [LHsExpr id])
    collect_args LHsCmd id
    fun (LHsExpr id
    argLHsExpr id -> [LHsExpr id] -> [LHsExpr id]
    forall a. a -> [a] -> [a]
    :[LHsExpr id]
    args)
        collect_args LHsCmd id
    fun [LHsExpr id]
    args = (LHsCmd id
    fun, [LHsExpr id]
    args)

    ppr_cmd (HsCmdLam XCmdLam (GhcPass p)
    _ MatchGroup (GhcPass p) (LHsCmd (GhcPass p))
    matches)
      = MatchGroup (GhcPass p) (LHsCmd (GhcPass p)) -> SDoc
    forall (idR :: Pass) body.
    (OutputableBndrId idR, Outputable body) =>
    MatchGroup (GhcPass idR) body -> SDoc
    pprMatches MatchGroup (GhcPass p) (LHsCmd (GhcPass p))
    matches

    ppr_cmd (HsCmdCase XCmdCase (GhcPass p)
    _ LHsExpr (GhcPass p)
    expr MatchGroup (GhcPass p) (LHsCmd (GhcPass p))
    matches)
      = [SDoc] -> SDoc
    sep [ [SDoc] -> SDoc
    sep [String -> SDoc
    text String
    "case", Int -> SDoc -> SDoc
    nest Int
    4 (LHsExpr (GhcPass p) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr LHsExpr (GhcPass p)
    expr), PtrString -> SDoc
    ptext (String -> PtrString
    sLit String
    "of")],
              Int -> SDoc -> SDoc
    nest Int
    2 (MatchGroup (GhcPass p) (LHsCmd (GhcPass p)) -> SDoc
    forall (idR :: Pass) body.
    (OutputableBndrId idR, Outputable body) =>
    MatchGroup (GhcPass idR) body -> SDoc
    pprMatches MatchGroup (GhcPass p) (LHsCmd (GhcPass p))
    matches) ]

    ppr_cmd (HsCmdLamCase XCmdLamCase (GhcPass p)
    _ MatchGroup (GhcPass p) (LHsCmd (GhcPass p))
    matches)
      = [SDoc] -> SDoc
    sep [ String -> SDoc
    text String
    "\\case", Int -> SDoc -> SDoc
    nest Int
    2 (MatchGroup (GhcPass p) (LHsCmd (GhcPass p)) -> SDoc
    forall (idR :: Pass) body.
    (OutputableBndrId idR, Outputable body) =>
    MatchGroup (GhcPass idR) body -> SDoc
    pprMatches MatchGroup (GhcPass p) (LHsCmd (GhcPass p))
    matches) ]

    ppr_cmd (HsCmdIf XCmdIf (GhcPass p)
    _ SyntaxExpr (GhcPass p)
    _ LHsExpr (GhcPass p)
    e LHsCmd (GhcPass p)
    ct LHsCmd (GhcPass p)
    ce)
      = [SDoc] -> SDoc
    sep [[SDoc] -> SDoc
    hsep [String -> SDoc
    text String
    "if", Int -> SDoc -> SDoc
    nest Int
    2 (LHsExpr (GhcPass p) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr LHsExpr (GhcPass p)
    e), PtrString -> SDoc
    ptext (String -> PtrString
    sLit String
    "then")],
             Int -> SDoc -> SDoc
    nest Int
    4 (LHsCmd (GhcPass p) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr LHsCmd (GhcPass p)
    ct),
             String -> SDoc
    text String
    "else",
             Int -> SDoc -> SDoc
    nest Int
    4 (LHsCmd (GhcPass p) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr LHsCmd (GhcPass p)
    ce)]

    -- special case: let ... in let ...
    ppr_cmd (HsCmdLet XCmdLet (GhcPass p)
    _ (L SrcSpan
    _ HsLocalBinds (GhcPass p)
    binds) cmd :: LHsCmd (GhcPass p)
    cmd@(L SrcSpan
    _ (HsCmdLet {})))
      = [SDoc] -> SDoc
    sep [SDoc -> Int -> SDoc -> SDoc
    hang (String -> SDoc
    text String
    "let") Int
    2 ([SDoc] -> SDoc
    hsep [HsLocalBinds (GhcPass p) -> SDoc
    forall (idL :: Pass) (idR :: Pass).
    (OutputableBndrId idL, OutputableBndrId idR) =>
    HsLocalBindsLR (GhcPass idL) (GhcPass idR) -> SDoc
    pprBinds HsLocalBinds (GhcPass p)
    binds, PtrString -> SDoc
    ptext (String -> PtrString
    sLit String
    "in")]),
             LHsCmd (GhcPass p) -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    LHsCmd (GhcPass p) -> SDoc
    ppr_lcmd LHsCmd (GhcPass p)
    cmd]

    ppr_cmd (HsCmdLet XCmdLet (GhcPass p)
    _ (L SrcSpan
    _ HsLocalBinds (GhcPass p)
    binds) LHsCmd (GhcPass p)
    cmd)
      = [SDoc] -> SDoc
    sep [SDoc -> Int -> SDoc -> SDoc
    hang (String -> SDoc
    text String
    "let") Int
    2 (HsLocalBinds (GhcPass p) -> SDoc
    forall (idL :: Pass) (idR :: Pass).
    (OutputableBndrId idL, OutputableBndrId idR) =>
    HsLocalBindsLR (GhcPass idL) (GhcPass idR) -> SDoc
    pprBinds HsLocalBinds (GhcPass p)
    binds),
             SDoc -> Int -> SDoc -> SDoc
    hang (String -> SDoc
    text String
    "in")  Int
    2 (LHsCmd (GhcPass p) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr LHsCmd (GhcPass p)
    cmd)]

    ppr_cmd (HsCmdDo XCmdDo (GhcPass p)
    _ (L SrcSpan
    _ [CmdLStmt (GhcPass p)]
    stmts))  = HsStmtContext Any -> [CmdLStmt (GhcPass p)] -> SDoc
    forall (p :: Pass) body any.
    (OutputableBndrId p, Outputable body) =>
    HsStmtContext any -> [LStmt (GhcPass p) body] -> SDoc
    pprDo HsStmtContext Any
    forall p. HsStmtContext p
    ArrowExpr [CmdLStmt (GhcPass p)]
    stmts

    ppr_cmd (HsCmdArrApp XCmdArrApp (GhcPass p)
    _ LHsExpr (GhcPass p)
    arrow LHsExpr (GhcPass p)
    arg HsArrAppType
    HsFirstOrderApp Bool
    True)
      = [SDoc] -> SDoc
    hsep [LHsExpr (GhcPass p) -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    LHsExpr (GhcPass p) -> SDoc
    ppr_lexpr LHsExpr (GhcPass p)
    arrow, SDoc
    larrowt, LHsExpr (GhcPass p) -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    LHsExpr (GhcPass p) -> SDoc
    ppr_lexpr LHsExpr (GhcPass p)
    arg]
    ppr_cmd (HsCmdArrApp XCmdArrApp (GhcPass p)
    _ LHsExpr (GhcPass p)
    arrow LHsExpr (GhcPass p)
    arg HsArrAppType
    HsFirstOrderApp Bool
    False)
      = [SDoc] -> SDoc
    hsep [LHsExpr (GhcPass p) -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    LHsExpr (GhcPass p) -> SDoc
    ppr_lexpr LHsExpr (GhcPass p)
    arg, SDoc
    arrowt, LHsExpr (GhcPass p) -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    LHsExpr (GhcPass p) -> SDoc
    ppr_lexpr LHsExpr (GhcPass p)
    arrow]
    ppr_cmd (HsCmdArrApp XCmdArrApp (GhcPass p)
    _ LHsExpr (GhcPass p)
    arrow LHsExpr (GhcPass p)
    arg HsArrAppType
    HsHigherOrderApp Bool
    True)
      = [SDoc] -> SDoc
    hsep [LHsExpr (GhcPass p) -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    LHsExpr (GhcPass p) -> SDoc
    ppr_lexpr LHsExpr (GhcPass p)
    arrow, SDoc
    larrowtt, LHsExpr (GhcPass p) -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    LHsExpr (GhcPass p) -> SDoc
    ppr_lexpr LHsExpr (GhcPass p)
    arg]
    ppr_cmd (HsCmdArrApp XCmdArrApp (GhcPass p)
    _ LHsExpr (GhcPass p)
    arrow LHsExpr (GhcPass p)
    arg HsArrAppType
    HsHigherOrderApp Bool
    False)
      = [SDoc] -> SDoc
    hsep [LHsExpr (GhcPass p) -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    LHsExpr (GhcPass p) -> SDoc
    ppr_lexpr LHsExpr (GhcPass p)
    arg, SDoc
    arrowtt, LHsExpr (GhcPass p) -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    LHsExpr (GhcPass p) -> SDoc
    ppr_lexpr LHsExpr (GhcPass p)
    arrow]

    ppr_cmd (HsCmdArrForm XCmdArrForm (GhcPass p)
    _ (L SrcSpan
    _ (HsVar XVar (GhcPass p)
    _ (L SrcSpan
    _ IdP (GhcPass p)
    v))) LexicalFixity
    _ (Just Fixity
    _) [LHsCmdTop (GhcPass p)
    arg1, LHsCmdTop (GhcPass p)
    arg2])
      = SDoc -> Int -> SDoc -> SDoc
    hang (HsCmdTop (GhcPass p) -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    HsCmdTop (GhcPass p) -> SDoc
    pprCmdArg (LHsCmdTop (GhcPass p) -> HsCmdTop (GhcPass p)
    forall l e. GenLocated l e -> e
    unLoc LHsCmdTop (GhcPass p)
    arg1)) Int
    4 ([SDoc] -> SDoc
    sep [ IdGhcP p -> SDoc
    forall a. OutputableBndr a => a -> SDoc
    pprInfixOcc IdGhcP p
    IdP (GhcPass p)
    v
                                             , HsCmdTop (GhcPass p) -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    HsCmdTop (GhcPass p) -> SDoc
    pprCmdArg (LHsCmdTop (GhcPass p) -> HsCmdTop (GhcPass p)
    forall l e. GenLocated l e -> e
    unLoc LHsCmdTop (GhcPass p)
    arg2)])
    ppr_cmd (HsCmdArrForm XCmdArrForm (GhcPass p)
    _ (L SrcSpan
    _ (HsVar XVar (GhcPass p)
    _ (L SrcSpan
    _ IdP (GhcPass p)
    v))) LexicalFixity
    Infix Maybe Fixity
    _    [LHsCmdTop (GhcPass p)
    arg1, LHsCmdTop (GhcPass p)
    arg2])
      = SDoc -> Int -> SDoc -> SDoc
    hang (HsCmdTop (GhcPass p) -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    HsCmdTop (GhcPass p) -> SDoc
    pprCmdArg (LHsCmdTop (GhcPass p) -> HsCmdTop (GhcPass p)
    forall l e. GenLocated l e -> e
    unLoc LHsCmdTop (GhcPass p)
    arg1)) Int
    4 ([SDoc] -> SDoc
    sep [ IdGhcP p -> SDoc
    forall a. OutputableBndr a => a -> SDoc
    pprInfixOcc IdGhcP p
    IdP (GhcPass p)
    v
                                             , HsCmdTop (GhcPass p) -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    HsCmdTop (GhcPass p) -> SDoc
    pprCmdArg (LHsCmdTop (GhcPass p) -> HsCmdTop (GhcPass p)
    forall l e. GenLocated l e -> e
    unLoc LHsCmdTop (GhcPass p)
    arg2)])
    ppr_cmd (HsCmdArrForm XCmdArrForm (GhcPass p)
    _ (L SrcSpan
    _ (HsConLikeOut XConLikeOut (GhcPass p)
    _ ConLike
    c)) LexicalFixity
    _ (Just Fixity
    _) [LHsCmdTop (GhcPass p)
    arg1, LHsCmdTop (GhcPass p)
    arg2])
      = SDoc -> Int -> SDoc -> SDoc
    hang (HsCmdTop (GhcPass p) -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    HsCmdTop (GhcPass p) -> SDoc
    pprCmdArg (LHsCmdTop (GhcPass p) -> HsCmdTop (GhcPass p)
    forall l e. GenLocated l e -> e
    unLoc LHsCmdTop (GhcPass p)
    arg1)) Int
    4 ([SDoc] -> SDoc
    sep [ Name -> SDoc
    forall a. OutputableBndr a => a -> SDoc
    pprInfixOcc (ConLike -> Name
    conLikeName ConLike
    c)
                                             , HsCmdTop (GhcPass p) -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    HsCmdTop (GhcPass p) -> SDoc
    pprCmdArg (LHsCmdTop (GhcPass p) -> HsCmdTop (GhcPass p)
    forall l e. GenLocated l e -> e
    unLoc LHsCmdTop (GhcPass p)
    arg2)])
    ppr_cmd (HsCmdArrForm XCmdArrForm (GhcPass p)
    _ (L SrcSpan
    _ (HsConLikeOut XConLikeOut (GhcPass p)
    _ ConLike
    c)) LexicalFixity
    Infix Maybe Fixity
    _    [LHsCmdTop (GhcPass p)
    arg1, LHsCmdTop (GhcPass p)
    arg2])
      = SDoc -> Int -> SDoc -> SDoc
    hang (HsCmdTop (GhcPass p) -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    HsCmdTop (GhcPass p) -> SDoc
    pprCmdArg (LHsCmdTop (GhcPass p) -> HsCmdTop (GhcPass p)
    forall l e. GenLocated l e -> e
    unLoc LHsCmdTop (GhcPass p)
    arg1)) Int
    4 ([SDoc] -> SDoc
    sep [ Name -> SDoc
    forall a. OutputableBndr a => a -> SDoc
    pprInfixOcc (ConLike -> Name
    conLikeName ConLike
    c)
                                             , HsCmdTop (GhcPass p) -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    HsCmdTop (GhcPass p) -> SDoc
    pprCmdArg (LHsCmdTop (GhcPass p) -> HsCmdTop (GhcPass p)
    forall l e. GenLocated l e -> e
    unLoc LHsCmdTop (GhcPass p)
    arg2)])
    ppr_cmd (HsCmdArrForm XCmdArrForm (GhcPass p)
    _ LHsExpr (GhcPass p)
    op LexicalFixity
    _ Maybe Fixity
    _ [LHsCmdTop (GhcPass p)]
    args)
      = SDoc -> Int -> SDoc -> SDoc
    hang (String -> SDoc
    text String
    "(|" SDoc -> SDoc -> SDoc
    <+> LHsExpr (GhcPass p) -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    LHsExpr (GhcPass p) -> SDoc
    ppr_lexpr LHsExpr (GhcPass p)
    op)
             Int
    4 ([SDoc] -> SDoc
    sep ((LHsCmdTop (GhcPass p) -> SDoc)
    -> [LHsCmdTop (GhcPass p)] -> [SDoc]
    forall a b. (a -> b) -> [a] -> [b]
    map (HsCmdTop (GhcPass p) -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    HsCmdTop (GhcPass p) -> SDoc
    pprCmdArg(HsCmdTop (GhcPass p) -> SDoc)
    -> (LHsCmdTop (GhcPass p) -> HsCmdTop (GhcPass p))
    -> LHsCmdTop (GhcPass p)
    -> SDoc
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    .LHsCmdTop (GhcPass p) -> HsCmdTop (GhcPass p)
    forall l e. GenLocated l e -> e
    unLoc) [LHsCmdTop (GhcPass p)]
    args) SDoc -> SDoc -> SDoc
    <+> String -> SDoc
    text String
    "|)")
    ppr_cmd (XCmd XXCmd (GhcPass p)
    x) = case forall (p :: Pass). IsPass p => GhcPass p
    ghcPass @p of
    #if __GLASGOW_HASKELL__ < 811
      GhcPs -> ppr x
      GhcRn -> ppr x
    #endif
      GhcPass p
    GhcTc -> case XXCmd (GhcPass p)
    x of
        HsWrap HsWrapper
    w HsCmd GhcTc
    cmd -> HsWrapper -> (Bool -> SDoc) -> SDoc
    pprHsWrapper HsWrapper
    w (\Bool
    _ -> SDoc -> SDoc
    parens (HsCmd GhcTc -> SDoc
    forall (p :: Pass). OutputableBndrId p => HsCmd (GhcPass p) -> SDoc
    ppr_cmd HsCmd GhcTc
    cmd))

    pprCmdArg :: (OutputableBndrId p) => HsCmdTop (GhcPass p) -> SDoc
    pprCmdArg :: forall (p :: Pass).
    OutputableBndrId p =>
    HsCmdTop (GhcPass p) -> SDoc
    pprCmdArg (HsCmdTop XCmdTop (GhcPass p)
    _ LHsCmd (GhcPass p)
    cmd)
      = LHsCmd (GhcPass p) -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    LHsCmd (GhcPass p) -> SDoc
    ppr_lcmd LHsCmd (GhcPass p)
    cmd

    instance (OutputableBndrId p) => Outputable (HsCmdTop (GhcPass p)) where
        ppr :: HsCmdTop (GhcPass p) -> SDoc
    ppr = HsCmdTop (GhcPass p) -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    HsCmdTop (GhcPass p) -> SDoc
    pprCmdArg

    {-
    ************************************************************************
    *                                                                      *
    \subsection{Record binds}
    *                                                                      *
    ************************************************************************
    -}

    -- | Haskell Record Bindings
    type HsRecordBinds p = HsRecFields p (LHsExpr p)

    {-
    ************************************************************************
    *                                                                      *
    \subsection{@Match@, @GRHSs@, and @GRHS@ datatypes}
    *                                                                      *
    ************************************************************************

    @Match@es are sets of pattern bindings and right hand sides for
    functions, patterns or case branches. For example, if a function @g@
    is defined as:
    \begin{verbatim}
    g (x,y) = y
    g ((x:ys),y) = y+1,
    \end{verbatim}
    then \tr{g} has two @Match@es: @(x,y) = y@ and @((x:ys),y) = y+1@.

    It is always the case that each element of an @[Match]@ list has the
    same number of @pats@s inside it.  This corresponds to saying that
    a function defined by pattern matching must have the same number of
    patterns in each equation.
    -}

    data MatchGroup p body
      = MG { forall p body. MatchGroup p body -> XMG p body
    mg_ext     :: XMG p body -- Post-typechecker, types of args and result
           , forall p body. MatchGroup p body -> Located [LMatch p body]
    mg_alts    :: Located [LMatch p body]  -- The alternatives
           , forall p body. MatchGroup p body -> Origin
    mg_origin  :: Origin }
         -- The type is the type of the entire group
         --      t1 -> ... -> tn -> tr
         -- where there are n patterns
      | XMatchGroup !(XXMatchGroup p body)

    data MatchGroupTc
      = MatchGroupTc
           { MatchGroupTc -> [Scaled Type]
    mg_arg_tys :: [Scaled Type]  -- Types of the arguments, t1..tn
           , MatchGroupTc -> Type
    mg_res_ty  :: Type    -- Type of the result, tr
           } deriving Typeable MatchGroupTc
    Typeable MatchGroupTc
    -> (forall (c :: * -> *).
        (forall d b. Data d => c (d -> b) -> d -> c b)
        -> (forall g. g -> c g) -> MatchGroupTc -> c MatchGroupTc)
    -> (forall (c :: * -> *).
        (forall b r. Data b => c (b -> r) -> c r)
        -> (forall r. r -> c r) -> Constr -> c MatchGroupTc)
    -> (MatchGroupTc -> Constr)
    -> (MatchGroupTc -> DataType)
    -> (forall (t :: * -> *) (c :: * -> *).
        Typeable t =>
        (forall d. Data d => c (t d)) -> Maybe (c MatchGroupTc))
    -> (forall (t :: * -> * -> *) (c :: * -> *).
        Typeable t =>
        (forall d e. (Data d, Data e) => c (t d e))
        -> Maybe (c MatchGroupTc))
    -> ((forall b. Data b => b -> b) -> MatchGroupTc -> MatchGroupTc)
    -> (forall r r'.
        (r -> r' -> r)
        -> r -> (forall d. Data d => d -> r') -> MatchGroupTc -> r)
    -> (forall r r'.
        (r' -> r -> r)
        -> r -> (forall d. Data d => d -> r') -> MatchGroupTc -> r)
    -> (forall u. (forall d. Data d => d -> u) -> MatchGroupTc -> [u])
    -> (forall u.
        Int -> (forall d. Data d => d -> u) -> MatchGroupTc -> u)
    -> (forall (m :: * -> *).
        Monad m =>
        (forall d. Data d => d -> m d) -> MatchGroupTc -> m MatchGroupTc)
    -> (forall (m :: * -> *).
        MonadPlus m =>
        (forall d. Data d => d -> m d) -> MatchGroupTc -> m MatchGroupTc)
    -> (forall (m :: * -> *).
        MonadPlus m =>
        (forall d. Data d => d -> m d) -> MatchGroupTc -> m MatchGroupTc)
    -> Data MatchGroupTc
    MatchGroupTc -> DataType
    MatchGroupTc -> Constr
    (forall b. Data b => b -> b) -> MatchGroupTc -> MatchGroupTc
    forall a.
    Typeable a
    -> (forall (c :: * -> *).
        (forall d b. Data d => c (d -> b) -> d -> c b)
        -> (forall g. g -> c g) -> a -> c a)
    -> (forall (c :: * -> *).
        (forall b r. Data b => c (b -> r) -> c r)
        -> (forall r. r -> c r) -> Constr -> c a)
    -> (a -> Constr)
    -> (a -> DataType)
    -> (forall (t :: * -> *) (c :: * -> *).
        Typeable t =>
        (forall d. Data d => c (t d)) -> Maybe (c a))
    -> (forall (t :: * -> * -> *) (c :: * -> *).
        Typeable t =>
        (forall d e. (Data d, Data e) => c (t d e)) -> Maybe (c a))
    -> ((forall b. Data b => b -> b) -> a -> a)
    -> (forall r r'.
        (r -> r' -> r) -> r -> (forall d. Data d => d -> r') -> a -> r)
    -> (forall r r'.
        (r' -> r -> r) -> r -> (forall d. Data d => d -> r') -> a -> r)
    -> (forall u. (forall d. Data d => d -> u) -> a -> [u])
    -> (forall u. Int -> (forall d. Data d => d -> u) -> a -> u)
    -> (forall (m :: * -> *).
        Monad m =>
        (forall d. Data d => d -> m d) -> a -> m a)
    -> (forall (m :: * -> *).
        MonadPlus m =>
        (forall d. Data d => d -> m d) -> a -> m a)
    -> (forall (m :: * -> *).
        MonadPlus m =>
        (forall d. Data d => d -> m d) -> a -> m a)
    -> Data a
    forall u. Int -> (forall d. Data d => d -> u) -> MatchGroupTc -> u
    forall u. (forall d. Data d => d -> u) -> MatchGroupTc -> [u]
    forall r r'.
    (r -> r' -> r)
    -> r -> (forall d. Data d => d -> r') -> MatchGroupTc -> r
    forall r r'.
    (r' -> r -> r)
    -> r -> (forall d. Data d => d -> r') -> MatchGroupTc -> r
    forall (m :: * -> *).
    Monad m =>
    (forall d. Data d => d -> m d) -> MatchGroupTc -> m MatchGroupTc
    forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d) -> MatchGroupTc -> m MatchGroupTc
    forall (c :: * -> *).
    (forall b r. Data b => c (b -> r) -> c r)
    -> (forall r. r -> c r) -> Constr -> c MatchGroupTc
    forall (c :: * -> *).
    (forall d b. Data d => c (d -> b) -> d -> c b)
    -> (forall g. g -> c g) -> MatchGroupTc -> c MatchGroupTc
    forall (t :: * -> *) (c :: * -> *).
    Typeable t =>
    (forall d. Data d => c (t d)) -> Maybe (c MatchGroupTc)
    forall (t :: * -> * -> *) (c :: * -> *).
    Typeable t =>
    (forall d e. (Data d, Data e) => c (t d e))
    -> Maybe (c MatchGroupTc)
    gmapMo :: forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d) -> MatchGroupTc -> m MatchGroupTc
    $cgmapMo :: forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d) -> MatchGroupTc -> m MatchGroupTc
    gmapMp :: forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d) -> MatchGroupTc -> m MatchGroupTc
    $cgmapMp :: forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d) -> MatchGroupTc -> m MatchGroupTc
    gmapM :: forall (m :: * -> *).
    Monad m =>
    (forall d. Data d => d -> m d) -> MatchGroupTc -> m MatchGroupTc
    $cgmapM :: forall (m :: * -> *).
    Monad m =>
    (forall d. Data d => d -> m d) -> MatchGroupTc -> m MatchGroupTc
    gmapQi :: forall u. Int -> (forall d. Data d => d -> u) -> MatchGroupTc -> u
    $cgmapQi :: forall u. Int -> (forall d. Data d => d -> u) -> MatchGroupTc -> u
    gmapQ :: forall u. (forall d. Data d => d -> u) -> MatchGroupTc -> [u]
    $cgmapQ :: forall u. (forall d. Data d => d -> u) -> MatchGroupTc -> [u]
    gmapQr :: forall r r'.
    (r' -> r -> r)
    -> r -> (forall d. Data d => d -> r') -> MatchGroupTc -> r
    $cgmapQr :: forall r r'.
    (r' -> r -> r)
    -> r -> (forall d. Data d => d -> r') -> MatchGroupTc -> r
    gmapQl :: forall r r'.
    (r -> r' -> r)
    -> r -> (forall d. Data d => d -> r') -> MatchGroupTc -> r
    $cgmapQl :: forall r r'.
    (r -> r' -> r)
    -> r -> (forall d. Data d => d -> r') -> MatchGroupTc -> r
    gmapT :: (forall b. Data b => b -> b) -> MatchGroupTc -> MatchGroupTc
    $cgmapT :: (forall b. Data b => b -> b) -> MatchGroupTc -> MatchGroupTc
    dataCast2 :: forall (t :: * -> * -> *) (c :: * -> *).
    Typeable t =>
    (forall d e. (Data d, Data e) => c (t d e))
    -> Maybe (c MatchGroupTc)
    $cdataCast2 :: forall (t :: * -> * -> *) (c :: * -> *).
    Typeable t =>
    (forall d e. (Data d, Data e) => c (t d e))
    -> Maybe (c MatchGroupTc)
    dataCast1 :: forall (t :: * -> *) (c :: * -> *).
    Typeable t =>
    (forall d. Data d => c (t d)) -> Maybe (c MatchGroupTc)
    $cdataCast1 :: forall (t :: * -> *) (c :: * -> *).
    Typeable t =>
    (forall d. Data d => c (t d)) -> Maybe (c MatchGroupTc)
    dataTypeOf :: MatchGroupTc -> DataType
    $cdataTypeOf :: MatchGroupTc -> DataType
    toConstr :: MatchGroupTc -> Constr
    $ctoConstr :: MatchGroupTc -> Constr
    gunfold :: forall (c :: * -> *).
    (forall b r. Data b => c (b -> r) -> c r)
    -> (forall r. r -> c r) -> Constr -> c MatchGroupTc
    $cgunfold :: forall (c :: * -> *).
    (forall b r. Data b => c (b -> r) -> c r)
    -> (forall r. r -> c r) -> Constr -> c MatchGroupTc
    gfoldl :: forall (c :: * -> *).
    (forall d b. Data d => c (d -> b) -> d -> c b)
    -> (forall g. g -> c g) -> MatchGroupTc -> c MatchGroupTc
    $cgfoldl :: forall (c :: * -> *).
    (forall d b. Data d => c (d -> b) -> d -> c b)
    -> (forall g. g -> c g) -> MatchGroupTc -> c MatchGroupTc
    Data

    type instance XMG         GhcPs b = NoExtField
    type instance XMG         GhcRn b = NoExtField
    type instance XMG         GhcTc b = MatchGroupTc

    type instance XXMatchGroup (GhcPass _) b = NoExtCon

    -- | Located Match
    type LMatch id body = Located (Match id body)
    -- ^ May have 'GHC.Parser.Annotation.AnnKeywordId' : 'GHC.Parser.Annotation.AnnSemi' when in a
    --   list

    -- For details on above see note [Api annotations] in GHC.Parser.Annotation
    data Match p body
      = Match {
            forall p body. Match p body -> XCMatch p body
    m_ext :: XCMatch p body,
            forall p body. Match p body -> HsMatchContext (NoGhcTc p)
    m_ctxt :: HsMatchContext (NoGhcTc p),
              -- See note [m_ctxt in Match]
            forall p body. Match p body -> [LPat p]
    m_pats :: [LPat p], -- The patterns
            forall p body. Match p body -> GRHSs p body
    m_grhss :: (GRHSs p body)
      }
      | XMatch !(XXMatch p body)

    type instance XCMatch (GhcPass _) b = NoExtField
    type instance XXMatch (GhcPass _) b = NoExtCon

    instance (OutputableBndrId pr, Outputable body)
                => Outputable (Match (GhcPass pr) body) where
      ppr :: Match (GhcPass pr) body -> SDoc
    ppr = Match (GhcPass pr) body -> SDoc
    forall (pr :: Pass) body.
    (OutputableBndrId pr, Outputable body) =>
    Match (GhcPass pr) body -> SDoc
    pprMatch

    {-
    Note [m_ctxt in Match]
    ~~~~~~~~~~~~~~~~~~~~~~

    A Match can occur in a number of contexts, such as a FunBind, HsCase, HsLam and
    so on.

    In order to simplify tooling processing and pretty print output, the provenance
    is captured in an HsMatchContext.

    This is particularly important for the API Annotations for a multi-equation
    FunBind.

    The parser initially creates a FunBind with a single Match in it for
    every function definition it sees.

    These are then grouped together by getMonoBind into a single FunBind,
    where all the Matches are combined.

    In the process, all the original FunBind fun_id's bar one are
    discarded, including the locations.

    This causes a problem for source to source conversions via API
    Annotations, so the original fun_ids and infix flags are preserved in
    the Match, when it originates from a FunBind.

    Example infix function definition requiring individual API Annotations

        (&&&  ) [] [] =  []
        xs    &&&   [] =  xs
        (  &&&  ) [] ys =  ys

    -}

    isInfixMatch :: Match id body -> Bool
    isInfixMatch :: forall id body. Match id body -> Bool
    isInfixMatch Match id body
    match = case Match id body -> HsMatchContext (NoGhcTc id)
    forall p body. Match p body -> HsMatchContext (NoGhcTc p)
    m_ctxt Match id body
    match of
      FunRhs {mc_fixity :: forall p. HsMatchContext p -> LexicalFixity
    mc_fixity = LexicalFixity
    Infix} -> Bool
    True
      HsMatchContext (NoGhcTc id)
    _                          -> Bool
    False

    isEmptyMatchGroup :: MatchGroup id body -> Bool
    isEmptyMatchGroup :: forall id body. MatchGroup id body -> Bool
    isEmptyMatchGroup (MG { mg_alts :: forall p body. MatchGroup p body -> Located [LMatch p body]
    mg_alts = Located [LMatch id body]
    ms }) = [LMatch id body] -> Bool
    forall (t :: * -> *) a. Foldable t => t a -> Bool
    null ([LMatch id body] -> Bool) -> [LMatch id body] -> Bool
    forall a b. (a -> b) -> a -> b
    $ Located [LMatch id body] -> [LMatch id body]
    forall l e. GenLocated l e -> e
    unLoc Located [LMatch id body]
    ms
    isEmptyMatchGroup (XMatchGroup {})      = Bool
    False

    -- | Is there only one RHS in this list of matches?
    isSingletonMatchGroup :: [LMatch id body] -> Bool
    isSingletonMatchGroup :: forall id body. [LMatch id body] -> Bool
    isSingletonMatchGroup [LMatch id body]
    matches
      | [L SrcSpan
    _ Match id body
    match] <- [LMatch id body]
    matches
      , Match { m_grhss :: forall p body. Match p body -> GRHSs p body
    m_grhss = GRHSs { grhssGRHSs :: forall p body. GRHSs p body -> [LGRHS p body]
    grhssGRHSs = [LGRHS id body
    _] } } <- Match id body
    match
      = Bool
    True
      | Bool
    otherwise
      = Bool
    False

    matchGroupArity :: MatchGroup (GhcPass id) body -> Arity
    -- Precondition: MatchGroup is non-empty
    -- This is called before type checking, when mg_arg_tys is not set
    matchGroupArity :: forall (id :: Pass) body. MatchGroup (GhcPass id) body -> Int
    matchGroupArity (MG { mg_alts :: forall p body. MatchGroup p body -> Located [LMatch p body]
    mg_alts = Located [LMatch (GhcPass id) body]
    alts })
      | L SrcSpan
    _ (LMatch (GhcPass id) body
    alt1:[LMatch (GhcPass id) body]
    _) <- Located [LMatch (GhcPass id) body]
    alts = [Located (Pat (GhcPass id))] -> Int
    forall (t :: * -> *) a. Foldable t => t a -> Int
    length (LMatch (GhcPass id) body -> [LPat (GhcPass id)]
    forall (id :: Pass) body.
    LMatch (GhcPass id) body -> [LPat (GhcPass id)]
    hsLMatchPats LMatch (GhcPass id) body
    alt1)
      | Bool
    otherwise        = String -> Int
    forall a. String -> a
    panic String
    "matchGroupArity"

    hsLMatchPats :: LMatch (GhcPass id) body -> [LPat (GhcPass id)]
    hsLMatchPats :: forall (id :: Pass) body.
    LMatch (GhcPass id) body -> [LPat (GhcPass id)]
    hsLMatchPats (L SrcSpan
    _ (Match { m_pats :: forall p body. Match p body -> [LPat p]
    m_pats = [LPat (GhcPass id)]
    pats })) = [LPat (GhcPass id)]
    pats

    -- | Guarded Right-Hand Sides
    --
    -- GRHSs are used both for pattern bindings and for Matches
    --
    --  - 'GHC.Parser.Annotation.AnnKeywordId' : 'GHC.Parser.Annotation.AnnVbar',
    --        'GHC.Parser.Annotation.AnnEqual','GHC.Parser.Annotation.AnnWhere',
    --        'GHC.Parser.Annotation.AnnOpen','GHC.Parser.Annotation.AnnClose'
    --        'GHC.Parser.Annotation.AnnRarrow','GHC.Parser.Annotation.AnnSemi'

    -- For details on above see note [Api annotations] in GHC.Parser.Annotation
    data GRHSs p body
      = GRHSs {
          forall p body. GRHSs p body -> XCGRHSs p body
    grhssExt :: XCGRHSs p body,
          forall p body. GRHSs p body -> [LGRHS p body]
    grhssGRHSs :: [LGRHS p body],      -- ^ Guarded RHSs
          forall p body. GRHSs p body -> LHsLocalBinds p
    grhssLocalBinds :: LHsLocalBinds p -- ^ The where clause
        }
      | XGRHSs !(XXGRHSs p body)

    type instance XCGRHSs (GhcPass _) b = NoExtField
    type instance XXGRHSs (GhcPass _) b = NoExtCon

    -- | Located Guarded Right-Hand Side
    type LGRHS id body = Located (GRHS id body)

    -- | Guarded Right Hand Side.
    data GRHS p body = GRHS (XCGRHS p body)
                            [GuardLStmt p] -- Guards
                            body           -- Right hand side
                      | XGRHS !(XXGRHS p body)

    type instance XCGRHS (GhcPass _) b = NoExtField
    type instance XXGRHS (GhcPass _) b = NoExtCon

    -- We know the list must have at least one @Match@ in it.

    pprMatches :: (OutputableBndrId idR, Outputable body)
               => MatchGroup (GhcPass idR) body -> SDoc
    pprMatches :: forall (idR :: Pass) body.
    (OutputableBndrId idR, Outputable body) =>
    MatchGroup (GhcPass idR) body -> SDoc
    pprMatches MG { mg_alts :: forall p body. MatchGroup p body -> Located [LMatch p body]
    mg_alts = Located [LMatch (GhcPass idR) body]
    matches }
        = [SDoc] -> SDoc
    vcat ((Match (GhcPass idR) body -> SDoc)
    -> [Match (GhcPass idR) body] -> [SDoc]
    forall a b. (a -> b) -> [a] -> [b]
    map Match (GhcPass idR) body -> SDoc
    forall (pr :: Pass) body.
    (OutputableBndrId pr, Outputable body) =>
    Match (GhcPass pr) body -> SDoc
    pprMatch ((LMatch (GhcPass idR) body -> Match (GhcPass idR) body)
    -> [LMatch (GhcPass idR) body] -> [Match (GhcPass idR) body]
    forall a b. (a -> b) -> [a] -> [b]
    map LMatch (GhcPass idR) body -> Match (GhcPass idR) body
    forall l e. GenLocated l e -> e
    unLoc (Located [LMatch (GhcPass idR) body] -> [LMatch (GhcPass idR) body]
    forall l e. GenLocated l e -> e
    unLoc Located [LMatch (GhcPass idR) body]
    matches)))
          -- Don't print the type; it's only a place-holder before typechecking

    -- Exported to GHC.Hs.Binds, which can't see the defn of HsMatchContext
    pprFunBind :: (OutputableBndrId idR, Outputable body)
               => MatchGroup (GhcPass idR) body -> SDoc
    pprFunBind :: forall (idR :: Pass) body.
    (OutputableBndrId idR, Outputable body) =>
    MatchGroup (GhcPass idR) body -> SDoc
    pprFunBind MatchGroup (GhcPass idR) body
    matches = MatchGroup (GhcPass idR) body -> SDoc
    forall (idR :: Pass) body.
    (OutputableBndrId idR, Outputable body) =>
    MatchGroup (GhcPass idR) body -> SDoc
    pprMatches MatchGroup (GhcPass idR) body
    matches

    -- Exported to GHC.Hs.Binds, which can't see the defn of HsMatchContext
    pprPatBind :: forall bndr p body. (OutputableBndrId bndr,
                                       OutputableBndrId p,
                                       Outputable body)
               => LPat (GhcPass bndr) -> GRHSs (GhcPass p) body -> SDoc
    pprPatBind :: forall (bndr :: Pass) (p :: Pass) body.
    (OutputableBndrId bndr, OutputableBndrId p, Outputable body) =>
    LPat (GhcPass bndr) -> GRHSs (GhcPass p) body -> SDoc
    pprPatBind LPat (GhcPass bndr)
    pat (GRHSs (GhcPass p) body
    grhss)
     = [SDoc] -> SDoc
    sep [Located (Pat (GhcPass bndr)) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr Located (Pat (GhcPass bndr))
    LPat (GhcPass bndr)
    pat,
           Int -> SDoc -> SDoc
    nest Int
    2 (HsMatchContext (GhcPass p) -> GRHSs (GhcPass p) body -> SDoc
    forall (idR :: Pass) body passL.
    (OutputableBndrId idR, Outputable body) =>
    HsMatchContext passL -> GRHSs (GhcPass idR) body -> SDoc
    pprGRHSs (HsMatchContext (GhcPass p)
    forall p. HsMatchContext p
    PatBindRhs :: HsMatchContext (GhcPass p)) GRHSs (GhcPass p) body
    grhss)]

    pprMatch :: (OutputableBndrId idR, Outputable body)
             => Match (GhcPass idR) body -> SDoc
    pprMatch :: forall (pr :: Pass) body.
    (OutputableBndrId pr, Outputable body) =>
    Match (GhcPass pr) body -> SDoc
    pprMatch (Match { m_pats :: forall p body. Match p body -> [LPat p]
    m_pats = [LPat (GhcPass idR)]
    pats, m_ctxt :: forall p body. Match p body -> HsMatchContext (NoGhcTc p)
    m_ctxt = HsMatchContext (NoGhcTc (GhcPass idR))
    ctxt, m_grhss :: forall p body. Match p body -> GRHSs p body
    m_grhss = GRHSs (GhcPass idR) body
    grhss })
      = [SDoc] -> SDoc
    sep [ [SDoc] -> SDoc
    sep (SDoc
    herald SDoc -> [SDoc] -> [SDoc]
    forall a. a -> [a] -> [a]
    : (Located (Pat (GhcPass idR)) -> SDoc)
    -> [Located (Pat (GhcPass idR))] -> [SDoc]
    forall a b. (a -> b) -> [a] -> [b]
    map (Int -> SDoc -> SDoc
    nest Int
    2 (SDoc -> SDoc)
    -> (Located (Pat (GhcPass idR)) -> SDoc)
    -> Located (Pat (GhcPass idR))
    -> SDoc
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    . PprPrec -> LPat (GhcPass idR) -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    PprPrec -> LPat (GhcPass p) -> SDoc
    pprParendLPat PprPrec
    appPrec) [Located (Pat (GhcPass idR))]
    other_pats)
            , Int -> SDoc -> SDoc
    nest Int
    2 (HsMatchContext (GhcPass (NoGhcTcPass idR))
    -> GRHSs (GhcPass idR) body -> SDoc
    forall (idR :: Pass) body passL.
    (OutputableBndrId idR, Outputable body) =>
    HsMatchContext passL -> GRHSs (GhcPass idR) body -> SDoc
    pprGRHSs HsMatchContext (GhcPass (NoGhcTcPass idR))
    HsMatchContext (NoGhcTc (GhcPass idR))
    ctxt GRHSs (GhcPass idR) body
    grhss) ]
      where
        (SDoc
    herald, [Located (Pat (GhcPass idR))]
    other_pats)
            = case HsMatchContext (NoGhcTc (GhcPass idR))
    ctxt of
                FunRhs {mc_fun :: forall p. HsMatchContext p -> LIdP p
    mc_fun=L SrcSpan
    _ IdP (NoGhcTc (GhcPass idR))
    fun, mc_fixity :: forall p. HsMatchContext p -> LexicalFixity
    mc_fixity=LexicalFixity
    fixity, mc_strictness :: forall p. HsMatchContext p -> SrcStrictness
    mc_strictness=SrcStrictness
    strictness}
                    | SrcStrictness
    SrcStrict <- SrcStrictness
    strictness
                    -> ASSERT(null pats)     -- A strict variable binding
                       (Char -> SDoc
    char Char
    '!'SDoc -> SDoc -> SDoc
    <>IdGhcP (NoGhcTcPass idR) -> SDoc
    forall a. OutputableBndr a => a -> SDoc
    pprPrefixOcc IdGhcP (NoGhcTcPass idR)
    IdP (NoGhcTc (GhcPass idR))
    fun, [Located (Pat (GhcPass idR))]
    [LPat (GhcPass idR)]
    pats)

                    | LexicalFixity
    Prefix <- LexicalFixity
    fixity
                    -> (IdGhcP (NoGhcTcPass idR) -> SDoc
    forall a. OutputableBndr a => a -> SDoc
    pprPrefixOcc IdGhcP (NoGhcTcPass idR)
    IdP (NoGhcTc (GhcPass idR))
    fun, [Located (Pat (GhcPass idR))]
    [LPat (GhcPass idR)]
    pats) -- f x y z = e
                                                -- Not pprBndr; the AbsBinds will
                                                -- have printed the signature
                    | Bool
    otherwise
                    -> case [LPat (GhcPass idR)]
    pats of
                         (LPat (GhcPass idR)
    p1:LPat (GhcPass idR)
    p2:[LPat (GhcPass idR)]
    rest)
                            | [Located (Pat (GhcPass idR))] -> Bool
    forall (t :: * -> *) a. Foldable t => t a -> Bool
    null [Located (Pat (GhcPass idR))]
    [LPat (GhcPass idR)]
    rest -> (SDoc
    pp_infix, [])           -- x &&& y = e
                            | Bool
    otherwise -> (SDoc -> SDoc
    parens SDoc
    pp_infix, [Located (Pat (GhcPass idR))]
    [LPat (GhcPass idR)]
    rest)  -- (x &&& y) z = e
                            where
                              pp_infix :: SDoc
    pp_infix = PprPrec -> LPat (GhcPass idR) -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    PprPrec -> LPat (GhcPass p) -> SDoc
    pprParendLPat PprPrec
    opPrec LPat (GhcPass idR)
    p1
                                         SDoc -> SDoc -> SDoc
    <+> IdGhcP (NoGhcTcPass idR) -> SDoc
    forall a. OutputableBndr a => a -> SDoc
    pprInfixOcc IdGhcP (NoGhcTcPass idR)
    IdP (NoGhcTc (GhcPass idR))
    fun
                                         SDoc -> SDoc -> SDoc
    <+> PprPrec -> LPat (GhcPass idR) -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    PprPrec -> LPat (GhcPass p) -> SDoc
    pprParendLPat PprPrec
    opPrec LPat (GhcPass idR)
    p2
                         [LPat (GhcPass idR)]
    _ -> String -> SDoc -> (SDoc, [Located (Pat (GhcPass idR))])
    forall a. HasCallStack => String -> SDoc -> a
    pprPanic String
    "pprMatch" (HsMatchContext (GhcPass (NoGhcTcPass idR)) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr HsMatchContext (GhcPass (NoGhcTcPass idR))
    HsMatchContext (NoGhcTc (GhcPass idR))
    ctxt SDoc -> SDoc -> SDoc
    $$ [Located (Pat (GhcPass idR))] -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr [Located (Pat (GhcPass idR))]
    [LPat (GhcPass idR)]
    pats)

                HsMatchContext (NoGhcTc (GhcPass idR))
    LambdaExpr -> (Char -> SDoc
    char Char
    '\\', [Located (Pat (GhcPass idR))]
    [LPat (GhcPass idR)]
    pats)

                HsMatchContext (NoGhcTc (GhcPass idR))
    _ -> case [LPat (GhcPass idR)]
    pats of
                       []    -> (SDoc
    empty, [])
                       [LPat (GhcPass idR)
    pat] -> (Located (Pat (GhcPass idR)) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr Located (Pat (GhcPass idR))
    LPat (GhcPass idR)
    pat, [])  -- No parens around the single pat in a case
                       [LPat (GhcPass idR)]
    _     -> String -> SDoc -> (SDoc, [Located (Pat (GhcPass idR))])
    forall a. HasCallStack => String -> SDoc -> a
    pprPanic String
    "pprMatch" (HsMatchContext (GhcPass (NoGhcTcPass idR)) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr HsMatchContext (GhcPass (NoGhcTcPass idR))
    HsMatchContext (NoGhcTc (GhcPass idR))
    ctxt SDoc -> SDoc -> SDoc
    $$ [Located (Pat (GhcPass idR))] -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr [Located (Pat (GhcPass idR))]
    [LPat (GhcPass idR)]
    pats)

    pprGRHSs :: (OutputableBndrId idR, Outputable body)
             => HsMatchContext passL -> GRHSs (GhcPass idR) body -> SDoc
    pprGRHSs :: forall (idR :: Pass) body passL.
    (OutputableBndrId idR, Outputable body) =>
    HsMatchContext passL -> GRHSs (GhcPass idR) body -> SDoc
    pprGRHSs HsMatchContext passL
    ctxt (GRHSs XCGRHSs (GhcPass idR) body
    _ [LGRHS (GhcPass idR) body]
    grhss (L SrcSpan
    _ HsLocalBinds (GhcPass idR)
    binds))
      = [SDoc] -> SDoc
    vcat ((LGRHS (GhcPass idR) body -> SDoc)
    -> [LGRHS (GhcPass idR) body] -> [SDoc]
    forall a b. (a -> b) -> [a] -> [b]
    map (HsMatchContext passL -> GRHS (GhcPass idR) body -> SDoc
    forall (idR :: Pass) body passL.
    (OutputableBndrId idR, Outputable body) =>
    HsMatchContext passL -> GRHS (GhcPass idR) body -> SDoc
    pprGRHS HsMatchContext passL
    ctxt (GRHS (GhcPass idR) body -> SDoc)
    -> (LGRHS (GhcPass idR) body -> GRHS (GhcPass idR) body)
    -> LGRHS (GhcPass idR) body
    -> SDoc
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    . LGRHS (GhcPass idR) body -> GRHS (GhcPass idR) body
    forall l e. GenLocated l e -> e
    unLoc) [LGRHS (GhcPass idR) body]
    grhss)
      -- Print the "where" even if the contents of the binds is empty. Only
      -- EmptyLocalBinds means no "where" keyword
     SDoc -> SDoc -> SDoc
    $$ Bool -> SDoc -> SDoc
    ppUnless (HsLocalBinds (GhcPass idR) -> Bool
    forall a b. HsLocalBindsLR a b -> Bool
    eqEmptyLocalBinds HsLocalBinds (GhcPass idR)
    binds)
          (String -> SDoc
    text String
    "where" SDoc -> SDoc -> SDoc
    $$ Int -> SDoc -> SDoc
    nest Int
    4 (HsLocalBinds (GhcPass idR) -> SDoc
    forall (idL :: Pass) (idR :: Pass).
    (OutputableBndrId idL, OutputableBndrId idR) =>
    HsLocalBindsLR (GhcPass idL) (GhcPass idR) -> SDoc
    pprBinds HsLocalBinds (GhcPass idR)
    binds))

    pprGRHS :: (OutputableBndrId idR, Outputable body)
            => HsMatchContext passL -> GRHS (GhcPass idR) body -> SDoc
    pprGRHS :: forall (idR :: Pass) body passL.
    (OutputableBndrId idR, Outputable body) =>
    HsMatchContext passL -> GRHS (GhcPass idR) body -> SDoc
    pprGRHS HsMatchContext passL
    ctxt (GRHS XCGRHS (GhcPass idR) body
    _ [] body
    body)
     =  HsMatchContext passL -> body -> SDoc
    forall body passL.
    Outputable body =>
    HsMatchContext passL -> body -> SDoc
    pp_rhs HsMatchContext passL
    ctxt body
    body

    pprGRHS HsMatchContext passL
    ctxt (GRHS XCGRHS (GhcPass idR) body
    _ [GuardLStmt (GhcPass idR)]
    guards body
    body)
     = [SDoc] -> SDoc
    sep [SDoc
    vbar SDoc -> SDoc -> SDoc
    <+> [GuardLStmt (GhcPass idR)] -> SDoc
    forall a. Outputable a => [a] -> SDoc
    interpp'SP [GuardLStmt (GhcPass idR)]
    guards, HsMatchContext passL -> body -> SDoc
    forall body passL.
    Outputable body =>
    HsMatchContext passL -> body -> SDoc
    pp_rhs HsMatchContext passL
    ctxt body
    body]

    pp_rhs :: Outputable body => HsMatchContext passL -> body -> SDoc
    pp_rhs :: forall body passL.
    Outputable body =>
    HsMatchContext passL -> body -> SDoc
    pp_rhs HsMatchContext passL
    ctxt body
    rhs = HsMatchContext passL -> SDoc
    forall p. HsMatchContext p -> SDoc
    matchSeparator HsMatchContext passL
    ctxt SDoc -> SDoc -> SDoc
    <+> SDoc -> SDoc
    pprDeeper (body -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr body
    rhs)

    {-
    ************************************************************************
    *                                                                      *
    \subsection{Do stmts and list comprehensions}
    *                                                                      *
    ************************************************************************
    -}

    -- | Located @do@ block Statement
    type LStmt id body = Located (StmtLR id id body)

    -- | Located Statement with separate Left and Right id's
    type LStmtLR idL idR body = Located (StmtLR idL idR body)

    -- | @do@ block Statement
    type Stmt id body = StmtLR id id body

    -- | Command Located Statement
    type CmdLStmt   id = LStmt id (LHsCmd  id)

    -- | Command Statement
    type CmdStmt    id = Stmt  id (LHsCmd  id)

    -- | Expression Located Statement
    type ExprLStmt  id = LStmt id (LHsExpr id)

    -- | Expression Statement
    type ExprStmt   id = Stmt  id (LHsExpr id)

    -- | Guard Located Statement
    type GuardLStmt id = LStmt id (LHsExpr id)

    -- | Guard Statement
    type GuardStmt  id = Stmt  id (LHsExpr id)

    -- | Ghci Located Statement
    type GhciLStmt  id = LStmt id (LHsExpr id)

    -- | Ghci Statement
    type GhciStmt   id = Stmt  id (LHsExpr id)

    -- The SyntaxExprs in here are used *only* for do-notation and monad
    -- comprehensions, which have rebindable syntax. Otherwise they are unused.
    -- | API Annotations when in qualifier lists or guards
    --  - 'GHC.Parser.Annotation.AnnKeywordId' : 'GHC.Parser.Annotation.AnnVbar',
    --         'GHC.Parser.Annotation.AnnComma','GHC.Parser.Annotation.AnnThen',
    --         'GHC.Parser.Annotation.AnnBy','GHC.Parser.Annotation.AnnBy',
    --         'GHC.Parser.Annotation.AnnGroup','GHC.Parser.Annotation.AnnUsing'

    -- For details on above see note [Api annotations] in GHC.Parser.Annotation
    data StmtLR idL idR body -- body should always be (LHs**** idR)
      = LastStmt  -- Always the last Stmt in ListComp, MonadComp,
                  -- and (after the renamer, see GHC.Rename.Expr.checkLastStmt) DoExpr, MDoExpr
                  -- Not used for GhciStmtCtxt, PatGuard, which scope over other stuff
              (XLastStmt idL idR body)
              body
              (Maybe Bool)  -- Whether return was stripped
                -- Just True <=> return with a dollar was stripped by ApplicativeDo
                -- Just False <=> return without a dollar was stripped by ApplicativeDo
                -- Nothing <=> Nothing was stripped
              (SyntaxExpr idR)   -- The return operator
                -- The return operator is used only for MonadComp
                -- For ListComp we use the baked-in 'return'
                -- For DoExpr, MDoExpr, we don't apply a 'return' at all
                -- See Note [Monad Comprehensions]
                -- - 'GHC.Parser.Annotation.AnnKeywordId' : 'GHC.Parser.Annotation.AnnLarrow'

      -- For details on above see note [Api annotations] in GHC.Parser.Annotation
      | BindStmt (XBindStmt idL idR body)
                 -- ^ Post renaming has optional fail and bind / (>>=) operator.
                 -- Post typechecking, also has multiplicity of the argument
                 -- and the result type of the function passed to bind;
                 -- that is, (P, S) in (>>=) :: Q -> (R # P -> S) -> T
                 -- See Note [The type of bind in Stmts]
                 (LPat idL)
                 body

      -- | 'ApplicativeStmt' represents an applicative expression built with
      -- '<$>' and '<*>'.  It is generated by the renamer, and is desugared into the
      -- appropriate applicative expression by the desugarer, but it is intended
      -- to be invisible in error messages.
      --
      -- For full details, see Note [ApplicativeDo] in "GHC.Rename.Expr"
      --
      | ApplicativeStmt
                 (XApplicativeStmt idL idR body) -- Post typecheck, Type of the body
                 [ ( SyntaxExpr idR
                   , ApplicativeArg idL) ]
                          -- [(<$>, e1), (<*>, e2), ..., (<*>, en)]
                 (Maybe (SyntaxExpr idR))  -- 'join', if necessary

      | BodyStmt (XBodyStmt idL idR body) -- Post typecheck, element type
                                          -- of the RHS (used for arrows)
                 body              -- See Note [BodyStmt]
                 (SyntaxExpr idR)  -- The (>>) operator
                 (SyntaxExpr idR)  -- The `guard` operator; used only in MonadComp
                                   -- See notes [Monad Comprehensions]

      -- | - 'GHC.Parser.Annotation.AnnKeywordId' : 'GHC.Parser.Annotation.AnnLet'
      --          'GHC.Parser.Annotation.AnnOpen' @'{'@,'GHC.Parser.Annotation.AnnClose' @'}'@,

      -- For details on above see note [Api annotations] in GHC.Parser.Annotation
      | LetStmt  (XLetStmt idL idR body) (LHsLocalBindsLR idL idR)

      -- ParStmts only occur in a list/monad comprehension
      | ParStmt  (XParStmt idL idR body)    -- Post typecheck,
                                            -- S in (>>=) :: Q -> (R -> S) -> T
                 [ParStmtBlock idL idR]
                 (HsExpr idR)               -- Polymorphic `mzip` for monad comprehensions
                 (SyntaxExpr idR)           -- The `>>=` operator
                                            -- See notes [Monad Comprehensions]
                -- After renaming, the ids are the binders
                -- bound by the stmts and used after themp

      | TransStmt {
          forall idL idR body. StmtLR idL idR body -> XTransStmt idL idR body
    trS_ext   :: XTransStmt idL idR body, -- Post typecheck,
                                                -- R in (>>=) :: Q -> (R -> S) -> T
          forall idL idR body. StmtLR idL idR body -> TransForm
    trS_form  :: TransForm,
          forall idL idR body. StmtLR idL idR body -> [ExprLStmt idL]
    trS_stmts :: [ExprLStmt idL],   -- Stmts to the *left* of the 'group'
                                          -- which generates the tuples to be grouped

          forall idL idR body. StmtLR idL idR body -> [(IdP idR, IdP idR)]
    trS_bndrs :: [(IdP idR, IdP idR)], -- See Note [TransStmt binder map]

          forall idL idR body. StmtLR idL idR body -> LHsExpr idR
    trS_using :: LHsExpr idR,
          forall idL idR body. StmtLR idL idR body -> Maybe (LHsExpr idR)
    trS_by :: Maybe (LHsExpr idR),  -- "by e" (optional)
            -- Invariant: if trS_form = GroupBy, then grp_by = Just e

          forall idL idR body. StmtLR idL idR body -> SyntaxExpr idR
    trS_ret :: SyntaxExpr idR,      -- The monomorphic 'return' function for
                                          -- the inner monad comprehensions
          forall idL idR body. StmtLR idL idR body -> SyntaxExpr idR
    trS_bind :: SyntaxExpr idR,     -- The '(>>=)' operator
          forall idL idR body. StmtLR idL idR body -> HsExpr idR
    trS_fmap :: HsExpr idR          -- The polymorphic 'fmap' function for desugaring
                                          -- Only for 'group' forms
                                          -- Just a simple HsExpr, because it's
                                          -- too polymorphic for tcSyntaxOp
        }                                 -- See Note [Monad Comprehensions]

      -- Recursive statement (see Note [How RecStmt works] below)
      -- | - 'GHC.Parser.Annotation.AnnKeywordId' : 'GHC.Parser.Annotation.AnnRec'

      -- For details on above see note [Api annotations] in GHC.Parser.Annotation
      | RecStmt
         { forall idL idR body. StmtLR idL idR body -> XRecStmt idL idR body
    recS_ext :: XRecStmt idL idR body
         , forall idL idR body. StmtLR idL idR body -> [LStmtLR idL idR body]
    recS_stmts :: [LStmtLR idL idR body]

            -- The next two fields are only valid after renaming
         , forall idL idR body. StmtLR idL idR body -> [IdP idR]
    recS_later_ids :: [IdP idR]
                             -- The ids are a subset of the variables bound by the
                             -- stmts that are used in stmts that follow the RecStmt

         , forall idL idR body. StmtLR idL idR body -> [IdP idR]
    recS_rec_ids :: [IdP idR]
                             -- Ditto, but these variables are the "recursive" ones,
                             -- that are used before they are bound in the stmts of
                             -- the RecStmt.
            -- An Id can be in both groups
            -- Both sets of Ids are (now) treated monomorphically
            -- See Note [How RecStmt works] for why they are separate

            -- Rebindable syntax
         , forall idL idR body. StmtLR idL idR body -> SyntaxExpr idR
    recS_bind_fn :: SyntaxExpr idR -- The bind function
         , forall idL idR body. StmtLR idL idR body -> SyntaxExpr idR
    recS_ret_fn  :: SyntaxExpr idR -- The return function
         , forall idL idR body. StmtLR idL idR body -> SyntaxExpr idR
    recS_mfix_fn :: SyntaxExpr idR -- The mfix function
          }
      | XStmtLR !(XXStmtLR idL idR body)

    -- Extra fields available post typechecking for RecStmt.
    data RecStmtTc =
      RecStmtTc
         { RecStmtTc -> Type
    recS_bind_ty :: Type       -- S in (>>=) :: Q -> (R -> S) -> T
         , RecStmtTc -> [HsExpr GhcTc]
    recS_later_rets :: [PostTcExpr] -- (only used in the arrow version)
         , RecStmtTc -> [HsExpr GhcTc]
    recS_rec_rets :: [PostTcExpr] -- These expressions correspond 1-to-1
                                      -- with recS_later_ids and recS_rec_ids,
                                      -- and are the expressions that should be
                                      -- returned by the recursion.
                                      -- They may not quite be the Ids themselves,
                                      -- because the Id may be *polymorphic*, but
                                      -- the returned thing has to be *monomorphic*,
                                      -- so they may be type applications

          , RecStmtTc -> Type
    recS_ret_ty :: Type        -- The type of
                                       -- do { stmts; return (a,b,c) }
                                       -- With rebindable syntax the type might not
                                       -- be quite as simple as (m (tya, tyb, tyc)).
          }

    type instance XLastStmt        (GhcPass _) (GhcPass _) b = NoExtField

    type instance XBindStmt        (GhcPass _) GhcPs b = NoExtField
    type instance XBindStmt        (GhcPass _) GhcRn b = XBindStmtRn
    type instance XBindStmt        (GhcPass _) GhcTc b = XBindStmtTc

    data XBindStmtRn = XBindStmtRn
      { XBindStmtRn -> SyntaxExpr GhcRn
    xbsrn_bindOp :: SyntaxExpr GhcRn
      , XBindStmtRn -> FailOperator GhcRn
    xbsrn_failOp :: FailOperator GhcRn
      }

    data XBindStmtTc = XBindStmtTc
      { XBindStmtTc -> SyntaxExpr GhcTc
    xbstc_bindOp :: SyntaxExpr GhcTc
      , XBindStmtTc -> Type
    xbstc_boundResultType :: Type -- If (>>=) :: Q -> (R -> S) -> T, this is S
      , XBindStmtTc -> Type
    xbstc_boundResultMult :: Mult -- If (>>=) :: Q -> (R -> S) -> T, this is S
      , XBindStmtTc -> FailOperator GhcTc
    xbstc_failOp :: FailOperator GhcTc
      }

    type instance XApplicativeStmt (GhcPass _) GhcPs b = NoExtField
    type instance XApplicativeStmt (GhcPass _) GhcRn b = NoExtField
    type instance XApplicativeStmt (GhcPass _) GhcTc b = Type

    type instance XBodyStmt        (GhcPass _) GhcPs b = NoExtField
    type instance XBodyStmt        (GhcPass _) GhcRn b = NoExtField
    type instance XBodyStmt        (GhcPass _) GhcTc b = Type

    type instance XLetStmt         (GhcPass _) (GhcPass _) b = NoExtField

    type instance XParStmt         (GhcPass _) GhcPs b = NoExtField
    type instance XParStmt         (GhcPass _) GhcRn b = NoExtField
    type instance XParStmt         (GhcPass _) GhcTc b = Type

    type instance XTransStmt       (GhcPass _) GhcPs b = NoExtField
    type instance XTransStmt       (GhcPass _) GhcRn b = NoExtField
    type instance XTransStmt       (GhcPass _) GhcTc b = Type

    type instance XRecStmt         (GhcPass _) GhcPs b = NoExtField
    type instance XRecStmt         (GhcPass _) GhcRn b = NoExtField
    type instance XRecStmt         (GhcPass _) GhcTc b = RecStmtTc

    type instance XXStmtLR         (GhcPass _) (GhcPass _) b = NoExtCon

    data TransForm   -- The 'f' below is the 'using' function, 'e' is the by function
      = ThenForm     -- then f               or    then f by e             (depending on trS_by)
      | GroupForm    -- then group using f   or    then group by e using f (depending on trS_by)
      deriving Typeable TransForm
    Typeable TransForm
    -> (forall (c :: * -> *).
        (forall d b. Data d => c (d -> b) -> d -> c b)
        -> (forall g. g -> c g) -> TransForm -> c TransForm)
    -> (forall (c :: * -> *).
        (forall b r. Data b => c (b -> r) -> c r)
        -> (forall r. r -> c r) -> Constr -> c TransForm)
    -> (TransForm -> Constr)
    -> (TransForm -> DataType)
    -> (forall (t :: * -> *) (c :: * -> *).
        Typeable t =>
        (forall d. Data d => c (t d)) -> Maybe (c TransForm))
    -> (forall (t :: * -> * -> *) (c :: * -> *).
        Typeable t =>
        (forall d e. (Data d, Data e) => c (t d e)) -> Maybe (c TransForm))
    -> ((forall b. Data b => b -> b) -> TransForm -> TransForm)
    -> (forall r r'.
        (r -> r' -> r)
        -> r -> (forall d. Data d => d -> r') -> TransForm -> r)
    -> (forall r r'.
        (r' -> r -> r)
        -> r -> (forall d. Data d => d -> r') -> TransForm -> r)
    -> (forall u. (forall d. Data d => d -> u) -> TransForm -> [u])
    -> (forall u.
        Int -> (forall d. Data d => d -> u) -> TransForm -> u)
    -> (forall (m :: * -> *).
        Monad m =>
        (forall d. Data d => d -> m d) -> TransForm -> m TransForm)
    -> (forall (m :: * -> *).
        MonadPlus m =>
        (forall d. Data d => d -> m d) -> TransForm -> m TransForm)
    -> (forall (m :: * -> *).
        MonadPlus m =>
        (forall d. Data d => d -> m d) -> TransForm -> m TransForm)
    -> Data TransForm
    TransForm -> DataType
    TransForm -> Constr
    (forall b. Data b => b -> b) -> TransForm -> TransForm
    forall a.
    Typeable a
    -> (forall (c :: * -> *).
        (forall d b. Data d => c (d -> b) -> d -> c b)
        -> (forall g. g -> c g) -> a -> c a)
    -> (forall (c :: * -> *).
        (forall b r. Data b => c (b -> r) -> c r)
        -> (forall r. r -> c r) -> Constr -> c a)
    -> (a -> Constr)
    -> (a -> DataType)
    -> (forall (t :: * -> *) (c :: * -> *).
        Typeable t =>
        (forall d. Data d => c (t d)) -> Maybe (c a))
    -> (forall (t :: * -> * -> *) (c :: * -> *).
        Typeable t =>
        (forall d e. (Data d, Data e) => c (t d e)) -> Maybe (c a))
    -> ((forall b. Data b => b -> b) -> a -> a)
    -> (forall r r'.
        (r -> r' -> r) -> r -> (forall d. Data d => d -> r') -> a -> r)
    -> (forall r r'.
        (r' -> r -> r) -> r -> (forall d. Data d => d -> r') -> a -> r)
    -> (forall u. (forall d. Data d => d -> u) -> a -> [u])
    -> (forall u. Int -> (forall d. Data d => d -> u) -> a -> u)
    -> (forall (m :: * -> *).
        Monad m =>
        (forall d. Data d => d -> m d) -> a -> m a)
    -> (forall (m :: * -> *).
        MonadPlus m =>
        (forall d. Data d => d -> m d) -> a -> m a)
    -> (forall (m :: * -> *).
        MonadPlus m =>
        (forall d. Data d => d -> m d) -> a -> m a)
    -> Data a
    forall u. Int -> (forall d. Data d => d -> u) -> TransForm -> u
    forall u. (forall d. Data d => d -> u) -> TransForm -> [u]
    forall r r'.
    (r -> r' -> r)
    -> r -> (forall d. Data d => d -> r') -> TransForm -> r
    forall r r'.
    (r' -> r -> r)
    -> r -> (forall d. Data d => d -> r') -> TransForm -> r
    forall (m :: * -> *).
    Monad m =>
    (forall d. Data d => d -> m d) -> TransForm -> m TransForm
    forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d) -> TransForm -> m TransForm
    forall (c :: * -> *).
    (forall b r. Data b => c (b -> r) -> c r)
    -> (forall r. r -> c r) -> Constr -> c TransForm
    forall (c :: * -> *).
    (forall d b. Data d => c (d -> b) -> d -> c b)
    -> (forall g. g -> c g) -> TransForm -> c TransForm
    forall (t :: * -> *) (c :: * -> *).
    Typeable t =>
    (forall d. Data d => c (t d)) -> Maybe (c TransForm)
    forall (t :: * -> * -> *) (c :: * -> *).
    Typeable t =>
    (forall d e. (Data d, Data e) => c (t d e)) -> Maybe (c TransForm)
    gmapMo :: forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d) -> TransForm -> m TransForm
    $cgmapMo :: forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d) -> TransForm -> m TransForm
    gmapMp :: forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d) -> TransForm -> m TransForm
    $cgmapMp :: forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d) -> TransForm -> m TransForm
    gmapM :: forall (m :: * -> *).
    Monad m =>
    (forall d. Data d => d -> m d) -> TransForm -> m TransForm
    $cgmapM :: forall (m :: * -> *).
    Monad m =>
    (forall d. Data d => d -> m d) -> TransForm -> m TransForm
    gmapQi :: forall u. Int -> (forall d. Data d => d -> u) -> TransForm -> u
    $cgmapQi :: forall u. Int -> (forall d. Data d => d -> u) -> TransForm -> u
    gmapQ :: forall u. (forall d. Data d => d -> u) -> TransForm -> [u]
    $cgmapQ :: forall u. (forall d. Data d => d -> u) -> TransForm -> [u]
    gmapQr :: forall r r'.
    (r' -> r -> r)
    -> r -> (forall d. Data d => d -> r') -> TransForm -> r
    $cgmapQr :: forall r r'.
    (r' -> r -> r)
    -> r -> (forall d. Data d => d -> r') -> TransForm -> r
    gmapQl :: forall r r'.
    (r -> r' -> r)
    -> r -> (forall d. Data d => d -> r') -> TransForm -> r
    $cgmapQl :: forall r r'.
    (r -> r' -> r)
    -> r -> (forall d. Data d => d -> r') -> TransForm -> r
    gmapT :: (forall b. Data b => b -> b) -> TransForm -> TransForm
    $cgmapT :: (forall b. Data b => b -> b) -> TransForm -> TransForm
    dataCast2 :: forall (t :: * -> * -> *) (c :: * -> *).
    Typeable t =>
    (forall d e. (Data d, Data e) => c (t d e)) -> Maybe (c TransForm)
    $cdataCast2 :: forall (t :: * -> * -> *) (c :: * -> *).
    Typeable t =>
    (forall d e. (Data d, Data e) => c (t d e)) -> Maybe (c TransForm)
    dataCast1 :: forall (t :: * -> *) (c :: * -> *).
    Typeable t =>
    (forall d. Data d => c (t d)) -> Maybe (c TransForm)
    $cdataCast1 :: forall (t :: * -> *) (c :: * -> *).
    Typeable t =>
    (forall d. Data d => c (t d)) -> Maybe (c TransForm)
    dataTypeOf :: TransForm -> DataType
    $cdataTypeOf :: TransForm -> DataType
    toConstr :: TransForm -> Constr
    $ctoConstr :: TransForm -> Constr
    gunfold :: forall (c :: * -> *).
    (forall b r. Data b => c (b -> r) -> c r)
    -> (forall r. r -> c r) -> Constr -> c TransForm
    $cgunfold :: forall (c :: * -> *).
    (forall b r. Data b => c (b -> r) -> c r)
    -> (forall r. r -> c r) -> Constr -> c TransForm
    gfoldl :: forall (c :: * -> *).
    (forall d b. Data d => c (d -> b) -> d -> c b)
    -> (forall g. g -> c g) -> TransForm -> c TransForm
    $cgfoldl :: forall (c :: * -> *).
    (forall d b. Data d => c (d -> b) -> d -> c b)
    -> (forall g. g -> c g) -> TransForm -> c TransForm
    Data

    -- | Parenthesised Statement Block
    data ParStmtBlock idL idR
      = ParStmtBlock
            (XParStmtBlock idL idR)
            [ExprLStmt idL]
            [IdP idR]          -- The variables to be returned
            (SyntaxExpr idR)   -- The return operator
      | XParStmtBlock !(XXParStmtBlock idL idR)

    type instance XParStmtBlock  (GhcPass pL) (GhcPass pR) = NoExtField
    type instance XXParStmtBlock (GhcPass pL) (GhcPass pR) = NoExtCon

    -- | The fail operator
    --
    -- This is used for `.. <-` "bind statments" in do notation, including
    -- non-monadic "binds" in applicative.
    --
    -- The fail operator is 'Just expr' if it potentially fail monadically. if the
    -- pattern match cannot fail, or shouldn't fail monadically (regular incomplete
    -- pattern exception), it is 'Nothing'.
    --
    -- See Note [Monad fail : Rebindable syntax, overloaded strings] for the type of
    -- expression in the 'Just' case, and why it is so.
    --
    -- See Note [Failing pattern matches in Stmts] for which contexts for
    -- '@BindStmt@'s should use the monadic fail and which shouldn't.
    type FailOperator id = Maybe (SyntaxExpr id)

    -- | Applicative Argument
    data ApplicativeArg idL
      = ApplicativeArgOne      -- A single statement (BindStmt or BodyStmt)
        { forall idL. ApplicativeArg idL -> XApplicativeArgOne idL
    xarg_app_arg_one  :: XApplicativeArgOne idL
          -- ^ The fail operator, after renaming
          --
          -- The fail operator is needed if this is a BindStmt
          -- where the pattern can fail. E.g.:
          -- (Just a) <- stmt
          -- The fail operator will be invoked if the pattern
          -- match fails.
          -- It is also used for guards in MonadComprehensions.
          -- The fail operator is Nothing
          -- if the pattern match can't fail
        , forall idL. ApplicativeArg idL -> LPat idL
    app_arg_pattern   :: LPat idL -- WildPat if it was a BodyStmt (see below)
        , forall idL. ApplicativeArg idL -> LHsExpr idL
    arg_expr          :: LHsExpr idL
        , forall idL. ApplicativeArg idL -> Bool
    is_body_stmt      :: Bool
          -- ^ True <=> was a BodyStmt,
          -- False <=> was a BindStmt.
          -- See Note [Applicative BodyStmt]
        }
      | ApplicativeArgMany     -- do { stmts; return vars }
        { forall idL. ApplicativeArg idL -> XApplicativeArgMany idL
    xarg_app_arg_many :: XApplicativeArgMany idL
        , forall idL. ApplicativeArg idL -> [ExprLStmt idL]
    app_stmts         :: [ExprLStmt idL] -- stmts
        , forall idL. ApplicativeArg idL -> HsExpr idL
    final_expr        :: HsExpr idL    -- return (v1,..,vn), or just (v1,..,vn)
        , forall idL. ApplicativeArg idL -> LPat idL
    bv_pattern        :: LPat idL      -- (v1,...,vn)
        , forall idL. ApplicativeArg idL -> HsStmtContext GhcRn
    stmt_context      :: HsStmtContext GhcRn -- context of the do expression
                                                   -- used in pprArg
        }
      | XApplicativeArg !(XXApplicativeArg idL)

    type instance XApplicativeArgOne GhcPs = NoExtField
    type instance XApplicativeArgOne GhcRn = FailOperator GhcRn
    type instance XApplicativeArgOne GhcTc = FailOperator GhcTc

    type instance XApplicativeArgMany (GhcPass _) = NoExtField
    type instance XXApplicativeArg    (GhcPass _) = NoExtCon

    {-
    Note [The type of bind in Stmts]
    ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
    Some Stmts, notably BindStmt, keep the (>>=) bind operator.
    We do NOT assume that it has type
        (>>=) :: m a -> (a -> m b) -> m b
    In some cases (see #303, #1537) it might have a more
    exotic type, such as
        (>>=) :: m i j a -> (a -> m j k b) -> m i k b
    So we must be careful not to make assumptions about the type.
    In particular, the monad may not be uniform throughout.

    Note [TransStmt binder map]
    ~~~~~~~~~~~~~~~~~~~~~~~~~~~
    The [(idR,idR)] in a TransStmt behaves as follows:

      * Before renaming: []

      * After renaming:
              [ (x27,x27), ..., (z35,z35) ]
        These are the variables
           bound by the stmts to the left of the 'group'
           and used either in the 'by' clause,
                    or     in the stmts following the 'group'
        Each item is a pair of identical variables.

      * After typechecking:
              [ (x27:Int, x27:[Int]), ..., (z35:Bool, z35:[Bool]) ]
        Each pair has the same unique, but different *types*.

    Note [BodyStmt]
    ~~~~~~~~~~~~~~~
    BodyStmts are a bit tricky, because what they mean
    depends on the context.  Consider the following contexts:

            A do expression of type (m res_ty)
            ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
            * BodyStmt E any_ty:   do { ....; E; ... }
                    E :: m any_ty
              Translation: E >> ...

            A list comprehensions of type [elt_ty]
            ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
            * BodyStmt E Bool:   [ .. | .... E ]
                            [ .. | ..., E, ... ]
                            [ .. | .... | ..., E | ... ]
                    E :: Bool
              Translation: if E then fail else ...

            A guard list, guarding a RHS of type rhs_ty
            ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
            * BodyStmt E BooParStmtBlockl:   f x | ..., E, ... = ...rhs...
                    E :: Bool
              Translation: if E then fail else ...

            A monad comprehension of type (m res_ty)
            ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
            * BodyStmt E Bool:   [ .. | .... E ]
                    E :: Bool
              Translation: guard E >> ...

    Array comprehensions are handled like list comprehensions.

    Note [How RecStmt works]
    ~~~~~~~~~~~~~~~~~~~~~~~~
    Example:
       HsDo [ BindStmt x ex

            , RecStmt { recS_rec_ids   = [a, c]
                      , recS_stmts     = [ BindStmt b (return (a,c))
                                         , LetStmt a = ...b...
                                         , BindStmt c ec ]
                      , recS_later_ids = [a, b]

            , return (a b) ]

    Here, the RecStmt binds a,b,c; but
      - Only a,b are used in the stmts *following* the RecStmt,
      - Only a,c are used in the stmts *inside* the RecStmt
            *before* their bindings

    Why do we need *both* rec_ids and later_ids?  For monads they could be
    combined into a single set of variables, but not for arrows.  That
    follows from the types of the respective feedback operators:

            mfix :: MonadFix m => (a -> m a) -> m a
            loop :: ArrowLoop a => a (b,d) (c,d) -> a b c

    * For mfix, the 'a' covers the union of the later_ids and the rec_ids
    * For 'loop', 'c' is the later_ids and 'd' is the rec_ids

    Note [Typing a RecStmt]
    ~~~~~~~~~~~~~~~~~~~~~~~
    A (RecStmt stmts) types as if you had written

      (v1,..,vn, _, ..., _) <- mfix (\~(_, ..., _, r1, ..., rm) ->
                                     do { stmts
                                        ; return (v1,..vn, r1, ..., rm) })

    where v1..vn are the later_ids
          r1..rm are the rec_ids

    Note [Monad Comprehensions]
    ~~~~~~~~~~~~~~~~~~~~~~~~~~~
    Monad comprehensions require separate functions like 'return' and
    '>>=' for desugaring. These functions are stored in the statements
    used in monad comprehensions. For example, the 'return' of the 'LastStmt'
    expression is used to lift the body of the monad comprehension:

      [ body | stmts ]
       =>
      stmts >>= \bndrs -> return body

    In transform and grouping statements ('then ..' and 'then group ..') the
    'return' function is required for nested monad comprehensions, for example:

      [ body | stmts, then f, rest ]
       =>
      f [ env | stmts ] >>= \bndrs -> [ body | rest ]

    BodyStmts require the 'Control.Monad.guard' function for boolean
    expressions:

      [ body | exp, stmts ]
       =>
      guard exp >> [ body | stmts ]

    Parallel statements require the 'Control.Monad.Zip.mzip' function:

      [ body | stmts1 | stmts2 | .. ]
       =>
      mzip stmts1 (mzip stmts2 (..)) >>= \(bndrs1, (bndrs2, ..)) -> return body

    In any other context than 'MonadComp', the fields for most of these
    'SyntaxExpr's stay bottom.

    Note [Applicative BodyStmt]

    (#12143) For the purposes of ApplicativeDo, we treat any BodyStmt
    as if it was a BindStmt with a wildcard pattern.  For example,

      do
        x <- A
        B
        return x

    is transformed as if it were

      do
        x <- A
        _ <- B
        return x

    so it transforms to

      (\(x,_) -> x) <$> A <*> B

    But we have to remember when we treat a BodyStmt like a BindStmt,
    because in error messages we want to emit the original syntax the user
    wrote, not our internal representation.  So ApplicativeArgOne has a
    Bool flag that is True when the original statement was a BodyStmt, so
    that we can pretty-print it correctly.
    -}

    instance (Outputable (StmtLR idL idL (LHsExpr idL)),
              Outputable (XXParStmtBlock idL idR))
            => Outputable (ParStmtBlock idL idR) where
      ppr :: ParStmtBlock idL idR -> SDoc
    ppr (ParStmtBlock XParStmtBlock idL idR
    _ [ExprLStmt idL]
    stmts [IdP idR]
    _ SyntaxExpr idR
    _) = [ExprLStmt idL] -> SDoc
    forall a. Outputable a => [a] -> SDoc
    interpp'SP [ExprLStmt idL]
    stmts
      ppr (XParStmtBlock XXParStmtBlock idL idR
    x)          = XXParStmtBlock idL idR -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr XXParStmtBlock idL idR
    x

    instance (OutputableBndrId pl, OutputableBndrId pr,
              Outputable body)
             => Outputable (StmtLR (GhcPass pl) (GhcPass pr) body) where
        ppr :: StmtLR (GhcPass pl) (GhcPass pr) body -> SDoc
    ppr StmtLR (GhcPass pl) (GhcPass pr) body
    stmt = StmtLR (GhcPass pl) (GhcPass pr) body -> SDoc
    forall (pl :: Pass) (pr :: Pass) body.
    (OutputableBndrId pl, OutputableBndrId pr, Outputable body) =>
    StmtLR (GhcPass pl) (GhcPass pr) body -> SDoc
    pprStmt StmtLR (GhcPass pl) (GhcPass pr) body
    stmt

    pprStmt :: forall idL idR body . (OutputableBndrId idL,
                                      OutputableBndrId idR,
                                      Outputable body)
            => (StmtLR (GhcPass idL) (GhcPass idR) body) -> SDoc
    pprStmt :: forall (pl :: Pass) (pr :: Pass) body.
    (OutputableBndrId pl, OutputableBndrId pr, Outputable body) =>
    StmtLR (GhcPass pl) (GhcPass pr) body -> SDoc
    pprStmt (LastStmt XLastStmt (GhcPass idL) (GhcPass idR) body
    _ body
    expr Maybe Bool
    m_dollar_stripped SyntaxExpr (GhcPass idR)
    _)
      = SDoc -> SDoc
    whenPprDebug (String -> SDoc
    text String
    "[last]") SDoc -> SDoc -> SDoc
    <+>
          (case Maybe Bool
    m_dollar_stripped of
            Just Bool
    True -> String -> SDoc
    text String
    "return $"
            Just Bool
    False -> String -> SDoc
    text String
    "return"
            Maybe Bool
    Nothing -> SDoc
    empty) SDoc -> SDoc -> SDoc
    <+>
          body -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr body
    expr
    pprStmt (BindStmt XBindStmt (GhcPass idL) (GhcPass idR) body
    _ LPat (GhcPass idL)
    pat body
    expr) = [SDoc] -> SDoc
    hsep [Located (Pat (GhcPass idL)) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr Located (Pat (GhcPass idL))
    LPat (GhcPass idL)
    pat, SDoc
    larrow, body -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr body
    expr]
    pprStmt (LetStmt XLetStmt (GhcPass idL) (GhcPass idR) body
    _ (L SrcSpan
    _ HsLocalBindsLR (GhcPass idL) (GhcPass idR)
    binds))   = [SDoc] -> SDoc
    hsep [String -> SDoc
    text String
    "let", HsLocalBindsLR (GhcPass idL) (GhcPass idR) -> SDoc
    forall (idL :: Pass) (idR :: Pass).
    (OutputableBndrId idL, OutputableBndrId idR) =>
    HsLocalBindsLR (GhcPass idL) (GhcPass idR) -> SDoc
    pprBinds HsLocalBindsLR (GhcPass idL) (GhcPass idR)
    binds]
    pprStmt (BodyStmt XBodyStmt (GhcPass idL) (GhcPass idR) body
    _ body
    expr SyntaxExpr (GhcPass idR)
    _ SyntaxExpr (GhcPass idR)
    _)     = body -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr body
    expr
    pprStmt (ParStmt XParStmt (GhcPass idL) (GhcPass idR) body
    _ [ParStmtBlock (GhcPass idL) (GhcPass idR)]
    stmtss HsExpr (GhcPass idR)
    _ SyntaxExpr (GhcPass idR)
    _)   = [SDoc] -> SDoc
    sep (SDoc -> [SDoc] -> [SDoc]
    punctuate (String -> SDoc
    text String
    " | ") ((ParStmtBlock (GhcPass idL) (GhcPass idR) -> SDoc)
    -> [ParStmtBlock (GhcPass idL) (GhcPass idR)] -> [SDoc]
    forall a b. (a -> b) -> [a] -> [b]
    map ParStmtBlock (GhcPass idL) (GhcPass idR) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr [ParStmtBlock (GhcPass idL) (GhcPass idR)]
    stmtss))

    pprStmt (TransStmt { trS_stmts :: forall idL idR body. StmtLR idL idR body -> [ExprLStmt idL]
    trS_stmts = [ExprLStmt (GhcPass idL)]
    stmts, trS_by :: forall idL idR body. StmtLR idL idR body -> Maybe (LHsExpr idR)
    trS_by = Maybe (LHsExpr (GhcPass idR))
    by
                       , trS_using :: forall idL idR body. StmtLR idL idR body -> LHsExpr idR
    trS_using = LHsExpr (GhcPass idR)
    using, trS_form :: forall idL idR body. StmtLR idL idR body -> TransForm
    trS_form = TransForm
    form })
      = [SDoc] -> SDoc
    sep ([SDoc] -> SDoc) -> [SDoc] -> SDoc
    forall a b. (a -> b) -> a -> b
    $ SDoc -> [SDoc] -> [SDoc]
    punctuate SDoc
    comma ((ExprLStmt (GhcPass idL) -> SDoc)
    -> [ExprLStmt (GhcPass idL)] -> [SDoc]
    forall a b. (a -> b) -> [a] -> [b]
    map ExprLStmt (GhcPass idL) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr [ExprLStmt (GhcPass idL)]
    stmts [SDoc] -> [SDoc] -> [SDoc]
    forall a. [a] -> [a] -> [a]
    ++ [Maybe (LHsExpr (GhcPass idR))
    -> LHsExpr (GhcPass idR) -> TransForm -> SDoc
    forall body.
    Outputable body =>
    Maybe body -> body -> TransForm -> SDoc
    pprTransStmt Maybe (LHsExpr (GhcPass idR))
    by LHsExpr (GhcPass idR)
    using TransForm
    form])

    pprStmt (RecStmt { recS_stmts :: forall idL idR body. StmtLR idL idR body -> [LStmtLR idL idR body]
    recS_stmts = [LStmtLR (GhcPass idL) (GhcPass idR) body]
    segment, recS_rec_ids :: forall idL idR body. StmtLR idL idR body -> [IdP idR]
    recS_rec_ids = [IdP (GhcPass idR)]
    rec_ids
                     , recS_later_ids :: forall idL idR body. StmtLR idL idR body -> [IdP idR]
    recS_later_ids = [IdP (GhcPass idR)]
    later_ids })
      = String -> SDoc
    text String
    "rec" SDoc -> SDoc -> SDoc
    <+>
        [SDoc] -> SDoc
    vcat [ [LStmtLR (GhcPass idL) (GhcPass idR) body] -> SDoc
    forall (idL :: Pass) (idR :: Pass) body.
    (OutputableBndrId idL, OutputableBndrId idR, Outputable body) =>
    [LStmtLR (GhcPass idL) (GhcPass idR) body] -> SDoc
    ppr_do_stmts [LStmtLR (GhcPass idL) (GhcPass idR) body]
    segment
             , SDoc -> SDoc
    whenPprDebug ([SDoc] -> SDoc
    vcat [ String -> SDoc
    text String
    "rec_ids=" SDoc -> SDoc -> SDoc
    <> [IdGhcP idR] -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr [IdGhcP idR]
    [IdP (GhcPass idR)]
    rec_ids
                                , String -> SDoc
    text String
    "later_ids=" SDoc -> SDoc -> SDoc
    <> [IdGhcP idR] -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr [IdGhcP idR]
    [IdP (GhcPass idR)]
    later_ids])]

    pprStmt (ApplicativeStmt XApplicativeStmt (GhcPass idL) (GhcPass idR) body
    _ [(SyntaxExpr (GhcPass idR), ApplicativeArg (GhcPass idL))]
    args Maybe (SyntaxExpr (GhcPass idR))
    mb_join)
      = (PprStyle -> SDoc) -> SDoc
    getPprStyle ((PprStyle -> SDoc) -> SDoc) -> (PprStyle -> SDoc) -> SDoc
    forall a b. (a -> b) -> a -> b
    $ \PprStyle
    style ->
          if PprStyle -> Bool
    userStyle PprStyle
    style
             then SDoc
    pp_for_user
             else SDoc
    pp_debug
      where
      -- make all the Applicative stuff invisible in error messages by
      -- flattening the whole ApplicativeStmt nest back to a sequence
      -- of statements.
       pp_for_user :: SDoc
    pp_for_user = [SDoc] -> SDoc
    vcat ([SDoc] -> SDoc) -> [SDoc] -> SDoc
    forall a b. (a -> b) -> a -> b
    $ ((SyntaxExprGhc idR, ApplicativeArg (GhcPass idL)) -> [SDoc])
    -> [(SyntaxExprGhc idR, ApplicativeArg (GhcPass idL))] -> [SDoc]
    forall (t :: * -> *) a b. Foldable t => (a -> [b]) -> t a -> [b]
    concatMap (SyntaxExprGhc idR, ApplicativeArg (GhcPass idL)) -> [SDoc]
    forall a. (a, ApplicativeArg (GhcPass idL)) -> [SDoc]
    flattenArg [(SyntaxExpr (GhcPass idR), ApplicativeArg (GhcPass idL))]
    [(SyntaxExprGhc idR, ApplicativeArg (GhcPass idL))]
    args

       -- ppr directly rather than transforming here, because we need to
       -- inject a "return" which is hard when we're polymorphic in the id
       -- type.
       flattenStmt :: ExprLStmt (GhcPass idL) -> [SDoc]
       flattenStmt :: ExprLStmt (GhcPass idL) -> [SDoc]
    flattenStmt (L SrcSpan
    _ (ApplicativeStmt XApplicativeStmt
      (GhcPass idL) (GhcPass idL) (LHsExpr (GhcPass idL))
    _ [(SyntaxExpr (GhcPass idL), ApplicativeArg (GhcPass idL))]
    args Maybe (SyntaxExpr (GhcPass idL))
    _)) = ((SyntaxExprGhc idL, ApplicativeArg (GhcPass idL)) -> [SDoc])
    -> [(SyntaxExprGhc idL, ApplicativeArg (GhcPass idL))] -> [SDoc]
    forall (t :: * -> *) a b. Foldable t => (a -> [b]) -> t a -> [b]
    concatMap (SyntaxExprGhc idL, ApplicativeArg (GhcPass idL)) -> [SDoc]
    forall a. (a, ApplicativeArg (GhcPass idL)) -> [SDoc]
    flattenArg [(SyntaxExpr (GhcPass idL), ApplicativeArg (GhcPass idL))]
    [(SyntaxExprGhc idL, ApplicativeArg (GhcPass idL))]
    args
       flattenStmt ExprLStmt (GhcPass idL)
    stmt = [ExprLStmt (GhcPass idL) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr ExprLStmt (GhcPass idL)
    stmt]

       flattenArg :: forall a . (a, ApplicativeArg (GhcPass idL)) -> [SDoc]
       flattenArg :: forall a. (a, ApplicativeArg (GhcPass idL)) -> [SDoc]
    flattenArg (a
    _, ApplicativeArgOne XApplicativeArgOne (GhcPass idL)
    _ LPat (GhcPass idL)
    pat LHsExpr (GhcPass idL)
    expr Bool
    isBody)
         | Bool
    isBody =  -- See Note [Applicative BodyStmt]
         [StmtLR (GhcPass idL) (GhcPass idL) (LHsExpr (GhcPass idL)) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr (XBodyStmt (GhcPass idL) (GhcPass idL) (LHsExpr (GhcPass idL))
    -> LHsExpr (GhcPass idL)
    -> SyntaxExpr (GhcPass idL)
    -> SyntaxExpr (GhcPass idL)
    -> StmtLR (GhcPass idL) (GhcPass idL) (LHsExpr (GhcPass idL))
    forall idL idR body.
    XBodyStmt idL idR body
    -> body -> SyntaxExpr idR -> SyntaxExpr idR -> StmtLR idL idR body
    BodyStmt (String
    -> XBodyStmt (GhcPass idL) (GhcPass idL) (LHsExpr (GhcPass idL))
    forall a. String -> a
    panic String
    "pprStmt") LHsExpr (GhcPass idL)
    expr SyntaxExpr (GhcPass idL)
    forall (p :: Pass). IsPass p => SyntaxExpr (GhcPass p)
    noSyntaxExpr SyntaxExpr (GhcPass idL)
    forall (p :: Pass). IsPass p => SyntaxExpr (GhcPass p)
    noSyntaxExpr
                 :: ExprStmt (GhcPass idL))]
         | Bool
    otherwise =
         [StmtLR (GhcPass idL) (GhcPass idL) (LHsExpr (GhcPass idL)) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr (XBindStmt (GhcPass idL) (GhcPass idL) (LHsExpr (GhcPass idL))
    -> LPat (GhcPass idL)
    -> LHsExpr (GhcPass idL)
    -> StmtLR (GhcPass idL) (GhcPass idL) (LHsExpr (GhcPass idL))
    forall idL idR body.
    XBindStmt idL idR body -> LPat idL -> body -> StmtLR idL idR body
    BindStmt (String
    -> XBindStmt (GhcPass idL) (GhcPass idL) (LHsExpr (GhcPass idL))
    forall a. String -> a
    panic String
    "pprStmt") LPat (GhcPass idL)
    pat LHsExpr (GhcPass idL)
    expr :: ExprStmt (GhcPass idL))]
       flattenArg (a
    _, ApplicativeArgMany XApplicativeArgMany (GhcPass idL)
    _ [ExprLStmt (GhcPass idL)]
    stmts HsExpr (GhcPass idL)
    _ LPat (GhcPass idL)
    _ HsStmtContext GhcRn
    _) =
         (ExprLStmt (GhcPass idL) -> [SDoc])
    -> [ExprLStmt (GhcPass idL)] -> [SDoc]
    forall (t :: * -> *) a b. Foldable t => (a -> [b]) -> t a -> [b]
    concatMap ExprLStmt (GhcPass idL) -> [SDoc]
    flattenStmt [ExprLStmt (GhcPass idL)]
    stmts

       pp_debug :: SDoc
    pp_debug =
         let
             ap_expr :: SDoc
    ap_expr = [SDoc] -> SDoc
    sep (SDoc -> [SDoc] -> [SDoc]
    punctuate (String -> SDoc
    text String
    " |") (((SyntaxExprGhc idR, ApplicativeArg (GhcPass idL)) -> SDoc)
    -> [(SyntaxExprGhc idR, ApplicativeArg (GhcPass idL))] -> [SDoc]
    forall a b. (a -> b) -> [a] -> [b]
    map (SyntaxExprGhc idR, ApplicativeArg (GhcPass idL)) -> SDoc
    forall a. (a, ApplicativeArg (GhcPass idL)) -> SDoc
    pp_arg [(SyntaxExpr (GhcPass idR), ApplicativeArg (GhcPass idL))]
    [(SyntaxExprGhc idR, ApplicativeArg (GhcPass idL))]
    args))
         in
           SDoc -> SDoc
    whenPprDebug (if Maybe (SyntaxExprGhc idR) -> Bool
    forall a. Maybe a -> Bool
    isJust Maybe (SyntaxExpr (GhcPass idR))
    Maybe (SyntaxExprGhc idR)
    mb_join then String -> SDoc
    text String
    "[join]" else SDoc
    empty) SDoc -> SDoc -> SDoc
    <+>
           (if [(SyntaxExprGhc idR, ApplicativeArg (GhcPass idL))] -> Int -> Bool
    forall a. [a] -> Int -> Bool
    lengthAtLeast [(SyntaxExpr (GhcPass idR), ApplicativeArg (GhcPass idL))]
    [(SyntaxExprGhc idR, ApplicativeArg (GhcPass idL))]
    args Int
    2 then SDoc -> SDoc
    parens else SDoc -> SDoc
    forall a. a -> a
    id) SDoc
    ap_expr

       pp_arg :: (a, ApplicativeArg (GhcPass idL)) -> SDoc
       pp_arg :: forall a. (a, ApplicativeArg (GhcPass idL)) -> SDoc
    pp_arg (a
    _, ApplicativeArg (GhcPass idL)
    applicativeArg) = ApplicativeArg (GhcPass idL) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr ApplicativeArg (GhcPass idL)
    applicativeArg

    instance (OutputableBndrId idL)
          => Outputable (ApplicativeArg (GhcPass idL)) where
      ppr :: ApplicativeArg (GhcPass idL) -> SDoc
    ppr = ApplicativeArg (GhcPass idL) -> SDoc
    forall (idL :: Pass).
    OutputableBndrId idL =>
    ApplicativeArg (GhcPass idL) -> SDoc
    pprArg

    pprArg :: forall idL . (OutputableBndrId idL) => ApplicativeArg (GhcPass idL) -> SDoc
    pprArg :: forall (idL :: Pass).
    OutputableBndrId idL =>
    ApplicativeArg (GhcPass idL) -> SDoc
    pprArg (ApplicativeArgOne XApplicativeArgOne (GhcPass idL)
    _ LPat (GhcPass idL)
    pat GenLocated SrcSpan (HsExpr (GhcPass idL))
    expr Bool
    isBody)
      | Bool
    isBody =  -- See Note [Applicative BodyStmt]
        ExprStmt (GhcPass idL) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr (XBodyStmt
      (GhcPass idL)
      (GhcPass idL)
      (GenLocated SrcSpan (HsExpr (GhcPass idL)))
    -> GenLocated SrcSpan (HsExpr (GhcPass idL))
    -> SyntaxExpr (GhcPass idL)
    -> SyntaxExpr (GhcPass idL)
    -> ExprStmt (GhcPass idL)
    forall idL idR body.
    XBodyStmt idL idR body
    -> body -> SyntaxExpr idR -> SyntaxExpr idR -> StmtLR idL idR body
    BodyStmt (String
    -> XBodyStmt
         (GhcPass idL)
         (GhcPass idL)
         (GenLocated SrcSpan (HsExpr (GhcPass idL)))
    forall a. String -> a
    panic String
    "pprStmt") GenLocated SrcSpan (HsExpr (GhcPass idL))
    expr SyntaxExpr (GhcPass idL)
    forall (p :: Pass). IsPass p => SyntaxExpr (GhcPass p)
    noSyntaxExpr SyntaxExpr (GhcPass idL)
    forall (p :: Pass). IsPass p => SyntaxExpr (GhcPass p)
    noSyntaxExpr
                :: ExprStmt (GhcPass idL))
      | Bool
    otherwise =
        ExprStmt (GhcPass idL) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr (XBindStmt
      (GhcPass idL)
      (GhcPass idL)
      (GenLocated SrcSpan (HsExpr (GhcPass idL)))
    -> LPat (GhcPass idL)
    -> GenLocated SrcSpan (HsExpr (GhcPass idL))
    -> ExprStmt (GhcPass idL)
    forall idL idR body.
    XBindStmt idL idR body -> LPat idL -> body -> StmtLR idL idR body
    BindStmt (String
    -> XBindStmt
         (GhcPass idL)
         (GhcPass idL)
         (GenLocated SrcSpan (HsExpr (GhcPass idL)))
    forall a. String -> a
    panic String
    "pprStmt") LPat (GhcPass idL)
    pat GenLocated SrcSpan (HsExpr (GhcPass idL))
    expr :: ExprStmt (GhcPass idL))
    pprArg (ApplicativeArgMany XApplicativeArgMany (GhcPass idL)
    _ [ExprLStmt (GhcPass idL)]
    stmts HsExpr (GhcPass idL)
    return LPat (GhcPass idL)
    pat HsStmtContext GhcRn
    ctxt) =
         Located (Pat (GhcPass idL)) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr Located (Pat (GhcPass idL))
    LPat (GhcPass idL)
    pat SDoc -> SDoc -> SDoc
    <+>
         String -> SDoc
    text String
    "<-" SDoc -> SDoc -> SDoc
    <+>
         HsExpr (GhcPass idL) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr (XDo (GhcPass idL)
    -> HsStmtContext GhcRn
    -> Located [ExprLStmt (GhcPass idL)]
    -> HsExpr (GhcPass idL)
    forall p.
    XDo p -> HsStmtContext GhcRn -> Located [ExprLStmt p] -> HsExpr p
    HsDo (String -> XDo (GhcPass idL)
    forall a. String -> a
    panic String
    "pprStmt") HsStmtContext GhcRn
    ctxt ([ExprLStmt (GhcPass idL)] -> Located [ExprLStmt (GhcPass idL)]
    forall e. e -> Located e
    noLoc
                   ([ExprLStmt (GhcPass idL)]
    stmts [ExprLStmt (GhcPass idL)]
    -> [ExprLStmt (GhcPass idL)] -> [ExprLStmt (GhcPass idL)]
    forall a. [a] -> [a] -> [a]
    ++
                       [ExprStmt (GhcPass idL) -> ExprLStmt (GhcPass idL)
    forall e. e -> Located e
    noLoc (XLastStmt
      (GhcPass idL)
      (GhcPass idL)
      (GenLocated SrcSpan (HsExpr (GhcPass idL)))
    -> GenLocated SrcSpan (HsExpr (GhcPass idL))
    -> Maybe Bool
    -> SyntaxExpr (GhcPass idL)
    -> ExprStmt (GhcPass idL)
    forall idL idR body.
    XLastStmt idL idR body
    -> body -> Maybe Bool -> SyntaxExpr idR -> StmtLR idL idR body
    LastStmt NoExtField
    XLastStmt
      (GhcPass idL)
      (GhcPass idL)
      (GenLocated SrcSpan (HsExpr (GhcPass idL)))
    noExtField (HsExpr (GhcPass idL) -> GenLocated SrcSpan (HsExpr (GhcPass idL))
    forall e. e -> Located e
    noLoc HsExpr (GhcPass idL)
    return) Maybe Bool
    forall a. Maybe a
    Nothing SyntaxExpr (GhcPass idL)
    forall (p :: Pass). IsPass p => SyntaxExpr (GhcPass p)
    noSyntaxExpr)])))

    pprTransformStmt :: (OutputableBndrId p)
                     => [IdP (GhcPass p)] -> LHsExpr (GhcPass p)
                     -> Maybe (LHsExpr (GhcPass p)) -> SDoc
    pprTransformStmt :: forall (p :: Pass).
    OutputableBndrId p =>
    [IdP (GhcPass p)]
    -> LHsExpr (GhcPass p) -> Maybe (LHsExpr (GhcPass p)) -> SDoc
    pprTransformStmt [IdP (GhcPass p)]
    bndrs LHsExpr (GhcPass p)
    using Maybe (LHsExpr (GhcPass p))
    by
      = [SDoc] -> SDoc
    sep [ String -> SDoc
    text String
    "then" SDoc -> SDoc -> SDoc
    <+> SDoc -> SDoc
    whenPprDebug (SDoc -> SDoc
    braces ([IdGhcP p] -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr [IdGhcP p]
    [IdP (GhcPass p)]
    bndrs))
            , Int -> SDoc -> SDoc
    nest Int
    2 (LHsExpr (GhcPass p) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr LHsExpr (GhcPass p)
    using)
            , Int -> SDoc -> SDoc
    nest Int
    2 (Maybe (LHsExpr (GhcPass p)) -> SDoc
    forall body. Outputable body => Maybe body -> SDoc
    pprBy Maybe (LHsExpr (GhcPass p))
    by)]

    pprTransStmt :: Outputable body => Maybe body -> body -> TransForm -> SDoc
    pprTransStmt :: forall body.
    Outputable body =>
    Maybe body -> body -> TransForm -> SDoc
    pprTransStmt Maybe body
    by body
    using TransForm
    ThenForm
      = [SDoc] -> SDoc
    sep [ String -> SDoc
    text String
    "then", Int -> SDoc -> SDoc
    nest Int
    2 (body -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr body
    using), Int -> SDoc -> SDoc
    nest Int
    2 (Maybe body -> SDoc
    forall body. Outputable body => Maybe body -> SDoc
    pprBy Maybe body
    by)]
    pprTransStmt Maybe body
    by body
    using TransForm
    GroupForm
      = [SDoc] -> SDoc
    sep [ String -> SDoc
    text String
    "then group", Int -> SDoc -> SDoc
    nest Int
    2 (Maybe body -> SDoc
    forall body. Outputable body => Maybe body -> SDoc
    pprBy Maybe body
    by), Int -> SDoc -> SDoc
    nest Int
    2 (PtrString -> SDoc
    ptext (String -> PtrString
    sLit String
    "using") SDoc -> SDoc -> SDoc
    <+> body -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr body
    using)]

    pprBy :: Outputable body => Maybe body -> SDoc
    pprBy :: forall body. Outputable body => Maybe body -> SDoc
    pprBy Maybe body
    Nothing  = SDoc
    empty
    pprBy (Just body
    e) = String -> SDoc
    text String
    "by" SDoc -> SDoc -> SDoc
    <+> body -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr body
    e

    pprDo :: (OutputableBndrId p, Outputable body)
          => HsStmtContext any -> [LStmt (GhcPass p) body] -> SDoc
    pprDo :: forall (p :: Pass) body any.
    (OutputableBndrId p, Outputable body) =>
    HsStmtContext any -> [LStmt (GhcPass p) body] -> SDoc
    pprDo (DoExpr Maybe ModuleName
    m)    [LStmt (GhcPass p) body]
    stmts =
      Maybe ModuleName -> SDoc
    ppr_module_name_prefix Maybe ModuleName
    m SDoc -> SDoc -> SDoc
    <> String -> SDoc
    text String
    "do"  SDoc -> SDoc -> SDoc
    <+> [LStmt (GhcPass p) body] -> SDoc
    forall (idL :: Pass) (idR :: Pass) body.
    (OutputableBndrId idL, OutputableBndrId idR, Outputable body) =>
    [LStmtLR (GhcPass idL) (GhcPass idR) body] -> SDoc
    ppr_do_stmts [LStmt (GhcPass p) body]
    stmts
    pprDo HsStmtContext any
    GhciStmtCtxt  [LStmt (GhcPass p) body]
    stmts = String -> SDoc
    text String
    "do"  SDoc -> SDoc -> SDoc
    <+> [LStmt (GhcPass p) body] -> SDoc
    forall (idL :: Pass) (idR :: Pass) body.
    (OutputableBndrId idL, OutputableBndrId idR, Outputable body) =>
    [LStmtLR (GhcPass idL) (GhcPass idR) body] -> SDoc
    ppr_do_stmts [LStmt (GhcPass p) body]
    stmts
    pprDo HsStmtContext any
    ArrowExpr     [LStmt (GhcPass p) body]
    stmts = String -> SDoc
    text String
    "do"  SDoc -> SDoc -> SDoc
    <+> [LStmt (GhcPass p) body] -> SDoc
    forall (idL :: Pass) (idR :: Pass) body.
    (OutputableBndrId idL, OutputableBndrId idR, Outputable body) =>
    [LStmtLR (GhcPass idL) (GhcPass idR) body] -> SDoc
    ppr_do_stmts [LStmt (GhcPass p) body]
    stmts
    pprDo (MDoExpr Maybe ModuleName
    m)   [LStmt (GhcPass p) body]
    stmts =
      Maybe ModuleName -> SDoc
    ppr_module_name_prefix Maybe ModuleName
    m SDoc -> SDoc -> SDoc
    <> String -> SDoc
    text String
    "mdo"  SDoc -> SDoc -> SDoc
    <+> [LStmt (GhcPass p) body] -> SDoc
    forall (idL :: Pass) (idR :: Pass) body.
    (OutputableBndrId idL, OutputableBndrId idR, Outputable body) =>
    [LStmtLR (GhcPass idL) (GhcPass idR) body] -> SDoc
    ppr_do_stmts [LStmt (GhcPass p) body]
    stmts
    pprDo HsStmtContext any
    ListComp      [LStmt (GhcPass p) body]
    stmts = SDoc -> SDoc
    brackets    (SDoc -> SDoc) -> SDoc -> SDoc
    forall a b. (a -> b) -> a -> b
    $ [LStmt (GhcPass p) body] -> SDoc
    forall (p :: Pass) body.
    (OutputableBndrId p, Outputable body) =>
    [LStmt (GhcPass p) body] -> SDoc
    pprComp [LStmt (GhcPass p) body]
    stmts
    pprDo HsStmtContext any
    MonadComp     [LStmt (GhcPass p) body]
    stmts = SDoc -> SDoc
    brackets    (SDoc -> SDoc) -> SDoc -> SDoc
    forall a b. (a -> b) -> a -> b
    $ [LStmt (GhcPass p) body] -> SDoc
    forall (p :: Pass) body.
    (OutputableBndrId p, Outputable body) =>
    [LStmt (GhcPass p) body] -> SDoc
    pprComp [LStmt (GhcPass p) body]
    stmts
    pprDo HsStmtContext any
    _             [LStmt (GhcPass p) body]
    _     = String -> SDoc
    forall a. String -> a
    panic String
    "pprDo" -- PatGuard, ParStmtCxt

    ppr_module_name_prefix :: Maybe ModuleName -> SDoc
    ppr_module_name_prefix :: Maybe ModuleName -> SDoc
    ppr_module_name_prefix = \case
      Maybe ModuleName
    Nothing -> SDoc
    empty
      Just ModuleName
    module_name -> ModuleName -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr ModuleName
    module_name SDoc -> SDoc -> SDoc
    <> Char -> SDoc
    char Char
    '.'

    ppr_do_stmts :: (OutputableBndrId idL, OutputableBndrId idR,
                     Outputable body)
                 => [LStmtLR (GhcPass idL) (GhcPass idR) body] -> SDoc
    -- Print a bunch of do stmts
    ppr_do_stmts :: forall (idL :: Pass) (idR :: Pass) body.
    (OutputableBndrId idL, OutputableBndrId idR, Outputable body) =>
    [LStmtLR (GhcPass idL) (GhcPass idR) body] -> SDoc
    ppr_do_stmts [LStmtLR (GhcPass idL) (GhcPass idR) body]
    stmts = ([SDoc] -> SDoc) -> [SDoc] -> SDoc
    pprDeeperList [SDoc] -> SDoc
    vcat ((LStmtLR (GhcPass idL) (GhcPass idR) body -> SDoc)
    -> [LStmtLR (GhcPass idL) (GhcPass idR) body] -> [SDoc]
    forall a b. (a -> b) -> [a] -> [b]
    map LStmtLR (GhcPass idL) (GhcPass idR) body -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr [LStmtLR (GhcPass idL) (GhcPass idR) body]
    stmts)

    pprComp :: (OutputableBndrId p, Outputable body)
            => [LStmt (GhcPass p) body] -> SDoc
    pprComp :: forall (p :: Pass) body.
    (OutputableBndrId p, Outputable body) =>
    [LStmt (GhcPass p) body] -> SDoc
    pprComp [LStmt (GhcPass p) body]
    quals     -- Prints:  body | qual1, ..., qualn
      | Just ([LStmt (GhcPass p) body]
    initStmts, L SrcSpan
    _ (LastStmt XLastStmt (GhcPass p) (GhcPass p) body
    _ body
    body Maybe Bool
    _ SyntaxExpr (GhcPass p)
    _)) <- [LStmt (GhcPass p) body]
    -> Maybe ([LStmt (GhcPass p) body], LStmt (GhcPass p) body)
    forall a. [a] -> Maybe ([a], a)
    snocView [LStmt (GhcPass p) body]
    quals
      = if [LStmt (GhcPass p) body] -> Bool
    forall (t :: * -> *) a. Foldable t => t a -> Bool
    null [LStmt (GhcPass p) body]
    initStmts
           -- If there are no statements in a list comprehension besides the last
           -- one, we simply treat it like a normal list. This does arise
           -- occasionally in code that GHC generates, e.g., in implementations of
           -- 'range' for derived 'Ix' instances for product datatypes with exactly
           -- one constructor (e.g., see #12583).
           then body -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr body
    body
           else SDoc -> Int -> SDoc -> SDoc
    hang (body -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr body
    body SDoc -> SDoc -> SDoc
    <+> SDoc
    vbar) Int
    2 ([LStmt (GhcPass p) body] -> SDoc
    forall (p :: Pass) body.
    (OutputableBndrId p, Outputable body) =>
    [LStmt (GhcPass p) body] -> SDoc
    pprQuals [LStmt (GhcPass p) body]
    initStmts)
      | Bool
    otherwise
      = String -> SDoc -> SDoc
    forall a. HasCallStack => String -> SDoc -> a
    pprPanic String
    "pprComp" ([LStmt (GhcPass p) body] -> SDoc
    forall (p :: Pass) body.
    (OutputableBndrId p, Outputable body) =>
    [LStmt (GhcPass p) body] -> SDoc
    pprQuals [LStmt (GhcPass p) body]
    quals)

    pprQuals :: (OutputableBndrId p, Outputable body)
             => [LStmt (GhcPass p) body] -> SDoc
    -- Show list comprehension qualifiers separated by commas
    pprQuals :: forall (p :: Pass) body.
    (OutputableBndrId p, Outputable body) =>
    [LStmt (GhcPass p) body] -> SDoc
    pprQuals [LStmt (GhcPass p) body]
    quals = [LStmt (GhcPass p) body] -> SDoc
    forall a. Outputable a => [a] -> SDoc
    interpp'SP [LStmt (GhcPass p) body]
    quals

    {-
    ************************************************************************
    *                                                                      *
                    Template Haskell quotation brackets
    *                                                                      *
    ************************************************************************
    -}

    -- | Haskell Splice
    data HsSplice id
       = HsTypedSplice       --  $$z  or $$(f 4)
            (XTypedSplice id)
            SpliceDecoration -- Whether $$( ) variant found, for pretty printing
            (IdP id)         -- A unique name to identify this splice point
            (LHsExpr id)     -- See Note [Pending Splices]

       | HsUntypedSplice     --  $z  or $(f 4)
            (XUntypedSplice id)
            SpliceDecoration -- Whether $( ) variant found, for pretty printing
            (IdP id)         -- A unique name to identify this splice point
            (LHsExpr id)     -- See Note [Pending Splices]

       | HsQuasiQuote        -- See Note [Quasi-quote overview] in GHC.Tc.Gen.Splice
            (XQuasiQuote id)
            (IdP id)         -- Splice point
            (IdP id)         -- Quoter
            SrcSpan          -- The span of the enclosed string
            FastString       -- The enclosed string

       -- AZ:TODO: use XSplice instead of HsSpliced
       | HsSpliced  -- See Note [Delaying modFinalizers in untyped splices] in
                    -- GHC.Rename.Splice.
                    -- This is the result of splicing a splice. It is produced by
                    -- the renamer and consumed by the typechecker. It lives only
                    -- between the two.
            (XSpliced id)
            ThModFinalizers     -- TH finalizers produced by the splice.
            (HsSplicedThing id) -- The result of splicing
       | XSplice !(XXSplice id) -- Note [Trees that Grow] extension point

    newtype HsSplicedT = HsSplicedT DelayedSplice deriving (Typeable HsSplicedT
    Typeable HsSplicedT
    -> (forall (c :: * -> *).
        (forall d b. Data d => c (d -> b) -> d -> c b)
        -> (forall g. g -> c g) -> HsSplicedT -> c HsSplicedT)
    -> (forall (c :: * -> *).
        (forall b r. Data b => c (b -> r) -> c r)
        -> (forall r. r -> c r) -> Constr -> c HsSplicedT)
    -> (HsSplicedT -> Constr)
    -> (HsSplicedT -> DataType)
    -> (forall (t :: * -> *) (c :: * -> *).
        Typeable t =>
        (forall d. Data d => c (t d)) -> Maybe (c HsSplicedT))
    -> (forall (t :: * -> * -> *) (c :: * -> *).
        Typeable t =>
        (forall d e. (Data d, Data e) => c (t d e))
        -> Maybe (c HsSplicedT))
    -> ((forall b. Data b => b -> b) -> HsSplicedT -> HsSplicedT)
    -> (forall r r'.
        (r -> r' -> r)
        -> r -> (forall d. Data d => d -> r') -> HsSplicedT -> r)
    -> (forall r r'.
        (r' -> r -> r)
        -> r -> (forall d. Data d => d -> r') -> HsSplicedT -> r)
    -> (forall u. (forall d. Data d => d -> u) -> HsSplicedT -> [u])
    -> (forall u.
        Int -> (forall d. Data d => d -> u) -> HsSplicedT -> u)
    -> (forall (m :: * -> *).
        Monad m =>
        (forall d. Data d => d -> m d) -> HsSplicedT -> m HsSplicedT)
    -> (forall (m :: * -> *).
        MonadPlus m =>
        (forall d. Data d => d -> m d) -> HsSplicedT -> m HsSplicedT)
    -> (forall (m :: * -> *).
        MonadPlus m =>
        (forall d. Data d => d -> m d) -> HsSplicedT -> m HsSplicedT)
    -> Data HsSplicedT
    HsSplicedT -> DataType
    HsSplicedT -> Constr
    (forall b. Data b => b -> b) -> HsSplicedT -> HsSplicedT
    forall a.
    Typeable a
    -> (forall (c :: * -> *).
        (forall d b. Data d => c (d -> b) -> d -> c b)
        -> (forall g. g -> c g) -> a -> c a)
    -> (forall (c :: * -> *).
        (forall b r. Data b => c (b -> r) -> c r)
        -> (forall r. r -> c r) -> Constr -> c a)
    -> (a -> Constr)
    -> (a -> DataType)
    -> (forall (t :: * -> *) (c :: * -> *).
        Typeable t =>
        (forall d. Data d => c (t d)) -> Maybe (c a))
    -> (forall (t :: * -> * -> *) (c :: * -> *).
        Typeable t =>
        (forall d e. (Data d, Data e) => c (t d e)) -> Maybe (c a))
    -> ((forall b. Data b => b -> b) -> a -> a)
    -> (forall r r'.
        (r -> r' -> r) -> r -> (forall d. Data d => d -> r') -> a -> r)
    -> (forall r r'.
        (r' -> r -> r) -> r -> (forall d. Data d => d -> r') -> a -> r)
    -> (forall u. (forall d. Data d => d -> u) -> a -> [u])
    -> (forall u. Int -> (forall d. Data d => d -> u) -> a -> u)
    -> (forall (m :: * -> *).
        Monad m =>
        (forall d. Data d => d -> m d) -> a -> m a)
    -> (forall (m :: * -> *).
        MonadPlus m =>
        (forall d. Data d => d -> m d) -> a -> m a)
    -> (forall (m :: * -> *).
        MonadPlus m =>
        (forall d. Data d => d -> m d) -> a -> m a)
    -> Data a
    forall u. Int -> (forall d. Data d => d -> u) -> HsSplicedT -> u
    forall u. (forall d. Data d => d -> u) -> HsSplicedT -> [u]
    forall r r'.
    (r -> r' -> r)
    -> r -> (forall d. Data d => d -> r') -> HsSplicedT -> r
    forall r r'.
    (r' -> r -> r)
    -> r -> (forall d. Data d => d -> r') -> HsSplicedT -> r
    forall (m :: * -> *).
    Monad m =>
    (forall d. Data d => d -> m d) -> HsSplicedT -> m HsSplicedT
    forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d) -> HsSplicedT -> m HsSplicedT
    forall (c :: * -> *).
    (forall b r. Data b => c (b -> r) -> c r)
    -> (forall r. r -> c r) -> Constr -> c HsSplicedT
    forall (c :: * -> *).
    (forall d b. Data d => c (d -> b) -> d -> c b)
    -> (forall g. g -> c g) -> HsSplicedT -> c HsSplicedT
    forall (t :: * -> *) (c :: * -> *).
    Typeable t =>
    (forall d. Data d => c (t d)) -> Maybe (c HsSplicedT)
    forall (t :: * -> * -> *) (c :: * -> *).
    Typeable t =>
    (forall d e. (Data d, Data e) => c (t d e)) -> Maybe (c HsSplicedT)
    gmapMo :: forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d) -> HsSplicedT -> m HsSplicedT
    $cgmapMo :: forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d) -> HsSplicedT -> m HsSplicedT
    gmapMp :: forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d) -> HsSplicedT -> m HsSplicedT
    $cgmapMp :: forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d) -> HsSplicedT -> m HsSplicedT
    gmapM :: forall (m :: * -> *).
    Monad m =>
    (forall d. Data d => d -> m d) -> HsSplicedT -> m HsSplicedT
    $cgmapM :: forall (m :: * -> *).
    Monad m =>
    (forall d. Data d => d -> m d) -> HsSplicedT -> m HsSplicedT
    gmapQi :: forall u. Int -> (forall d. Data d => d -> u) -> HsSplicedT -> u
    $cgmapQi :: forall u. Int -> (forall d. Data d => d -> u) -> HsSplicedT -> u
    gmapQ :: forall u. (forall d. Data d => d -> u) -> HsSplicedT -> [u]
    $cgmapQ :: forall u. (forall d. Data d => d -> u) -> HsSplicedT -> [u]
    gmapQr :: forall r r'.
    (r' -> r -> r)
    -> r -> (forall d. Data d => d -> r') -> HsSplicedT -> r
    $cgmapQr :: forall r r'.
    (r' -> r -> r)
    -> r -> (forall d. Data d => d -> r') -> HsSplicedT -> r
    gmapQl :: forall r r'.
    (r -> r' -> r)
    -> r -> (forall d. Data d => d -> r') -> HsSplicedT -> r
    $cgmapQl :: forall r r'.
    (r -> r' -> r)
    -> r -> (forall d. Data d => d -> r') -> HsSplicedT -> r
    gmapT :: (forall b. Data b => b -> b) -> HsSplicedT -> HsSplicedT
    $cgmapT :: (forall b. Data b => b -> b) -> HsSplicedT -> HsSplicedT
    dataCast2 :: forall (t :: * -> * -> *) (c :: * -> *).
    Typeable t =>
    (forall d e. (Data d, Data e) => c (t d e)) -> Maybe (c HsSplicedT)
    $cdataCast2 :: forall (t :: * -> * -> *) (c :: * -> *).
    Typeable t =>
    (forall d e. (Data d, Data e) => c (t d e)) -> Maybe (c HsSplicedT)
    dataCast1 :: forall (t :: * -> *) (c :: * -> *).
    Typeable t =>
    (forall d. Data d => c (t d)) -> Maybe (c HsSplicedT)
    $cdataCast1 :: forall (t :: * -> *) (c :: * -> *).
    Typeable t =>
    (forall d. Data d => c (t d)) -> Maybe (c HsSplicedT)
    dataTypeOf :: HsSplicedT -> DataType
    $cdataTypeOf :: HsSplicedT -> DataType
    toConstr :: HsSplicedT -> Constr
    $ctoConstr :: HsSplicedT -> Constr
    gunfold :: forall (c :: * -> *).
    (forall b r. Data b => c (b -> r) -> c r)
    -> (forall r. r -> c r) -> Constr -> c HsSplicedT
    $cgunfold :: forall (c :: * -> *).
    (forall b r. Data b => c (b -> r) -> c r)
    -> (forall r. r -> c r) -> Constr -> c HsSplicedT
    gfoldl :: forall (c :: * -> *).
    (forall d b. Data d => c (d -> b) -> d -> c b)
    -> (forall g. g -> c g) -> HsSplicedT -> c HsSplicedT
    $cgfoldl :: forall (c :: * -> *).
    (forall d b. Data d => c (d -> b) -> d -> c b)
    -> (forall g. g -> c g) -> HsSplicedT -> c HsSplicedT
    Data)

    type instance XTypedSplice   (GhcPass _) = NoExtField
    type instance XUntypedSplice (GhcPass _) = NoExtField
    type instance XQuasiQuote    (GhcPass _) = NoExtField
    type instance XSpliced       (GhcPass _) = NoExtField
    type instance XXSplice       GhcPs       = NoExtCon
    type instance XXSplice       GhcRn       = NoExtCon
    type instance XXSplice       GhcTc       = HsSplicedT

    -- | A splice can appear with various decorations wrapped around it. This data
    -- type captures explicitly how it was originally written, for use in the pretty
    -- printer.
    data SpliceDecoration
      = DollarSplice  -- ^ $splice or $$splice
      | BareSplice    -- ^ bare splice
      deriving (Typeable SpliceDecoration
    Typeable SpliceDecoration
    -> (forall (c :: * -> *).
        (forall d b. Data d => c (d -> b) -> d -> c b)
        -> (forall g. g -> c g) -> SpliceDecoration -> c SpliceDecoration)
    -> (forall (c :: * -> *).
        (forall b r. Data b => c (b -> r) -> c r)
        -> (forall r. r -> c r) -> Constr -> c SpliceDecoration)
    -> (SpliceDecoration -> Constr)
    -> (SpliceDecoration -> DataType)
    -> (forall (t :: * -> *) (c :: * -> *).
        Typeable t =>
        (forall d. Data d => c (t d)) -> Maybe (c SpliceDecoration))
    -> (forall (t :: * -> * -> *) (c :: * -> *).
        Typeable t =>
        (forall d e. (Data d, Data e) => c (t d e))
        -> Maybe (c SpliceDecoration))
    -> ((forall b. Data b => b -> b)
        -> SpliceDecoration -> SpliceDecoration)
    -> (forall r r'.
        (r -> r' -> r)
        -> r -> (forall d. Data d => d -> r') -> SpliceDecoration -> r)
    -> (forall r r'.
        (r' -> r -> r)
        -> r -> (forall d. Data d => d -> r') -> SpliceDecoration -> r)
    -> (forall u.
        (forall d. Data d => d -> u) -> SpliceDecoration -> [u])
    -> (forall u.
        Int -> (forall d. Data d => d -> u) -> SpliceDecoration -> u)
    -> (forall (m :: * -> *).
        Monad m =>
        (forall d. Data d => d -> m d)
        -> SpliceDecoration -> m SpliceDecoration)
    -> (forall (m :: * -> *).
        MonadPlus m =>
        (forall d. Data d => d -> m d)
        -> SpliceDecoration -> m SpliceDecoration)
    -> (forall (m :: * -> *).
        MonadPlus m =>
        (forall d. Data d => d -> m d)
        -> SpliceDecoration -> m SpliceDecoration)
    -> Data SpliceDecoration
    SpliceDecoration -> DataType
    SpliceDecoration -> Constr
    (forall b. Data b => b -> b)
    -> SpliceDecoration -> SpliceDecoration
    forall a.
    Typeable a
    -> (forall (c :: * -> *).
        (forall d b. Data d => c (d -> b) -> d -> c b)
        -> (forall g. g -> c g) -> a -> c a)
    -> (forall (c :: * -> *).
        (forall b r. Data b => c (b -> r) -> c r)
        -> (forall r. r -> c r) -> Constr -> c a)
    -> (a -> Constr)
    -> (a -> DataType)
    -> (forall (t :: * -> *) (c :: * -> *).
        Typeable t =>
        (forall d. Data d => c (t d)) -> Maybe (c a))
    -> (forall (t :: * -> * -> *) (c :: * -> *).
        Typeable t =>
        (forall d e. (Data d, Data e) => c (t d e)) -> Maybe (c a))
    -> ((forall b. Data b => b -> b) -> a -> a)
    -> (forall r r'.
        (r -> r' -> r) -> r -> (forall d. Data d => d -> r') -> a -> r)
    -> (forall r r'.
        (r' -> r -> r) -> r -> (forall d. Data d => d -> r') -> a -> r)
    -> (forall u. (forall d. Data d => d -> u) -> a -> [u])
    -> (forall u. Int -> (forall d. Data d => d -> u) -> a -> u)
    -> (forall (m :: * -> *).
        Monad m =>
        (forall d. Data d => d -> m d) -> a -> m a)
    -> (forall (m :: * -> *).
        MonadPlus m =>
        (forall d. Data d => d -> m d) -> a -> m a)
    -> (forall (m :: * -> *).
        MonadPlus m =>
        (forall d. Data d => d -> m d) -> a -> m a)
    -> Data a
    forall u.
    Int -> (forall d. Data d => d -> u) -> SpliceDecoration -> u
    forall u. (forall d. Data d => d -> u) -> SpliceDecoration -> [u]
    forall r r'.
    (r -> r' -> r)
    -> r -> (forall d. Data d => d -> r') -> SpliceDecoration -> r
    forall r r'.
    (r' -> r -> r)
    -> r -> (forall d. Data d => d -> r') -> SpliceDecoration -> r
    forall (m :: * -> *).
    Monad m =>
    (forall d. Data d => d -> m d)
    -> SpliceDecoration -> m SpliceDecoration
    forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d)
    -> SpliceDecoration -> m SpliceDecoration
    forall (c :: * -> *).
    (forall b r. Data b => c (b -> r) -> c r)
    -> (forall r. r -> c r) -> Constr -> c SpliceDecoration
    forall (c :: * -> *).
    (forall d b. Data d => c (d -> b) -> d -> c b)
    -> (forall g. g -> c g) -> SpliceDecoration -> c SpliceDecoration
    forall (t :: * -> *) (c :: * -> *).
    Typeable t =>
    (forall d. Data d => c (t d)) -> Maybe (c SpliceDecoration)
    forall (t :: * -> * -> *) (c :: * -> *).
    Typeable t =>
    (forall d e. (Data d, Data e) => c (t d e))
    -> Maybe (c SpliceDecoration)
    gmapMo :: forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d)
    -> SpliceDecoration -> m SpliceDecoration
    $cgmapMo :: forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d)
    -> SpliceDecoration -> m SpliceDecoration
    gmapMp :: forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d)
    -> SpliceDecoration -> m SpliceDecoration
    $cgmapMp :: forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d)
    -> SpliceDecoration -> m SpliceDecoration
    gmapM :: forall (m :: * -> *).
    Monad m =>
    (forall d. Data d => d -> m d)
    -> SpliceDecoration -> m SpliceDecoration
    $cgmapM :: forall (m :: * -> *).
    Monad m =>
    (forall d. Data d => d -> m d)
    -> SpliceDecoration -> m SpliceDecoration
    gmapQi :: forall u.
    Int -> (forall d. Data d => d -> u) -> SpliceDecoration -> u
    $cgmapQi :: forall u.
    Int -> (forall d. Data d => d -> u) -> SpliceDecoration -> u
    gmapQ :: forall u. (forall d. Data d => d -> u) -> SpliceDecoration -> [u]
    $cgmapQ :: forall u. (forall d. Data d => d -> u) -> SpliceDecoration -> [u]
    gmapQr :: forall r r'.
    (r' -> r -> r)
    -> r -> (forall d. Data d => d -> r') -> SpliceDecoration -> r
    $cgmapQr :: forall r r'.
    (r' -> r -> r)
    -> r -> (forall d. Data d => d -> r') -> SpliceDecoration -> r
    gmapQl :: forall r r'.
    (r -> r' -> r)
    -> r -> (forall d. Data d => d -> r') -> SpliceDecoration -> r
    $cgmapQl :: forall r r'.
    (r -> r' -> r)
    -> r -> (forall d. Data d => d -> r') -> SpliceDecoration -> r
    gmapT :: (forall b. Data b => b -> b)
    -> SpliceDecoration -> SpliceDecoration
    $cgmapT :: (forall b. Data b => b -> b)
    -> SpliceDecoration -> SpliceDecoration
    dataCast2 :: forall (t :: * -> * -> *) (c :: * -> *).
    Typeable t =>
    (forall d e. (Data d, Data e) => c (t d e))
    -> Maybe (c SpliceDecoration)
    $cdataCast2 :: forall (t :: * -> * -> *) (c :: * -> *).
    Typeable t =>
    (forall d e. (Data d, Data e) => c (t d e))
    -> Maybe (c SpliceDecoration)
    dataCast1 :: forall (t :: * -> *) (c :: * -> *).
    Typeable t =>
    (forall d. Data d => c (t d)) -> Maybe (c SpliceDecoration)
    $cdataCast1 :: forall (t :: * -> *) (c :: * -> *).
    Typeable t =>
    (forall d. Data d => c (t d)) -> Maybe (c SpliceDecoration)
    dataTypeOf :: SpliceDecoration -> DataType
    $cdataTypeOf :: SpliceDecoration -> DataType
    toConstr :: SpliceDecoration -> Constr
    $ctoConstr :: SpliceDecoration -> Constr
    gunfold :: forall (c :: * -> *).
    (forall b r. Data b => c (b -> r) -> c r)
    -> (forall r. r -> c r) -> Constr -> c SpliceDecoration
    $cgunfold :: forall (c :: * -> *).
    (forall b r. Data b => c (b -> r) -> c r)
    -> (forall r. r -> c r) -> Constr -> c SpliceDecoration
    gfoldl :: forall (c :: * -> *).
    (forall d b. Data d => c (d -> b) -> d -> c b)
    -> (forall g. g -> c g) -> SpliceDecoration -> c SpliceDecoration
    $cgfoldl :: forall (c :: * -> *).
    (forall d b. Data d => c (d -> b) -> d -> c b)
    -> (forall g. g -> c g) -> SpliceDecoration -> c SpliceDecoration
    Data, SpliceDecoration -> SpliceDecoration -> Bool
    (SpliceDecoration -> SpliceDecoration -> Bool)
    -> (SpliceDecoration -> SpliceDecoration -> Bool)
    -> Eq SpliceDecoration
    forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
    /= :: SpliceDecoration -> SpliceDecoration -> Bool
    $c/= :: SpliceDecoration -> SpliceDecoration -> Bool
    == :: SpliceDecoration -> SpliceDecoration -> Bool
    $c== :: SpliceDecoration -> SpliceDecoration -> Bool
    Eq, Int -> SpliceDecoration -> ShowS
    [SpliceDecoration] -> ShowS
    SpliceDecoration -> String
    (Int -> SpliceDecoration -> ShowS)
    -> (SpliceDecoration -> String)
    -> ([SpliceDecoration] -> ShowS)
    -> Show SpliceDecoration
    forall a.
    (Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
    showList :: [SpliceDecoration] -> ShowS
    $cshowList :: [SpliceDecoration] -> ShowS
    show :: SpliceDecoration -> String
    $cshow :: SpliceDecoration -> String
    showsPrec :: Int -> SpliceDecoration -> ShowS
    $cshowsPrec :: Int -> SpliceDecoration -> ShowS
    Show)

    instance Outputable SpliceDecoration where
      ppr :: SpliceDecoration -> SDoc
    ppr SpliceDecoration
    x = String -> SDoc
    text (String -> SDoc) -> String -> SDoc
    forall a b. (a -> b) -> a -> b
    $ SpliceDecoration -> String
    forall a. Show a => a -> String
    show SpliceDecoration
    x

    isTypedSplice :: HsSplice id -> Bool
    isTypedSplice :: forall id. HsSplice id -> Bool
    isTypedSplice (HsTypedSplice {}) = Bool
    True
    isTypedSplice HsSplice id
    _                  = Bool
    False   -- Quasi-quotes are untyped splices

    -- | Finalizers produced by a splice with
    -- 'Language.Haskell.TH.Syntax.addModFinalizer'
    --
    -- See Note [Delaying modFinalizers in untyped splices] in GHC.Rename.Splice. For how
    -- this is used.
    --
    newtype ThModFinalizers = ThModFinalizers [ForeignRef (TH.Q ())]

    -- A Data instance which ignores the argument of 'ThModFinalizers'.
    instance Data ThModFinalizers where
      gunfold :: forall (c :: * -> *).
    (forall b r. Data b => c (b -> r) -> c r)
    -> (forall r. r -> c r) -> Constr -> c ThModFinalizers
    gunfold forall b r. Data b => c (b -> r) -> c r
    _ forall r. r -> c r
    z Constr
    _ = ThModFinalizers -> c ThModFinalizers
    forall r. r -> c r
    z (ThModFinalizers -> c ThModFinalizers)
    -> ThModFinalizers -> c ThModFinalizers
    forall a b. (a -> b) -> a -> b
    $ [ForeignRef (Q ())] -> ThModFinalizers
    ThModFinalizers []
      toConstr :: ThModFinalizers -> Constr
    toConstr  ThModFinalizers
    a   = DataType -> String -> [String] -> Fixity -> Constr
    mkConstr (ThModFinalizers -> DataType
    forall a. Data a => a -> DataType
    dataTypeOf ThModFinalizers
    a) String
    "ThModFinalizers" [] Fixity
    Data.Prefix
      dataTypeOf :: ThModFinalizers -> DataType
    dataTypeOf ThModFinalizers
    a  = String -> [Constr] -> DataType
    mkDataType String
    "HsExpr.ThModFinalizers" [ThModFinalizers -> Constr
    forall a. Data a => a -> Constr
    toConstr ThModFinalizers
    a]

    -- See Note [Running typed splices in the zonker]
    -- These are the arguments that are passed to `GHC.Tc.Gen.Splice.runTopSplice`
    data DelayedSplice =
      DelayedSplice
        TcLclEnv          -- The local environment to run the splice in
        (LHsExpr GhcRn)   -- The original renamed expression
        TcType            -- The result type of running the splice, unzonked
        (LHsExpr GhcTc)   -- The typechecked expression to run and splice in the result

    -- A Data instance which ignores the argument of 'DelayedSplice'.
    instance Data DelayedSplice where
      gunfold :: forall (c :: * -> *).
    (forall b r. Data b => c (b -> r) -> c r)
    -> (forall r. r -> c r) -> Constr -> c DelayedSplice
    gunfold forall b r. Data b => c (b -> r) -> c r
    _ forall r. r -> c r
    _ Constr
    _ = String -> c DelayedSplice
    forall a. String -> a
    panic String
    "DelayedSplice"
      toConstr :: DelayedSplice -> Constr
    toConstr  DelayedSplice
    a   = DataType -> String -> [String] -> Fixity -> Constr
    mkConstr (DelayedSplice -> DataType
    forall a. Data a => a -> DataType
    dataTypeOf DelayedSplice
    a) String
    "DelayedSplice" [] Fixity
    Data.Prefix
      dataTypeOf :: DelayedSplice -> DataType
    dataTypeOf DelayedSplice
    a  = String -> [Constr] -> DataType
    mkDataType String
    "HsExpr.DelayedSplice" [DelayedSplice -> Constr
    forall a. Data a => a -> Constr
    toConstr DelayedSplice
    a]

    -- | Haskell Spliced Thing
    --
    -- Values that can result from running a splice.
    data HsSplicedThing id
        = HsSplicedExpr (HsExpr id) -- ^ Haskell Spliced Expression
        | HsSplicedTy   (HsType id) -- ^ Haskell Spliced Type
        | HsSplicedPat  (Pat id)    -- ^ Haskell Spliced Pattern

    -- See Note [Pending Splices]
    type SplicePointName = Name

    -- | Pending Renamer Splice
    data PendingRnSplice
      = PendingRnSplice UntypedSpliceFlavour SplicePointName (LHsExpr GhcRn)

    data UntypedSpliceFlavour
      = UntypedExpSplice
      | UntypedPatSplice
      | UntypedTypeSplice
      | UntypedDeclSplice
      deriving Typeable UntypedSpliceFlavour
    Typeable UntypedSpliceFlavour
    -> (forall (c :: * -> *).
        (forall d b. Data d => c (d -> b) -> d -> c b)
        -> (forall g. g -> c g)
        -> UntypedSpliceFlavour
        -> c UntypedSpliceFlavour)
    -> (forall (c :: * -> *).
        (forall b r. Data b => c (b -> r) -> c r)
        -> (forall r. r -> c r) -> Constr -> c UntypedSpliceFlavour)
    -> (UntypedSpliceFlavour -> Constr)
    -> (UntypedSpliceFlavour -> DataType)
    -> (forall (t :: * -> *) (c :: * -> *).
        Typeable t =>
        (forall d. Data d => c (t d)) -> Maybe (c UntypedSpliceFlavour))
    -> (forall (t :: * -> * -> *) (c :: * -> *).
        Typeable t =>
        (forall d e. (Data d, Data e) => c (t d e))
        -> Maybe (c UntypedSpliceFlavour))
    -> ((forall b. Data b => b -> b)
        -> UntypedSpliceFlavour -> UntypedSpliceFlavour)
    -> (forall r r'.
        (r -> r' -> r)
        -> r -> (forall d. Data d => d -> r') -> UntypedSpliceFlavour -> r)
    -> (forall r r'.
        (r' -> r -> r)
        -> r -> (forall d. Data d => d -> r') -> UntypedSpliceFlavour -> r)
    -> (forall u.
        (forall d. Data d => d -> u) -> UntypedSpliceFlavour -> [u])
    -> (forall u.
        Int -> (forall d. Data d => d -> u) -> UntypedSpliceFlavour -> u)
    -> (forall (m :: * -> *).
        Monad m =>
        (forall d. Data d => d -> m d)
        -> UntypedSpliceFlavour -> m UntypedSpliceFlavour)
    -> (forall (m :: * -> *).
        MonadPlus m =>
        (forall d. Data d => d -> m d)
        -> UntypedSpliceFlavour -> m UntypedSpliceFlavour)
    -> (forall (m :: * -> *).
        MonadPlus m =>
        (forall d. Data d => d -> m d)
        -> UntypedSpliceFlavour -> m UntypedSpliceFlavour)
    -> Data UntypedSpliceFlavour
    UntypedSpliceFlavour -> DataType
    UntypedSpliceFlavour -> Constr
    (forall b. Data b => b -> b)
    -> UntypedSpliceFlavour -> UntypedSpliceFlavour
    forall a.
    Typeable a
    -> (forall (c :: * -> *).
        (forall d b. Data d => c (d -> b) -> d -> c b)
        -> (forall g. g -> c g) -> a -> c a)
    -> (forall (c :: * -> *).
        (forall b r. Data b => c (b -> r) -> c r)
        -> (forall r. r -> c r) -> Constr -> c a)
    -> (a -> Constr)
    -> (a -> DataType)
    -> (forall (t :: * -> *) (c :: * -> *).
        Typeable t =>
        (forall d. Data d => c (t d)) -> Maybe (c a))
    -> (forall (t :: * -> * -> *) (c :: * -> *).
        Typeable t =>
        (forall d e. (Data d, Data e) => c (t d e)) -> Maybe (c a))
    -> ((forall b. Data b => b -> b) -> a -> a)
    -> (forall r r'.
        (r -> r' -> r) -> r -> (forall d. Data d => d -> r') -> a -> r)
    -> (forall r r'.
        (r' -> r -> r) -> r -> (forall d. Data d => d -> r') -> a -> r)
    -> (forall u. (forall d. Data d => d -> u) -> a -> [u])
    -> (forall u. Int -> (forall d. Data d => d -> u) -> a -> u)
    -> (forall (m :: * -> *).
        Monad m =>
        (forall d. Data d => d -> m d) -> a -> m a)
    -> (forall (m :: * -> *).
        MonadPlus m =>
        (forall d. Data d => d -> m d) -> a -> m a)
    -> (forall (m :: * -> *).
        MonadPlus m =>
        (forall d. Data d => d -> m d) -> a -> m a)
    -> Data a
    forall u.
    Int -> (forall d. Data d => d -> u) -> UntypedSpliceFlavour -> u
    forall u.
    (forall d. Data d => d -> u) -> UntypedSpliceFlavour -> [u]
    forall r r'.
    (r -> r' -> r)
    -> r -> (forall d. Data d => d -> r') -> UntypedSpliceFlavour -> r
    forall r r'.
    (r' -> r -> r)
    -> r -> (forall d. Data d => d -> r') -> UntypedSpliceFlavour -> r
    forall (m :: * -> *).
    Monad m =>
    (forall d. Data d => d -> m d)
    -> UntypedSpliceFlavour -> m UntypedSpliceFlavour
    forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d)
    -> UntypedSpliceFlavour -> m UntypedSpliceFlavour
    forall (c :: * -> *).
    (forall b r. Data b => c (b -> r) -> c r)
    -> (forall r. r -> c r) -> Constr -> c UntypedSpliceFlavour
    forall (c :: * -> *).
    (forall d b. Data d => c (d -> b) -> d -> c b)
    -> (forall g. g -> c g)
    -> UntypedSpliceFlavour
    -> c UntypedSpliceFlavour
    forall (t :: * -> *) (c :: * -> *).
    Typeable t =>
    (forall d. Data d => c (t d)) -> Maybe (c UntypedSpliceFlavour)
    forall (t :: * -> * -> *) (c :: * -> *).
    Typeable t =>
    (forall d e. (Data d, Data e) => c (t d e))
    -> Maybe (c UntypedSpliceFlavour)
    gmapMo :: forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d)
    -> UntypedSpliceFlavour -> m UntypedSpliceFlavour
    $cgmapMo :: forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d)
    -> UntypedSpliceFlavour -> m UntypedSpliceFlavour
    gmapMp :: forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d)
    -> UntypedSpliceFlavour -> m UntypedSpliceFlavour
    $cgmapMp :: forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d)
    -> UntypedSpliceFlavour -> m UntypedSpliceFlavour
    gmapM :: forall (m :: * -> *).
    Monad m =>
    (forall d. Data d => d -> m d)
    -> UntypedSpliceFlavour -> m UntypedSpliceFlavour
    $cgmapM :: forall (m :: * -> *).
    Monad m =>
    (forall d. Data d => d -> m d)
    -> UntypedSpliceFlavour -> m UntypedSpliceFlavour
    gmapQi :: forall u.
    Int -> (forall d. Data d => d -> u) -> UntypedSpliceFlavour -> u
    $cgmapQi :: forall u.
    Int -> (forall d. Data d => d -> u) -> UntypedSpliceFlavour -> u
    gmapQ :: forall u.
    (forall d. Data d => d -> u) -> UntypedSpliceFlavour -> [u]
    $cgmapQ :: forall u.
    (forall d. Data d => d -> u) -> UntypedSpliceFlavour -> [u]
    gmapQr :: forall r r'.
    (r' -> r -> r)
    -> r -> (forall d. Data d => d -> r') -> UntypedSpliceFlavour -> r
    $cgmapQr :: forall r r'.
    (r' -> r -> r)
    -> r -> (forall d. Data d => d -> r') -> UntypedSpliceFlavour -> r
    gmapQl :: forall r r'.
    (r -> r' -> r)
    -> r -> (forall d. Data d => d -> r') -> UntypedSpliceFlavour -> r
    $cgmapQl :: forall r r'.
    (r -> r' -> r)
    -> r -> (forall d. Data d => d -> r') -> UntypedSpliceFlavour -> r
    gmapT :: (forall b. Data b => b -> b)
    -> UntypedSpliceFlavour -> UntypedSpliceFlavour
    $cgmapT :: (forall b. Data b => b -> b)
    -> UntypedSpliceFlavour -> UntypedSpliceFlavour
    dataCast2 :: forall (t :: * -> * -> *) (c :: * -> *).
    Typeable t =>
    (forall d e. (Data d, Data e) => c (t d e))
    -> Maybe (c UntypedSpliceFlavour)
    $cdataCast2 :: forall (t :: * -> * -> *) (c :: * -> *).
    Typeable t =>
    (forall d e. (Data d, Data e) => c (t d e))
    -> Maybe (c UntypedSpliceFlavour)
    dataCast1 :: forall (t :: * -> *) (c :: * -> *).
    Typeable t =>
    (forall d. Data d => c (t d)) -> Maybe (c UntypedSpliceFlavour)
    $cdataCast1 :: forall (t :: * -> *) (c :: * -> *).
    Typeable t =>
    (forall d. Data d => c (t d)) -> Maybe (c UntypedSpliceFlavour)
    dataTypeOf :: UntypedSpliceFlavour -> DataType
    $cdataTypeOf :: UntypedSpliceFlavour -> DataType
    toConstr :: UntypedSpliceFlavour -> Constr
    $ctoConstr :: UntypedSpliceFlavour -> Constr
    gunfold :: forall (c :: * -> *).
    (forall b r. Data b => c (b -> r) -> c r)
    -> (forall r. r -> c r) -> Constr -> c UntypedSpliceFlavour
    $cgunfold :: forall (c :: * -> *).
    (forall b r. Data b => c (b -> r) -> c r)
    -> (forall r. r -> c r) -> Constr -> c UntypedSpliceFlavour
    gfoldl :: forall (c :: * -> *).
    (forall d b. Data d => c (d -> b) -> d -> c b)
    -> (forall g. g -> c g)
    -> UntypedSpliceFlavour
    -> c UntypedSpliceFlavour
    $cgfoldl :: forall (c :: * -> *).
    (forall d b. Data d => c (d -> b) -> d -> c b)
    -> (forall g. g -> c g)
    -> UntypedSpliceFlavour
    -> c UntypedSpliceFlavour
    Data

    -- | Pending Type-checker Splice
    data PendingTcSplice
      = PendingTcSplice SplicePointName (LHsExpr GhcTc)

    {-
    Note [Pending Splices]
    ~~~~~~~~~~~~~~~~~~~~~~
    When we rename an untyped bracket, we name and lift out all the nested
    splices, so that when the typechecker hits the bracket, it can
    typecheck those nested splices without having to walk over the untyped
    bracket code.  So for example
        [| f $(g x) |]
    looks like

        HsBracket (HsApp (HsVar "f") (HsSpliceE _ (g x)))

    which the renamer rewrites to

        HsRnBracketOut (HsApp (HsVar f) (HsSpliceE sn (g x)))
                       [PendingRnSplice UntypedExpSplice sn (g x)]

    * The 'sn' is the Name of the splice point, the SplicePointName

    * The PendingRnExpSplice gives the splice that splice-point name maps to;
      and the typechecker can now conveniently find these sub-expressions

    * The other copy of the splice, in the second argument of HsSpliceE
                                    in the renamed first arg of HsRnBracketOut
      is used only for pretty printing

    There are four varieties of pending splices generated by the renamer,
    distinguished by their UntypedSpliceFlavour

     * Pending expression splices (UntypedExpSplice), e.g.,
           [|$(f x) + 2|]

       UntypedExpSplice is also used for
         * quasi-quotes, where the pending expression expands to
              $(quoter "...blah...")
           (see GHC.Rename.Splice.makePending, HsQuasiQuote case)

         * cross-stage lifting, where the pending expression expands to
              $(lift x)
           (see GHC.Rename.Splice.checkCrossStageLifting)

     * Pending pattern splices (UntypedPatSplice), e.g.,
           [| \$(f x) -> x |]

     * Pending type splices (UntypedTypeSplice), e.g.,
           [| f :: $(g x) |]

     * Pending declaration (UntypedDeclSplice), e.g.,
           [| let $(f x) in ... |]

    There is a fifth variety of pending splice, which is generated by the type
    checker:

      * Pending *typed* expression splices, (PendingTcSplice), e.g.,
            [||1 + $$(f 2)||]

    It would be possible to eliminate HsRnBracketOut and use HsBracketOut for the
    output of the renamer. However, when pretty printing the output of the renamer,
    e.g., in a type error message, we *do not* want to print out the pending
    splices. In contrast, when pretty printing the output of the type checker, we
    *do* want to print the pending splices. So splitting them up seems to make
    sense, although I hate to add another constructor to HsExpr.
    -}

    instance OutputableBndrId p
           => Outputable (HsSplicedThing (GhcPass p)) where
      ppr :: HsSplicedThing (GhcPass p) -> SDoc
    ppr (HsSplicedExpr HsExpr (GhcPass p)
    e) = HsExpr (GhcPass p) -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    HsExpr (GhcPass p) -> SDoc
    ppr_expr HsExpr (GhcPass p)
    e
      ppr (HsSplicedTy   HsType (GhcPass p)
    t) = HsType (GhcPass p) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr HsType (GhcPass p)
    t
      ppr (HsSplicedPat  Pat (GhcPass p)
    p) = Pat (GhcPass p) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr Pat (GhcPass p)
    p

    instance (OutputableBndrId p) => Outputable (HsSplice (GhcPass p)) where
      ppr :: HsSplice (GhcPass p) -> SDoc
    ppr HsSplice (GhcPass p)
    s = HsSplice (GhcPass p) -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    HsSplice (GhcPass p) -> SDoc
    pprSplice HsSplice (GhcPass p)
    s

    pprPendingSplice :: (OutputableBndrId p)
                     => SplicePointName -> LHsExpr (GhcPass p) -> SDoc
    pprPendingSplice :: forall (p :: Pass).
    OutputableBndrId p =>
    Name -> LHsExpr (GhcPass p) -> SDoc
    pprPendingSplice Name
    n LHsExpr (GhcPass p)
    e = SDoc -> SDoc
    angleBrackets (Name -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr Name
    n SDoc -> SDoc -> SDoc
    <> SDoc
    comma SDoc -> SDoc -> SDoc
    <+> LHsExpr (GhcPass p) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr (LHsExpr (GhcPass p) -> LHsExpr (GhcPass p)
    forall (p :: Pass). LHsExpr (GhcPass p) -> LHsExpr (GhcPass p)
    stripParensLHsExpr LHsExpr (GhcPass p)
    e))

    pprSpliceDecl ::  (OutputableBndrId p)
              => HsSplice (GhcPass p) -> SpliceExplicitFlag -> SDoc
    pprSpliceDecl :: forall (p :: Pass).
    OutputableBndrId p =>
    HsSplice (GhcPass p) -> SpliceExplicitFlag -> SDoc
    pprSpliceDecl e :: HsSplice (GhcPass p)
    e@HsQuasiQuote{} SpliceExplicitFlag
    _ = HsSplice (GhcPass p) -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    HsSplice (GhcPass p) -> SDoc
    pprSplice HsSplice (GhcPass p)
    e
    pprSpliceDecl HsSplice (GhcPass p)
    e SpliceExplicitFlag
    ExplicitSplice   = String -> SDoc
    text String
    "$" SDoc -> SDoc -> SDoc
    <> HsSplice (GhcPass p) -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    HsSplice (GhcPass p) -> SDoc
    ppr_splice_decl HsSplice (GhcPass p)
    e
    pprSpliceDecl HsSplice (GhcPass p)
    e SpliceExplicitFlag
    ImplicitSplice   = HsSplice (GhcPass p) -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    HsSplice (GhcPass p) -> SDoc
    ppr_splice_decl HsSplice (GhcPass p)
    e

    ppr_splice_decl :: (OutputableBndrId p)
                    => HsSplice (GhcPass p) -> SDoc
    ppr_splice_decl :: forall (p :: Pass).
    OutputableBndrId p =>
    HsSplice (GhcPass p) -> SDoc
    ppr_splice_decl (HsUntypedSplice XUntypedSplice (GhcPass p)
    _ SpliceDecoration
    _ IdP (GhcPass p)
    n LHsExpr (GhcPass p)
    e) = SDoc -> IdP (GhcPass p) -> LHsExpr (GhcPass p) -> SDoc -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    SDoc -> IdP (GhcPass p) -> LHsExpr (GhcPass p) -> SDoc -> SDoc
    ppr_splice SDoc
    empty IdP (GhcPass p)
    n LHsExpr (GhcPass p)
    e SDoc
    empty
    ppr_splice_decl HsSplice (GhcPass p)
    e = HsSplice (GhcPass p) -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    HsSplice (GhcPass p) -> SDoc
    pprSplice HsSplice (GhcPass p)
    e

    pprSplice :: forall p. (OutputableBndrId p) => HsSplice (GhcPass p) -> SDoc
    pprSplice :: forall (p :: Pass).
    OutputableBndrId p =>
    HsSplice (GhcPass p) -> SDoc
    pprSplice (HsTypedSplice XTypedSplice (GhcPass p)
    _ SpliceDecoration
    DollarSplice IdP (GhcPass p)
    n LHsExpr (GhcPass p)
    e)
      = SDoc -> IdP (GhcPass p) -> LHsExpr (GhcPass p) -> SDoc -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    SDoc -> IdP (GhcPass p) -> LHsExpr (GhcPass p) -> SDoc -> SDoc
    ppr_splice (String -> SDoc
    text String
    "$$") IdP (GhcPass p)
    n LHsExpr (GhcPass p)
    e SDoc
    empty
    pprSplice (HsTypedSplice XTypedSplice (GhcPass p)
    _ SpliceDecoration
    BareSplice IdP (GhcPass p)
    _ LHsExpr (GhcPass p)
    _ )
      = String -> SDoc
    forall a. String -> a
    panic String
    "Bare typed splice"  -- impossible
    pprSplice (HsUntypedSplice XUntypedSplice (GhcPass p)
    _ SpliceDecoration
    DollarSplice IdP (GhcPass p)
    n LHsExpr (GhcPass p)
    e)
      = SDoc -> IdP (GhcPass p) -> LHsExpr (GhcPass p) -> SDoc -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    SDoc -> IdP (GhcPass p) -> LHsExpr (GhcPass p) -> SDoc -> SDoc
    ppr_splice (String -> SDoc
    text String
    "$")  IdP (GhcPass p)
    n LHsExpr (GhcPass p)
    e SDoc
    empty
    pprSplice (HsUntypedSplice XUntypedSplice (GhcPass p)
    _ SpliceDecoration
    BareSplice IdP (GhcPass p)
    n LHsExpr (GhcPass p)
    e)
      = SDoc -> IdP (GhcPass p) -> LHsExpr (GhcPass p) -> SDoc -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    SDoc -> IdP (GhcPass p) -> LHsExpr (GhcPass p) -> SDoc -> SDoc
    ppr_splice SDoc
    empty  IdP (GhcPass p)
    n LHsExpr (GhcPass p)
    e SDoc
    empty
    pprSplice (HsQuasiQuote XQuasiQuote (GhcPass p)
    _ IdP (GhcPass p)
    n IdP (GhcPass p)
    q SrcSpan
    _ FastString
    s)      = IdGhcP p -> IdGhcP p -> FastString -> SDoc
    forall p. OutputableBndr p => p -> p -> FastString -> SDoc
    ppr_quasi IdGhcP p
    IdP (GhcPass p)
    n IdGhcP p
    IdP (GhcPass p)
    q FastString
    s
    pprSplice (HsSpliced XSpliced (GhcPass p)
    _ ThModFinalizers
    _ HsSplicedThing (GhcPass p)
    thing)         = HsSplicedThing (GhcPass p) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr HsSplicedThing (GhcPass p)
    thing
    pprSplice (XSplice XXSplice (GhcPass p)
    x)                   = case forall (p :: Pass). IsPass p => GhcPass p
    ghcPass @p of
    #if __GLASGOW_HASKELL__ < 811
                                                GhcPs -> noExtCon x
                                                GhcRn -> noExtCon x
    #endif
                                                GhcPass p
    GhcTc -> case XXSplice (GhcPass p)
    x of
                                                           HsSplicedT DelayedSplice
    _ -> String -> SDoc
    text String
    "Unevaluated typed splice"

    ppr_quasi :: OutputableBndr p => p -> p -> FastString -> SDoc
    ppr_quasi :: forall p. OutputableBndr p => p -> p -> FastString -> SDoc
    ppr_quasi p
    n p
    quoter FastString
    quote = SDoc -> SDoc
    whenPprDebug (SDoc -> SDoc
    brackets (p -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr p
    n)) SDoc -> SDoc -> SDoc
    <>
                               Char -> SDoc
    char Char
    '[' SDoc -> SDoc -> SDoc
    <> p -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr p
    quoter SDoc -> SDoc -> SDoc
    <> SDoc
    vbar SDoc -> SDoc -> SDoc
    <>
                               FastString -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr FastString
    quote SDoc -> SDoc -> SDoc
    <> String -> SDoc
    text String
    "|]"

    ppr_splice :: (OutputableBndrId p)
               => SDoc -> (IdP (GhcPass p)) -> LHsExpr (GhcPass p) -> SDoc -> SDoc
    ppr_splice :: forall (p :: Pass).
    OutputableBndrId p =>
    SDoc -> IdP (GhcPass p) -> LHsExpr (GhcPass p) -> SDoc -> SDoc
    ppr_splice SDoc
    herald IdP (GhcPass p)
    n LHsExpr (GhcPass p)
    e SDoc
    trail
        = SDoc
    herald SDoc -> SDoc -> SDoc
    <> SDoc -> SDoc
    whenPprDebug (SDoc -> SDoc
    brackets (IdGhcP p -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr IdGhcP p
    IdP (GhcPass p)
    n)) SDoc -> SDoc -> SDoc
    <> LHsExpr (GhcPass p) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr LHsExpr (GhcPass p)
    e SDoc -> SDoc -> SDoc
    <> SDoc
    trail

    -- | Haskell Bracket
    data HsBracket p
      = ExpBr  (XExpBr p)   (LHsExpr p)    -- [|  expr  |]
      | PatBr  (XPatBr p)   (LPat p)      -- [p| pat   |]
      | DecBrL (XDecBrL p)  [LHsDecl p]   -- [d| decls |]; result of parser
      | DecBrG (XDecBrG p)  (HsGroup p)   -- [d| decls |]; result of renamer
      | TypBr  (XTypBr p)   (LHsType p)   -- [t| type  |]
      | VarBr  (XVarBr p)   Bool (IdP p)  -- True: 'x, False: ''T
                                    -- (The Bool flag is used only in pprHsBracket)
      | TExpBr (XTExpBr p) (LHsExpr p)    -- [||  expr  ||]
      | XBracket !(XXBracket p)           -- Note [Trees that Grow] extension point

    type instance XExpBr      (GhcPass _) = NoExtField
    type instance XPatBr      (GhcPass _) = NoExtField
    type instance XDecBrL     (GhcPass _) = NoExtField
    type instance XDecBrG     (GhcPass _) = NoExtField
    type instance XTypBr      (GhcPass _) = NoExtField
    type instance XVarBr      (GhcPass _) = NoExtField
    type instance XTExpBr     (GhcPass _) = NoExtField
    type instance XXBracket   (GhcPass _) = NoExtCon

    isTypedBracket :: HsBracket id -> Bool
    isTypedBracket :: forall id. HsBracket id -> Bool
    isTypedBracket (TExpBr {}) = Bool
    True
    isTypedBracket HsBracket id
    _           = Bool
    False

    instance OutputableBndrId p
              => Outputable (HsBracket (GhcPass p)) where
      ppr :: HsBracket (GhcPass p) -> SDoc
    ppr = HsBracket (GhcPass p) -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    HsBracket (GhcPass p) -> SDoc
    pprHsBracket

    pprHsBracket :: (OutputableBndrId p) => HsBracket (GhcPass p) -> SDoc
    pprHsBracket :: forall (p :: Pass).
    OutputableBndrId p =>
    HsBracket (GhcPass p) -> SDoc
    pprHsBracket (ExpBr XExpBr (GhcPass p)
    _ LHsExpr (GhcPass p)
    e)   = SDoc -> SDoc -> SDoc
    thBrackets SDoc
    empty (LHsExpr (GhcPass p) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr LHsExpr (GhcPass p)
    e)
    pprHsBracket (PatBr XPatBr (GhcPass p)
    _ LPat (GhcPass p)
    p)   = SDoc -> SDoc -> SDoc
    thBrackets (Char -> SDoc
    char Char
    'p') (Located (Pat (GhcPass p)) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr Located (Pat (GhcPass p))
    LPat (GhcPass p)
    p)
    pprHsBracket (DecBrG XDecBrG (GhcPass p)
    _ HsGroup (GhcPass p)
    gp) = SDoc -> SDoc -> SDoc
    thBrackets (Char -> SDoc
    char Char
    'd') (HsGroup (GhcPass p) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr HsGroup (GhcPass p)
    gp)
    pprHsBracket (DecBrL XDecBrL (GhcPass p)
    _ [LHsDecl (GhcPass p)]
    ds) = SDoc -> SDoc -> SDoc
    thBrackets (Char -> SDoc
    char Char
    'd') ([SDoc] -> SDoc
    vcat ((LHsDecl (GhcPass p) -> SDoc) -> [LHsDecl (GhcPass p)] -> [SDoc]
    forall a b. (a -> b) -> [a] -> [b]
    map LHsDecl (GhcPass p) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr [LHsDecl (GhcPass p)]
    ds))
    pprHsBracket (TypBr XTypBr (GhcPass p)
    _ LHsType (GhcPass p)
    t)   = SDoc -> SDoc -> SDoc
    thBrackets (Char -> SDoc
    char Char
    't') (LHsType (GhcPass p) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr LHsType (GhcPass p)
    t)
    pprHsBracket (VarBr XVarBr (GhcPass p)
    _ Bool
    True IdP (GhcPass p)
    n)
      = Char -> SDoc
    char Char
    '\'' SDoc -> SDoc -> SDoc
    <> IdGhcP p -> SDoc
    forall a. OutputableBndr a => a -> SDoc
    pprPrefixOcc IdGhcP p
    IdP (GhcPass p)
    n
    pprHsBracket (VarBr XVarBr (GhcPass p)
    _ Bool
    False IdP (GhcPass p)
    n)
      = String -> SDoc
    text String
    "''" SDoc -> SDoc -> SDoc
    <> IdGhcP p -> SDoc
    forall a. OutputableBndr a => a -> SDoc
    pprPrefixOcc IdGhcP p
    IdP (GhcPass p)
    n
    pprHsBracket (TExpBr XTExpBr (GhcPass p)
    _ LHsExpr (GhcPass p)
    e)  = SDoc -> SDoc
    thTyBrackets (LHsExpr (GhcPass p) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr LHsExpr (GhcPass p)
    e)

    thBrackets :: SDoc -> SDoc -> SDoc
    thBrackets :: SDoc -> SDoc -> SDoc
    thBrackets SDoc
    pp_kind SDoc
    pp_body = Char -> SDoc
    char Char
    '[' SDoc -> SDoc -> SDoc
    <> SDoc
    pp_kind SDoc -> SDoc -> SDoc
    <> SDoc
    vbar SDoc -> SDoc -> SDoc
    <+>
                                 SDoc
    pp_body SDoc -> SDoc -> SDoc
    <+> String -> SDoc
    text String
    "|]"

    thTyBrackets :: SDoc -> SDoc
    thTyBrackets :: SDoc -> SDoc
    thTyBrackets SDoc
    pp_body = String -> SDoc
    text String
    "[||" SDoc -> SDoc -> SDoc
    <+> SDoc
    pp_body SDoc -> SDoc -> SDoc
    <+> PtrString -> SDoc
    ptext (String -> PtrString
    sLit String
    "||]")

    instance Outputable PendingRnSplice where
      ppr :: PendingRnSplice -> SDoc
    ppr (PendingRnSplice UntypedSpliceFlavour
    _ Name
    n LHsExpr GhcRn
    e) = Name -> LHsExpr GhcRn -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    Name -> LHsExpr (GhcPass p) -> SDoc
    pprPendingSplice Name
    n LHsExpr GhcRn
    e

    instance Outputable PendingTcSplice where
      ppr :: PendingTcSplice -> SDoc
    ppr (PendingTcSplice Name
    n LHsExpr GhcTc
    e) = Name -> LHsExpr GhcTc -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    Name -> LHsExpr (GhcPass p) -> SDoc
    pprPendingSplice Name
    n LHsExpr GhcTc
    e

    {-
    ************************************************************************
    *                                                                      *
    \subsection{Enumerations and list comprehensions}
    *                                                                      *
    ************************************************************************
    -}

    -- | Arithmetic Sequence Information
    data ArithSeqInfo id
      = From            (LHsExpr id)
      | FromThen        (LHsExpr id)
                        (LHsExpr id)
      | FromTo          (LHsExpr id)
                        (LHsExpr id)
      | FromThenTo      (LHsExpr id)
                        (LHsExpr id)
                        (LHsExpr id)
    -- AZ: Should ArithSeqInfo have a TTG extension?

    instance OutputableBndrId p
             => Outputable (ArithSeqInfo (GhcPass p)) where
        ppr :: ArithSeqInfo (GhcPass p) -> SDoc
    ppr (From LHsExpr (GhcPass p)
    e1)             = [SDoc] -> SDoc
    hcat [LHsExpr (GhcPass p) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr LHsExpr (GhcPass p)
    e1, SDoc
    pp_dotdot]
        ppr (FromThen LHsExpr (GhcPass p)
    e1 LHsExpr (GhcPass p)
    e2)      = [SDoc] -> SDoc
    hcat [LHsExpr (GhcPass p) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr LHsExpr (GhcPass p)
    e1, SDoc
    comma, SDoc
    space, LHsExpr (GhcPass p) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr LHsExpr (GhcPass p)
    e2, SDoc
    pp_dotdot]
        ppr (FromTo LHsExpr (GhcPass p)
    e1 LHsExpr (GhcPass p)
    e3)        = [SDoc] -> SDoc
    hcat [LHsExpr (GhcPass p) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr LHsExpr (GhcPass p)
    e1, SDoc
    pp_dotdot, LHsExpr (GhcPass p) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr LHsExpr (GhcPass p)
    e3]
        ppr (FromThenTo LHsExpr (GhcPass p)
    e1 LHsExpr (GhcPass p)
    e2 LHsExpr (GhcPass p)
    e3)
          = [SDoc] -> SDoc
    hcat [LHsExpr (GhcPass p) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr LHsExpr (GhcPass p)
    e1, SDoc
    comma, SDoc
    space, LHsExpr (GhcPass p) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr LHsExpr (GhcPass p)
    e2, SDoc
    pp_dotdot, LHsExpr (GhcPass p) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr LHsExpr (GhcPass p)
    e3]

    pp_dotdot :: SDoc
    pp_dotdot :: SDoc
    pp_dotdot = String -> SDoc
    text String
    " .. "

    {-
    ************************************************************************
    *                                                                      *
    \subsection{HsMatchCtxt}
    *                                                                      *
    ************************************************************************
    -}

    -- | Haskell Match Context
    --
    -- Context of a pattern match. This is more subtle than it would seem. See Note
    -- [Varieties of pattern matches].
    data HsMatchContext p
      = FunRhs { forall p. HsMatchContext p -> LIdP p
    mc_fun        :: LIdP p    -- ^ function binder of @f@
               , forall p. HsMatchContext p -> LexicalFixity
    mc_fixity     :: LexicalFixity -- ^ fixing of @f@
               , forall p. HsMatchContext p -> SrcStrictness
    mc_strictness :: SrcStrictness -- ^ was @f@ banged?
                                                -- See Note [FunBind vs PatBind]
               }
                                    -- ^A pattern matching on an argument of a
                                    -- function binding
      | LambdaExpr                  -- ^Patterns of a lambda
      | CaseAlt                     -- ^Patterns and guards on a case alternative
      | IfAlt                       -- ^Guards of a multi-way if alternative
      | ProcExpr                    -- ^Patterns of a proc
      | PatBindRhs                  -- ^A pattern binding  eg [y] <- e = e
      | PatBindGuards               -- ^Guards of pattern bindings, e.g.,
                                    --    (Just b) | Just _ <- x = e
                                    --             | otherwise   = e'

      | RecUpd                      -- ^Record update [used only in GHC.HsToCore.Expr to
                                    --    tell matchWrapper what sort of
                                    --    runtime error message to generate]

      | StmtCtxt (HsStmtContext p)  -- ^Pattern of a do-stmt, list comprehension,
                                    -- pattern guard, etc

      | ThPatSplice            -- ^A Template Haskell pattern splice
      | ThPatQuote             -- ^A Template Haskell pattern quotation [p| (a,b) |]
      | PatSyn                 -- ^A pattern synonym declaration

    instance OutputableBndrId p => Outputable (HsMatchContext (GhcPass p)) where
      ppr :: HsMatchContext (GhcPass p) -> SDoc
    ppr m :: HsMatchContext (GhcPass p)
    m@(FunRhs{})          = String -> SDoc
    text String
    "FunRhs" SDoc -> SDoc -> SDoc
    <+> Located (IdGhcP p) -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr (HsMatchContext (GhcPass p) -> LIdP (GhcPass p)
    forall p. HsMatchContext p -> LIdP p
    mc_fun HsMatchContext (GhcPass p)
    m) SDoc -> SDoc -> SDoc
    <+> LexicalFixity -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr (HsMatchContext (GhcPass p) -> LexicalFixity
    forall p. HsMatchContext p -> LexicalFixity
    mc_fixity HsMatchContext (GhcPass p)
    m)
      ppr HsMatchContext (GhcPass p)
    LambdaExpr            = String -> SDoc
    text String
    "LambdaExpr"
      ppr HsMatchContext (GhcPass p)
    CaseAlt               = String -> SDoc
    text String
    "CaseAlt"
      ppr HsMatchContext (GhcPass p)
    IfAlt                 = String -> SDoc
    text String
    "IfAlt"
      ppr HsMatchContext (GhcPass p)
    ProcExpr              = String -> SDoc
    text String
    "ProcExpr"
      ppr HsMatchContext (GhcPass p)
    PatBindRhs            = String -> SDoc
    text String
    "PatBindRhs"
      ppr HsMatchContext (GhcPass p)
    PatBindGuards         = String -> SDoc
    text String
    "PatBindGuards"
      ppr HsMatchContext (GhcPass p)
    RecUpd                = String -> SDoc
    text String
    "RecUpd"
      ppr (StmtCtxt HsStmtContext (GhcPass p)
    _)          = String -> SDoc
    text String
    "StmtCtxt _"
      ppr HsMatchContext (GhcPass p)
    ThPatSplice           = String -> SDoc
    text String
    "ThPatSplice"
      ppr HsMatchContext (GhcPass p)
    ThPatQuote            = String -> SDoc
    text String
    "ThPatQuote"
      ppr HsMatchContext (GhcPass p)
    PatSyn                = String -> SDoc
    text String
    "PatSyn"

    isPatSynCtxt :: HsMatchContext p -> Bool
    isPatSynCtxt :: forall p. HsMatchContext p -> Bool
    isPatSynCtxt HsMatchContext p
    ctxt =
      case HsMatchContext p
    ctxt of
        HsMatchContext p
    PatSyn -> Bool
    True
        HsMatchContext p
    _      -> Bool
    False

    -- | Haskell Statement Context.
    data HsStmtContext p
      = ListComp
      | MonadComp

      | DoExpr (Maybe ModuleName)        -- ^[ModuleName.]do { ... }
      | MDoExpr (Maybe ModuleName)       -- ^[ModuleName.]mdo { ... }  ie recursive do-expression
      | ArrowExpr                        -- ^do-notation in an arrow-command context

      | GhciStmtCtxt                     -- ^A command-line Stmt in GHCi pat <- rhs
      | PatGuard (HsMatchContext p)      -- ^Pattern guard for specified thing
      | ParStmtCtxt (HsStmtContext p)    -- ^A branch of a parallel stmt
      | TransStmtCtxt (HsStmtContext p)  -- ^A branch of a transform stmt

    qualifiedDoModuleName_maybe :: HsStmtContext p -> Maybe ModuleName
    qualifiedDoModuleName_maybe :: forall p. HsStmtContext p -> Maybe ModuleName
    qualifiedDoModuleName_maybe HsStmtContext p
    ctxt = case HsStmtContext p
    ctxt of
      DoExpr Maybe ModuleName
    m -> Maybe ModuleName
    m
      MDoExpr Maybe ModuleName
    m -> Maybe ModuleName
    m
      HsStmtContext p
    _ -> Maybe ModuleName
    forall a. Maybe a
    Nothing

    isComprehensionContext :: HsStmtContext id -> Bool
    -- Uses comprehension syntax [ e | quals ]
    isComprehensionContext :: forall id. HsStmtContext id -> Bool
    isComprehensionContext HsStmtContext id
    ListComp          = Bool
    True
    isComprehensionContext HsStmtContext id
    MonadComp         = Bool
    True
    isComprehensionContext (ParStmtCtxt HsStmtContext id
    c)   = HsStmtContext id -> Bool
    forall id. HsStmtContext id -> Bool
    isComprehensionContext HsStmtContext id
    c
    isComprehensionContext (TransStmtCtxt HsStmtContext id
    c) = HsStmtContext id -> Bool
    forall id. HsStmtContext id -> Bool
    isComprehensionContext HsStmtContext id
    c
    isComprehensionContext HsStmtContext id
    _ = Bool
    False

    -- | Is this a monadic context?
    isMonadStmtContext :: HsStmtContext id -> Bool
    isMonadStmtContext :: forall id. HsStmtContext id -> Bool
    isMonadStmtContext HsStmtContext id
    MonadComp            = Bool
    True
    isMonadStmtContext DoExpr{}             = Bool
    True
    isMonadStmtContext MDoExpr{}            = Bool
    True
    isMonadStmtContext HsStmtContext id
    GhciStmtCtxt         = Bool
    True
    isMonadStmtContext (ParStmtCtxt HsStmtContext id
    ctxt)   = HsStmtContext id -> Bool
    forall id. HsStmtContext id -> Bool
    isMonadStmtContext HsStmtContext id
    ctxt
    isMonadStmtContext (TransStmtCtxt HsStmtContext id
    ctxt) = HsStmtContext id -> Bool
    forall id. HsStmtContext id -> Bool
    isMonadStmtContext HsStmtContext id
    ctxt
    isMonadStmtContext HsStmtContext id
    _ = Bool
    False -- ListComp, PatGuard, ArrowExpr

    isMonadCompContext :: HsStmtContext id -> Bool
    isMonadCompContext :: forall id. HsStmtContext id -> Bool
    isMonadCompContext HsStmtContext id
    MonadComp = Bool
    True
    isMonadCompContext HsStmtContext id
    _         = Bool
    False

    matchSeparator :: HsMatchContext p -> SDoc
    matchSeparator :: forall p. HsMatchContext p -> SDoc
    matchSeparator (FunRhs {})   = String -> SDoc
    text String
    "="
    matchSeparator HsMatchContext p
    CaseAlt       = String -> SDoc
    text String
    "->"
    matchSeparator HsMatchContext p
    IfAlt         = String -> SDoc
    text String
    "->"
    matchSeparator HsMatchContext p
    LambdaExpr    = String -> SDoc
    text String
    "->"
    matchSeparator HsMatchContext p
    ProcExpr      = String -> SDoc
    text String
    "->"
    matchSeparator HsMatchContext p
    PatBindRhs    = String -> SDoc
    text String
    "="
    matchSeparator HsMatchContext p
    PatBindGuards = String -> SDoc
    text String
    "="
    matchSeparator (StmtCtxt HsStmtContext p
    _)  = String -> SDoc
    text String
    "<-"
    matchSeparator HsMatchContext p
    RecUpd        = String -> SDoc
    text String
    "=" -- This can be printed by the pattern
                                           -- match checker trace
    matchSeparator HsMatchContext p
    ThPatSplice  = String -> SDoc
    forall a. String -> a
    panic String
    "unused"
    matchSeparator HsMatchContext p
    ThPatQuote   = String -> SDoc
    forall a. String -> a
    panic String
    "unused"
    matchSeparator HsMatchContext p
    PatSyn       = String -> SDoc
    forall a. String -> a
    panic String
    "unused"

    pprMatchContext :: Outputable (IdP p)
                    => HsMatchContext p -> SDoc
    pprMatchContext :: forall p. Outputable (IdP p) => HsMatchContext p -> SDoc
    pprMatchContext HsMatchContext p
    ctxt
      | HsMatchContext p -> Bool
    forall p. HsMatchContext p -> Bool
    want_an HsMatchContext p
    ctxt = String -> SDoc
    text String
    "an" SDoc -> SDoc -> SDoc
    <+> HsMatchContext p -> SDoc
    forall p. Outputable (IdP p) => HsMatchContext p -> SDoc
    pprMatchContextNoun HsMatchContext p
    ctxt
      | Bool
    otherwise    = String -> SDoc
    text String
    "a"  SDoc -> SDoc -> SDoc
    <+> HsMatchContext p -> SDoc
    forall p. Outputable (IdP p) => HsMatchContext p -> SDoc
    pprMatchContextNoun HsMatchContext p
    ctxt
      where
        want_an :: HsMatchContext p -> Bool
    want_an (FunRhs {}) = Bool
    True  -- Use "an" in front
        want_an HsMatchContext p
    ProcExpr    = Bool
    True
        want_an HsMatchContext p
    _           = Bool
    False

    pprMatchContextNoun :: Outputable (IdP id)
                        => HsMatchContext id -> SDoc
    pprMatchContextNoun :: forall p. Outputable (IdP p) => HsMatchContext p -> SDoc
    pprMatchContextNoun (FunRhs {mc_fun :: forall p. HsMatchContext p -> LIdP p
    mc_fun=L SrcSpan
    _ IdP id
    fun})
                                        = String -> SDoc
    text String
    "equation for"
                                          SDoc -> SDoc -> SDoc
    <+> SDoc -> SDoc
    quotes (IdP id -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr IdP id
    fun)
    pprMatchContextNoun HsMatchContext id
    CaseAlt         = String -> SDoc
    text String
    "case alternative"
    pprMatchContextNoun HsMatchContext id
    IfAlt           = String -> SDoc
    text String
    "multi-way if alternative"
    pprMatchContextNoun HsMatchContext id
    RecUpd          = String -> SDoc
    text String
    "record-update construct"
    pprMatchContextNoun HsMatchContext id
    ThPatSplice     = String -> SDoc
    text String
    "Template Haskell pattern splice"
    pprMatchContextNoun HsMatchContext id
    ThPatQuote      = String -> SDoc
    text String
    "Template Haskell pattern quotation"
    pprMatchContextNoun HsMatchContext id
    PatBindRhs      = String -> SDoc
    text String
    "pattern binding"
    pprMatchContextNoun HsMatchContext id
    PatBindGuards   = String -> SDoc
    text String
    "pattern binding guards"
    pprMatchContextNoun HsMatchContext id
    LambdaExpr      = String -> SDoc
    text String
    "lambda abstraction"
    pprMatchContextNoun HsMatchContext id
    ProcExpr        = String -> SDoc
    text String
    "arrow abstraction"
    pprMatchContextNoun (StmtCtxt HsStmtContext id
    ctxt) = String -> SDoc
    text String
    "pattern binding in"
                                          SDoc -> SDoc -> SDoc
    $$ HsStmtContext id -> SDoc
    forall id. Outputable (IdP id) => HsStmtContext id -> SDoc
    pprAStmtContext HsStmtContext id
    ctxt
    pprMatchContextNoun HsMatchContext id
    PatSyn          = String -> SDoc
    text String
    "pattern synonym declaration"

    -----------------
    pprAStmtContext, pprStmtContext :: Outputable (IdP id)
                                    => HsStmtContext id -> SDoc
    pprAStmtContext :: forall id. Outputable (IdP id) => HsStmtContext id -> SDoc
    pprAStmtContext HsStmtContext id
    ctxt = SDoc
    article SDoc -> SDoc -> SDoc
    <+> HsStmtContext id -> SDoc
    forall id. Outputable (IdP id) => HsStmtContext id -> SDoc
    pprStmtContext HsStmtContext id
    ctxt
      where
        pp_an :: SDoc
    pp_an = String -> SDoc
    text String
    "an"
        pp_a :: SDoc
    pp_a  = String -> SDoc
    text String
    "a"
        article :: SDoc
    article = case HsStmtContext id
    ctxt of
                      MDoExpr Maybe ModuleName
    Nothing -> SDoc
    pp_an
                      HsStmtContext id
    GhciStmtCtxt  -> SDoc
    pp_an
                      HsStmtContext id
    _             -> SDoc
    pp_a

    -----------------
    pprStmtContext :: forall id. Outputable (IdP id) => HsStmtContext id -> SDoc
    pprStmtContext HsStmtContext id
    GhciStmtCtxt    = String -> SDoc
    text String
    "interactive GHCi command"
    pprStmtContext (DoExpr Maybe ModuleName
    m)      = Maybe ModuleName -> SDoc -> SDoc
    prependQualified Maybe ModuleName
    m (String -> SDoc
    text String
    "'do' block")
    pprStmtContext (MDoExpr Maybe ModuleName
    m)     = Maybe ModuleName -> SDoc -> SDoc
    prependQualified Maybe ModuleName
    m (String -> SDoc
    text String
    "'mdo' block")
    pprStmtContext HsStmtContext id
    ArrowExpr       = String -> SDoc
    text String
    "'do' block in an arrow command"
    pprStmtContext HsStmtContext id
    ListComp        = String -> SDoc
    text String
    "list comprehension"
    pprStmtContext HsStmtContext id
    MonadComp       = String -> SDoc
    text String
    "monad comprehension"
    pprStmtContext (PatGuard HsMatchContext id
    ctxt) = String -> SDoc
    text String
    "pattern guard for" SDoc -> SDoc -> SDoc
    $$ HsMatchContext id -> SDoc
    forall p. Outputable (IdP p) => HsMatchContext p -> SDoc
    pprMatchContext HsMatchContext id
    ctxt

    -- Drop the inner contexts when reporting errors, else we get
    --     Unexpected transform statement
    --     in a transformed branch of
    --          transformed branch of
    --          transformed branch of monad comprehension
    pprStmtContext (ParStmtCtxt HsStmtContext id
    c) =
      SDoc -> SDoc -> SDoc
    ifPprDebug ([SDoc] -> SDoc
    sep [String -> SDoc
    text String
    "parallel branch of", HsStmtContext id -> SDoc
    forall id. Outputable (IdP id) => HsStmtContext id -> SDoc
    pprAStmtContext HsStmtContext id
    c])
                 (HsStmtContext id -> SDoc
    forall id. Outputable (IdP id) => HsStmtContext id -> SDoc
    pprStmtContext HsStmtContext id
    c)
    pprStmtContext (TransStmtCtxt HsStmtContext id
    c) =
      SDoc -> SDoc -> SDoc
    ifPprDebug ([SDoc] -> SDoc
    sep [String -> SDoc
    text String
    "transformed branch of", HsStmtContext id -> SDoc
    forall id. Outputable (IdP id) => HsStmtContext id -> SDoc
    pprAStmtContext HsStmtContext id
    c])
                 (HsStmtContext id -> SDoc
    forall id. Outputable (IdP id) => HsStmtContext id -> SDoc
    pprStmtContext HsStmtContext id
    c)

    prependQualified :: Maybe ModuleName -> SDoc -> SDoc
    prependQualified :: Maybe ModuleName -> SDoc -> SDoc
    prependQualified Maybe ModuleName
    Nothing  SDoc
    t = SDoc
    t
    prependQualified (Just ModuleName
    _) SDoc
    t = String -> SDoc
    text String
    "qualified" SDoc -> SDoc -> SDoc
    <+> SDoc
    t

    instance OutputableBndrId p
          => Outputable (HsStmtContext (GhcPass p)) where
        ppr :: HsStmtContext (GhcPass p) -> SDoc
    ppr = HsStmtContext (GhcPass p) -> SDoc
    forall id. Outputable (IdP id) => HsStmtContext id -> SDoc
    pprStmtContext

    -- Used to generate the string for a *runtime* error message
    matchContextErrString :: OutputableBndrId p
                          => HsMatchContext (GhcPass p) -> SDoc
    matchContextErrString :: forall (p :: Pass).
    OutputableBndrId p =>
    HsMatchContext (GhcPass p) -> SDoc
    matchContextErrString (FunRhs{mc_fun :: forall p. HsMatchContext p -> LIdP p
    mc_fun=L SrcSpan
    _ IdP (GhcPass p)
    fun})   = String -> SDoc
    text String
    "function" SDoc -> SDoc -> SDoc
    <+> IdGhcP p -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr IdGhcP p
    IdP (GhcPass p)
    fun
    matchContextErrString HsMatchContext (GhcPass p)
    CaseAlt                    = String -> SDoc
    text String
    "case"
    matchContextErrString HsMatchContext (GhcPass p)
    IfAlt                      = String -> SDoc
    text String
    "multi-way if"
    matchContextErrString HsMatchContext (GhcPass p)
    PatBindRhs                 = String -> SDoc
    text String
    "pattern binding"
    matchContextErrString HsMatchContext (GhcPass p)
    PatBindGuards              = String -> SDoc
    text String
    "pattern binding guards"
    matchContextErrString HsMatchContext (GhcPass p)
    RecUpd                     = String -> SDoc
    text String
    "record update"
    matchContextErrString HsMatchContext (GhcPass p)
    LambdaExpr                 = String -> SDoc
    text String
    "lambda"
    matchContextErrString HsMatchContext (GhcPass p)
    ProcExpr                   = String -> SDoc
    text String
    "proc"
    matchContextErrString HsMatchContext (GhcPass p)
    ThPatSplice                = String -> SDoc
    forall a. String -> a
    panic String
    "matchContextErrString"  -- Not used at runtime
    matchContextErrString HsMatchContext (GhcPass p)
    ThPatQuote                 = String -> SDoc
    forall a. String -> a
    panic String
    "matchContextErrString"  -- Not used at runtime
    matchContextErrString HsMatchContext (GhcPass p)
    PatSyn                     = String -> SDoc
    forall a. String -> a
    panic String
    "matchContextErrString"  -- Not used at runtime
    matchContextErrString (StmtCtxt (ParStmtCtxt HsStmtContext (GhcPass p)
    c))   = HsMatchContext (GhcPass p) -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    HsMatchContext (GhcPass p) -> SDoc
    matchContextErrString (HsStmtContext (GhcPass p) -> HsMatchContext (GhcPass p)
    forall p. HsStmtContext p -> HsMatchContext p
    StmtCtxt HsStmtContext (GhcPass p)
    c)
    matchContextErrString (StmtCtxt (TransStmtCtxt HsStmtContext (GhcPass p)
    c)) = HsMatchContext (GhcPass p) -> SDoc
    forall (p :: Pass).
    OutputableBndrId p =>
    HsMatchContext (GhcPass p) -> SDoc
    matchContextErrString (HsStmtContext (GhcPass p) -> HsMatchContext (GhcPass p)
    forall p. HsStmtContext p -> HsMatchContext p
    StmtCtxt HsStmtContext (GhcPass p)
    c)
    matchContextErrString (StmtCtxt (PatGuard HsMatchContext (GhcPass p)
    _))      = String -> SDoc
    text String
    "pattern guard"
    matchContextErrString (StmtCtxt HsStmtContext (GhcPass p)
    GhciStmtCtxt)      = String -> SDoc
    text String
    "interactive GHCi command"
    matchContextErrString (StmtCtxt (DoExpr Maybe ModuleName
    m))        = Maybe ModuleName -> SDoc -> SDoc
    prependQualified Maybe ModuleName
    m (String -> SDoc
    text String
    "'do' block")
    matchContextErrString (StmtCtxt HsStmtContext (GhcPass p)
    ArrowExpr)         = String -> SDoc
    text String
    "'do' block"
    matchContextErrString (StmtCtxt (MDoExpr Maybe ModuleName
    m))       = Maybe ModuleName -> SDoc -> SDoc
    prependQualified Maybe ModuleName
    m (String -> SDoc
    text String
    "'mdo' block")
    matchContextErrString (StmtCtxt HsStmtContext (GhcPass p)
    ListComp)          = String -> SDoc
    text String
    "list comprehension"
    matchContextErrString (StmtCtxt HsStmtContext (GhcPass p)
    MonadComp)         = String -> SDoc
    text String
    "monad comprehension"

    pprMatchInCtxt :: (OutputableBndrId idR, Outputable body)
                   => Match (GhcPass idR) body -> SDoc
    pprMatchInCtxt :: forall (pr :: Pass) body.
    (OutputableBndrId pr, Outputable body) =>
    Match (GhcPass pr) body -> SDoc
    pprMatchInCtxt Match (GhcPass idR) body
    match  = SDoc -> Int -> SDoc -> SDoc
    hang (String -> SDoc
    text String
    "In" SDoc -> SDoc -> SDoc
    <+> HsMatchContext (GhcPass (NoGhcTcPass idR)) -> SDoc
    forall p. Outputable (IdP p) => HsMatchContext p -> SDoc
    pprMatchContext (Match (GhcPass idR) body -> HsMatchContext (NoGhcTc (GhcPass idR))
    forall p body. Match p body -> HsMatchContext (NoGhcTc p)
    m_ctxt Match (GhcPass idR) body
    match)
                                            SDoc -> SDoc -> SDoc
    <> SDoc
    colon)
                                 Int
    4 (Match (GhcPass idR) body -> SDoc
    forall (pr :: Pass) body.
    (OutputableBndrId pr, Outputable body) =>
    Match (GhcPass pr) body -> SDoc
    pprMatch Match (GhcPass idR) body
    match)

    pprStmtInCtxt :: (OutputableBndrId idL,
                      OutputableBndrId idR,
                      Outputable body)
                  => HsStmtContext (GhcPass idL)
                  -> StmtLR (GhcPass idL) (GhcPass idR) body
                  -> SDoc
    pprStmtInCtxt :: forall (idL :: Pass) (idR :: Pass) body.
    (OutputableBndrId idL, OutputableBndrId idR, Outputable body) =>
    HsStmtContext (GhcPass idL)
    -> StmtLR (GhcPass idL) (GhcPass idR) body -> SDoc
    pprStmtInCtxt HsStmtContext (GhcPass idL)
    ctxt (LastStmt XLastStmt (GhcPass idL) (GhcPass idR) body
    _ body
    e Maybe Bool
    _ SyntaxExpr (GhcPass idR)
    _)
      | HsStmtContext (GhcPass idL) -> Bool
    forall id. HsStmtContext id -> Bool
    isComprehensionContext HsStmtContext (GhcPass idL)
    ctxt      -- For [ e | .. ], do not mutter about "stmts"
      = SDoc -> Int -> SDoc -> SDoc
    hang (String -> SDoc
    text String
    "In the expression:") Int
    2 (body -> SDoc
    forall a. Outputable a => a -> SDoc
    ppr body
    e)

    pprStmtInCtxt HsStmtContext (GhcPass idL)
    ctxt StmtLR (GhcPass idL) (GhcPass idR) body
    stmt
      = SDoc -> Int -> SDoc -> SDoc
    hang (String -> SDoc
    text String
    "In a stmt of" SDoc -> SDoc -> SDoc
    <+> HsStmtContext (GhcPass idL) -> SDoc
    forall id. Outputable (IdP id) => HsStmtContext id -> SDoc
    pprAStmtContext HsStmtContext (GhcPass idL)
    ctxt SDoc -> SDoc -> SDoc
    <> SDoc
    colon)
           Int
    2 (StmtLR (GhcPass idL) (GhcPass idR) body -> SDoc
    forall {idR :: Pass} {idL :: Pass} {body}.
    (OutputableBndr (IdGhcP idR),
     OutputableBndr (IdGhcP (NoGhcTcPass idR)),
     OutputableBndr (IdGhcP idL),
     OutputableBndr (IdGhcP (NoGhcTcPass idL)), IsPass idR, IsPass idL,
     Outputable body) =>
    StmtLR (GhcPass idL) (GhcPass idR) body -> SDoc
    ppr_stmt StmtLR (GhcPass idL) (GhcPass idR) body
    stmt)
      where
        -- For Group and Transform Stmts, don't print the nested stmts!
        ppr_stmt :: StmtLR (GhcPass idL) (GhcPass idR) body -> SDoc
    ppr_stmt (TransStmt { trS_by :: forall idL idR body. StmtLR idL idR body -> Maybe (LHsExpr idR)
    trS_by = Maybe (LHsExpr (GhcPass idR))
    by, trS_using :: forall idL idR body. StmtLR idL idR body -> LHsExpr idR
    trS_using = LHsExpr (GhcPass idR)
    using
                            , trS_form :: forall idL idR body. StmtLR idL idR body -> TransForm
    trS_form = TransForm
    form }) = Maybe (LHsExpr (GhcPass idR))
    -> LHsExpr (GhcPass idR) -> TransForm -> SDoc
    forall body.
    Outputable body =>
    Maybe body -> body -> TransForm -> SDoc
    pprTransStmt Maybe (LHsExpr (GhcPass idR))
    by LHsExpr (GhcPass idR)
    using TransForm
    form
        ppr_stmt StmtLR (GhcPass idL) (GhcPass idR) body
    stmt = StmtLR (GhcPass idL) (GhcPass idR) body -> SDoc
    forall (pl :: Pass) (pr :: Pass) body.
    (OutputableBndrId pl, OutputableBndrId pr, Outputable body) =>
    StmtLR (GhcPass pl) (GhcPass pr) body -> SDoc
    pprStmt StmtLR (GhcPass idL) (GhcPass idR) body
    stmt