Commit 9ffadf21 authored by simonpj@microsoft.com's avatar simonpj@microsoft.com

Make record selectors into ordinary functions

This biggish patch addresses Trac #2670.  The main effect is to make
record selectors into ordinary functions, whose unfoldings appear in
interface files, in contrast to their previous existence as magic
"implicit Ids".  This means that the usual machinery of optimisation,
analysis, and inlining applies to them, which was failing before when
the selector was somewhat complicated.  (Which it can be when
strictness annotations, unboxing annotations, and GADTs are involved.)

The change involves the following points

* Changes in Var.lhs to the representation of Var.  Now a LocalId can
  have an IdDetails as well as a GlobalId.  In particular, the
  information that an Id is a record selector is kept in the
  IdDetails.  While compiling the current module, the record selector
  *must* be a LocalId, so that it participates properly in compilation
  (free variables etc).

  This led me to change the (hidden) representation of Var, so that there
  is now only one constructor for Id, not two.

* The IdDetails is persisted into interface files, so that an
  importing module can see which Ids are records selectors.

* In TcTyClDecls, we generate the record-selector bindings in renamed,
  but not typechecked form.  In this way, we can get the typechecker
  to add all the types and so on, which is jolly helpful especially
  when GADTs or type families are involved.  Just like derived
  instance declarations.

  This is the big new chunk of 180 lines of code (much of which is
  commentary).  A call to the same function, mkAuxBinds, is needed in
  TcInstDcls for associated types.

* The typechecker therefore has to pin the correct IdDetails on to 
  the record selector, when it typechecks it.  There was a neat way
  to do this, by adding a new sort of signature to HsBinds.Sig, namely
  IdSig.  This contains an Id (with the correct Name, Type, and IdDetails);
  the type checker uses it as the binder for the final binding.  This
  worked out rather easily.

* Record selectors are no longer "implicit ids", which entails changes to
     IfaceSyn.ifaceDeclSubBndrs
     HscTypes.implicitTyThings
     TidyPgm.getImplicitBinds
  (These three functions must agree.)

* MkId.mkRecordSelectorId is deleted entirely, some 300+ lines (incl
  comments) of very error prone code.  Happy days.

* A TyCon no longer contains the list of record selectors: 
  algTcSelIds is gone

The renamer is unaffected, including the way that import and export of
record selectors is handled.

Other small things

* IfaceSyn.ifaceDeclSubBndrs had a fragile test for whether a data
  constructor had a wrapper.  I've replaced that with an explicit flag
  in the interface file. More robust I hope.

