- where
- cache = hsc_FC hsc_env
- dflags = hsc_dflags hsc_env
-
- -- We've found the module, so the remaining question is
- -- whether it's visible or not
- found :: FinderCacheEntry -> FindResult
- found (loc, Nothing)
- | home_allowed = Found loc HomePackage
- | otherwise = NotFound []
- found (loc, Just (pkg, exposed_mod))
- | explicit && not exposed_mod = ModuleHidden pkg_name
- | explicit && not (exposed pkg) = PackageHidden pkg_name
- | otherwise =
- Found loc (ExtPackage (mkPackageId (package pkg)))
- where
- pkg_name = packageConfigId pkg
-
- found_new entry = do
- addToFinderCache cache name entry
- return $! found entry
-
- not_cached
- | not home_allowed = do
- j <- findPackageModule' dflags name
- case j of
- Ok entry -> found_new entry
- MultiplePackages pkgs -> return (FoundMultiple pkgs)
- CantFindAmongst paths -> return (NotFound paths)
-
- | otherwise = do
- j <- findHomeModule' dflags name
- case j of
- Ok entry -> found_new entry
- MultiplePackages pkgs -> return (FoundMultiple pkgs)
- CantFindAmongst home_files -> do
- r <- findPackageModule' dflags name
- case r of
- CantFindAmongst pkg_files ->
- return (NotFound (home_files ++ pkg_files))
- MultiplePackages pkgs ->
- return (FoundMultiple pkgs)
- Ok entry ->
- found_new entry
-
-addHomeModuleToFinder :: HscEnv -> Module -> ModLocation -> IO ()
-addHomeModuleToFinder hsc_env mod loc
- = addToFinderCache (hsc_FC hsc_env) mod (loc, Nothing)
-
-uncacheModule :: HscEnv -> Module -> IO ()
-uncacheModule hsc_env mod = removeFromFinderCache (hsc_FC hsc_env) mod
+-- -----------------------------------------------------------------------------
+-- Helpers
+
+this `orIfNotFound` or_this = do
+ res <- this
+ case res of
+ NotFound here _ -> do
+ res2 <- or_this
+ case res2 of
+ NotFound or_here pkg -> return (NotFound (here ++ or_here) pkg)
+ _other -> return res2
+ _other -> return res
+
+
+homeSearchCache :: HscEnv -> ModuleName -> IO FindResult -> IO FindResult
+homeSearchCache hsc_env mod_name do_this = do
+ m <- lookupFinderCache (hsc_FC hsc_env) mod_name
+ case m of
+ Just result -> return result
+ Nothing -> do
+ result <- do_this
+ addToFinderCache (hsc_FC hsc_env) mod_name result
+ case result of
+ Found loc mod -> addToModLocationCache (hsc_MLC hsc_env) mod loc
+ _other -> return ()
+ return result
+
+findExposedPackageModule :: HscEnv -> ModuleName -> IO FindResult
+findExposedPackageModule hsc_env mod_name
+ -- not found in any package:
+ | null found = return (NotFound [] Nothing)
+ -- found in just one exposed package:
+ | [(pkg_conf, _)] <- found_exposed
+ = let pkgid = mkPackageId (package pkg_conf) in
+ findPackageModule_ hsc_env (mkModule pkgid mod_name) pkg_conf
+ -- not found in any exposed package, report how it was hidden:
+ | null found_exposed, ((pkg_conf, exposed_mod):_) <- found
+ = let pkgid = mkPackageId (package pkg_conf) in
+ if not (exposed_mod)
+ then return (ModuleHidden pkgid)
+ else return (PackageHidden pkgid)
+ | otherwise
+ = return (FoundMultiple (map (mkPackageId.package.fst) found_exposed))
+ where
+ dflags = hsc_dflags hsc_env
+ found = lookupModuleInAllPackages dflags mod_name
+ found_exposed = filter is_exposed found
+ is_exposed (pkg_conf,exposed_mod) = exposed pkg_conf && exposed_mod
+
+
+modLocationCache :: HscEnv -> Module -> IO FindResult -> IO FindResult
+modLocationCache hsc_env mod do_this = do
+ mb_loc <- lookupModLocationCache mlc mod
+ case mb_loc of
+ Just loc -> return (Found loc mod)
+ Nothing -> do
+ result <- do_this
+ case result of
+ Found loc mod -> addToModLocationCache (hsc_MLC hsc_env) mod loc
+ _other -> return ()
+ return result
+ where
+ mlc = hsc_MLC hsc_env
+
+addHomeModuleToFinder :: HscEnv -> ModuleName -> ModLocation -> IO Module
+addHomeModuleToFinder hsc_env mod_name loc = do
+ let mod = mkModule (thisPackage (hsc_dflags hsc_env)) mod_name
+ addToFinderCache (hsc_FC hsc_env) mod_name (Found loc mod)
+ addToModLocationCache (hsc_MLC hsc_env) mod loc
+ return mod
+
+uncacheModule :: HscEnv -> ModuleName -> IO ()
+uncacheModule hsc_env mod = do
+ let this_pkg = thisPackage (hsc_dflags hsc_env)
+ removeFromFinderCache (hsc_FC hsc_env) mod
+ removeFromModLocationCache (hsc_MLC hsc_env) (mkModule this_pkg mod)