2 % (c) The University of Glasgow 2006
3 % (c) The GRASP/AQUA Project, Glasgow University, 1992-1998
5 \section[Id]{@Ids@: Value and constructor identifiers}
11 -- Simple construction
12 mkGlobalId, mkLocalId, mkLocalIdWithInfo,
13 mkSysLocal, mkUserLocal, mkVanillaGlobal,
14 mkTemplateLocals, mkTemplateLocalsNum, mkWildId, mkTemplateLocal,
15 mkWorkerId, mkExportedLocalId,
18 idName, idType, idUnique, idInfo,
19 isId, globalIdDetails, idPrimRep,
20 recordSelectorFieldLabel,
23 setIdName, setIdUnique, Id.setIdType, setIdExported, setIdNotExported,
24 setIdInfo, lazySetIdInfo, modifyIdInfo, maybeModifyIdInfo,
25 zapLamIdInfo, zapDemandIdInfo,
28 isImplicitId, isDeadBinder, isDictId,
29 isExportedId, isLocalId, isGlobalId,
30 isRecordSelector, isNaughtyRecordSelector,
32 isPrimOpId, isPrimOpId_maybe,
33 isFCallId, isFCallId_maybe,
34 isDataConWorkId, isDataConWorkId_maybe, isDataConId_maybe, idDataCon,
35 isBottomingId, idIsFrom,
38 -- Inline pragma stuff
39 idInlinePragma, setInlinePragma, modifyInlinePragma,
42 -- One shot lambda stuff
43 isOneShotBndr, isOneShotLambda, isStateHackType,
44 setOneShotLambda, clearOneShotLambda,
50 setIdNewStrictness, zapIdNewStrictness,
66 idNewDemandInfo, idNewDemandInfo_maybe,
67 idNewStrictness, idNewStrictness_maybe,
70 idSpecialisation, idCoreRules, idHasRules,
76 newStrictnessFromOld -- Temporary
81 #include "HsVersions.h"
86 import Var hiding (mkLocalId, mkGlobalId, mkExportedLocalId)
93 import qualified Demand
107 -- infixl so you can say (id `set` a `set` b)
108 infixl 1 `setIdUnfolding`,
110 `setIdNewDemandInfo`,
111 `setIdNewStrictness`,
113 `setIdSpecialisation`,
116 #ifdef OLD_STRICTNESS
125 %************************************************************************
127 \subsection{Simple Id construction}
129 %************************************************************************
131 Absolutely all Ids are made by mkId. It is just like Var.mkId,
132 but in addition it pins free-tyvar-info onto the Id's type,
133 where it can easily be found.
136 mkLocalIdWithInfo :: Name -> Type -> IdInfo -> Id
137 mkLocalIdWithInfo name ty info = Var.mkLocalId name (addFreeTyVars ty) info
139 mkExportedLocalId :: Name -> Type -> Id
140 mkExportedLocalId name ty = Var.mkExportedLocalId name (addFreeTyVars ty) vanillaIdInfo
142 mkGlobalId :: GlobalIdDetails -> Name -> Type -> IdInfo -> Id
143 mkGlobalId details name ty info = Var.mkGlobalId details name (addFreeTyVars ty) info
147 mkLocalId :: Name -> Type -> Id
148 mkLocalId name ty = mkLocalIdWithInfo name ty vanillaIdInfo
150 -- SysLocal: for an Id being created by the compiler out of thin air...
151 mkSysLocal :: FastString -> Unique -> Type -> Id
152 mkSysLocal fs uniq ty = mkLocalId (mkSystemVarName uniq fs) ty
155 -- UserLocal: an Id with a name the user might recognize...
156 mkUserLocal :: OccName -> Unique -> Type -> SrcLoc -> Id
157 mkVanillaGlobal :: Name -> Type -> IdInfo -> Id
159 mkUserLocal occ uniq ty loc = mkLocalId (mkInternalName uniq occ loc) ty
160 mkVanillaGlobal = mkGlobalId VanillaGlobal
163 Make some local @Ids@ for a template @CoreExpr@. These have bogus
164 @Uniques@, but that's OK because the templates are supposed to be
165 instantiated before use.
168 -- "Wild Id" typically used when you need a binder that you don't expect to use
169 mkWildId :: Type -> Id
170 mkWildId ty = mkSysLocal FSLIT("wild") (mkBuiltinUnique 1) ty
172 mkWorkerId :: Unique -> Id -> Type -> Id
173 -- A worker gets a local name. CoreTidy will externalise it if necessary.
174 mkWorkerId uniq unwrkr ty
175 = mkLocalId wkr_name ty
177 wkr_name = mkInternalName uniq (mkWorkerOcc (getOccName unwrkr)) (getSrcLoc unwrkr)
179 -- "Template locals" typically used in unfoldings
180 mkTemplateLocals :: [Type] -> [Id]
181 mkTemplateLocals tys = zipWith mkTemplateLocal [1..] tys
183 mkTemplateLocalsNum :: Int -> [Type] -> [Id]
184 -- The Int gives the starting point for unique allocation
185 mkTemplateLocalsNum n tys = zipWith mkTemplateLocal [n..] tys
187 mkTemplateLocal :: Int -> Type -> Id
188 mkTemplateLocal i ty = mkSysLocal FSLIT("tpl") (mkBuiltinUnique i) ty
192 %************************************************************************
194 \subsection[Id-general-funs]{General @Id@-related functions}
196 %************************************************************************
199 setIdType :: Id -> Type -> Id
200 -- Add free tyvar info to the type
201 setIdType id ty = seqType ty `seq` Var.setIdType id (addFreeTyVars ty)
203 idPrimRep :: Id -> PrimRep
204 idPrimRep id = typePrimRep (idType id)
208 %************************************************************************
210 \subsection{Special Ids}
212 %************************************************************************
215 recordSelectorFieldLabel :: Id -> (TyCon, FieldLabel)
216 recordSelectorFieldLabel id = case globalIdDetails id of
217 RecordSelId tycon lbl _ -> (tycon,lbl)
218 other -> panic "recordSelectorFieldLabel"
220 isRecordSelector id = case globalIdDetails id of
221 RecordSelId {} -> True
224 isNaughtyRecordSelector id = case globalIdDetails id of
225 RecordSelId { sel_naughty = n } -> n
228 isClassOpId_maybe id = case globalIdDetails id of
229 ClassOpId cls -> Just cls
232 isPrimOpId id = case globalIdDetails id of
236 isPrimOpId_maybe id = case globalIdDetails id of
237 PrimOpId op -> Just op
240 isFCallId id = case globalIdDetails id of
244 isFCallId_maybe id = case globalIdDetails id of
245 FCallId call -> Just call
248 isDataConWorkId id = case globalIdDetails id of
249 DataConWorkId _ -> True
252 isDataConWorkId_maybe id = case globalIdDetails id of
253 DataConWorkId con -> Just con
256 isDataConId_maybe :: Id -> Maybe DataCon
257 isDataConId_maybe id = case globalIdDetails id of
258 DataConWorkId con -> Just con
259 DataConWrapId con -> Just con
262 idDataCon :: Id -> DataCon
263 -- Get from either the worker or the wrapper to the DataCon
264 -- Currently used only in the desugarer
265 -- INVARIANT: idDataCon (dataConWrapId d) = d
266 -- (Remember, dataConWrapId can return either the wrapper or the worker.)
267 idDataCon id = case globalIdDetails id of
268 DataConWorkId con -> con
269 DataConWrapId con -> con
270 other -> pprPanic "idDataCon" (ppr id)
273 isDictId :: Id -> Bool
274 isDictId id = isDictTy (idType id)
276 -- hasNoBinding returns True of an Id which may not have a
277 -- binding, even though it is defined in this module.
278 -- Data constructor workers used to be things of this kind, but
279 -- they aren't any more. Instead, we inject a binding for
280 -- them at the CorePrep stage.
281 -- EXCEPT: unboxed tuples, which definitely have no binding
282 hasNoBinding id = case globalIdDetails id of
285 DataConWorkId dc -> isUnboxedTupleCon dc
288 isImplicitId :: Id -> Bool
289 -- isImplicitId tells whether an Id's info is implied by other
290 -- declarations, so we don't need to put its signature in an interface
291 -- file, even if it's mentioned in some other interface unfolding.
293 = case globalIdDetails id of
294 RecordSelId {} -> True
298 DataConWorkId _ -> True
299 DataConWrapId _ -> True
300 -- These are are implied by their type or class decl;
301 -- remember that all type and class decls appear in the interface file.
302 -- The dfun id is not an implicit Id; it must *not* be omitted, because
303 -- it carries version info for the instance decl
306 idIsFrom :: Module -> Id -> Bool
307 idIsFrom mod id = nameIsLocalOrFrom mod (idName id)
311 isDeadBinder :: Id -> Bool
312 isDeadBinder bndr | isId bndr = isDeadOcc (idOccInfo bndr)
313 | otherwise = False -- TyVars count as not dead
317 %************************************************************************
319 \subsection{IdInfo stuff}
321 %************************************************************************
324 ---------------------------------
326 idArity :: Id -> Arity
327 idArity id = arityInfo (idInfo id)
329 setIdArity :: Id -> Arity -> Id
330 setIdArity id arity = modifyIdInfo (`setArityInfo` arity) id
332 #ifdef OLD_STRICTNESS
333 ---------------------------------
335 idStrictness :: Id -> StrictnessInfo
336 idStrictness id = strictnessInfo (idInfo id)
338 setIdStrictness :: Id -> StrictnessInfo -> Id
339 setIdStrictness id strict_info = modifyIdInfo (`setStrictnessInfo` strict_info) id
342 -- isBottomingId returns true if an application to n args would diverge
343 isBottomingId :: Id -> Bool
344 isBottomingId id = isBottomingSig (idNewStrictness id)
346 idNewStrictness_maybe :: Id -> Maybe StrictSig
347 idNewStrictness :: Id -> StrictSig
349 idNewStrictness_maybe id = newStrictnessInfo (idInfo id)
350 idNewStrictness id = idNewStrictness_maybe id `orElse` topSig
352 setIdNewStrictness :: Id -> StrictSig -> Id
353 setIdNewStrictness id sig = modifyIdInfo (`setNewStrictnessInfo` Just sig) id
355 zapIdNewStrictness :: Id -> Id
356 zapIdNewStrictness id = modifyIdInfo (`setNewStrictnessInfo` Nothing) id
358 ---------------------------------
360 idWorkerInfo :: Id -> WorkerInfo
361 idWorkerInfo id = workerInfo (idInfo id)
363 setIdWorkerInfo :: Id -> WorkerInfo -> Id
364 setIdWorkerInfo id work_info = modifyIdInfo (`setWorkerInfo` work_info) id
366 ---------------------------------
368 idUnfolding :: Id -> Unfolding
369 idUnfolding id = unfoldingInfo (idInfo id)
371 setIdUnfolding :: Id -> Unfolding -> Id
372 setIdUnfolding id unfolding = modifyIdInfo (`setUnfoldingInfo` unfolding) id
374 #ifdef OLD_STRICTNESS
375 ---------------------------------
377 idDemandInfo :: Id -> Demand.Demand
378 idDemandInfo id = demandInfo (idInfo id)
380 setIdDemandInfo :: Id -> Demand.Demand -> Id
381 setIdDemandInfo id demand_info = modifyIdInfo (`setDemandInfo` demand_info) id
384 idNewDemandInfo_maybe :: Id -> Maybe NewDemand.Demand
385 idNewDemandInfo :: Id -> NewDemand.Demand
387 idNewDemandInfo_maybe id = newDemandInfo (idInfo id)
388 idNewDemandInfo id = newDemandInfo (idInfo id) `orElse` NewDemand.topDmd
390 setIdNewDemandInfo :: Id -> NewDemand.Demand -> Id
391 setIdNewDemandInfo id dmd = modifyIdInfo (`setNewDemandInfo` Just dmd) id
393 ---------------------------------
395 idSpecialisation :: Id -> SpecInfo
396 idSpecialisation id = specInfo (idInfo id)
398 idCoreRules :: Id -> [CoreRule]
399 idCoreRules id = specInfoRules (idSpecialisation id)
401 idHasRules :: Id -> Bool
402 idHasRules id = not (isEmptySpecInfo (idSpecialisation id))
404 setIdSpecialisation :: Id -> SpecInfo -> Id
405 setIdSpecialisation id spec_info = modifyIdInfo (`setSpecInfo` spec_info) id
407 ---------------------------------
409 idCafInfo :: Id -> CafInfo
410 #ifdef OLD_STRICTNESS
411 idCafInfo id = case cgInfo (idInfo id) of
412 NoCgInfo -> pprPanic "idCafInfo" (ppr id)
413 info -> cgCafInfo info
415 idCafInfo id = cafInfo (idInfo id)
418 setIdCafInfo :: Id -> CafInfo -> Id
419 setIdCafInfo id caf_info = modifyIdInfo (`setCafInfo` caf_info) id
421 ---------------------------------
423 #ifdef OLD_STRICTNESS
424 idCprInfo :: Id -> CprInfo
425 idCprInfo id = cprInfo (idInfo id)
427 setIdCprInfo :: Id -> CprInfo -> Id
428 setIdCprInfo id cpr_info = modifyIdInfo (`setCprInfo` cpr_info) id
431 ---------------------------------
433 idOccInfo :: Id -> OccInfo
434 idOccInfo id = occInfo (idInfo id)
436 setIdOccInfo :: Id -> OccInfo -> Id
437 setIdOccInfo id occ_info = modifyIdInfo (`setOccInfo` occ_info) id
441 ---------------------------------
443 The inline pragma tells us to be very keen to inline this Id, but it's still
444 OK not to if optimisation is switched off.
447 idInlinePragma :: Id -> InlinePragInfo
448 idInlinePragma id = inlinePragInfo (idInfo id)
450 setInlinePragma :: Id -> InlinePragInfo -> Id
451 setInlinePragma id prag = modifyIdInfo (`setInlinePragInfo` prag) id
453 modifyInlinePragma :: Id -> (InlinePragInfo -> InlinePragInfo) -> Id
454 modifyInlinePragma id fn = modifyIdInfo (\info -> info `setInlinePragInfo` (fn (inlinePragInfo info))) id
458 ---------------------------------
461 idLBVarInfo :: Id -> LBVarInfo
462 idLBVarInfo id = lbvarInfo (idInfo id)
464 isOneShotBndr :: Id -> Bool
465 -- This one is the "business end", called externally.
466 -- Its main purpose is to encapsulate the Horrible State Hack
467 isOneShotBndr id = isOneShotLambda id || isStateHackType (idType id)
469 isStateHackType :: Type -> Bool
474 = case splitTyConApp_maybe ty of
475 Just (tycon,_) -> tycon == statePrimTyCon
477 -- This is a gross hack. It claims that
478 -- every function over realWorldStatePrimTy is a one-shot
479 -- function. This is pretty true in practice, and makes a big
480 -- difference. For example, consider
481 -- a `thenST` \ r -> ...E...
482 -- The early full laziness pass, if it doesn't know that r is one-shot
483 -- will pull out E (let's say it doesn't mention r) to give
484 -- let lvl = E in a `thenST` \ r -> ...lvl...
485 -- When `thenST` gets inlined, we end up with
486 -- let lvl = E in \s -> case a s of (r, s') -> ...lvl...
487 -- and we don't re-inline E.
489 -- It would be better to spot that r was one-shot to start with, but
490 -- I don't want to rely on that.
492 -- Another good example is in fill_in in PrelPack.lhs. We should be able to
493 -- spot that fill_in has arity 2 (and when Keith is done, we will) but we can't yet.
496 -- The OneShotLambda functions simply fiddle with the IdInfo flag
497 isOneShotLambda :: Id -> Bool
498 isOneShotLambda id = case idLBVarInfo id of
499 IsOneShotLambda -> True
502 setOneShotLambda :: Id -> Id
503 setOneShotLambda id = modifyIdInfo (`setLBVarInfo` IsOneShotLambda) id
505 clearOneShotLambda :: Id -> Id
506 clearOneShotLambda id
507 | isOneShotLambda id = modifyIdInfo (`setLBVarInfo` NoLBVarInfo) id
510 -- But watch out: this may change the type of something else
512 -- If we change the one-shot-ness of x, f's type changes
516 zapLamIdInfo :: Id -> Id
517 zapLamIdInfo id = maybeModifyIdInfo (zapLamInfo (idInfo id)) id
519 zapDemandIdInfo id = maybeModifyIdInfo (zapDemandInfo (idInfo id)) id