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
15 applySubstToIdInfo, apply_to_IdInfo, -- not for general use, please
18 exactArity, atLeastArity, unknownArity,
19 arityInfo, addArityInfo, ppArityInfo,
22 noDemandInfo, mkDemandInfo, demandInfo, ppDemandInfo, addDemandInfo, willBeDemanded,
24 StrictnessInfo(..), -- Non-abstract
25 Demand(..), NewOrData, -- Non-abstract
28 mkStrictnessInfo, mkBottomStrictnessInfo, noStrictnessInfo, bottomIsGuaranteed,
29 strictnessInfo, ppStrictnessInfo, addStrictnessInfo,
31 unfoldInfo, addUnfoldInfo,
33 IdSpecEnv, specInfo, addSpecInfo,
35 UpdateInfo, UpdateSpec,
36 mkUpdateInfo, updateInfo, updateInfoMaybe, ppUpdateInfo, addUpdateInfo,
38 ArgUsageInfo, ArgUsage(..), ArgUsageType,
39 mkArgUsageInfo, argUsageInfo, addArgUsageInfo, getArgUsage,
41 FBTypeInfo, FBType(..), FBConsum(..), FBProd(..),
42 fbTypeInfo, ppFBTypeInfo, addFBTypeInfo, mkFBTypeInfo, getFBType
45 #include "HsVersions.h"
48 import {-# SOURCE #-} CoreUnfold ( Unfolding, noUnfolding )
49 import {-# SOURCE #-} CoreSyn ( SimplifiableCoreExpr )
50 -- for mkdependHS, CoreSyn.hi-boot refers to it:
51 import BinderInfo ( BinderInfo )
53 import SpecEnv ( SpecEnv, emptySpecEnv, isEmptySpecEnv )
54 import BasicTypes ( NewOrData )
57 import Maybes ( firstJust )
59 import Unique ( pprUnique )
60 import Util ( mapAccumL )
62 ord = fromEnum :: Char -> Int
63 showTypeCategory = panic "IdInfo.showTypeCategory"
66 An @IdInfo@ gives {\em optional} information about an @Id@. If
67 present it never lies, but it may not be present, in which case there
68 is always a conservative assumption which can be made.
70 Two @Id@s may have different info even though they have the same
71 @Unique@ (and are hence the same @Id@); for example, one might lack
72 the properties attached to the other.
74 The @IdInfo@ gives information about the value, or definition, of the
75 @Id@. It does {\em not} contain information about the @Id@'s usage
76 (except for @DemandInfo@? ToDo).
81 ArityInfo -- Its arity
83 DemandInfo -- Whether or not it is definitely
86 IdSpecEnv -- Specialisations of this function which exist
88 StrictnessInfo -- Strictness properties
90 Unfolding -- Its unfolding; for locally-defined
91 -- things, this can *only* be NoUnfolding
93 UpdateInfo -- Which args should be updated
95 ArgUsageInfo -- how this Id uses its arguments
97 FBTypeInfo -- the Foldr/Build W/W property of this function.
101 noIdInfo = IdInfo UnknownArity UnknownDemand emptySpecEnv NoStrictnessInfo noUnfolding
102 NoUpdateInfo NoArgUsageInfo NoFBTypeInfo
105 Simply turgid. But BE CAREFUL: don't @apply_to_Id@ if that @Id@
106 will in turn @apply_to_IdInfo@ of the self-same @IdInfo@. (A very
107 nasty loop, friends...)
109 apply_to_IdInfo ty_fn idinfo@(IdInfo arity demand spec strictness unfold
110 update arg_usage fb_ww)
111 | isEmptySpecEnv spec
114 = panic "IdInfo:apply_to_IdInfo"
117 Variant of the same thing for the typechecker.
119 applySubstToIdInfo s0 (IdInfo arity demand spec strictness unfold
120 update arg_usage fb_ww)
121 = panic "IdInfo:applySubstToIdInfo"
125 ppIdInfo :: Bool -- True <=> print specialisations, please
129 ppIdInfo specs_please
130 (IdInfo arity demand specenv strictness unfold update arg_usage fbtype)
132 -- order is important!:
136 ppStrictnessInfo strictness,
139 then empty -- ToDo -- sty (not (isDataCon for_this_id))
140 -- better_id_fn inline_env (mEnvToList specenv)
143 -- DemandInfo needn't be printed since it has no effect on interfaces
149 %************************************************************************
151 \subsection[arity-IdInfo]{Arity info about an @Id@}
153 %************************************************************************
157 = UnknownArity -- No idea
158 | ArityExactly Int -- Arity is exactly this
159 | ArityAtLeast Int -- Arity is this or greater
163 exactArity = ArityExactly
164 atLeastArity = ArityAtLeast
165 unknownArity = UnknownArity
167 arityInfo (IdInfo arity _ _ _ _ _ _ _) = arity
169 addArityInfo (IdInfo _ a b c d e f g) arity = IdInfo arity a b c d e f g
171 ppArityInfo UnknownArity = empty
172 ppArityInfo (ArityExactly arity) = hsep [ptext SLIT("_A_"), int arity]
173 ppArityInfo (ArityAtLeast arity) = hsep [ptext SLIT("_A>_"), int arity]
176 %************************************************************************
178 \subsection[demand-IdInfo]{Demand info about an @Id@}
180 %************************************************************************
182 Whether a value is certain to be demanded or not. (This is the
183 information that is computed by the ``front-end'' of the strictness
186 This information is only used within a module, it is not exported
192 | DemandedAsPer Demand
196 noDemandInfo = UnknownDemand
198 mkDemandInfo :: Demand -> DemandInfo
199 mkDemandInfo demand = DemandedAsPer demand
201 willBeDemanded :: DemandInfo -> Bool
202 willBeDemanded (DemandedAsPer demand) = isStrict demand
203 willBeDemanded _ = False
207 demandInfo (IdInfo _ demand _ _ _ _ _ _) = demand
209 addDemandInfo (IdInfo a _ c d e f g h) demand = IdInfo a demand c d e f g h
211 ppDemandInfo UnknownDemand = text "{-# L #-}"
212 ppDemandInfo (DemandedAsPer info) = hsep [text "{-#", text (showList [info] ""), text "#-}"]
215 %************************************************************************
217 \subsection[specialisation-IdInfo]{Specialisation info about an @Id@}
219 %************************************************************************
221 A @IdSpecEnv@ holds details of an @Id@'s specialisations.
224 type IdSpecEnv = SpecEnv SimplifiableCoreExpr
227 For example, if \tr{f}'s @SpecEnv@ contains the mapping:
229 [List a, b] ===> (\d -> f' a b)
231 then when we find an application of f to matching types, we simply replace
232 it by the matching RHS:
234 f (List Int) Bool ===> (\d -> f' Int Bool)
236 All the stuff about how many dictionaries to discard, and what types
237 to apply the specialised function to, are handled by the fact that the
238 SpecEnv contains a template for the result of the specialisation.
240 There is one more exciting case, which is dealt with in exactly the same
241 way. If the specialised value is unboxed then it is lifted at its
242 definition site and unlifted at its uses. For example:
244 pi :: forall a. Num a => a
246 might have a specialisation
248 [Int#] ===> (case pi' of Lift pi# -> pi#)
250 where pi' :: Lift Int# is the specialised version of pi.
254 specInfo :: IdInfo -> IdSpecEnv
255 specInfo (IdInfo _ _ spec _ _ _ _ _) = spec
257 addSpecInfo id_info spec | isEmptySpecEnv spec = id_info
258 addSpecInfo (IdInfo a b _ d e f g h) spec = IdInfo a b spec d e f g h
262 %************************************************************************
264 \subsection[strictness-IdInfo]{Strictness info about an @Id@}
266 %************************************************************************
268 We specify the strictness of a function by giving information about
269 each of the ``wrapper's'' arguments (see the description about
270 worker/wrapper-style transformations in the PJ/Launchbury paper on
273 The list of @Demands@ specifies: (a)~the strictness properties
274 of a function's arguments; (b)~the {\em existence} of a ``worker''
275 version of the function; and (c)~the type signature of that worker (if
276 it exists); i.e. its calling convention.
282 | BottomGuaranteed -- This Id guarantees never to return;
283 -- it is bottom regardless of its arguments.
284 -- Useful for "error" and other disguised
287 | StrictnessInfo [Demand]
288 Bool -- True <=> there is a worker. There might not be, even for a
289 -- strict function, because:
290 -- (a) the function might be small enough to inline,
291 -- so no need for w/w split
292 -- (b) the strictness info might be "SSS" or something, so no w/w split.
294 -- Worker's Id, if applicable, and a list of the constructors
295 -- mentioned by the wrapper. This is necessary so that the
296 -- renamer can slurp them in. Without this info, the renamer doesn't
297 -- know which data types to slurp in concretely. Remember, for
298 -- strict things we don't put the unfolding in the interface file, to save space.
299 -- This constructor list allows the renamer to behave much as if the
300 -- unfolding *was* in the interface file.
304 mkStrictnessInfo :: [Demand] -> Bool -> StrictnessInfo
306 mkStrictnessInfo xs has_wrkr
307 | all is_lazy xs = NoStrictnessInfo -- Uninteresting
308 | otherwise = StrictnessInfo xs has_wrkr
310 is_lazy (WwLazy False) = True -- NB "Absent" args do *not* count!
311 is_lazy _ = False -- (as they imply a worker)
313 noStrictnessInfo = NoStrictnessInfo
314 mkBottomStrictnessInfo = BottomGuaranteed
316 bottomIsGuaranteed BottomGuaranteed = True
317 bottomIsGuaranteed other = False
319 strictnessInfo (IdInfo _ _ _ strict _ _ _ _) = strict
321 addStrictnessInfo id_info NoStrictnessInfo = id_info
322 addStrictnessInfo (IdInfo a b d _ e f g h) strict = IdInfo a b d strict e f g h
324 ppStrictnessInfo NoStrictnessInfo = empty
325 ppStrictnessInfo BottomGuaranteed = ptext SLIT("_bot_")
327 ppStrictnessInfo (StrictnessInfo wrapper_args wrkr_maybe)
328 = hsep [ptext SLIT("_S_"), text (showList wrapper_args "")]
333 workerExists :: StrictnessInfo -> Bool
334 workerExists (StrictnessInfo _ worker_exists) = worker_exists
335 workerExists other = False
339 %************************************************************************
341 \subsection[unfolding-IdInfo]{Unfolding info about an @Id@}
343 %************************************************************************
346 unfoldInfo (IdInfo _ _ _ _ unfolding _ _ _) = unfolding
348 addUnfoldInfo (IdInfo a b d e _ f g h) uf = IdInfo a b d e uf f g h
351 %************************************************************************
353 \subsection[update-IdInfo]{Update-analysis info about an @Id@}
355 %************************************************************************
360 | SomeUpdateInfo UpdateSpec
362 -- we need Eq/Ord to cross-chk update infos in interfaces
364 -- the form in which we pass update-analysis info between modules:
365 type UpdateSpec = [Int]
369 mkUpdateInfo = SomeUpdateInfo
371 updateInfoMaybe NoUpdateInfo = Nothing
372 updateInfoMaybe (SomeUpdateInfo []) = Nothing
373 updateInfoMaybe (SomeUpdateInfo u) = Just u
376 Text instance so that the update annotations can be read in.
379 #ifdef REALLY_HASKELL_1_3
380 instance Read UpdateInfo where
382 instance Text UpdateInfo where
384 readsPrec p s | null s = panic "IdInfo: empty update pragma?!"
385 | otherwise = [(SomeUpdateInfo (map ok_digit s),"")]
387 ok_digit c | c >= '0' && c <= '2' = ord c - ord '0'
388 | otherwise = panic "IdInfo: not a digit while reading update pragma"
390 updateInfo (IdInfo _ _ _ _ _ update _ _) = update
392 addUpdateInfo id_info NoUpdateInfo = id_info
393 addUpdateInfo (IdInfo a b d e f _ g h) upd_info = IdInfo a b d e f upd_info g h
395 ppUpdateInfo NoUpdateInfo = empty
396 ppUpdateInfo (SomeUpdateInfo []) = empty
397 ppUpdateInfo (SomeUpdateInfo spec) = (<>) (ptext SLIT("_U_ ")) (hcat (map int spec))
400 %************************************************************************
402 \subsection[argUsage-IdInfo]{Argument Usage info about an @Id@}
404 %************************************************************************
409 | SomeArgUsageInfo ArgUsageType
410 -- ??? deriving (Eq, Ord)
412 data ArgUsage = ArgUsage Int -- number of arguments (is linear!)
414 type ArgUsageType = [ArgUsage] -- c_1 -> ... -> BLOB
418 mkArgUsageInfo [] = NoArgUsageInfo
419 mkArgUsageInfo au = SomeArgUsageInfo au
421 getArgUsage :: ArgUsageInfo -> ArgUsageType
422 getArgUsage NoArgUsageInfo = []
423 getArgUsage (SomeArgUsageInfo u) = u
427 argUsageInfo (IdInfo _ _ _ _ _ _ au _) = au
429 addArgUsageInfo id_info NoArgUsageInfo = id_info
430 addArgUsageInfo (IdInfo a b d e f g _ h) au_info = IdInfo a b d e f g au_info h
432 ppArgUsageInfo NoArgUsageInfo = empty
433 ppArgUsageInfo (SomeArgUsageInfo aut) = (<>) (ptext SLIT("_L_ ")) (ppArgUsageType aut)
435 ppArgUsage (ArgUsage n) = int n
436 ppArgUsage (UnknownArgUsage) = char '-'
438 ppArgUsageType aut = hcat
440 hcat (punctuate comma (map ppArgUsage aut)),
444 %************************************************************************
446 \subsection[FBType-IdInfo]{Type of an expression through Foldr/build's eyes}
448 %************************************************************************
453 | SomeFBTypeInfo FBType
455 data FBType = FBType [FBConsum] FBProd deriving (Eq)
457 data FBConsum = FBGoodConsum | FBBadConsum deriving(Eq)
458 data FBProd = FBGoodProd | FBBadProd deriving(Eq)
462 mkFBTypeInfo = SomeFBTypeInfo
464 getFBType :: FBTypeInfo -> Maybe FBType
465 getFBType NoFBTypeInfo = Nothing
466 getFBType (SomeFBTypeInfo u) = Just u
470 fbTypeInfo (IdInfo _ _ _ _ _ _ _ fb) = fb
472 addFBTypeInfo id_info NoFBTypeInfo = id_info
473 addFBTypeInfo (IdInfo a b d e f g h _) fb_info = IdInfo a b d e f g h fb_info
475 ppFBTypeInfo NoFBTypeInfo = empty
476 ppFBTypeInfo (SomeFBTypeInfo (FBType cons prod))
477 = (<>) (ptext SLIT("_F_ ")) (ppFBType cons prod)
479 ppFBType cons prod = hcat
480 ([ char '"' ] ++ map ppCons cons ++ [ char '-', ppProd prod, char '"' ])
482 ppCons FBGoodConsum = char 'G'
483 ppCons FBBadConsum = char 'B'
484 ppProd FBGoodProd = char 'G'
485 ppProd FBBadProd = char 'B'