summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMatthew Pickering <matthewtpickering@gmail.com>2022-12-27 10:12:36 +0000
committerMarge Bot <ben+marge-bot@smart-cactus.org>2023-01-24 05:37:52 -0500
commit4fe9eaff11ccf1fe185de2918aef4f96fd200c72 (patch)
tree16d5b2d4047afd65c4a0ba6251ce55f187fd9e4e
parent06cc0a9529f2fe0dfa40d9966a52a982653bfcb9 (diff)
downloadhaskell-4fe9eaff11ccf1fe185de2918aef4f96fd200c72.tar.gz
Key ModSummary cache by UnitId as well as FilePath
Multiple units can refer to the same files without any problem. Just another assumption which needs to be updated when we may have multiple home units. However, there is the invariant that within each unit each file only maps to one module, so as long as we also key the cache by UnitId then we are all good. This led to some confusing behaviour in GHCi when reloading, multipleHomeUnits_shared distils the essence of what can go wrong. Fixes #22679
-rw-r--r--compiler/GHC/Driver/Make.hs19
-rw-r--r--testsuite/tests/driver/multipleHomeUnits/A.hs1
-rw-r--r--testsuite/tests/driver/multipleHomeUnits/all.T5
-rw-r--r--testsuite/tests/driver/multipleHomeUnits/multipleHomeUnits_shared.stderr2
-rw-r--r--testsuite/tests/driver/multipleHomeUnits/shared.script1
-rw-r--r--testsuite/tests/driver/multipleHomeUnits/unitShared11
-rw-r--r--testsuite/tests/driver/multipleHomeUnits/unitShared21
7 files changed, 21 insertions, 9 deletions
diff --git a/compiler/GHC/Driver/Make.hs b/compiler/GHC/Driver/Make.hs
index eee37601f1..0e3348fd45 100644
--- a/compiler/GHC/Driver/Make.hs
+++ b/compiler/GHC/Driver/Make.hs
@@ -1580,11 +1580,13 @@ downsweep hsc_env old_summaries excl_mods allow_dup_roots
logger = hsc_logger hsc_env
roots = hsc_targets hsc_env
- -- A cache from file paths to the already summarised modules.
+ -- A cache from file paths to the already summarised modules. The same file
+ -- can be used in multiple units so the map is also keyed by which unit the
+ -- file was used in.
-- Reuse these if we can because the most expensive part of downsweep is
-- reading the headers.
- old_summary_map :: M.Map FilePath ModSummary
- old_summary_map = M.fromList [(msHsFilePath ms, ms) | ms <- old_summaries]
+ old_summary_map :: M.Map (UnitId, FilePath) ModSummary
+ old_summary_map = M.fromList [((ms_unitid ms, msHsFilePath ms), ms) | ms <- old_summaries]
getRootSummary :: Target -> IO (Either (UnitId, DriverMessages) ModSummary)
getRootSummary Target { targetId = TargetFile file mb_phase
@@ -1966,7 +1968,7 @@ mkRootMap summaries = Map.fromListWith (flip (++))
summariseFile
:: HscEnv
-> HomeUnit
- -> M.Map FilePath ModSummary -- old summaries
+ -> M.Map (UnitId, FilePath) ModSummary -- old summaries
-> FilePath -- source file name
-> Maybe Phase -- start phase
-> Maybe (StringBuffer,UTCTime)
@@ -1974,9 +1976,8 @@ summariseFile
summariseFile hsc_env' home_unit old_summaries src_fn mb_phase maybe_buf
-- we can use a cached summary if one is available and the
- -- source file hasn't changed, But we have to look up the summary
- -- by source file, rather than module name as we do in summarise.
- | Just old_summary <- M.lookup src_fn old_summaries
+ -- source file hasn't changed,
+ | Just old_summary <- M.lookup (homeUnitId home_unit, src_fn) old_summaries
= do
let location = ms_location $ old_summary
@@ -2085,7 +2086,7 @@ data SummariseResult =
summariseModule
:: HscEnv
-> HomeUnit
- -> M.Map FilePath ModSummary
+ -> M.Map (UnitId, FilePath) ModSummary
-- ^ Map of old summaries
-> IsBootInterface -- True <=> a {-# SOURCE #-} import
-> Located ModuleName -- Imported module to be summarised
@@ -2146,7 +2147,7 @@ summariseModule hsc_env' home_unit old_summary_map is_boot (L _ wanted_mod) mb_p
Right ms -> FoundHome ms
new_summary_cache_check loc mod src_fn h
- | Just old_summary <- Map.lookup src_fn old_summary_map =
+ | Just old_summary <- Map.lookup ((toUnitId (moduleUnit mod), src_fn)) old_summary_map =
-- check the hash on the source file, and
-- return the cached summary if it hasn't changed. If the
diff --git a/testsuite/tests/driver/multipleHomeUnits/A.hs b/testsuite/tests/driver/multipleHomeUnits/A.hs
new file mode 100644
index 0000000000..d843c00b78
--- /dev/null
+++ b/testsuite/tests/driver/multipleHomeUnits/A.hs
@@ -0,0 +1 @@
+module A where
diff --git a/testsuite/tests/driver/multipleHomeUnits/all.T b/testsuite/tests/driver/multipleHomeUnits/all.T
index ebee7b9f5d..d289a447a6 100644
--- a/testsuite/tests/driver/multipleHomeUnits/all.T
+++ b/testsuite/tests/driver/multipleHomeUnits/all.T
@@ -66,5 +66,10 @@ test('multipleHomeUnits_recomp', [copy_files,extra_files([ 'Recomp.hs', 'unitRec
test('multipleHomeUnits_recomp_th', [filter_stdout_lines(r'.*Compiling.*'), copy_files, extra_files(['thRecomp.script', 'unitRecompTH', 'unitDep', 'RecompTH.hs', 'Dep.hs', '../../ghci/shell.hs']) , extra_run_opts('-v1 -unit @unitRecompTH -unit @unitDep')], ghci_script, ['thRecomp.script'])
+test('multipleHomeUnits_shared', [extra_files([ 'A.hs', 'unitShared1', 'unitShared2'])], multiunit_compile, [['unitShared1', 'unitShared2'], '-fhide-source-paths'])
+
+test('multipleHomeUnits_shared_ghci', [extra_files([ 'shared.script', 'A.hs', 'unitShared1', 'unitShared2']), extra_run_opts('-unit @unitShared1 -unit @unitShared2')], ghci_script, ['shared.script'])
+
+
diff --git a/testsuite/tests/driver/multipleHomeUnits/multipleHomeUnits_shared.stderr b/testsuite/tests/driver/multipleHomeUnits/multipleHomeUnits_shared.stderr
new file mode 100644
index 0000000000..172ab096f1
--- /dev/null
+++ b/testsuite/tests/driver/multipleHomeUnits/multipleHomeUnits_shared.stderr
@@ -0,0 +1,2 @@
+[1 of 2] Compiling A[shared1]
+[2 of 2] Compiling A[shared2]
diff --git a/testsuite/tests/driver/multipleHomeUnits/shared.script b/testsuite/tests/driver/multipleHomeUnits/shared.script
new file mode 100644
index 0000000000..38963a94f7
--- /dev/null
+++ b/testsuite/tests/driver/multipleHomeUnits/shared.script
@@ -0,0 +1 @@
+:r
diff --git a/testsuite/tests/driver/multipleHomeUnits/unitShared1 b/testsuite/tests/driver/multipleHomeUnits/unitShared1
new file mode 100644
index 0000000000..3266a7c2a4
--- /dev/null
+++ b/testsuite/tests/driver/multipleHomeUnits/unitShared1
@@ -0,0 +1 @@
+-i A -this-unit-id shared1
diff --git a/testsuite/tests/driver/multipleHomeUnits/unitShared2 b/testsuite/tests/driver/multipleHomeUnits/unitShared2
new file mode 100644
index 0000000000..75e32ae633
--- /dev/null
+++ b/testsuite/tests/driver/multipleHomeUnits/unitShared2
@@ -0,0 +1 @@
+-i A -this-unit-id shared2