* I renamed isIdVar to isId, which touched a few otherwise-unrelated files.
parent 24a5fdb5
...@@ -318,7 +318,6 @@ data DataCon ...@@ -318,7 +318,6 @@ data DataCon
dcOrigArgTys :: [Type], -- Original argument types dcOrigArgTys :: [Type], -- Original argument types
-- (before unboxing and flattening of strict fields) -- (before unboxing and flattening of strict fields)
dcOrigResTy :: Type, -- Original result type, as seen by the user dcOrigResTy :: Type, -- Original result type, as seen by the user
-- INVARIANT: mentions only dcUnivTyVars
-- NB: for a data instance, the original user result type may -- NB: for a data instance, the original user result type may
-- differ from the DataCon's representation TyCon. Example -- differ from the DataCon's representation TyCon. Example
-- data instance T [a] where MkT :: a -> T [a] -- data instance T [a] where MkT :: a -> T [a]
...@@ -636,8 +635,10 @@ dataConFieldLabels = dcFields ...@@ -636,8 +635,10 @@ dataConFieldLabels = dcFields
-- | Extract the type for any given labelled field of the 'DataCon' -- | Extract the type for any given labelled field of the 'DataCon'
dataConFieldType :: DataCon -> FieldLabel -> Type dataConFieldType :: DataCon -> FieldLabel -> Type
dataConFieldType con label = expectJust "unexpected label" $ dataConFieldType con label
lookup label (dcFields con `zip` dcOrigArgTys con) = case lookup label (dcFields con `zip` dcOrigArgTys con) of
Just ty -> ty
Nothing -> pprPanic "dataConFieldType" (ppr con <+> ppr label)
-- | The strictness markings decided on by the compiler. Does not include those for -- | The strictness markings decided on by the compiler. Does not include those for
-- existential dictionaries. The list is in one-to-one correspondence with the arity of the 'DataCon' -- existential dictionaries. The list is in one-to-one correspondence with the arity of the 'DataCon'
...@@ -726,7 +727,7 @@ dataConUserType :: DataCon -> Type ...@@ -726,7 +727,7 @@ dataConUserType :: DataCon -> Type
-- --
-- rather than: -- rather than:
-- --
-- > T :: forall a c. forall b. (c=[a]) => a -> b -> T c -- > T :: forall a c. forall b. (c~[a]) => a -> b -> T c
-- --
-- NB: If the constructor is part of a data instance, the result type -- NB: If the constructor is part of a data instance, the result type
-- mentions the family tycon, not the internal one. -- mentions the family tycon, not the internal one.
......
...@@ -27,14 +27,14 @@ module Id ( ...@@ -27,14 +27,14 @@ module Id (
-- ** Simple construction -- ** Simple construction
mkGlobalId, mkVanillaGlobal, mkVanillaGlobalWithInfo, mkGlobalId, mkVanillaGlobal, mkVanillaGlobalWithInfo,
mkLocalId, mkLocalIdWithInfo, mkLocalId, mkLocalIdWithInfo, mkExportedLocalId,
mkSysLocal, mkSysLocalM, mkUserLocal, mkUserLocalM, mkSysLocal, mkSysLocalM, mkUserLocal, mkUserLocalM,
mkTemplateLocals, mkTemplateLocalsNum, mkTemplateLocal, mkTemplateLocals, mkTemplateLocalsNum, mkTemplateLocal,
mkWorkerId, mkExportedLocalId, mkWorkerId,
-- ** Taking an Id apart -- ** Taking an Id apart
idName, idType, idUnique, idInfo, idName, idType, idUnique, idInfo, idDetails,
isId, globalIdDetails, idPrimRep, isId, idPrimRep,
recordSelectorFieldLabel, recordSelectorFieldLabel,
-- ** Modifying an Id -- ** Modifying an Id
...@@ -104,8 +104,13 @@ import CoreSyn ( CoreRule, Unfolding ) ...@@ -104,8 +104,13 @@ import CoreSyn ( CoreRule, Unfolding )
import IdInfo import IdInfo
import BasicTypes import BasicTypes
-- Imported and re-exported
import Var( Id, DictId,
idInfo, idDetails, globaliseId,
isId, isLocalId, isGlobalId, isExportedId )
import qualified Var import qualified Var
import Var
import TyCon import TyCon
import Type import Type
import TcType import TcType
...@@ -156,26 +161,19 @@ idName :: Id -> Name ...@@ -156,26 +161,19 @@ idName :: Id -> Name
idName = Var.varName idName = Var.varName
idUnique :: Id -> Unique idUnique :: Id -> Unique
idUnique = varUnique idUnique = Var.varUnique
idType :: Id -> Kind idType :: Id -> Kind
idType = varType idType = Var.varType
idInfo :: Id -> IdInfo
idInfo = varIdInfo
idPrimRep :: Id -> PrimRep idPrimRep :: Id -> PrimRep
idPrimRep id = typePrimRep (idType id) idPrimRep id = typePrimRep (idType id)
globalIdDetails :: Id -> GlobalIdDetails
globalIdDetails = globalIdVarDetails
setIdName :: Id -> Name -> Id setIdName :: Id -> Name -> Id
setIdName = setVarName setIdName = Var.setVarName
setIdUnique :: Id -> Unique -> Id setIdUnique :: Id -> Unique -> Id
setIdUnique = setVarUnique setIdUnique = Var.setVarUnique
-- | Not only does this set the 'Id' 'Type', it also evaluates the type to try and -- | Not only does this set the 'Id' 'Type', it also evaluates the type to try and
-- reduce space usage -- reduce space usage
...@@ -183,10 +181,10 @@ setIdType :: Id -> Type -> Id ...@@ -183,10 +181,10 @@ setIdType :: Id -> Type -> Id
setIdType id ty = seqType ty `seq` Var.setVarType id ty setIdType id ty = seqType ty `seq` Var.setVarType id ty
setIdExported :: Id -> Id setIdExported :: Id -> Id
setIdExported = setIdVarExported setIdExported = Var.setIdExported
setIdNotExported :: Id -> Id setIdNotExported :: Id -> Id
setIdNotExported = setIdVarNotExported setIdNotExported = Var.setIdNotExported
localiseId :: Id -> Id localiseId :: Id -> Id
-- Make an with the same unique and type as the -- Make an with the same unique and type as the
...@@ -199,11 +197,8 @@ localiseId id ...@@ -199,11 +197,8 @@ localiseId id
where where
name = idName id name = idName id
globaliseId :: GlobalIdDetails -> Id -> Id
globaliseId = globaliseIdVar
lazySetIdInfo :: Id -> IdInfo -> Id lazySetIdInfo :: Id -> IdInfo -> Id
lazySetIdInfo = lazySetVarIdInfo lazySetIdInfo = Var.lazySetIdInfo
setIdInfo :: Id -> IdInfo -> Id setIdInfo :: Id -> IdInfo -> Id
setIdInfo id info = seqIdInfo info `seq` (lazySetIdInfo id info) setIdInfo id info = seqIdInfo info `seq` (lazySetIdInfo id info)
...@@ -240,8 +235,8 @@ Anyway, we removed it in March 2008. ...@@ -240,8 +235,8 @@ Anyway, we removed it in March 2008.
\begin{code} \begin{code}
-- | For an explanation of global vs. local 'Id's, see "Var#globalvslocal" -- | For an explanation of global vs. local 'Id's, see "Var#globalvslocal"
mkGlobalId :: GlobalIdDetails -> Name -> Type -> IdInfo -> Id mkGlobalId :: IdDetails -> Name -> Type -> IdInfo -> Id
mkGlobalId = mkGlobalIdVar mkGlobalId = Var.mkGlobalVar
-- | Make a global 'Id' without any extra information at all -- | Make a global 'Id' without any extra information at all
mkVanillaGlobal :: Name -> Type -> Id mkVanillaGlobal :: Name -> Type -> Id
...@@ -249,7 +244,7 @@ mkVanillaGlobal name ty = mkVanillaGlobalWithInfo name ty vanillaIdInfo ...@@ -249,7 +244,7 @@ mkVanillaGlobal name ty = mkVanillaGlobalWithInfo name ty vanillaIdInfo
-- | Make a global 'Id' with no global information but some generic 'IdInfo' -- | Make a global 'Id' with no global information but some generic 'IdInfo'
mkVanillaGlobalWithInfo :: Name -> Type -> IdInfo -> Id mkVanillaGlobalWithInfo :: Name -> Type -> IdInfo -> Id
mkVanillaGlobalWithInfo = mkGlobalId VanillaGlobal mkVanillaGlobalWithInfo = mkGlobalId VanillaId
-- | For an explanation of global vs. local 'Id's, see "Var#globalvslocal" -- | For an explanation of global vs. local 'Id's, see "Var#globalvslocal"
...@@ -257,16 +252,18 @@ mkLocalId :: Name -> Type -> Id ...@@ -257,16 +252,18 @@ mkLocalId :: Name -> Type -> Id
mkLocalId name ty = mkLocalIdWithInfo name ty vanillaIdInfo mkLocalId name ty = mkLocalIdWithInfo name ty vanillaIdInfo
mkLocalIdWithInfo :: Name -> Type -> IdInfo -> Id mkLocalIdWithInfo :: Name -> Type -> IdInfo -> Id
mkLocalIdWithInfo = mkLocalIdVar mkLocalIdWithInfo name ty info = Var.mkLocalVar VanillaId name ty info
-- Note [Free type variables] -- Note [Free type variables]
-- | Create a local 'Id' that is marked as exported. This prevents things attached to it from being removed as dead code. -- | Create a local 'Id' that is marked as exported.
-- This prevents things attached to it from being removed as dead code.
mkExportedLocalId :: Name -> Type -> Id mkExportedLocalId :: Name -> Type -> Id
mkExportedLocalId name ty = mkExportedLocalIdVar name ty vanillaIdInfo mkExportedLocalId name ty = Var.mkExportedLocalVar VanillaId name ty vanillaIdInfo
-- Note [Free type variables] -- Note [Free type variables]
-- | Create a system local 'Id'. These are local 'Id's (see "Var#globalvslocal") that are created by the compiler out of thin air -- | Create a system local 'Id'. These are local 'Id's (see "Var#globalvslocal")
-- that are created by the compiler out of thin air
mkSysLocal :: FastString -> Unique -> Type -> Id mkSysLocal :: FastString -> Unique -> Type -> Id
mkSysLocal fs uniq ty = mkLocalId (mkSystemVarName uniq fs) ty mkSysLocal fs uniq ty = mkLocalId (mkSystemVarName uniq fs) ty
...@@ -309,29 +306,6 @@ mkTemplateLocalsNum n tys = zipWith mkTemplateLocal [n..] tys ...@@ -309,29 +306,6 @@ mkTemplateLocalsNum n tys = zipWith mkTemplateLocal [n..] tys
\end{code} \end{code}
%************************************************************************
%* *
\subsection{Basic predicates on @Id@s}
%* *
%************************************************************************
\begin{code}
isId :: Id -> Bool
isId = isIdVar
-- | For an explanation of global vs. local 'Id's, see "Var#globalvslocal"
isLocalId :: Id -> Bool
isLocalId = isLocalIdVar
-- | For an explanation of global vs. local 'Id's, see "Var#globalvslocal"
isGlobalId :: Id -> Bool
isGlobalId = isGlobalIdVar
-- | Determines whether an 'Id' is marked as exported and hence will not be considered dead code
isExportedId :: Id -> Bool
isExportedId = isExportedIdVar
\end{code}
%************************************************************************ %************************************************************************
%* * %* *
\subsection{Special Ids} \subsection{Special Ids}
...@@ -342,8 +316,8 @@ isExportedId = isExportedIdVar ...@@ -342,8 +316,8 @@ isExportedId = isExportedIdVar
-- | If the 'Id' is that for a record selector, extract the 'sel_tycon' and label. Panic otherwise -- | If the 'Id' is that for a record selector, extract the 'sel_tycon' and label. Panic otherwise
recordSelectorFieldLabel :: Id -> (TyCon, FieldLabel) recordSelectorFieldLabel :: Id -> (TyCon, FieldLabel)
recordSelectorFieldLabel id recordSelectorFieldLabel id
= case globalIdDetails id of = case Var.idDetails id of
RecordSelId { sel_tycon = tycon, sel_label = lbl } -> (tycon,lbl) RecSelId { sel_tycon = tycon } -> (tycon, idName id)
_ -> panic "recordSelectorFieldLabel" _ -> panic "recordSelectorFieldLabel"
isRecordSelector :: Id -> Bool isRecordSelector :: Id -> Bool
...@@ -357,44 +331,44 @@ isPrimOpId_maybe :: Id -> Maybe PrimOp ...@@ -357,44 +331,44 @@ isPrimOpId_maybe :: Id -> Maybe PrimOp
isFCallId_maybe :: Id -> Maybe ForeignCall isFCallId_maybe :: Id -> Maybe ForeignCall
isDataConWorkId_maybe :: Id -> Maybe DataCon isDataConWorkId_maybe :: Id -> Maybe DataCon
isRecordSelector id = case globalIdDetails id of isRecordSelector id = case Var.idDetails id of
RecordSelId {} -> True RecSelId {} -> True
_ -> False _ -> False
isNaughtyRecordSelector id = case globalIdDetails id of isNaughtyRecordSelector id = case Var.idDetails id of
RecordSelId { sel_naughty = n } -> n RecSelId { sel_naughty = n } -> n
_ -> False _ -> False
isClassOpId_maybe id = case globalIdDetails id of isClassOpId_maybe id = case Var.idDetails id of
ClassOpId cls -> Just cls ClassOpId cls -> Just cls
_other -> Nothing _other -> Nothing
isPrimOpId id = case globalIdDetails id of isPrimOpId id = case Var.idDetails id of
PrimOpId _ -> True PrimOpId _ -> True
_ -> False _ -> False
isPrimOpId_maybe id = case globalIdDetails id of isPrimOpId_maybe id = case Var.idDetails id of
PrimOpId op -> Just op PrimOpId op -> Just op
_ -> Nothing _ -> Nothing
isFCallId id = case globalIdDetails id of isFCallId id = case Var.idDetails id of
FCallId _ -> True FCallId _ -> True
_ -> False _ -> False
isFCallId_maybe id = case globalIdDetails id of isFCallId_maybe id = case Var.idDetails id of
FCallId call -> Just call FCallId call -> Just call
_ -> Nothing _ -> Nothing
isDataConWorkId id = case globalIdDetails id of isDataConWorkId id = case Var.idDetails id of
DataConWorkId _ -> True DataConWorkId _ -> True
_ -> False _ -> False
isDataConWorkId_maybe id = case globalIdDetails id of isDataConWorkId_maybe id = case Var.idDetails id of
DataConWorkId con -> Just con DataConWorkId con -> Just con
_ -> Nothing _ -> Nothing
isDataConId_maybe :: Id -> Maybe DataCon isDataConId_maybe :: Id -> Maybe DataCon
isDataConId_maybe id = case globalIdDetails id of isDataConId_maybe id = case Var.idDetails id of
DataConWorkId con -> Just con DataConWorkId con -> Just con
DataConWrapId con -> Just con DataConWrapId con -> Just con
_ -> Nothing _ -> Nothing
...@@ -417,7 +391,7 @@ hasNoBinding :: Id -> Bool ...@@ -417,7 +391,7 @@ hasNoBinding :: Id -> Bool
-- they aren't any more. Instead, we inject a binding for -- they aren't any more. Instead, we inject a binding for
-- them at the CorePrep stage. -- them at the CorePrep stage.
-- EXCEPT: unboxed tuples, which definitely have no binding -- EXCEPT: unboxed tuples, which definitely have no binding
hasNoBinding id = case globalIdDetails id of hasNoBinding id = case Var.idDetails id of
PrimOpId _ -> True -- See Note [Primop wrappers] PrimOpId _ -> True -- See Note [Primop wrappers]
FCallId _ -> True FCallId _ -> True
DataConWorkId dc -> isUnboxedTupleCon dc DataConWorkId dc -> isUnboxedTupleCon dc
...@@ -428,11 +402,10 @@ isImplicitId :: Id -> Bool ...@@ -428,11 +402,10 @@ isImplicitId :: Id -> Bool
-- declarations, so we don't need to put its signature in an interface -- declarations, so we don't need to put its signature in an interface
-- file, even if it's mentioned in some other interface unfolding. -- file, even if it's mentioned in some other interface unfolding.
isImplicitId id isImplicitId id
= case globalIdDetails id of = case Var.idDetails id of
RecordSelId {} -> True
FCallId _ -> True FCallId _ -> True
ClassOpId _ -> True
PrimOpId _ -> True PrimOpId _ -> True
ClassOpId _ -> True
DataConWorkId _ -> True DataConWorkId _ -> True
DataConWrapId _ -> True DataConWrapId _ -> True
-- These are are implied by their type or class decl; -- These are are implied by their type or class decl;
...@@ -469,13 +442,13 @@ isDeadBinder bndr | isId bndr = isDeadOcc (idOccInfo bndr) ...@@ -469,13 +442,13 @@ isDeadBinder bndr | isId bndr = isDeadOcc (idOccInfo bndr)
\begin{code} \begin{code}
isTickBoxOp :: Id -> Bool isTickBoxOp :: Id -> Bool
isTickBoxOp id = isTickBoxOp id =
case globalIdDetails id of case Var.idDetails id of
TickBoxOpId _ -> True TickBoxOpId _ -> True
_ -> False _ -> False
isTickBoxOp_maybe :: Id -> Maybe TickBoxOp isTickBoxOp_maybe :: Id -> Maybe TickBoxOp
isTickBoxOp_maybe id = isTickBoxOp_maybe id =
case globalIdDetails id of case Var.idDetails id of
TickBoxOpId tick -> Just tick TickBoxOpId tick -> Just tick
_ -> Nothing _ -> Nothing
\end{code} \end{code}
......
...@@ -9,8 +9,8 @@ Haskell. [WDP 94/11]) ...@@ -9,8 +9,8 @@ Haskell. [WDP 94/11])
\begin{code} \begin{code}
module IdInfo ( module IdInfo (
-- * The GlobalIdDetails type -- * The IdDetails type
GlobalIdDetails(..), notGlobalId, -- Not abstract IdDetails(..), pprIdDetails,
-- * The IdInfo type -- * The IdInfo type
IdInfo, -- Abstract IdInfo, -- Abstract
...@@ -234,31 +234,23 @@ seqNewDemandInfo (Just dmd) = seqDemand dmd ...@@ -234,31 +234,23 @@ seqNewDemandInfo (Just dmd) = seqDemand dmd
%************************************************************************ %************************************************************************
%* * %* *
\subsection{GlobalIdDetails} IdDetails
%* * %* *
%************************************************************************ %************************************************************************
This type is here (rather than in Id.lhs) mainly because there's
an IdInfo.hi-boot, but no Id.hi-boot, and GlobalIdDetails is imported
(recursively) by Var.lhs.
\begin{code} \begin{code}
-- | Information pertaining to global 'Id's. See "Var#globalvslocal" for the distinction -- | The 'IdDetails' of an 'Id' give stable, and necessary,
-- between global and local in this context -- information about the Id.
data GlobalIdDetails data IdDetails
= VanillaGlobal -- ^ The 'Id' is imported from elsewhere or is a default method 'Id' = VanillaId
-- | The 'Id' for a record selector -- | The 'Id' for a record selector
| RecordSelId | RecSelId
{ sel_tycon :: TyCon -- ^ For a data type family, this is the /instance/ 'TyCon' { sel_tycon :: TyCon -- ^ For a data type family, this is the /instance/ 'TyCon'
-- not the family 'TyCon' -- not the family 'TyCon'
, sel_label :: FieldLabel
, sel_naughty :: Bool -- True <=> a "naughty" selector which can't actually exist, for example @x@ in: , sel_naughty :: Bool -- True <=> a "naughty" selector which can't actually exist, for example @x@ in:
-- -- data T = forall a. MkT { x :: a }
-- > data T = forall a. MkT { x :: a } } -- See Note [Naughty record selectors] in TcTyClsDecls
}
-- See Note [Naughty record selectors]
-- with MkId.mkRecordSelectorId
| DataConWorkId DataCon -- ^ The 'Id' is for a data constructor /worker/ | DataConWorkId DataCon -- ^ The 'Id' is for a data constructor /worker/
| DataConWrapId DataCon -- ^ The 'Id' is for a data constructor /wrapper/ | DataConWrapId DataCon -- ^ The 'Id' is for a data constructor /wrapper/
...@@ -275,25 +267,29 @@ data GlobalIdDetails ...@@ -275,25 +267,29 @@ data GlobalIdDetails
| TickBoxOpId TickBoxOp -- ^ The 'Id' is for a HPC tick box (both traditional and binary) | TickBoxOpId TickBoxOp -- ^ The 'Id' is for a HPC tick box (both traditional and binary)
| NotGlobalId -- ^ Used as a convenient extra return value from 'globalIdDetails' | DFunId -- ^ A dictionary function. We don't use this in an essential way,
-- currently, but it's kind of nice that we can keep track of
-- | An entirely unhelpful 'GlobalIdDetails' -- which Ids are DFuns, across module boundaries too
notGlobalId :: GlobalIdDetails
notGlobalId = NotGlobalId
instance Outputable IdDetails where
instance Outputable GlobalIdDetails where ppr = pprIdDetails
ppr NotGlobalId = ptext (sLit "[***NotGlobalId***]")
ppr VanillaGlobal = ptext (sLit "[GlobalId]") pprIdDetails :: IdDetails -> SDoc
ppr (DataConWorkId _) = ptext (sLit "[DataCon]") pprIdDetails VanillaId = empty
ppr (DataConWrapId _) = ptext (sLit "[DataConWrapper]") pprIdDetails (RecSelId {}) = ptext (sLit "[RecSel]")
ppr (ClassOpId _) = ptext (sLit "[ClassOp]") pprIdDetails (DataConWorkId _) = ptext (sLit "[DataCon]")
ppr (PrimOpId _) = ptext (sLit "[PrimOp]") pprIdDetails (DataConWrapId _) = ptext (sLit "[DataConWrapper]")
ppr (FCallId _) = ptext (sLit "[ForeignCall]") pprIdDetails (ClassOpId _) = ptext (sLit "[ClassOp]")
ppr (TickBoxOpId _) = ptext (sLit "[TickBoxOp]") pprIdDetails (PrimOpId _) = ptext (sLit "[PrimOp]")
ppr (RecordSelId {}) = ptext (sLit "[RecSel]") pprIdDetails (FCallId _) = ptext (sLit "[ForeignCall]")
pprIdDetails (TickBoxOpId _) = ptext (sLit "[TickBoxOp]")
pprIdDetails DFunId = ptext (sLit "[DFunId]")
\end{code} \end{code}
%************************************************************************ %************************************************************************
%* * %* *
\subsection{The main IdInfo type} \subsection{The main IdInfo type}
......
\begin{code} \begin{code}
module IdInfo where module IdInfo where
import Outputable
data IdInfo data IdInfo
data GlobalIdDetails data IdDetails
notGlobalId :: GlobalIdDetails pprIdDetails :: IdDetails -> SDoc
seqIdInfo :: IdInfo -> ()
\end{code} \end{code}
\ No newline at end of file
This diff is collapsed.
...@@ -28,21 +28,22 @@ module Var ( ...@@ -28,21 +28,22 @@ module Var (
-- * The main data type -- * The main data type
Var, Var,
-- ** Constructing 'Var's
mkLocalIdVar, mkExportedLocalIdVar, mkGlobalIdVar,
-- ** Taking 'Var's apart -- ** Taking 'Var's apart
varName, varUnique, varType, varIdInfo, globalIdVarDetails, varName, varUnique, varType,
-- ** Modifying 'Var's -- ** Modifying 'Var's
setVarName, setVarUnique, setVarType, setVarName, setVarUnique, setVarType,
setIdVarExported, setIdVarNotExported,
globaliseIdVar, lazySetVarIdInfo, -- ** Constructing, taking apart, modifying 'Id's
mkGlobalVar, mkLocalVar, mkExportedLocalVar,
idInfo, idDetails,
lazySetIdInfo, setIdDetails, globaliseId,
setIdExported, setIdNotExported,
-- ** Predicates -- ** Predicates
isCoVar, isIdVar, isTyVar, isTcTyVar, isCoVar, isId, isTyVar, isTcTyVar,
isLocalVar, isLocalIdVar, isLocalVar, isLocalId,
isGlobalIdVar, isExportedIdVar, isGlobalId, isExportedId,
mustHaveLocalBinding, mustHaveLocalBinding,
-- * Type variable data type -- * Type variable data type
...@@ -77,8 +78,7 @@ module Var ( ...@@ -77,8 +78,7 @@ module Var (
import {-# SOURCE #-} TypeRep( Type, Kind ) import {-# SOURCE #-} TypeRep( Type, Kind )
import {-# SOURCE #-} TcType( TcTyVarDetails, pprTcTyVarDetails ) import {-# SOURCE #-} TcType( TcTyVarDetails, pprTcTyVarDetails )
import {-# SOURCE #-} IdInfo( GlobalIdDetails, notGlobalId, import {-# SOURCE #-} IdInfo( IdDetails, IdInfo, pprIdDetails )
IdInfo )
import {-# SOURCE #-} TypeRep( isCoercionKind ) import {-# SOURCE #-} TypeRep( isCoercionKind )
import Name hiding (varName) import Name hiding (varName)
...@@ -122,25 +122,22 @@ data Var ...@@ -122,25 +122,22 @@ data Var
varType :: Kind, varType :: Kind,
tcTyVarDetails :: TcTyVarDetails } tcTyVarDetails :: TcTyVarDetails }
| GlobalId { -- Used for imported Ids, dict selectors etc | Id {
-- See Note [GlobalId/LocalId] below
varName :: !Name, -- Always an External or WiredIn Name
realUnique :: FastInt,
varType :: Type,
idInfo_ :: IdInfo,
gblDetails :: GlobalIdDetails }
| LocalId { -- Used for locally-defined Ids
-- See Note [GlobalId/LocalId] below
varName :: !Name, varName :: !Name,
realUnique :: FastInt, realUnique :: FastInt,
varType :: Type, varType :: Type,
idInfo_ :: IdInfo, idScope :: IdScope,
lclDetails :: LocalIdDetails } idDetails :: IdDetails, -- Stable, doesn't change
idInfo :: IdInfo } -- Unstable, updated by simplifier
data LocalIdDetails data IdScope -- See Note [GlobalId/LocalId]
= GlobalId