2 % (c) The GRASP/AQUA Project, Glasgow University, 1992-1995
4 \section[StgSyn]{Shared term graph (STG) syntax for spineless-tagless code generation}
6 This data type represents programs just before code generation
7 (conversion to @AbstractC@): basically, what we have is a stylised
8 form of @CoreSyntax@, the style being one that happens to be ideally
9 suited to spineless tagless code generation.
12 #include "HsVersions.h"
18 StgBinding(..), StgExpr(..), StgRhs(..),
19 StgCaseAlternatives(..), StgCaseDefault(..),
21 StgParCommunicate(..),
22 #endif {- Data Parallel Haskell -}
27 stgArgOcc, stgUnsatOcc, stgStdHeapOcc, stgNoUpdHeapOcc,
28 stgNormalOcc, stgFakeFunAppOcc,
31 -- a set of synonyms for the most common (only :-) parameterisation
32 PlainStgAtom(..), PlainStgLiveVars(..), PlainStgProgram(..),
33 PlainStgBinding(..), PlainStgExpr(..), PlainStgRhs(..),
34 PlainStgCaseAlternatives(..), PlainStgCaseDefault(..),
37 --UNUSED: fvsFromAtoms,
41 collectExportedStgBinders,
43 -- and to make the interface self-sufficient...
44 Outputable(..), NamedThing(..), Pretty(..),
45 Unique, ExportFlag, SrcLoc, PprStyle, PrettyRep,
47 BasicLit, Class, ClassOp,
49 Binds, Expr, GRHS, GRHSsAndBinds, InPat,
51 Id, IdInfo, Maybe, Name, FullName, ShortName,
52 PrimKind, PrimOp, CostCentre, TyCon, TyVar,
53 UniqSet(..), UniqFM, Bag,
54 TyVarTemplate, UniType, TauType(..),
55 ThetaType(..), SigmaType(..),
56 TyVarEnv(..), IdEnv(..)
58 IF_ATTACK_PRAGMAS(COMMA isLitLitLit)
59 IF_ATTACK_PRAGMAS(COMMA cmpTyCon COMMA cmpTyVar COMMA cmpClass)
60 IF_ATTACK_PRAGMAS(COMMA cmpUniType)
63 import AbsPrel ( getPrimOpResultInfo, PrimOpResultInfo(..),
65 IF_ATTACK_PRAGMAS(COMMA tagOf_PrimOp)
66 IF_ATTACK_PRAGMAS(COMMA pprPrimOp)
68 import AbsSyn ( Binds, Expr, GRHS, GRHSsAndBinds, InPat )
70 import BasicLit ( typeOfBasicLit, kindOfBasicLit, isLitLitLit,
71 BasicLit(..) -- (..) for pragmas
73 import Id ( getIdUniType, getIdKind, toplevelishId,
74 isTopLevId, Id, IdInfo
76 import Maybes ( Maybe(..), catMaybes )
79 import PrimKind ( PrimKind )
80 import CostCentre ( showCostCentre, CostCentre )
86 %************************************************************************
88 \subsection[StgBinding]{@StgBinding@}
90 %************************************************************************
92 As usual, expressions are interesting; other things are boring. Here
93 are the boring things [except note the @StgRhs@], parameterised with
94 respect to binder and bindee information (just as in @CoreSyntax@):
96 data StgBinding binder bindee
97 = StgNonRec binder (StgRhs binder bindee)
98 | StgRec [(binder, StgRhs binder bindee)]
101 An @StgProgram@ is just a list of @StgBindings@; the
102 properties/restrictions-on this list are the same as for a
103 @CoreProgram@ (a list of @CoreBindings@).
105 --type StgProgram binder bindee = [StgBinding binder bindee]
108 %************************************************************************
110 \subsection[StgAtom]{@StgAtom@}
112 %************************************************************************
117 | StgLitAtom BasicLit
121 getAtomKind (StgVarAtom local) = getIdKind local
122 getAtomKind (StgLitAtom lit) = kindOfBasicLit lit
125 fvsFromAtoms :: [PlainStgAtom] -> (UniqSet Id) -- ToDo: this looks like a HACK to me (WDP)
126 fvsFromAtoms as = mkUniqSet [ id | (StgVarAtom id) <- as, not (toplevelishId id) ]
129 isLitLitStgAtom (StgLitAtom x) = isLitLitLit x
130 isLitLitStgAtom _ = False
133 %************************************************************************
135 \subsection[StgExpr]{STG expressions}
137 %************************************************************************
139 The @StgExpr@ data type is parameterised on binder and bindee info, as
142 %************************************************************************
144 \subsubsection[StgExpr-application]{@StgExpr@ application}
146 %************************************************************************
148 An application is of a function to a list of atoms [not expressions].
149 Operationally, we want to push the arguments on the stack and call the
150 function. (If the arguments were expressions, we would have to build
151 their closures first.)
153 There is no constructor for a lone variable; it would appear as
156 type StgLiveVars bindee = UniqSet bindee
158 data StgExpr binder bindee
160 (StgAtom bindee) -- function
161 [StgAtom bindee] -- arguments
162 (StgLiveVars bindee) -- Live vars in continuation; ie not
163 -- including the function and args
165 -- NB: a literal is: StgApp <lit-atom> [] ...
168 %************************************************************************
170 \subsubsection[StgExpr-apps]{@StgConApp@ and @StgPrimApp@---saturated applications}
172 %************************************************************************
174 There are two specialised forms of application, for
175 constructors and primitives.
177 | StgConApp -- always saturated
178 Id -- data constructor
180 (StgLiveVars bindee) -- Live vars in continuation; ie not
181 -- including the constr and args
183 | StgPrimApp -- always saturated
186 (StgLiveVars bindee) -- Live vars in continuation; ie not
187 -- including the op and args
189 These forms are to do ``inline versions,'' as it were.
190 An example might be: @f x = x:[]@.
192 %************************************************************************
194 \subsubsection[StgExpr-case]{@StgExpr@: case-expressions}
196 %************************************************************************
198 This has the same boxed/unboxed business as Core case expressions.
201 (StgExpr binder bindee)
202 -- the thing to examine
204 (StgLiveVars bindee) -- Live vars of whole case
205 -- expression; i.e., those which mustn't be
208 (StgLiveVars bindee) -- Live vars of RHSs;
209 -- i.e., those which must be saved before eval.
211 -- note that an alt's constructor's
212 -- binder-variables are NOT counted in the
213 -- free vars for the alt's RHS
215 Unique -- Occasionally needed to compile case
216 -- statements, as the uniq for a local
217 -- variable to hold the tag of a primop with
220 (StgCaseAlternatives binder bindee)
223 %************************************************************************
225 \subsubsection[StgExpr-lets]{@StgExpr@: @let(rec)@-expressions}
227 %************************************************************************
229 The various forms of let(rec)-expression encode most of the
230 interesting things we want to do.
234 let-closure x = [free-vars] expr [args]
239 let x = (\free-vars -> \args -> expr) free-vars
241 \tr{args} may be empty (and is for most closures). It isn't under
242 circumstances like this:
248 let-closure x = [z] [y] (y+z)
250 The idea is that we compile code for @(y+z)@ in an environment in which
251 @z@ is bound to an offset from \tr{Node}, and @y@ is bound to an
252 offset from the stack pointer.
254 (A let-closure is an @StgLet@ with a @StgRhsClosure@ RHS.)
258 let-constructor x = Constructor [args]
262 (A let-constructor is an @StgLet@ with a @StgRhsCon@ RHS.)
265 Letrec-expressions are essentially the same deal as
266 let-closure/let-constructor, so we use a common structure and
267 distinguish between them with an @is_recursive@ boolean flag.
271 let-unboxed u = an arbitrary arithmetic expression in unboxed values
274 All the stuff on the RHS must be fully evaluated. No function calls either!
276 (We've backed away from this toward case-expressions with
277 suitably-magical alts ...)
280 ~[Advanced stuff here! Not to start with, but makes pattern matching
281 generate more efficient code.]
284 let-escapes-not fail = expr
287 Here the idea is that @e'@ guarantees not to put @fail@ in a data structure,
288 or pass it to another function. All @e'@ will ever do is tail-call @fail@.
289 Rather than build a closure for @fail@, all we need do is to record the stack
290 level at the moment of the @let-escapes-not@; then entering @fail@ is just
291 a matter of adjusting the stack pointer back down to that point and entering
296 f x y = let z = huge-expression in
302 (A let-escapes-not is an @StgLetNoEscape@.)
305 We may eventually want:
307 let-literal x = BasicLit
311 (ToDo: is this obsolete?)
314 And so the code for let(rec)-things:
317 (StgBinding binder bindee) -- right hand sides (see below)
318 (StgExpr binder bindee) -- body
320 | StgLetNoEscape -- remember: ``advanced stuff''
321 (StgLiveVars bindee) -- Live in the whole let-expression
322 -- Mustn't overwrite these stack slots
323 -- *Doesn't* include binders of the let(rec).
325 (StgLiveVars bindee) -- Live in the right hand sides (only)
326 -- These are the ones which must be saved on
327 -- the stack if they aren't there already
328 -- *Does* include binders of the let(rec) if recursive.
330 (StgBinding binder bindee) -- right hand sides (see below)
331 (StgExpr binder bindee) -- body
334 %************************************************************************
336 \subsubsection[StgExpr-scc]{@StgExpr@: @scc@ expressions}
338 %************************************************************************
340 Finally for @scc@ expressions we introduce a new STG construct.
344 UniType -- the type of the body
345 CostCentre -- label of SCC expression
346 (StgExpr binder bindee) -- scc expression
349 %************************************************************************
351 \subsection[DataParallel]{Data parallel extensions to STG syntax}
353 %************************************************************************
357 | StgParConApp -- saturated parallel constructor
359 Int -- What parallel context
365 (StgExpr binder bindee) -- The thing we are communicating
366 (StgParCommunicate binder bindee)
367 #endif {- Data Parallel Haskell -}
371 %************************************************************************
373 \subsection[StgRhs]{STG right-hand sides}
375 %************************************************************************
377 Here's the rest of the interesting stuff for @StgLet@s; the first
378 flavour is for closures:
380 data StgRhs binder bindee
382 CostCentre -- cost centre to be attached (default is CCC)
383 StgBinderInfo -- Info about how this binder is used (see below)
384 [bindee] -- non-global free vars; a list, rather than
385 -- a set, because order is important
386 UpdateFlag -- ReEntrant | Updatable | SingleEntry
387 [binder] -- arguments; if empty, then not a function;
388 -- as above, order is important
389 (StgExpr binder bindee) -- body
391 An example may be in order. Consider:
393 let t = \x -> \y -> ... x ... y ... p ... q in e
395 Pulling out the free vars and stylising somewhat, we get the equivalent:
397 let t = (\[p,q] -> \[x,y] -> ... x ... y ... p ...q) p q
399 Stg-operationally, the @[x,y]@ are on the stack, the @[p,q]@ are
400 offsets from @Node@ into the closure, and the code ptr for the closure
401 will be exactly that in parentheses above.
403 The second flavour of right-hand-side is for constructors (simple but important):
406 CostCentre -- Cost centre to be attached (default is CCC).
407 -- Top-level (static) ones will end up with
408 -- DontCareCC, because we don't count static
409 -- data in heap profiles, and we don't set CCC
410 -- from static closure.
412 [StgAtom bindee] -- args
415 Here's the @StgBinderInfo@ type, and its combining op:
421 Bool -- At least one occurrence as an argument
423 Bool -- At least one occurrence in an unsaturated application
425 Bool -- This thing (f) has at least occurrence of the form:
426 -- x = [..] \u [] -> f a b c
427 -- where the application is saturated
429 Bool -- Ditto for non-updatable x.
431 Bool -- At least one fake application occurrence, that is
432 -- an StgApp f args where args is an empty list
433 -- This is due to the fact that we do not have a
434 -- StgVar constructor.
435 -- Used by the lambda lifter.
436 -- True => "at least one unsat app" is True too
438 stgArgOcc = StgBinderInfo True False False False False
439 stgUnsatOcc = StgBinderInfo False True False False False
440 stgStdHeapOcc = StgBinderInfo False False True False False
441 stgNoUpdHeapOcc = StgBinderInfo False False False True False
442 stgNormalOcc = StgBinderInfo False False False False False
443 -- [Andre] can't think of a good name for the last one.
444 stgFakeFunAppOcc = StgBinderInfo False True False False True
446 combineStgBinderInfo :: StgBinderInfo -> StgBinderInfo -> StgBinderInfo
448 combineStgBinderInfo NoStgBinderInfo info2 = info2
449 combineStgBinderInfo info1 NoStgBinderInfo = info1
450 combineStgBinderInfo (StgBinderInfo arg1 unsat1 std_heap1 upd_heap1 fkap1)
451 (StgBinderInfo arg2 unsat2 std_heap2 upd_heap2 fkap2)
452 = StgBinderInfo (arg1 || arg2)
454 (std_heap1 || std_heap2)
455 (upd_heap1 || upd_heap2)
459 %************************************************************************
461 \subsection[Stg-case-alternatives]{STG case alternatives}
463 %************************************************************************
465 Just like in @CoreSyntax@ (except no type-world stuff).
468 data StgCaseAlternatives binder bindee
469 = StgAlgAlts UniType -- so we can find out things about constructor family
470 [(Id, -- alts: data constructor,
471 [binder], -- constructor's parameters,
472 [Bool], -- "use mask", same length as
473 -- parameters; a True in a
474 -- param's position if it is
476 StgExpr binder bindee)] -- ...right-hand side.
477 (StgCaseDefault binder bindee)
478 | StgPrimAlts UniType -- so we can find out things about constructor family
479 [(BasicLit, -- alts: unboxed literal,
480 StgExpr binder bindee)] -- rhs.
481 (StgCaseDefault binder bindee)
485 Int -- What context we are in
487 [(Id,StgExpr binder bindee)]
488 (StgCaseDefault binder bindee)
489 | StgParPrimAlts UniType
490 Int -- What context we are in
491 [(BasicLit, -- alts: unboxed literal,
492 StgExpr binder bindee)] -- rhs.
493 (StgCaseDefault binder bindee)
494 #endif {- Data Parallel Haskell -}
496 data StgCaseDefault binder bindee
497 = StgNoDefault -- small con family: all
498 -- constructor accounted for
499 | StgBindDefault binder -- form: var -> expr
500 Bool -- True <=> var is used in rhs
501 -- i.e., False <=> "_ -> expr"
502 (StgExpr binder bindee)
505 %************************************************************************
507 \subsection[Stg-parComummunicate]{Communication operations}
509 %************************************************************************
513 data StgParCommunicate binder bindee
515 [StgAtom bindee] -- Sending PODs
518 [StgAtom bindee] -- Fetching PODs
520 | StgToPodized -- Convert a POD to the podized form
522 | StgFromPodized -- Convert a POD from the podized form
523 #endif {- Data Parallel Haskell -}
526 %************************************************************************
528 \subsection[PlainStg]{The Plain STG parameterisation}
530 %************************************************************************
532 This happens to be the only one we use at the moment.
535 type PlainStgProgram = [StgBinding Id Id]
536 type PlainStgBinding = StgBinding Id Id
537 type PlainStgAtom = StgAtom Id
538 type PlainStgLiveVars= UniqSet Id
539 type PlainStgExpr = StgExpr Id Id
540 type PlainStgRhs = StgRhs Id Id
541 type PlainStgCaseAlternatives = StgCaseAlternatives Id Id
542 type PlainStgCaseDefault = StgCaseDefault Id Id
545 %************************************************************************
547 \subsubsection[UpdateFlag-datatype]{@UpdateFlag@}
549 %************************************************************************
551 This is also used in @LambdaFormInfo@ in the @ClosureInfo@ module.
554 data UpdateFlag = ReEntrant | Updatable | SingleEntry
556 instance Outputable UpdateFlag where
558 = ppChar (case u of { ReEntrant -> 'r'; Updatable -> 'u'; SingleEntry -> 's' })
561 %************************************************************************
563 \subsection[Stg-utility-functions]{Utility functions}
565 %************************************************************************
568 For doing interfaces, we want the exported top-level Ids from the
569 final pre-codegen STG code, so as to be sure we have the
570 latest/greatest pragma info.
573 collectExportedStgBinders
574 :: [PlainStgBinding] -- input: PlainStgProgram
575 -> [Id] -- exported top-level Ids
577 collectExportedStgBinders binds
578 = exported_from_here [] binds
580 exported_from_here es [] = es
582 exported_from_here es ((StgNonRec b _) : binds)
583 = if not (isExported b) then
584 exported_from_here es binds
586 exported_from_here (b:es) binds
588 exported_from_here es ((StgRec []) : binds)
589 = exported_from_here es binds
591 exported_from_here es ((StgRec ((b, rhs) : pairs)) : binds)
594 (StgNonRec b rhs : (StgRec pairs : binds))
595 -- OK, a total hack; laziness rules
598 %************************************************************************
600 \subsection[Stg-pretty-printing]{Pretty-printing}
602 %************************************************************************
604 Robin Popplestone asked for semi-colon separators on STG binds; here's
605 hoping he likes terminators instead... Ditto for case alternatives.
608 pprStgBinding :: (Outputable bndr, Outputable bdee, Ord bdee) =>
609 PprStyle -> StgBinding bndr bdee -> Pretty
611 pprStgBinding sty (StgNonRec binder rhs)
612 = ppHang (ppCat [ppr sty binder, ppEquals])
613 4 (ppBeside (ppr sty rhs) ppSemi)
615 pprStgBinding sty (StgRec pairs)
616 = ppAboves ((ifPprDebug sty (ppStr "{- StgRec -}")) :
617 (map (ppr_bind sty) pairs))
619 ppr_bind sty (binder, expr)
620 = ppHang (ppCat [ppr sty binder, ppEquals])
621 4 (ppBeside (ppr sty expr) ppSemi)
623 pprPlainStgBinding :: PprStyle -> PlainStgBinding -> Pretty
624 pprPlainStgBinding sty b = pprStgBinding sty b
628 instance (Outputable bdee) => Outputable (StgAtom bdee) where
631 instance (Outputable bndr, Outputable bdee, Ord bdee)
632 => Outputable (StgBinding bndr bdee) where
635 instance (Outputable bndr, Outputable bdee, Ord bdee)
636 => Outputable (StgExpr bndr bdee) where
640 instance (Outputable bndr, Outputable bdee, Ord bdee)
641 => Outputable (StgCaseDefault bndr bdee) where
642 ppr sty deflt = panic "ppr:StgCaseDefault"
645 instance (Outputable bndr, Outputable bdee, Ord bdee)
646 => Outputable (StgRhs bndr bdee) where
647 ppr sty rhs = pprStgRhs sty rhs
651 pprStgAtom :: (Outputable bdee) => PprStyle -> StgAtom bdee -> Pretty
653 pprStgAtom sty (StgVarAtom var) = ppr sty var
654 pprStgAtom sty (StgLitAtom lit) = ppr sty lit
658 pprStgExpr :: (Outputable bndr, Outputable bdee, Ord bdee) =>
659 PprStyle -> StgExpr bndr bdee -> Pretty
661 pprStgExpr sty (StgApp func [] lvs)
662 = ppBeside (ppr sty func) (pprStgLVs sty lvs)
665 pprStgExpr sty (StgApp func args lvs)
666 = ppHang (ppBeside (ppr sty func) (pprStgLVs sty lvs))
667 4 (ppSep (map (ppr sty) args))
671 pprStgExpr sty (StgConApp con args lvs)
672 = ppBesides [ ppBeside (ppr sty con) (pprStgLVs sty lvs),
673 ppStr "! [", interppSP sty args, ppStr "]" ]
675 pprStgExpr sty (StgPrimApp op args lvs)
676 = ppBesides [ ppr sty op, ppChar '#', pprStgLVs sty lvs,
677 ppStr " [", interppSP sty args, ppStr "]" ]
681 -- special case: let v = <very specific thing>
687 -- Very special! Suspicious! (SLPJ)
689 pprStgExpr sty (StgLet (StgNonRec binder (StgRhsClosure cc bi free_vars upd_flag args rhs))
692 (ppHang (ppBesides [ppStr "let { ", ppr sty binder, ppStr " = ",
693 ppStr (showCostCentre sty True{-as string-} cc),
694 pp_binder_info sty bi,
695 ppStr " [", ifPprDebug sty (interppSP sty free_vars), ppStr "] \\",
696 ppr sty upd_flag, ppStr " [",
697 interppSP sty args, ppStr "]"])
698 8 (ppSep [ppCat [ppr sty rhs, ppStr "} in"]]))
701 -- special case: let ... in let ...
703 pprStgExpr sty (StgLet bind expr@(StgLet _ _))
705 (ppSep [ppHang (ppStr "let {") 2 (ppCat [pprStgBinding sty bind, ppStr "} in"])])
709 pprStgExpr sty (StgLet bind expr)
710 = ppSep [ppHang (ppStr "let {") 2 (pprStgBinding sty bind),
711 ppHang (ppStr "} in ") 2 (ppr sty expr)]
713 pprStgExpr sty (StgLetNoEscape lvs_whole lvs_rhss bind expr)
714 = ppSep [ppHang (ppStr "let-no-escape {")
715 2 (pprStgBinding sty bind),
716 ppHang (ppBeside (ppStr "} in ")
719 ppBesides [ppStr "-- lvs: [", interppSP sty (uniqSetToList lvs_whole),
720 ppStr "]; rhs lvs: [", interppSP sty (uniqSetToList lvs_rhss),
726 pprStgExpr sty (StgSCC ty cc expr)
727 = ppSep [ ppCat [ppStr "_scc_", ppStr (showCostCentre sty True{-as string-} cc)],
728 pprStgExpr sty expr ]
732 pprStgExpr sty (StgCase expr lvs_whole lvs_rhss uniq alts)
733 = ppSep [ppSep [ppStr "case",
734 ppNest 4 (ppCat [pprStgExpr sty expr,
735 ifPprDebug sty (ppBeside (ppStr "::") (pp_ty alts))]),
739 ppBesides [ppStr "-- lvs: [", interppSP sty (uniqSetToList lvs_whole),
740 ppStr "]; rhs lvs: [", interppSP sty (uniqSetToList lvs_rhss),
741 ppStr "]; uniq: ", pprUnique uniq])),
742 ppNest 2 (ppr_alts sty alts),
745 pp_ty (StgAlgAlts ty _ _) = ppr sty ty
746 pp_ty (StgPrimAlts ty _ _) = ppr sty ty
748 ppr_alts sty (StgAlgAlts ty alts deflt)
749 = ppAboves [ ppAboves (map (ppr_bxd_alt sty) alts),
750 ppr_default sty deflt ]
752 ppr_bxd_alt sty (con, params, use_mask, expr)
753 = ppHang (ppCat [ppr_con sty con, interppSP sty params, ppStr "->"])
754 4 (ppBeside (ppr sty expr) ppSemi)
758 then ppBesides [ppLparen, ppr sty con, ppRparen]
761 ppr_alts sty (StgPrimAlts ty alts deflt)
762 = ppAboves [ ppAboves (map (ppr_ubxd_alt sty) alts),
763 ppr_default sty deflt ]
765 ppr_ubxd_alt sty (lit, expr)
766 = ppHang (ppCat [ppr sty lit, ppStr "->"])
767 4 (ppBeside (ppr sty expr) ppSemi)
770 ppr_alts sty (StgParAlgAlts ty dim params alts deflt)
771 = ppAboves [ ppBeside (ppCat (map (ppr sty) params))
772 (ppCat [ppStr "|" , ppr sty dim , ppStr "|"]),
773 ppAboves (map (ppr_bxd_alt sty) alts),
774 ppr_default sty deflt ]
776 ppr_bxd_alt sty (con, expr)
777 = ppHang (ppCat [ppStr "\\/", ppr_con sty con, ppStr "->"])
782 then ppBesides [ppLparen, ppr sty con, ppRparen]
785 ppr_alts sty (StgParPrimAlts ty dim alts deflt)
786 = ppAboves [ ifPprShowAll sty (ppr sty ty),
787 ppCat [ppStr "|" , ppr sty dim , ppStr "|"],
788 ppAboves (map (ppr_ubxd_alt sty) alts),
789 ppr_default sty deflt ]
791 ppr_ubxd_alt sty (lit, expr)
792 = ppHang (ppCat [ppStr "\\/", ppr sty lit, ppStr "->"]) 4 (ppr sty expr)
793 #endif {- Data Parallel Haskell -}
795 ppr_default sty StgNoDefault = ppNil
796 ppr_default sty (StgBindDefault binder used expr)
797 = ppHang (ppCat [pp_binder, ppStr "->"]) 4 (ppr sty expr)
799 pp_binder = if used then ppr sty binder else ppChar '_'
804 pprStgExpr sty (StgParConApp con dim args lvs)
805 = ppBesides [ppr sty con, pprStgLVs sty lvs, ppStr "!<<" ,ppr sty dim ,
806 ppStr ">> [", interppSP sty args, ppStr "]" ]
808 pprStgExpr sty (StgParComm dim expr comm)
809 = ppSep [ppSep [ppStr "COMM ",
810 ppNest 2 (pprStgExpr sty expr),ppStr "{"],
811 ppNest 2 (ppr_comm sty comm),
814 ppr_comm sty (StgParSend args)
815 = ppSep [ppStr "SEND [",interppSP sty args, ppStr "]" ]
816 ppr_comm sty (StgParFetch args)
817 = ppSep [ppStr "FETCH [",interppSP sty args, ppStr "]" ]
818 ppr_comm sty (StgToPodized)
820 ppr_comm sty (StgFromPodized)
821 = ppStr "FromPodized"
822 #endif {- Data Parallel Haskell -}
826 -- pprStgLVs :: PprStyle -> StgLiveVars bindee -> Pretty
828 pprStgLVs PprForUser lvs = ppNil
831 = if isEmptyUniqSet lvs then
834 ppBesides [ppStr "{-lvs:", interpp'SP sty (uniqSetToList lvs), ppStr "-}"]
838 pprStgRhs :: (Outputable bndr, Outputable bdee, Ord bdee) =>
839 PprStyle -> StgRhs bndr bdee -> Pretty
842 pprStgRhs sty (StgRhsClosure cc bi [free_var] upd_flag [{-no args-}] (StgApp func [] lvs))
843 = ppBesides [ ppStr (showCostCentre sty True{-as String-} cc),
844 pp_binder_info sty bi,
845 ppStr " [", ifPprDebug sty (ppr sty free_var),
846 ppStr "] \\", ppr sty upd_flag, ppStr " [] ", ppr sty func ]
848 pprStgRhs sty (StgRhsClosure cc bi free_vars upd_flag args body)
849 = ppHang (ppBesides [ ppStr (showCostCentre sty True{-as String-} cc),
850 pp_binder_info sty bi,
851 ppStr " [", ifPprDebug sty (interppSP sty free_vars),
852 ppStr "] \\", ppr sty upd_flag, ppStr " [", interppSP sty args, ppStr "]"])
855 pprStgRhs sty (StgRhsCon cc con args)
856 = ppBesides [ ppStr (showCostCentre sty True{-as String-} cc),
857 ppSP, ppr sty con, ppStr " [", interppSP sty args, ppStr "]" ]
860 pp_binder_info PprForUser _ = ppNil
862 pp_binder_info sty NoStgBinderInfo = ppNil
864 -- cases so boring that we print nothing
865 pp_binder_info sty (StgBinderInfo True b c d e) = ppNil
868 pp_binder_info sty (StgBinderInfo a b c d e)
869 = ppBesides [ppChar '(', ppInterleave ppComma (map pp_bool [a,b,c,d,e]), ppChar ')']
871 pp_bool x = ppr (panic "pp_bool") x
874 Collect @IdInfo@ stuff that is most easily just snaffled straight
875 from the STG bindings.
878 stgArity :: PlainStgRhs -> Int
880 stgArity (StgRhsCon _ _ _) = 0 -- it's a constructor, fully applied
881 stgArity (StgRhsClosure _ _ _ _ args _ ) = length args