2 % (c) The GRASP/AQUA Project, Glasgow University, 1993-1996
4 \section[IdInfo]{@IdInfos@: Non-essential information about @Ids@}
6 (And a pretty good illustration of quite a few things wrong with
10 #include "HsVersions.h"
17 applySubstToIdInfo, apply_to_IdInfo, -- not for general use, please
20 exactArity, atLeastArity, unknownArity,
21 arityInfo, addArityInfo, ppArityInfo,
24 noDemandInfo, mkDemandInfo, demandInfo, ppDemandInfo, addDemandInfo, willBeDemanded,
26 StrictnessInfo(..), -- Non-abstract
27 Demand(..), NewOrData, -- Non-abstract
30 mkStrictnessInfo, mkBottomStrictnessInfo, noStrictnessInfo, bottomIsGuaranteed,
31 strictnessInfo, ppStrictnessInfo, addStrictnessInfo,
33 unfoldInfo, addUnfoldInfo,
35 specInfo, addSpecInfo,
37 UpdateInfo, SYN_IE(UpdateSpec),
38 mkUpdateInfo, updateInfo, updateInfoMaybe, ppUpdateInfo, addUpdateInfo,
41 deforestInfo, ppDeforestInfo, addDeforestInfo,
43 ArgUsageInfo, ArgUsage(..), SYN_IE(ArgUsageType),
44 mkArgUsageInfo, argUsageInfo, addArgUsageInfo, getArgUsage,
46 FBTypeInfo, FBType(..), FBConsum(..), FBProd(..),
47 fbTypeInfo, ppFBTypeInfo, addFBTypeInfo, mkFBTypeInfo, getFBType
51 IMPORT_1_3(Char(toLower))
53 #if defined(__GLASGOW_HASKELL__) && __GLASGOW_HASKELL__ <= 201
54 IMPORT_DELOOPER(IdLoop) -- IdInfo is a dependency-loop ranch, and
55 -- we break those loops by using IdLoop and
56 -- *not* importing much of anything else,
57 -- except from the very general "utils".
59 import {-# SOURCE #-} SpecEnv
60 import {-# SOURCE #-} Id
61 import {-# SOURCE #-} CoreUnfold
62 import {-# SOURCE #-} StdIdInfo
65 import BasicTypes ( NewOrData )
66 import CmdLineOpts ( opt_OmitInterfacePragmas )
69 import Maybes ( firstJust )
70 import Outputable ( ifaceStyle, PprStyle(..), Outputable(..){-instances-} )
73 import Unique ( pprUnique )
74 import Util ( mapAccumL, panic, assertPanic, pprPanic )
76 #ifdef REALLY_HASKELL_1_3
77 ord = fromEnum :: Char -> Int
80 showTypeCategory = panic "IdInfo.showTypeCategory"
83 An @IdInfo@ gives {\em optional} information about an @Id@. If
84 present it never lies, but it may not be present, in which case there
85 is always a conservative assumption which can be made.
87 Two @Id@s may have different info even though they have the same
88 @Unique@ (and are hence the same @Id@); for example, one might lack
89 the properties attached to the other.
91 The @IdInfo@ gives information about the value, or definition, of the
92 @Id@. It does {\em not} contain information about the @Id@'s usage
93 (except for @DemandInfo@? ToDo).
98 ArityInfo -- Its arity
100 DemandInfo -- Whether or not it is definitely
103 SpecEnv -- Specialisations of this function which exist
105 StrictnessInfo -- Strictness properties
107 Unfolding -- Its unfolding; for locally-defined
108 -- things, this can *only* be NoUnfolding
110 UpdateInfo -- Which args should be updated
112 DeforestInfo -- Whether its definition should be
113 -- unfolded during deforestation
115 ArgUsageInfo -- how this Id uses its arguments
117 FBTypeInfo -- the Foldr/Build W/W property of this function.
121 noIdInfo = IdInfo UnknownArity UnknownDemand nullSpecEnv NoStrictnessInfo noUnfolding
122 NoUpdateInfo Don'tDeforest NoArgUsageInfo NoFBTypeInfo
125 Simply turgid. But BE CAREFUL: don't @apply_to_Id@ if that @Id@
126 will in turn @apply_to_IdInfo@ of the self-same @IdInfo@. (A very
127 nasty loop, friends...)
129 apply_to_IdInfo ty_fn idinfo@(IdInfo arity demand spec strictness unfold
130 update deforest arg_usage fb_ww)
134 = panic "IdInfo:apply_to_IdInfo"
137 Variant of the same thing for the typechecker.
139 applySubstToIdInfo s0 (IdInfo arity demand spec strictness unfold
140 update deforest arg_usage fb_ww)
141 = panic "IdInfo:applySubstToIdInfo"
146 -> Bool -- True <=> print specialisations, please
150 ppIdInfo sty specs_please
151 (IdInfo arity demand specenv strictness unfold update deforest arg_usage fbtype)
153 -- order is important!:
154 ppArityInfo sty arity,
155 ppUpdateInfo sty update,
156 ppDeforestInfo sty deforest,
158 ppStrictnessInfo sty strictness,
161 then empty -- ToDo -- sty (not (isDataCon for_this_id))
162 -- better_id_fn inline_env (mEnvToList specenv)
165 -- DemandInfo needn't be printed since it has no effect on interfaces
166 ppDemandInfo sty demand,
167 ppFBTypeInfo sty fbtype
171 %************************************************************************
173 \subsection[arity-IdInfo]{Arity info about an @Id@}
175 %************************************************************************
179 = UnknownArity -- No idea
180 | ArityExactly Int -- Arity is exactly this
181 | ArityAtLeast Int -- Arity is this or greater
185 exactArity = ArityExactly
186 atLeastArity = ArityAtLeast
187 unknownArity = UnknownArity
189 arityInfo (IdInfo arity _ _ _ _ _ _ _ _) = arity
191 addArityInfo (IdInfo _ a c d e f g h i) arity = IdInfo arity a c d e f g h i
193 ppArityInfo sty UnknownArity = empty
194 ppArityInfo sty (ArityExactly arity) = hsep [ptext SLIT("_A_"), int arity]
195 ppArityInfo sty (ArityAtLeast arity) = hsep [ptext SLIT("_A>_"), int arity]
198 %************************************************************************
200 \subsection[demand-IdInfo]{Demand info about an @Id@}
202 %************************************************************************
204 Whether a value is certain to be demanded or not. (This is the
205 information that is computed by the ``front-end'' of the strictness
208 This information is only used within a module, it is not exported
214 | DemandedAsPer Demand
218 noDemandInfo = UnknownDemand
220 mkDemandInfo :: Demand -> DemandInfo
221 mkDemandInfo demand = DemandedAsPer demand
223 willBeDemanded :: DemandInfo -> Bool
224 willBeDemanded (DemandedAsPer demand) = isStrict demand
225 willBeDemanded _ = False
229 demandInfo (IdInfo _ demand _ _ _ _ _ _ _) = demand
231 addDemandInfo (IdInfo a _ c d e f g h i) demand = IdInfo a demand c d e f g h i
233 ppDemandInfo PprInterface _ = empty
234 ppDemandInfo sty UnknownDemand = text "{-# L #-}"
235 ppDemandInfo sty (DemandedAsPer info) = hsep [text "{-#", text (showList [info] ""), text "#-}"]
238 %************************************************************************
240 \subsection[specialisation-IdInfo]{Specialisation info about an @Id@}
242 %************************************************************************
247 specInfo (IdInfo _ _ spec _ _ _ _ _ _) = spec
249 addSpecInfo id_info spec | isNullSpecEnv spec = id_info
250 addSpecInfo (IdInfo a b _ d e f g h i) spec = IdInfo a b spec d e f g h i
253 %************************************************************************
255 \subsection[strictness-IdInfo]{Strictness info about an @Id@}
257 %************************************************************************
259 We specify the strictness of a function by giving information about
260 each of the ``wrapper's'' arguments (see the description about
261 worker/wrapper-style transformations in the PJ/Launchbury paper on
264 The list of @Demands@ specifies: (a)~the strictness properties
265 of a function's arguments; (b)~the {\em existence} of a ``worker''
266 version of the function; and (c)~the type signature of that worker (if
267 it exists); i.e. its calling convention.
273 | BottomGuaranteed -- This Id guarantees never to return;
274 -- it is bottom regardless of its arguments.
275 -- Useful for "error" and other disguised
278 | StrictnessInfo [Demand]
279 Bool -- True <=> there is a worker. There might not be, even for a
280 -- strict function, because:
281 -- (a) the function might be small enough to inline,
282 -- so no need for w/w split
283 -- (b) the strictness info might be "SSS" or something, so no w/w split.
285 -- Worker's Id, if applicable, and a list of the constructors
286 -- mentioned by the wrapper. This is necessary so that the
287 -- renamer can slurp them in. Without this info, the renamer doesn't
288 -- know which data types to slurp in concretely. Remember, for
289 -- strict things we don't put the unfolding in the interface file, to save space.
290 -- This constructor list allows the renamer to behave much as if the
291 -- unfolding *was* in the interface file.
295 mkStrictnessInfo :: [Demand] -> Bool -> StrictnessInfo
297 mkStrictnessInfo xs has_wrkr
298 | all is_lazy xs = NoStrictnessInfo -- Uninteresting
299 | otherwise = StrictnessInfo xs has_wrkr
301 is_lazy (WwLazy False) = True -- NB "Absent" args do *not* count!
302 is_lazy _ = False -- (as they imply a worker)
304 noStrictnessInfo = NoStrictnessInfo
305 mkBottomStrictnessInfo = BottomGuaranteed
307 bottomIsGuaranteed BottomGuaranteed = True
308 bottomIsGuaranteed other = False
310 strictnessInfo (IdInfo _ _ _ strict _ _ _ _ _) = strict
312 addStrictnessInfo id_info NoStrictnessInfo = id_info
313 addStrictnessInfo (IdInfo a b d _ e f g h i) strict = IdInfo a b d strict e f g h i
315 ppStrictnessInfo sty NoStrictnessInfo = empty
316 ppStrictnessInfo sty BottomGuaranteed = ptext SLIT("_bot_")
318 ppStrictnessInfo sty (StrictnessInfo wrapper_args wrkr_maybe)
319 = hsep [ptext SLIT("_S_"), text (showList wrapper_args "")]
324 workerExists :: StrictnessInfo -> Bool
325 workerExists (StrictnessInfo _ worker_exists) = worker_exists
326 workerExists other = False
330 %************************************************************************
332 \subsection[unfolding-IdInfo]{Unfolding info about an @Id@}
334 %************************************************************************
337 unfoldInfo (IdInfo _ _ _ _ unfolding _ _ _ _) = unfolding
339 addUnfoldInfo (IdInfo a b d e _ f g h i) uf = IdInfo a b d e uf f g h i
342 %************************************************************************
344 \subsection[update-IdInfo]{Update-analysis info about an @Id@}
346 %************************************************************************
351 | SomeUpdateInfo UpdateSpec
353 -- we need Eq/Ord to cross-chk update infos in interfaces
355 -- the form in which we pass update-analysis info between modules:
356 type UpdateSpec = [Int]
360 mkUpdateInfo = SomeUpdateInfo
362 updateInfoMaybe NoUpdateInfo = Nothing
363 updateInfoMaybe (SomeUpdateInfo []) = Nothing
364 updateInfoMaybe (SomeUpdateInfo u) = Just u
367 Text instance so that the update annotations can be read in.
370 #ifdef REALLY_HASKELL_1_3
371 instance Read UpdateInfo where
373 instance Text UpdateInfo where
375 readsPrec p s | null s = panic "IdInfo: empty update pragma?!"
376 | otherwise = [(SomeUpdateInfo (map ok_digit s),"")]
378 ok_digit c | c >= '0' && c <= '2' = ord c - ord '0'
379 | otherwise = panic "IdInfo: not a digit while reading update pragma"
381 updateInfo (IdInfo _ _ _ _ _ update _ _ _) = update
383 addUpdateInfo id_info NoUpdateInfo = id_info
384 addUpdateInfo (IdInfo a b d e f _ g h i) upd_info = IdInfo a b d e f upd_info g h i
386 ppUpdateInfo sty NoUpdateInfo = empty
387 ppUpdateInfo sty (SomeUpdateInfo []) = empty
388 ppUpdateInfo sty (SomeUpdateInfo spec) = (<>) (ptext SLIT("_U_ ")) (hcat (map int spec))
391 %************************************************************************
393 \subsection[deforest-IdInfo]{Deforestation info about an @Id@}
395 %************************************************************************
397 The deforest info says whether this Id is to be unfolded during
398 deforestation. Therefore, when the deforest pragma is true, we must
399 also have the unfolding information available for this Id.
403 = Don'tDeforest -- just a bool, might extend this
404 | DoDeforest -- later.
405 -- deriving (Eq, Ord)
409 deforestInfo (IdInfo _ _ _ _ _ _ deforest _ _) = deforest
411 addDeforestInfo id_info Don'tDeforest = id_info
412 addDeforestInfo (IdInfo a b d e f g _ h i) deforest = IdInfo a b d e f g deforest h i
414 ppDeforestInfo sty Don'tDeforest = empty
415 ppDeforestInfo sty DoDeforest = ptext SLIT("_DEFOREST_")
418 %************************************************************************
420 \subsection[argUsage-IdInfo]{Argument Usage info about an @Id@}
422 %************************************************************************
427 | SomeArgUsageInfo ArgUsageType
428 -- ??? deriving (Eq, Ord)
430 data ArgUsage = ArgUsage Int -- number of arguments (is linear!)
432 type ArgUsageType = [ArgUsage] -- c_1 -> ... -> BLOB
436 mkArgUsageInfo [] = NoArgUsageInfo
437 mkArgUsageInfo au = SomeArgUsageInfo au
439 getArgUsage :: ArgUsageInfo -> ArgUsageType
440 getArgUsage NoArgUsageInfo = []
441 getArgUsage (SomeArgUsageInfo u) = u
445 argUsageInfo (IdInfo _ _ _ _ _ _ _ au _) = au
447 addArgUsageInfo id_info NoArgUsageInfo = id_info
448 addArgUsageInfo (IdInfo a b d e f g h _ i) au_info = IdInfo a b d e f g h au_info i
450 ppArgUsageInfo sty NoArgUsageInfo = empty
451 ppArgUsageInfo sty (SomeArgUsageInfo aut) = (<>) (ptext SLIT("_L_ ")) (ppArgUsageType aut)
453 ppArgUsage (ArgUsage n) = int n
454 ppArgUsage (UnknownArgUsage) = char '-'
456 ppArgUsageType aut = hcat
458 hcat (punctuate comma (map ppArgUsage aut)),
462 %************************************************************************
464 \subsection[FBType-IdInfo]{Type of an expression through Foldr/build's eyes}
466 %************************************************************************
471 | SomeFBTypeInfo FBType
473 data FBType = FBType [FBConsum] FBProd deriving (Eq)
475 data FBConsum = FBGoodConsum | FBBadConsum deriving(Eq)
476 data FBProd = FBGoodProd | FBBadProd deriving(Eq)
480 mkFBTypeInfo = SomeFBTypeInfo
482 getFBType :: FBTypeInfo -> Maybe FBType
483 getFBType NoFBTypeInfo = Nothing
484 getFBType (SomeFBTypeInfo u) = Just u
488 fbTypeInfo (IdInfo _ _ _ _ _ _ _ _ fb) = fb
490 addFBTypeInfo id_info NoFBTypeInfo = id_info
491 addFBTypeInfo (IdInfo a b d e f g h i _) fb_info = IdInfo a b d e f g h i fb_info
493 ppFBTypeInfo sty NoFBTypeInfo = empty
494 ppFBTypeInfo sty (SomeFBTypeInfo (FBType cons prod))
495 = (<>) (ptext SLIT("_F_ ")) (ppFBType cons prod)
497 ppFBType cons prod = hcat
498 ([ char '"' ] ++ map ppCons cons ++ [ char '-', ppProd prod, char '"' ])
500 ppCons FBGoodConsum = char 'G'
501 ppCons FBBadConsum = char 'B'
502 ppProd FBGoodProd = char 'G'
503 ppProd FBBadProd = char 'B'