[project @ 2000-12-19 17:32:44 by simonpj]
[ghc-hetmet.git] / ghc / compiler / rename / RnEnv.lhs
index f7e34dd..9a7e56d 100644 (file)
@@ -11,12 +11,12 @@ module RnEnv where          -- Export everything
 import HsSyn
 import RdrHsSyn                ( RdrNameIE )
 import RdrName         ( RdrName, rdrNameModule, rdrNameOcc, isQual, isUnqual, isOrig,
-                         mkRdrUnqual, mkRdrUnqual, qualifyRdrName, lookupRdrEnv, foldRdrEnv
+                         mkRdrUnqual, mkRdrQual, qualifyRdrName, lookupRdrEnv, foldRdrEnv
                        )
 import HsTypes         ( hsTyVarName, replaceTyVarName )
 import HscTypes                ( Provenance(..), pprNameProvenance, hasBetterProv,
                          ImportReason(..), GlobalRdrEnv, AvailEnv,
-                         AvailInfo, Avails, GenAvailInfo(..) )
+                         AvailInfo, Avails, GenAvailInfo(..), NameSupply(..) )
 import RnMonad
 import Name            ( Name, NamedThing(..),
                          getSrcLoc, 
@@ -67,10 +67,11 @@ newTopBinder mod rdr_name loc
        returnRn ()
     )                          `thenRn_`
 
-    getNameSupplyRn            `thenRn` \ (us, cache, ipcache) ->
+    getNameSupplyRn            `thenRn` \ name_supply -> 
     let 
        occ = rdrNameOcc rdr_name
        key = (moduleName mod, occ)
+       cache = nsNames name_supply
     in
     case lookupFM cache key of
 
@@ -85,8 +86,8 @@ newTopBinder mod rdr_name loc
                        new_name  = setNameModuleAndLoc name mod loc
                        new_cache = addToFM cache key new_name
                     in
-                    setNameSupplyRn (us, new_cache, ipcache)   `thenRn_`
-                    -- traceRn (text "newTopBinder: overwrite" <+> ppr new_name) `thenRn_`
+                    setNameSupplyRn (name_supply {nsNames = new_cache})        `thenRn_`
+                    traceRn (text "newTopBinder: overwrite" <+> ppr new_name) `thenRn_`
                     returnRn new_name
                     
        -- Miss in the cache!
@@ -94,13 +95,13 @@ newTopBinder mod rdr_name loc
        -- Even for locally-defined names we use implicitImportProvenance; 
        -- updateProvenances will set it to rights
        Nothing -> let
