diff options
author | simonpj <unknown> | 2000-10-30 09:52:16 +0000 |
---|---|---|
committer | simonpj <unknown> | 2000-10-30 09:52:16 +0000 |
commit | 2ecf1c9f639dc75f1078e88c2e551116923f742a (patch) | |
tree | 79dd1c552bb8616a4490a2a9632478ef180f334a /ghc/compiler/rename | |
parent | 73c0472d57af773f9920bf27547211d5c8785943 (diff) | |
download | haskell-2ecf1c9f639dc75f1078e88c2e551116923f742a.tar.gz |
[project @ 2000-10-30 09:52:14 by simonpj]
First steps to making it work
Diffstat (limited to 'ghc/compiler/rename')
-rw-r--r-- | ghc/compiler/rename/Rename.lhs | 115 | ||||
-rw-r--r-- | ghc/compiler/rename/RnEnv.lhs | 26 | ||||
-rw-r--r-- | ghc/compiler/rename/RnHiFiles.lhs | 56 | ||||
-rw-r--r-- | ghc/compiler/rename/RnIfaces.lhs | 29 | ||||
-rw-r--r-- | ghc/compiler/rename/RnNames.lhs | 132 | ||||
-rw-r--r-- | ghc/compiler/rename/RnSource.lhs | 3 |
6 files changed, 181 insertions, 180 deletions
diff --git a/ghc/compiler/rename/Rename.lhs b/ghc/compiler/rename/Rename.lhs index 65f980d5d7..094a01f4c3 100644 --- a/ghc/compiler/rename/Rename.lhs +++ b/ghc/compiler/rename/Rename.lhs @@ -10,7 +10,7 @@ module Rename ( renameModule, closeIfaceDecls, checkOldIface ) where import HsSyn import RdrHsSyn ( RdrNameHsModule, RdrNameHsDecl, RdrNameDeprecation, - RdrNameTyClDecl, RdrNameRuleDecl, RdrNameInstDecl + RdrNameTyClDecl, RdrNameRuleDecl, RdrNameInstDecl, RdrNameImportDecl ) import RnHsSyn ( RenamedHsDecl, RenamedTyClDecl, RenamedRuleDecl, RenamedInstDecl, extractHsTyNames, @@ -26,24 +26,24 @@ import RnIfaces ( slurpImpDecls, mkImportInfo, RecompileRequired, recompileRequired ) import RnHiFiles ( findAndReadIface, removeContext, loadExports, loadFixDecls, loadDeprecs ) -import RnEnv ( availName, availsToNameSet, +import RnEnv ( availName, emptyAvailEnv, unitAvailEnv, availEnvElts, plusAvailEnv, groupAvails, warnUnusedImports, warnUnusedLocalBinds, warnUnusedModules, lookupOrigNames, lookupGlobalRn, newGlobalName ) import Module ( Module, ModuleName, WhereFrom(..), - moduleNameUserString, moduleName, - lookupModuleEnv + moduleNameUserString, moduleName ) import Name ( Name, isLocallyDefined, NamedThing(..), getSrcLoc, nameOccName, nameModule, mkNameEnv, nameEnvElts, extendNameEnv ) +import RdrName ( elemRdrEnv ) import OccName ( occNameFlavour ) import NameSet import TysWiredIn ( unitTyCon, intTyCon, boolTyCon ) import PrelNames ( mAIN_Name, pREL_MAIN_Name, pRELUDE_Name, - ioTyCon_RDR, + ioTyCon_RDR, main_RDR, unpackCString_RDR, unpackCStringFoldr_RDR, unpackCStringUtf8_RDR, eqString_RDR ) @@ -61,9 +61,9 @@ import IO ( openFile, IOMode(..) ) import HscTypes ( PersistentCompilerState, HomeIfaceTable, HomeSymbolTable, ModIface(..), WhatsImported(..), VersionInfo(..), ImportVersion, IfaceDecls(..), - GlobalRdrEnv, AvailEnv, Avails, GenAvailInfo(..), AvailInfo, + GlobalRdrEnv, AvailEnv, GenAvailInfo(..), AvailInfo, Provenance(..), ImportReason(..), initialVersionInfo, - Deprecations(..), lookupDeprec + Deprecations(..), lookupDeprec, lookupTable ) import List ( partition, nub ) \end{code} @@ -100,18 +100,21 @@ renameModule dflags hit hst old_pcs this_module rdr_module \begin{code} rename :: Module -> RdrNameHsModule -> RnMG (Maybe (ModIface, [RenamedHsDecl])) -rename this_module this_mod@(HsModule mod_name vers exports imports local_decls mod_deprec loc) - = -- FIND THE GLOBAL NAME ENVIRONMENT - getGlobalNames this_mod `thenRn` \ maybe_stuff -> +rename this_module contents@(HsModule _ _ _ imports local_decls mod_deprec loc) + = pushSrcLocRn loc $ - -- CHECK FOR EARLY EXIT - case maybe_stuff of { - Nothing -> -- Everything is up to date; no need to recompile further - rnDump [] [] `thenRn_` - returnRn Nothing ; - - Just (gbl_env, local_gbl_env, export_avails, global_avail_env) -> + -- FIND THE GLOBAL NAME ENVIRONMENT + getGlobalNames this_module contents `thenRn` \ (gbl_env, local_gbl_env, + export_avails, global_avail_env) -> + -- Exit if we've found any errors + checkErrsRn `thenRn` \ no_errs_so_far -> + if not no_errs_so_far then + -- Found errors already, so exit now + rnDump [] [] `thenRn_` + returnRn Nothing + else + -- DEAL WITH DEPRECATIONS rnDeprecs local_gbl_env mod_deprec [d | DeprecD d <- local_decls] `thenRn` \ my_deprecs -> @@ -124,6 +127,9 @@ rename this_module this_mod@(HsModule mod_name vers exports imports local_decls rnSourceDecls local_decls ) `thenRn` \ (rn_local_decls, source_fvs) -> + -- CHECK THAT main IS DEFINED, IF REQUIRED + checkMain this_module local_gbl_env `thenRn_` + -- SLURP IN ALL THE NEEDED DECLARATIONS implicitFVs mod_name rn_local_decls `thenRn` \ implicit_fvs -> let @@ -157,9 +163,6 @@ rename this_module this_mod@(HsModule mod_name vers exports imports local_decls getNameSupplyRn `thenRn` \ name_supply -> getIfacesRn `thenRn` \ ifaces -> let - direct_import_mods :: [ModuleName] - direct_import_mods = nub [m | ImportDecl m _ _ _ _ _ <- imports] - -- We record fixities even for things that aren't exported, -- so that we can change into the context of this moodule easily fixities = mkNameEnv [ (name, fixity) @@ -168,7 +171,7 @@ rename this_module this_mod@(HsModule mod_name vers exports imports local_decls -- Sort the exports to make them easier to compare for versions - my_exports = groupAvails export_avails + my_exports = groupAvails this_module export_avails mod_iface = ModIface { mi_module = this_module, mi_version = initialVersionInfo, @@ -185,13 +188,23 @@ rename this_module this_mod@(HsModule mod_name vers exports imports local_decls in -- REPORT UNUSED NAMES, AND DEBUG DUMP - reportUnusedNames mod_name direct_import_mods - gbl_env global_avail_env - export_avails source_fvs - rn_imp_decls `thenRn_` + reportUnusedNames mod_iface imports global_avail_env + real_source_fvs rn_imp_decls `thenRn_` returnRn (Just (mod_iface, final_decls)) - } + where + mod_name = moduleName this_module +\end{code} + +Checking that main is defined + +\begin{code} +checkMain :: Module -> GlobalRdrEnv -> RnMG () +checkMain this_mod local_env + | moduleName this_mod == mAIN_Name + = checkRn (main_RDR `elemRdrEnv` local_env) noMainErr + | otherwise + = returnRn () \end{code} @implicitFVs@ forces the renamer to slurp in some things which aren't @@ -508,23 +521,22 @@ closeIfaceDecls dflags hit hst pcs %********************************************************* \begin{code} -reportUnusedNames :: ModuleName -> [ModuleName] - -> GlobalRdrEnv -> AvailEnv - -> Avails -> NameSet -> [RenamedHsDecl] +reportUnusedNames :: ModIface -> [RdrNameImportDecl] + -> AvailEnv + -> NameSet + -> [RenamedHsDecl] -> RnMG () -reportUnusedNames mod_name direct_import_mods - gbl_env avail_env - export_avails mentioned_names - imported_decls +reportUnusedNames my_mod_iface imports avail_env + used_names imported_decls = warnUnusedModules unused_imp_mods `thenRn_` warnUnusedLocalBinds bad_locals `thenRn_` warnUnusedImports bad_imp_names `thenRn_` - printMinimalImports mod_name minimal_imports `thenRn_` - warnDeprecations really_used_names `thenRn_` + printMinimalImports my_mod_iface minimal_imports `thenRn_` + warnDeprecations my_mod_iface really_used_names `thenRn_` returnRn () where - used_names = mentioned_names `unionNameSets` availsToNameSet export_avails + gbl_env = mi_globals my_mod_iface -- Now, a use of C implies a use of T, -- if C was brought into scope by T(..) or T(C) @@ -603,7 +615,10 @@ reportUnusedNames mod_name direct_import_mods | otherwise = addToFM acc m emptyAvailEnv -- Add an empty collection of imports for a module -- from which we have sucked only instance decls - + + direct_import_mods :: [ModuleName] + direct_import_mods = nub [m | ImportDecl m _ _ _ _ _ <- imports] + -- unused_imp_mods are the directly-imported modules -- that are not mentioned in minimal_imports unused_imp_mods = [m | m <- direct_import_mods, @@ -614,7 +629,7 @@ reportUnusedNames mod_name direct_import_mods module_unused mod = moduleName mod `elem` unused_imp_mods -warnDeprecations used_names +warnDeprecations my_mod_iface used_names = doptRn Opt_WarnDeprecations `thenRn` \ warn_drs -> if not warn_drs then returnRn () else @@ -629,17 +644,16 @@ warnDeprecations used_names mapRn_ warnDeprec deprecs where - lookup_deprec hit pit n - = case lookupModuleEnv hit mod of - Just iface -> lookupDeprec iface n - Nothing -> case lookupModuleEnv pit mod of - Just iface -> lookupDeprec iface n - Nothing -> pprPanic "warnDeprecations:" (ppr n) - where - mod = nameModule n + mod = mi_module my_mod_iface + my_deprecs = mi_deprecs my_mod_iface + lookup_deprec hit pit n + | isLocalThing mod n = lookupDeprec my_deprecs n + | otherwise = case lookupTable hit pit n of + Just iface -> lookupDeprec (mi_deprecs iface) n + Nothing -> pprPanic "warnDeprecations:" (ppr n) -- ToDo: deal with original imports with 'qualified' and 'as M' clauses -printMinimalImports mod_name imps +printMinimalImports my_mod_iface imps = doptRn Opt_D_dump_minimal_imports `thenRn` \ dump_minimal -> if not dump_minimal then returnRn () else @@ -649,7 +663,8 @@ printMinimalImports mod_name imps }) `thenRn_` returnRn () where - filename = moduleNameUserString mod_name ++ ".imports" + filename = moduleNameUserString (moduleName (mi_module my_mod_iface)) + ++ ".imports" ppr_mod_ie (mod_name, ies) | mod_name == pRELUDE_Name = empty @@ -786,6 +801,10 @@ dupFixityDecl rdr_name loc1 loc2 badDeprec d = sep [ptext SLIT("Illegal deprecation when whole module is deprecated"), nest 4 (ppr d)] + +noMainErr + = hsep [ptext SLIT("Module"), quotes (ppr mAIN_Name), + ptext SLIT("must include a definition for"), quotes (ptext SLIT("main"))] \end{code} diff --git a/ghc/compiler/rename/RnEnv.lhs b/ghc/compiler/rename/RnEnv.lhs index 4fc2a3ab98..023e10c523 100644 --- a/ghc/compiler/rename/RnEnv.lhs +++ b/ghc/compiler/rename/RnEnv.lhs @@ -21,7 +21,7 @@ import RnMonad import Name ( Name, NamedThing(..), getSrcLoc, mkLocalName, mkImportedLocalName, mkGlobalName, - mkIPName, nameOccName, nameModule, + mkIPName, nameOccName, nameModule_maybe, extendNameEnv_C, plusNameEnv_C, nameEnvElts, setNameModuleAndLoc ) @@ -49,10 +49,25 @@ import FastString ( FastString ) \begin{code} newTopBinder :: Module -> RdrName -> SrcLoc -> RnM d Name + -- newTopBinder puts into the cache the binder with the + -- module information set correctly. When the decl is later renamed, + -- the binding site will thereby get the correct module. + -- There maybe occurrences that don't have the correct Module, but + -- by the typechecker will propagate the binding definition to all + -- the occurrences, so that doesn't matter + newTopBinder mod rdr_name loc = -- First check the cache traceRn (text "newTopBinder" <+> ppr mod <+> ppr loc) `thenRn_` + -- There should never be a qualified name in a binding position (except in instance decls) + -- The parser doesn't check this because the same parser parses instance decls + (if isQual rdr_name then + qualNameErr (text "its declaration") (rdr_name,loc) + else + returnRn () + ) `thenRn_` + getNameSupplyRn `thenRn` \ (us, cache, ipcache) -> let occ = rdrNameOcc rdr_name @@ -639,10 +654,10 @@ filterAvail (IEThingAll _) avail@(AvailTC _ _) = Just avail filterAvail ie avail = Nothing ------------------------------------- -groupAvails :: Avails -> [(ModuleName, Avails)] +groupAvails :: Module -> Avails -> [(ModuleName, Avails)] -- Group by module and sort by occurrence -- This keeps the list in canonical order -groupAvails avails +groupAvails this_mod avails = [ (mkSysModuleNameFS fs, sortLt lt avails) | (fs,avails) <- fmToList groupFM ] @@ -654,7 +669,10 @@ groupAvails avails add env avail = addToFM_C combine env mod_fs [avail] where - mod_fs = moduleNameFS (moduleName (nameModule (availName avail))) + mod_fs = moduleNameFS (moduleName avail_mod) + avail_mod = case nameModule_maybe (availName avail) of + Just m -> m + Nothing -> this_mod combine old _ = avail:old a1 `lt` a2 = occ1 < occ2 diff --git a/ghc/compiler/rename/RnHiFiles.lhs b/ghc/compiler/rename/RnHiFiles.lhs index 9a1366927e..77f753a56a 100644 --- a/ghc/compiler/rename/RnHiFiles.lhs +++ b/ghc/compiler/rename/RnHiFiles.lhs @@ -87,9 +87,14 @@ loadInterface doc mod from Just err -> failWithRn ifaces err tryLoadInterface :: SDoc -> ModuleName -> WhereFrom -> RnM d (Ifaces, Maybe Message) - -- Returns (Just err) if an error happened - -- Guarantees to return with iImpModInfo m --> (..., True) - -- (If the load fails, we plug in a vanilla placeholder) + -- Returns (Just err) if an error happened + -- It *doesn't* add an error to the monad, because sometimes it's ok to fail... + -- Specifically, when we read the usage information from an interface file, + -- we try to read the interfaces it mentions. But it's OK to fail; perhaps + -- the module has changed, and that interface is no longer used. + + -- tryLoadInterface guarantees to return with iImpModInfo m --> (..., True) + -- (If the load fails, we plug in a vanilla placeholder) tryLoadInterface doc_str mod_name from = getHomeIfaceTableRn `thenRn` \ hit -> getIfacesRn `thenRn` \ ifaces -> @@ -271,14 +276,12 @@ loadExport this_mod (mod, entities) = mapRn (load_entity mod) entities `thenRn` \ avails -> returnRn (mod, avails) where - new_name mod occ = newGlobalName mod occ - load_entity mod (Avail occ) - = new_name mod occ `thenRn` \ name -> + = newGlobalName mod occ `thenRn` \ name -> returnRn (Avail name) load_entity mod (AvailTC occ occs) - = new_name mod occ `thenRn` \ name -> - mapRn (new_name mod) occs `thenRn` \ names -> + = newGlobalName mod occ `thenRn` \ name -> + mapRn (newGlobalName mod) occs `thenRn` \ names -> returnRn (AvailTC name names) @@ -298,7 +301,7 @@ loadDecl :: Module -> (Version, RdrNameTyClDecl) -> RnM d (NameEnv Version, DeclsMap) loadDecl mod (version_map, decls_map) (version, decl) - = getIfaceDeclBinders new_name decl `thenRn` \ full_avail -> + = getIfaceDeclBinders mod decl `thenRn` \ full_avail -> let main_name = availName full_avail new_decls_map = extendNameEnvList decls_map stuff @@ -308,15 +311,6 @@ loadDecl mod (version_map, decls_map) (version, decl) new_version_map = extendNameEnv version_map main_name version in returnRn (new_version_map, new_decls_map) - where - -- newTopBinder puts into the cache the binder with the - -- module information set correctly. When the decl is later renamed, - -- the binding site will thereby get the correct module. - -- There maybe occurrences that don't have the correct Module, but - -- by the typechecker will propagate the binding definition to all - -- the occurrences, so that doesn't matter - new_name rdr_name loc = newTopBinder mod rdr_name loc - ----------------------------------------------------- -- Loading fixity decls @@ -427,27 +421,27 @@ are handled by the sourc-code specific stuff in @RnNames@. \begin{code} getIfaceDeclBinders, getTyClDeclBinders - :: (RdrName -> SrcLoc -> RnM d Name) -- New-name function + :: Module -> RdrNameTyClDecl -> RnM d AvailInfo -getIfaceDeclBinders new_name tycl_decl - = getTyClDeclBinders new_name tycl_decl `thenRn` \ avail -> - getSysTyClDeclBinders new_name tycl_decl `thenRn` \ extras -> +getIfaceDeclBinders mod tycl_decl + = getTyClDeclBinders mod tycl_decl `thenRn` \ avail -> + getSysTyClDeclBinders mod tycl_decl `thenRn` \ extras -> returnRn (addSysAvails avail extras) -- Add the sys-binders to avail. When we import the decl, -- it's full_avail that will get added to the 'already-slurped' set (iSlurp) -- If we miss out sys-binders, we'll read the decl multiple times! -getTyClDeclBinders new_name (IfaceSig var ty prags src_loc) - = new_name var src_loc `thenRn` \ var_name -> +getTyClDeclBinders mod (IfaceSig var ty prags src_loc) + = newTopBinder mod var src_loc `thenRn` \ var_name -> returnRn (Avail var_name) -getTyClDeclBinders new_name tycl_decl +getTyClDeclBinders mod tycl_decl = mapRn do_one (tyClDeclNames tycl_decl) `thenRn` \ (main_name:sub_names) -> returnRn (AvailTC main_name (main_name : sub_names)) where - do_one (name,loc) = new_name name loc + do_one (name,loc) = newTopBinder mod name loc \end{code} @getDeclSysBinders@ gets the implicit binders introduced by a decl. @@ -460,13 +454,13 @@ and the dict fun of an instance decl, because both of these have bindings of their own elsewhere. \begin{code} -getSysTyClDeclBinders new_name (ClassDecl _ cname _ _ sigs _ names src_loc) - = sequenceRn [new_name n src_loc | n <- names] +getSysTyClDeclBinders mod (ClassDecl _ cname _ _ sigs _ names src_loc) + = sequenceRn [newTopBinder mod n src_loc | n <- names] -getSysTyClDeclBinders new_name (TyData _ _ _ _ cons _ _ _ _ _) - = sequenceRn [new_name wkr_name src_loc | ConDecl _ wkr_name _ _ _ src_loc <- cons] +getSysTyClDeclBinders mod (TyData _ _ _ _ cons _ _ _ _ _) + = sequenceRn [newTopBinder mod wkr_name src_loc | ConDecl _ wkr_name _ _ _ src_loc <- cons] -getSysTyClDeclBinders new_name other_decl +getSysTyClDeclBinders mod other_decl = returnRn [] \end{code} diff --git a/ghc/compiler/rename/RnIfaces.lhs b/ghc/compiler/rename/RnIfaces.lhs index 7d85e22d1b..9d0ffaf549 100644 --- a/ghc/compiler/rename/RnIfaces.lhs +++ b/ghc/compiler/rename/RnIfaces.lhs @@ -250,17 +250,7 @@ mkImportInfo this_mod imports -- For (a) a library module, we don't record it at all unless it contains orphans -- (We must never lose track of orphans.) -- - -- (b) a source-imported module, don't record the dependency at all - -- - -- (b) may seem a bit strange. The idea is that the usages in a .hi file records - -- *all* the module's dependencies other than the loop-breakers. We use - -- this info in findAndReadInterface to decide whether to look for a .hi file or - -- a .hi-boot file. - -- - -- This means we won't track version changes, or orphans, from .hi-boot files. - -- The former is potentially rather bad news. It could be fixed by recording - -- whether something is a boot file along with the usage info for it, but - -- I can't be bothered just now. + -- (b) a home-package module mk_imp_info mod_name (has_orphans, is_boot, opened) so_far | mod_name == this_mod -- Check if M appears in the set of modules 'below' M @@ -279,11 +269,15 @@ mkImportInfo this_mod imports go_for_it NothingAtAll - | is_lib_module && not has_orphans - = so_far - - | is_lib_module -- Record the module version only - = go_for_it (Everything module_vers) + | is_lib_module + -- Ignore modules from other packages, unless it has + -- orphans, in which case we must remember it in our + -- dependencies. But in that case we only record the + -- module version, nothing more detailed + = if has_orphans then + go_for_it (Everything module_vers) + else + so_far | otherwise = go_for_it whats_imported @@ -654,6 +648,9 @@ data ImportDeclResult importDecl name = -- Check if it was loaded before beginning this module + if isLocallyDefined name then + returnRn AlreadySlurped + else checkAlreadyAvailable name `thenRn` \ done -> if done then returnRn AlreadySlurped diff --git a/ghc/compiler/rename/RnNames.lhs b/ghc/compiler/rename/RnNames.lhs index e2094c8100..eaffb11725 100644 --- a/ghc/compiler/rename/RnNames.lhs +++ b/ghc/compiler/rename/RnNames.lhs @@ -28,16 +28,15 @@ import FiniteMap import PrelNames ( pRELUDE_Name, mAIN_Name, main_RDR ) import UniqFM ( lookupUFM ) import Bag ( bagToList ) -import Module ( ModuleName, mkModuleInThisPackage, WhereFrom(..) ) +import Module ( ModuleName, moduleName, WhereFrom(..) ) import NameSet import Name ( Name, nameSrcLoc, setLocalNameSort, nameOccName, nameEnvElts ) import HscTypes ( Provenance(..), ImportReason(..), GlobalRdrEnv, GenAvailInfo(..), AvailInfo, Avails, AvailEnv ) -import RdrName ( RdrName, rdrNameOcc, setRdrNameOcc, mkRdrQual, mkRdrUnqual, isUnqual ) +import RdrName ( RdrName, rdrNameOcc, setRdrNameOcc, mkRdrQual, mkRdrUnqual ) import OccName ( setOccNameSpace, dataName ) import NameSet ( elemNameSet, emptyNameSet ) -import SrcLoc ( SrcLoc ) import Outputable import Maybes ( maybeToBool, catMaybes, mapMaybe ) import UniqFM ( emptyUFM, listToUFM ) @@ -55,19 +54,17 @@ import List ( partition ) %************************************************************************ \begin{code} -getGlobalNames :: RdrNameHsModule - -> RnMG (Maybe (GlobalRdrEnv, -- Maps all in-scope things - GlobalRdrEnv, -- Maps just *local* things - Avails, -- The exported stuff - AvailEnv -- Maps a name to its parent AvailInfo - -- Just for in-scope things only - )) - -- Nothing => no need to recompile - -getGlobalNames (HsModule this_mod _ exports imports decls _ mod_loc) +getGlobalNames :: Module -> RdrNameHsModule + -> RnMG (GlobalRdrEnv, -- Maps all in-scope things + GlobalRdrEnv, -- Maps just *local* things + Avails, -- The exported stuff + AvailEnv) -- Maps a name to its parent AvailInfo + -- Just for in-scope things only + +getGlobalNames this_mod (HsModule _ _ exports imports decls _ mod_loc) = -- These two fix-loops are to get the right -- provenance information into a Name - fixRn ( \ ~(Just (rec_gbl_env, _, rec_export_avails, _)) -> + fixRn ( \ ~(rec_gbl_env, _, rec_export_avails, _) -> let rec_unqual_fn :: Name -> Bool -- Is this chap in scope unqualified? @@ -80,8 +77,7 @@ getGlobalNames (HsModule this_mod _ exports imports decls _ mod_loc) -- PROCESS LOCAL DECLS -- Do these *first* so that the correct provenance gets -- into the global name cache. - importsFromLocalDecls this_mod rec_exp_fn decls - `thenRn` \ (local_gbl_env, local_mod_avails) -> + importsFromLocalDecls this_mod rec_exp_fn decls `thenRn` \ (local_gbl_env, local_mod_avails) -> -- PROCESS IMPORT DECLS -- Do the non {- SOURCE -} ones first, so that we get a helpful @@ -91,10 +87,8 @@ getGlobalNames (HsModule this_mod _ exports imports decls _ mod_loc) is_source_import (ImportDecl _ ImportByUserSource _ _ _ _) = True is_source_import other = False in - mapAndUnzipRn (importsFromImportDecl rec_unqual_fn) ordinary - `thenRn` \ (imp_gbl_envs1, imp_avails_s1) -> - mapAndUnzipRn (importsFromImportDecl rec_unqual_fn) source - `thenRn` \ (imp_gbl_envs2, imp_avails_s2) -> + mapAndUnzipRn (importsFromImportDecl rec_unqual_fn) ordinary `thenRn` \ (imp_gbl_envs1, imp_avails_s1) -> + mapAndUnzipRn (importsFromImportDecl rec_unqual_fn) source `thenRn` \ (imp_gbl_envs2, imp_avails_s2) -> -- COMBINE RESULTS -- We put the local env second, so that a local provenance @@ -106,46 +100,29 @@ getGlobalNames (HsModule this_mod _ exports imports decls _ mod_loc) all_avails :: ExportAvails all_avails = foldr plusExportAvails local_mod_avails (imp_avails_s2 ++ imp_avails_s1) + (_, global_avail_env) = all_avails in - -- TRY FOR EARLY EXIT - -- We can't go for an early exit before this because we have to check - -- for name clashes. Consider: - -- - -- module A where module B where - -- import B h = True - -- f = h - -- - -- Suppose I've compiled everything up, and then I add a - -- new definition to module B, that defines "f". - -- - -- Then I must detect the name clash in A before going for an early - -- exit. The early-exit code checks what's actually needed from B - -- to compile A, and of course that doesn't include B.f. That's - -- why we wait till after the plusEnv stuff to do the early-exit. - - -- Check For early exit - checkErrsRn `thenRn` \ no_errs_so_far -> - if not no_errs_so_far then - -- Found errors already, so exit now - returnRn Nothing - else - - -- PROCESS EXPORT LISTS - exportsFromAvail this_mod exports all_avails gbl_env `thenRn` \ export_avails -> - + -- PROCESS EXPORT LIST (but not if we've had errors already) + checkErrsRn `thenRn` \ no_errs_so_far -> + (if no_errs_so_far then + exportsFromAvail this_mod_name exports all_avails gbl_env + else + returnRn [] + ) `thenRn` \ export_avails -> -- ALL DONE - returnRn (Just (gbl_env, local_gbl_env, export_avails, global_avail_env)) + returnRn (gbl_env, local_gbl_env, export_avails, global_avail_env) ) where + this_mod_name = moduleName this_mod all_imports = prel_imports ++ imports -- NB: opt_NoImplicitPrelude is slightly different to import Prelude (); -- because the former doesn't even look at Prelude.hi for instance declarations, -- whereas the latter does. - prel_imports | this_mod == pRELUDE_Name || + prel_imports | this_mod_name == pRELUDE_Name || explicit_prelude_import || opt_NoImplicitPrelude = [] @@ -197,8 +174,8 @@ importsFromImportDecl is_unqual (ImportDecl imp_mod_name from qual_only as_mod i \begin{code} -importsFromLocalDecls mod_name rec_exp_fn decls - = mapRn (getLocalDeclBinders (newLocalName mod rec_exp_fn)) decls `thenRn` \ avails_s -> +importsFromLocalDecls this_mod rec_exp_fn decls + = mapRn (getLocalDeclBinders this_mod rec_exp_fn) decls `thenRn` \ avails_s -> let avails = concat avails_s @@ -216,32 +193,33 @@ importsFromLocalDecls mod_name rec_exp_fn decls recordLocalSlurps avails `thenRn_` -- Build the environment - qualifyImports mod_name + qualifyImports (moduleName this_mod) True -- Want unqualified names Nothing -- no 'as M' [] -- Hide nothing (\n -> LocalDef) -- Provenance is local avails - where - mod = mkModuleInThisPackage mod_name --------------------------- -getLocalDeclBinders :: (RdrName -> SrcLoc -> RnMG Name) +getLocalDeclBinders :: Module + -> (Name -> Bool) -- Whether exported -> RdrNameHsDecl -> RnMG Avails -getLocalDeclBinders new_name (ValD binds) - = mapRn do_one (bagToList (collectTopBinders binds)) - where - do_one (rdr_name, loc) = new_name rdr_name loc `thenRn` \ name -> - returnRn (Avail name) - -getLocalDeclBinders new_name (TyClD tycl_decl) - = getTyClDeclBinders new_name tycl_decl `thenRn` \ avail -> +getLocalDeclBinders mod rec_exp_fn (TyClD tycl_decl) + = -- For type and class decls, we generate Global names, with + -- no export indicator. They need to be global because they get + -- permanently bound into the TyCons and Classes. They don't need + -- an export indicator because they are all implicitly exported. + getTyClDeclBinders mod tycl_decl `thenRn` \ avail -> returnRn [avail] -getLocalDeclBinders new_name (ForD (ForeignDecl nm kind _ ext_nm _ loc)) +getLocalDeclBinders mod rec_exp_fn (ValD binds) + = mapRn (newLocalBinder mod rec_exp_fn) + (bagToList (collectTopBinders binds)) + +getLocalDeclBinders mod rec_exp_fn (ForD (ForeignDecl nm kind _ ext_nm _ loc)) | binds_haskell_name kind - = new_name nm loc `thenRn` \ name -> - returnRn [Avail name] + = newLocalBinder mod rec_exp_fn (nm, loc) `thenRn` \ avail -> + returnRn [avail] | otherwise -- a foreign export = lookupOrigName nm `thenRn_` @@ -251,25 +229,17 @@ getLocalDeclBinders new_name (ForD (ForeignDecl nm kind _ ext_nm _ loc)) binds_haskell_name FoLabel = True binds_haskell_name FoExport = isDynamicExtName ext_nm -getLocalDeclBinders new_name (FixD _) = returnRn [] -getLocalDeclBinders new_name (DeprecD _) = returnRn [] -getLocalDeclBinders new_name (DefD _) = returnRn [] -getLocalDeclBinders new_name (InstD _) = returnRn [] -getLocalDeclBinders new_name (RuleD _) = returnRn [] - +getLocalDeclBinders mod rec_exp_fn (FixD _) = returnRn [] +getLocalDeclBinders mod rec_exp_fn (DeprecD _) = returnRn [] +getLocalDeclBinders mod rec_exp_fn (DefD _) = returnRn [] +getLocalDeclBinders mod rec_exp_fn (InstD _) = returnRn [] +getLocalDeclBinders mod rec_exp_fn (RuleD _) = returnRn [] --------------------------- -newLocalName mod rec_exp_fn rdr_name loc - = check_unqual rdr_name loc `thenRn_` +newLocalBinder mod rec_exp_fn (rdr_name, loc) + = -- Generate a local name, and with a suitable export indicator newTopBinder mod rdr_name loc `thenRn` \ name -> - returnRn (setLocalNameSort name (rec_exp_fn name)) - where - -- There should never be a qualified name in a binding position (except in instance decls) - -- The parser doesn't check this because the same parser parses instance decls - check_unqual rdr_name loc - | isUnqual rdr_name = returnRn () - | otherwise = qualNameErr (text "the binding for" <+> quotes (ppr rdr_name)) - (rdr_name,loc) + returnRn (Avail (setLocalNameSort name (rec_exp_fn name))) \end{code} diff --git a/ghc/compiler/rename/RnSource.lhs b/ghc/compiler/rename/RnSource.lhs index 51af082373..693c6000fb 100644 --- a/ghc/compiler/rename/RnSource.lhs +++ b/ghc/compiler/rename/RnSource.lhs @@ -414,6 +414,9 @@ rnClassBinds (ClassDecl _ _ _ _ _ mbinds _ _ ) -- G returnRn (ClassDecl context cname tyvars fds sigs mbinds' names src_loc, meth_fvs) where meth_doc = text "the default-methods for class" <+> ppr cname + +rnClassBinds _ tycl_decl = returnRn (tycl_decl, emptyFVs) + -- Not a class declaration \end{code} |