| ... |
... |
@@ -78,10 +78,11 @@ import GHC.Types.Unique.Set |
|
78
|
78
|
import qualified Data.List as L(sort)
|
|
79
|
79
|
import Data.List.NonEmpty ( NonEmpty (..) )
|
|
80
|
80
|
import Data.Set (Set)
|
|
81
|
|
-import qualified Data.Set as Set (empty, intersection, difference, null, toList)
|
|
|
81
|
+import qualified Data.Set as Set (empty, intersection, difference, null, toList, member)
|
|
82
|
82
|
import qualified System.Directory as SD
|
|
83
|
83
|
import qualified System.OsPath as OsPath
|
|
84
|
84
|
import qualified Data.List.NonEmpty as NE
|
|
|
85
|
+import GHC.Iface.Errors.Types
|
|
85
|
86
|
|
|
86
|
87
|
type FileExt = OsString -- Filename extension
|
|
87
|
88
|
type BaseName = OsPath -- Basename of file
|
| ... |
... |
@@ -247,8 +248,12 @@ findImportedModuleNoHsc fc fopts ue home_module_name_providers_map mb_home_unit |
|
247
|
248
|
ue_findHomeUnitEnv home_unit_id ue
|
|
248
|
249
|
|
|
249
|
250
|
other_fopts :: [(UnitId, FinderOpts)]
|
|
250
|
|
- other_fopts = homeUnitDepsFinderOpts ue home_module_name_providers_map
|
|
|
251
|
+ other_fopts =
|
|
|
252
|
+ let
|
|
|
253
|
+ (providers, others) = homeUnitDepsFinderOpts ue home_module_name_providers_map
|
|
251
|
254
|
unit_state mod_name
|
|
|
255
|
+ in
|
|
|
256
|
+ providers ++ others
|
|
252
|
257
|
|
|
253
|
258
|
-- | Locate a plugin module requested by the user, for a compiler
|
|
254
|
259
|
-- plugin. This consults the same set of exposed packages as
|
| ... |
... |
@@ -263,11 +268,17 @@ findPluginModuleNoHsc |
|
263
|
268
|
-> ModuleName
|
|
264
|
269
|
-> IO FindResult
|
|
265
|
270
|
findPluginModuleNoHsc fc fopts ue home_module_name_providers_map mb_home_unit@(Just home_unit) mod_name =
|
|
266
|
|
- findHomeModuleAmongDeps fc fopts ue home_module_name_providers_map
|
|
267
|
|
- mb_home_unit mod_name
|
|
|
271
|
+ home_import
|
|
268
|
272
|
`orIfNotFound`
|
|
269
|
|
- findExposedPluginPackageModule fc fopts unit_state mod_name
|
|
|
273
|
+ (findHomeModuleAmongDeps fc ue home_module_name_providers_map
|
|
|
274
|
+ mb_home_unit mod_name
|
|
|
275
|
+ `combineFindResult`
|
|
|
276
|
+ findExposedPluginPackageModule fc fopts unit_state mod_name
|
|
|
277
|
+ )
|
|
270
|
278
|
where
|
|
|
279
|
+ home_import =
|
|
|
280
|
+ findHomeModule fc fopts home_unit mod_name
|
|
|
281
|
+
|
|
271
|
282
|
unit_state = HUG.homeUnitEnv_units $
|
|
272
|
283
|
ue_findHomeUnitEnv (homeUnitId home_unit) ue
|
|
273
|
284
|
findPluginModuleNoHsc fc fopts ue _ Nothing mod_name =
|
| ... |
... |
@@ -291,9 +302,9 @@ findPluginModule hsc_env mod_name = do |
|
291
|
302
|
rankedHomeUnitDeps :: HomeModuleNameProvidersMap
|
|
292
|
303
|
-> ModuleName
|
|
293
|
304
|
-> Set UnitId
|
|
294
|
|
- -> [UnitId]
|
|
|
305
|
+ -> ([UnitId], [UnitId])
|
|
295
|
306
|
rankedHomeUnitDeps _ _ home_unit_deps | Set.null home_unit_deps
|
|
296
|
|
- = []
|
|
|
307
|
+ = ([], [])
|
|
297
|
308
|
-- The special handling of the situation where the dependency set is empty does
|
|
298
|
309
|
-- not change the result, but it avoids triggering evaluation of the module
|
|
299
|
310
|
-- graph. This is particularly important in one-shot mode, where the module
|
| ... |
... |
@@ -309,7 +320,7 @@ rankedHomeUnitDeps _ _ home_unit_deps | Set.null home_unit_deps |
|
309
|
320
|
-- 3 | import {-# source #-} A
|
|
310
|
321
|
-- | ^^^^^^^^^^^^^^^^^^^^^^^
|
|
311
|
322
|
rankedHomeUnitDeps home_module_name_providers_map mod_name home_unit_deps
|
|
312
|
|
- = Set.toList cached_deps ++ Set.toList uncached_deps
|
|
|
323
|
+ = (Set.toList cached_deps, Set.toList uncached_deps)
|
|
313
|
324
|
where
|
|
314
|
325
|
|
|
315
|
326
|
cached_providers :: Set UnitId
|
| ... |
... |
@@ -330,12 +341,19 @@ homeUnitDepsFinderOpts |
|
330
|
341
|
-> HomeModuleNameProvidersMap
|
|
331
|
342
|
-> UnitState -- ^ unit state of the requesting home unit
|
|
332
|
343
|
-> ModuleName
|
|
333
|
|
- -> [(UnitId, FinderOpts)]
|
|
|
344
|
+ -> ([(UnitId, FinderOpts)], [(UnitId, FinderOpts)])
|
|
334
|
345
|
homeUnitDepsFinderOpts ue home_module_name_providers_map unit_state mod_name =
|
|
335
|
|
- [ (uid, initFinderOpts (ue_unitFlags uid ue))
|
|
336
|
|
- | uid <- rankedHomeUnitDeps home_module_name_providers_map mod_name
|
|
|
346
|
+ let
|
|
|
347
|
+ (providers, otherHomeUnits) = rankedHomeUnitDeps home_module_name_providers_map mod_name
|
|
337
|
348
|
(homeUnitDepends unit_state)
|
|
338
|
|
- ]
|
|
|
349
|
+ in
|
|
|
350
|
+ ( [ (uid, initFinderOpts (ue_unitFlags uid ue))
|
|
|
351
|
+ | uid <- providers
|
|
|
352
|
+ ]
|
|
|
353
|
+ , [ (uid, initFinderOpts (ue_unitFlags uid ue))
|
|
|
354
|
+ | uid <- otherHomeUnits
|
|
|
355
|
+ ]
|
|
|
356
|
+ )
|
|
339
|
357
|
|
|
340
|
358
|
-- | Search for @mod_name@ in the given home unit.
|
|
341
|
359
|
findHomeUnitDepModule
|
| ... |
... |
@@ -364,30 +382,29 @@ findHomeUnitDepModule fc ue home_module_name_providers_map mod_name (uid, opts) |
|
364
|
382
|
-- successful result.
|
|
365
|
383
|
findHomeModuleAmongDeps
|
|
366
|
384
|
:: FinderCache
|
|
367
|
|
- -> FinderOpts
|
|
368
|
385
|
-> UnitEnv
|
|
369
|
386
|
-> HomeModuleNameProvidersMap
|
|
370
|
387
|
-> Maybe HomeUnit
|
|
371
|
388
|
-> ModuleName
|
|
372
|
389
|
-> IO FindResult
|
|
373
|
|
-findHomeModuleAmongDeps fc fopts ue home_module_name_providers_map mb_home_unit mod_name =
|
|
374
|
|
- foldr1 orIfNotFound (home_import :| map home_pkg_import other_fopts)
|
|
375
|
|
- -- Do not try to be smart and change this to `foldr orIfNotFound home_import
|
|
376
|
|
- -- (map home_pkg_import other_fopts)`, as that would not be the same.
|
|
377
|
|
- -- `home_import` is first because we need to first look within the current
|
|
378
|
|
- -- unit before looking at the other units in order.
|
|
|
390
|
+findHomeModuleAmongDeps fc ue home_module_name_providers_map mb_home_unit mod_name =
|
|
|
391
|
+ findInDirectDeps `orIfNotFound` findInOtherDeps
|
|
379
|
392
|
where
|
|
380
|
|
- home_import = case mb_home_unit of
|
|
381
|
|
- Just home_unit -> findHomeModule fc fopts home_unit mod_name
|
|
382
|
|
- Nothing -> pure $
|
|
383
|
|
- NoPackage (panic "findHomeModuleAmongDeps: no home-unit")
|
|
|
393
|
+ findInDirectDeps = case provider_fopts of
|
|
|
394
|
+ p:ps -> foldr1 combineFindResult (home_pkg_import p :| map home_pkg_import ps)
|
|
|
395
|
+ [] -> pure notFound
|
|
|
396
|
+
|
|
|
397
|
+ findInOtherDeps = case other_fopts of
|
|
|
398
|
+ p:ps -> foldr1 orIfNotFound (home_pkg_import p :| map home_pkg_import ps)
|
|
|
399
|
+ [] -> pure notFound
|
|
|
400
|
+
|
|
384
|
401
|
home_pkg_import = findHomeUnitDepModule fc ue home_module_name_providers_map mod_name
|
|
385
|
402
|
|
|
386
|
403
|
unit_state = case homeUnitId <$> mb_home_unit of
|
|
387
|
404
|
Nothing -> ue_homeUnitState ue
|
|
388
|
405
|
Just home_unit_id -> HUG.homeUnitEnv_units $
|
|
389
|
406
|
ue_findHomeUnitEnv home_unit_id ue
|
|
390
|
|
- other_fopts = homeUnitDepsFinderOpts ue home_module_name_providers_map
|
|
|
407
|
+ (provider_fopts, other_fopts) = homeUnitDepsFinderOpts ue home_module_name_providers_map
|
|
391
|
408
|
unit_state mod_name
|
|
392
|
409
|
|
|
393
|
410
|
-- | Search the home-unit graph and otherwise the regular exposed package
|
| ... |
... |
@@ -401,10 +418,17 @@ findHomeOrRegularPackageModule |
|
401
|
418
|
-> ModuleName
|
|
402
|
419
|
-> IO FindResult
|
|
403
|
420
|
findHomeOrRegularPackageModule fc fopts ue home_module_name_providers_map mb_home_unit mod_name =
|
|
404
|
|
- findHomeModuleAmongDeps fc fopts ue home_module_name_providers_map
|
|
405
|
|
- mb_home_unit mod_name
|
|
406
|
|
- `orIfNotFound`
|
|
407
|
|
- findExposedPackageModule fc fopts unit_state mod_name NoPkgQual
|
|
|
421
|
+ case mb_home_unit of
|
|
|
422
|
+ Just home_unit ->
|
|
|
423
|
+ findHomeModule fc fopts home_unit mod_name
|
|
|
424
|
+ `orIfNotFound`
|
|
|
425
|
+ (findHomeModuleAmongDeps fc ue home_module_name_providers_map
|
|
|
426
|
+ mb_home_unit mod_name
|
|
|
427
|
+ `combineFindResult`
|
|
|
428
|
+ findExposedPackageModule fc fopts unit_state mod_name NoPkgQual
|
|
|
429
|
+ )
|
|
|
430
|
+ Nothing ->
|
|
|
431
|
+ findExposedPackageModule fc fopts unit_state mod_name NoPkgQual
|
|
408
|
432
|
where
|
|
409
|
433
|
unit_state = case homeUnitId <$> mb_home_unit of
|
|
410
|
434
|
Nothing -> ue_homeUnitState ue
|
| ... |
... |
@@ -470,6 +494,40 @@ orIfNotFound this or_this = do |
|
470
|
494
|
_other -> return res2
|
|
471
|
495
|
_other -> return res
|
|
472
|
496
|
|
|
|
497
|
+combineFindResult :: Monad m => m FindResult -> m FindResult -> m FindResult
|
|
|
498
|
+combineFindResult this or_this = do
|
|
|
499
|
+ res <- this
|
|
|
500
|
+ case res of
|
|
|
501
|
+ NotFound { fr_paths = paths1, fr_mods_hidden = mh1
|
|
|
502
|
+ , fr_pkgs_hidden = ph1, fr_unusables = u1, fr_suggestions = s1 }
|
|
|
503
|
+ -> do res2 <- or_this
|
|
|
504
|
+ case res2 of
|
|
|
505
|
+ NotFound { fr_paths = paths2, fr_pkg = mb_pkg2, fr_mods_hidden = mh2
|
|
|
506
|
+ , fr_pkgs_hidden = ph2, fr_unusables = u2
|
|
|
507
|
+ , fr_suggestions = s2 }
|
|
|
508
|
+ -> return (NotFound { fr_paths = paths1 ++ paths2
|
|
|
509
|
+ , fr_pkg = mb_pkg2 -- snd arg is the package search
|
|
|
510
|
+ , fr_mods_hidden = mh1 ++ mh2
|
|
|
511
|
+ , fr_pkgs_hidden = ph1 ++ ph2
|
|
|
512
|
+ , fr_unusables = u1 ++ u2
|
|
|
513
|
+ , fr_suggestions = s1 ++ s2 })
|
|
|
514
|
+ _other -> return res2
|
|
|
515
|
+ NoPackage{} -> pure res
|
|
|
516
|
+ FoundMultiple ms -> do
|
|
|
517
|
+ otherRes <- or_this
|
|
|
518
|
+ case otherRes of
|
|
|
519
|
+ Found _ other_mod -> pure $ FoundMultiple $ ms ++ [(other_mod, HomeOrigin)]
|
|
|
520
|
+ NoPackage{} -> pure res
|
|
|
521
|
+ FoundMultiple other_ms -> pure $ FoundMultiple $ ms ++ other_ms
|
|
|
522
|
+ NotFound{} -> pure res
|
|
|
523
|
+ Found _mod_location modl -> do
|
|
|
524
|
+ otherRes <- or_this
|
|
|
525
|
+ case otherRes of
|
|
|
526
|
+ Found _ other_mod -> pure $ FoundMultiple $ [(modl, HomeOrigin), (other_mod, HomeOrigin)]
|
|
|
527
|
+ NoPackage{} -> pure res
|
|
|
528
|
+ FoundMultiple other_ms -> pure $ FoundMultiple $ [(modl, HomeOrigin)] ++ other_ms
|
|
|
529
|
+ NotFound{} -> pure res
|
|
|
530
|
+
|
|
473
|
531
|
-- | Helper function for 'findHomeModule': this function wraps an IO action
|
|
474
|
532
|
-- which would look up @mod_name@ in the file system (the home package),
|
|
475
|
533
|
-- and first consults the 'hsc_FC' cache to see if the lookup has already
|
| ... |
... |
@@ -483,8 +541,12 @@ homeSearchCache fc home_unit mod_name do_this = do |
|
483
|
541
|
|
|
484
|
542
|
findExposedPackageModule :: FinderCache -> FinderOpts -> UnitState -> ModuleName -> PkgQual -> IO FindResult
|
|
485
|
543
|
findExposedPackageModule fc fopts units mod_name mb_pkg =
|
|
486
|
|
- findLookupResult fc fopts
|
|
487
|
|
- $ lookupModuleWithSuggestions units mod_name mb_pkg
|
|
|
544
|
+ findLookupResult fc fopts $
|
|
|
545
|
+ case lookupModuleWithSuggestions units mod_name mb_pkg of
|
|
|
546
|
+ lf@(LookupFound _ (u, _))
|
|
|
547
|
+ | unitId u `Set.member` homeUnitDepends units -> LookupNotFound []
|
|
|
548
|
+ | otherwise -> lf
|
|
|
549
|
+ other -> other
|
|
488
|
550
|
|
|
489
|
551
|
findExposedPluginPackageModule :: FinderCache -> FinderOpts -> UnitState -> ModuleName -> IO FindResult
|
|
490
|
552
|
findExposedPluginPackageModule fc fopts units mod_name =
|
| ... |
... |
@@ -509,7 +571,7 @@ findLookupResult fc fopts r = case r of |
|
509
|
571
|
, fr_unusables = []
|
|
510
|
572
|
, fr_suggestions = []})
|
|
511
|
573
|
LookupMultiple rs ->
|
|
512
|
|
- return (FoundMultiple rs)
|
|
|
574
|
+ return (FoundMultiple $ map (\ (m, o) -> (m, ExternalUnitOrigin o)) rs)
|
|
513
|
575
|
LookupHidden fr_pkgs_hidden mod_hiddens ->
|
|
514
|
576
|
return (NotFound{ fr_paths = [], fr_pkg = Nothing
|
|
515
|
577
|
, fr_pkgs_hidden
|
| ... |
... |
@@ -588,6 +650,15 @@ mkHomeHidden uid = |
|
588
|
650
|
, fr_unusables = []
|
|
589
|
651
|
, fr_suggestions = []}
|
|
590
|
652
|
|
|
|
653
|
+notFound =
|
|
|
654
|
+ NotFound { fr_paths = []
|
|
|
655
|
+ , fr_pkg = Nothing
|
|
|
656
|
+ , fr_mods_hidden = []
|
|
|
657
|
+ , fr_pkgs_hidden = []
|
|
|
658
|
+ , fr_unusables = []
|
|
|
659
|
+ , fr_suggestions = []}
|
|
|
660
|
+
|
|
|
661
|
+
|
|
591
|
662
|
findHomePackageModule :: FinderCache -> FinderOpts -> UnitId -> ModuleName -> IO FindResult
|
|
592
|
663
|
findHomePackageModule fc fopts home_unit mod_name = do
|
|
593
|
664
|
let uid = RealUnit (Definite home_unit)
|