-                       (us', us1) = splitUniqSupply us
+                       (us', us1) = splitUniqSupply (nsUniqs name_supply)
                        uniq       = uniqFromSupply us1
                        new_name   = mkGlobalName uniq mod occ loc
                        new_cache  = addToFM cache key new_name
                   in
-                  setNameSupplyRn (us', new_cache, ipcache)    `thenRn_`
-                  -- traceRn (text "newTopBinder: new" <+> ppr new_name) `thenRn_`
+                  setNameSupplyRn (name_supply {nsUniqs = us', nsNames = new_cache})   `thenRn_`
+                  traceRn (text "newTopBinder: new" <+> ppr new_name) `thenRn_`
                   returnRn new_name
 
 
@@ -123,32 +124,36 @@ newGlobalName :: ModuleName -> OccName -> RnM d Name
   -- (but since it affects DLL-ery it does matter that we get it right
   --  in the end).
 newGlobalName mod_name occ
-  = getNameSupplyRn            `thenRn` \ (us, cache, ipcache) ->
+  = getNameSupplyRn            `thenRn` \ name_supply ->
     let
        key = (mod_name, occ)
+       cache = nsNames name_supply
     in
     case lookupFM cache key of
        Just name -> -- traceRn (text "newGlobalName: hit" <+> ppr name) `thenRn_`
                     returnRn name
 
-       Nothing   -> setNameSupplyRn (us', new_cache, ipcache)                  `thenRn_`
-                    -- traceRn (text "newGlobalName: new" <+> ppr name)        `thenRn_`
+       Nothing   -> setNameSupplyRn (name_supply {nsUniqs = us', nsNames = new_cache})  `thenRn_`
+                    -- traceRn (text "newGlobalName: new" <+> ppr name)                  `thenRn_`
                     returnRn name
                  where
-                    (us', us1) = splitUniqSupply us
+                    (us', us1) = splitUniqSupply (nsUniqs name_supply)
                     uniq       = uniqFromSupply us1
                     mod        = mkVanillaModule mod_name
                     name       = mkGlobalName uniq mod occ noSrcLoc
                     new_cache  = addToFM cache key name
 
 newIPName rdr_name
-  = getNameSupplyRn            `thenRn` \ (us, cache, ipcache) ->
+  = getNameSupplyRn            `thenRn` \ name_supply ->
+    let
+       ipcache = nsIPs name_supply
+    in
     case lookupFM ipcache key of
        Just name -> returnRn name
-       Nothing   -> setNameSupplyRn (us', cache, new_ipcache)  `thenRn_`
+       Nothing   -> setNameSupplyRn (name_supply {nsUniqs = us', nsIPs = new_ipcache}) `thenRn_`
                     returnRn name
                  where
-                    (us', us1)  = splitUniqSupply us
+                    (us', us1)  = splitUniqSupply (nsUniqs name_supply)
                     uniq        = uniqFromSupply us1
                     name        = mkIPName uniq key
                     new_ipcache = addToFM ipcache key name
@@ -298,16 +303,16 @@ lookupSysBinder rdr_name
 newLocalsRn :: [(RdrName,SrcLoc)]
            -> RnMS [Name]
 newLocalsRn rdr_names_w_loc
- =  getNameSupplyRn            `thenRn` \ (us, cache, ipcache) ->
+ =  getNameSupplyRn            `thenRn` \ name_supply ->
     let
        n          = length rdr_names_w_loc
-       (us', us1) = splitUniqSupply us
+       (us', us1) = splitUniqSupply (nsUniqs name_supply)
        uniqs      = uniqsFromSupply n us1
        names      = [ mkLocalName uniq (rdrNameOcc rdr_name) loc
                     | ((rdr_name,loc), uniq) <- rdr_names_w_loc `zip` uniqs
                     ]
     in
-    setNameSupplyRn (us', cache, ipcache)      `thenRn_`
+    setNameSupplyRn (name_supply {nsUniqs = us'})      `thenRn_`
     returnRn names
 
 
@@ -353,13 +358,13 @@ bindCoreLocalRn :: RdrName -> (Name -> RnMS a) -> RnMS a
 bindCoreLocalRn rdr_name enclosed_scope
   = getSrcLocRn                `thenRn` \ loc ->
     getLocalNameEnv            `thenRn` \ name_env ->
-    getNameSupplyRn            `thenRn` \ (us, cache, ipcache) ->
+    getNameSupplyRn            `thenRn` \ name_supply ->
     let
-       (us', us1) = splitUniqSupply us
+       (us', us1) = splitUniqSupply (nsUniqs name_supply)
        uniq       = uniqFromSupply us1
        name       = mkLocalName uniq (rdrNameOcc rdr_name) loc
     in
-    setNameSupplyRn (us', cache, ipcache)      `thenRn_`
+    setNameSupplyRn (name_supply {nsUniqs = us'})      `thenRn_`
     let
        new_name_env = extendRdrEnv name_env rdr_name name
     in
@@ -405,7 +410,7 @@ bindLocalsFVRn doc rdr_names enclosed_scope
 
 -------------------------------------
 extendTyVarEnvFVRn :: [Name] -> RnMS (a, FreeVars) -> RnMS (a, FreeVars)
-       -- This tiresome function is used only in rnDecl on InstDecl
+       -- This tiresome function is used only in rnSourceDecl on InstDecl
 extendTyVarEnvFVRn tyvars enclosed_scope
   = bindLocalNames tyvars enclosed_scope       `thenRn` \ (thing, fvs) -> 
     returnRn (thing, delListFromNameSet fvs tyvars)
@@ -486,6 +491,56 @@ checkDupNames doc_str rdr_names_w_loc
 %************************************************************************
 
 \begin{code}
+mkGlobalRdrEnv :: ModuleName           -- Imported module (after doing the "as M" name change)
+              -> Bool                  -- True <=> want unqualified import
+              -> [AvailInfo]           -- What's to be hidden (but only the unqualified 
+                                       --      version is hidden)
+              -> (Name -> Provenance)
+              -> Avails                -- Whats imported and how
+              -> GlobalRdrEnv
+
+mkGlobalRdrEnv this_mod unqual_imp hides mk_provenance avails
+  = gbl_env2
+  where
+       -- Make the name environment.  We're talking about a 
+       -- single module here, so there must be no name clashes.
+       -- In practice there only ever will be if it's the module
+       -- being compiled.
+
+       -- Add the things that are available
+    gbl_env1 = foldl add_avail emptyRdrEnv avails
+
+       -- Delete things that are hidden
+    gbl_env2 = foldl del_avail gbl_env1 hides
+
+    add_avail :: GlobalRdrEnv -> AvailInfo -> GlobalRdrEnv
+    add_avail env avail = foldl add_name env (availNames avail)
+
+    add_name env name
+       | unqual_imp = env2
+       | otherwise  = env1
+       where
+         env1 = addOneToGlobalRdrEnv env  (mkRdrQual this_mod occ) (name,prov)
+         env2 = addOneToGlobalRdrEnv env1 (mkRdrUnqual occ)        (name,prov)
+         occ  = nameOccName name
+         prov = mk_provenance name
+
+    del_avail env avail = foldl delOneFromGlobalRdrEnv env rdr_names
+                       where
+                         rdr_names = map (mkRdrUnqual . nameOccName) (availNames avail)
+
+mkIfaceGlobalRdrEnv :: [(ModuleName,Avails)] -> GlobalRdrEnv
+-- Used to construct a GlobalRdrEnv for an interface that we've
+-- read from a .hi file.  We can't construct the original top-level
+-- environment because we don't have enough info, but we compromise
+-- by making an environment from its exports
+mkIfaceGlobalRdrEnv m_avails
+  = foldl add emptyRdrEnv m_avails
+  where
+    add env (mod,avails) = plusGlobalRdrEnv env (mkGlobalRdrEnv mod True [] (\n -> LocalDef) avails)
+\end{code}
+
+\begin{code}
 plusGlobalRdrEnv :: GlobalRdrEnv -> GlobalRdrEnv -> GlobalRdrEnv
 plusGlobalRdrEnv env1 env2 = plusFM_C combine_globals env1 env2