-tcLookupDataCon :: Name -> TcM s (DataCon, [TcType], TcType)
-tcLookupDataCon con_name
- = tcLookupValue con_name `thenNF_Tc` \ con_id ->
- case isDataConId_maybe con_id of {
- Nothing -> failWithTc (badCon con_id);
- Just data_con ->
-
- tcInstId con_id `thenNF_Tc` \ (_, _, con_tau) ->
- -- Ignore the con_theta; overloaded constructors only
- -- behave differently when called, not when used for
- -- matching.
- let
- (arg_tys, result_ty) = splitFunTys con_tau
- in
- ASSERT( maybeToBool (splitAlgTyConApp_maybe result_ty) )
- returnTc (data_con, arg_tys, result_ty) }
+data TcEnv
+ = TcEnv {
+ tcGST :: Name -> Maybe TyThing, -- The type environment at the moment we began this compilation
+
+ tcInsts :: InstEnv, -- All instances (both imported and in this module)
+
+ tcGEnv :: TypeEnv, -- The global type environment we've accumulated while
+ {- NameEnv TyThing-} -- compiling this module:
+ -- types and classes (both imported and local)
+ -- imported Ids
+ -- (Ids defined in this module are in the local envt)
+
+ tcLEnv :: NameEnv TcTyThing, -- The local type environment: Ids and TyVars
+ -- defined in this module
+
+ tcTyVars :: TcRef TcTyVarSet -- The "global tyvars"
+ -- Namely, the in-scope TyVars bound in tcLEnv, plus the tyvars
+ -- mentioned in the types of Ids bound in tcLEnv
+ -- Why mutable? see notes with tcGetGlobalTyVars
+ }
+
+\end{code}
+
+The Global-Env/Local-Env story
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+During type checking, we keep in the GlobalEnv
+ * All types and classes
+ * All Ids derived from types and classes (constructors, selectors)
+ * Imported Ids
+
+At the end of type checking, we zonk the local bindings,
+and as we do so we add to the GlobalEnv
+ * Locally defined top-level Ids
+
+Why? Because they are now Ids not TcIds. This final GlobalEnv is
+used thus:
+ a) fed back (via the knot) to typechecking the
+ unfoldings of interface signatures
+
+ b) used to augment the GlobalSymbolTable
+
+
+\begin{code}
+data TcTyThing
+ = AGlobal TyThing -- Used only in the return type of a lookup
+ | ATcId TcId -- Ids defined in this module
+ | ATyVar TyVar -- Type variables
+ | AThing TcKind -- Used temporarily, during kind checking
+-- Here's an example of how the AThing guy is used
+-- Suppose we are checking (forall a. T a Int):
+-- 1. We first bind (a -> AThink kv), where kv is a kind variable.
+-- 2. Then we kind-check the (T a Int) part.
+-- 3. Then we zonk the kind variable.
+-- 4. Now we know the kind for 'a', and we add (a -> ATyVar a::K) to the environment
+
+initTcEnv :: HomeSymbolTable -> PackageTypeEnv -> IO TcEnv
+initTcEnv hst pte
+ = do { gtv_var <- newIORef emptyVarSet ;
+ return (TcEnv { tcGST = lookup,
+ tcGEnv = emptyNameEnv,
+ tcInsts = emptyInstEnv,
+ tcLEnv = emptyNameEnv,
+ tcTyVars = gtv_var
+ })}
+ where
+ lookup name | isLocalName name = Nothing
+ | otherwise = lookupType hst pte name
+
+
+tcEnvClasses env = [cl | AClass cl <- nameEnvElts (tcGEnv env)]
+tcEnvTyCons env = [tc | ATyCon tc <- nameEnvElts (tcGEnv env)]
+tcEnvIds env = [id | AnId id <- nameEnvElts (tcGEnv env)]
+tcEnvTyVars env = [tv | ATyVar tv <- nameEnvElts (tcLEnv env)]
+tcEnvTcIds env = [id | ATcId id <- nameEnvElts (tcLEnv env)]
+
+getTcGEnv (TcEnv { tcGEnv = genv }) = genv
+
+-- This data type is used to help tie the knot
+-- when type checking type and class declarations
+data TyThingDetails = SynTyDetails Type
+ | DataTyDetails ClassContext [DataCon]
+ | ClassDetails ClassContext [Id] [ClassOpItem] DataCon
+\end{code}
+
+
+%************************************************************************
+%* *
+\subsection{Basic lookups}
+%* *
+%************************************************************************
+
+\begin{code}
+lookup_global :: TcEnv -> Name -> Maybe TyThing
+ -- Try the global envt and then the global symbol table
+lookup_global env name
+ = case lookupNameEnv (tcGEnv env) name of
+ Just thing -> Just thing
+ Nothing -> tcGST env name
+
+lookup_local :: TcEnv -> Name -> Maybe TcTyThing
+ -- Try the local envt and then try the global
+lookup_local env name
+ = case lookupNameEnv (tcLEnv env) name of
+ Just thing -> Just thing
+ Nothing -> case lookup_global env name of
+ Just thing -> Just (AGlobal thing)
+ Nothing -> Nothing
+\end{code}