[project @ 2000-10-25 13:51:50 by simonpj]
[ghc-hetmet.git] / ghc / compiler / basicTypes / Module.lhs
1 %
2 % (c) The GRASP/AQUA Project, Glasgow University, 1992-1998
3 %
4 \section[Module]{The @Module@ module.}
5
6 Representing modules and their flavours.
7
8
9 Notes on DLLs
10 ~~~~~~~~~~~~~
11 When compiling module A, which imports module B, we need to 
12 know whether B will be in the same DLL as A.  
13         If it's in the same DLL, we refer to B_f_closure
14         If it isn't, we refer to _imp__B_f_closure
15 When compiling A, we record in B's Module value whether it's
16 in a different DLL, by setting the DLL flag.
17
18
19
20
21 \begin{code}
22 module Module 
23     (
24       Module, moduleName
25                             -- abstract, instance of Eq, Ord, Outputable
26     , ModuleName
27     , isModuleInThisPackage, mkModuleInThisPackage
28
29     , moduleNameString          -- :: ModuleName -> EncodedString
30     , moduleNameUserString      -- :: ModuleName -> UserString
31     , moduleNameFS              -- :: ModuleName -> EncodedFS
32
33     , moduleString              -- :: Module -> EncodedString
34     , moduleUserString          -- :: Module -> UserString
35     , moduleName                -- :: Module -> ModuleName
36
37     , mkVanillaModule           -- :: ModuleName -> Module
38     , mkPrelModule              -- :: UserString -> Module
39     , mkModule                  -- :: ModuleName -> PackageName -> Module
40     , mkHomeModule              -- :: ModuleName -> Module
41
42 --    , mkSrcModule
43
44     , mkModuleName              -- :: UserString -> ModuleName
45     , mkModuleNameFS            -- :: UserFS    -> ModuleName
46     , mkSysModuleNameFS         -- :: EncodedFS -> ModuleName
47
48     , pprModule,
49  
50     , PackageName
51
52         -- Where to find a .hi file
53     , WhereFrom(..)
54
55     , ModuleEnv,
56     , elemModuleEnv, extendModuleEnv, extendModuleEnvList, plusModuleEnv_C
57     , delModuleEnvList, delModuleEnv, plusModuleEnv, lookupModuleEnv
58     , lookupWithDefaultModuleEnv, mapModuleEnv, mkModuleEnv, emptyModuleEnv
59     , moduleEnvElts, unitModuleEnv, isEmptyModuleEnv, foldModuleEnv
60     , lookupModuleEnvByName, extendModuleEnv_C
61
62     ) where
63
64 #include "HsVersions.h"
65 import OccName
66 import Outputable
67 import CmdLineOpts      ( opt_InPackage )
68 import FastString       ( FastString, uniqueOfFS )
69 import Unique           ( Uniquable(..), mkUniqueGrimily )
70 import UniqFM
71 \end{code}
72
73
74 %************************************************************************
75 %*                                                                      *
76 \subsection{Interface file flavour}
77 %*                                                                      *
78 %************************************************************************
79
80 A further twist to the tale is the support for dynamically linked
81 libraries under Win32. Here, dealing with the use of global variables
82 that's residing in a DLL requires special handling at the point of use
83 (there's an extra level of indirection, i.e., (**v) to get at v's
84 value, rather than just (*v) .) When slurping in an interface file we
85 then record whether it's coming from a .hi corresponding to a module
86 that's packaged up in a DLL or not, so that we later can emit the
87 appropriate code.
88
89 The logic for how an interface file is marked as corresponding to a
90 module that's hiding in a DLL is explained elsewhere (ToDo: give
91 renamer href here.)
92
93 \begin{code}
94 data Module = Module ModuleName PackageInfo
95
96 data PackageInfo 
97   = ThisPackage                         -- A module from the same package 
98                                         -- as the one being compiled
99   | AnotherPackage PackageName          -- A module from a different package
100
101 type PackageName = FastString           -- No encoding at all
102
103 preludePackage :: PackageName
104 preludePackage = SLIT("std")
105
106 instance Outputable PackageInfo where
107         -- Just used in debug prints of lex tokens and in debug modde
108    ppr ThisPackage        = ptext SLIT("<THIS>")
109    ppr (AnotherPackage p) = ptext p
110 \end{code}
111
112
113 %************************************************************************
114 %*                                                                      *
115 \subsection{Where from}
116 %*                                                                      *
117 %************************************************************************
118
119 The @WhereFrom@ type controls where the renamer looks for an interface file
120
121 \begin{code}
122 data WhereFrom = ImportByUser           -- Ordinary user import: look for M.hi
123                | ImportByUserSource     -- User {- SOURCE -}: look for M.hi-boot
124                | ImportBySystem         -- Non user import.  Look for M.hi if M is in
125                                         -- the module this module depends on, or is a system-ish module; 
126                                         -- M.hi-boot otherwise
127
128 instance Outputable WhereFrom where
129   ppr ImportByUser       = empty
130   ppr ImportByUserSource = ptext SLIT("{- SOURCE -}")
131   ppr ImportBySystem     = ptext SLIT("{- SYSTEM IMPORT -}")
132 \end{code}
133
134
135 %************************************************************************
136 %*                                                                      *
137 \subsection{The name of a module}
138 %*                                                                      *
139 %************************************************************************
140
141 \begin{code}
142 newtype ModuleName = ModuleName EncodedFS
143         -- Haskell module names can include the quote character ',
144         -- so the module names have the z-encoding applied to them
145
146 instance Uniquable ModuleName where
147   getUnique (ModuleName nm) = mkUniqueGrimily (uniqueOfFS nm)
148
149 instance Eq ModuleName where
150   nm1 == nm2 = getUnique nm1 == getUnique nm2
151
152 -- Warning: gives an ordering relation based on the uniques of the
153 -- FastStrings which are the (encoded) module names.  This is _not_
154 -- a lexicographical ordering.
155 instance Ord ModuleName where
156   nm1 `compare` nm2 = getUnique nm1 `compare` getUnique nm2
157
158 instance Outputable ModuleName where
159   ppr = pprModuleName
160
161
162 pprModuleName :: ModuleName -> SDoc
163 pprModuleName (ModuleName nm) = pprEncodedFS nm
164
165 moduleNameFS :: ModuleName -> EncodedFS
166 moduleNameFS (ModuleName mod) = mod
167
168 moduleNameString :: ModuleName -> EncodedString
169 moduleNameString (ModuleName mod) = _UNPK_ mod
170
171 moduleNameUserString :: ModuleName -> UserString
172 moduleNameUserString (ModuleName mod) = decode (_UNPK_ mod)
173
174 -- used to be called mkSrcModule
175 mkModuleName :: UserString -> ModuleName
176 mkModuleName s = ModuleName (_PK_ (encode s))
177
178 -- used to be called mkSrcModuleFS
179 mkModuleNameFS :: UserFS -> ModuleName
180 mkModuleNameFS s = ModuleName (encodeFS s)
181
182 -- used to be called mkSysModuleFS
183 mkSysModuleNameFS :: EncodedFS -> ModuleName
184 mkSysModuleNameFS s = ModuleName s 
185
186 -- Make a module in this package
187 mkModuleInThisPackage :: ModuleName -> Module
188 mkModuleInThisPackage nm = Module nm ThisPackage
189 \end{code}
190
191 \begin{code}
192 instance Outputable Module where
193   ppr = pprModule
194
195 instance Uniquable Module where
196   getUnique (Module nm _) = getUnique nm
197
198 -- Same if they have the same name.
199 instance Eq Module where
200   m1 == m2 = getUnique m1 == getUnique m2
201
202 -- Warning: gives an ordering relation based on the uniques of the
203 -- FastStrings which are the (encoded) module names.  This is _not_
204 -- a lexicographical ordering.
205 instance Ord Module where
206   m1 `compare` m2 = getUnique m1 `compare` getUnique m2
207 \end{code}
208
209
210 \begin{code}
211 pprModule :: Module -> SDoc
212 pprModule (Module mod p) = getPprStyle $ \ sty ->
213                            if debugStyle sty then
214                                 -- Print the package too
215                                 ppr p <> dot <> pprModuleName mod
216                            else
217                                 pprModuleName mod
218 \end{code}
219
220
221 \begin{code}
222 mkModule :: ModuleName  -- Name of the module
223          -> PackageName
224          -> Module
225 mkModule mod_nm pack_name
226   = Module mod_nm pack_info
227   where
228     pack_info | pack_name == opt_InPackage = ThisPackage
229               | otherwise                  = AnotherPackage pack_name
230
231 mkHomeModule :: ModuleName -> Module
232 mkHomeModule mod_nm = Module mod_nm ThisPackage
233
234 -- Used temporarily when we first come across Foo.x in an interface
235 -- file, but before we've opened Foo.hi.
236 -- (Until we've opened Foo.hi we don't know what the PackageInfo is.)
237 mkVanillaModule :: ModuleName -> Module
238 mkVanillaModule name = mkModule name (panic "mkVanillaModule:unknown mod_kind field")
239
240 mkPrelModule :: ModuleName -> Module
241 mkPrelModule name = mkModule name preludePackage
242
243 moduleString :: Module -> EncodedString
244 moduleString (Module (ModuleName fs) _) = _UNPK_ fs
245
246 moduleName :: Module -> ModuleName
247 moduleName (Module mod _) = mod
248
249 moduleUserString :: Module -> UserString
250 moduleUserString (Module mod _) = moduleNameUserString mod
251
252 isModuleInThisPackage :: Module -> Bool
253 isModuleInThisPackage (Module nm ThisPackage) = True
254 isModuleInThisPackage _                       = False
255 \end{code}
256
257 %************************************************************************
258 %*                                                                      *
259 \subsection{@ModuleEnv@s}
260 %*                                                                      *
261 %************************************************************************
262
263 \begin{code}
264 type ModuleEnv elt = UniqFM elt
265
266 emptyModuleEnv       :: ModuleEnv a
267 mkModuleEnv          :: [(Module, a)] -> ModuleEnv a
268 unitModuleEnv        :: Module -> a -> ModuleEnv a
269 extendModuleEnv      :: ModuleEnv a -> Module -> a -> ModuleEnv a
270 extendModuleEnv_C    :: (a->a->a) -> ModuleEnv a -> Module -> a -> ModuleEnv a
271 plusModuleEnv        :: ModuleEnv a -> ModuleEnv a -> ModuleEnv a
272 extendModuleEnvList  :: ModuleEnv a -> [(Module, a)] -> ModuleEnv a
273                   
274 delModuleEnvList     :: ModuleEnv a -> [Module] -> ModuleEnv a
275 delModuleEnv         :: ModuleEnv a -> Module -> ModuleEnv a
276 plusModuleEnv_C      :: (a -> a -> a) -> ModuleEnv a -> ModuleEnv a -> ModuleEnv a
277 mapModuleEnv         :: (a -> b) -> ModuleEnv a -> ModuleEnv b
278 moduleEnvElts        :: ModuleEnv a -> [a]
279                   
280 isEmptyModuleEnv     :: ModuleEnv a -> Bool
281 lookupModuleEnv      :: ModuleEnv a -> Module     -> Maybe a
282 lookupModuleEnvByName:: ModuleEnv a -> ModuleName -> Maybe a
283 lookupWithDefaultModuleEnv :: ModuleEnv a -> a -> Module -> a
284 elemModuleEnv        :: Module -> ModuleEnv a -> Bool
285 foldModuleEnv        :: (a -> b -> b) -> b -> ModuleEnv a -> b
286
287 elemModuleEnv       = elemUFM
288 extendModuleEnv     = addToUFM
289 extendModuleEnv_C   = addToUFM_C
290 extendModuleEnvList = addListToUFM
291 plusModuleEnv_C     = plusUFM_C
292 delModuleEnvList    = delListFromUFM
293 delModuleEnv        = delFromUFM
294 plusModuleEnv       = plusUFM
295 lookupModuleEnv     = lookupUFM
296 lookupModuleEnvByName = lookupUFM
297 lookupWithDefaultModuleEnv = lookupWithDefaultUFM
298 mapModuleEnv        = mapUFM
299 mkModuleEnv         = listToUFM
300 emptyModuleEnv      = emptyUFM
301 moduleEnvElts       = eltsUFM
302 unitModuleEnv       = unitUFM
303 isEmptyModuleEnv    = isNullUFM
304 foldModuleEnv       = foldUFM
305 \end{code}